Merging changes from CHIMERA_M1_0_1_BRANCH.

This commit is contained in:
bryner%netscape.com 2003-01-08 06:33:05 +00:00
Родитель 41dc25b8ff
Коммит b434ea0790
132 изменённых файлов: 5507 добавлений и 4686 удалений

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -3,7 +3,7 @@
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>646 106 458 263 0 0 1600 1002 </string>
<string>674 107 458 263 0 0 1600 1002 </string>
<key>IBEditorPositions</key>
<dict>
<key>214</key>
@ -12,6 +12,6 @@
<key>IBFramework Version</key>
<string>286.0</string>
<key>IBSystem Version</key>
<string>6D52</string>
<string>6G30</string>
</dict>
</plist>

Двоичные данные
camino/PreferencePanes/Appearance/English.lproj/Appearance.nib/objects.nib сгенерированный

Двоичный файл не отображается.

Просмотреть файл

@ -17,11 +17,7 @@
</dict>
<key>IBLastGroupID</key>
<string>8</string>
<key>IBOpenObjects</key>
<array>
<integer>5</integer>
</array>
<key>IBSystem Version</key>
<string>6F21</string>
<string>6G30</string>
</dict>
</plist>

Двоичные данные
camino/PreferencePanes/Navigation/English.lproj/Navigation.nib/objects.nib сгенерированный

Двоичный файл не отображается.

Двоичные данные
camino/resources/images/app/disclosureArrowDown.tiff Normal file

Двоичный файл не отображается.

Двоичные данные
camino/resources/images/app/disclosureArrowRight.tiff Normal file

Двоичный файл не отображается.

Просмотреть файл

Просмотреть файл

@ -68,6 +68,7 @@
closeCurrentTab = id;
closeOtherTabs = id;
closeSendersTab = id;
copyImage = id;
copyImageLocation = id;
copyLinkLocation = id;
endAddBookmarkSheet = id;
@ -80,6 +81,7 @@
goToLocationFromToolbarURLField = id;
home = id;
manageBookmarks = id;
manageHistory = id;
moveTabToNewWindow = id;
newTab = id;
nextTab = id;

Просмотреть файл

@ -3,7 +3,7 @@
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>66 21 653 383 0 0 1152 848 </string>
<string>65 36 653 383 0 0 1152 848 </string>
<key>IBEditorPositions</key>
<dict>
<key>124</key>
@ -15,17 +15,17 @@
<key>297</key>
<string>107 466 213 294 0 0 1600 1002 </string>
<key>314</key>
<string>73 542 213 132 0 0 1600 1002 </string>
<string>72 544 213 150 0 0 1600 1002 </string>
<key>336</key>
<string>486 756 213 180 0 0 1600 1002 </string>
<key>365</key>
<string>31 719 93 162 0 0 1600 1002 </string>
<key>463</key>
<string>97 693 213 246 0 0 1600 1002 </string>
<string>349 487 213 246 0 0 1600 1002 </string>
<key>56</key>
<string>450 634 343 68 0 0 1280 1002 </string>
<key>654</key>
<string>206 785 198 144 0 0 1600 1002 </string>
<string>140 644 198 144 0 0 1152 848 </string>
</dict>
<key>IBFramework Version</key>
<string>286.0</string>
@ -42,6 +42,6 @@
<key>IBLockedObjects</key>
<array/>
<key>IBSystem Version</key>
<string>6F21</string>
<string>6G30</string>
</dict>
</plist>

Двоичные данные
camino/resources/localized/English.lproj/BrowserWindow.nib/objects.nib сгенерированный

Двоичный файл не отображается.

14
camino/resources/localized/English.lproj/Keychain.nib/classes.nib сгенерированный Normal file
Просмотреть файл

@ -0,0 +1,14 @@
{
IBClasses = (
{CLASS = FirstResponder; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{CLASS = KeychainBrowserListener; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{
ACTIONS = {hitButtonCancel = id; hitButtonOK = id; hitButtonOther = id; shutdown = id; };
CLASS = KeychainService;
LANGUAGE = ObjC;
OUTLETS = {confirmChangePasswordPanel = id; confirmStorePasswordPanel = id; };
SUPERCLASS = NSObject;
}
);
IBVersion = 1;
}

12
camino/resources/localized/English.lproj/Keychain.nib/info.nib сгенерированный Normal file
Просмотреть файл

@ -0,0 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>240 146 356 240 0 0 1024 746 </string>
<key>IBFramework Version</key>
<string>283.0</string>
<key>IBSystem Version</key>
<string>6F21</string>
</dict>
</plist>

0
camino/resources/localized/English.lproj/Keychain.nib/objects.nib сгенерированный Normal file
Просмотреть файл

Двоичный файл не отображается.

Просмотреть файл

@ -20,6 +20,7 @@
doReload = id;
doSearch = id;
doStop = id;
downloadsWindow = id;
exportBookmarks = id;
feedbackLink = id;
findAgain = id;
@ -61,7 +62,6 @@
mCreateBookmarksFolderMenuItem = NSMenuItem;
mCreateBookmarksSeparatorMenuItem = NSMenuItem;
mDockMenu = NSMenu;
mFilterList = NSPopUpButton;
mFilterView = NSView;
mGoMenu = NSMenu;
mServersSubmenu = NSMenu;

Просмотреть файл

@ -3,11 +3,11 @@
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>237 33 482 372 0 0 1600 1002 </string>
<string>105 33 482 372 0 0 1600 1002 </string>
<key>IBEditorPositions</key>
<dict>
<key>266</key>
<string>437 533 277 90 0 0 1152 848 </string>
<string>644 623 277 90 0 0 1600 1002 </string>
<key>29</key>
<string>11 957 446 44 0 0 1600 1002 </string>
<key>494</key>
@ -31,7 +31,11 @@
</dict>
<key>IBLastGroupID</key>
<string>2</string>
<key>IBOpenObjects</key>
<array>
<integer>29</integer>
</array>
<key>IBSystem Version</key>
<string>6F21</string>
<string>6G30</string>
</dict>
</plist>

Двоичные данные
camino/resources/localized/English.lproj/MainMenu.nib/objects.nib сгенерированный

Двоичный файл не отображается.

Просмотреть файл

@ -1,18 +1,40 @@
{
IBClasses = (
{
CLASS = CHStackView;
LANGUAGE = ObjC;
OUTLETS = {mDataSource = id; };
SUPERCLASS = NSView;
},
{CLASS = FirstResponder; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{CLASS = NSObject; LANGUAGE = ObjC; },
{CLASS = NSView; LANGUAGE = ObjC; SUPERCLASS = NSResponder; },
{
CLASS = ProgressDlgController;
LANGUAGE = ObjC;
OUTLETS = {
mElapsedTimeLabel = NSTextField;
mFromField = NSTextField;
mProgressBar = NSProgressIndicator;
mStatusLabel = NSTextField;
mTimeLeftLabel = NSTextField;
mToField = NSTextField;
mNoDownloadsText = NSTextField;
mScrollView = NSScrollView;
mStackView = CHStackView;
};
SUPERCLASS = NSWindowController;
},
{
ACTIONS = {stop = id; toggleDisclosure = id; };
CLASS = ProgressViewController;
LANGUAGE = ObjC;
OUTLETS = {
mLocationsLabel = NSTextField;
mLocationsLabelCompact = NSTextField;
mProgressBar = NSProgressIndicator;
mProgressView = NSView;
mProgressViewCompact = NSView;
mServerLabel = NSTextField;
mStatusLabel = NSTextField;
mTimeLeftLabel = NSTextField;
mTimeLeftLabelCompact = NSTextField;
};
SUPERCLASS = NSObject;
}
);
IBVersion = 1;

Просмотреть файл

@ -1,12 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist SYSTEM "file://localhost/System/Library/DTDs/PropertyList.dtd">
<plist version="0.9">
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>94 26 404 250 0 0 1152 746 </string>
<string>24 42 592 284 0 0 1600 1002 </string>
<key>IBFramework Version</key>
<string>248.0</string>
<string>286.0</string>
<key>IBSystem Version</key>
<string>5S60</string>
<string>6G30</string>
</dict>
</plist>

Двоичные данные
camino/resources/localized/English.lproj/ProgressDialog.nib/objects.nib сгенерированный

Двоичный файл не отображается.

22
camino/resources/localized/English.lproj/ProgressView.nib/classes.nib сгенерированный Normal file
Просмотреть файл

@ -0,0 +1,22 @@
{
IBClasses = (
{CLASS = FirstResponder; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{
ACTIONS = {close = id; open = id; reveal = id; stop = id; toggleDisclosure = id; };
CLASS = ProgressViewController;
LANGUAGE = ObjC;
OUTLETS = {
mCompletedView = NSView;
mCompletedViewCompact = NSView;
mExpandedCancelButton = NSButton;
mExpandedOpenButton = NSButton;
mExpandedRevealButton = NSButton;
mProgressBar = NSProgressIndicator;
mProgressView = NSView;
mProgressViewCompact = NSView;
};
SUPERCLASS = NSObject;
}
);
IBVersion = 1;
}

27
camino/resources/localized/English.lproj/ProgressView.nib/info.nib сгенерированный Normal file
Просмотреть файл

@ -0,0 +1,27 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>75 299 448 284 0 0 1600 1002 </string>
<key>IBEditorPositions</key>
<dict>
<key>27</key>
<string>573 628 420 80 0 0 1600 1002 </string>
<key>5</key>
<string>573 564 420 208 0 0 1600 1002 </string>
<key>71</key>
<string>573 564 420 208 0 0 1600 1002 </string>
<key>97</key>
<string>573 628 420 80 0 0 1600 1002 </string>
</dict>
<key>IBFramework Version</key>
<string>286.0</string>
<key>IBOpenObjects</key>
<array>
<integer>5</integer>
</array>
<key>IBSystem Version</key>
<string>6G30</string>
</dict>
</plist>

Двоичные данные
camino/resources/localized/English.lproj/ProgressView.nib/objects.nib сгенерированный Normal file

Двоичный файл не отображается.

Просмотреть файл

@ -3,13 +3,9 @@
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>410 67 356 301 0 0 1152 848 </string>
<string>325 55 356 301 0 0 1024 746 </string>
<key>IBFramework Version</key>
<string>286.0</string>
<key>IBOpenObjects</key>
<array>
<integer>251</integer>
</array>
<string>283.0</string>
<key>IBSystem Version</key>
<string>6F21</string>
</dict>

Двоичные данные
camino/resources/localized/English.lproj/alert.nib/objects.nib сгенерированный

Двоичный файл не отображается.

Просмотреть файл

@ -37,10 +37,14 @@
* ***** END LICENSE BLOCK ***** */
#import <Cocoa/Cocoa.h>
#import "SecurityDialogs.h"
#import "CocoaPromptService.h"
#include "nsIGenericFactory.h"
#import "KeychainService.h"
#import "nsDownloadListener.h"
#import "ProgressDlgController.h"
#include "nsIGenericFactory.h"
// {0ffd3880-7a1a-11d6-a384-975d1d5f86fc}
#define NS_SECURITYDIALOGS_CID \
@ -55,6 +59,27 @@
NS_GENERIC_FACTORY_CONSTRUCTOR(SecurityDialogs);
NS_GENERIC_FACTORY_CONSTRUCTOR(CocoaPromptService);
NS_GENERIC_FACTORY_CONSTRUCTOR(KeychainPrompt);
//NS_GENERIC_FACTORY_CONSTRUCTOR(nsDownloadListener);
static NS_IMETHODIMP
nsDownloadListenerConstructor(nsISupports *aOuter, REFNSIID aIID, void **aResult)
{
*aResult = NULL;
if (aOuter)
return NS_ERROR_NO_AGGREGATION;
nsDownloadListener* inst;
NS_NEWXPCOM(inst, nsDownloadListener);
if (!inst)
return NS_ERROR_OUT_OF_MEMORY;
NS_ADDREF(inst);
inst->SetDisplayFactory([ProgressDlgController sharedDownloadController]);
nsresult rv = inst->QueryInterface(aIID, aResult);
NS_RELEASE(inst);
return rv;
}
// used by MainController to register the components in which we want to override
// with the Gecko embed layer.
@ -83,6 +108,12 @@ static const nsModuleComponentInfo gAppComponents[] = {
NS_KEYCHAINPROMPT_CID,
"@mozilla.org/wallet/single-sign-on-prompt;1",
KeychainPromptConstructor
},
{
"Download",
NS_DOWNLOAD_CID,
NS_DOWNLOAD_CONTRACTID,
nsDownloadListenerConstructor
}
};

Просмотреть файл

@ -52,9 +52,8 @@
{
IBOutlet NSApplication* mApplication;
// The following two items are used by the filter list when saving files.
// The following item is added to NSSavePanels as an accessory view
IBOutlet NSView* mFilterView;
IBOutlet NSPopUpButton* mFilterList;
// IBOutlet NSMenuItem* mOfflineMenuItem;
IBOutlet NSMenuItem* mCloseWindowMenuItem;
@ -137,11 +136,12 @@
-(IBAction) addFolder:(id)aSender;
-(IBAction) addSeparator:(id)aSender;
//Window menu actions
// Window menu actions
-(IBAction) newTab:(id)aSender;
-(IBAction) closeTab:(id)aSender;
-(IBAction) downloadsWindow:(id)aSender;
//Help menu actions
// Help menu actions
-(IBAction) infoLink:(id)aSender;
-(IBAction) feedbackLink:(id)aSender;
@ -154,7 +154,8 @@
- (void)adjustBookmarksMenuItemsEnabling:(BOOL)inBrowserWindowFrontmost;
-(NSWindow*)getFrontmostBrowserWindow;
- (NSView*)getSavePanelView;
- (NSWindow*)getFrontmostBrowserWindow;
- (MVPreferencesController *)preferencesController;
- (void)displayPreferencesWindow:sender;

Просмотреть файл

@ -260,19 +260,7 @@ const int kReuseWindowOnAE = 2;
- (NSApplicationTerminateReply)applicationShouldTerminate:(NSApplication *)sender
{
if ([ProgressDlgController numDownloadInProgress] > 0)
{
NSString *alert = NSLocalizedString(@"QuitWithDownloadsMsg", @"Really Quit?");
NSString *message = NSLocalizedString(@"QuitWithDownloadsExpl", @"");
NSString *okButton = NSLocalizedString(@"QuitWithdownloadsButtonDefault",@"Cancel");
NSString *altButton = NSLocalizedString(@"QuitWithdownloadsButtonAlt",@"Quit");
// while the panel is up, download dialogs won't update (no timers firing) but
// downloads continue (PLEvents being processed)
if (NSRunAlertPanel(alert, message, okButton, altButton, nil) == NSAlertDefaultReturn)
return NSTerminateCancel;
}
return NSTerminateNow;
return [[ProgressDlgController sharedDownloadController] allowTerminate];
}
-(void)applicationWillTerminate: (NSNotification*)aNotification
@ -439,7 +427,7 @@ const int kReuseWindowOnAE = 2;
{
BrowserWindowController* browserController = [self getMainWindowBrowserController];
if (browserController)
[browserController saveDocument:NO filterView:mFilterView filterList: mFilterList];
[browserController saveDocument:NO filterView:mFilterView];
}
-(IBAction) pageSetup:(id)aSender
@ -584,6 +572,11 @@ const int kReuseWindowOnAE = 2;
}
}
-(IBAction) downloadsWindow:(id)aSender
{
[[ProgressDlgController sharedDownloadController] showWindow:aSender];
}
- (void)adjustBookmarksMenuItemsEnabling:(BOOL)inBrowserWindowFrontmost;
{
[mAddBookmarkMenuItem setEnabled:inBrowserWindowFrontmost];
@ -591,6 +584,11 @@ const int kReuseWindowOnAE = 2;
[mCreateBookmarksSeparatorMenuItem setEnabled:NO]; // separators are not implemented yet
}
- (NSView*)getSavePanelView
{
return mFilterView;
}
-(NSWindow*)getFrontmostBrowserWindow
{
// for some reason, [NSApp mainWindow] doesn't always work, so we have to

Просмотреть файл

@ -47,7 +47,58 @@ NSGETMODULE(_name) (nsIComponentManager* aCompMgr, \
}
// NSGetModule entry points
DECL_NSGETMODULE(UcharUtil) DECL_NSGETMODULE(nsUConvModule) DECL_NSGETMODULE(nsUCvJAModule) DECL_NSGETMODULE(nsUCvCnModule) DECL_NSGETMODULE(nsUCvLatinModule) DECL_NSGETMODULE(nsUCvTWModule) DECL_NSGETMODULE(nsUCvTW2Module) DECL_NSGETMODULE(nsUCvKoModule) DECL_NSGETMODULE(nsLocaleModule) DECL_NSGETMODULE(nsStringBundleModule) DECL_NSGETMODULE(nsLWBrkModule) DECL_NSGETMODULE(nsCharDetModule) DECL_NSGETMODULE(xpconnect) DECL_NSGETMODULE(cacheservice) DECL_NSGETMODULE(necko_core_and_primary_protocols) DECL_NSGETMODULE(necko_secondary_protocols) DECL_NSGETMODULE(nsURILoaderModule) DECL_NSGETMODULE(nsPrefModule) DECL_NSGETMODULE(nsCJVMManagerModule) DECL_NSGETMODULE(nsSecurityManagerModule) DECL_NSGETMODULE(nsChromeModule) DECL_NSGETMODULE(nsRDFModule) DECL_NSGETMODULE(nsParserModule) DECL_NSGETMODULE(nsGfxMacModule) DECL_NSGETMODULE(nsGfx2Module) DECL_NSGETMODULE(nsImageLib2Module) DECL_NSGETMODULE(nsPNGDecoderModule) DECL_NSGETMODULE(nsGIFModule2) DECL_NSGETMODULE(nsJPEGDecoderModule) DECL_NSGETMODULE(nsPluginModule) DECL_NSGETMODULE(javascript__protocol) DECL_NSGETMODULE(DOM_components) DECL_NSGETMODULE(nsViewModule) DECL_NSGETMODULE(nsWidgetMacModule) DECL_NSGETMODULE(nsContentModule) DECL_NSGETMODULE(nsLayoutModule) DECL_NSGETMODULE(nsMorkModule) DECL_NSGETMODULE(docshell_provider) DECL_NSGETMODULE(embedcomponents) DECL_NSGETMODULE(Browser_Embedding_Module) DECL_NSGETMODULE(nsEditorModule) DECL_NSGETMODULE(nsTransactionManagerModule) DECL_NSGETMODULE(nsTextServicesModule) DECL_NSGETMODULE(nsProfileModule) DECL_NSGETMODULE(Session_History_Module) DECL_NSGETMODULE(application) DECL_NSGETMODULE(nsCookieModule) DECL_NSGETMODULE(nsXMLExtrasModule) DECL_NSGETMODULE(nsUniversalCharDetModule) DECL_NSGETMODULE(BOOT) DECL_NSGETMODULE(NSS)
DECL_NSGETMODULE(UcharUtil)
DECL_NSGETMODULE(nsUConvModule)
DECL_NSGETMODULE(nsUCvJAModule)
DECL_NSGETMODULE(nsUCvCnModule)
DECL_NSGETMODULE(nsUCvLatinModule)
DECL_NSGETMODULE(nsUCvTWModule)
DECL_NSGETMODULE(nsUCvTW2Module)
DECL_NSGETMODULE(nsUCvKoModule)
DECL_NSGETMODULE(nsLocaleModule)
DECL_NSGETMODULE(nsStringBundleModule)
DECL_NSGETMODULE(nsLWBrkModule)
DECL_NSGETMODULE(nsCharDetModule)
DECL_NSGETMODULE(xpconnect)
DECL_NSGETMODULE(cacheservice)
DECL_NSGETMODULE(necko_core_and_primary_protocols)
DECL_NSGETMODULE(necko_secondary_protocols)
DECL_NSGETMODULE(nsURILoaderModule)
DECL_NSGETMODULE(nsPrefModule)
DECL_NSGETMODULE(nsCJVMManagerModule)
DECL_NSGETMODULE(nsSecurityManagerModule)
DECL_NSGETMODULE(nsChromeModule)
DECL_NSGETMODULE(nsRDFModule)
DECL_NSGETMODULE(nsParserModule)
DECL_NSGETMODULE(nsGfxMacModule)
DECL_NSGETMODULE(nsGfx2Module)
DECL_NSGETMODULE(nsImageLib2Module)
DECL_NSGETMODULE(nsPNGDecoderModule)
DECL_NSGETMODULE(nsGIFModule2)
DECL_NSGETMODULE(nsJPEGDecoderModule)
DECL_NSGETMODULE(nsPluginModule)
DECL_NSGETMODULE(javascript__protocol)
DECL_NSGETMODULE(JS_component_loader)
DECL_NSGETMODULE(DOM_components)
DECL_NSGETMODULE(nsViewModule)
DECL_NSGETMODULE(nsWidgetMacModule)
DECL_NSGETMODULE(nsContentModule)
DECL_NSGETMODULE(nsLayoutModule)
DECL_NSGETMODULE(nsMorkModule)
DECL_NSGETMODULE(docshell_provider)
DECL_NSGETMODULE(embedcomponents)
DECL_NSGETMODULE(Browser_Embedding_Module)
DECL_NSGETMODULE(nsEditorModule)
DECL_NSGETMODULE(nsTransactionManagerModule)
DECL_NSGETMODULE(nsTextServicesModule)
DECL_NSGETMODULE(nsProfileModule)
DECL_NSGETMODULE(Session_History_Module)
DECL_NSGETMODULE(application)
DECL_NSGETMODULE(nsCookieModule)
DECL_NSGETMODULE(nsXMLExtrasModule)
DECL_NSGETMODULE(nsUniversalCharDetModule)
DECL_NSGETMODULE(BOOT)
DECL_NSGETMODULE(NSS)
#line 52 "nsStaticComponents.cpp.in"
/**
@ -55,7 +106,58 @@ DECL_NSGETMODULE(UcharUtil) DECL_NSGETMODULE(nsUConvModule) DECL_NSGETMODULE(nsU
*/
static nsStaticModuleInfo gStaticModuleInfo[] = {
#define MODULE(_name) { (#_name), NSGETMODULE(_name) }
MODULE(UcharUtil), MODULE(nsUConvModule), MODULE(nsUCvJAModule), MODULE(nsUCvCnModule), MODULE(nsUCvLatinModule), MODULE(nsUCvTWModule), MODULE(nsUCvTW2Module), MODULE(nsUCvKoModule), MODULE(nsLocaleModule), MODULE(nsStringBundleModule), MODULE(nsLWBrkModule), MODULE(nsCharDetModule), MODULE(xpconnect), MODULE(cacheservice), MODULE(necko_core_and_primary_protocols), MODULE(necko_secondary_protocols), MODULE(nsURILoaderModule), MODULE(nsPrefModule), MODULE(nsCJVMManagerModule), MODULE(nsSecurityManagerModule), MODULE(nsChromeModule), MODULE(nsRDFModule), MODULE(nsParserModule), MODULE(nsGfxMacModule), MODULE(nsGfx2Module), MODULE(nsImageLib2Module), MODULE(nsPNGDecoderModule), MODULE(nsGIFModule2), MODULE(nsJPEGDecoderModule), MODULE(nsPluginModule), MODULE(javascript__protocol), MODULE(DOM_components), MODULE(nsViewModule), MODULE(nsWidgetMacModule), MODULE(nsContentModule), MODULE(nsLayoutModule), MODULE(nsMorkModule), MODULE(docshell_provider), MODULE(embedcomponents), MODULE(Browser_Embedding_Module), MODULE(nsEditorModule), MODULE(nsTransactionManagerModule), MODULE(nsTextServicesModule), MODULE(nsProfileModule), MODULE(Session_History_Module), MODULE(application), MODULE(nsCookieModule), MODULE(nsXMLExtrasModule), MODULE(nsUniversalCharDetModule), MODULE(BOOT), MODULE(NSS),
MODULE(UcharUtil),
MODULE(nsUConvModule),
MODULE(nsUCvJAModule),
MODULE(nsUCvCnModule),
MODULE(nsUCvLatinModule),
MODULE(nsUCvTWModule),
MODULE(nsUCvTW2Module),
MODULE(nsUCvKoModule),
MODULE(nsLocaleModule),
MODULE(nsStringBundleModule),
MODULE(nsLWBrkModule),
MODULE(nsCharDetModule),
MODULE(xpconnect),
MODULE(cacheservice),
MODULE(necko_core_and_primary_protocols),
MODULE(necko_secondary_protocols),
MODULE(nsURILoaderModule),
MODULE(nsPrefModule),
MODULE(nsCJVMManagerModule),
MODULE(nsSecurityManagerModule),
MODULE(nsChromeModule),
MODULE(nsRDFModule),
MODULE(nsParserModule),
MODULE(nsGfxMacModule),
MODULE(nsGfx2Module),
MODULE(nsImageLib2Module),
MODULE(nsPNGDecoderModule),
MODULE(nsGIFModule2),
MODULE(nsJPEGDecoderModule),
MODULE(nsPluginModule),
MODULE(javascript__protocol),
MODULE(JS_component_loader),
MODULE(DOM_components),
MODULE(nsViewModule),
MODULE(nsWidgetMacModule),
MODULE(nsContentModule),
MODULE(nsLayoutModule),
MODULE(nsMorkModule),
MODULE(docshell_provider),
MODULE(embedcomponents),
MODULE(Browser_Embedding_Module),
MODULE(nsEditorModule),
MODULE(nsTransactionManagerModule),
MODULE(nsTextServicesModule),
MODULE(nsProfileModule),
MODULE(Session_History_Module),
MODULE(application),
MODULE(nsCookieModule),
MODULE(nsXMLExtrasModule),
MODULE(nsUniversalCharDetModule),
MODULE(BOOT),
MODULE(NSS),
#line 60 "nsStaticComponents.cpp.in"
};

Просмотреть файл

@ -601,7 +601,7 @@ const int kBookmarksRootItemTag = -2;
//Set cell's textual contents
//[cellValue replaceCharactersInRange:NSMakeRange(0, [cellValue length]) withString:[NSString stringWith_nsAString: nameAttr]];
cellValue = [[NSMutableAttributedString alloc] initWithString:[NSString stringWith_nsAString: nameAttr]];
cellValue = [[[NSMutableAttributedString alloc] initWithString:[NSString stringWith_nsAString: nameAttr]] autorelease];
//Create an attributed string to hold the empty attachment, then release the components.
NSMutableAttributedString* attachmentAttrString = [NSMutableAttributedString attributedStringWithAttachment:textAttachment];

Просмотреть файл

@ -100,6 +100,7 @@
- (BOOL)isOpaque
{
// see http://developer.apple.com/qa/qa2001/qa1117.html
if ( ([self tabViewType] == NSNoTabsBezelBorder) && (NSAppKitVersionNumber < 633) )
return NO;

Просмотреть файл

@ -54,6 +54,8 @@ static const int kEscapeKeyCode = 53;
BOOL madeFirstResponder = [super makeFirstResponder:responder];
if (madeFirstResponder && oldResponder != [self firstResponder])
[(BrowserWindowController*)[self delegate] focusChangedFrom:oldResponder to:[self firstResponder]];
//NSLog(@"Old FR %@, new FR %@, responder %@, made %d", oldResponder, [self firstResponder], responder, madeFirstResponder);
return madeFirstResponder;
}

Просмотреть файл

@ -109,12 +109,12 @@ typedef enum
IBOutlet NSTextField* mLocationSheetURLField;
IBOutlet NSView* mStatusBar; // contains the status text, progress bar, and lock
IBOutlet PageProxyIcon* mProxyIcon;
IBOutlet BrowserContentView* mContentView;
IBOutlet BrowserContentView* mContentView;
IBOutlet BookmarksDataSource* mSidebarBookmarksDataSource;
IBOutlet HistoryDataSource* mHistoryDataSource;
IBOutlet HistoryDataSource* mHistoryDataSource;
IBOutlet BookmarksToolbar* mPersonalToolbar;
IBOutlet BookmarksToolbar* mPersonalToolbar;
IBOutlet NSWindow* mAddBookmarkSheetWindow;
IBOutlet NSTextField* mAddBookmarkTitleField;
@ -191,6 +191,8 @@ typedef enum
- (void)updateLocationFields:(NSString *)locationString;
- (void)updateSiteIcons:(NSImage *)siteIconImage;
- (void)updateToolbarItems;
- (void)loadingStarted;
- (void)loadingDone;
- (void)focusURLBar;
// call to update the image of the lock icon with a value from nsIWebProgressListener
@ -211,9 +213,9 @@ typedef enum
- (IBAction)viewSource:(id)aSender; // focussed frame or page
- (IBAction)viewPageSource:(id)aSender; // top-level page
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList;
- (void)saveURL: (NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList
url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename;
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView;
- (void)saveURL:(NSView*)aFilterView url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename;
- (IBAction)printDocument:(id)aSender;
- (IBAction)pageSetup:(id)aSender;
- (IBAction)performSearch:(id)aSender;
@ -302,6 +304,7 @@ typedef enum
- (IBAction)bookmarkLink: (id)aSender;
- (IBAction)copyLinkLocation:(id)aSender;
- (IBAction)copyImage:(id)sender;
- (IBAction)copyImageLocation:(id)sender;
- (BookmarksToolbar*) bookmarksToolbar;

Просмотреть файл

@ -816,6 +816,19 @@ static NSArray* sToolbarDefaults = nil;
else
return YES;
}
- (void)loadingStarted
{
[self updateToolbarItems];
[self startThrobber];
}
- (void)loadingDone
{
[self updateToolbarItems];
[self stopThrobber];
[mHistoryDataSource refresh];
}
- (void)updateToolbarItems
{
@ -960,16 +973,14 @@ static NSArray* sToolbarDefaults = nil;
}
}
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView
{
[[mBrowserView getBrowserView] saveDocument:focusedFrame filterView:aFilterView filterList:aFilterList];
[[mBrowserView getBrowserView] saveDocument:focusedFrame filterView:aFilterView];
}
- (void)saveURL: (NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList
url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename
- (void)saveURL: (NSView*)aFilterView url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename
{
[[mBrowserView getBrowserView] saveURL: aFilterView filterList: aFilterList
url: aURLSpec suggestedFilename: aFilename];
[[mBrowserView getBrowserView] saveURL: aFilterView url: aURLSpec suggestedFilename: aFilename];
}
- (void)loadSourceOfURL:(NSString*)urlStr
@ -1890,12 +1901,14 @@ static NSArray* sToolbarDefaults = nil;
- (IBAction)savePageAs:(id)aSender
{
[self saveDocument:NO filterView:nil filterList: nil];
NSView* accessoryView = [[NSApp delegate] getSavePanelView];
[self saveDocument:NO filterView:accessoryView];
}
- (IBAction)saveFrameAs:(id)aSender
{
[self saveDocument:YES filterView:nil filterList: nil];
NSView* accessoryView = [[NSApp delegate] getSavePanelView];
[self saveDocument:YES filterView:accessoryView];
}
- (IBAction)saveLinkAs:(id)aSender
@ -1915,8 +1928,7 @@ static NSArray* sToolbarDefaults = nil;
nsAutoString text;
GeckoUtils::GatherTextUnder(mContextMenuNode, text);
[self saveURL: nil filterList: nil
url: hrefStr suggestedFilename: [NSString stringWith_nsAString: text]];
[self saveURL:nil url:hrefStr suggestedFilename:[NSString stringWith_nsAString:text]];
}
- (IBAction)saveImageAs:(id)aSender
@ -1931,11 +1943,18 @@ static NSArray* sToolbarDefaults = nil;
NSString* hrefStr = [NSString stringWith_nsAString: url];
[self saveURL: nil filterList: nil
url: hrefStr suggestedFilename: [NSString stringWith_nsAString: text]];
[self saveURL:nil url:hrefStr suggestedFilename: [NSString stringWith_nsAString: text]];
}
}
- (IBAction)copyImage:(id)sender
{
nsCOMPtr<nsIWebBrowser> webBrowser = getter_AddRefs([[[self getBrowserWrapper] getBrowserView] getWebBrowser]);
nsCOMPtr<nsIClipboardCommands> clipboard(do_GetInterface(webBrowser));
if (clipboard)
clipboard->CopyImageContents();
}
- (IBAction)copyImageLocation:(id)sender
{
nsCOMPtr<nsIWebBrowser> webBrowser = getter_AddRefs([[[self getBrowserWrapper] getBrowserView] getWebBrowser]);

Просмотреть файл

@ -335,10 +335,8 @@ const NSString* kOfflineNotificationName = @"offlineModeChanged";
mTabTitle = [mLoadingStatusString retain];
[mTabItem setLabel:mTabTitle];
if (mWindowController) {
[mWindowController updateToolbarItems];
[mWindowController startThrobber];
}
if (mWindowController)
[mWindowController loadingStarted];
}
- (void)onLoadingCompleted:(BOOL)succeeded
@ -402,10 +400,8 @@ const NSString* kOfflineNotificationName = @"offlineModeChanged";
[self removeFromSuperview];
}
if (mWindowController) {
[mWindowController updateToolbarItems];
[mWindowController stopThrobber];
}
if (mWindowController)
[mWindowController loadingDone];
}
- (void)onProgressChange:(int)currentBytes outOf:(int)maxBytes

Просмотреть файл

@ -139,8 +139,7 @@ ContentClickListener::MouseClick(nsIDOMEvent* aEvent)
nsAutoString text;
GeckoUtils::GatherTextUnder(content, text);
[mBrowserController saveURL: nil filterList: nil
url: hrefStr suggestedFilename: [NSString stringWith_nsAString: text]];
[mBrowserController saveURL:nil url:hrefStr suggestedFilename:[NSString stringWith_nsAString:text]];
}
return NS_OK;

Просмотреть файл

@ -51,10 +51,16 @@
class nsIPrefBranch;
enum KeychainPromptResult { kSave, kDontRemember, kNeverRemember } ;
@class CHBrowserView;
@interface KeychainService : NSObject
{
IBOutlet id confirmStorePasswordPanel;
IBOutlet id confirmChangePasswordPanel;
BOOL mIsEnabled;
BOOL mIsAutoFillEnabled;
@ -64,6 +70,13 @@ class nsIPrefBranch;
+ (KeychainService*) instance;
- (void) shutdown:(id)sender;
- (IBAction)hitButtonOK:(id)sender;
- (IBAction)hitButtonCancel:(id)sender;
- (IBAction)hitButtonOther:(id)sender;
- (KeychainPromptResult)confirmStorePassword:(NSWindow*)parent;
- (BOOL)confirmChangedPassword:(NSWindow*)parent;
- (BOOL) getUsernameAndPassword:(NSString*)realm port:(PRInt32)inPort user:(NSMutableString*)username password:(NSMutableString*)pwd item:(KCItemRef*)outItem;
- (BOOL) findUsernameAndPassword:(NSString*)realm port:(PRInt32)inPort;
- (void) storeUsernameAndPassword:(NSString*)realm port:(PRInt32)inPort user:(NSString*)username password:(NSString*)pwd;
@ -75,13 +88,43 @@ class nsIPrefBranch;
- (BOOL) isEnabled;
- (BOOL) isAutoFillEnabled;
// routines to manipulate the keychain deny list for which hosts we shouldn't
// ask about
- (void) addHostToDenyList:(NSString*)host;
- (BOOL) isHostInDenyList:(NSString*)host;
@end
//
// KeychainDenyList
//
// A singleton object that maintains a list of sites where we should
// not prompt the user for saving in the keychain. This object also
// handles archiving the list in the user's profile dir.
//
@interface KeychainDenyList : NSObject
{
NSMutableArray* mDenyList; // the list
BOOL mIsDirty; // do we need to write the list to disk?
}
+ (KeychainDenyList*) instance;
- (void) shutdown:(id)sender;
- (BOOL) isHostPresent:(NSString*)host;
- (void) addHost:(NSString*)host;
- (void) removeHost:(NSString*)host;
- (void) writeToDisk;
@end
class KeychainPrompt : public nsIAuthPromptWrapper
{
public:
KeychainPrompt();
KeychainPrompt(KeychainService*);
virtual ~KeychainPrompt();
NS_DECL_ISUPPORTS
@ -95,7 +138,6 @@ protected:
static void ExtractHostAndPort(const PRUnichar* inRealm, NSString** outHost, PRInt32* outPort);
nsCOMPtr<nsIPrompt> mPrompt;
KeychainService* mKeychain;
};
//
@ -105,7 +147,7 @@ class KeychainFormSubmitObserver : public nsIObserver,
public nsIFormSubmitObserver
{
public:
KeychainFormSubmitObserver(KeychainService*);
KeychainFormSubmitObserver();
virtual ~KeychainFormSubmitObserver();
NS_DECL_ISUPPORTS
@ -116,12 +158,10 @@ public:
private:
static BOOL CheckStorePasswordYN(nsIDOMWindowInternal*);
static KeychainPromptResult CheckStorePasswordYN(nsIDOMWindowInternal*);
static BOOL CheckChangeDataYN(nsIDOMWindowInternal*);
static NSWindow* GetNSWindow(nsIDOMWindowInternal* inWindow);
KeychainService* mKeychain;
};
//
@ -129,11 +169,10 @@ private:
//
@interface KeychainBrowserListener : NSObject<CHBrowserListener>
{
KeychainService* mKeychain;
CHBrowserView* mBrowserView;
}
- (id)initWithBrowser:(KeychainService*)keychain browser:(CHBrowserView*)aBrowser;
- (id)initWithBrowser:(CHBrowserView*)aBrowser;
@end

Просмотреть файл

@ -69,6 +69,9 @@
#include "nsIWindowWatcher.h"
#include "nsIWebBrowserChrome.h"
#include "nsIEmbeddingSiteWindow.h"
#include "nsAppDirectoryServiceDefs.h"
extern NSString* XPCOMShutDownNotificationName;
nsresult
@ -114,7 +117,7 @@ int KeychainPrefChangedCallback(const char* inPref, void* unused)
// observer service uses a weakref.
nsCOMPtr<nsIObserverService> svc = do_GetService("@mozilla.org/observer-service;1");
NS_ASSERTION(svc, "Keychain can't get observer service");
mFormSubmitObserver = new KeychainFormSubmitObserver(self);
mFormSubmitObserver = new KeychainFormSubmitObserver();
if ( mFormSubmitObserver && svc ) {
NS_ADDREF(mFormSubmitObserver);
svc->AddObserver(mFormSubmitObserver, NS_FORMSUBMIT_SUBJECT, PR_FALSE);
@ -122,7 +125,7 @@ int KeychainPrefChangedCallback(const char* inPref, void* unused)
// register for the cocoa notification posted when XPCOM shutdown so we
// can unregister the pref callbacks we register below
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(shutdown:) name:@"XPCOM Shutdown"
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(shutdown:) name:XPCOMShutDownNotificationName
object:nil];
// cache the values of the prefs and register pref-changed callbacks. Yeah, I know
@ -139,6 +142,10 @@ int KeychainPrefChangedCallback(const char* inPref, void* unused)
pref->RegisterCallback(gAutoFillEnabledPref, KeychainPrefChangedCallback, nsnull);
}
}
// load the keychain.nib file with our dialogs in it
BOOL success = [NSBundle loadNibNamed:@"Keychain" owner:self];
NS_ASSERTION(success, "can't load keychain prompt dialogs");
}
return self;
}
@ -168,6 +175,8 @@ int KeychainPrefChangedCallback(const char* inPref, void* unused)
pref->UnregisterCallback(gUseKeychainPref, KeychainPrefChangedCallback, nsnull);
pref->UnregisterCallback(gAutoFillEnabledPref, KeychainPrefChangedCallback, nsnull);
}
[sInstance release];
}
@ -324,7 +333,181 @@ int KeychainPrefChangedCallback(const char* inPref, void* unused)
//
- (void) addListenerToView:(CHBrowserView*)view
{
[view addListener:[[[KeychainBrowserListener alloc] initWithBrowser:self browser:view] autorelease]];
[view addListener:[[[KeychainBrowserListener alloc] initWithBrowser:view] autorelease]];
}
//
// hitButtonOK:
// hitButtonCancel:
// hitButtonOther:
//
// actions for the buttons of the keychain prompt dialogs.
//
enum { kOKButton = 0, kCancelButton = 1, kOtherButton = 2 };
- (IBAction)hitButtonOK:(id)sender
{
[NSApp stopModalWithCode:kOKButton];
}
- (IBAction)hitButtonCancel:(id)sender
{
[NSApp stopModalWithCode:kCancelButton];
}
- (IBAction)hitButtonOther:(id)sender
{
[NSApp stopModalWithCode:kOtherButton];
}
//
// confirmStorePassword:
//
// Puts up a dialog when the keychain doesn't yet have an entry from
// this site asking to store it, forget it this once, or mark the site
// on a deny list so we never ask again.
//
- (KeychainPromptResult)confirmStorePassword:(NSWindow*)parent
{
int result = [NSApp runModalForWindow:confirmStorePasswordPanel relativeToWindow:parent];
[confirmStorePasswordPanel close];
// the results of hitButtonXX: map to the corresponding values in the
// |KeychainPromptResult| enum so we can just cast and return
return NS_STATIC_CAST(KeychainPromptResult, result);
}
//
// confirmChangedPassword:
//
// The password stored in the keychain differs from what the user typed
// in. Ask what they want to do to resolve the issue.
//
- (BOOL)confirmChangedPassword:(NSWindow*)parent
{
int result = [NSApp runModalForWindow:confirmChangePasswordPanel relativeToWindow:parent];
[confirmChangePasswordPanel close];
return (result == kOKButton);
}
- (void) addHostToDenyList:(NSString*)host
{
[[KeychainDenyList instance] addHost:host];
}
- (BOOL) isHostInDenyList:(NSString*)host
{
return [[KeychainDenyList instance] isHostPresent:host];
}
@end
@interface KeychainDenyList (KeychainDenyListPrivate)
- (NSString*) pathToDenyListFile;
@end
@implementation KeychainDenyList
static KeychainDenyList *sDenyListInstance = nil;
+ (KeychainDenyList*) instance
{
return sDenyListInstance ? sDenyListInstance : sDenyListInstance = [[self alloc] init];
}
- (id) init
{
if ( (self = [super init]) ) {
mDenyList = [[NSUnarchiver unarchiveObjectWithFile:[self pathToDenyListFile]] retain];
if ( !mDenyList )
mDenyList = [[NSMutableArray alloc] init];
mIsDirty = NO;
// register for the cocoa notification posted when XPCOM shutdown so we
// can release our singleton and flush the file
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(shutdown:) name:XPCOMShutDownNotificationName object:nil];
}
return self;
}
- (void) dealloc
{
[self writeToDisk];
[mDenyList release];
}
//
// shutdown:
//
// Called in response to the cocoa notification "XPCOM Shutdown" sent by the cocoa
// browser service before it terminates embedding and shuts down xpcom. Allows us
// to get rid of anything we're holding onto for the length of the app.
//
- (void) shutdown:(id)unused
{
[sDenyListInstance release];
}
//
// writeToDisk
//
// flushes the deny list to the save file in the user's profile, but only
// if it has changed since we read it in.
//
- (void) writeToDisk
{
if ( mIsDirty )
[NSArchiver archiveRootObject:mDenyList toFile:[self pathToDenyListFile]];
mIsDirty = NO;
}
- (BOOL) isHostPresent:(NSString*)host
{
return [mDenyList containsObject:host];
}
- (void) addHost:(NSString*)host
{
if ( ![self isHostPresent:host] ) {
[mDenyList addObject:host];
mIsDirty = YES;
}
}
- (void) removeHost:(NSString*)host
{
if ( [self isHostPresent:host] ) {
[mDenyList removeObject:host];
mIsDirty = YES;
}
}
//
// pathToDenyListFile
//
// returns a path ('/' delimited) that cocoa can use to point to the
// deny list save file in the current user's profile
//
- (NSString*) pathToDenyListFile
{
NSMutableString* path = [[[NSMutableString alloc] init] autorelease];
nsCOMPtr<nsIFile> appProfileDir;
NS_GetSpecialDirectory(NS_APP_USER_PROFILE_50_DIR, getter_AddRefs(appProfileDir));
if ( appProfileDir ) {
nsAutoString profilePath;
appProfileDir->GetPath(profilePath);
[path setString:[NSString stringWith_nsAString:profilePath]];
[path appendString:@"/Keychain Deny List"]; // |profilePath| is '/' delimited
}
return path;
}
@end
@ -338,12 +521,6 @@ NS_IMPL_ISUPPORTS2(KeychainPrompt,
nsIAuthPromptWrapper)
KeychainPrompt::KeychainPrompt()
: mKeychain([KeychainService instance])
{
NS_INIT_ISUPPORTS();
}
KeychainPrompt::KeychainPrompt(KeychainService* keychain) : mKeychain(keychain)
{
NS_INIT_ISUPPORTS();
}
@ -391,7 +568,8 @@ KeychainPrompt::ExtractHostAndPort(const PRUnichar* inRealm, NSString** outHost,
void
KeychainPrompt::PreFill(const PRUnichar *realm, PRUnichar **user, PRUnichar **pwd)
{
if(![mKeychain isEnabled] || ![mKeychain isAutoFillEnabled])
KeychainService* keychain = [KeychainService instance];
if(![keychain isEnabled] || ![keychain isAutoFillEnabled])
return;
NSString* host = nil;
@ -409,7 +587,7 @@ KeychainPrompt::PreFill(const PRUnichar *realm, PRUnichar **user, PRUnichar **pw
// Pre-fill user/password if found in the keychain.
//
KCItemRef ignore;
if([mKeychain getUsernameAndPassword:(NSString*)host port:port user:username password:password item:&ignore]) {
if([keychain getUsernameAndPassword:(NSString*)host port:port user:username password:password item:&ignore]) {
if ( user )
*user = [username createNewUnicodeBuffer];
if ( pwd )
@ -427,10 +605,12 @@ KeychainPrompt::ProcessPrompt(const PRUnichar* realm, bool checked, PRUnichar* u
NSString* username = [NSString stringWithPRUnichars:user];
NSString* password = [NSString stringWithPRUnichars:pwd];
KeychainService* keychain = [KeychainService instance];
NSMutableString* origUsername = [NSMutableString string];
NSMutableString* origPwd = [NSMutableString string];
KCItemRef itemRef;
bool found = [mKeychain getUsernameAndPassword:(NSString*)host port:port user:origUsername password:origPwd item:&itemRef];
bool found = [keychain getUsernameAndPassword:(NSString*)host port:port user:origUsername password:origPwd item:&itemRef];
//
// Update, store or remove the user/password depending on the user
@ -438,11 +618,11 @@ KeychainPrompt::ProcessPrompt(const PRUnichar* realm, bool checked, PRUnichar* u
// keychain.
//
if(checked && !found)
[mKeychain storeUsernameAndPassword:(NSString*)host port:port user:username password:password];
[keychain storeUsernameAndPassword:(NSString*)host port:port user:username password:password];
else if(checked && found && (![origUsername isEqualToString:username] || ![origPwd isEqualToString:password]))
[mKeychain updateUsernameAndPassword:(NSString*)host port:port user:username password:password item:itemRef];
[keychain updateUsernameAndPassword:(NSString*)host port:port user:username password:password item:itemRef];
else if(!checked && found)
[mKeychain removeUsernameAndPassword:(NSString*)host port:port item:itemRef];
[keychain removeUsernameAndPassword:(NSString*)host port:port item:itemRef];
}
//
@ -476,7 +656,7 @@ KeychainPrompt::PromptUsernameAndPassword(const PRUnichar *dialogTitle,
{
PreFill(realm, user, pwd);
PRBool checked = [mKeychain isEnabled];
PRBool checked = [[KeychainService instance] isEnabled];
PRUnichar* checkTitle = [NSLocalizedString(@"KeychainCheckTitle", @"") createNewUnicodeBuffer];
nsresult rv = mPrompt->PromptUsernameAndPassword(dialogTitle, text, user, pwd, checkTitle, &checked, _retval);
@ -501,7 +681,7 @@ KeychainPrompt::PromptPassword(const PRUnichar *dialogTitle,
{
PreFill(realm, nsnull, pwd);
PRBool checked = [mKeychain isEnabled];
PRBool checked = [[KeychainService instance] isEnabled];
PRUnichar* checkTitle = [NSLocalizedString(@"KeychainCheckTitle", @"") createNewUnicodeBuffer];
nsresult rv = mPrompt->PromptPassword(dialogTitle, text, pwd, checkTitle, &checked, _retval);
@ -530,7 +710,7 @@ NS_IMPL_ISUPPORTS2(KeychainFormSubmitObserver,
nsIObserver,
nsIFormSubmitObserver)
KeychainFormSubmitObserver::KeychainFormSubmitObserver(KeychainService* keychain) : mKeychain(keychain)
KeychainFormSubmitObserver::KeychainFormSubmitObserver()
{
NS_INIT_ISUPPORTS();
//NSLog(@"Keychain form submit observer created.");
@ -551,7 +731,8 @@ NS_IMETHODIMP
KeychainFormSubmitObserver::Notify(nsIContent* node, nsIDOMWindowInternal* window, nsIURI* actionURL,
PRBool* cancelSubmit)
{
if (![mKeychain isEnabled])
KeychainService* keychain = [KeychainService instance];
if (![keychain isEnabled])
return NS_OK;
nsCOMPtr<nsIDOMHTMLFormElement> formNode(do_QueryInterface(node));
@ -590,25 +771,41 @@ KeychainFormSubmitObserver::Notify(nsIContent* node, nsIDOMWindowInternal* windo
docURL->GetHost(host);
docURL->GetPort(&port);
// is the host in the deny list? if yes, bail. otherwise check the keychain.
NSString* realm = [NSString stringWithCString:host.get()];
if ( [keychain isHostInDenyList:realm] )
return NS_OK;
//
// If there's already an entry in the keychain, check if the username
// and password match. If not, ask the user what they want to do and replace
// it as necessary. If there's no entry, ask if they want to remember it
// and then put it into the keychain
//
NSString* realm = [NSString stringWithCString:host.get()];
NSString* existingUser = [NSMutableString string];
NSString* existingPassword = [NSMutableString string];
KCItemRef itemRef;
BOOL foundExistingPassword = [mKeychain getUsernameAndPassword:realm port:port user:existingUser password:existingPassword item:&itemRef];
BOOL foundExistingPassword = [keychain getUsernameAndPassword:realm port:port user:existingUser password:existingPassword item:&itemRef];
if ( foundExistingPassword ) {
if ( !([existingUser isEqualToString:username] && [existingPassword isEqualToString:password]) )
if ( CheckChangeDataYN(window) )
[mKeychain updateUsernameAndPassword:realm port:port user:username password:password item:itemRef];
[keychain updateUsernameAndPassword:realm port:port user:username password:password item:itemRef];
}
else {
if (CheckStorePasswordYN(window))
[mKeychain storeUsernameAndPassword:realm port:port user:username password:password];
switch (CheckStorePasswordYN(window)) {
case kSave:
[keychain storeUsernameAndPassword:realm port:port user:username password:password];
break;
case kNeverRemember:
// tell the keychain we never want to be prompted about this host again
[keychain addHostToDenyList:realm];
break;
case kDontRemember:
// do nothing at all
break;
}
}
}
@ -644,12 +841,11 @@ KeychainFormSubmitObserver::GetNSWindow(nsIDOMWindowInternal* inWindow)
return nswindow;
}
BOOL
KeychainPromptResult
KeychainFormSubmitObserver::CheckStorePasswordYN(nsIDOMWindowInternal* window)
{
NSWindow* nswindow = GetNSWindow(window);
nsAlertController* dialog = CHBrowserService::GetAlertController();
return [dialog confirmStorePassword:nswindow];
return [[KeychainService instance] confirmStorePassword:nswindow];
}
@ -657,16 +853,14 @@ BOOL
KeychainFormSubmitObserver::CheckChangeDataYN(nsIDOMWindowInternal* window)
{
NSWindow* nswindow = GetNSWindow(window);
nsAlertController* dialog = CHBrowserService::GetAlertController();
return [dialog confirmChangedPassword:nswindow];
return [[KeychainService instance] confirmChangedPassword:nswindow];
}
@implementation KeychainBrowserListener
- (id)initWithBrowser:(KeychainService*)keychain browser:(CHBrowserView*)aBrowser
- (id)initWithBrowser:(CHBrowserView*)aBrowser
{
if ( (self = [super init]) ) {
mKeychain = keychain;
mBrowserView = aBrowser;
}
return self;
@ -683,7 +877,8 @@ KeychainFormSubmitObserver::CheckChangeDataYN(nsIDOMWindowInternal* window)
if(!succeeded)
return;
if(![mKeychain isEnabled] || ![mKeychain isAutoFillEnabled])
KeychainService* keychain = [KeychainService instance];
if(![keychain isEnabled] || ![keychain isAutoFillEnabled])
return;
nsCOMPtr<nsIDOMWindow> domWin = getter_AddRefs([mBrowserView getContentWindow]);
@ -750,7 +945,7 @@ KeychainFormSubmitObserver::CheckChangeDataYN(nsIDOMWindowInternal* window)
docURL->GetPort(&port);
KCItemRef ignore;
if ([mKeychain getUsernameAndPassword:hostStr port:port user:username password:password item:&ignore]) {
if ([keychain getUsernameAndPassword:hostStr port:port user:username password:password item:&ignore]) {
nsAutoString user, pwd;
[username assignTo_nsAString:user];
[password assignTo_nsAString:pwd];

Просмотреть файл

@ -286,7 +286,7 @@ static nsresult MakeFaviconURIFromURI(const nsAString& inURIString, nsAString& o
NSImage* faviconImage = nil;
NS_DURING
faviconImage = [[NSImage alloc] initWithData:data];
faviconImage = [[[NSImage alloc] initWithData:data] autorelease];
NS_HANDLER
NSLog(@"Exception \"%@ making\" favicon image for %@", localException, inURI);
faviconImage = nil;

Просмотреть файл

@ -53,8 +53,6 @@
IBOutlet id confirmPanelText;
IBOutlet id confirmPanelButton1;
IBOutlet id confirmPanelButton2;
IBOutlet id confirmStorePasswordPanel;
IBOutlet id confirmChangePasswordPanel;
IBOutlet id promptPanel;
IBOutlet id promptPanelCheck;
IBOutlet id promptPanelText;
@ -90,8 +88,6 @@
- (int)confirmCheckEx:(NSWindow*)parent title:(NSString*)title text:(NSString*)text
button1:(NSString*)btn1 button2:(NSString*)btn2 button3:(NSString*)btn3
checkMsg:(NSString*)checkMsg checkValue:(BOOL*)checkValue;
- (BOOL)confirmStorePassword:(NSWindow*)parent;
- (BOOL)confirmChangedPassword:(NSWindow*)parent;
- (BOOL)prompt:(NSWindow*)parent title:(NSString*)title text:(NSString*)text promptText:(NSMutableString*)promptText checkMsg:(NSString*)checkMsg checkValue:(BOOL*)checkValue doCheck:(BOOL)doCheck;
- (BOOL)promptUserNameAndPassword:(NSWindow*)parent title:(NSString*)title text:(NSString*)text userNameText:(NSMutableString*)userNameText passwordText:(NSMutableString*)passwordText checkMsg:(NSString*)checkMsg checkValue:(BOOL*)checkValue doCheck:(BOOL)doCheck;

Просмотреть файл

@ -154,19 +154,6 @@ enum { kOKButton = 0, kCancelButton = 1, kOtherButton = 2 };
return result;
}
- (BOOL)confirmStorePassword:(NSWindow*)parent
{
int result = [NSApp runModalForWindow:confirmStorePasswordPanel relativeToWindow:parent];
[confirmStorePasswordPanel close];
return (result == kOKButton);
}
- (BOOL)confirmChangedPassword:(NSWindow*)parent
{
int result = [NSApp runModalForWindow:confirmChangePasswordPanel relativeToWindow:parent];
[confirmChangePasswordPanel close];
return (result == kOKButton);
}
- (BOOL)prompt:(NSWindow*)parent title:(NSString*)title text:(NSString*)text promptText:(NSMutableString*)promptText checkMsg:(NSString*)checkMsg checkValue:(BOOL*)checkValue doCheck:(BOOL)doCheck
{

Просмотреть файл

@ -20,6 +20,8 @@
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
* Calum Robinson <calumr@mac.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
@ -38,49 +40,72 @@
#import <AppKit/AppKit.h>
#import "CHDownloadProgressDisplay.h"
#import "CHStackView.h"
#include "nscore.h"
/*
How ProgressViewController and ProgressDlgController work.
ProgressDlgController manages the window the the downloads are displayed in.
It contains a single CHStackView, a custom class that asks its datasource
for a list of views to display, in a similar fashion to the way NSTableView
asks its datasource for data to display. There is a single instance of
ProgressDlgController, returned by +sharedDownloadController.
The ProgressDlgController is a subclass of CHDownloadController, which
means that it gets asked to create new objects conforming to the
CHDownloadProgressDisplay protocol, which are used to display
the progress of a single download. It does so by returning instances of
ProgressViewController, which manage an NSView that contains a progress
indicator, some text fields for status info and a cancel button.
After a ProgressViewController is requested, the CHStackView is reloaded,
which causes it to ask the ProgressDlgController (it's datasource) to
provide it with a list of all the subviews to be diaplyed. It calculates
it's new frame, and arranges the subviews in a vertical list.
The ProgressDlgController now needs to resize its window. It knows when
to do this because is watches for changes in the CHStackViews frame (using
NSViews built in NSNotification for this).
Expanding/contracting download progress views
When a disclosure triangle is clicked, the ProgressViewController just swaps
the expanded view for a smaller one. It saves the new state as the users
preference for "browser.download.compactView". If the option key was held down,
a notification is posted (that all ProgressViewControllers listen for) that
makes all ProgressViewControllers change their state to the new state of the sender.
class nsIWebBrowserPersist;
class nsISupports;
class nsIInputStream;
class nsDownloadListener;
*/
#import "CHDownloadProgressDisplay.h"
@interface ChimeraDownloadControllerFactory : DownloadControllerFactory
@end
@interface ProgressDlgController : NSWindowController <CHDownloadProgressDisplay>
@interface ProgressDlgController : NSWindowController<CHDownloadDisplayFactory, CHStackViewDataSource>
{
IBOutlet NSTextField *mElapsedTimeLabel;
IBOutlet NSTextField *mFromField;
IBOutlet NSTextField *mStatusLabel;
IBOutlet NSTextField *mTimeLeftLabel;
IBOutlet NSTextField *mToField;
IBOutlet NSProgressIndicator *mProgressBar;
NSToolbarItem *leaveOpenToggleToolbarItem;
BOOL mSaveFileDialogShouldStayOpen;
BOOL mDoingAutoFileDownload;
BOOL mIsFileSave;
BOOL mDownloadIsComplete;
long mCurrentProgress; // if progress bar is indeterminate, can still calc stats.
CHDownloader *mDownloader; // we hold a ref to this
NSTimer *mDownloadTimer;
IBOutlet CHStackView *mStackView;
IBOutlet NSScrollView *mScrollView;
IBOutlet NSTextField *mNoDownloadsText;
NSSize mDefaultWindowSize;
NSTimer *mDownloadTimer;
NSMutableArray *mProgressViewControllers;
int mNumActiveDownloads;
}
+ (int)numDownloadInProgress;
+ (ProgressDlgController *)sharedDownloadController;
-(void)autosaveWindowFrame;
- (int)numDownloadsInProgress;
-(void) setupDownloadTimer;
-(void) killDownloadTimer;
-(void) setDownloadProgress:(NSTimer *)aTimer;
-(NSString *) formatTime:(int)aSeconds;
-(NSString *) formatFuzzyTime:(int)aSeconds;
-(NSString *) formatBytes:(float)aBytes;
- (void)autosaveWindowFrame;
- (void)setupDownloadTimer;
- (void)killDownloadTimer;
- (void)setDownloadProgress:(NSTimer *)aTimer;
- (void)didStartDownload:(id <CHDownloadProgressDisplay>)progressDisplay;
- (void)didEndDownload:(id <CHDownloadProgressDisplay>)progressDisplay;
- (void)removeDownload:(id <CHDownloadProgressDisplay>)progressDisplay;
- (NSApplicationTerminateReply)allowTerminate;
@end

Просмотреть файл

@ -20,6 +20,7 @@
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Calum Robinson <calumr@mac.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
@ -35,504 +36,319 @@
*
* ***** END LICENSE BLOCK ***** */
#import "NSView+Utils.h"
#import "ProgressDlgController.h"
#include "nsCOMPtr.h"
#include "nsString.h"
#include "nsCRT.h"
#include "nsIWebBrowserPersist.h"
#include "nsIInputStream.h"
#include "nsIURL.h"
#include "nsILocalFile.h"
#include "nsIDOMHTMLDocument.h"
#include "nsIWebProgressListener.h"
#include "nsIDownload.h"
#include "nsIComponentManager.h"
#include "nsIPref.h"
static NSString *SaveFileToolbarIdentifier = @"Save File Dialog Toolbar";
static NSString *CancelToolbarItemIdentifier = @"Cancel Toolbar Item";
static NSString *ShowFileToolbarItemIdentifier = @"Show File Toolbar Item";
static NSString *OpenFileToolbarItemIdentifier = @"Open File Toolbar Item";
static NSString *LeaveOpenToolbarItemIdentifier = @"Leave Open Toggle Toolbar Item";
#import "ProgressViewController.h"
#import "PreferenceManager.h"
static NSString *ProgressWindowFrameSaveName = @"ProgressWindow";
@implementation ChimeraDownloadControllerFactory : DownloadControllerFactory
- (NSWindowController<CHDownloadProgressDisplay> *)createDownloadController
{
NSWindowController* progressController = [[ProgressDlgController alloc] initWithWindowNibName: @"ProgressDialog"];
NSAssert([progressController conformsToProtocol:@protocol(CHDownloadProgressDisplay)],
@"progressController should conform to CHDownloadProgressDisplay protocol");
return progressController;
}
@interface ProgressDlgController(PrivateProgressDlgController)
- (void)resizeWindowToFit;
- (void)rebuildViews;
- (NSSize)windowSizeForStackSize:(NSSize)stackSize;
@end
#pragma mark -
@interface ProgressDlgController(Private)
-(void)setupToolbar;
@end
@implementation ProgressDlgController
static int gNumActiveDownloads = 0;
static id gSharedProgressController = nil;
+ (int)numDownloadInProgress
+ (ProgressDlgController *)sharedDownloadController;
{
return gNumActiveDownloads;
if (gSharedProgressController == nil)
gSharedProgressController = [[ProgressDlgController alloc] init];
return gSharedProgressController;
}
- (id)init
{
if ((self == [super initWithWindowNibName:@"ProgressDialog"]))
{
// Register for notifications when the stack view changes size
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(stackViewResized:)
name:StackViewResizedNotificationName
object:nil];
mProgressViewControllers = [[NSMutableArray alloc] init];
mDefaultWindowSize = [[self window] frame].size;
// it would be nice if we could get the frame from the name, and then
// mess with it before setting it.
[[self window] setFrameUsingName:ProgressWindowFrameSaveName];
// set the window to its default height
NSRect windowFrame = [[self window] frame];
windowFrame.size.height = mDefaultWindowSize.height;
[[self window] setFrame:windowFrame display:NO];
// We provide the views for the stack view, from mProgressViewControllers
[mStackView setDataSource:self];
[mScrollView setDrawsBackground:NO];
[mNoDownloadsText retain]; // so we can remove it from its superview
}
return self;
}
- (void)dealloc
{
// if we get here because we're quitting, the listener will still be alive
// yet we're going away. As a result, we need to tell the d/l listener to
// forget it ever met us and necko will clean it up on its own.
if ( mDownloader)
mDownloader->DetachDownloadDisplay();
NS_IF_RELEASE(mDownloader);
if (self == gSharedProgressController)
gSharedProgressController = nil;
[[NSNotificationCenter defaultCenter] removeObserver:self];
[mProgressViewControllers release];
[mNoDownloadsText release];
[self killDownloadTimer];
[super dealloc];
}
- (void)windowDidLoad
- (void)didStartDownload:(id <CHDownloadProgressDisplay>)progressDisplay
{
[super windowDidLoad];
mDownloadIsComplete = NO;
mDoingAutoFileDownload = NO;
[self showWindow:nil]; // make sure the window is visible
if (!mIsFileSave) {
nsCOMPtr<nsIPref> prefs(do_GetService(NS_PREF_CONTRACTID));
PRBool save = PR_FALSE;
prefs->GetBoolPref("browser.download.progressDnldDialog.keepAlive", &save);
mSaveFileDialogShouldStayOpen = save;
PRBool autoHelperDispatch = PR_FALSE;
prefs->GetBoolPref("browser.download.autoDispatch", &autoHelperDispatch);
mDoingAutoFileDownload = autoHelperDispatch;
[self rebuildViews];
[self setupDownloadTimer];
}
- (void)didEndDownload:(id <CHDownloadProgressDisplay>)progressDisplay
{
[self rebuildViews]; // to swap in the completed view
}
- (void)removeDownload:(id <CHDownloadProgressDisplay>)progressDisplay
{
[mProgressViewControllers removeObject:progressDisplay];
if ([mProgressViewControllers count] == 0)
{
// Stop doing stuff if there aren't any downloads going on
[self killDownloadTimer];
}
[self setupToolbar];
[mProgressBar setUsesThreadedAnimation:YES];
[mProgressBar startAnimation:self]; // move to onStateChange
[self rebuildViews];
}
- (void)setupToolbar
- (void)stackViewResized:(NSNotification *)notification
{
NSToolbar *toolbar = [[[NSToolbar alloc] initWithIdentifier:SaveFileToolbarIdentifier] autorelease];
[toolbar setDisplayMode:NSToolbarDisplayModeDefault];
[toolbar setAllowsUserCustomization:YES];
[toolbar setAutosavesConfiguration:YES];
[toolbar setDelegate:self];
[[self window] setToolbar:toolbar];
NSDictionary* userInfo = [notification userInfo];
NSSize oldStackSize = [[userInfo objectForKey:@"oldsize"] sizeValue];
// this code is used to auto-resize the downloads window when
// its contents change size, if the window is in its standard, "zoomed"
// state. This allows the user to choose between auto-resizing behavior,
// by leaving the window alone, or their own size, by resizing it.
// get the size the window would have been if it had been in the
// standard state, given the old size of the contents
NSSize oldZoomedWindowSize = [self windowSizeForStackSize:oldStackSize];
NSSize curWindowSize = [[self window] frame].size;
// only resize if the window matches the stack size
if (CHCloseSizes(oldZoomedWindowSize, curWindowSize, 4.0))
[self resizeWindowToFit];
}
- (NSArray *)toolbarAllowedItemIdentifiers:(NSToolbar *)toolbar
// given the dimensions of our stack view, return the dimensions of the window,
// assuming the window is zoomed to show as much of the contents as possible.
- (NSSize)windowSizeForStackSize:(NSSize)stackSize
{
return [NSArray arrayWithObjects: CancelToolbarItemIdentifier,
ShowFileToolbarItemIdentifier,
OpenFileToolbarItemIdentifier,
LeaveOpenToolbarItemIdentifier,
NSToolbarCustomizeToolbarItemIdentifier,
NSToolbarFlexibleSpaceItemIdentifier,
NSToolbarSpaceItemIdentifier,
NSToolbarSeparatorItemIdentifier,
nil];
NSSize actualScrollFrame = [mScrollView frame].size;
NSSize scrollFrameSize = [NSScrollView frameSizeForContentSize:stackSize
hasHorizontalScroller:NO hasVerticalScroller:YES borderType:NSNoBorder];
// frameSizeForContentSize seems to return a width 1 pixel too narrow
scrollFrameSize.width += 1;
NSRect contentRect = [[[self window] contentView] frame];
contentRect.size.width += scrollFrameSize.width - actualScrollFrame.width;
contentRect.size.height += scrollFrameSize.height - actualScrollFrame.height;
contentRect.origin = [[self window] convertBaseToScreen:contentRect.origin]; // convert to screen
NSRect advisoryWindowFrame = [NSWindow frameRectForContentRect:contentRect styleMask:[[self window] styleMask]];
NSRect constrainedRect = [[self window] constrainFrameRect:advisoryWindowFrame toScreen:[[self window] screen]];
return constrainedRect.size;
}
- (NSArray *)toolbarDefaultItemIdentifiers:(NSToolbar *)toolbar
- (void)resizeWindowToFit
{
return [NSArray arrayWithObjects: CancelToolbarItemIdentifier,
NSToolbarFlexibleSpaceItemIdentifier,
LeaveOpenToolbarItemIdentifier,
NSToolbarFlexibleSpaceItemIdentifier,
ShowFileToolbarItemIdentifier,
OpenFileToolbarItemIdentifier,
nil];
if ([mProgressViewControllers count] > 0)
{
NSSize scrollFrameSize = [NSScrollView frameSizeForContentSize:[mStackView bounds].size
hasHorizontalScroller:NO hasVerticalScroller:YES borderType:NSNoBorder];
NSSize curScrollFrameSize = [mScrollView frame].size;
NSRect windowFrame = [[self window] frame];
float frameDelta = (scrollFrameSize.height - curScrollFrameSize.height);
windowFrame.size.height += frameDelta;
windowFrame.origin.y -= frameDelta; // maintain top
[[self window] setFrame:windowFrame display:YES];
}
}
- (BOOL)validateToolbarItem:(NSToolbarItem *)toolbarItem
- (void)rebuildViews
{
if ([toolbarItem action] == @selector(cancel)) // cancel button
return (!mDownloadIsComplete);
if ([toolbarItem action] == @selector(pauseAndResumeDownload)) // pause/resume button
return (NO); // Hey - it hasn't been hooked up yet. !mDownloadIsComplete when it is.
if ([toolbarItem action] == @selector(showFile)) // show file
return (mDownloadIsComplete);
if ([toolbarItem action] == @selector(openFile)) // open file
return (mDownloadIsComplete);
return YES; // turn it on otherwise.
[mStackView reloadSubviews];
if ([mProgressViewControllers count] == 0)
{
[[[self window] contentView] addSubview:mNoDownloadsText];
}
else
{
[mNoDownloadsText removeFromSuperview];
}
}
- (int)numDownloadsInProgress
{
unsigned int numViews = [mProgressViewControllers count];
int numActive = 0;
for (unsigned int i = 0; i < numViews; i++)
{
if ([[mProgressViewControllers objectAtIndex:i] isActive])
++numActive;
}
return numActive;
}
-(void)autosaveWindowFrame
{
[[self window] saveFrameUsingName: ProgressWindowFrameSaveName];
}
- (NSToolbarItem *) toolbar:(NSToolbar *)toolbar
itemForItemIdentifier:(NSString *)itemIdent
willBeInsertedIntoToolbar:(BOOL)willBeInserted
{
NSToolbarItem *toolbarItem = [[[NSToolbarItem alloc] initWithItemIdentifier:itemIdent] autorelease];
if ( [itemIdent isEqual:CancelToolbarItemIdentifier] )
{
[toolbarItem setLabel:NSLocalizedString(@"Cancel",@"Cancel")];
[toolbarItem setPaletteLabel:NSLocalizedString(@"CancelPaletteLabel",@"Cancel Download")];
[toolbarItem setToolTip:NSLocalizedString(@"CancelToolTip",@"Cancel this file download")];
[toolbarItem setImage:[NSImage imageNamed:@"saveCancel"]];
[toolbarItem setTarget:self];
[toolbarItem setAction:@selector(cancel)];
}
else if ( [itemIdent isEqual:ShowFileToolbarItemIdentifier] )
{
[toolbarItem setLabel:NSLocalizedString(@"Show File",@"Show File")];
[toolbarItem setPaletteLabel:NSLocalizedString(@"Show File",@"Show File")];
[toolbarItem setToolTip:NSLocalizedString(@"ShowToolTip",@"Show the saved file in the Finder")];
[toolbarItem setImage:[NSImage imageNamed:@"saveShowFile"]];
[toolbarItem setTarget:self];
[toolbarItem setAction:@selector(showFile)];
}
else if ( [itemIdent isEqual:OpenFileToolbarItemIdentifier] )
{
[toolbarItem setLabel:NSLocalizedString(@"Open File",@"Open File")];
[toolbarItem setPaletteLabel:NSLocalizedString(@"Open File",@"Open File")];
[toolbarItem setToolTip:NSLocalizedString(@"OpenToolTip",@"Open the saved file in its default application.")];
[toolbarItem setImage:[NSImage imageNamed:@"saveOpenFile"]];
[toolbarItem setTarget:self];
[toolbarItem setAction:@selector(openFile)];
}
else if ( [itemIdent isEqual:LeaveOpenToolbarItemIdentifier] )
{
if ( !mIsFileSave && !mDoingAutoFileDownload )
{
if ( mSaveFileDialogShouldStayOpen )
{
[toolbarItem setLabel:NSLocalizedString(@"Leave Open",@"Leave Open")];
[toolbarItem setPaletteLabel:NSLocalizedString(@"Toggle Close Behavior",@"Toggle Close Behavior")];
[toolbarItem setToolTip:NSLocalizedString(@"LeaveOpenToolTip",@"Window will stay open when download finishes.")];
[toolbarItem setImage:[NSImage imageNamed:@"saveLeaveOpenYES"]];
[toolbarItem setTarget:self];
[toolbarItem setAction:@selector(toggleLeaveOpen)];
}
else
{
[toolbarItem setLabel:NSLocalizedString(@"Close When Done",@"Close When Done")];
[toolbarItem setPaletteLabel:NSLocalizedString(@"Toggle Close Behavior",@"Toggle Close Behavior")];
[toolbarItem setToolTip:NSLocalizedString(@"CloseWhenDoneToolTip",@"Window will close automatically when download finishes.")];
[toolbarItem setImage:[NSImage imageNamed:@"saveLeaveOpenNO"]];
[toolbarItem setTarget:self];
[toolbarItem setAction:@selector(toggleLeaveOpen)];
}
if ( willBeInserted )
{
leaveOpenToggleToolbarItem = toolbarItem; //establish reference
}
}
} else
{
toolbarItem = nil;
}
return toolbarItem;
}
-(void)cancel
{
if (mDownloader) // we should always have one
mDownloader->CancelDownload();
// clean up downloaded file. - do it here on in CancelDownload?
NSFileManager *fileManager = [NSFileManager defaultManager];
NSString *thePath = [[mToField stringValue] stringByExpandingTildeInPath];
if ([fileManager isDeletableFileAtPath:thePath])
// if we delete it, fantastic. if not, oh well. better to move to trash instead?
[fileManager removeFileAtPath:thePath handler:nil];
// we can _not_ set the |mDownloadIsComplete| flag here because the download really
// isn't done yet. We'll probably continue to process more PLEvents that are already
// in the queue until we get a STATE_STOP state change. As a result, we just keep
// going until that comes in (and it will, because we called CancelDownload() above).
// Ensure that the window goes away when we get there by flipping the 'stay alive'
// flag. (bug 154913)
mSaveFileDialogShouldStayOpen = NO;
}
-(void)showFile
{
NSString *theFile = [[mToField stringValue] stringByExpandingTildeInPath];
if ([[NSWorkspace sharedWorkspace] selectFile:theFile
inFileViewerRootedAtPath:[theFile stringByDeletingLastPathComponent]])
return;
// hmmm. it didn't work. that's odd. need localized error messages. for now, just beep.
NSBeep();
}
-(void)openFile
{
NSString *theFile = [[mToField stringValue] stringByExpandingTildeInPath];
if ([[NSWorkspace sharedWorkspace] openFile:theFile])
return;
// hmmm. it didn't work. that's odd. need localized error message. for now, just beep.
NSBeep();
}
-(void)toggleLeaveOpen
{
if ( ! mSaveFileDialogShouldStayOpen ) {
mSaveFileDialogShouldStayOpen = YES;
[leaveOpenToggleToolbarItem setLabel:NSLocalizedString(@"Leave Open",@"Leave Open")];
[leaveOpenToggleToolbarItem setPaletteLabel:NSLocalizedString(@"Toggle Close Behavior",@"Toggle Close Behavior")];
[leaveOpenToggleToolbarItem setToolTip:NSLocalizedString(@"LeaveOpenToolTip",@"Window will stay open when download finishes.")];
[leaveOpenToggleToolbarItem setImage:[NSImage imageNamed:@"saveLeaveOpenYES"]];
} else {
mSaveFileDialogShouldStayOpen = NO;
[leaveOpenToggleToolbarItem setLabel:NSLocalizedString(@"Close When Done",@"Close When Done")];
[leaveOpenToggleToolbarItem setPaletteLabel:NSLocalizedString(@"Toggle Close Behavior",@"Toggle Close Behavior")];
[leaveOpenToggleToolbarItem setToolTip:NSLocalizedString(@"CloseWhenDoneToolTip",@"Window will close automatically when download finishes.")];
[leaveOpenToggleToolbarItem setImage:[NSImage imageNamed:@"saveLeaveOpenNO"]];
}
nsCOMPtr<nsIPref> prefs(do_GetService(NS_PREF_CONTRACTID));
prefs->SetBoolPref("browser.download.progressDnldDialog.keepAlive", mSaveFileDialogShouldStayOpen);
[[self window] saveFrameUsingName:ProgressWindowFrameSaveName];
}
- (void)windowWillClose:(NSNotification *)notification
{
[self autosaveWindowFrame];
[self autorelease];
}
- (BOOL)windowShouldClose:(NSNotification *)notification
{
[self killDownloadTimer];
if (!mDownloadIsComplete) { //whoops. hard cancel.
[self cancel];
return NO; // let setDownloadProgress handle the close.
}
return YES;
}
- (void)killDownloadTimer
{
if (mDownloadTimer) {
if (mDownloadTimer)
{
[mDownloadTimer invalidate];
[mDownloadTimer release];
mDownloadTimer = nil;
}
}
}
- (void)setupDownloadTimer
{
[self killDownloadTimer];
mDownloadTimer = [[NSTimer scheduledTimerWithTimeInterval:1.0
target:self
selector:@selector(setDownloadProgress:)
userInfo:nil
repeats:YES] retain];
}
-(NSString *)formatTime:(int)seconds
{
NSMutableString *theTime =[[[NSMutableString alloc] initWithCapacity:8] autorelease];
[theTime setString:@""];
NSString *padZero = [NSString stringWithString:@"0"];
//write out new elapsed time
if (seconds >= 3600){
[theTime appendFormat:@"%d:",(seconds / 3600)];
seconds = seconds % 3600;
}
NSString *elapsedMin = [NSString stringWithFormat:@"%d:",(seconds / 60)];
if ([elapsedMin length] == 2)
[theTime appendString:[padZero stringByAppendingString:elapsedMin]];
else
[theTime appendString:elapsedMin];
seconds = seconds % 60;
NSString *elapsedSec = [NSString stringWithFormat:@"%d",seconds];
if ([elapsedSec length] == 2)
[theTime appendString:elapsedSec];
else
[theTime appendString:[padZero stringByAppendingString:elapsedSec]];
return theTime;
}
// fuzzy time gives back strings like "about 5 seconds"
-(NSString *)formatFuzzyTime:(int)seconds
{
// check for seconds first
if (seconds < 60) {
if (seconds < 7)
return [[[NSString alloc] initWithFormat:NSLocalizedString(@"UnderSec",@"Under %d seconds"),5] autorelease];
if (seconds < 13)
return [[[NSString alloc] initWithFormat:NSLocalizedString(@"UnderSec",@"Under %d seconds"),10] autorelease];
return [[[NSString alloc] initWithString:NSLocalizedString(@"UnderMin",@"Under a minute")] autorelease];
}
// seconds becomes minutes and we keep checking.
seconds = seconds/60;
if (seconds < 60) {
if (seconds < 2)
return [[[NSString alloc] initWithString:NSLocalizedString(@"AboutMin",@"About a minute")] autorelease];
// OK, tell the good people how much time we have left.
return [[[NSString alloc] initWithFormat:NSLocalizedString(@"AboutMins",@"About %d minutes"),seconds] autorelease];
}
//this download will never seemingly never end. now seconds become hours.
seconds = seconds/60;
if (seconds < 2)
return [[[NSString alloc] initWithString:NSLocalizedString(@"AboutHour",@"Over an hour")] autorelease];
return [[[NSString alloc] initWithFormat:NSLocalizedString(@"AboutHours",@"Over %d hours"),seconds] autorelease];
}
-(NSString *)formatBytes:(float)bytes
{ // this is simpler than my first try. I peaked at Omnigroup byte formatting code.
// if bytes are negative, we return question marks.
if (bytes < 0)
return [[[NSString alloc] initWithString:@"???"] autorelease];
// bytes first.
if (bytes < 1024)
return [[[NSString alloc] initWithFormat:@"%.1f bytes",bytes] autorelease];
// kb
bytes = bytes/1024;
if (bytes < 1024)
return [[[NSString alloc] initWithFormat:@"%.1f KB",bytes] autorelease];
// mb
bytes = bytes/1024;
if (bytes < 1024)
return [[[NSString alloc] initWithFormat:@"%.1f MB",bytes] autorelease];
// gb
bytes = bytes/1024;
return [[[NSString alloc] initWithFormat:@"%.1f GB",bytes] autorelease];
}
// this handles lots of things.
- (void)setDownloadProgress:(NSTimer *)downloadTimer;
{
// XXX this logic needs cleaning up.
// Ack! we're closing the window with the download still running!
if (mDownloadIsComplete)
mDownloadTimer = [[NSTimer scheduledTimerWithTimeInterval:1.0
target:self
selector:@selector(setDownloadProgress:)
userInfo:nil
repeats:YES] retain];
}
// Called by our timer to refresh all the download stats
- (void)setDownloadProgress:(NSTimer *)aTimer
{
[mProgressViewControllers makeObjectsPerformSelector:@selector(refreshDownloadInfo)];
// if the window is minimized, we want to update the dock image here. But how?
}
- (NSApplicationTerminateReply)allowTerminate
{
if ([self numDownloadsInProgress] > 0)
{
[[self window] performClose:self];
return;
// make sure the window is visible
[self showWindow:self];
NSString *alert = NSLocalizedString(@"QuitWithDownloadsMsg", @"Really Quit?");
NSString *message = NSLocalizedString(@"QuitWithDownloadsExpl", @"");
NSString *okButton = NSLocalizedString(@"QuitWithdownloadsButtonDefault",@"Cancel");
NSString *altButton = NSLocalizedString(@"QuitWithdownloadsButtonAlt",@"Quit");
// while the panel is up, download dialogs won't update (no timers firing) but
// downloads continue (PLEvents being processed)
id panel = NSGetAlertPanel(alert, message, okButton, altButton, nil, message);
[NSApp beginSheet:panel
modalForWindow:[self window]
modalDelegate:self
didEndSelector:@selector(sheetDidEnd:returnCode:contextInfo:)
contextInfo:NULL];
int sheetResult = [NSApp runModalForWindow: panel];
[NSApp endSheet: panel];
[panel orderOut: self];
NSReleaseAlertPanel(panel);
return (sheetResult == NSAlertDefaultReturn) ? NSTerminateCancel : NSTerminateNow;
}
// get the elapsed time
NSArray *elapsedTimeArray = [[mElapsedTimeLabel stringValue] componentsSeparatedByString:@":"];
int j = [elapsedTimeArray count];
int elapsedSec = [[elapsedTimeArray objectAtIndex:(j-1)] intValue] + [[elapsedTimeArray objectAtIndex:(j-2)] intValue]*60;
if (j==3) // this download is taking forever.
elapsedSec += [[elapsedTimeArray objectAtIndex:0] intValue]*3600;
// update elapsed time
[mElapsedTimeLabel setStringValue:[self formatTime:(++elapsedSec)]];
// for status field & time left
float maxBytes = ([mProgressBar maxValue]);
float byteSec = mCurrentProgress/elapsedSec;
// OK - if downloadTimer is nil, we're done - fix maxBytes value for status report.
if (!downloadTimer)
maxBytes = mCurrentProgress;
// update status field
NSString *labelString = NSLocalizedString(@"LabelString",@"%@ of %@ total (at %@/sec)");
[mStatusLabel setStringValue: [NSString stringWithFormat:labelString, [self formatBytes:mCurrentProgress], [self formatBytes:maxBytes], [self formatBytes:byteSec]]];
// updating estimated time left field
// if maxBytes < 0, can't calc time left.
// if !downloadTimer, download is finished. either way, make sure time left is 0.
if ((maxBytes > 0) && (downloadTimer))
{
int secToGo = (int)ceil((elapsedSec*maxBytes/mCurrentProgress) - elapsedSec);
[mTimeLeftLabel setStringValue:[self formatFuzzyTime:secToGo]];
}
else if (!downloadTimer)
{ // download done. Set remaining time to 0, fix progress bar & cancel button
mDownloadIsComplete = YES; // all done. we got a STATE_STOP
[mTimeLeftLabel setStringValue:@""];
[self setProgressTo:mCurrentProgress ofMax:mCurrentProgress];
if (!mSaveFileDialogShouldStayOpen || mDoingAutoFileDownload)
[[self window] performClose:self]; // close window
else
[[self window] update]; // redraw window
}
else //maxBytes is undetermined. Set remaining time to question marks.
[mTimeLeftLabel setStringValue:@"???"];
return NSTerminateNow;
}
- (void)sheetDidEnd:(NSWindow *)sheet returnCode:(int)returnCode contextInfo:(void *)contextInfo
{
[NSApp stopModalWithCode:returnCode];
}
#pragma mark -
// CHDownloadProgressDisplay protocol methods
- (void)onStartDownload:(BOOL)isFileSave;
// implement to zoom to a size that just fits the contents
- (NSRect)windowWillUseStandardFrame:(NSWindow *)sender defaultFrame:(NSRect)defaultFrame
{
mIsFileSave = isFileSave;
NSSize scrollFrameSize = [NSScrollView frameSizeForContentSize:[mStackView bounds].size
hasHorizontalScroller:NO hasVerticalScroller:YES borderType:NSNoBorder];
[self window]; // make the window
[[self window] setFrameUsingName: ProgressWindowFrameSaveName];
NSSize curScrollFrameSize = [mScrollView frame].size;
float frameDelta = (scrollFrameSize.height - curScrollFrameSize.height);
[self showWindow: self];
[self setupDownloadTimer];
gNumActiveDownloads++;
NSRect windowFrame = [[self window] frame];
windowFrame.size.height += frameDelta;
windowFrame.origin.y -= frameDelta; // maintain top
windowFrame.size.width = mDefaultWindowSize.width;
// cocoa will ensure that the window fits onscreen for us
return windowFrame;
}
- (void)onEndDownload
#pragma mark -
/*
CHStackView datasource methods
*/
- (int)subviewsForStackView:(CHStackView *)stackView
{
gNumActiveDownloads --;
return [mProgressViewControllers count];
}
- (NSView *)viewForStackView:(CHStackView *)aResizingView atIndex:(int)index
{
return [[mProgressViewControllers objectAtIndex:index] view];
}
#pragma mark -
/*
Just create a progress view, but don't display it (otherwise the URL fields etc.
are just blank)
*/
- (id <CHDownloadProgressDisplay>)createProgressDisplay
{
ProgressViewController *newController = [[ProgressViewController alloc] init];
[newController setProgressWindowController:self];
[mProgressViewControllers addObject:newController];
// if we're quitting, our progress window is already gone and we're in the
// process of shutting down gecko and all the d/l listeners. The timer, at
// that point, is the only thing keeping us alive. Killing it will cause
// us to go away immediately, so kung-fu deathgrip it until we're done twiddling
// bits on ourself.
[self retain]; // Enter The Dragon!
[self killDownloadTimer];
[self setDownloadProgress:nil];
[self release];
}
- (void)setProgressTo:(long)aCurProgress ofMax:(long)aMaxProgress
{
mCurrentProgress = aCurProgress; // fall back for stat calcs
if (![mProgressBar isIndeterminate]) //most likely - just update value
{
if (aCurProgress == aMaxProgress) //handles little bug in FTP download size
[mProgressBar setMaxValue:aMaxProgress];
[mProgressBar setDoubleValue:aCurProgress];
}
else if (aMaxProgress > 0) // ok, we're starting up with good max & cur values
{
[mProgressBar setIndeterminate:NO];
[mProgressBar setMaxValue:aMaxProgress];
[mProgressBar setDoubleValue:aCurProgress];
} // if neither case was true, it's barber pole city.
}
-(void) setDownloadListener: (CHDownloader*)aDownloader
{
if (mDownloader != aDownloader)
NS_IF_RELEASE(mDownloader);
NS_IF_ADDREF(mDownloader = aDownloader);
}
- (void)setSourceURL:(NSString*)aSourceURL
{
[mFromField setStringValue: aSourceURL];
[mFromField display]; // force an immmeditate update
}
- (void)setDestinationPath:(NSString*)aDestPath
{
[mToField setStringValue: [aDestPath stringByAbbreviatingWithTildeInPath]];
[mToField display]; // force an immmeditate update
// also set the window title
NSString* downloadFileName = [aDestPath lastPathComponent];
if ([downloadFileName length] == 0)
downloadFileName = aDestPath;
[[self window] setTitle:[NSString stringWithFormat:NSLocalizedString(@"DownloadingTitle", @""), downloadFileName]];
return newController;
}
@end

Просмотреть файл

@ -0,0 +1,105 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: NPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Netscape Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/NPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 2002
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Calum Robinson <calumr@mac.com>
* Simon Fraser <sfraser@netscape.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the NPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the NPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#import "CHDownloadProgressDisplay.h"
class CHDownloader;
@class ProgressDlgController;
@interface ProgressViewController : NSObject<CHDownloadProgressDisplay>
{
// we share one progress bar between both views. It's in the expanded
// view by default
IBOutlet NSProgressIndicator *mProgressBar;
// in-progress expanded view
IBOutlet NSView *mProgressView;
IBOutlet NSButton *mExpandedCancelButton;
// in-progress collapsed view
IBOutlet NSView *mProgressViewCompact;
// completed expanded view
IBOutlet NSView *mCompletedView;
IBOutlet NSButton *mExpandedRevealButton;
IBOutlet NSButton *mExpandedOpenButton;
// completed collapsed view
IBOutlet NSView *mCompletedViewCompact;
BOOL mViewIsCompact;
BOOL mIsFileSave;
BOOL mUserCancelled;
BOOL mDownloadingError;
BOOL mDownloadDone;
BOOL mRemoveWhenDone;
NSTimeInterval mDownloadTime; // only set when done
long mCurrentProgress; // if progress bar is indeterminate, can still calc stats.
long mDownloadSize;
NSString *mSourceURL;
NSString *mDestPath;
NSDate *mStartTime;
CHDownloader *mDownloader; // we hold a ref to this
ProgressDlgController *mProgressWindowController; // not retained
}
+ (NSString *)formatTime:(int)aSeconds;
+ (NSString *)formatFuzzyTime:(int)aSeconds;
+ (NSString *)formatBytes:(float)aBytes;
- (NSView *)view;
- (IBAction)close:(id)sender;
- (IBAction)stop:(id)sender;
- (IBAction)toggleDisclosure:(id)sender;
- (IBAction)reveal:(id)sender;
- (IBAction)open:(id)sender;
- (BOOL)isActive;
- (void)setProgressWindowController:(ProgressDlgController*)progressWindowController;
@end

Просмотреть файл

@ -0,0 +1,544 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: NPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Netscape Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/NPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 2002
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Calum Robinson <calumr@mac.com>
* Simon Fraser <sfraser@netscape.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the NPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the NPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#import "NSView+Utils.h"
#import "ProgressViewController.h"
#import "ProgressDlgController.h"
#import "PreferenceManager.h"
enum
{
kLabelTagFilename = 1000,
kLabelTagProgress,
kLabelTagSource,
kLabelTagDestination,
kLabelTagTimeRemaining,
kLabelTagStatus, // 1005
kLabelTagTimeRemainingLabel
};
// Notification sent when user holds option key and expands/contracts a progress view
static NSString *ProgressViewsShouldResize = @"ProgressViewsShouldResize";
@interface ProgressViewController(ProgressViewControllerPrivate)
- (void)viewDidLoad;
- (void)refreshDownloadInfo;
- (void)moveProgressBarToCurrentView;
- (void)updateButtons;
@end
@implementation ProgressViewController
+ (NSString *)formatTime:(int)seconds
{
NSMutableString *theTime = [NSMutableString stringWithCapacity:8];
NSString *padZero = [NSString stringWithString:@"0"];
//write out new elapsed time
if (seconds >= 3600)
{
[theTime appendFormat:@"%d:",(seconds / 3600)];
seconds = seconds % 3600;
}
NSString *elapsedMin = [NSString stringWithFormat:@"%d:",(seconds / 60)];
if ([elapsedMin length] == 2)
[theTime appendString:[padZero stringByAppendingString:elapsedMin]];
else
[theTime appendString:elapsedMin];
seconds = seconds % 60;
NSString *elapsedSec = [NSString stringWithFormat:@"%d",seconds];
if ([elapsedSec length] == 2)
[theTime appendString:elapsedSec];
else
[theTime appendString:[padZero stringByAppendingString:elapsedSec]];
return theTime;
}
// fuzzy time gives back strings like "about 5 seconds"
+ (NSString *)formatFuzzyTime:(int)seconds
{
// check for seconds first
if (seconds < 60) {
if (seconds < 7)
return [NSString stringWithFormat:NSLocalizedString(@"UnderSec", @"Under %d seconds"), 5];
if (seconds < 13)
return [NSString stringWithFormat:NSLocalizedString(@"UnderSec", @"Under %d seconds"), 10];
return [NSString stringWithFormat:NSLocalizedString(@"UnderMin", @"Under a minute")];
}
// seconds becomes minutes and we keep checking.
seconds = seconds/60;
if (seconds < 60) {
if (seconds < 2)
return [NSString stringWithFormat:NSLocalizedString(@"AboutMin",@"About a minute")];
// OK, tell the good people how much time we have left.
return [NSString stringWithFormat:NSLocalizedString(@"AboutMins",@"About %d minutes"), seconds];
}
//this download will never seemingly never end. now seconds become hours.
seconds = seconds/60;
if (seconds < 2)
return [NSString stringWithFormat:NSLocalizedString(@"AboutHour", @"Over an hour")];
return [NSString stringWithFormat:NSLocalizedString(@"AboutHours", @"Over %d hours"), seconds];
}
+ (NSString *)formatBytes:(float)bytes
{
// if bytes are negative, we return question marks.
if (bytes < 0)
return [NSString stringWithString:@"?"];
// bytes first.
if (bytes < 1024)
return [NSString stringWithFormat:@"%.1f bytes",bytes];
// kb
bytes = bytes/1024;
if (bytes < 1024)
return [NSString stringWithFormat:@"%.1f KB",bytes];
// mb
bytes = bytes/1024;
if (bytes < 1024)
return [NSString stringWithFormat:@"%.1f MB",bytes];
// gb
bytes = bytes/1024;
return [NSString stringWithFormat:@"%.1f GB",bytes];
}
#pragma mark -
- (id)init
{
if ((self = [super init]))
{
[NSBundle loadNibNamed:@"ProgressView" owner:self];
[self viewDidLoad];
// Register for notifications when one of the progress views is expanded/contracted
// whilst holding the option button
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(changeCollapsedStateNotification:)
name:ProgressViewsShouldResize
object:nil];
[mExpandedRevealButton setEnabled:NO];
[mExpandedOpenButton setEnabled:NO];
}
return self;
}
- (void)dealloc
{
[[NSNotificationCenter defaultCenter] removeObserver:self
name:ProgressViewsShouldResize
object:nil];
// if we get here because we're quitting, the listener will still be alive
// yet we're going away. As a result, we need to tell the d/l listener to
// forget it ever met us and necko will clean it up on its own.
if (mDownloader)
mDownloader->DetachDownloadDisplay();
NS_IF_RELEASE(mDownloader);
[mStartTime release];
[mSourceURL release];
[mDestPath release];
[mProgressBar release];
[super dealloc];
}
// Save the expand/contract view pref (called when the user clicks the dislosure triangle)
- (void)setCompactViewPref
{
[[PreferenceManager sharedInstance] setPref:"browser.download.compactView" toBoolean:mViewIsCompact];
}
- (void)viewDidLoad
{
mViewIsCompact = [[PreferenceManager sharedInstance] getBooleanPref:"browser.download.compactView" withSuccess:NULL];
[mProgressBar retain]; // make sure it survives being moved between views
if (mViewIsCompact)
[self moveProgressBarToCurrentView];
// this isn't necessarily better. Need to profile.
[mProgressBar setUsesThreadedAnimation:YES];
}
- (NSView *)view
{
if (mViewIsCompact)
return (mDownloadDone ? mCompletedViewCompact : mProgressViewCompact);
else
return (mDownloadDone ? mCompletedView : mProgressView);
}
- (IBAction)toggleDisclosure:(id)sender
{
mViewIsCompact = !mViewIsCompact;
[self moveProgressBarToCurrentView];
// Is option/alt held down?
if ([[[sender window] currentEvent] modifierFlags] & NSAlternateKeyMask)
{
// Get all progress views to look the same as self
[[NSNotificationCenter defaultCenter] postNotificationName:ProgressViewsShouldResize
object:[NSNumber numberWithBool:mViewIsCompact]];
}
// Set the pref only when the user clicks the disclosure triangle
[self setCompactViewPref];
// Re-calculate the new view & window sizes
[[NSNotificationCenter defaultCenter] postNotificationName:StackViewReloadNotificationName
object:self];
[self refreshDownloadInfo];
}
- (void)changeCollapsedStateNotification:(NSNotification *)notification
{
// note that this will get called on the view that is being clicked, as well
// as the other views. Don't do redundant work here, like redrawing.
mViewIsCompact = [[notification object] boolValue];
// Don't call [enclosingStackView reloadSubviews]; here, because it will be done
// by the original view that was option-clicked, not us
}
-(void)cancel
{
mUserCancelled = YES;
if (mDownloader) // we should always have one
mDownloader->CancelDownload();
// clean up downloaded file. - do it here or in CancelDownload?
NSFileManager *fileManager = [NSFileManager defaultManager];
if ([fileManager isDeletableFileAtPath:mDestPath])
{
// if we delete it, fantastic. if not, oh well. better to move to trash instead?
[fileManager removeFileAtPath:mDestPath handler:nil];
}
}
- (IBAction)close:(id)sender
{
if (!mDownloadDone)
{
mRemoveWhenDone = YES;
[self cancel];
}
else
{
[mProgressWindowController removeDownload:self];
}
}
- (IBAction)stop:(id)sender
{
[self cancel];
}
- (IBAction)reveal:(id)sender
{
if ([[NSWorkspace sharedWorkspace] selectFile:mDestPath
inFileViewerRootedAtPath:[mDestPath stringByDeletingLastPathComponent]])
return;
// hmmm. it didn't work. that's odd. need localized error messages. for now, just beep.
NSBeep();
}
- (IBAction)open:(id)sender
{
if ([[NSWorkspace sharedWorkspace] openFile:mDestPath])
return;
// hmmm. it didn't work. that's odd. need localized error message. for now, just beep.
NSBeep();
}
// Called just before the view will be shown to the user
- (void)downloadDidStart
{
mStartTime = [[NSDate alloc] init];
// [mProgressBar startAnimation:self]; // moved to onStartDownload
[self refreshDownloadInfo];
}
- (void)downloadDidEnd
{
mDownloadDone = YES;
mDownloadTime = -[mStartTime timeIntervalSinceNow];
[mProgressBar stopAnimation:self];
[mExpandedCancelButton setEnabled:NO];
[self refreshDownloadInfo];
}
// this handles lots of things.
- (void)refreshDownloadInfo
{
NSView* curView = [self view];
NSString* filename = [mSourceURL lastPathComponent];
NSString *destPath = [mDestPath stringByAbbreviatingWithTildeInPath];
NSString* tooltipFormat = NSLocalizedString(mDownloadDone ? @"DownloadedTooltipFormat" : @"DownloadingTooltipFormat", @"");
id filenameLabel = [curView viewWithTag:kLabelTagFilename];
[filenameLabel setStringValue:filename];
[filenameLabel setToolTip:[NSString stringWithFormat:tooltipFormat, [mSourceURL lastPathComponent], mSourceURL, destPath]];
id destLabel = [curView viewWithTag:kLabelTagDestination];
[destLabel setStringValue:destPath];
id locationLabel = [curView viewWithTag:kLabelTagSource];
[locationLabel setStringValue:mSourceURL];
if (mDownloadDone)
{
id statusLabel = [curView viewWithTag:kLabelTagStatus];
if (statusLabel)
{
NSString* statusString;
if (mUserCancelled)
statusString = NSLocalizedString(@"DownloadCancelled", @"Cancelled");
else if (mDownloadingError)
statusString = NSLocalizedString(@"DownloadInterrupted", @"Interrupted");
else
statusString = NSLocalizedString(@"DownloadCompleted", @"Completed");
[statusLabel setStringValue: statusString];
}
// set progress label
id progressLabel = [curView viewWithTag:kLabelTagProgress];
if (progressLabel)
{
float byteSec = mCurrentProgress / mDownloadTime;
// show how much we downloaded, become some types of disconnects make us think
// we finished successfully
[progressLabel setStringValue:[NSString stringWithFormat:
NSLocalizedString(@"DownloadDoneStatusString", @"%@ of %@ done (at %@/sec)"),
[[self class] formatBytes:mCurrentProgress],
[[self class] formatBytes:mDownloadSize],
[[self class] formatBytes:byteSec]]];
}
id timeLabel = [curView viewWithTag:kLabelTagTimeRemaining];
if (timeLabel)
[timeLabel setStringValue:[[self class] formatTime:(int)mDownloadTime]];
id timeLabelLabel = [curView viewWithTag:kLabelTagTimeRemainingLabel];
if (timeLabelLabel)
[timeLabelLabel setStringValue:NSLocalizedString(@"DownloadRemainingLabelDone", @"Time elapsed:")];
[self updateButtons];
}
else
{
NSTimeInterval elapsedTime = -[mStartTime timeIntervalSinceNow];
// update status field
id progressLabel = [curView viewWithTag:kLabelTagProgress];
if (progressLabel)
{
NSString *statusLabelString = NSLocalizedString(@"DownloadStatusString", @"%@ of %@ total (at %@/sec)");
float byteSec = mCurrentProgress / elapsedTime;
[progressLabel setStringValue:[NSString stringWithFormat:statusLabelString,
[[self class] formatBytes:mCurrentProgress],
(mDownloadSize > 0 ? [[self class] formatBytes:mDownloadSize] : @"?"),
[[self class] formatBytes:byteSec]]];
}
id timeLabel = [curView viewWithTag:kLabelTagTimeRemaining];
if (timeLabel)
{
if (mDownloadSize > 0)
{
int secToGo = (int)ceil((elapsedTime * mDownloadSize / mCurrentProgress) - elapsedTime);
[timeLabel setStringValue:[[self class] formatFuzzyTime:secToGo]];
}
else // mDownloadSize is undetermined. Set remaining time to question marks.
{
NSString *calculatingString = NSLocalizedString(@"DownloadCalculatingString", @"Unknown");
[timeLabel setStringValue:calculatingString];
}
}
}
}
- (void)updateButtons
{
// note: this will stat every time, which will be expensive! We could use
// FNNotify/FNSubscribe to avoid this (writing a Cocoa wrapper around it).
if (mDownloadDone && !mDownloadingError)
{
BOOL destFileExists = [[NSFileManager defaultManager] fileExistsAtPath:mDestPath];
[mExpandedRevealButton setEnabled:destFileExists];
[mExpandedOpenButton setEnabled:destFileExists];
}
}
- (void)moveProgressBarToCurrentView
{
[mProgressBar moveToView:(mViewIsCompact ? mProgressViewCompact : mProgressView) resize:YES];
[mProgressBar startAnimation:self]; // this is necessary to keep it animating for some reason
}
- (void)setProgressWindowController:(ProgressDlgController*)progressWindowController
{
mProgressWindowController = progressWindowController;
}
- (BOOL)isActive
{
return !mDownloadDone;
}
#pragma mark -
- (void)onStartDownload:(BOOL)isFileSave
{
mIsFileSave = isFileSave;
[self downloadDidStart];
[mProgressWindowController didStartDownload:self];
// need to do this after the view as been put in the window, otherwise it doesn't work
[mProgressBar startAnimation:self];
}
- (void)onEndDownload:(BOOL)completedOK
{
mDownloadingError = !completedOK;
[self downloadDidEnd];
[mProgressWindowController didEndDownload:self];
if (mRemoveWhenDone)
[mProgressWindowController removeDownload:self];
}
- (void)setProgressTo:(long)aCurProgress ofMax:(long)aMaxProgress
{
mCurrentProgress = aCurProgress; // fall back for stat calcs
mDownloadSize = aMaxProgress;
if (![mProgressBar isIndeterminate]) //most likely - just update value
{
if (aCurProgress == aMaxProgress) //handles little bug in FTP download size
[mProgressBar setMaxValue:aMaxProgress];
[mProgressBar setDoubleValue:aCurProgress];
}
else if (aMaxProgress > 0) // ok, we're starting up with good max & cur values
{
[mProgressBar setIndeterminate:NO];
[mProgressBar setMaxValue:aMaxProgress];
[mProgressBar setDoubleValue:aCurProgress];
} // if neither case was true, it's barber pole city.
}
-(void)setDownloadListener:(CHDownloader*)aDownloader
{
if (mDownloader != aDownloader)
NS_IF_RELEASE(mDownloader);
NS_IF_ADDREF(mDownloader = aDownloader);
}
#if 0
/*
This is kind of a hack. It should probably be done somewhere else so Mozilla can have
it too, but until Apple fixes the problems with the setting of comments without
reverting to Applescript, I have left it in.
Turned off for now, until we find a better way to do this. Won't Carbon APIs work?
*/
- (void)tryToSetFinderComments
{
if (mDestPath && mSourceURL)
{
CFURLRef fileURL = CFURLCreateWithFileSystemPath( NULL,
(CFStringRef)mDestPath,
kCFURLPOSIXPathStyle,
NO);
NSString *hfsPath = (NSString *)CFURLCopyFileSystemPath(fileURL,
kCFURLHFSPathStyle);
CFRelease(fileURL);
NSAppleScript *setCommentScript = [[NSAppleScript alloc] initWithSource:
[NSString stringWithFormat:@"tell application \"Finder\" to set comment of file \"%@\" to \"%@\"", hfsPath, mSourceURL]];
NSDictionary *errorInfo = NULL;
[setCommentScript executeAndReturnError:&errorInfo];
if (errorInfo)
{
NSLog(@"Get error when running AppleScript to set comments for '%@':\n %@",
mDestPath,
[errorInfo objectForKey:NSAppleScriptErrorMessage]);
}
}
}
#endif
- (void)setSourceURL:(NSString*)aSourceURL
{
[mSourceURL autorelease];
mSourceURL = [aSourceURL copy];
//[self tryToSetFinderComments];
}
- (void)setDestinationPath:(NSString*)aDestPath
{
[mDestPath autorelease];
mDestPath = [aDestPath copy];
//[self tryToSetFinderComments];
}
@end

Просмотреть файл

@ -56,7 +56,7 @@ public:
nsHeaderSniffer(nsIWebBrowserPersist* aPersist, nsIFile* aFile, nsIURI* aURL,
nsIDOMDocument* aDocument, nsIInputStream* aPostData,
const nsAString& aSuggestedFilename, PRBool aBypassCache,
NSView* aFilterView, NSPopUpButton* aFilterList);
NSView* aFilterView);
virtual ~nsHeaderSniffer();
NS_DECL_ISUPPORTS
@ -79,6 +79,5 @@ private:
nsCString mContentType;
nsCString mContentDisposition;
NSView* mFilterView;
NSPopUpButton* mFilterList;
};

Просмотреть файл

@ -38,6 +38,8 @@
#import "NSString+Utils.h"
#import "ChimeraUIConstants.h"
#include "SaveHeaderSniffer.h"
#include "netCore.h"
@ -56,7 +58,7 @@ const char* const persistContractID = "@mozilla.org/embedding/browser/nsWebBrows
nsHeaderSniffer::nsHeaderSniffer(nsIWebBrowserPersist* aPersist, nsIFile* aFile, nsIURI* aURL,
nsIDOMDocument* aDocument, nsIInputStream* aPostData,
const nsAString& aSuggestedFilename, PRBool aBypassCache,
NSView* aFilterView, NSPopUpButton* aFilterList)
NSView* aFilterView)
: mPersist(aPersist)
, mTmpFile(aFile)
, mURL(aURL)
@ -65,9 +67,8 @@ nsHeaderSniffer::nsHeaderSniffer(nsIWebBrowserPersist* aPersist, nsIFile* aFile,
, mDefaultFilename(aSuggestedFilename)
, mBypassCache(aBypassCache)
, mFilterView(aFilterView)
, mFilterList(aFilterList)
{
NS_INIT_ISUPPORTS();
NS_INIT_ISUPPORTS();
}
nsHeaderSniffer::~nsHeaderSniffer()
@ -183,14 +184,16 @@ nsresult nsHeaderSniffer::PerformSave(nsIURI* inOriginalURI)
return rv;
nsCOMPtr<nsIPrefBranch> dirBranch;
prefs->GetBranch("browser.download.", getter_AddRefs(dirBranch));
PRInt32 filterIndex = 0;
PRInt32 filterIndex = eSaveFormatHTMLComplete;
if (dirBranch) {
nsresult rv = dirBranch->GetIntPref("save_converter_index", &filterIndex);
if (NS_FAILED(rv))
filterIndex = 0;
filterIndex = eSaveFormatHTMLComplete;
}
if (mFilterList)
[mFilterList selectItemAtIndex: filterIndex];
NSPopUpButton* filterList = [mFilterView viewWithTag:kSaveFormatPopupTag];
if (filterList)
[filterList selectItemAtIndex: filterIndex];
// We need to figure out what file name to use.
nsAutoString defaultFileName;
@ -294,17 +297,17 @@ nsresult nsHeaderSniffer::PerformSave(nsIURI* inOriginalURI)
return NS_OK;
// Update the filter index.
if (isHTML && mFilterList) {
filterIndex = [mFilterList indexOfSelectedItem];
if (isHTML && filterList) {
filterIndex = [filterList indexOfSelectedItem];
dirBranch->SetIntPref("save_converter_index", filterIndex);
}
// Convert the content type to text/plain if it was selected in the filter.
if (isHTML && filterIndex == 2)
if (isHTML && filterIndex == eSaveFormatPlainText)
mContentType = "text/plain";
nsCOMPtr<nsISupports> sourceData;
if (isHTML && filterIndex != 1)
if (isHTML && filterIndex != eSaveFormatHTMLSource)
sourceData = do_QueryInterface(mDocument);
else
sourceData = do_QueryInterface(mURL);

Просмотреть файл

@ -21,6 +21,7 @@
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
* Calum Robinson <calumr@mac.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
@ -49,6 +50,8 @@
#include "nsIWebBrowserPersist.h"
#include "nsIURI.h"
#include "nsILocalFile.h"
#include "nsITimer.h"
#include "nsExternalHelperAppService.h"
@ -56,24 +59,28 @@
class nsDownloadListener : public CHDownloader,
public nsIDownload,
public nsIWebProgressListener
public nsIWebProgressListener,
public nsITimerCallback
{
public:
nsDownloadListener(DownloadControllerFactory* inDownloadControllerFactory);
nsDownloadListener();
virtual ~nsDownloadListener();
NS_DECL_ISUPPORTS_INHERITED
NS_DECL_NSIDOWNLOAD
NS_DECL_NSIWEBPROGRESSLISTENER
// nsITimerCallback
NS_IMETHOD Notify(nsITimer *timer);
public:
//void BeginDownload();
void InitDialog();
virtual void PauseDownload();
virtual void ResumeDownload();
virtual void CancelDownload();
virtual void DownloadDone();
virtual void DownloadDone(nsresult aStatus);
virtual void DetachDownloadDisplay();
private:
@ -84,10 +91,13 @@ private:
nsCOMPtr<nsIURI> mURI; // The URI of our source file. Null if we're saving a complete document.
nsCOMPtr<nsILocalFile> mDestination; // Our destination URL.
nsCOMPtr<nsITimer> mEndRefreshTimer; // Timer used to update the status to done
nsresult mDownloadStatus; // status from last nofication
PRInt64 mStartTime; // When the download started
PRPackedBool mBypassCache; // Whether we should bypass the cache or not.
PRPackedBool mNetworkTransfer; // true if the first OnStateChange has the NETWORK bit set
PRPackedBool mGotFirstStateChange; // true after we've seen the first OnStateChange
PRPackedBool mUserCanceled; // true if the user canceled the download
PRPackedBool mSentCancel; // true when we've notified the backend of the cancel
};

Просмотреть файл

@ -21,7 +21,7 @@
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
*
* Calum Robinson <calumr@mac.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
@ -46,20 +46,25 @@
#include "nsIURL.h"
#include "netCore.h"
nsDownloadListener::nsDownloadListener(DownloadControllerFactory* inControllerFactory)
: CHDownloader(inControllerFactory)
nsDownloadListener::nsDownloadListener()
: mDownloadStatus(NS_OK)
, mBypassCache(PR_FALSE)
, mNetworkTransfer(PR_FALSE)
, mGotFirstStateChange(PR_FALSE)
, mUserCanceled(PR_FALSE)
, mSentCancel(PR_FALSE)
{
mStartTime = LL_ZERO;
}
nsDownloadListener::~nsDownloadListener()
{
// if we go away before the timer fires, cancel it
if (mEndRefreshTimer)
mEndRefreshTimer->Cancel();
}
NS_IMPL_ISUPPORTS_INHERITED2(nsDownloadListener, CHDownloader, nsIDownload, nsIWebProgressListener)
NS_IMPL_ISUPPORTS_INHERITED3(nsDownloadListener, CHDownloader, nsIDownload, nsIWebProgressListener, nsITimerCallback)
#pragma mark -
@ -193,14 +198,14 @@ nsDownloadListener::OnProgressChange(nsIWebProgress *aWebProgress,
PRInt32 aCurTotalProgress,
PRInt32 aMaxTotalProgress)
{
if (mUserCanceled)
if (mUserCanceled && !mSentCancel)
{
if (mHelperAppLauncher)
mHelperAppLauncher->Cancel();
else if (aRequest)
aRequest->Cancel(NS_BINDING_ABORTED);
mUserCanceled = false;
mSentCancel = PR_TRUE;
}
[mDownloadDisplay setProgressTo:aCurTotalProgress ofMax:aMaxTotalProgress];
@ -236,7 +241,7 @@ nsDownloadListener::OnSecurityChange(nsIWebProgress *aWebProgress, nsIRequest *a
// Implementation of nsIWebProgressListener
/* void onStateChange (in nsIWebProgress aWebProgress, in nsIRequest aRequest, in unsigned long aStateFlags, in unsigned long aStatus); */
NS_IMETHODIMP
nsDownloadListener::OnStateChange(nsIWebProgress *aWebProgress, nsIRequest *aRequest, PRUint32 aStateFlags,
nsDownloadListener::OnStateChange(nsIWebProgress *aWebProgress, nsIRequest *aRequest, PRUint32 aStateFlags,
PRUint32 aStatus)
{
// NSLog(@"State changed: state %u, status %u", aStateFlags, aStatus);
@ -250,29 +255,64 @@ nsDownloadListener::OnStateChange(nsIWebProgress *aWebProgress, nsIRequest *aRe
// the window and controller. We will get this even in the event of a cancel,
// so this is the only place in the listener where we should kill the download.
if ((aStateFlags & STATE_STOP) && (!mNetworkTransfer || (aStateFlags & STATE_IS_NETWORK))) {
DownloadDone();
DownloadDone(aStatus);
}
return NS_OK;
}
#pragma mark -
// nsITimerCallback implementation
NS_IMETHODIMP nsDownloadListener::Notify(nsITimer *timer)
{
// resset the destination, since uniquifying the filename may have
// changed it
nsAutoString pathStr;
mDestination->GetPath(pathStr);
[mDownloadDisplay setDestinationPath: [NSString stringWith_nsAString:pathStr]];
// cancelling should give us a failure status
[mDownloadDisplay onEndDownload:(NS_SUCCEEDED(mDownloadStatus) && !mUserCanceled)];
mEndRefreshTimer = NULL;
return NS_OK;
}
#pragma mark -
void
nsDownloadListener::InitDialog()
{
// dialog has to be shown before the outlets get hooked up
[mDownloadDisplay onStartDownload:(BOOL)IsFileSave()];
if (mURI)
{
nsCAutoString spec;
mURI->GetSpec(spec);
// we need to be careful not to show a password in the url
nsCAutoString userPassword;
mURI->GetUserPass(userPassword);
if (!userPassword.IsEmpty())
{
// ugh, build it by hand
nsCAutoString hostport, path;
mURI->GetScheme(spec);
mURI->GetHostPort(hostport);
mURI->GetPath(path);
spec.Append("://");
spec.Append(hostport);
spec.Append(path);
}
else
mURI->GetSpec(spec);
[mDownloadDisplay setSourceURL: [NSString stringWithUTF8String:spec.get()]];
}
nsAutoString pathStr;
mDestination->GetPath(pathStr);
[mDownloadDisplay setDestinationPath: [NSString stringWith_nsAString:pathStr]];
[mDownloadDisplay onStartDownload:IsFileSave()];
}
void
@ -292,19 +332,19 @@ nsDownloadListener::CancelDownload()
{
mUserCanceled = PR_TRUE;
if (mWebPersist)
if (mWebPersist && !mSentCancel)
{
mWebPersist->CancelSave();
mUserCanceled = PR_FALSE;
mSentCancel = PR_TRUE;
}
// delete any files we've created...
// DownloadDone will get called (eventually)
}
void
nsDownloadListener::DownloadDone()
nsDownloadListener::DownloadDone(nsresult aStatus)
{
// break the reference cycle by removing ourselves as a listener
if (mWebPersist)
@ -314,8 +354,23 @@ nsDownloadListener::DownloadDone()
}
mHelperAppLauncher = nsnull;
[mDownloadDisplay onEndDownload];
mDownloadStatus = aStatus;
// hack alert!
// Our destination file gets uniquified after the OnStop notification is sent
// (in nsExternalAppHandler::ExecuteDesiredAction), so we never get a chance
// to figure out the final filename. To work around this, set a timer to fire
// in the near future, from which we'll send the done callback.
mEndRefreshTimer = do_CreateInstance("@mozilla.org/timer;1");
if (mEndRefreshTimer)
{
nsresult rv = mEndRefreshTimer->InitWithCallback(this, 0, nsITimer::TYPE_ONE_SHOT); // defaults to 1-shot, normal priority
if (NS_FAILED(rv))
mEndRefreshTimer = NULL;
}
if (!mEndRefreshTimer) // timer creation or init failed, so just do it now
[mDownloadDisplay onEndDownload:(NS_SUCCEEDED(aStatus) && !mUserCanceled)];
}
//

Просмотреть файл

@ -38,7 +38,6 @@
#import "NSString+Utils.h"
#import "CHBrowserService.h"
#import "CHDownloadFactories.h"
#import "CHBrowserView.h"
#include "nsIWindowWatcher.h"
@ -107,14 +106,6 @@ CHBrowserService::InitEmbedding()
static NS_DEFINE_CID(kHelperDlgCID, NS_HELPERAPPLAUNCHERDIALOG_CID);
nsresult rv = cr->RegisterFactory(kHelperDlgCID, NS_IHELPERAPPLAUNCHERDLG_CLASSNAME, NS_IHELPERAPPLAUNCHERDLG_CONTRACTID,
sSingleton);
// replace the downloader with our own which does not rely on the xpfe downlaod manager
nsCOMPtr<nsIFactory> downloadFactory;
rv = NewDownloadListenerFactory(getter_AddRefs(downloadFactory));
if (NS_FAILED(rv)) return rv;
static NS_DEFINE_CID(kDownloadCID, NS_DOWNLOAD_CID);
rv = cr->RegisterFactory(kDownloadCID, "Download", NS_DOWNLOAD_CONTRACTID, downloadFactory);
return rv;
}

Просмотреть файл

@ -163,9 +163,8 @@ enum {
// nsIWebBrowserSetup methods
- (void)setProperty:(unsigned int)property toValue:(unsigned int)value;
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList;
- (void)saveURL: (NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList
url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename;
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView;
- (void)saveURL:(NSView*)aFilterView url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename;
- (void)printDocument;
- (void)pageSetup;

Просмотреть файл

@ -430,7 +430,6 @@ const char kDirServiceContractID[] = "@mozilla.org/file/directory_service;1";
suggestedFilename: (NSString*)aFileName
bypassCache: (BOOL)aBypassCache
filterView: (NSView*)aFilterView
filterList: (NSPopUpButton*)aFilterList
{
// Create our web browser persist object. This is the object that knows
// how to actually perform the saving of the page (and of the images
@ -477,7 +476,7 @@ const char kDirServiceContractID[] = "@mozilla.org/file/directory_service;1";
[aFileName assignTo_nsAString:fileName];
nsHeaderSniffer* sniffer = new nsHeaderSniffer(webPersist, tmpFile, aURI,
aDocument, postData, fileName, aBypassCache,
aFilterView, aFilterList);
aFilterView);
if (!sniffer)
return;
webPersist->SetProgressListener(sniffer); // owned
@ -572,8 +571,7 @@ const char kDirServiceContractID[] = "@mozilla.org/file/directory_service;1";
return found;
}
- (void)saveURL: (NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList
url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename
- (void)saveURL: (NSView*)aFilterView url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename
{
nsCOMPtr<nsIURI> url;
nsresult rv = NS_NewURI(getter_AddRefs(url), [aURLSpec UTF8String]);
@ -584,8 +582,7 @@ const char kDirServiceContractID[] = "@mozilla.org/file/directory_service;1";
withDocument: nsnull
suggestedFilename: aFilename
bypassCache: YES
filterView: aFilterView
filterList: aFilterList];
filterView: aFilterView];
}
-(NSString*)getFocusedURLString
@ -616,7 +613,7 @@ const char kDirServiceContractID[] = "@mozilla.org/file/directory_service;1";
return [NSString stringWith_nsAString: urlStr];
}
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView
{
if (!_webBrowser)
return;
@ -656,8 +653,7 @@ const char kDirServiceContractID[] = "@mozilla.org/file/directory_service;1";
withDocument: domDocument
suggestedFilename: @""
bypassCache: NO
filterView: aFilterView
filterList: aFilterList];
filterView: aFilterView];
}
-(void)doCommand:(const char*)commandName

Просмотреть файл

@ -20,6 +20,7 @@
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
* Calum Robinson <calumr@mac.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
@ -45,19 +46,17 @@
1. The CHDownloadProgressDisplay protocol.
This is a formal protocol that needs to be implemented by
a window controller for your progress window. Its methods
will be called by the underlying C++ downloading classes.
an object (eg. a window controller or a view controller)
for your progress window. Its methods will be called by the
underlying C++ downloading classes.
2. The Obj-C DownloadControllerFactory class.
This class should be subclassed by an embedder, with an
implementation of 'createDownloadController' that hands back
a new instance of an NSWindowController that implements the
<CHDownloadProgressDisplay> protocol.
The underlying C++ classes use this factory to create the
progress window controller.
2. The CHDownloadDisplayFactory protocol
This is a formal protocol that can be implemented by
any object that can create objects that themselves
implement CHDownloadProgressDisplay. This would probably be
an NSWindowController.
3. The CHDownloader C++ class
This base class exists to hide the complextity of the download
@ -90,10 +89,10 @@
In both cases, creating the nsDownloadListener and calling its Init() method
calls nsDownloder::CreateDownloadDisplay(). The nsDownloder has as a member
variable a DownloadControllerFactory (see above), which got passed to it
via our XPCOM factory for nsIDownload objects. It then uses that DownloadControllerFactory
to get an instance of the download progress window controller, which then
shows the download progress window.
variable an object that implements CHDownloadDisplayFactory (see above), which got set
on it via a call to SetDisplayFactory. It then uses that CHDownloadDisplayFactory
to create an instance of the download progress display, which then controls
something (like a view or window) that shows in the UI.
Simple, eh?
@ -105,13 +104,13 @@
class CHDownloader;
// a formal protocol for something that implements progress display
// Embedders can make a window controller that conforms to this
// A formal protocol for something that implements progress display.
// Embedders can make a window or view controller that conforms to this
// protocol, and reuse nsDownloadListener to get download UI.
@protocol CHDownloadProgressDisplay
- (void)onStartDownload:(BOOL)isFileSave;
- (void)onEndDownload;
- (void)onEndDownload:(BOOL)completedOK;
- (void)setProgressTo:(long)aCurProgress ofMax:(long)aMaxProgress;
@ -121,35 +120,34 @@ class CHDownloader;
@end
// subclass this, and have your subclass instantiate and return your window
// controller in createDownloadController
@interface DownloadControllerFactory : NSObject
{
}
// A formal protocol which is implemented by a factory of progress UI.
@protocol CHDownloadDisplayFactory
- (NSWindowController<CHDownloadProgressDisplay> *)createDownloadController;
- (id <CHDownloadProgressDisplay>)createProgressDisplay;
@end
// Pure virtual base class for a generic downloader, that the progress UI can talk to.
// It implements nsISupports so that it can be refcounted. This class insulates the
// UI code from having to know too much about the nsIDownloadListener.
// It is responsible for creating the download UI, via the DownloadControllerFactory
// UI code from having to know too much about the nsDownloadListener.
// It is responsible for creating the download UI, via the CHDownloadController
// that it owns.
class CHDownloader : public nsISupports
{
public:
CHDownloader(DownloadControllerFactory* inControllerFactory);
CHDownloader();
virtual ~CHDownloader();
NS_DECL_ISUPPORTS
virtual void SetDisplayFactory(id<CHDownloadDisplayFactory> inDownloadDisplayFactory); // retains
virtual void PauseDownload() = 0;
virtual void ResumeDownload() = 0;
virtual void CancelDownload() = 0;
virtual void DownloadDone() = 0;
virtual void DetachDownloadDisplay() = 0; // tell downloader to forget about its display
virtual void DownloadDone(nsresult aStatus) = 0;
virtual void DetachDownloadDisplay() = 0; // tell downloader to forget about its display
virtual void CreateDownloadDisplay();
@ -160,8 +158,8 @@ protected:
protected:
DownloadControllerFactory* mControllerFactory;
id <CHDownloadProgressDisplay> mDownloadDisplay; // something that implements the CHDownloadProgressDisplay protocol
PRBool mIsFileSave; // true if we're doing a save, rather than a download
id<CHDownloadDisplayFactory> mDisplayFactory;
id<CHDownloadProgressDisplay> mDownloadDisplay; // something that implements the CHDownloadProgressDisplay protocol
PRBool mIsFileSave; // true if we're doing a save, rather than a download
};

Просмотреть файл

@ -20,6 +20,7 @@
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
* Calum Robinson <calumr@mac.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
@ -37,40 +38,34 @@
#import "CHDownloadProgressDisplay.h"
// CHDownloader is a simple class that that the download UI can talk to
@implementation DownloadControllerFactory
- (NSWindowController<CHDownloadProgressDisplay> *)createDownloadController
{
// a dummy implementation. You should provide a subclass that
// returns an instance of your progress dialog controller.
return nil;
}
@end
#pragma mark -
// see the header file for comments
CHDownloader::CHDownloader(DownloadControllerFactory* inControllerFactory)
: mControllerFactory(inControllerFactory)
CHDownloader::CHDownloader()
: mDisplayFactory(NULL)
, mDownloadDisplay(nil)
, mIsFileSave(PR_FALSE)
{
NS_INIT_ISUPPORTS();
[mControllerFactory retain];
}
CHDownloader::~CHDownloader()
{
[mControllerFactory release];
[mDisplayFactory release];
}
NS_IMPL_ISUPPORTS1(CHDownloader, nsISupports);
void
CHDownloader::SetDisplayFactory(id<CHDownloadDisplayFactory> inDownloadControllerFactory)
{
mDisplayFactory = inDownloadControllerFactory;
[mDisplayFactory retain];
}
void
CHDownloader::CreateDownloadDisplay()
{
mDownloadDisplay = [mControllerFactory createDownloadController];
NS_ASSERTION(mDisplayFactory, "Should have a UI factory");
mDownloadDisplay = [mDisplayFactory createProgressDisplay];
[mDownloadDisplay setDownloadListener:this];
}

Просмотреть файл

@ -0,0 +1,61 @@
/* ***** BEGIN LICENSE BLOCK *****
* Version: NPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Netscape Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/NPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is Chimera code.
*
* The Initial Developer of the Original Code is
* Calum Robinson.
* Portions created by the Initial Developer are Copyright (C) 2002
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Calum Robinson <calumr@mac.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the NPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the NPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#import <AppKit/AppKit.h>
// views contained in the stack should send this notification when they change size
extern NSString* StackViewReloadNotificationName;
// the stack view sends this notification after it has adjusted to subview sizes
extern NSString* StackViewResizedNotificationName;
@interface CHStackView : NSView
{
IBOutlet id mDataSource;
}
- (void)setDataSource:(id)aDataSource;
- (void)reloadSubviews;
@end
@protocol CHStackViewDataSource
- (int)subviewsForStackView:(CHStackView *)stackView;
- (NSView *)viewForStackView:(CHStackView *)stackView atIndex:(int)index;
@end

Просмотреть файл

@ -0,0 +1,143 @@
/* ***** BEGIN LICENSE BLOCK *****
* Version: NPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Netscape Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/NPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is Chimera code.
*
* The Initial Developer of the Original Code is
* Calum Robinson.
* Portions created by the Initial Developer are Copyright (C) 2002
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Calum Robinson <calumr@mac.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the NPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the NPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
/*
This class was inspired by the OAStack view from OmniGroup, but not copied directly. This
implementation is a little simpler, which is fine.
It's like NSTableView, except the data source returns views instead of strings/images etc.
*/
#import "CHStackView.h"
NSString* StackViewReloadNotificationName = @"ReloadStackView";
NSString* StackViewResizedNotificationName = @"StackViewResized";
@implementation CHStackView
- (id)initWithFrame:(NSRect)frameRect
{
if ((self = [super initWithFrame:frameRect]))
{
// Register for notifications when one of the subviews changes size
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(reloadNotification:)
name:StackViewReloadNotificationName
object:nil];
}
return self;
}
- (void)dealloc
{
[[NSNotificationCenter defaultCenter] removeObserver:self];
[super dealloc];
}
- (void)setDataSource:(id)aDataSource
{
mDataSource = aDataSource; // should this retain?
[self reloadSubviews];
}
- (void)reloadNotification:(NSNotification *)notification
{
[self reloadSubviews];
}
- (void)reloadSubviews
{
NSRect newFrame = [self frame];
NSSize oldSize = [self bounds].size;
int i, subviewCount = [mDataSource subviewsForStackView:self];
NSPoint nextOrigin = NSZeroPoint;
// we'll maintain the width of the stack view, assuming that it's
// scaled by its superview.
newFrame.size.height = 0.0;
[[self subviews] makeObjectsPerformSelector:@selector(removeFromSuperview)];
for (i = 0; i < subviewCount; i++)
{
NSView *subview = [mDataSource viewForStackView:self atIndex:i];
NSRect subviewFrame = [subview frame];
unsigned int autoResizeMask = [subview autoresizingMask];
if (autoResizeMask & NSViewWidthSizable)
subviewFrame.size.width = newFrame.size.width;
newFrame.size.height += NSHeight(subviewFrame);
subviewFrame.origin = nextOrigin;
[subview setFrame:subviewFrame];
nextOrigin.y += NSHeight(subviewFrame);
[self addSubview:subview];
// If there are more subviews, add a separator
if (i + 1 < subviewCount)
{
NSBox *separator = [[NSBox alloc] initWithFrame:
NSMakeRect(nextOrigin.x, nextOrigin.y - 1.0, NSWidth([subview frame]), 1.0)];
[separator setBoxType:NSBoxSeparator];
[separator setAutoresizingMask:NSViewWidthSizable];
[self addSubview:separator];
[separator release];
}
}
NSRect newBounds = newFrame;
newBounds.origin = NSZeroPoint;
[self setFrame:newFrame];
[self setNeedsDisplay:YES];
[[NSNotificationCenter defaultCenter] postNotificationName:StackViewResizedNotificationName
object:self
userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSValue valueWithSize:oldSize], @"oldsize", nil]];
}
- (BOOL)isFlipped
{
return YES;
}
@end

Просмотреть файл

@ -0,0 +1,60 @@
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is Chimera code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 2002
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#import <AppKit/AppKit.h>
#ifdef __cplusplus
extern "C" {
#endif
// utility routine; returns YES if the sizes are equal, with the given slop
BOOL CHCloseSizes(NSSize aSize, NSSize bSize, float slop);
#ifdef __cplusplus
}
#endif
// category on NSView to add utilities for easy view resizing etc.
@interface NSView(CHViewUtils)
// move the recipient view from its superview to the destView,
// maintaining the relative size and position of the view based
// on its autoresize flags.
- (void)moveToView:(NSView*)destView resize:(BOOL)resize;
@end

Просмотреть файл

@ -0,0 +1,154 @@
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is Chimera code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 2002
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#import "NSView+Utils.h"
BOOL CHCloseSizes(NSSize aSize, NSSize bSize, float slop)
{
return (fabs(aSize.width - bSize.width) <= slop) &&
(fabs(aSize.height - bSize.height) <= slop);
}
// mask has 3 bits: 0 = 1 scales, 1 = 2 scales, 2 = 3 scales.
static void RedistributeSpace(int resizeMask, float newWidth, /* in out */ float ioSpaces[3])
{
float oldWidth = ioSpaces[0] + ioSpaces[1] + ioSpaces[2];
if (resizeMask != 0)
{
switch (resizeMask)
{
// 1 scalable section
case 1: // first
ioSpaces[0] += newWidth - oldWidth; // it can go negative
break;
case 2: // middle
ioSpaces[1] += newWidth - oldWidth; // it can go negative
break;
case 4: // last
ioSpaces[2] += newWidth - oldWidth; // it can go negative
break;
// 2 scalable sections
case 3: // last fixed
{
float oldScaledWidth = ioSpaces[0] + ioSpaces[1];
float newScaledWidth = (newWidth - ioSpaces[2]);
ioSpaces[0] = newScaledWidth * (ioSpaces[0] / oldScaledWidth);
ioSpaces[1] = newScaledWidth * (ioSpaces[1] / oldScaledWidth);
break;
}
case 5: // middle fixed
{
float oldScaledWidth = ioSpaces[0] + ioSpaces[2];
float newScaledWidth = (newWidth - ioSpaces[1]);
ioSpaces[0] = newScaledWidth * (ioSpaces[0] / oldScaledWidth);
ioSpaces[2] = newScaledWidth * (ioSpaces[2] / oldScaledWidth);
break;
}
case 6: // first fixed
{
float oldScaledWidth = ioSpaces[1] + ioSpaces[2];
float newScaledWidth = (newWidth - ioSpaces[0]);
ioSpaces[1] = newScaledWidth * (ioSpaces[1] / oldScaledWidth);
ioSpaces[2] = newScaledWidth * (ioSpaces[2] / oldScaledWidth);
break;
}
// all scalable
case 7:
ioSpaces[0] *= newWidth / oldWidth;
ioSpaces[1] *= newWidth / oldWidth;
ioSpaces[2] *= newWidth / oldWidth;
break;
}
}
// otherwise nothing changes
}
@implementation NSView(CHViewUtils)
- (void)moveToView:(NSView*)destView resize:(BOOL)resize
{
//resize &= [destView autoresizesSubviews];
NSRect oldFrame = [self frame];
NSRect oldSuperBounds = [[self superview] bounds];
[self retain];
[self removeFromSuperview];
[destView addSubview:self];
[self release];
[destView setAutoresizesSubviews:YES];
if (resize)
{
unsigned int resizeMask = [self autoresizingMask];
NSRect newFrame = oldFrame;
if (resizeMask != NSViewNotSizable && !NSEqualRects([destView bounds], oldSuperBounds))
{
float spaces[3];
// horizontal
float newWidth = NSWidth([destView bounds]);
spaces[0] = NSMinX(oldFrame);
spaces[1] = NSWidth(oldFrame);
spaces[2] = NSMaxX(oldSuperBounds) - NSMaxX(oldFrame);
RedistributeSpace(resizeMask & 0x07, newWidth, spaces);
newFrame.origin.x = spaces[0];
newFrame.size.width = spaces[1];
// vertical. we assume that the view should stick to the top of the destView here
float newHeight = NSHeight([destView bounds]);
spaces[0] = NSMinY(oldFrame);
spaces[1] = NSHeight(oldFrame);
spaces[2] = NSMaxY(oldSuperBounds) - NSMaxY(oldFrame);
RedistributeSpace((resizeMask >> 3) & 0x07, newHeight, spaces);
newFrame.origin.y = spaces[0];
newFrame.size.height = spaces[1];
}
[self setFrame:newFrame];
[self setNeedsDisplay:YES];
}
}
@end

Просмотреть файл

@ -51,24 +51,31 @@ class nsIRDFService;
@interface RDFOutlineViewItem : NSObject
{
nsIRDFResource* mResource;
unsigned int mCacheVersion; // if matches the cache version in the data source,
// cached values are valid
BOOL mExpandable;
int mNumChildren;
NSArray* mChildNodes;
}
- (nsIRDFResource*) resource;
- (void) setResource: (nsIRDFResource*) aResource;
- (nsIRDFResource*)resource; // addRefs the result
- (void)setResource:(nsIRDFResource*) aResource;
@end
@interface RDFOutlineViewDataSource : NSObject {
nsIRDFDataSource* mDataSource;
nsIRDFContainer* mContainer;
nsIRDFContainerUtils* mContainerUtils;
nsIRDFResource* mRootResource;
nsIRDFService* mRDFService;
@interface RDFOutlineViewDataSource : NSObject
{
nsIRDFDataSource* mDataSource;
nsIRDFContainer* mContainer;
nsIRDFContainerUtils* mContainerUtils;
nsIRDFResource* mRootResource;
nsIRDFService* mRDFService;
IBOutlet ExtendedOutlineView* mOutlineView;
IBOutlet ExtendedOutlineView* mOutlineView;
NSMutableDictionary* mDictionary;
NSMutableDictionary* mDictionary;
unsigned int mCacheVersion;
}
// Initialization Methods
@ -85,7 +92,6 @@ class nsIRDFService;
- (BOOL)outlineView:(NSOutlineView *)outlineView isItemExpandable:(id)item;
- (int)outlineView:(NSOutlineView *)outlineView numberOfChildrenOfItem:(id)item;
- (id)outlineView:(NSOutlineView *)outlineView objectValueForTableColumn:(NSTableColumn *)tableColumn byItem:(id)item;
- (void)outlineView:(NSOutlineView *)outlineView setObjectValue:(id)object forTableColumn:(NSTableColumn *)tableColumn byItem:(id)item;
// tooltip support from the ExtendedOutlineView. Override to provide a tooltip
// other than the Name property for each item in the view.
@ -94,14 +100,14 @@ class nsIRDFService;
- (void)reloadDataForItem:(id)item reloadChildren: (BOOL)aReloadChildren;
// Implementation Methods
- (id) makeWrapperFor: (nsIRDFResource*) aRDFResource;
- (id)getWrapperFor:(nsIRDFResource*) aRDFResource;
- (void)invalidateCachedItems;
// override to do something different with the cell data rather than just
// return a string (add an icon in an attributed string, for example).
-(id) createCellContents:(const nsAString&)inValue withColumn:(NSString*)inColumn byItem:(id) inItem;
- (id)createCellContents:(NSString*)inValue withColumn:(NSString*)inColumn byItem:(id)inItem;
-(void) getPropertyString:(NSString*)inPropertyURI forItem:(RDFOutlineViewItem*)inItem
result:(PRUnichar**)outResult;
- (NSString*)getPropertyString:(NSString*)inPropertyURI forItem:(RDFOutlineViewItem*)inItem;
@end

Просмотреть файл

@ -41,6 +41,7 @@
#import "RDFOutlineViewDataSource.h"
#import "CHBrowserService.h"
#include "nsCRT.h"
#include "nsIRDFDataSource.h"
#include "nsIRDFService.h"
#include "nsIRDFLiteral.h"
@ -55,14 +56,116 @@
#include "nsXPIDLString.h"
#include "nsString.h"
@interface RDFOutlineViewDataSource(Private);
- (void)registerForShutdownNotification;
- (void)cleanup;
@interface RDFOutlineViewItem(Private)
- (unsigned int)cacheVersion;
- (void)setNumChildren:(int)numChildren isExpandable:(BOOL)expandable cacheVersion:(unsigned int)version;
- (void)setChildren:(NSArray*)childArray;
- (BOOL)cacheValid:(unsigned int)version needChildren:(BOOL)needChildren;
- (BOOL)cachedChildren;
- (BOOL)isExpandable;
- (int)numChildren;
- (id)childAtIndex:(int)index;
@end
@implementation RDFOutlineViewItem
- (id)init
{
if ((self = [super init]))
{
mCacheVersion = 0;
mExpandable = NO;
mNumChildren = 0;
}
return self;
}
- (void)dealloc
{
[mChildNodes release];
NS_IF_RELEASE(mResource);
[super dealloc];
}
- (nsIRDFResource*)resource
{
NS_IF_ADDREF(mResource);
return mResource;
}
- (void)setResource:(nsIRDFResource*) aResource
{
nsIRDFResource* oldResource = mResource;
NS_IF_ADDREF(mResource = aResource);
NS_IF_RELEASE(oldResource);
}
- (unsigned int)cacheVersion
{
return mCacheVersion;
}
- (void)setNumChildren:(int)numChildren isExpandable:(BOOL)expandable cacheVersion:(unsigned int)version;
{
mNumChildren = numChildren;
mExpandable = expandable;
mCacheVersion = version;
}
- (void)setChildren:(NSArray*)childArray
{
// childArray can legally be nil here. If it is, we're clearing the cached children
NSArray* oldChildren = mChildNodes;
mChildNodes = childArray;
[mChildNodes retain];
[oldChildren release];
}
- (BOOL)cacheValid:(unsigned int)version needChildren:(BOOL)needChildren;
{
return (mCacheVersion == version) && (needChildren ? (mChildNodes != nil) : 1);
}
- (BOOL)cachedChildren
{
return (mChildNodes != nil);
}
- (BOOL)isExpandable
{
return mExpandable;
}
- (int)numChildren
{
return mNumChildren;
}
- (id)childAtIndex:(int)index
{
if (mChildNodes)
return [mChildNodes objectAtIndex:index];
return nil;
}
@end
#pragma mark -
@interface RDFOutlineViewDataSource(Private)
- (void)registerForShutdownNotification;
- (void)cleanup;
- (void)updateItemProperties:(id)item enumerateChildren:(BOOL)doChildren;
@end
@implementation RDFOutlineViewDataSource
- (id)init
@ -70,6 +173,7 @@
if ((self = [super init]))
{
[self registerForShutdownNotification];
mCacheVersion = 1;
}
return self;
}
@ -78,7 +182,7 @@
{
[[NSNotificationCenter defaultCenter] removeObserver:self];
[self cleanup];
[self cleanup];
[super dealloc];
}
@ -167,123 +271,62 @@
// XXX - For now, we'll just say that none of our items are editable, as we aren't using any
// RDF datasources that are mutable.
//
- (BOOL) outlineView: (NSOutlineView*) aOutlineView shouldEditTableColumn: (NSTableColumn*) aTableColumn
- (BOOL) outlineView: (NSOutlineView*)aOutlineView shouldEditTableColumn: (NSTableColumn*) aTableColumn
item: (id) aItem
{
return NO;
return NO;
}
- (BOOL) outlineView: (NSOutlineView*) aOutlineView isItemExpandable: (id) aItem
- (BOOL) outlineView: (NSOutlineView*)aOutlineView isItemExpandable:(id)aItem
{
if (!mDataSource)
return NO;
if (!aItem)
return YES; // The root is always open
nsCOMPtr<nsIRDFResource> itemResource = dont_AddRef([aItem resource]);
PRBool isSeq = PR_FALSE;
mContainerUtils->IsSeq(mDataSource, itemResource, &isSeq);
if (isSeq)
return YES;
nsCOMPtr<nsIRDFResource> childProperty;
mRDFService->GetResource("http://home.netscape.com/NC-rdf#child", getter_AddRefs(childProperty));
nsCOMPtr<nsIRDFNode> childNode;
mDataSource->GetTarget(itemResource, childProperty, PR_TRUE, getter_AddRefs(childNode));
return childNode != nsnull;
if (!mDataSource)
return NO;
if (!aItem)
return YES; // The root is always open
if (![aItem cacheValid:mCacheVersion needChildren:NO])
[self updateItemProperties:aItem enumerateChildren:NO];
return [aItem isExpandable];
}
- (id) outlineView: (NSOutlineView*) aOutlineView child: (int) aIndex
ofItem: (id) aItem
- (id)outlineView:(NSOutlineView*)aOutlineView child:(int)aIndex ofItem:(id)aItem
{
if (!mDataSource)
return nil;
if (!mDataSource)
return nil;
if (!aItem)
{
nsCOMPtr<nsIRDFResource> rootResource = dont_AddRef([self rootResource]);
aItem = [self getWrapperFor:rootResource];
}
if (![aItem cacheValid:mCacheVersion needChildren:YES])
[self updateItemProperties:aItem enumerateChildren:YES];
nsCOMPtr<nsIRDFResource> resource = !aItem ? dont_AddRef([self rootResource]) : dont_AddRef([aItem resource]);
nsCOMPtr<nsIRDFResource> ordinalResource;
mContainerUtils->IndexToOrdinalResource(aIndex + 1, getter_AddRefs(ordinalResource));
nsCOMPtr<nsIRDFNode> childNode;
mDataSource->GetTarget(resource, ordinalResource, PR_TRUE, getter_AddRefs(childNode));
if (childNode) {
// Yay. A regular container. We don't need to count, we can go directly to
// our object.
nsCOMPtr<nsIRDFResource> childResource(do_QueryInterface(childNode));
if (childResource)
return [self makeWrapperFor:childResource];
}
else
{
// Oh well, not a regular container. We need to count, dagnabbit.
nsCOMPtr<nsIRDFResource> childProperty;
mRDFService->GetResource("http://home.netscape.com/NC-rdf#child", getter_AddRefs(childProperty));
nsCOMPtr<nsISimpleEnumerator> childNodes;
mDataSource->GetTargets(resource, childProperty, PR_TRUE, getter_AddRefs(childNodes));
nsCOMPtr<nsISupports> supp;
PRInt32 count = 0;
PRBool hasMore = PR_FALSE;
while (NS_SUCCEEDED(childNodes->HasMoreElements(&hasMore)) && hasMore)
{
childNodes->GetNext(getter_AddRefs(supp));
if (count == aIndex)
break;
count ++;
}
nsCOMPtr<nsIRDFResource> childResource(do_QueryInterface(supp));
if (childResource) {
return [self makeWrapperFor:childResource];
}
}
return nil;
return [aItem childAtIndex:aIndex];
}
- (int) outlineView: (NSOutlineView*) aOutlineView numberOfChildrenOfItem: (id) aItem;
- (int)outlineView:(NSOutlineView*)aOutlineView numberOfChildrenOfItem:(id) aItem;
{
if (!mDataSource)
return 0;
nsCOMPtr<nsIRDFResource> resource = dont_AddRef(aItem ? [aItem resource] : [self rootResource]);
// XXX just assume NC:child is the only containment arc for now
nsCOMPtr<nsIRDFResource> childProperty;
mRDFService->GetResource("http://home.netscape.com/NC-rdf#child", getter_AddRefs(childProperty));
nsCOMPtr<nsISimpleEnumerator> childNodes;
mDataSource->GetTargets(resource, childProperty, PR_TRUE, getter_AddRefs(childNodes));
PRBool hasMore = PR_FALSE;
PRInt32 count = 0;
while (NS_SUCCEEDED(childNodes->HasMoreElements(&hasMore)) && hasMore)
{
nsCOMPtr<nsISupports> supp;
childNodes->GetNext(getter_AddRefs(supp));
count ++;
}
if (count == 0) {
nsresult rv = mContainer->Init(mDataSource, resource);
if (NS_FAILED(rv))
return 0;
mContainer->GetCount(&count);
}
return count;
if (!mDataSource)
return 0;
if (!aItem)
{
nsCOMPtr<nsIRDFResource> rootResource = dont_AddRef([self rootResource]);
aItem = [self getWrapperFor:rootResource];
}
if (![aItem cacheValid:mCacheVersion needChildren:YES])
[self updateItemProperties:aItem enumerateChildren:YES];
return [aItem numChildren];
}
- (id) outlineView: (NSOutlineView*) aOutlineView objectValueForTableColumn: (NSTableColumn*) aTableColumn
byItem: (id) aItem
- (id)outlineView:(NSOutlineView*)aOutlineView objectValueForTableColumn:(NSTableColumn*)aTableColumn
byItem:(id)aItem
{
if (!mDataSource || !aItem)
return nil;
@ -291,25 +334,22 @@
// The table column's identifier is the RDF Resource URI of the property being displayed in
// that column, e.g. "http://home.netscape.com/NC-rdf#Name"
NSString* columnPropertyURI = [aTableColumn identifier];
nsXPIDLString literalValue;
[self getPropertyString:columnPropertyURI forItem:aItem result:getter_Copies(literalValue)];
NSString* propString = [self getPropertyString:columnPropertyURI forItem:aItem];
return [self createCellContents:literalValue withColumn:columnPropertyURI byItem:aItem];
return [self createCellContents:propString withColumn:columnPropertyURI byItem:aItem];
}
//
// createCellContents:withColumn:byItem
//
// Constructs a NSString from the given string data for this item in the given column.
// This should be overridden to do more fancy things, such as add an icon, etc.
//
-(id) createCellContents:(const nsAString&)inValue withColumn:(NSString*)inColumn byItem:(id) inItem
- (id)createCellContents:(NSString*)inValue withColumn:(NSString*)inColumn byItem:(id)inItem
{
return [NSString stringWith_nsAString: inValue];
return inValue;
}
//
// outlineView:tooltipForString
//
@ -318,21 +358,9 @@
//
- (NSString *)outlineView:(NSOutlineView *)outlineView tooltipStringForItem:(id)inItem
{
nsXPIDLString literalValue;
[self getPropertyString:@"http://home.netscape.com/NC-rdf#Name" forItem:inItem result:getter_Copies(literalValue)];
return [NSString stringWith_nsAString:literalValue];
return [self getPropertyString:@"http://home.netscape.com/NC-rdf#Name" forItem:inItem];
}
- (void) outlineView: (NSOutlineView*) aOutlineView setObjectValue: (id) aObject
forTableColumn: (NSTableColumn*) aTableColumn
byItem: (id) aItem
{
}
- (void) reloadDataForItem: (id) aItem reloadChildren: (BOOL) aReloadChildren
{
if (!aItem)
@ -341,7 +369,7 @@
[mOutlineView reloadItem: aItem reloadChildren: aReloadChildren];
}
- (id) makeWrapperFor: (nsIRDFResource*) aRDFResource
- (id)getWrapperFor:(nsIRDFResource*) aRDFResource
{
const char* k;
aRDFResource->GetValueConst(&k);
@ -350,8 +378,9 @@
// see if we've created a wrapper already, if not, create a new wrapper object
// and stash it in our dictionary
RDFOutlineViewItem* item = [mDictionary objectForKey:key];
if (!item) {
item = [[RDFOutlineViewItem alloc] init];
if (!item)
{
item = [[[RDFOutlineViewItem alloc] init] autorelease];
[item setResource: aRDFResource];
[mDictionary setObject:item forKey:key]; // retains |item|
}
@ -359,14 +388,56 @@
return item;
}
-(void) getPropertyString:(NSString*)inPropertyURI forItem:(RDFOutlineViewItem*)inItem
result:(PRUnichar**)outResult
- (void)invalidateCachedItems
{
if ( !outResult )
return;
*outResult = nil;
mCacheVersion++;
}
- (void)updateItemProperties:(id)item enumerateChildren:(BOOL)doChildren
{
BOOL isExpandable = NO;
NSMutableArray* itemChildren = doChildren ? [[[NSMutableArray alloc] initWithCapacity:10] autorelease] : nil;
nsCOMPtr<nsIRDFResource> itemResource = dont_AddRef([item resource]);
PRBool isSeq = PR_FALSE;
mContainerUtils->IsSeq(mDataSource, itemResource, &isSeq);
if (isSeq)
isExpandable = YES;
nsCOMPtr<nsIRDFResource> childProperty;
mRDFService->GetResource("http://home.netscape.com/NC-rdf#child", getter_AddRefs(childProperty));
nsCOMPtr<nsISimpleEnumerator> childNodes;
mDataSource->GetTargets(itemResource, childProperty, PR_TRUE, getter_AddRefs(childNodes));
PRBool hasMore = PR_FALSE;
while (NS_SUCCEEDED(childNodes->HasMoreElements(&hasMore)) && hasMore)
{
nsCOMPtr<nsISupports> supp;
childNodes->GetNext(getter_AddRefs(supp));
nsCOMPtr<nsIRDFResource> childResource = do_QueryInterface(supp);
if (childResource)
{
id childItem = [self getWrapperFor:childResource];
if (childItem)
{
isExpandable = YES;
if (!itemChildren) break; // know enough already
[itemChildren addObject:childItem];
}
}
}
// itemChildren will be nil here if we don't care about children, but that's OK.
// the setChildren call will clear the cached child list.
[item setNumChildren:[itemChildren count] isExpandable:isExpandable cacheVersion:mCacheVersion];
[item setChildren:itemChildren];
}
- (NSString*)getPropertyString:(NSString*)inPropertyURI forItem:(RDFOutlineViewItem*)inItem
{
nsCOMPtr<nsIRDFResource> propertyResource;
mRDFService->GetResource([inPropertyURI UTF8String], getter_AddRefs(propertyResource));
@ -378,38 +449,20 @@
#if DEBUG
NSLog(@"ValueNode is null in RDF objectValueForTableColumn");
#endif
return;
return @"";
}
nsCOMPtr<nsIRDFLiteral> valueLiteral(do_QueryInterface(valueNode));
if (!valueLiteral)
return;
return @"";
valueLiteral->GetValue(outResult);
const PRUnichar* value = NULL;
valueLiteral->GetValueConst(&value);
if (value)
return [NSString stringWithCharacters:value length:nsCRT::strlen(value)];
return @"";
}
@end
@implementation RDFOutlineViewItem
- (void) dealloc
{
NS_IF_RELEASE(mResource);
[super dealloc];
}
- (nsIRDFResource*) resource
{
NS_IF_ADDREF(mResource);
return mResource;
}
- (void) setResource: (nsIRDFResource*) aResource
{
nsIRDFResource* oldResource = mResource;
NS_IF_ADDREF(mResource = aResource);
NS_IF_RELEASE(oldResource);
}
@end

Просмотреть файл

@ -49,17 +49,23 @@ class HistoryDataSourceObserver;
{
HistoryDataSourceObserver* mObserver; // STRONG ref, should be nsCOMPtr but can't
IBOutlet BrowserWindowController* mBrowserWindowController;
BOOL mUpdatesEnabled;
BOOL mNeedsRefresh;
}
// overridden to create a attributed string with icon
-(id) createCellContents:(const nsAString&)inValue withColumn:(NSString*)inColumn byItem:(id) inItem;
- (id)createCellContents:(NSString*)inValue withColumn:(NSString*)inColumn byItem:(id) inItem;
- (NSString *)outlineView:(NSOutlineView *)outlineView tooltipStringForItem:(id)inItem;
-(void) enableObserver;
-(void) disableObserver;
- (void)enableObserver;
- (void)disableObserver;
-(IBAction)openHistoryItem: (id)aSender;
-(IBAction)deleteHistoryItems: (id)aSender;
- (void)setNeedsRefresh:(BOOL)needsRefresh;
- (BOOL)needsRefresh;
- (void)refresh;
- (IBAction)openHistoryItem: (id)aSender;
- (IBAction)deleteHistoryItems: (id)aSender;
@end

Просмотреть файл

@ -63,33 +63,29 @@
class HistoryDataSourceObserver : public nsIRDFObserver
{
public:
HistoryDataSourceObserver(NSOutlineView* outlineView) :
mOutlineView(outlineView), mEnabled(false)
HistoryDataSourceObserver(HistoryDataSource* dataSource)
: mHistoryDataSource(dataSource)
{
NS_INIT_ISUPPORTS();
}
virtual ~HistoryDataSourceObserver() { } ;
virtual ~HistoryDataSourceObserver() { }
NS_DECL_ISUPPORTS
NS_IMETHODIMP OnAssert(nsIRDFDataSource*, nsIRDFResource*, nsIRDFResource*, nsIRDFNode*) ;
NS_IMETHODIMP OnUnassert(nsIRDFDataSource*, nsIRDFResource*, nsIRDFResource*, nsIRDFNode*) { return NS_OK; }
NS_IMETHOD OnAssert(nsIRDFDataSource*, nsIRDFResource*, nsIRDFResource*, nsIRDFNode*);
NS_IMETHOD OnUnassert(nsIRDFDataSource*, nsIRDFResource*, nsIRDFResource*, nsIRDFNode*);
NS_IMETHODIMP OnMove(nsIRDFDataSource*, nsIRDFResource*, nsIRDFResource*, nsIRDFResource*, nsIRDFNode*)
NS_IMETHOD OnMove(nsIRDFDataSource*, nsIRDFResource*, nsIRDFResource*, nsIRDFResource*, nsIRDFNode*)
{ return NS_OK; }
NS_IMETHODIMP OnChange(nsIRDFDataSource*, nsIRDFResource*, nsIRDFResource*, nsIRDFNode*, nsIRDFNode*);
NS_IMETHOD OnChange(nsIRDFDataSource*, nsIRDFResource*, nsIRDFResource*, nsIRDFNode*, nsIRDFNode*);
NS_IMETHODIMP BeginUpdateBatch(nsIRDFDataSource*) { return NS_OK; }
NS_IMETHODIMP EndUpdateBatch(nsIRDFDataSource*) { return NS_OK; }
void Enable() { mEnabled = true; }
void Disable() { mEnabled = false; }
NS_IMETHOD BeginUpdateBatch(nsIRDFDataSource*) { return NS_OK; }
NS_IMETHOD EndUpdateBatch(nsIRDFDataSource*) { return NS_OK; }
private:
NSOutlineView* mOutlineView;
bool mEnabled;
HistoryDataSource* mHistoryDataSource;
};
NS_IMPL_ISUPPORTS1(HistoryDataSourceObserver, nsIRDFObserver)
@ -105,15 +101,30 @@ NS_IMETHODIMP
HistoryDataSourceObserver::OnAssert(nsIRDFDataSource*, nsIRDFResource*,
nsIRDFResource* aProperty, nsIRDFNode*)
{
if(mEnabled) {
const char* p;
aProperty->GetValueConst(&p);
if (strcmp("http://home.netscape.com/NC-rdf#Date", p) == 0)
[mOutlineView reloadData];
}
const char* p;
aProperty->GetValueConst(&p);
if (strcmp("http://home.netscape.com/NC-rdf#Date", p) == 0)
[mHistoryDataSource setNeedsRefresh:YES];
return NS_OK;
}
//
// OnUnassert
//
// This gets called on redirects, when nsGlobalHistory::RemovePage is called.
//
NS_IMETHODIMP
HistoryDataSourceObserver::OnUnassert(nsIRDFDataSource*, nsIRDFResource*,
nsIRDFResource* aProperty, nsIRDFNode*)
{
const char* p;
aProperty->GetValueConst(&p);
if (strcmp("http://home.netscape.com/NC-rdf#Date", p) == 0)
[mHistoryDataSource setNeedsRefresh:YES];
return NS_OK;
}
//
// OnChange
@ -125,12 +136,12 @@ NS_IMETHODIMP
HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
nsIRDFResource* aProperty, nsIRDFNode*, nsIRDFNode*)
{
if(mEnabled) {
const char* p;
aProperty->GetValueConst(&p);
if (strcmp("http://home.netscape.com/NC-rdf#Date", p) == 0)
[mOutlineView reloadData];
}
const char* p;
aProperty->GetValueConst(&p);
if (strcmp("http://home.netscape.com/NC-rdf#Date", p) == 0)
[mHistoryDataSource setNeedsRefresh:YES];
return NS_OK;
}
@ -138,7 +149,7 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
@interface HistoryDataSource(Private)
- (void)cleanup;
- (void)cleanupHistory;
@end
@ -146,12 +157,12 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
- (void) dealloc
{
[self cleanup];
[self cleanupHistory];
[super dealloc];
}
// "non-virtual" cleanup method -- safe to call from dealloc.
- (void)cleanup
- (void)cleanupHistory
{
if (mDataSource && mObserver)
{
@ -163,7 +174,7 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
// "virtual" method; called from superclass
- (void)cleanupDataSource
{
[self cleanup];
[self cleanupHistory];
[super cleanupDataSource];
}
@ -181,7 +192,8 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
NS_ASSERTION(mRDFService, "Uh oh, RDF service not loaded in parent class");
if ( !mDataSource ) {
if ( !mDataSource )
{
// Get the Global History DataSource
mRDFService->GetDataSource("rdf:history", &mDataSource);
// Get the Date Folder Root
@ -191,14 +203,15 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
[mOutlineView setDoubleAction: @selector(openHistoryItem:)];
[mOutlineView setDeleteAction: @selector(deleteHistoryItems:)];
mObserver = new HistoryDataSourceObserver(mOutlineView);
mObserver = new HistoryDataSourceObserver(self);
if ( mObserver ) {
NS_ADDREF(mObserver);
mDataSource->AddObserver(mObserver);
}
[mOutlineView reloadData];
}
else {
else
{
// everything is loaded, but we have to refresh our tree otherwise
// changes that took place while the drawer was closed won't be noticed
[mOutlineView reloadData];
@ -207,18 +220,41 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
NS_ASSERTION(mDataSource, "Uh oh, History RDF Data source not created");
}
- (void) enableObserver
- (void)enableObserver
{
if ( mObserver )
mObserver->Enable();
mUpdatesEnabled = YES;
}
-(void) disableObserver
-(void)disableObserver
{
if ( mObserver )
mObserver->Disable();
mUpdatesEnabled = NO;
}
- (void)setNeedsRefresh:(BOOL)needsRefresh
{
mNeedsRefresh = needsRefresh;
}
- (BOOL)needsRefresh
{
return mNeedsRefresh;
}
- (void)refresh
{
if (mNeedsRefresh)
{
[self invalidateCachedItems];
if (mUpdatesEnabled)
{
// this can be very slow! See bug 180109.
//NSLog(@"history reload started");
[self reloadDataForItem:nil reloadChildren:NO];
//NSLog(@"history reload done");
}
mNeedsRefresh = NO;
}
}
//
// createCellContents:withColumn:byItem
@ -226,31 +262,29 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
// override to create an NSAttributedString instead of just the string with the
// given text. We add an icon and adjust the positioning of the text w/in the cell
//
-(id) createCellContents:(const nsAString&)inValue withColumn:(NSString*)inColumn byItem:(id) inItem
-(id) createCellContents:(NSString*)inValue withColumn:(NSString*)inColumn byItem:(id) inItem
{
NSMutableAttributedString *cellValue = [[NSMutableAttributedString alloc] init];
//Set cell's textual contents
[cellValue replaceCharactersInRange:NSMakeRange(0, [cellValue length]) withString:[NSString stringWith_nsAString:inValue]];
if ([inValue length] == 0)
inValue = [self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:inItem];
if ([inColumn isEqualToString: @"http://home.netscape.com/NC-rdf#Name"]) {
NSMutableAttributedString *attachmentAttrString = nil;
NSFileWrapper *fileWrapper = [[NSFileWrapper alloc] initRegularFileWithContents:nil];
NSTextAttachment *textAttachment = [[NSTextAttachment alloc] initWithFileWrapper:fileWrapper];
NSCell *attachmentAttrStringCell;
NSMutableAttributedString *cellValue = [[[NSMutableAttributedString alloc] initWithString:inValue] autorelease];
if ([inColumn isEqualToString:@"http://home.netscape.com/NC-rdf#Name"])
{
NSFileWrapper *fileWrapper = [[NSFileWrapper alloc] initRegularFileWithContents:nil];
NSTextAttachment *textAttachment = [[NSTextAttachment alloc] initWithFileWrapper:fileWrapper];
//Create an attributed string to hold the empty attachment, then release the components.
attachmentAttrString = [[NSMutableAttributedString attributedStringWithAttachment:textAttachment] retain];
// Create an attributed string to hold the empty attachment, then release the components.
NSMutableAttributedString *attachmentAttrString = [NSMutableAttributedString attributedStringWithAttachment:textAttachment];
[textAttachment release];
[fileWrapper release];
//Get the cell of the text attachment.
attachmentAttrStringCell = (NSCell *)[(NSTextAttachment *)[attachmentAttrString attribute:
NSCell* attachmentAttrStringCell = (NSCell *)[(NSTextAttachment *)[attachmentAttrString attribute:
NSAttachmentAttributeName atIndex:0 effectiveRange:nil] attachmentCell];
if ([self outlineView:mOutlineView isItemExpandable:inItem]) {
if ([self outlineView:mOutlineView isItemExpandable:inItem])
[attachmentAttrStringCell setImage:[NSImage imageNamed:@"folder"]];
}
else
[attachmentAttrStringCell setImage:[NSImage imageNamed:@"smallbookmark"]];
@ -298,11 +332,8 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
id item = [toDrag objectAtIndex: 0];
// if we have just one item, we add some more flavours
nsXPIDLString urlLiteral, nameLiteral;
[self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:item result:getter_Copies(urlLiteral)];
[self getPropertyString:@"http://home.netscape.com/NC-rdf#Name" forItem:item result:getter_Copies(nameLiteral)];
NSString* url = [NSString stringWith_nsAString: urlLiteral];
NSString* title = [NSString stringWith_nsAString: nameLiteral];
NSString* url = [self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:item];
NSString* title = [self getPropertyString:@"http://home.netscape.com/NC-rdf#Name" forItem:item];
NSString *cleanedTitle = [title stringByReplacingCharactersInSet:[NSCharacterSet controlCharacterSet] withString:@" "];
[pboard declareURLPasteboardWithAdditionalTypes:[NSArray array] owner:self];
@ -340,11 +371,8 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
return;
}
nsXPIDLString urlLiteral;
[self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:item result:getter_Copies(urlLiteral)];
// get uri
NSString* url = [NSString stringWith_nsAString: urlLiteral];
NSString* url = [self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:item];
[[mBrowserWindowController getBrowserWrapper] loadURI: url referrer: nil flags: NSLoadFlagsNone activate:YES];
}
@ -376,14 +404,15 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
index = [currIndex intValue];
RDFOutlineViewItem* item = [mOutlineView itemAtRow: index];
if (![mOutlineView isExpandable: item]) {
nsXPIDLString urlLiteral;
[self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:item result:getter_Copies(urlLiteral)];
history->RemovePage(NS_ConvertUCS2toUTF8(urlLiteral).get());
NSString* urlString = [self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:item];
history->RemovePage([urlString UTF8String]);
}
}
history->EndBatchUpdate();
if ( clearSelectionWhenDone )
[mOutlineView deselectAll:self];
[self invalidateCachedItems];
[mOutlineView reloadData]; // necessary or the outline is really horked
}
}
@ -402,9 +431,8 @@ HistoryDataSourceObserver::OnChange(nsIRDFDataSource*, nsIRDFResource*,
NSString* pageTitle = [super outlineView:outlineView tooltipStringForItem:inItem];
// append url
nsXPIDLString literalValue;
[self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:inItem result:getter_Copies(literalValue)];
return [NSString stringWithFormat:@"%@\n%@", pageTitle, [NSString stringWith_nsAString:literalValue]];
NSString* url = [self getPropertyString:@"http://home.netscape.com/NC-rdf#URL" forItem:inItem];
return [NSString stringWithFormat:@"%@\n%@", pageTitle, [url stringByTruncatingTo:80 at:kTruncateAtEnd]];
}
return nil;
}

Просмотреть файл

@ -52,3 +52,13 @@ const int kDividerTag = 4000;
// the tag of the separator after which to insert bookmark items
const int kBookmarksDividerTag = -1;
// Save file dialog
const int kSaveFormatPopupTag = 1000;
enum
{
eSaveFormatHTMLComplete = 0,
eSaveFormatHTMLSource,
eSaveFormatPlainText
};

Просмотреть файл

@ -45,6 +45,9 @@ class nsIPref;
NSUserDefaults* mDefaults;
ICInstance mInternetConfig;
nsIPref* mPrefs;
// proxies notification stuff
CFRunLoopSourceRef mRunLoopSource;
}
+ (PreferenceManager *)sharedInstance;

Просмотреть файл

@ -38,6 +38,7 @@
#import <Cocoa/Cocoa.h>
#import <SystemConfiguration/SystemConfiguration.h>
#import "PreferenceManager.h"
#import "UserDefaults.h"
#import "CHBrowserService.h"
@ -60,11 +61,23 @@ app_getModuleInfo(nsStaticModuleInfo **info, PRUint32 *count);
@interface PreferenceManager(PreferenceManagerPrivate)
+ (PreferenceManager *) sharedInstanceDontCreate;
- (void)registerNotificationListener;
- (void)termEmbedding: (NSNotification*)aNotification;
- (void)xpcomTerminate: (NSNotification*)aNotification;
- (void)configureProxies;
- (BOOL)updateOneProxy:(NSDictionary*)configDict
protocol:(NSString*)protocol
proxyEnableKey:(NSString*)enableKey
proxyURLKey:(NSString*)urlKey
proxyPortKey:(NSString*)portKey;
- (void)registerForProxyChanges;
- (BOOL)readSystemProxySettings;
@end
@ -76,7 +89,7 @@ static PreferenceManager* gSharedInstance = nil;
static BOOL gMadePrefManager;
#endif
+ (PreferenceManager *) sharedInstance
+ (PreferenceManager *)sharedInstance
{
if (!gSharedInstance)
{
@ -88,13 +101,20 @@ static BOOL gMadePrefManager;
gSharedInstance = [[PreferenceManager alloc] init];
}
return gSharedInstance;
return gSharedInstance;
}
+ (PreferenceManager *)sharedInstanceDontCreate
{
return gSharedInstance;
}
- (id) init
{
if ((self = [super init]))
{
mRunLoopSource = NULL;
[self registerNotificationListener];
if ([self initInternetConfig] == NO) {
@ -115,6 +135,8 @@ static BOOL gMadePrefManager;
- (void) dealloc
{
[[NSNotificationCenter defaultCenter] removeObserver:self];
if (self == gSharedInstance)
gSharedInstance = nil;
[super dealloc];
}
@ -123,6 +145,13 @@ static BOOL gMadePrefManager;
::ICStop(mInternetConfig);
mInternetConfig = nil;
NS_IF_RELEASE(mPrefs);
// remove our runloop observer
if (mRunLoopSource)
{
CFRunLoopRemoveSource(CFRunLoopGetCurrent(), mRunLoopSource, kCFRunLoopCommonModes);
CFRelease(mRunLoopSource);
mRunLoopSource = NULL;
}
}
- (void)xpcomTerminate: (NSNotification*)aNotification
@ -145,14 +174,14 @@ static BOOL gMadePrefManager;
object: nil];
}
- (void) savePrefsFile
- (void)savePrefsFile
{
nsCOMPtr<nsIPrefService> prefsService = do_GetService(NS_PREF_CONTRACTID);
if (prefsService)
prefsService->SavePrefFile(nsnull);
}
- (BOOL) initInternetConfig
- (BOOL)initInternetConfig
{
OSStatus error;
error = ::ICStart(&mInternetConfig, 'CHIM');
@ -164,7 +193,7 @@ static BOOL gMadePrefManager;
return YES;
}
- (BOOL) initMozillaPrefs
- (BOOL)initMozillaPrefs
{
#ifdef _BUILD_STATIC_BIN
@ -246,15 +275,8 @@ static BOOL gMadePrefManager;
return YES;
}
- (void) syncMozillaPrefs
- (void)syncMozillaPrefs
{
CFArrayRef cfArray;
CFDictionaryRef cfDictionary;
CFNumberRef cfNumber;
CFStringRef cfString;
char strbuf[1024];
int numbuf;
if (!mPrefs) {
NSLog(@"Mozilla prefs not set up successfully");
return;
@ -268,19 +290,101 @@ static BOOL gMadePrefManager;
// fix up the cookie prefs. If 'p3p' or 'accept foreign cookies' are on, remap them to
// something that chimera can deal with.
PRInt32 acceptCookies = 0;
static const char* kCookieBehaviorPref = "network.cookie.cookieBehavior";
static const char* kCookieBehaviorPref = "network.cookie.cookieBehavior";
mPrefs->GetIntPref(kCookieBehaviorPref, &acceptCookies);
if ( acceptCookies == 1 ) { // accept foreign cookies, assume off
if ( acceptCookies == 1 ) { // accept foreign cookies, assume off
acceptCookies = 2;
mPrefs->SetIntPref(kCookieBehaviorPref, acceptCookies);
}
mPrefs->SetIntPref(kCookieBehaviorPref, acceptCookies);
}
else if ( acceptCookies == 3 ) { // p3p, assume all cookies on
acceptCookies = 0;
mPrefs->SetIntPref(kCookieBehaviorPref, acceptCookies);
mPrefs->SetIntPref(kCookieBehaviorPref, acceptCookies);
}
[self configureProxies];
}
#pragma mark -
- (void)configureProxies
{
[self readSystemProxySettings];
[self registerForProxyChanges];
}
static void SCProxiesChangedCallback(SCDynamicStoreRef store, CFArrayRef changedKeys, void * /* info */)
{
PreferenceManager* prefsManager = [PreferenceManager sharedInstanceDontCreate];
[prefsManager readSystemProxySettings];
#if DEBUG
NSLog(@"Updating proxies");
#endif
}
- (void)registerForProxyChanges
{
if (mRunLoopSource) // don't register twice
return;
SCDynamicStoreContext context = {0, NULL, NULL, NULL, NULL};
SCDynamicStoreRef dynamicStoreRef = SCDynamicStoreCreate(NULL, CFSTR("ChimeraProxiesNotification"), SCProxiesChangedCallback, &context);
if (dynamicStoreRef)
{
CFStringRef proxyIdentifier = SCDynamicStoreKeyCreateProxies(NULL);
CFArrayRef keyList = CFArrayCreate(NULL, (const void **)&proxyIdentifier, 1, &kCFTypeArrayCallBacks);
Boolean set = SCDynamicStoreSetNotificationKeys(dynamicStoreRef, keyList, NULL);
if (set)
{
mRunLoopSource = SCDynamicStoreCreateRunLoopSource(NULL, dynamicStoreRef, 0);
if (mRunLoopSource)
{
CFRunLoopAddSource(CFRunLoopGetCurrent(), mRunLoopSource, kCFRunLoopCommonModes);
// we keep the ref to the source, so that we can remove it when the prefs manager is cleaned up.
}
}
CFRelease(proxyIdentifier);
CFRelease(keyList);
CFRelease(dynamicStoreRef);
}
}
- (BOOL)updateOneProxy:(NSDictionary*)configDict
protocol:(NSString*)protocol
proxyEnableKey:(NSString*)enableKey
proxyURLKey:(NSString*)urlKey
proxyPortKey:(NSString*)portKey
{
BOOL gotProxy = NO;
BOOL enabled = (BOOL)[[configDict objectForKey:enableKey] intValue];
if (enabled)
{
NSString* protocolProxy = [configDict objectForKey:urlKey];
int proxyPort = [[configDict objectForKey:portKey] intValue];
if ([protocolProxy length] > 0 && proxyPort != 0)
{
[self setPref:[[NSString stringWithFormat:@"network.proxy.%@", protocol] cString] toString:protocolProxy];
[self setPref:[[NSString stringWithFormat:@"network.proxy.%@_port", protocol] cString] toInt:proxyPort];
gotProxy = YES;
}
}
return gotProxy;
}
- (BOOL)readSystemProxySettings
{
BOOL usingProxies = NO;
PRInt32 proxyType, newProxyType;
mPrefs->GetIntPref("network.proxy.type", &proxyType);
newProxyType = proxyType;
if (proxyType == 0 || proxyType == 1)
{
// get proxies from SystemConfiguration
mPrefs->SetIntPref("network.proxy.type", 0); // 0 == no proxies
mPrefs->ClearUserPref("network.proxy.http");
mPrefs->ClearUserPref("network.proxy.http_port");
mPrefs->ClearUserPref("network.proxy.ssl");
@ -293,94 +397,66 @@ static BOOL gMadePrefManager;
mPrefs->ClearUserPref("network.proxy.socks_port");
mPrefs->ClearUserPref("network.proxy.no_proxies_on");
if ((cfDictionary = SCDynamicStoreCopyProxies (NULL)) != NULL) {
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesHTTPEnable, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE && numbuf == 1) {
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesHTTPProxy, (const void **)&cfString) == TRUE) {
if (CFStringGetCString (cfString, strbuf, sizeof(strbuf)-1, kCFStringEncodingASCII) == TRUE) {
mPrefs->SetCharPref("network.proxy.http", strbuf);
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesHTTPPort, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE) {
mPrefs->SetIntPref("network.proxy.http_port", numbuf);
}
mPrefs->SetIntPref("network.proxy.type", 1);
}
}
}
NSDictionary* proxyConfigDict = (NSDictionary*)SCDynamicStoreCopyProxies(NULL);
if (proxyConfigDict)
{
BOOL gotAProxy = NO;
gotAProxy |= [self updateOneProxy:proxyConfigDict protocol:@"http"
proxyEnableKey:(NSString*)kSCPropNetProxiesHTTPEnable
proxyURLKey:(NSString*)kSCPropNetProxiesHTTPProxy
proxyPortKey:(NSString*)kSCPropNetProxiesHTTPPort];
gotAProxy |= [self updateOneProxy:proxyConfigDict protocol:@"ssl"
proxyEnableKey:(NSString*)kSCPropNetProxiesHTTPSEnable
proxyURLKey:(NSString*)kSCPropNetProxiesHTTPSProxy
proxyPortKey:(NSString*)kSCPropNetProxiesHTTPSPort];
gotAProxy |= [self updateOneProxy:proxyConfigDict protocol:@"ftp"
proxyEnableKey:(NSString*)kSCPropNetProxiesFTPEnable
proxyURLKey:(NSString*)kSCPropNetProxiesFTPProxy
proxyPortKey:(NSString*)kSCPropNetProxiesFTPPort];
gotAProxy |= [self updateOneProxy:proxyConfigDict protocol:@"gopher"
proxyEnableKey:(NSString*)kSCPropNetProxiesGopherEnable
proxyURLKey:(NSString*)kSCPropNetProxiesGopherProxy
proxyPortKey:(NSString*)kSCPropNetProxiesGopherPort];
gotAProxy |= [self updateOneProxy:proxyConfigDict protocol:@"socks"
proxyEnableKey:(NSString*)kSCPropNetProxiesSOCKSEnable
proxyURLKey:(NSString*)kSCPropNetProxiesSOCKSProxy
proxyPortKey:(NSString*)kSCPropNetProxiesSOCKSPort];
if (gotAProxy)
{
newProxyType = 1;
NSArray* exceptions = [proxyConfigDict objectForKey:(NSString*)kSCPropNetProxiesExceptionsList];
if (exceptions)
{
NSString* sitesList = [exceptions componentsJoinedByString:@", "];
if ([sitesList length] > 0)
[self setPref:"network.proxy.no_proxies_on" toString:sitesList];
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesHTTPSEnable, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE && numbuf == 1) {
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesHTTPSProxy, (const void **)&cfString) == TRUE) {
if (CFStringGetCString (cfString, strbuf, sizeof(strbuf)-1, kCFStringEncodingASCII) == TRUE) {
mPrefs->SetCharPref("network.proxy.ssl", strbuf);
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesHTTPSPort, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE) {
mPrefs->SetIntPref("network.proxy.ssl_port", numbuf);
}
mPrefs->SetIntPref("network.proxy.type", 1);
}
}
}
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesFTPEnable, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE && numbuf == 1) {
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesFTPProxy, (const void **)&cfString) == TRUE) {
if (CFStringGetCString (cfString, strbuf, sizeof(strbuf)-1, kCFStringEncodingASCII) == TRUE) {
mPrefs->SetCharPref("network.proxy.ftp", strbuf);
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesFTPPort, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE) {
mPrefs->SetIntPref("network.proxy.ftp_port", numbuf);
}
mPrefs->SetIntPref("network.proxy.type", 1);
}
}
}
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesGopherEnable, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE && numbuf == 1) {
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesGopherProxy, (const void **)&cfString) == TRUE) {
if (CFStringGetCString (cfString, strbuf, sizeof(strbuf)-1, kCFStringEncodingASCII) == TRUE) {
mPrefs->SetCharPref("network.proxy.gopher", strbuf);
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesGopherPort, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE) {
mPrefs->SetIntPref("network.proxy.gopher_port", numbuf);
}
mPrefs->SetIntPref("network.proxy.type", 1);
}
}
}
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesSOCKSEnable, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE && numbuf == 1) {
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesSOCKSProxy, (const void **)&cfString) == TRUE) {
if (CFStringGetCString (cfString, strbuf, sizeof(strbuf)-1, kCFStringEncodingASCII) == TRUE) {
mPrefs->SetCharPref("network.proxy.socks", strbuf);
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesSOCKSPort, (const void **)&cfNumber) == TRUE) {
if (CFNumberGetValue (cfNumber, kCFNumberIntType, &numbuf) == TRUE) {
mPrefs->SetIntPref("network.proxy.socks_port", numbuf);
}
mPrefs->SetIntPref("network.proxy.type", 1);
}
}
}
}
if (CFDictionaryGetValueIfPresent (cfDictionary, kSCPropNetProxiesExceptionsList, (const void **)&cfArray) == TRUE) {
cfString = CFStringCreateByCombiningStrings (NULL, cfArray, CFSTR(", "));
if (CFStringGetLength (cfString) > 0) {
if (CFStringGetCString (cfString, strbuf, sizeof(strbuf)-1, kCFStringEncodingASCII) == TRUE) {
mPrefs->SetCharPref("network.proxy.no_proxies_on", strbuf);
}
}
}
CFRelease (cfDictionary);
usingProxies = YES;
}
else
{
newProxyType = 0;
}
[proxyConfigDict release];
}
if (newProxyType != proxyType)
mPrefs->SetIntPref("network.proxy.type", 1);
}
return usingProxies;
}
#pragma mark -
- (NSString*)getStringPref: (const char*)prefName withSuccess:(BOOL*)outSuccess
{
NSString *prefValue = @"";
@ -406,16 +482,16 @@ static BOOL gMadePrefManager;
{
// colors are stored in HTML-like #FFFFFF strings
NSString* colorString = [self getStringPref:prefName withSuccess:outSuccess];
NSColor* returnColor = [NSColor blackColor];
NSColor* returnColor = [NSColor blackColor];
if ([colorString hasPrefix:@"#"] && [colorString length] == 7)
{
unsigned int redInt, greenInt, blueInt;
sscanf([colorString cString], "#%02x%02x%02x", &redInt, &greenInt, &blueInt);
float redFloat = ((float)redInt / 255.0);
float greenFloat = ((float)greenInt / 255.0);
float blueFloat = ((float)blueInt / 255.0);
float redFloat = ((float)redInt / 255.0);
float greenFloat = ((float)greenInt / 255.0);
float blueFloat = ((float)blueInt / 255.0);
returnColor = [NSColor colorWithCalibratedRed:redFloat green:greenFloat blue:blueFloat alpha:1.0f];
}
@ -548,7 +624,7 @@ static BOOL gMadePrefManager;
mPrefs->SetCharPref("browser.startup.homepage", [homepagePref UTF8String]);
}
else {
homepagePref = [self getStringPref:"browser.startup.homepage" withSuccess:NULL];
homepagePref = [self getStringPref:"browser.startup.homepage" withSuccess:NULL];
}
if (homepagePref && [homepagePref length] > 0 && ![homepagePref isEqualToString:@"HomePageDefault"])

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>646 106 458 263 0 0 1600 1002 </string>
<key>IBEditorPositions</key>
<dict>
<key>214</key>
<string>70 395 152 96 0 0 1152 746 </string>
</dict>
<key>IBFramework Version</key>
<string>286.0</string>
<key>IBSystem Version</key>
<string>6D52</string>
</dict>
</plist>

Двоичные данные
chimera/PreferencePanes/Appearance/English.lproj/Appearance.nib/objects.nib сгенерированный

Двоичный файл не отображается.

Просмотреть файл

@ -1,27 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>140 56 522 320 0 0 1280 1002 </string>
<key>IBFramework Version</key>
<string>286.0</string>
<key>IBGroupedObjects</key>
<dict>
<key>5</key>
<array>
<string>12</string>
<string>24</string>
<string>56</string>
</array>
</dict>
<key>IBLastGroupID</key>
<string>8</string>
<key>IBOpenObjects</key>
<array>
<integer>5</integer>
</array>
<key>IBSystem Version</key>
<string>6F21</string>
</dict>
</plist>

Двоичные данные
chimera/PreferencePanes/Navigation/English.lproj/Navigation.nib/objects.nib сгенерированный

Двоичный файл не отображается.

Просмотреть файл

Просмотреть файл

Просмотреть файл

Просмотреть файл

@ -1,177 +0,0 @@
{
IBClasses = (
{CLASS = AutoCompleteDataSource; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{
ACTIONS = {onBlur = id; onResize = id; };
CLASS = AutoCompleteTextField;
LANGUAGE = ObjC;
OUTLETS = {mProxyIcon = PageProxyIcon; };
SUPERCLASS = NSTextField;
},
{CLASS = BookmarkItem; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{
ACTIONS = {
addBookmark = id;
addFolder = id;
deleteBookmarks = id;
openBookmarkInNewTab = id;
openBookmarkInNewWindow = id;
showBookmarkInfo = id;
};
CLASS = BookmarksDataSource;
LANGUAGE = ObjC;
OUTLETS = {
mBrowserWindowController = id;
mDeleteBookmarkButton = id;
mEditBookmarkButton = id;
mOutlineView = id;
};
SUPERCLASS = NSObject;
},
{
CLASS = BookmarksOutlineView;
LANGUAGE = ObjC;
SUPERCLASS = ExtendedOutlineView;
},
{
ACTIONS = {addFolder = id; };
CLASS = BookmarksToolbar;
LANGUAGE = ObjC;
SUPERCLASS = NSView;
},
{CLASS = BrowserContainerView; LANGUAGE = ObjC; SUPERCLASS = NSView; },
{
CLASS = BrowserContentView;
LANGUAGE = ObjC;
OUTLETS = {
mBookmarksToolbar = BookmarksToolbar;
mBrowserContainerView = NSView;
mStatusBar = NSView;
};
SUPERCLASS = NSView;
},
{CLASS = BrowserTabView; LANGUAGE = ObjC; SUPERCLASS = NSTabView; },
{
CLASS = BrowserWindow;
LANGUAGE = ObjC;
OUTLETS = {mAutoCompleteTextField = id; };
SUPERCLASS = NSWindow;
},
{
ACTIONS = {
back = id;
biggerTextSize = id;
bookmarkLink = id;
bookmarkPage = id;
cancelAddBookmarkSheet = id;
cancelLocationSheet = id;
closeCurrentTab = id;
closeOtherTabs = id;
closeSendersTab = id;
copyImageLocation = id;
copyLinkLocation = id;
endAddBookmarkSheet = id;
endLocationSheet = id;
forward = id;
frameToNewTab = id;
frameToNewWindow = id;
frameToThisWindow = id;
getInfo = id;
goToLocationFromToolbarURLField = id;
home = id;
manageBookmarks = id;
moveTabToNewWindow = id;
newTab = id;
nextTab = id;
openLinkInNewTab = id;
openLinkInNewWindow = id;
pageSetup = id;
performSearch = id;
previousTab = id;
printDocument = id;
reload = id;
reloadSendersTab = id;
saveFrameAs = id;
saveImageAs = id;
saveLinkAs = id;
savePageAs = id;
sendURL = id;
smallerTextSize = id;
stop = id;
toggleSidebar = id;
viewOnlyThisImage = id;
viewPageSource = id;
viewSource = id;
};
CLASS = BrowserWindowController;
LANGUAGE = ObjC;
OUTLETS = {
mAddBookmarkCheckbox = NSButton;
mAddBookmarkFolderField = NSPopUpButton;
mAddBookmarkSheetWindow = NSWindow;
mAddBookmarkTitleField = NSTextField;
mBackItem = NSMenuItem;
mContentView = BrowserContentView;
mCopyItem = NSMenuItem;
mForwardItem = NSMenuItem;
mHistoryDataSource = HistoryDataSource;
mImageLinkMenu = NSMenu;
mImageMenu = NSMenu;
mInputMenu = NSMenu;
mLinkMenu = NSMenu;
mLocationSheetURLField = NSTextField;
mLocationSheetWindow = NSWindow;
mLocationToolbarView = NSView;
mLock = NSImageView;
mPageMenu = NSMenu;
mPersonalToolbar = BookmarksToolbar;
mProgress = NSProgressIndicator;
mProxyIcon = PageProxyIcon;
mSidebarBookmarksDataSource = BookmarksDataSource;
mSidebarDrawer = NSDrawer;
mSidebarSourceTabView = NSTabView;
mSidebarTabView = NSTabView;
mStatus = NSTextField;
mStatusBar = NSView;
mTabBrowser = BrowserTabView;
mTabMenu = NSMenu;
mURLBar = NSTextField;
};
SUPERCLASS = NSWindowController;
},
{
ACTIONS = {load = id; };
CLASS = BrowserWrapper;
LANGUAGE = ObjC;
OUTLETS = {
mLockIcon = id;
mWindowController = id;
progress = id;
progressSuper = id;
status = id;
urlbar = id;
};
SUPERCLASS = NSView;
},
{CLASS = ExtendedOutlineView; LANGUAGE = ObjC; SUPERCLASS = NSOutlineView; },
{CLASS = FirstResponder; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{
CLASS = HistoryDataSource;
LANGUAGE = ObjC;
OUTLETS = {mBrowserWindowController = id; };
SUPERCLASS = RDFOutlineViewDataSource;
},
{CLASS = LocationBar; LANGUAGE = ObjC; SUPERCLASS = NSView; },
{CLASS = MainController; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{CLASS = PageProxyIcon; LANGUAGE = ObjC; SUPERCLASS = NSImageView; },
{
CLASS = RDFOutlineViewDataSource;
LANGUAGE = ObjC;
OUTLETS = {mOutlineView = id; };
SUPERCLASS = NSObject;
},
{CLASS = RDFOutlineViewItem; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{CLASS = ThrobberHandler; LANGUAGE = ObjC; SUPERCLASS = NSObject; }
);
IBVersion = 1;
}

Просмотреть файл

@ -3,7 +3,7 @@
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>66 21 653 383 0 0 1152 848 </string>
<string>65 36 653 383 0 0 1152 848 </string>
<key>IBEditorPositions</key>
<dict>
<key>124</key>
@ -15,17 +15,17 @@
<key>297</key>
<string>107 466 213 294 0 0 1600 1002 </string>
<key>314</key>
<string>73 542 213 132 0 0 1600 1002 </string>
<string>72 544 213 150 0 0 1600 1002 </string>
<key>336</key>
<string>486 756 213 180 0 0 1600 1002 </string>
<key>365</key>
<string>31 719 93 162 0 0 1600 1002 </string>
<key>463</key>
<string>97 693 213 246 0 0 1600 1002 </string>
<string>349 487 213 246 0 0 1600 1002 </string>
<key>56</key>
<string>450 634 343 68 0 0 1280 1002 </string>
<key>654</key>
<string>206 785 198 144 0 0 1600 1002 </string>
<string>140 644 198 144 0 0 1152 848 </string>
</dict>
<key>IBFramework Version</key>
<string>286.0</string>
@ -42,6 +42,6 @@
<key>IBLockedObjects</key>
<array/>
<key>IBSystem Version</key>
<string>6F21</string>
<string>6G30</string>
</dict>
</plist>

Двоичные данные
chimera/resources/localized/English.lproj/BrowserWindow.nib/objects.nib сгенерированный

Двоичный файл не отображается.

0
chimera/resources/localized/English.lproj/Keychain.nib/classes.nib сгенерированный Normal file
Просмотреть файл

0
chimera/resources/localized/English.lproj/Keychain.nib/info.nib сгенерированный Normal file
Просмотреть файл

0
chimera/resources/localized/English.lproj/Keychain.nib/objects.nib сгенерированный Normal file
Просмотреть файл

Двоичный файл не отображается.

Просмотреть файл

@ -20,6 +20,7 @@
doReload = id;
doSearch = id;
doStop = id;
downloadsWindow = id;
exportBookmarks = id;
feedbackLink = id;
findAgain = id;
@ -61,7 +62,6 @@
mCreateBookmarksFolderMenuItem = NSMenuItem;
mCreateBookmarksSeparatorMenuItem = NSMenuItem;
mDockMenu = NSMenu;
mFilterList = NSPopUpButton;
mFilterView = NSView;
mGoMenu = NSMenu;
mServersSubmenu = NSMenu;

Просмотреть файл

@ -3,11 +3,11 @@
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>237 33 482 372 0 0 1600 1002 </string>
<string>105 33 482 372 0 0 1600 1002 </string>
<key>IBEditorPositions</key>
<dict>
<key>266</key>
<string>437 533 277 90 0 0 1152 848 </string>
<string>644 623 277 90 0 0 1600 1002 </string>
<key>29</key>
<string>11 957 446 44 0 0 1600 1002 </string>
<key>494</key>
@ -31,7 +31,11 @@
</dict>
<key>IBLastGroupID</key>
<string>2</string>
<key>IBOpenObjects</key>
<array>
<integer>29</integer>
</array>
<key>IBSystem Version</key>
<string>6F21</string>
<string>6G30</string>
</dict>
</plist>

Двоичные данные
chimera/resources/localized/English.lproj/MainMenu.nib/objects.nib сгенерированный

Двоичный файл не отображается.

Просмотреть файл

@ -1,19 +0,0 @@
{
IBClasses = (
{CLASS = FirstResponder; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
{
CLASS = ProgressDlgController;
LANGUAGE = ObjC;
OUTLETS = {
mElapsedTimeLabel = NSTextField;
mFromField = NSTextField;
mProgressBar = NSProgressIndicator;
mStatusLabel = NSTextField;
mTimeLeftLabel = NSTextField;
mToField = NSTextField;
};
SUPERCLASS = NSWindowController;
}
);
IBVersion = 1;
}

Просмотреть файл

@ -1,12 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist SYSTEM "file://localhost/System/Library/DTDs/PropertyList.dtd">
<plist version="0.9">
<dict>
<key>IBDocumentLocation</key>
<string>94 26 404 250 0 0 1152 746 </string>
<key>IBFramework Version</key>
<string>248.0</string>
<key>IBSystem Version</key>
<string>5S60</string>
</dict>
</plist>

Двоичные данные
chimera/resources/localized/English.lproj/ProgressDialog.nib/objects.nib сгенерированный

Двоичный файл не отображается.

0
chimera/resources/localized/English.lproj/ProgressView.nib/classes.nib сгенерированный Normal file
Просмотреть файл

0
chimera/resources/localized/English.lproj/ProgressView.nib/info.nib сгенерированный Normal file
Просмотреть файл

0
chimera/resources/localized/English.lproj/ProgressView.nib/objects.nib сгенерированный Normal file
Просмотреть файл

Просмотреть файл

@ -1,16 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>IBDocumentLocation</key>
<string>410 67 356 301 0 0 1152 848 </string>
<key>IBFramework Version</key>
<string>286.0</string>
<key>IBOpenObjects</key>
<array>
<integer>251</integer>
</array>
<key>IBSystem Version</key>
<string>6F21</string>
</dict>
</plist>

Двоичные данные
chimera/resources/localized/English.lproj/alert.nib/objects.nib сгенерированный

Двоичный файл не отображается.

Просмотреть файл

@ -37,10 +37,14 @@
* ***** END LICENSE BLOCK ***** */
#import <Cocoa/Cocoa.h>
#import "SecurityDialogs.h"
#import "CocoaPromptService.h"
#include "nsIGenericFactory.h"
#import "KeychainService.h"
#import "nsDownloadListener.h"
#import "ProgressDlgController.h"
#include "nsIGenericFactory.h"
// {0ffd3880-7a1a-11d6-a384-975d1d5f86fc}
#define NS_SECURITYDIALOGS_CID \
@ -55,6 +59,27 @@
NS_GENERIC_FACTORY_CONSTRUCTOR(SecurityDialogs);
NS_GENERIC_FACTORY_CONSTRUCTOR(CocoaPromptService);
NS_GENERIC_FACTORY_CONSTRUCTOR(KeychainPrompt);
//NS_GENERIC_FACTORY_CONSTRUCTOR(nsDownloadListener);
static NS_IMETHODIMP
nsDownloadListenerConstructor(nsISupports *aOuter, REFNSIID aIID, void **aResult)
{
*aResult = NULL;
if (aOuter)
return NS_ERROR_NO_AGGREGATION;
nsDownloadListener* inst;
NS_NEWXPCOM(inst, nsDownloadListener);
if (!inst)
return NS_ERROR_OUT_OF_MEMORY;
NS_ADDREF(inst);
inst->SetDisplayFactory([ProgressDlgController sharedDownloadController]);
nsresult rv = inst->QueryInterface(aIID, aResult);
NS_RELEASE(inst);
return rv;
}
// used by MainController to register the components in which we want to override
// with the Gecko embed layer.
@ -83,6 +108,12 @@ static const nsModuleComponentInfo gAppComponents[] = {
NS_KEYCHAINPROMPT_CID,
"@mozilla.org/wallet/single-sign-on-prompt;1",
KeychainPromptConstructor
},
{
"Download",
NS_DOWNLOAD_CID,
NS_DOWNLOAD_CONTRACTID,
nsDownloadListenerConstructor
}
};

Просмотреть файл

@ -52,9 +52,8 @@
{
IBOutlet NSApplication* mApplication;
// The following two items are used by the filter list when saving files.
// The following item is added to NSSavePanels as an accessory view
IBOutlet NSView* mFilterView;
IBOutlet NSPopUpButton* mFilterList;
// IBOutlet NSMenuItem* mOfflineMenuItem;
IBOutlet NSMenuItem* mCloseWindowMenuItem;
@ -137,11 +136,12 @@
-(IBAction) addFolder:(id)aSender;
-(IBAction) addSeparator:(id)aSender;
//Window menu actions
// Window menu actions
-(IBAction) newTab:(id)aSender;
-(IBAction) closeTab:(id)aSender;
-(IBAction) downloadsWindow:(id)aSender;
//Help menu actions
// Help menu actions
-(IBAction) infoLink:(id)aSender;
-(IBAction) feedbackLink:(id)aSender;
@ -154,7 +154,8 @@
- (void)adjustBookmarksMenuItemsEnabling:(BOOL)inBrowserWindowFrontmost;
-(NSWindow*)getFrontmostBrowserWindow;
- (NSView*)getSavePanelView;
- (NSWindow*)getFrontmostBrowserWindow;
- (MVPreferencesController *)preferencesController;
- (void)displayPreferencesWindow:sender;

Просмотреть файл

@ -260,19 +260,7 @@ const int kReuseWindowOnAE = 2;
- (NSApplicationTerminateReply)applicationShouldTerminate:(NSApplication *)sender
{
if ([ProgressDlgController numDownloadInProgress] > 0)
{
NSString *alert = NSLocalizedString(@"QuitWithDownloadsMsg", @"Really Quit?");
NSString *message = NSLocalizedString(@"QuitWithDownloadsExpl", @"");
NSString *okButton = NSLocalizedString(@"QuitWithdownloadsButtonDefault",@"Cancel");
NSString *altButton = NSLocalizedString(@"QuitWithdownloadsButtonAlt",@"Quit");
// while the panel is up, download dialogs won't update (no timers firing) but
// downloads continue (PLEvents being processed)
if (NSRunAlertPanel(alert, message, okButton, altButton, nil) == NSAlertDefaultReturn)
return NSTerminateCancel;
}
return NSTerminateNow;
return [[ProgressDlgController sharedDownloadController] allowTerminate];
}
-(void)applicationWillTerminate: (NSNotification*)aNotification
@ -439,7 +427,7 @@ const int kReuseWindowOnAE = 2;
{
BrowserWindowController* browserController = [self getMainWindowBrowserController];
if (browserController)
[browserController saveDocument:NO filterView:mFilterView filterList: mFilterList];
[browserController saveDocument:NO filterView:mFilterView];
}
-(IBAction) pageSetup:(id)aSender
@ -584,6 +572,11 @@ const int kReuseWindowOnAE = 2;
}
}
-(IBAction) downloadsWindow:(id)aSender
{
[[ProgressDlgController sharedDownloadController] showWindow:aSender];
}
- (void)adjustBookmarksMenuItemsEnabling:(BOOL)inBrowserWindowFrontmost;
{
[mAddBookmarkMenuItem setEnabled:inBrowserWindowFrontmost];
@ -591,6 +584,11 @@ const int kReuseWindowOnAE = 2;
[mCreateBookmarksSeparatorMenuItem setEnabled:NO]; // separators are not implemented yet
}
- (NSView*)getSavePanelView
{
return mFilterView;
}
-(NSWindow*)getFrontmostBrowserWindow
{
// for some reason, [NSApp mainWindow] doesn't always work, so we have to

Просмотреть файл

@ -47,7 +47,58 @@ NSGETMODULE(_name) (nsIComponentManager* aCompMgr, \
}
// NSGetModule entry points
DECL_NSGETMODULE(UcharUtil) DECL_NSGETMODULE(nsUConvModule) DECL_NSGETMODULE(nsUCvJAModule) DECL_NSGETMODULE(nsUCvCnModule) DECL_NSGETMODULE(nsUCvLatinModule) DECL_NSGETMODULE(nsUCvTWModule) DECL_NSGETMODULE(nsUCvTW2Module) DECL_NSGETMODULE(nsUCvKoModule) DECL_NSGETMODULE(nsLocaleModule) DECL_NSGETMODULE(nsStringBundleModule) DECL_NSGETMODULE(nsLWBrkModule) DECL_NSGETMODULE(nsCharDetModule) DECL_NSGETMODULE(xpconnect) DECL_NSGETMODULE(cacheservice) DECL_NSGETMODULE(necko_core_and_primary_protocols) DECL_NSGETMODULE(necko_secondary_protocols) DECL_NSGETMODULE(nsURILoaderModule) DECL_NSGETMODULE(nsPrefModule) DECL_NSGETMODULE(nsCJVMManagerModule) DECL_NSGETMODULE(nsSecurityManagerModule) DECL_NSGETMODULE(nsChromeModule) DECL_NSGETMODULE(nsRDFModule) DECL_NSGETMODULE(nsParserModule) DECL_NSGETMODULE(nsGfxMacModule) DECL_NSGETMODULE(nsGfx2Module) DECL_NSGETMODULE(nsImageLib2Module) DECL_NSGETMODULE(nsPNGDecoderModule) DECL_NSGETMODULE(nsGIFModule2) DECL_NSGETMODULE(nsJPEGDecoderModule) DECL_NSGETMODULE(nsPluginModule) DECL_NSGETMODULE(javascript__protocol) DECL_NSGETMODULE(DOM_components) DECL_NSGETMODULE(nsViewModule) DECL_NSGETMODULE(nsWidgetMacModule) DECL_NSGETMODULE(nsContentModule) DECL_NSGETMODULE(nsLayoutModule) DECL_NSGETMODULE(nsMorkModule) DECL_NSGETMODULE(docshell_provider) DECL_NSGETMODULE(embedcomponents) DECL_NSGETMODULE(Browser_Embedding_Module) DECL_NSGETMODULE(nsEditorModule) DECL_NSGETMODULE(nsTransactionManagerModule) DECL_NSGETMODULE(nsTextServicesModule) DECL_NSGETMODULE(nsProfileModule) DECL_NSGETMODULE(Session_History_Module) DECL_NSGETMODULE(application) DECL_NSGETMODULE(nsCookieModule) DECL_NSGETMODULE(nsXMLExtrasModule) DECL_NSGETMODULE(nsUniversalCharDetModule) DECL_NSGETMODULE(BOOT) DECL_NSGETMODULE(NSS)
DECL_NSGETMODULE(UcharUtil)
DECL_NSGETMODULE(nsUConvModule)
DECL_NSGETMODULE(nsUCvJAModule)
DECL_NSGETMODULE(nsUCvCnModule)
DECL_NSGETMODULE(nsUCvLatinModule)
DECL_NSGETMODULE(nsUCvTWModule)
DECL_NSGETMODULE(nsUCvTW2Module)
DECL_NSGETMODULE(nsUCvKoModule)
DECL_NSGETMODULE(nsLocaleModule)
DECL_NSGETMODULE(nsStringBundleModule)
DECL_NSGETMODULE(nsLWBrkModule)
DECL_NSGETMODULE(nsCharDetModule)
DECL_NSGETMODULE(xpconnect)
DECL_NSGETMODULE(cacheservice)
DECL_NSGETMODULE(necko_core_and_primary_protocols)
DECL_NSGETMODULE(necko_secondary_protocols)
DECL_NSGETMODULE(nsURILoaderModule)
DECL_NSGETMODULE(nsPrefModule)
DECL_NSGETMODULE(nsCJVMManagerModule)
DECL_NSGETMODULE(nsSecurityManagerModule)
DECL_NSGETMODULE(nsChromeModule)
DECL_NSGETMODULE(nsRDFModule)
DECL_NSGETMODULE(nsParserModule)
DECL_NSGETMODULE(nsGfxMacModule)
DECL_NSGETMODULE(nsGfx2Module)
DECL_NSGETMODULE(nsImageLib2Module)
DECL_NSGETMODULE(nsPNGDecoderModule)
DECL_NSGETMODULE(nsGIFModule2)
DECL_NSGETMODULE(nsJPEGDecoderModule)
DECL_NSGETMODULE(nsPluginModule)
DECL_NSGETMODULE(javascript__protocol)
DECL_NSGETMODULE(JS_component_loader)
DECL_NSGETMODULE(DOM_components)
DECL_NSGETMODULE(nsViewModule)
DECL_NSGETMODULE(nsWidgetMacModule)
DECL_NSGETMODULE(nsContentModule)
DECL_NSGETMODULE(nsLayoutModule)
DECL_NSGETMODULE(nsMorkModule)
DECL_NSGETMODULE(docshell_provider)
DECL_NSGETMODULE(embedcomponents)
DECL_NSGETMODULE(Browser_Embedding_Module)
DECL_NSGETMODULE(nsEditorModule)
DECL_NSGETMODULE(nsTransactionManagerModule)
DECL_NSGETMODULE(nsTextServicesModule)
DECL_NSGETMODULE(nsProfileModule)
DECL_NSGETMODULE(Session_History_Module)
DECL_NSGETMODULE(application)
DECL_NSGETMODULE(nsCookieModule)
DECL_NSGETMODULE(nsXMLExtrasModule)
DECL_NSGETMODULE(nsUniversalCharDetModule)
DECL_NSGETMODULE(BOOT)
DECL_NSGETMODULE(NSS)
#line 52 "nsStaticComponents.cpp.in"
/**
@ -55,7 +106,58 @@ DECL_NSGETMODULE(UcharUtil) DECL_NSGETMODULE(nsUConvModule) DECL_NSGETMODULE(nsU
*/
static nsStaticModuleInfo gStaticModuleInfo[] = {
#define MODULE(_name) { (#_name), NSGETMODULE(_name) }
MODULE(UcharUtil), MODULE(nsUConvModule), MODULE(nsUCvJAModule), MODULE(nsUCvCnModule), MODULE(nsUCvLatinModule), MODULE(nsUCvTWModule), MODULE(nsUCvTW2Module), MODULE(nsUCvKoModule), MODULE(nsLocaleModule), MODULE(nsStringBundleModule), MODULE(nsLWBrkModule), MODULE(nsCharDetModule), MODULE(xpconnect), MODULE(cacheservice), MODULE(necko_core_and_primary_protocols), MODULE(necko_secondary_protocols), MODULE(nsURILoaderModule), MODULE(nsPrefModule), MODULE(nsCJVMManagerModule), MODULE(nsSecurityManagerModule), MODULE(nsChromeModule), MODULE(nsRDFModule), MODULE(nsParserModule), MODULE(nsGfxMacModule), MODULE(nsGfx2Module), MODULE(nsImageLib2Module), MODULE(nsPNGDecoderModule), MODULE(nsGIFModule2), MODULE(nsJPEGDecoderModule), MODULE(nsPluginModule), MODULE(javascript__protocol), MODULE(DOM_components), MODULE(nsViewModule), MODULE(nsWidgetMacModule), MODULE(nsContentModule), MODULE(nsLayoutModule), MODULE(nsMorkModule), MODULE(docshell_provider), MODULE(embedcomponents), MODULE(Browser_Embedding_Module), MODULE(nsEditorModule), MODULE(nsTransactionManagerModule), MODULE(nsTextServicesModule), MODULE(nsProfileModule), MODULE(Session_History_Module), MODULE(application), MODULE(nsCookieModule), MODULE(nsXMLExtrasModule), MODULE(nsUniversalCharDetModule), MODULE(BOOT), MODULE(NSS),
MODULE(UcharUtil),
MODULE(nsUConvModule),
MODULE(nsUCvJAModule),
MODULE(nsUCvCnModule),
MODULE(nsUCvLatinModule),
MODULE(nsUCvTWModule),
MODULE(nsUCvTW2Module),
MODULE(nsUCvKoModule),
MODULE(nsLocaleModule),
MODULE(nsStringBundleModule),
MODULE(nsLWBrkModule),
MODULE(nsCharDetModule),
MODULE(xpconnect),
MODULE(cacheservice),
MODULE(necko_core_and_primary_protocols),
MODULE(necko_secondary_protocols),
MODULE(nsURILoaderModule),
MODULE(nsPrefModule),
MODULE(nsCJVMManagerModule),
MODULE(nsSecurityManagerModule),
MODULE(nsChromeModule),
MODULE(nsRDFModule),
MODULE(nsParserModule),
MODULE(nsGfxMacModule),
MODULE(nsGfx2Module),
MODULE(nsImageLib2Module),
MODULE(nsPNGDecoderModule),
MODULE(nsGIFModule2),
MODULE(nsJPEGDecoderModule),
MODULE(nsPluginModule),
MODULE(javascript__protocol),
MODULE(JS_component_loader),
MODULE(DOM_components),
MODULE(nsViewModule),
MODULE(nsWidgetMacModule),
MODULE(nsContentModule),
MODULE(nsLayoutModule),
MODULE(nsMorkModule),
MODULE(docshell_provider),
MODULE(embedcomponents),
MODULE(Browser_Embedding_Module),
MODULE(nsEditorModule),
MODULE(nsTransactionManagerModule),
MODULE(nsTextServicesModule),
MODULE(nsProfileModule),
MODULE(Session_History_Module),
MODULE(application),
MODULE(nsCookieModule),
MODULE(nsXMLExtrasModule),
MODULE(nsUniversalCharDetModule),
MODULE(BOOT),
MODULE(NSS),
#line 60 "nsStaticComponents.cpp.in"
};

Просмотреть файл

@ -1,883 +0,0 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: NPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Netscape Public License
* Version 1.1 (the "License"); you may not use this file except in
* compliance with the License. You may obtain a copy of the License at
* http://www.mozilla.org/NPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 2002
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
*
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the NPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the NPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#import "NSString+Utils.h"
#import "BookmarksDataSource.h"
#import "BookmarkInfoController.h"
#import "SiteIconProvider.h"
#include "nsCOMPtr.h"
#include "nsIContent.h"
#include "nsIDocument.h"
#include "nsIDocumentObserver.h"
#include "nsIDOMDocument.h"
#include "nsIDOMElement.h"
#include "nsINamespaceManager.h"
#include "nsVoidArray.h"
#import "BookmarksService.h"
@interface BookmarksDataSource(Private)
- (void)restoreFolderExpandedStates;
- (void)refreshChildrenOfItem:(nsIContent*)item;
@end
const int kBookmarksRootItemTag = -2;
@implementation BookmarksDataSource
-(id) init
{
if ( (self = [super init]) )
{
mCachedHref = nil;
}
return self;
}
- (void)dealloc
{
// NSLog(@"BookmarksDataSource dealloc");
[super dealloc];
}
-(void) awakeFromNib
{
// make sure these are disabled at the start since the outliner
// starts off with no selection.
[mEditBookmarkButton setEnabled:NO];
[mDeleteBookmarkButton setEnabled:NO];
}
-(void) windowClosing
{
BookmarksManager* bmManager = [BookmarksManager sharedBookmarksManagerDontAlloc];
[bmManager removeBookmarksClient:self];
}
-(void) ensureBookmarks
{
if (mRegisteredClient)
return;
BookmarksManager* bmManager = [BookmarksManager sharedBookmarksManager];
[bmManager addBookmarksClient:self];
mRegisteredClient = YES;
[mOutlineView setTarget: self];
[mOutlineView setDoubleAction: @selector(openBookmark:)];
[mOutlineView setDeleteAction: @selector(deleteBookmarks:)];
[mOutlineView reloadData];
[self restoreFolderExpandedStates];
}
-(IBAction)addBookmark:(id)aSender
{
[self addBookmark: aSender useSelection: YES isFolder: NO URL:nil title:nil];
}
-(IBAction)addFolder:(id)aSender
{
[self addBookmark: aSender useSelection: YES isFolder: YES URL:nil title:nil];
}
-(void)addBookmark:(id)aSender useSelection:(BOOL)aUseSel isFolder:(BOOL)aIsFolder URL:(NSString*)aURL title:(NSString*)aTitle
{
// We use the selected item to determine the parent only if aUseSel is YES.
BookmarkItem* item = nil;
if (aUseSel && ([mOutlineView numberOfSelectedRows] == 1))
{
// There is only one selected row. If it is a folder, use it as our parent.
// Otherwise, use our parent,
int index = [mOutlineView selectedRow];
item = [mOutlineView itemAtRow: index];
if (![mOutlineView isExpandable: item]) {
// We can't be used as the parent. Try our parent.
nsIContent* content = [item contentNode];
if (!content)
return;
nsCOMPtr<nsIContent> parentContent;
content->GetParent(*getter_AddRefs(parentContent));
nsCOMPtr<nsIContent> root;
BookmarksService::GetRootContent(getter_AddRefs(root));
// The root has no item, so we don't need to do a lookup unless we
// aren't the root.
if (parentContent != root) {
PRUint32 contentID;
parentContent->GetContentID(&contentID);
item = BookmarksService::GetWrapperFor(contentID);
}
}
}
[self addBookmark:aSender withParent:item isFolder:aIsFolder URL:aURL title:aTitle];
}
-(void)addBookmark:(id)aSender withParent:(BookmarkItem*)bmItem isFolder:(BOOL)aIsFolder URL:(NSString*)aURL title:(NSString*)aTitle
{
NSString* titleString = aTitle;
NSString* urlString = aURL;
if (!aIsFolder)
{
// If no URL and title were specified, get them from the current page.
if (!aURL || !aTitle)
[[mBrowserWindowController getBrowserWrapper] getTitle:&titleString andHref:&urlString];
mCachedHref = [NSString stringWithString:urlString];
[mCachedHref retain];
} else { // Folder
mCachedHref = nil;
titleString = NSLocalizedString(@"NewBookmarkFolder", @"");
}
NSTextField* textField = [mBrowserWindowController getAddBookmarkTitle];
NSString* bookmarkTitle = titleString;
NSString* cleanedTitle = [bookmarkTitle stringByReplacingCharactersInSet:[NSCharacterSet controlCharacterSet] withString:@" "];
[textField setStringValue: cleanedTitle];
[mBrowserWindowController cacheBookmarkDS: self];
// Show/hide the bookmark all tabs checkbox as appropriate.
NSTabView* tabView = [mBrowserWindowController getTabBrowser];
id checkbox = [mBrowserWindowController getAddBookmarkCheckbox];
BOOL hasSuperview = [checkbox superview] != nil;
if (aIsFolder && hasSuperview) {
// Just don't show it at all.
[checkbox removeFromSuperview];
[checkbox retain];
}
else if (!aIsFolder && !hasSuperview) {
// Put it back in.
[[[mBrowserWindowController getAddBookmarkSheetWindow] contentView] addSubview: checkbox];
[checkbox autorelease];
}
// Enable the bookmark all tabs checkbox if appropriate.
if (!aIsFolder)
[[mBrowserWindowController getAddBookmarkCheckbox] setEnabled: ([tabView numberOfTabViewItems] > 1)];
// Build up the folder list.
NSPopUpButton* popup = [mBrowserWindowController getAddBookmarkFolder];
[popup removeAllItems];
[popup addItemWithTitle: NSLocalizedString(@"BookmarksRootName", @"")];
[[popup lastItem] setTag:kBookmarksRootItemTag];
BookmarksManager* bmManager = [BookmarksManager sharedBookmarksManager];
[bmManager buildFlatFolderList:[popup menu] fromRoot:NULL];
int itemIndex = [popup indexOfItemWithTag:[bmItem intContentID]];
if (itemIndex != -1)
[popup selectItemAtIndex:itemIndex];
[popup synchronizeTitleAndSelectedItem];
[NSApp beginSheet: [mBrowserWindowController getAddBookmarkSheetWindow]
modalForWindow: [mBrowserWindowController window]
modalDelegate: nil //self
didEndSelector: nil //@selector(sheetDidEnd:)
contextInfo: nil];
}
-(void)endAddBookmark: (int)aCode
{
if (aCode == 0)
return;
BOOL isGroup = NO;
id checkbox = [mBrowserWindowController getAddBookmarkCheckbox];
if (([checkbox superview] != nil) && [checkbox isEnabled] && ([checkbox state] == NSOnState))
{
[mCachedHref release];
mCachedHref = nil;
isGroup = YES;
}
BookmarksManager* bmManager = [BookmarksManager sharedBookmarksManager];
NSString* titleString = [[mBrowserWindowController getAddBookmarkTitle] stringValue];
// Figure out the parent element.
nsCOMPtr<nsIContent> parentContent;
NSPopUpButton* popup = [mBrowserWindowController getAddBookmarkFolder];
NSMenuItem* selectedItem = [popup selectedItem];
int tag = [selectedItem tag];
if (tag != kBookmarksRootItemTag)
{
BookmarkItem* item = BookmarksService::GetWrapperFor(tag);
// Get the content node.
parentContent = [item contentNode];
}
if (isGroup)
{
id tabBrowser = [mBrowserWindowController getTabBrowser];
int count = [tabBrowser numberOfTabViewItems];
NSMutableArray* itemsArray = [[NSMutableArray alloc] initWithCapacity:count];
for (int i = 0; i < count; i++)
{
BrowserWrapper* browserWrapper = (BrowserWrapper*)[[tabBrowser tabViewItemAtIndex: i] view];
NSString* titleString = nil;
NSString* hrefString = nil;
[browserWrapper getTitle:&titleString andHref:&hrefString];
NSDictionary* itemDict = [NSDictionary dictionaryWithObjectsAndKeys:
titleString, @"title",
hrefString, @"href",
nil];
[itemsArray addObject:itemDict];
}
[bmManager addNewBookmarkGroup:titleString items:itemsArray withParent:parentContent];
}
else
{
if (mCachedHref)
{
[bmManager addNewBookmark:mCachedHref title:titleString withParent:parentContent];
[mCachedHref release];
mCachedHref = nil;
}
else
[bmManager addNewBookmarkFolder:titleString withParent:parentContent];
}
}
-(IBAction)deleteBookmarks: (id)aSender
{
int index = [mOutlineView selectedRow];
if (index == -1)
return;
// first, see how many items are selected
BOOL haveBookmarks = NO;
NSEnumerator* testSelRows = [mOutlineView selectedRowEnumerator];
for (NSNumber* currIndex = [testSelRows nextObject];
currIndex != nil;
currIndex = [testSelRows nextObject])
{
index = [currIndex intValue];
BookmarkItem* item = [mOutlineView itemAtRow: index];
if ([mOutlineView isExpandable: item]) {
// dumb check to see if we're deleting an empty folder. Should really
// recurse down
if ([self outlineView:mOutlineView numberOfChildrenOfItem: item] > 0)
haveBookmarks = YES;
} else
haveBookmarks = YES;
}
// ideally, we should count the number of doomed bookmarks and tell the user
if (haveBookmarks) {
NSString *alert = NSLocalizedString(@"DeteleBookmarksAlert",@"");
NSString *message = NSLocalizedString(@"DeteleBookmarksMsg",@"");
NSString *okButton = NSLocalizedString(@"DeteleBookmarksOKButton",@"");
NSString *cancelButton = NSLocalizedString(@"DeteleBookmarksCancelButton",@"");
if (NSRunAlertPanel(alert, message, okButton, cancelButton, nil) != NSAlertDefaultReturn)
return;
}
// The alert panel was the key window. As soon as we dismissed it, Cocoa will
// pick a new one for us. Ideally, it'll be the window we were using when
// we clicked the delete button. However, if by chance the BookmarkInfoController
// is visible, it will become the key window since it's a panel. If we then delete
// the bookmark and try to close the window before we've setup a new bookmark,
// we'll trigger the windowDidResignKey message, which will try to update the bookmark
// we just deleted, and things will crash. So, we'll trigger windowDidResignKey now
// and avoid the unpleasentness of a crash log.
if (![[mBrowserWindowController window] isKeyWindow])
[[mBrowserWindowController window] makeKeyWindow];
// we'll run into problems if a parent item and one if its children are both selected.
// A cheap way of having to avoid scanning the list to remove children is to have the
// outliner collapse all items that are being deleted. This will cull the selection
// for us and eliminate any children that happened to be selected.
NSEnumerator* selRows = [mOutlineView selectedRowEnumerator];
for (NSNumber* currIndex = [selRows nextObject];
currIndex != nil;
currIndex = [selRows nextObject]) {
index = [currIndex intValue];
BookmarkItem* item = [mOutlineView itemAtRow: index];
[mOutlineView collapseItem: item];
}
// create array of items we need to delete. Deleting items out of of the
// selection array is problematic for some reason.
NSMutableArray* itemsToDelete = [[[NSMutableArray alloc] init] autorelease];
selRows = [mOutlineView selectedRowEnumerator];
for (NSNumber* currIndex = [selRows nextObject];
currIndex != nil;
currIndex = [selRows nextObject]) {
index = [currIndex intValue];
BookmarkItem* item = [mOutlineView itemAtRow: index];
[itemsToDelete addObject: item];
}
// delete all bookmarks that are in our array
int count = [itemsToDelete count];
for (int i = 0; i < count; i++) {
BookmarkItem* item = [itemsToDelete objectAtIndex: i];
[self deleteBookmark: item];
}
// restore selection to location near last item deleted or last item
int total = [mOutlineView numberOfRows];
if (index >= total)
index = total - 1;
[mOutlineView selectRow: index byExtendingSelection: NO];
// lame, but makes sure we catch all delete events in Info Panel
[[NSNotificationCenter defaultCenter] postNotificationName:@"NSOutlineViewSelectionDidChangeNotification" object:mOutlineView];
}
-(void)deleteBookmark:(id)aItem
{
[aItem remove];
}
-(IBAction)openBookmark: (id)aSender
{
int index = [mOutlineView selectedRow];
if (index == -1)
return;
id item = [mOutlineView itemAtRow: index];
if (!item)
return;
if ([item isGroup])
{
NSArray* groupURLs = [[BookmarksManager sharedBookmarksManager] getBookmarkGroupURIs:item];
[mBrowserWindowController openTabGroup:groupURLs replaceExistingTabs:YES];
}
else if ([mOutlineView isExpandable: item])
{
if ([mOutlineView isItemExpanded: item])
[mOutlineView collapseItem: item];
else
[mOutlineView expandItem: item];
}
else
{
// if the command key is down, follow the command-click pref
if (([[NSApp currentEvent] modifierFlags] & NSCommandKeyMask) &&
[[PreferenceManager sharedInstance] getBooleanPref:"browser.tabs.opentabfor.middleclick" withSuccess:NULL])
{
BOOL loadInBackground = [[PreferenceManager sharedInstance] getBooleanPref:"browser.tabs.loadInBackground" withSuccess:NULL];
[mBrowserWindowController openNewTabWithURL:[item url] referrer:nil loadInBackground: loadInBackground];
}
else
[[mBrowserWindowController getBrowserWrapper] loadURI:[item url] referrer:nil flags:NSLoadFlagsNone activate:YES];
}
}
-(IBAction)openBookmarkInNewTab:(id)aSender
{
int index = [mOutlineView selectedRow];
if (index == -1)
return;
if ([mOutlineView numberOfSelectedRows] == 1)
{
BookmarkItem* item = [mOutlineView itemAtRow: index];
BOOL loadInBackground = [[PreferenceManager sharedInstance] getBooleanPref:"browser.tabs.loadInBackground" withSuccess:NULL];
[mBrowserWindowController openNewTabWithURL:[item url] referrer:nil loadInBackground: loadInBackground];
}
}
-(IBAction)openBookmarkInNewWindow:(id)aSender
{
int index = [mOutlineView selectedRow];
if (index == -1)
return;
if ([mOutlineView numberOfSelectedRows] == 1)
{
BookmarkItem* item = [mOutlineView itemAtRow: index];
BOOL loadInBackground = [[PreferenceManager sharedInstance] getBooleanPref:"browser.tabs.loadInBackground" withSuccess:NULL];
if ([item isGroup])
[mBrowserWindowController openNewWindowWithGroup:[item contentNode] loadInBackground:loadInBackground];
else
[mBrowserWindowController openNewWindowWithURL:[item url] referrer: nil loadInBackground: loadInBackground];
}
}
-(IBAction)showBookmarkInfo:(id)aSender
{
BookmarkInfoController *bic = [BookmarkInfoController sharedBookmarkInfoController];
int index = [mOutlineView selectedRow];
BookmarkItem* item = [mOutlineView itemAtRow: index];
[bic setBookmark:item];
[bic showWindow:bic];
}
- (void)restoreFolderExpandedStates
{
int curRow = 0;
while (curRow < [mOutlineView numberOfRows])
{
id item = [mOutlineView itemAtRow:curRow];
if (item)
{
nsCOMPtr<nsIContent> content;
content = [item contentNode];
PRBool isOpen = content && content->HasAttr(kNameSpaceID_None, BookmarksService::gOpenAtom);
if (isOpen)
[mOutlineView expandItem: item];
else
[mOutlineView collapseItem: item];
}
curRow ++;
}
}
- (void)refreshChildrenOfItem:(nsIContent*)item
{
BookmarkItem* bmItem = nil;
nsCOMPtr<nsIContent> parent;
if (item)
item->GetParent(*getter_AddRefs(parent));
if (parent) // we're not the root
bmItem = [[BookmarksManager sharedBookmarksManager] getWrapperForContent:item];
[self reloadDataForItem:bmItem reloadChildren:YES];
}
#pragma mark -
// BookmarksClient protocol
- (void)bookmarkAdded:(nsIContent*)bookmark inContainer:(nsIContent*)container isChangedRoot:(BOOL)isRoot
{
[self refreshChildrenOfItem:container];
}
- (void)bookmarkRemoved:(nsIContent*)bookmark inContainer:(nsIContent*)container isChangedRoot:(BOOL)isRoot
{
[self refreshChildrenOfItem:container];
}
- (void)bookmarkChanged:(nsIContent*)bookmark
{
BookmarkItem* item = [[BookmarksManager sharedBookmarksManager] getWrapperForContent:bookmark];
[self reloadDataForItem:item reloadChildren:NO];
}
- (void)specialFolder:(EBookmarksFolderType)folderType changedTo:(nsIContent*)newFolderContent
{
// change the icons
}
#pragma mark -
//
// outlineView:shouldEditTableColumn:item: (delegate method)
//
// Called by the outliner to determine whether or not we should allow the
// user to edit this item. We're leaving it off for now, becaue there are
// some usability issues with inline editing (no undo, Escape doesn't work).
- (BOOL)outlineView:(NSOutlineView *)outlineView shouldEditTableColumn:(NSTableColumn *)tableColumn item:(id)item
{
return NO; //([[tableColumn identifier] isEqualToString:@"name"]);
}
- (id)outlineView:(NSOutlineView *)outlineView child:(int)index ofItem:(id)item
{
if (!mRegisteredClient) return nil;
nsCOMPtr<nsIContent> content;
if (!item)
BookmarksService::GetRootContent(getter_AddRefs(content));
else
content = [item contentNode];
nsCOMPtr<nsIContent> child;
content->ChildAt(index, *getter_AddRefs(child));
if ( child )
return BookmarksService::GetWrapperFor(child);
return nil;
}
- (BOOL)outlineView:(NSOutlineView *)outlineView isItemExpandable:(id)item
{
if (!mRegisteredClient) return NO;
if (!item)
return YES; // The root node is always open.
return [item isFolder];
}
- (int)outlineView:(NSOutlineView *)outlineView numberOfChildrenOfItem:(id)item
{
if (!mRegisteredClient) return 0;
nsCOMPtr<nsIContent> content;
if (!item)
BookmarksService::GetRootContent(getter_AddRefs(content));
else
content = [item contentNode];
PRInt32 childCount;
content->ChildCount(childCount);
return childCount;
}
- (id)outlineView:(NSOutlineView *)outlineView objectValueForTableColumn:(NSTableColumn *)tableColumn byItem:(id)item
{
if (!mRegisteredClient) return nil;
NSString *columnName = [tableColumn identifier];
NSMutableAttributedString *cellValue = nil;
if ([columnName isEqualToString: @"name"])
{
NSFileWrapper *fileWrapper = [[NSFileWrapper alloc] initRegularFileWithContents:nil];
NSTextAttachment *textAttachment = [[NSTextAttachment alloc] initWithFileWrapper:fileWrapper];
nsIContent* content = [item contentNode];
nsAutoString nameAttr;
content->GetAttr(kNameSpaceID_None, BookmarksService::gNameAtom, nameAttr);
//Set cell's textual contents
//[cellValue replaceCharactersInRange:NSMakeRange(0, [cellValue length]) withString:[NSString stringWith_nsAString: nameAttr]];
cellValue = [[NSMutableAttributedString alloc] initWithString:[NSString stringWith_nsAString: nameAttr]];
//Create an attributed string to hold the empty attachment, then release the components.
NSMutableAttributedString* attachmentAttrString = [NSMutableAttributedString attributedStringWithAttachment:textAttachment];
[textAttachment release];
[fileWrapper release];
//Get the cell of the text attachment.
NSCell* attachmentAttrStringCell = (NSCell *)[(NSTextAttachment *)[attachmentAttrString attribute:NSAttachmentAttributeName atIndex:0 effectiveRange:nil] attachmentCell];
nsCOMPtr<nsIDOMElement> elt(do_QueryInterface(content));
NSImage* bookmarkImage = BookmarksService::CreateIconForBookmark(elt);
[attachmentAttrStringCell setImage:bookmarkImage];
//Insert the image
[cellValue replaceCharactersInRange:NSMakeRange(0, 0) withAttributedString:attachmentAttrString];
//Tweak the baseline to vertically center the text.
[cellValue addAttribute:NSBaselineOffsetAttributeName
value:[NSNumber numberWithFloat:-3.0]
range:NSMakeRange(0, 1)];
}
return cellValue;
}
- (void)outlineView:(NSOutlineView *)outlineView setObjectValue:(id)object forTableColumn:(NSTableColumn *)tableColumn byItem:(id)item
{
// object is really an NSString, even though objectValueForTableColumn returns NSAttributedStrings.
NSString *columnName = [tableColumn identifier];
if ( [columnName isEqualTo:@"name"] )
{
const unichar kAttachmentCharacter = NSAttachmentCharacter;
NSMutableString* mutableString = [NSMutableString stringWithString:object];
[mutableString replaceOccurrencesOfString:[NSString stringWithCharacters:&kAttachmentCharacter length:1] withString:@"" options:0 range:NSMakeRange(0, [mutableString length])];
nsAutoString nameAttr;
[mutableString assignTo_nsAString:nameAttr];
// stash it into the DOM
BookmarkItem* bmItem = (BookmarkItem*)item;
nsIContent* content = [bmItem contentNode];
if (content)
content->SetAttr(kNameSpaceID_None, BookmarksService::gNameAtom, nameAttr, PR_TRUE);
[bmItem itemChanged:YES];
}
}
- (BOOL)outlineView:(NSOutlineView *)ov writeItems:(NSArray*)items toPasteboard:(NSPasteboard*)pboard
{
if (!mRegisteredClient) return NO;
#ifdef FILTER_DESCENDANT_ON_DRAG
NSArray *toDrag = BookmarksService::FilterOutDescendantsForDrag(items);
#else
NSArray *toDrag = items;
#endif
int count = [toDrag count];
if (count > 0) {
// Create Pasteboard Data
NSMutableArray *draggedIDs = [NSMutableArray arrayWithCapacity: count];
for (int i = 0; i < count; i++)
[draggedIDs addObject: [[toDrag objectAtIndex: i] contentID]];
if (count == 1) {
// if we have just one item, we add some more flavours
[pboard declareTypes: [NSArray arrayWithObjects:
@"MozBookmarkType", NSURLPboardType, NSStringPboardType, nil] owner: self];
[pboard setPropertyList: draggedIDs forType: @"MozBookmarkType"];
NSString* itemURL = [[toDrag objectAtIndex: 0] url];
[pboard setString:itemURL forType: NSStringPboardType];
[[NSURL URLWithString:itemURL] writeToPasteboard: pboard];
// maybe construct the @"MozURLType" type here also
}
else {
// multiple bookmarks. Arrays of strings or NSURLs seem to
// confuse receivers. Not sure what the correct way is.
[pboard declareTypes: [NSArray arrayWithObject: @"MozBookmarkType"] owner: self];
[pboard setPropertyList: draggedIDs forType: @"MozBookmarkType"];
}
return YES;
}
return NO;
}
- (NSDragOperation)outlineView:(NSOutlineView*)ov validateDrop:(id <NSDraggingInfo>)info proposedItem:(id)item proposedChildIndex:(int)index
{
if (!mRegisteredClient) return NSDragOperationNone;
NSArray* types = [[info draggingPasteboard] types];
BOOL isCopy = ([info draggingSourceOperationMask] == NSDragOperationCopy);
// if the index is -1, deny the drop
if (index == NSOutlineViewDropOnItemIndex)
return NSDragOperationNone;
if ([types containsObject: @"MozBookmarkType"])
{
NSArray *draggedIDs = [[info draggingPasteboard] propertyListForType: @"MozBookmarkType"];
BookmarkItem* parent = (item) ? item : BookmarksService::GetRootItem();
return (BookmarksService::IsBookmarkDropValid(parent, index, draggedIDs, isCopy)) ? NSDragOperationGeneric : NSDragOperationNone;
}
if ([types containsObject: @"MozURLType"])
return NSDragOperationGeneric;
if ([types containsObject: NSStringPboardType])
return NSDragOperationGeneric;
if ([types containsObject: NSURLPboardType])
return NSDragOperationGeneric;
return NSDragOperationNone;
}
- (BOOL)outlineView:(NSOutlineView*)ov acceptDrop:(id <NSDraggingInfo>)info item:(id)item childIndex:(int)index
{
if (!mRegisteredClient) return NO;
NSArray* types = [[info draggingPasteboard] types];
BookmarkItem* parent = (item) ? item : BookmarksService::GetRootItem();
BOOL isCopy = ([info draggingSourceOperationMask] == NSDragOperationCopy);
BookmarkItem* beforeItem = [self outlineView:ov child:index ofItem:item];
if ([types containsObject: @"MozBookmarkType"])
{
NSArray *draggedItems = [[info draggingPasteboard] propertyListForType: @"MozBookmarkType"];
return BookmarksService::PerformBookmarkDrop(parent, beforeItem, index, draggedItems, isCopy);
}
else if ([types containsObject: @"MozURLType"])
{
NSDictionary* proxy = [[info draggingPasteboard] propertyListForType: @"MozURLType"];
return BookmarksService::PerformProxyDrop(parent, beforeItem, proxy);
}
else if ([types containsObject: NSStringPboardType])
{
NSString* draggedText = [[info draggingPasteboard] stringForType:NSStringPboardType];
return BookmarksService::PerformURLDrop(parent, beforeItem, draggedText, draggedText);
}
else if ([types containsObject: NSURLPboardType])
{
NSURL* urlData = [NSURL URLFromPasteboard:[info draggingPasteboard]];
return BookmarksService::PerformURLDrop(parent, beforeItem, [urlData absoluteString], [urlData absoluteString]);
}
return NO;
}
- (NSString *)outlineView:(NSOutlineView *)outlineView tooltipStringForItem:(id)item
{
if (!mRegisteredClient) return @"";
NSString* descStr = nil;
NSString* hrefStr = nil;
nsIContent* content = [item contentNode];
nsAutoString value;
content->GetAttr(kNameSpaceID_None, BookmarksService::gDescriptionAtom, value);
if (value.Length())
descStr = [NSString stringWith_nsAString:value];
// Only description for folders
if ([item isFolder])
return descStr;
// Extract the URL from the item
content->GetAttr(kNameSpaceID_None, BookmarksService::gHrefAtom, value);
if (value.Length())
hrefStr = [NSString stringWith_nsAString:value];
if (!hrefStr)
return descStr;
else if (!descStr)
return hrefStr;
// Display both URL and description
return [NSString stringWithFormat:@"%@\n%@", hrefStr, descStr];
}
/*
- (NSMenu *)outlineView:(NSOutlineView *)outlineView contextMenuForItem:(id)item
{
// TODO - return (custom?) context menu for item here.
// Note that according to HIG, there should never be disabled items in
// a context menu - instead, items that do not apply should be removed.
// We could nicely do that here.
}
*/
- (void)reloadDataForItem:(id)item reloadChildren: (BOOL)aReloadChildren
{
if (!item)
[mOutlineView reloadData];
else
[mOutlineView reloadItem: item reloadChildren: aReloadChildren];
}
- (BOOL)haveSelectedRow
{
return ([mOutlineView selectedRow] != -1);
}
-(void)outlineViewSelectionDidChange: (NSNotification*) aNotification
{
BookmarkInfoController *bic = [BookmarkInfoController sharedBookmarkInfoController];
int index = [mOutlineView selectedRow];
if (index == -1)
{
[mEditBookmarkButton setEnabled:NO];
[mDeleteBookmarkButton setEnabled:NO];
[bic close];
}
else
{
BookmarkItem* item = [mOutlineView itemAtRow: index];
[mEditBookmarkButton setEnabled:YES];
[mDeleteBookmarkButton setEnabled:![item isToobarRoot]];
if ([[bic window] isVisible])
[bic setBookmark:[mOutlineView itemAtRow:index]];
}
}
-(BOOL)validateMenuItem:(NSMenuItem*)aMenuItem
{
int index = [mOutlineView selectedRow];
BOOL haveSelection = (index != -1);
BOOL isBookmark = NO;
BOOL isGroup = NO;
BookmarkItem* item = nil;
if (haveSelection)
{
item = [mOutlineView itemAtRow: index];
isBookmark = ([mOutlineView isExpandable:item] == NO);
isGroup = [item isGroup];
}
// Bookmarks and Bookmark Groups can be opened in a new window
if (([aMenuItem action] == @selector(openBookmarkInNewWindow:)))
return (isBookmark || isGroup);
// Only Bookmarks can be opened in new tabs
if (([aMenuItem action] == @selector(openBookmarkInNewTab:)))
return isBookmark && [mBrowserWindowController newTabsAllowed];
if (([aMenuItem action] == @selector(showBookmarkInfo:)))
return haveSelection;
if (([aMenuItem action] == @selector(deleteBookmarks:)))
return haveSelection && ![item isToobarRoot]; // should deal with multiple selections
if (([aMenuItem action] == @selector(addFolder:)))
return YES;
return YES;
}
- (void)outlineViewItemWillExpand:(NSNotification *)notification
{
BookmarkItem* item = [[notification userInfo] objectForKey:[[[notification userInfo] allKeys] objectAtIndex: 0]];
[item contentNode]->SetAttr(kNameSpaceID_None, BookmarksService::gOpenAtom, NS_LITERAL_STRING("true"), PR_FALSE);
}
- (void)outlineViewItemWillCollapse:(NSNotification *)notification
{
BookmarkItem* item = [[notification userInfo] objectForKey:[[[notification userInfo] allKeys] objectAtIndex: 0]];
[item contentNode]->UnsetAttr(kNameSpaceID_None, BookmarksService::gOpenAtom, PR_FALSE);
}
@end

Просмотреть файл

@ -100,6 +100,7 @@
- (BOOL)isOpaque
{
// see http://developer.apple.com/qa/qa2001/qa1117.html
if ( ([self tabViewType] == NSNoTabsBezelBorder) && (NSAppKitVersionNumber < 633) )
return NO;

Просмотреть файл

@ -1,94 +0,0 @@
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is Chimera code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 2002
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Simon Fraser <sfraser@netscape.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#import "BrowserWindow.h"
#import "BrowserWindowController.h"
#import "AutoCompleteTextField.h"
static const int kEscapeKeyCode = 53;
@implementation BrowserWindow
- (void)dealloc
{
[super dealloc];
}
- (BOOL)makeFirstResponder:(NSResponder*)responder
{
NSResponder* oldResponder = [self firstResponder];
BOOL madeFirstResponder = [super makeFirstResponder:responder];
if (madeFirstResponder && oldResponder != [self firstResponder])
[(BrowserWindowController*)[self delegate] focusChangedFrom:oldResponder to:[self firstResponder]];
return madeFirstResponder;
}
- (void)sendEvent:(NSEvent *)theEvent
{
// We need this hack because NSWindow::sendEvent will eat the escape key
// and won't pass it down to the key handler of responders in the window.
// We have to override sendEvent for all of our escape key needs.
if ([theEvent type] == NSKeyDown &&
[theEvent keyCode] == kEscapeKeyCode && [self firstResponder] == [mAutoCompleteTextField fieldEditor])
[mAutoCompleteTextField revertText];
else
[super sendEvent:theEvent];
}
- (BOOL)suppressMakeKeyFront
{
return mSuppressMakeKeyFront;
}
- (void)setSuppressMakeKeyFront:(BOOL)inSuppress
{
mSuppressMakeKeyFront = inSuppress;
}
// accessor for the 'URL' Apple Event attribute
- (NSString*)getURL
{
BrowserWindowController* windowController = (BrowserWindowController*)[self delegate];
NSString* titleString = nil;
NSString* urlString = nil;
[[windowController getBrowserWrapper] getTitle:&titleString andHref:&urlString];
return urlString;
}
@end

Просмотреть файл

@ -109,12 +109,12 @@ typedef enum
IBOutlet NSTextField* mLocationSheetURLField;
IBOutlet NSView* mStatusBar; // contains the status text, progress bar, and lock
IBOutlet PageProxyIcon* mProxyIcon;
IBOutlet BrowserContentView* mContentView;
IBOutlet BrowserContentView* mContentView;
IBOutlet BookmarksDataSource* mSidebarBookmarksDataSource;
IBOutlet HistoryDataSource* mHistoryDataSource;
IBOutlet HistoryDataSource* mHistoryDataSource;
IBOutlet BookmarksToolbar* mPersonalToolbar;
IBOutlet BookmarksToolbar* mPersonalToolbar;
IBOutlet NSWindow* mAddBookmarkSheetWindow;
IBOutlet NSTextField* mAddBookmarkTitleField;
@ -191,6 +191,8 @@ typedef enum
- (void)updateLocationFields:(NSString *)locationString;
- (void)updateSiteIcons:(NSImage *)siteIconImage;
- (void)updateToolbarItems;
- (void)loadingStarted;
- (void)loadingDone;
- (void)focusURLBar;
// call to update the image of the lock icon with a value from nsIWebProgressListener
@ -211,9 +213,9 @@ typedef enum
- (IBAction)viewSource:(id)aSender; // focussed frame or page
- (IBAction)viewPageSource:(id)aSender; // top-level page
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList;
- (void)saveURL: (NSView*)aFilterView filterList: (NSPopUpButton*)aFilterList
url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename;
- (void)saveDocument:(BOOL)focusedFrame filterView:(NSView*)aFilterView;
- (void)saveURL:(NSView*)aFilterView url: (NSString*)aURLSpec suggestedFilename: (NSString*)aFilename;
- (IBAction)printDocument:(id)aSender;
- (IBAction)pageSetup:(id)aSender;
- (IBAction)performSearch:(id)aSender;
@ -302,6 +304,7 @@ typedef enum
- (IBAction)bookmarkLink: (id)aSender;
- (IBAction)copyLinkLocation:(id)aSender;
- (IBAction)copyImage:(id)sender;
- (IBAction)copyImageLocation:(id)sender;
- (BookmarksToolbar*) bookmarksToolbar;

Некоторые файлы не были показаны из-за слишком большого количества измененных файлов Показать больше