Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(846)

Unified Diff: chrome/browser/cocoa/hover_close_button.mm

Issue 2805055: [Mac] Use Core Graphics to draw the close button used within tabs, infobars, ... (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: '' Created 10 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: chrome/browser/cocoa/hover_close_button.mm
===================================================================
--- chrome/browser/cocoa/hover_close_button.mm (revision 51260)
+++ chrome/browser/cocoa/hover_close_button.mm (working copy)
@@ -1,21 +1,31 @@
-// Copyright (c) 2009 The Chromium Authors. All rights reserved.
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#import "chrome/browser/cocoa/hover_close_button.h"
#include "app/l10n_util.h"
-#include "base/nsimage_cache_mac.h"
+#include "base/scoped_nsobject.h"
+#import "chrome/browser/cocoa/third_party/NSBezierPath+MCAdditions.h"
#include "grit/generated_resources.h"
namespace {
+// Convenience function to return the middle point of the given |rect|.
+static NSPoint MidRect(NSRect rect) {
+ return NSMakePoint(NSMidX(rect), NSMidY(rect));
+}
-NSString* const kNormalImageString = @"close_bar.pdf";
-NSString* const kHoverImageString = @"close_bar_h.pdf";
-NSString* const kPressedImageString = @"close_bar_p.pdf";
-
+const CGFloat kCircleRadiusPercentage = 0.45;
+const CGFloat kCircleHoverWhite = 0.565;
+const CGFloat kCircleClickWhite = 0.396;
+const CGFloat kXShadowAlpha = 0.6;
+const CGFloat kXShadowCircleAlpha = 0.1;
} // namespace
+@interface HoverCloseButton(Private)
+- (void)setUpDrawingPaths;
+@end
+
@implementation HoverCloseButton
- (id)initWithFrame:(NSRect)frameRect {
@@ -29,10 +39,39 @@
[self commonInit];
}
+- (void)drawRect:(NSRect)rect {
+ if (!circlePath_.get() || !xPath_.get())
+ [self setUpDrawingPaths];
+
+ // If the user is hovering over the button, a light/dark gray circle is drawn
+ // behind the 'x'.
+ if (hoverState_ != kHoverStateNone) {
+ // Adjust the darkness of the circle depending on whether it is being
+ // clicked.
+ CGFloat white = (hoverState_ == kHoverStateMouseOver) ?
+ kCircleHoverWhite : kCircleClickWhite;
+ [[NSColor colorWithCalibratedWhite:white alpha:1.0] set];
+ [circlePath_ fill];
+ }
+
+ [[NSColor whiteColor] set];
+ [xPath_ fill];
+
+ // Give the 'x' an inner shadow for depth. If the button is in a hover state
+ // (circle behind it), then adjust the shadow accordingly (not as harsh).
+ NSShadow* shadow = [[NSShadow alloc] init];
+ CGFloat alpha = (hoverState_ != kHoverStateNone) ?
+ kXShadowCircleAlpha : kXShadowAlpha;
+ [shadow setShadowColor:[NSColor colorWithCalibratedWhite:0.0
+ alpha:alpha]];
+ [shadow setShadowOffset:NSMakeSize(0.0, -1.0)];
+ [shadow setShadowBlurRadius:2.0];
+ [xPath_ fillWithInnerShadow:shadow];
+}
+
- (void)commonInit {
[self setTrackingEnabled:YES];
- NSImage* alternateImage = nsimage_cache::ImageNamed(kPressedImageString);
- [self setAlternateImage:alternateImage];
+ hoverState_ = kHoverStateNone;
[self updateTrackingAreas];
// Set accessibility description.
@@ -42,20 +81,51 @@
forAttribute:NSAccessibilityDescriptionAttribute];
}
+- (void)setUpDrawingPaths {
+ NSPoint viewCenter = MidRect([self bounds]);
+
+ circlePath_.reset([[NSBezierPath bezierPath] retain]);
+ [circlePath_ moveToPoint:viewCenter];
+ CGFloat radius = kCircleRadiusPercentage * NSWidth([self bounds]);
+ [circlePath_ appendBezierPathWithArcWithCenter:viewCenter
+ radius:radius
+ startAngle:0.0
+ endAngle:365.0];
+
+ // Construct an 'x' by drawing two intersecting rectangles in the shape of a
+ // cross and then rotating the path by 45 degrees.
+ xPath_.reset([[NSBezierPath bezierPath] retain]);
+ [xPath_ appendBezierPathWithRect:NSMakeRect(3.5, 7.0, 9.0, 2.0)];
+ [xPath_ appendBezierPathWithRect:NSMakeRect(7.0, 3.5, 2.0, 9.0)];
+
+ NSPoint pathCenter = MidRect([xPath_ bounds]);
+
+ NSAffineTransform* transform = [NSAffineTransform transform];
+ [transform translateXBy:viewCenter.x yBy:viewCenter.y];
+ [transform rotateByDegrees:45.0];
+ [transform translateXBy:-pathCenter.x yBy:-pathCenter.y];
+
+ [xPath_ transformUsingAffineTransform:transform];
+}
+
- (void)dealloc {
[self setTrackingEnabled:NO];
[super dealloc];
}
- (void)mouseEntered:(NSEvent*)theEvent {
- [self setImage:nsimage_cache::ImageNamed(kHoverImageString)];
+ hoverState_ = kHoverStateMouseOver;
+ [self setNeedsDisplay:YES];
}
- (void)mouseExited:(NSEvent*)theEvent {
- [self setImage:nsimage_cache::ImageNamed(kNormalImageString)];
+ hoverState_ = kHoverStateNone;
+ [self setNeedsDisplay:YES];
}
- (void)mouseDown:(NSEvent*)theEvent {
+ hoverState_ = kHoverStateMouseDown;
+ [self setNeedsDisplay:YES];
// The hover button needs to hold onto itself here for a bit. Otherwise,
// it can be freed while |super mouseDown:| is in it's loop, and the
// |checkImageState| call will crash.
@@ -100,18 +170,15 @@
}
- (void)checkImageState {
- if (closeTrackingArea_.get()) {
- // Update the close buttons if the tab has moved.
- NSPoint mouseLoc = [[self window] mouseLocationOutsideOfEventStream];
- mouseLoc = [self convertPoint:mouseLoc fromView:nil];
- NSString* name = NSPointInRect(mouseLoc, [self bounds]) ?
- kHoverImageString : kNormalImageString;
- NSImage* newImage = nsimage_cache::ImageNamed(name);
- NSImage* buttonImage = [self image];
- if (![buttonImage isEqual:newImage]) {
- [self setImage:newImage];
- }
- }
+ if (!closeTrackingArea_.get())
+ return;
+
+ // Update the close buttons if the tab has moved.
+ NSPoint mouseLoc = [[self window] mouseLocationOutsideOfEventStream];
+ mouseLoc = [self convertPoint:mouseLoc fromView:nil];
+ hoverState_ = NSPointInRect(mouseLoc, [self bounds]) ?
+ kHoverStateMouseOver : kHoverStateNone;
+ [self setNeedsDisplay:YES];
}
@end

Powered by Google App Engine
This is Rietveld 408576698