Home | History | Annotate | Download | only in cocoa
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "chrome/browser/ui/cocoa/background_gradient_view.h"
      6 
      7 #import "chrome/browser/themes/theme_properties.h"
      8 #import "chrome/browser/themes/theme_service.h"
      9 #import "chrome/browser/ui/cocoa/nsview_additions.h"
     10 #import "chrome/browser/ui/cocoa/themed_window.h"
     11 #include "grit/theme_resources.h"
     12 
     13 @interface BackgroundGradientView (Private)
     14 - (void)commonInit;
     15 - (NSColor*)backgroundImageColor;
     16 @end
     17 
     18 @implementation BackgroundGradientView
     19 
     20 @synthesize showsDivider = showsDivider_;
     21 
     22 - (id)initWithFrame:(NSRect)frameRect {
     23   if ((self = [super initWithFrame:frameRect])) {
     24     [self commonInit];
     25   }
     26   return self;
     27 }
     28 
     29 - (id)initWithCoder:(NSCoder*)decoder {
     30   if ((self = [super initWithCoder:decoder])) {
     31     [self commonInit];
     32   }
     33   return self;
     34 }
     35 
     36 - (void)dealloc {
     37   [[NSNotificationCenter defaultCenter] removeObserver:self];
     38   [super dealloc];
     39 }
     40 
     41 - (void)commonInit {
     42   showsDivider_ = YES;
     43   [[NSNotificationCenter defaultCenter]
     44       addObserver:self
     45          selector:@selector(windowFocusDidChange:)
     46              name:NSApplicationWillBecomeActiveNotification
     47            object:NSApp];
     48   [[NSNotificationCenter defaultCenter]
     49       addObserver:self
     50          selector:@selector(windowFocusDidChange:)
     51              name:NSApplicationWillResignActiveNotification
     52            object:NSApp];
     53 }
     54 
     55 - (void)setShowsDivider:(BOOL)show {
     56   if (showsDivider_ == show)
     57     return;
     58   showsDivider_ = show;
     59   [self setNeedsDisplay:YES];
     60 }
     61 
     62 - (void)drawBackgroundWithOpaque:(BOOL)opaque {
     63   const NSRect bounds = [self bounds];
     64 
     65   if (opaque) {
     66     // If the background image is semi transparent then we need something
     67     // to blend against. Using 20% black gives us a color similar to Windows.
     68     [[NSColor colorWithCalibratedWhite:0.2 alpha:1.0] set];
     69     NSRectFill(bounds);
     70   }
     71 
     72   [[self backgroundImageColor] set];
     73   NSRectFillUsingOperation(bounds, NSCompositeSourceOver);
     74 
     75   if (showsDivider_) {
     76     // Draw bottom stroke
     77     [[self strokeColor] set];
     78     NSRect borderRect, contentRect;
     79     NSDivideRect(bounds, &borderRect, &contentRect, [self cr_lineWidth],
     80                  NSMinYEdge);
     81     NSRectFillUsingOperation(borderRect, NSCompositeSourceOver);
     82   }
     83 }
     84 
     85 - (NSColor*)strokeColor {
     86   NSWindow* window = [self window];
     87   if ([window parentWindow])
     88     window = [window parentWindow];
     89 
     90   BOOL isActive = [window isMainWindow];
     91   ui::ThemeProvider* themeProvider = [window themeProvider];
     92   if (!themeProvider)
     93     return [NSColor blackColor];
     94   return themeProvider->GetNSColor(
     95       isActive ? ThemeProperties::COLOR_TOOLBAR_STROKE :
     96                  ThemeProperties::COLOR_TOOLBAR_STROKE_INACTIVE);
     97 }
     98 
     99 - (NSColor*)backgroundImageColor {
    100   ThemeService* themeProvider =
    101       static_cast<ThemeService*>([[self window] themeProvider]);
    102   if (!themeProvider)
    103     return [[self window] backgroundColor];
    104 
    105   // Themes don't have an inactive image so only look for one if there's no
    106   // theme.
    107   if (![[self window] isMainWindow] && themeProvider->UsingDefaultTheme()) {
    108     NSColor* color = themeProvider->GetNSImageColorNamed(
    109         IDR_THEME_TOOLBAR_INACTIVE);
    110     if (color)
    111       return color;
    112   }
    113 
    114   return themeProvider->GetNSImageColorNamed(IDR_THEME_TOOLBAR);
    115 }
    116 
    117 - (void)windowFocusDidChange:(NSNotification*)notification {
    118   // The background color depends on the window's focus state.
    119   [self cr_recursivelySetNeedsDisplay:YES];
    120 }
    121 
    122 - (void)viewWillMoveToWindow:(NSWindow*)window {
    123   if ([self window]) {
    124     [[NSNotificationCenter defaultCenter]
    125         removeObserver:self
    126                   name:NSWindowDidBecomeKeyNotification
    127                 object:[self window]];
    128     [[NSNotificationCenter defaultCenter]
    129         removeObserver:self
    130                   name:NSWindowDidBecomeMainNotification
    131                 object:[self window]];
    132   }
    133   if (window) {
    134     [[NSNotificationCenter defaultCenter]
    135         addObserver:self
    136            selector:@selector(windowFocusDidChange:)
    137                name:NSWindowDidBecomeKeyNotification
    138              object:[self window]];
    139     [[NSNotificationCenter defaultCenter]
    140         addObserver:self
    141            selector:@selector(windowFocusDidChange:)
    142                name:NSWindowDidBecomeMainNotification
    143              object:[self window]];
    144   }
    145   [super viewWillMoveToWindow:window];
    146 }
    147 
    148 - (void)setFrameOrigin:(NSPoint)origin {
    149   // The background color depends on the view's vertical position.
    150   if (NSMinY([self frame]) != origin.y)
    151     [self setNeedsDisplay:YES];
    152 
    153   [super setFrameOrigin:origin];
    154 }
    155 
    156 @end
    157