diff options
author | viettrungluu@chromium.org <viettrungluu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-01-22 21:51:21 +0000 |
---|---|---|
committer | viettrungluu@chromium.org <viettrungluu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-01-22 21:51:21 +0000 |
commit | caadfcaf9a3a2d1170519e891aadf8ef143274b4 (patch) | |
tree | e40efe4908cf40fe0995d619ab520de7a33d47da /chrome/browser/app_controller_mac.mm | |
parent | 23cdb20c37deb0fcdef3a0611951008a3988a32c (diff) | |
download | chromium_src-caadfcaf9a3a2d1170519e891aadf8ef143274b4.zip chromium_src-caadfcaf9a3a2d1170519e891aadf8ef143274b4.tar.gz chromium_src-caadfcaf9a3a2d1170519e891aadf8ef143274b4.tar.bz2 |
Mac: improve situation with respect to launching/DnD local files.
This is half the solution, but it should make some stuff work. This should make
double-clicking on local HTML files (when Chromium is set as default browser)
work more correctly, both when Chromium is already running and when it's not.
(The same, but easier to check: dragging a file or files to the Chromium
application icon.) You should no longer be told that Chromium can't open HTML
files. It's not the full solution since an extraneous (NTP/home page) tab -- or
worse -- will be created if Chromium is not already running; solving this will
require modifying browser startup.
BUG=14808
TEST=Drag a file to the Chromium application icon, both when it's already running and when it's not; file should open in a tab. Do the same, but select multiple files; selected files should open in tabs. Check the same for the Chromium Dock icon (when Chromium is already running). Note that if Chromium is not running, there will be an extraneous (NTP or home page) tab.
Review URL: http://codereview.chromium.org/552109
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@36902 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/app_controller_mac.mm')
-rw-r--r-- | chrome/browser/app_controller_mac.mm | 91 |
1 files changed, 34 insertions, 57 deletions
diff --git a/chrome/browser/app_controller_mac.mm b/chrome/browser/app_controller_mac.mm index 1ffa922..6317a79 100644 --- a/chrome/browser/app_controller_mac.mm +++ b/chrome/browser/app_controller_mac.mm @@ -46,6 +46,7 @@ #include "chrome/common/temp_scaffolding_stubs.h" #include "grit/chromium_strings.h" #include "grit/generated_resources.h" +#include "net/base/net_util.h" // 10.6 adds a public API for the Spotlight-backed search menu item in the Help // menu. Provide the declaration so it can be called below when building with @@ -53,18 +54,15 @@ #if !defined(MAC_OS_X_VERSION_10_6) || \ MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_6 @interface NSApplication (SnowLeopardSDKDeclarations) -- (void)setHelpMenu:(NSMenu *)helpMenu; +- (void)setHelpMenu:(NSMenu*)helpMenu; @end #endif @interface AppController(PRIVATE) - (void)initMenuState; - (void)openURLs:(const std::vector<GURL>&)urls; -- (void)openPendingURLs; - (void)getUrl:(NSAppleEventDescriptor*)event withReply:(NSAppleEventDescriptor*)reply; -- (void)openFiles:(NSAppleEventDescriptor*)event - withReply:(NSAppleEventDescriptor*)reply; - (void)windowLayeringDidChange:(NSNotification*)inNotification; - (BOOL)userWillWaitForInProgressDownloads:(int)downloadCount; - (BOOL)shouldQuitWithInProgressDownloads; @@ -81,12 +79,12 @@ static bool g_is_opening_new_window = false; @implementation AppController +@synthesize startupComplete = startupComplete_; + // This method is called very early in application startup (ie, before // the profile is loaded or any preferences have been registered). Defer any // user-data initialization until -applicationDidFinishLaunching:. - (void)awakeFromNib { - pendingURLs_.reset(new std::vector<GURL>()); - // We need to register the handlers early to catch events fired on launch. NSAppleEventManager* em = [NSAppleEventManager sharedAppleEventManager]; [em setEventHandler:self @@ -97,10 +95,6 @@ static bool g_is_opening_new_window = false; andSelector:@selector(getUrl:withReply:) forEventClass:'WWW!' // A particularly ancient AppleEvent that dates andEventID:'OURL']; // back to the Spyglass days. - [em setEventHandler:self - andSelector:@selector(openFiles:withReply:) - forEventClass:kCoreEventClass - andEventID:kAEOpenDocuments]; // Register for various window layering changes. We use these to update // various UI elements (command-key equivalents, etc) when the frontmost @@ -168,8 +162,6 @@ static bool g_is_opening_new_window = false; andEventID:kAEGetURL]; [em removeEventHandlerForEventClass:'WWW!' andEventID:'OURL']; - [em removeEventHandlerForEventClass:kCoreEventClass - andEventID:kAEOpenDocuments]; // Close all the windows. BrowserList::CloseAllBrowsers(true); @@ -356,12 +348,18 @@ static bool g_is_opening_new_window = false; // Since Chrome is localized to more languages than the OS, tell Cocoa which // menu is the Help so it can add the search item to it. - if (helpMenu_ && [NSApp respondsToSelector:@selector(setHelpMenu:)]) { + if (helpMenu_ && [NSApp respondsToSelector:@selector(setHelpMenu:)]) [NSApp setHelpMenu:helpMenu_]; - } - // Now that we're initialized we can open any URLs we've been holding onto. - [self openPendingURLs]; + startupComplete_ = YES; + + // TODO(viettrungluu): This is very temporary, since this should be done "in" + // |BrowserMain()|, i.e., this list of startup URLs should be appended to the + // (probably-empty) list of URLs from the command line. + if (startupURLs_.size()) { + [self openURLs:startupURLs_]; + [self clearStartupURLs]; + } } // This is called after profiles have been loaded and preferences registered. @@ -693,9 +691,9 @@ static bool g_is_opening_new_window = false; // openings through that for uniform handling. - (void)openURLs:(const std::vector<GURL>&)urls { - if (pendingURLs_.get()) { - // too early to open; save for later - pendingURLs_->insert(pendingURLs_->end(), urls.begin(), urls.end()); + // If the browser hasn't started yet, just queue up the URLs. + if (!startupComplete_) { + startupURLs_.insert(startupURLs_.end(), urls.begin(), urls.end()); return; } @@ -711,17 +709,6 @@ static bool g_is_opening_new_window = false; launch.OpenURLsInBrowser(browser, false, urls); } -- (void)openPendingURLs { - // Since the existence of pendingURLs_ is a flag that it's too early to - // open URLs, we need to reset pendingURLs_. - std::vector<GURL> urls; - swap(urls, *pendingURLs_); - pendingURLs_.reset(); - - if (urls.size()) - [self openURLs:urls]; -} - - (void)getUrl:(NSAppleEventDescriptor*)event withReply:(NSAppleEventDescriptor*)reply { NSString* urlStr = [[event paramDescriptorForKeyword:keyDirectObject] @@ -734,37 +721,19 @@ static bool g_is_opening_new_window = false; [self openURLs:gurlVector]; } -- (void)openFiles:(NSAppleEventDescriptor*)event - withReply:(NSAppleEventDescriptor*)reply { - // Ordinarily we'd use the NSApplication delegate method - // -application:openFiles:, but Cocoa tries to be smart and it sends files - // specified on the command line into that delegate method. That's too smart - // for us (our setup isn't done by the time Cocoa triggers the delegate method - // and we crash). Since all we want are files dropped on the app icon, and we - // have cross-platform code to handle the command-line files anyway, an Apple - // Event handler fits the bill just right. - NSAppleEventDescriptor* fileList = - [event paramDescriptorForKeyword:keyDirectObject]; - if (!fileList) - return; +- (void)application:(NSApplication*)sender + openFiles:(NSArray*)filenames { std::vector<GURL> gurlVector; - - for (NSInteger i = 1; i <= [fileList numberOfItems]; ++i) { - NSAppleEventDescriptor* fileAliasDesc = [fileList descriptorAtIndex:i]; - if (!fileAliasDesc) - continue; - NSAppleEventDescriptor* fileURLDesc = - [fileAliasDesc coerceToDescriptorType:typeFileURL]; - if (!fileURLDesc) - continue; - NSData* fileURLData = [fileURLDesc data]; - if (!fileURLData) - continue; - GURL gurl(std::string((char*)[fileURLData bytes], [fileURLData length])); + for (NSString* file in filenames) { + GURL gurl = net::FilePathToFileURL(FilePath(base::SysNSStringToUTF8(file))); gurlVector.push_back(gurl); } + if (!gurlVector.empty()) + [self openURLs:gurlVector]; + else + NOTREACHED() << "Nothing to open!"; - [self openURLs:gurlVector]; + [sender replyToOpenOrPrint:NSApplicationDelegateReplySuccess]; } // Called when the preferences window is closed. We use this to release the @@ -868,6 +837,14 @@ static bool g_is_opening_new_window = false; return dockMenu; } +- (const std::vector<GURL>&)startupURLs { + return startupURLs_; +} + +- (void)clearStartupURLs { + startupURLs_.clear(); +} + @end //--------------------------------------------------------------------------- |