| OLD | NEW |
| 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #import "chrome/browser/cocoa/preferences_window_controller.h" | 5 #import "chrome/browser/cocoa/preferences_window_controller.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #include "app/l10n_util.h" | 9 #include "app/l10n_util.h" |
| 10 #include "app/l10n_util_mac.h" | 10 #include "app/l10n_util_mac.h" |
| 11 #include "app/resource_bundle.h" |
| 11 #include "base/logging.h" | 12 #include "base/logging.h" |
| 12 #include "base/mac_util.h" | 13 #include "base/mac_util.h" |
| 13 #include "base/string16.h" | 14 #include "base/string16.h" |
| 14 #include "base/string_util.h" | 15 #include "base/string_util.h" |
| 15 #include "base/sys_string_conversions.h" | 16 #include "base/sys_string_conversions.h" |
| 16 #include "chrome/browser/autofill/autofill_dialog.h" | 17 #include "chrome/browser/autofill/autofill_dialog.h" |
| 17 #include "chrome/browser/autofill/autofill_type.h" | 18 #include "chrome/browser/autofill/autofill_type.h" |
| 18 #include "chrome/browser/autofill/personal_data_manager.h" | 19 #include "chrome/browser/autofill/personal_data_manager.h" |
| 19 #include "chrome/browser/browser.h" | 20 #include "chrome/browser/browser.h" |
| 20 #include "chrome/browser/browser_list.h" | 21 #include "chrome/browser/browser_list.h" |
| 21 #include "chrome/browser/browser_process.h" | 22 #include "chrome/browser/browser_process.h" |
| 22 #import "chrome/browser/cocoa/clear_browsing_data_controller.h" | 23 #import "chrome/browser/cocoa/clear_browsing_data_controller.h" |
| 23 #import "chrome/browser/cocoa/content_settings_dialog_controller.h" | 24 #import "chrome/browser/cocoa/content_settings_dialog_controller.h" |
| 24 #import "chrome/browser/cocoa/custom_home_pages_model.h" | 25 #import "chrome/browser/cocoa/custom_home_pages_model.h" |
| 25 #import "chrome/browser/cocoa/font_language_settings_controller.h" | 26 #import "chrome/browser/cocoa/font_language_settings_controller.h" |
| 26 #import "chrome/browser/cocoa/import_settings_dialog.h" | 27 #import "chrome/browser/cocoa/import_settings_dialog.h" |
| 27 #import "chrome/browser/cocoa/keyword_editor_cocoa_controller.h" | 28 #import "chrome/browser/cocoa/keyword_editor_cocoa_controller.h" |
| 28 #import "chrome/browser/cocoa/l10n_util.h" | 29 #import "chrome/browser/cocoa/l10n_util.h" |
| 29 #import "chrome/browser/cocoa/search_engine_list_model.h" | 30 #import "chrome/browser/cocoa/search_engine_list_model.h" |
| 30 #import "chrome/browser/cocoa/sync_customize_controller_cppsafe.h" | 31 #import "chrome/browser/cocoa/sync_customize_controller_cppsafe.h" |
| 32 #import "chrome/browser/cocoa/vertical_gradient_view.h" |
| 31 #import "chrome/browser/cocoa/window_size_autosaver.h" | 33 #import "chrome/browser/cocoa/window_size_autosaver.h" |
| 32 #include "chrome/browser/download/download_manager.h" | 34 #include "chrome/browser/download/download_manager.h" |
| 33 #include "chrome/browser/extensions/extensions_service.h" | 35 #include "chrome/browser/extensions/extensions_service.h" |
| 36 #include "chrome/browser/managed_prefs_banner_base.h" |
| 34 #include "chrome/browser/metrics/metrics_service.h" | 37 #include "chrome/browser/metrics/metrics_service.h" |
| 35 #include "chrome/browser/metrics/user_metrics.h" | 38 #include "chrome/browser/metrics/user_metrics.h" |
| 36 #include "chrome/browser/net/dns_global.h" | 39 #include "chrome/browser/net/dns_global.h" |
| 37 #include "chrome/browser/net/url_fixer_upper.h" | 40 #include "chrome/browser/net/url_fixer_upper.h" |
| 38 #include "chrome/browser/options_window.h" | 41 #include "chrome/browser/options_window.h" |
| 39 #include "chrome/browser/options_util.h" | 42 #include "chrome/browser/options_util.h" |
| 40 #include "chrome/browser/pref_service.h" | 43 #include "chrome/browser/pref_service.h" |
| 41 #include "chrome/browser/profile.h" | 44 #include "chrome/browser/profile.h" |
| 42 #include "chrome/browser/safe_browsing/safe_browsing_service.h" | 45 #include "chrome/browser/safe_browsing/safe_browsing_service.h" |
| 43 #include "chrome/browser/session_startup_pref.h" | 46 #include "chrome/browser/session_startup_pref.h" |
| 44 #include "chrome/browser/shell_integration.h" | 47 #include "chrome/browser/shell_integration.h" |
| 45 #include "chrome/browser/sync/profile_sync_service.h" | 48 #include "chrome/browser/sync/profile_sync_service.h" |
| 46 #include "chrome/browser/sync/sync_ui_util.h" | 49 #include "chrome/browser/sync/sync_ui_util.h" |
| 47 #include "chrome/browser/tab_contents/tab_contents.h" | 50 #include "chrome/browser/tab_contents/tab_contents.h" |
| 48 #include "chrome/common/notification_details.h" | 51 #include "chrome/common/notification_details.h" |
| 49 #include "chrome/common/notification_observer.h" | 52 #include "chrome/common/notification_observer.h" |
| 50 #include "chrome/common/notification_type.h" | 53 #include "chrome/common/notification_type.h" |
| 51 #include "chrome/common/pref_names.h" | 54 #include "chrome/common/pref_names.h" |
| 52 #include "chrome/common/url_constants.h" | 55 #include "chrome/common/url_constants.h" |
| 53 #include "chrome/installer/util/google_update_settings.h" | 56 #include "chrome/installer/util/google_update_settings.h" |
| 54 #include "grit/chromium_strings.h" | 57 #include "grit/chromium_strings.h" |
| 55 #include "grit/generated_resources.h" | 58 #include "grit/generated_resources.h" |
| 56 #include "grit/locale_settings.h" | 59 #include "grit/locale_settings.h" |
| 60 #include "grit/theme_resources.h" |
| 57 #import "third_party/GTM/AppKit/GTMUILocalizerAndLayoutTweaker.h" | 61 #import "third_party/GTM/AppKit/GTMUILocalizerAndLayoutTweaker.h" |
| 58 #import "third_party/GTM/AppKit/GTMNSAnimation+Duration.h" | 62 #import "third_party/GTM/AppKit/GTMNSAnimation+Duration.h" |
| 59 | 63 |
| 60 namespace { | 64 namespace { |
| 61 | 65 |
| 66 // Colors for the managed preferences warning banner. |
| 67 static const double kBannerGradientColorTop[3] = |
| 68 {255.0 / 255.0, 242.0 / 255.0, 183.0 / 255.0}; |
| 69 static const double kBannerGradientColorBottom[3] = |
| 70 {250.0 / 255.0, 230.0 / 255.0, 145.0 / 255.0}; |
| 71 static const double kBannerStrokeColor = 135.0 / 255.0; |
| 72 |
| 73 // Preferences relevant to the general page potentially constrained by policy. |
| 74 static const wchar_t* kGeneralPolicyConstrainedPrefs[] = { |
| 75 prefs::kHomePage, |
| 76 prefs::kHomePageIsNewTabPage |
| 77 }; |
| 78 |
| 62 std::string GetNewTabUIURLString() { | 79 std::string GetNewTabUIURLString() { |
| 63 return URLFixerUpper::FixupURL(chrome::kChromeUINewTabURL, | 80 return URLFixerUpper::FixupURL(chrome::kChromeUINewTabURL, |
| 64 std::string()).possibly_invalid_spec(); | 81 std::string()).possibly_invalid_spec(); |
| 65 } | 82 } |
| 66 | 83 |
| 67 // Helper to remove all but the last view from the view hierarchy. | |
| 68 void RemoveAllButLastView(NSArray* views) { | |
| 69 NSArray* toRemove = [views subarrayWithRange:NSMakeRange(0, [views count]-1)]; | |
| 70 for (NSView* view in toRemove) { | |
| 71 [view removeFromSuperviewWithoutNeedingDisplay]; | |
| 72 } | |
| 73 } | |
| 74 | |
| 75 // Helper that sizes two buttons to fit in a row keeping their spacing, returns | 84 // Helper that sizes two buttons to fit in a row keeping their spacing, returns |
| 76 // the total horizontal size change. | 85 // the total horizontal size change. |
| 77 CGFloat SizeToFitButtonPair(NSButton* leftButton, NSButton* rightButton) { | 86 CGFloat SizeToFitButtonPair(NSButton* leftButton, NSButton* rightButton) { |
| 78 CGFloat widthShift = 0.0; | 87 CGFloat widthShift = 0.0; |
| 79 | 88 |
| 80 NSSize delta = [GTMUILocalizerAndLayoutTweaker sizeToFitView:leftButton]; | 89 NSSize delta = [GTMUILocalizerAndLayoutTweaker sizeToFitView:leftButton]; |
| 81 DCHECK_EQ(delta.height, 0.0) << "Height changes unsupported"; | 90 DCHECK_EQ(delta.height, 0.0) << "Height changes unsupported"; |
| 82 widthShift += delta.width; | 91 widthShift += delta.width; |
| 83 | 92 |
| 84 if (widthShift != 0.0) { | 93 if (widthShift != 0.0) { |
| (...skipping 257 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 342 - (void)setUseSuggest:(BOOL)value; | 351 - (void)setUseSuggest:(BOOL)value; |
| 343 - (void)setDnsPrefetch:(BOOL)value; | 352 - (void)setDnsPrefetch:(BOOL)value; |
| 344 - (void)setSafeBrowsing:(BOOL)value; | 353 - (void)setSafeBrowsing:(BOOL)value; |
| 345 - (void)setMetricsRecording:(BOOL)value; | 354 - (void)setMetricsRecording:(BOOL)value; |
| 346 - (void)setAskForSaveLocation:(BOOL)value; | 355 - (void)setAskForSaveLocation:(BOOL)value; |
| 347 - (void)setFileHandlerUIEnabled:(BOOL)value; | 356 - (void)setFileHandlerUIEnabled:(BOOL)value; |
| 348 - (void)setTranslateEnabled:(BOOL)value; | 357 - (void)setTranslateEnabled:(BOOL)value; |
| 349 - (void)setTabsToLinks:(BOOL)value; | 358 - (void)setTabsToLinks:(BOOL)value; |
| 350 - (void)displayPreferenceViewForPage:(OptionsPage)page | 359 - (void)displayPreferenceViewForPage:(OptionsPage)page |
| 351 animate:(BOOL)animate; | 360 animate:(BOOL)animate; |
| 361 - (void)resetSubViews; |
| 362 - (void)initBannerStateForPage:(OptionsPage)page; |
| 352 | 363 |
| 353 // KVC getter methods. | 364 // KVC getter methods. |
| 354 - (BOOL)fileHandlerUIEnabled; | 365 - (BOOL)fileHandlerUIEnabled; |
| 355 @end | 366 @end |
| 356 | 367 |
| 357 namespace PreferencesWindowControllerInternal { | 368 namespace PreferencesWindowControllerInternal { |
| 358 | 369 |
| 359 // A C++ class registered for changes in preferences. Bridges the | 370 // A C++ class registered for changes in preferences. Bridges the |
| 360 // notification back to the PWC. | 371 // notification back to the PWC. |
| 361 class PrefObserverBridge : public NotificationObserver, | 372 class PrefObserverBridge : public NotificationObserver, |
| (...skipping 14 matching lines...) Expand all Loading... |
| 376 | 387 |
| 377 // Overridden from ProfileSyncServiceObserver. | 388 // Overridden from ProfileSyncServiceObserver. |
| 378 virtual void OnStateChanged() { | 389 virtual void OnStateChanged() { |
| 379 [controller_ syncStateChanged]; | 390 [controller_ syncStateChanged]; |
| 380 } | 391 } |
| 381 | 392 |
| 382 private: | 393 private: |
| 383 PreferencesWindowController* controller_; // weak, owns us | 394 PreferencesWindowController* controller_; // weak, owns us |
| 384 }; | 395 }; |
| 385 | 396 |
| 397 // Tracks state for a managed prefs banner and triggers UI updates through the |
| 398 // PreferencesWindowController as appropriate. |
| 399 class ManagedPrefsBannerState : public ManagedPrefsBannerBase { |
| 400 public: |
| 401 virtual ~ManagedPrefsBannerState() { } |
| 402 |
| 403 BOOL IsVisible() { |
| 404 return DetermineVisibility() ? YES : NO; |
| 405 } |
| 406 |
| 407 // Create a banner state tracker object suitable for use with a given |page|. |
| 408 static ManagedPrefsBannerState* CreateForPage( |
| 409 PreferencesWindowController* controller, |
| 410 OptionsPage page, |
| 411 PrefService* prefs) { |
| 412 switch (page) { |
| 413 case OPTIONS_PAGE_GENERAL: |
| 414 return new ManagedPrefsBannerState(controller, page, prefs, |
| 415 kGeneralPolicyConstrainedPrefs, |
| 416 arraysize(kGeneralPolicyConstrainedPrefs)); |
| 417 case OPTIONS_PAGE_CONTENT: |
| 418 break; |
| 419 case OPTIONS_PAGE_ADVANCED: |
| 420 break; |
| 421 case OPTIONS_PAGE_DEFAULT: |
| 422 case OPTIONS_PAGE_COUNT: |
| 423 LOG(DFATAL) << "Invalid page value " << page; |
| 424 break; |
| 425 } |
| 426 return new ManagedPrefsBannerState(controller, page, prefs, NULL, 0); |
| 427 } |
| 428 |
| 429 protected: |
| 430 // Overridden from ManagedPrefsBannerBase. |
| 431 virtual void OnUpdateVisibility() { |
| 432 [controller_ switchToPage:page_ animate:YES]; |
| 433 } |
| 434 |
| 435 private: |
| 436 explicit ManagedPrefsBannerState(PreferencesWindowController* controller, |
| 437 OptionsPage page, |
| 438 PrefService* prefs, |
| 439 const wchar_t** relevant_prefs, |
| 440 size_t count) |
| 441 : ManagedPrefsBannerBase(prefs, relevant_prefs, count), |
| 442 controller_(controller), |
| 443 page_(page) { } |
| 444 |
| 445 PreferencesWindowController* controller_; // weak, owns us |
| 446 OptionsPage page_; // current options page |
| 447 }; |
| 448 |
| 386 } // namespace PreferencesWindowControllerInternal | 449 } // namespace PreferencesWindowControllerInternal |
| 387 | 450 |
| 388 @implementation PreferencesWindowController | 451 @implementation PreferencesWindowController |
| 389 | 452 |
| 390 - (id)initWithProfile:(Profile*)profile initialPage:(OptionsPage)initialPage { | 453 - (id)initWithProfile:(Profile*)profile initialPage:(OptionsPage)initialPage { |
| 391 DCHECK(profile); | 454 DCHECK(profile); |
| 392 // Use initWithWindowNibPath:: instead of initWithWindowNibName: so we | 455 // Use initWithWindowNibPath:: instead of initWithWindowNibName: so we |
| 393 // can override it in a unit test. | 456 // can override it in a unit test. |
| 394 NSString* nibPath = [mac_util::MainAppBundle() | 457 NSString* nibPath = [mac_util::MainAppBundle() |
| 395 pathForResource:@"Preferences" | 458 pathForResource:@"Preferences" |
| (...skipping 248 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 644 resizeViewWithoutAutoResizingSubViews:underTheHoodContentView_ | 707 resizeViewWithoutAutoResizingSubViews:underTheHoodContentView_ |
| 645 delta:NSMakeSize(0.0, verticalShift)]; | 708 delta:NSMakeSize(0.0, verticalShift)]; |
| 646 underTheHoodContentSize = [underTheHoodContentView_ frame].size; | 709 underTheHoodContentSize = [underTheHoodContentView_ frame].size; |
| 647 | 710 |
| 648 // Put the Under the Hood content view into the scroller and scroll it to the | 711 // Put the Under the Hood content view into the scroller and scroll it to the |
| 649 // top. | 712 // top. |
| 650 [underTheHoodScroller_ setDocumentView:underTheHoodContentView_]; | 713 [underTheHoodScroller_ setDocumentView:underTheHoodContentView_]; |
| 651 [underTheHoodContentView_ scrollPoint: | 714 [underTheHoodContentView_ scrollPoint: |
| 652 NSMakePoint(0, underTheHoodContentSize.height)]; | 715 NSMakePoint(0, underTheHoodContentSize.height)]; |
| 653 | 716 |
| 717 ResourceBundle& rb = ResourceBundle::GetSharedInstance(); |
| 718 NSImage* alertIcon = rb.GetNSImageNamed(IDR_WARNING); |
| 719 DCHECK(alertIcon); |
| 720 [managedPrefsBannerWarningImage_ setImage:alertIcon]; |
| 721 |
| 722 [self initBannerStateForPage:initialPage_]; |
| 654 [self switchToPage:initialPage_ animate:NO]; | 723 [self switchToPage:initialPage_ animate:NO]; |
| 655 | 724 |
| 656 // Save/restore position based on prefs. | 725 // Save/restore position based on prefs. |
| 657 if (g_browser_process && g_browser_process->local_state()) { | 726 if (g_browser_process && g_browser_process->local_state()) { |
| 658 sizeSaver_.reset([[WindowSizeAutosaver alloc] | 727 sizeSaver_.reset([[WindowSizeAutosaver alloc] |
| 659 initWithWindow:[self window] | 728 initWithWindow:[self window] |
| 660 prefService:g_browser_process->local_state() | 729 prefService:g_browser_process->local_state() |
| 661 path:prefs::kPreferencesWindowPlacement | 730 path:prefs::kPreferencesWindowPlacement |
| 662 state:kSaveWindowRect]); | 731 state:kSaveWindowRect]); |
| 663 } | 732 } |
| 733 |
| 734 // Initialize the banner gradient and stroke color. |
| 735 NSColor* bannerStartingColor = |
| 736 [NSColor colorWithCalibratedRed:kBannerGradientColorTop[0] |
| 737 green:kBannerGradientColorTop[1] |
| 738 blue:kBannerGradientColorTop[2] |
| 739 alpha:1.0]; |
| 740 NSColor* bannerEndingColor = |
| 741 [NSColor colorWithCalibratedRed:kBannerGradientColorBottom[0] |
| 742 green:kBannerGradientColorBottom[1] |
| 743 blue:kBannerGradientColorBottom[2] |
| 744 alpha:1.0]; |
| 745 scoped_nsobject<NSGradient> bannerGradient( |
| 746 [[NSGradient alloc] initWithStartingColor:bannerStartingColor |
| 747 endingColor:bannerEndingColor]); |
| 748 [managedPrefsBannerView_ setGradient:bannerGradient]; |
| 749 |
| 750 NSColor* bannerStrokeColor = |
| 751 [NSColor colorWithCalibratedWhite:kBannerStrokeColor |
| 752 alpha:1.0]; |
| 753 [managedPrefsBannerView_ setStrokeColor:bannerStrokeColor]; |
| 664 } | 754 } |
| 665 | 755 |
| 666 - (void)dealloc { | 756 - (void)dealloc { |
| 667 if (syncService_) { | 757 if (syncService_) { |
| 668 syncService_->RemoveObserver(observer_.get()); | 758 syncService_->RemoveObserver(observer_.get()); |
| 669 } | 759 } |
| 670 [customPagesSource_ removeObserver:self forKeyPath:@"customHomePages"]; | 760 [customPagesSource_ removeObserver:self forKeyPath:@"customHomePages"]; |
| 671 [[NSNotificationCenter defaultCenter] removeObserver:self]; | 761 [[NSNotificationCenter defaultCenter] removeObserver:self]; |
| 672 [self unregisterPrefObservers]; | 762 [self unregisterPrefObservers]; |
| 673 [animation_ setDelegate:nil]; | 763 [animation_ setDelegate:nil]; |
| (...skipping 1071 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1745 // Helper to update the window to display a preferences view for a page. | 1835 // Helper to update the window to display a preferences view for a page. |
| 1746 - (void)displayPreferenceViewForPage:(OptionsPage)page | 1836 - (void)displayPreferenceViewForPage:(OptionsPage)page |
| 1747 animate:(BOOL)animate { | 1837 animate:(BOOL)animate { |
| 1748 NSWindow* prefsWindow = [self window]; | 1838 NSWindow* prefsWindow = [self window]; |
| 1749 | 1839 |
| 1750 // Needs to go *after* the call to [self window], which triggers | 1840 // Needs to go *after* the call to [self window], which triggers |
| 1751 // awakeFromNib if necessary. | 1841 // awakeFromNib if necessary. |
| 1752 NSView* prefsView = [self getPrefsViewForPage:page]; | 1842 NSView* prefsView = [self getPrefsViewForPage:page]; |
| 1753 NSView* contentView = [prefsWindow contentView]; | 1843 NSView* contentView = [prefsWindow contentView]; |
| 1754 | 1844 |
| 1755 // Normally there is only one view, but if the user clicks really quickly, the | |
| 1756 // animation could still been running, and the last view is the one that was | |
| 1757 // animating in. | |
| 1758 NSArray* subviews = [contentView subviews]; | |
| 1759 NSView* currentPrefsView = nil; | |
| 1760 if ([subviews count]) { | |
| 1761 currentPrefsView = [subviews lastObject]; | |
| 1762 } | |
| 1763 | |
| 1764 // Make sure we aren't being told to display the same thing again. | 1845 // Make sure we aren't being told to display the same thing again. |
| 1765 if (currentPrefsView == prefsView) { | 1846 if (currentPrefsView_ == prefsView && |
| 1847 managedPrefsBannerVisible_ == bannerState_->IsVisible()) { |
| 1766 return; | 1848 return; |
| 1767 } | 1849 } |
| 1768 | 1850 |
| 1769 // Remember new options page as current page. | 1851 // Remember new options page as current page. |
| 1770 if (page != OPTIONS_PAGE_DEFAULT) | 1852 if (page != OPTIONS_PAGE_DEFAULT) |
| 1771 lastSelectedPage_.SetValue(page); | 1853 lastSelectedPage_.SetValue(page); |
| 1772 | 1854 |
| 1773 // Stop any running animation, and remove any past views that were on the way | 1855 // Stop any running animation, and reset the subviews to the new state. We |
| 1774 // out. | 1856 // re-add any views we need for animation later. |
| 1775 [animation_ stopAnimation]; | 1857 [animation_ stopAnimation]; |
| 1776 if ([subviews count]) { | 1858 NSView* oldPrefsView = currentPrefsView_; |
| 1777 RemoveAllButLastView(subviews); | 1859 currentPrefsView_ = prefsView; |
| 1778 } | 1860 [self resetSubViews]; |
| 1779 | 1861 |
| 1862 // Update the banner state. |
| 1863 [self initBannerStateForPage:page]; |
| 1864 BOOL showBanner = bannerState_->IsVisible(); |
| 1865 |
| 1866 // Update the window title. |
| 1867 NSToolbarItem* toolbarItem = [self getToolbarItemForPage:page]; |
| 1868 [prefsWindow setTitle:[toolbarItem label]]; |
| 1869 |
| 1870 // Calculate new frames for the subviews. |
| 1780 NSRect prefsViewFrame = [prefsView frame]; | 1871 NSRect prefsViewFrame = [prefsView frame]; |
| 1781 NSRect contentViewFrame = [contentView frame]; | 1872 NSRect contentViewFrame = [contentView frame]; |
| 1873 NSRect bannerViewFrame = [managedPrefsBannerView_ frame]; |
| 1874 |
| 1875 // Determine what height the managed prefs banner will use. |
| 1876 CGFloat bannerViewHeight = showBanner ? NSHeight(bannerViewFrame) : 0.0; |
| 1877 |
| 1782 if (animate) { | 1878 if (animate) { |
| 1783 // NSViewAnimation doesn't seem to honor subview resizing as it animates the | 1879 // NSViewAnimation doesn't seem to honor subview resizing as it animates the |
| 1784 // Window's frame. So instead of trying to get the top in the right place, | 1880 // Window's frame. So instead of trying to get the top in the right place, |
| 1785 // just set the origin where it should be at the end, and let the fade/size | 1881 // just set the origin where it should be at the end, and let the fade/size |
| 1786 // slide things into the right spot. | 1882 // slide things into the right spot. |
| 1787 prefsViewFrame.origin.y = 0.0; | 1883 prefsViewFrame.origin.y = 0.0; |
| 1788 } else { | 1884 } else { |
| 1789 // The prefView is anchored to the top of its parent, so set its origin so | 1885 // The prefView is anchored to the top of its parent, so set its origin so |
| 1790 // that the top is where it should be. When the window's frame is set, the | 1886 // that the top is where it should be. When the window's frame is set, the |
| 1791 // origin will be adjusted to keep it in the right spot. | 1887 // origin will be adjusted to keep it in the right spot. |
| 1792 prefsViewFrame.origin.y = | 1888 prefsViewFrame.origin.y = NSHeight(contentViewFrame) - |
| 1793 NSHeight(contentViewFrame) - NSHeight(prefsViewFrame); | 1889 NSHeight(prefsViewFrame) - bannerViewHeight; |
| 1794 } | 1890 } |
| 1891 bannerViewFrame.origin.y = NSHeight(prefsViewFrame); |
| 1892 bannerViewFrame.size.width = NSWidth(contentViewFrame); |
| 1795 [prefsView setFrame:prefsViewFrame]; | 1893 [prefsView setFrame:prefsViewFrame]; |
| 1796 | 1894 |
| 1797 // Add the view. | |
| 1798 [contentView addSubview:prefsView]; | |
| 1799 [prefsWindow setInitialFirstResponder:prefsView]; | |
| 1800 | |
| 1801 // Update the window title. | |
| 1802 NSToolbarItem* toolbarItem = [self getToolbarItemForPage:page]; | |
| 1803 [prefsWindow setTitle:[toolbarItem label]]; | |
| 1804 | |
| 1805 // Figure out the size of the window. | 1895 // Figure out the size of the window. |
| 1806 NSRect windowFrame = [contentView convertRect:[prefsWindow frame] | 1896 NSRect windowFrame = [contentView convertRect:[prefsWindow frame] |
| 1807 fromView:nil]; | 1897 fromView:nil]; |
| 1808 CGFloat titleToolbarHeight = | 1898 CGFloat titleToolbarHeight = |
| 1809 NSHeight(windowFrame) - NSHeight(contentViewFrame); | 1899 NSHeight(windowFrame) - NSHeight(contentViewFrame); |
| 1810 windowFrame.size.height = | 1900 windowFrame.size.height = |
| 1811 NSHeight(prefsViewFrame) + titleToolbarHeight; | 1901 NSHeight(prefsViewFrame) + titleToolbarHeight + bannerViewHeight; |
| 1812 DCHECK_GE(NSWidth(windowFrame), NSWidth(prefsViewFrame)) | 1902 DCHECK_GE(NSWidth(windowFrame), NSWidth(prefsViewFrame)) |
| 1813 << "Initial width set wasn't wide enough."; | 1903 << "Initial width set wasn't wide enough."; |
| 1814 windowFrame = [contentView convertRect:windowFrame toView:nil]; | 1904 windowFrame = [contentView convertRect:windowFrame toView:nil]; |
| 1815 windowFrame.origin.y = NSMaxY([prefsWindow frame]) - NSHeight(windowFrame); | 1905 windowFrame.origin.y = NSMaxY([prefsWindow frame]) - NSHeight(windowFrame); |
| 1816 | 1906 |
| 1817 // Now change the size. | 1907 // Now change the size. |
| 1818 if (animate) { | 1908 if (animate) { |
| 1819 NSDictionary* oldViewOut = | 1909 NSMutableArray* animations = [NSMutableArray arrayWithCapacity:4]; |
| 1910 if (oldPrefsView != prefsView) { |
| 1911 // Fade between prefs views if they change. |
| 1912 [contentView addSubview:oldPrefsView |
| 1913 positioned:NSWindowBelow |
| 1914 relativeTo:nil]; |
| 1915 [animations addObject: |
| 1916 [NSDictionary dictionaryWithObjectsAndKeys: |
| 1917 oldPrefsView, NSViewAnimationTargetKey, |
| 1918 NSViewAnimationFadeOutEffect, NSViewAnimationEffectKey, |
| 1919 nil]]; |
| 1920 [animations addObject: |
| 1921 [NSDictionary dictionaryWithObjectsAndKeys: |
| 1922 prefsView, NSViewAnimationTargetKey, |
| 1923 NSViewAnimationFadeInEffect, NSViewAnimationEffectKey, |
| 1924 nil]]; |
| 1925 } else { |
| 1926 // Make sure the prefs pane ends up in the right position in case we |
| 1927 // manipulate the banner. |
| 1928 [animations addObject: |
| 1929 [NSDictionary dictionaryWithObjectsAndKeys: |
| 1930 prefsView, NSViewAnimationTargetKey, |
| 1931 [NSValue valueWithRect:prefsViewFrame], |
| 1932 NSViewAnimationEndFrameKey, |
| 1933 nil]]; |
| 1934 } |
| 1935 if (showBanner != managedPrefsBannerVisible_) { |
| 1936 // Slide the warning banner in or out of view. |
| 1937 [animations addObject: |
| 1938 [NSDictionary dictionaryWithObjectsAndKeys: |
| 1939 managedPrefsBannerView_, NSViewAnimationTargetKey, |
| 1940 [NSValue valueWithRect:bannerViewFrame], |
| 1941 NSViewAnimationEndFrameKey, |
| 1942 nil]]; |
| 1943 } |
| 1944 // Window resize animation. |
| 1945 [animations addObject: |
| 1820 [NSDictionary dictionaryWithObjectsAndKeys: | 1946 [NSDictionary dictionaryWithObjectsAndKeys: |
| 1821 currentPrefsView, NSViewAnimationTargetKey, | 1947 prefsWindow, NSViewAnimationTargetKey, |
| 1822 NSViewAnimationFadeOutEffect, NSViewAnimationEffectKey, | 1948 [NSValue valueWithRect:windowFrame], NSViewAnimationEndFrameKey, |
| 1823 nil]; | 1949 nil]]; |
| 1824 NSDictionary* newViewIn = | 1950 [animation_ setViewAnimations:animations]; |
| 1825 [NSDictionary dictionaryWithObjectsAndKeys: | |
| 1826 prefsView, NSViewAnimationTargetKey, | |
| 1827 NSViewAnimationFadeInEffect, NSViewAnimationEffectKey, | |
| 1828 nil]; | |
| 1829 NSDictionary* windowResize = | |
| 1830 [NSDictionary dictionaryWithObjectsAndKeys: | |
| 1831 prefsWindow, NSViewAnimationTargetKey, | |
| 1832 [NSValue valueWithRect:windowFrame], NSViewAnimationEndFrameKey, | |
| 1833 nil]; | |
| 1834 [animation_ setViewAnimations: | |
| 1835 [NSArray arrayWithObjects:oldViewOut, newViewIn, windowResize, nil]]; | |
| 1836 // The default duration is 0.5s, which actually feels slow in here, so speed | 1951 // The default duration is 0.5s, which actually feels slow in here, so speed |
| 1837 // it up a bit. | 1952 // it up a bit. |
| 1838 [animation_ gtm_setDuration:0.2 | 1953 [animation_ gtm_setDuration:0.2 |
| 1839 eventMask:NSLeftMouseUpMask]; | 1954 eventMask:NSLeftMouseUpMask]; |
| 1840 [animation_ startAnimation]; | 1955 [animation_ startAnimation]; |
| 1841 } else { | 1956 } else { |
| 1842 [currentPrefsView removeFromSuperviewWithoutNeedingDisplay]; | |
| 1843 // If not animating, odds are we don't want to display either (because it | 1957 // If not animating, odds are we don't want to display either (because it |
| 1844 // is initial window setup). | 1958 // is initial window setup). |
| 1845 [prefsWindow setFrame:windowFrame display:NO]; | 1959 [prefsWindow setFrame:windowFrame display:NO]; |
| 1960 [managedPrefsBannerView_ setFrame:bannerViewFrame]; |
| 1846 } | 1961 } |
| 1962 |
| 1963 managedPrefsBannerVisible_ = showBanner; |
| 1964 } |
| 1965 |
| 1966 - (void)resetSubViews { |
| 1967 // Reset subviews to current prefs view and banner, remove any views that |
| 1968 // might have been left over from previous state or animation. |
| 1969 NSArray* subviews = [NSArray arrayWithObjects: |
| 1970 currentPrefsView_, managedPrefsBannerView_, nil]; |
| 1971 [[[self window] contentView] setSubviews:subviews]; |
| 1972 [[self window] setInitialFirstResponder:currentPrefsView_]; |
| 1847 } | 1973 } |
| 1848 | 1974 |
| 1849 - (void)animationDidEnd:(NSAnimation*)animation { | 1975 - (void)animationDidEnd:(NSAnimation*)animation { |
| 1850 DCHECK_EQ(animation_.get(), animation); | 1976 DCHECK_EQ(animation_.get(), animation); |
| 1851 // Animation finished, remove everything but the view we just added (it will | 1977 // Animation finished, reset subviews to current prefs view and the banner. |
| 1852 // be last in the list). | 1978 [self resetSubViews]; |
| 1853 NSArray* subviews = [[[self window] contentView] subviews]; | 1979 } |
| 1854 RemoveAllButLastView(subviews); | 1980 |
| 1981 // Reinitializes the banner state tracker object to watch for managed bits of |
| 1982 // preferences relevant to the given options |page|. |
| 1983 - (void)initBannerStateForPage:(OptionsPage)page { |
| 1984 page = [self normalizePage:page]; |
| 1985 bannerState_.reset( |
| 1986 PreferencesWindowControllerInternal::ManagedPrefsBannerState:: |
| 1987 CreateForPage(self, page, prefs_)); |
| 1855 } | 1988 } |
| 1856 | 1989 |
| 1857 - (void)switchToPage:(OptionsPage)page animate:(BOOL)animate { | 1990 - (void)switchToPage:(OptionsPage)page animate:(BOOL)animate { |
| 1858 [self displayPreferenceViewForPage:page animate:animate]; | 1991 [self displayPreferenceViewForPage:page animate:animate]; |
| 1859 NSToolbarItem* toolbarItem = [self getToolbarItemForPage:page]; | 1992 NSToolbarItem* toolbarItem = [self getToolbarItemForPage:page]; |
| 1860 [toolbar_ setSelectedItemIdentifier:[toolbarItem itemIdentifier]]; | 1993 [toolbar_ setSelectedItemIdentifier:[toolbarItem itemIdentifier]]; |
| 1861 } | 1994 } |
| 1862 | 1995 |
| 1863 // Called when the window is being closed. Send out a notification that the user | 1996 // Called when the window is being closed. Send out a notification that the user |
| 1864 // is done editing preferences. Make sure there are no pending field editors | 1997 // is done editing preferences. Make sure there are no pending field editors |
| (...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1955 case OPTIONS_PAGE_ADVANCED: | 2088 case OPTIONS_PAGE_ADVANCED: |
| 1956 return underTheHoodView_; | 2089 return underTheHoodView_; |
| 1957 case OPTIONS_PAGE_DEFAULT: | 2090 case OPTIONS_PAGE_DEFAULT: |
| 1958 case OPTIONS_PAGE_COUNT: | 2091 case OPTIONS_PAGE_COUNT: |
| 1959 LOG(DFATAL) << "Invalid page value " << page; | 2092 LOG(DFATAL) << "Invalid page value " << page; |
| 1960 } | 2093 } |
| 1961 return basicsView_; | 2094 return basicsView_; |
| 1962 } | 2095 } |
| 1963 | 2096 |
| 1964 @end | 2097 @end |
| OLD | NEW |