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
3 // found in the LICENSE file.
7 #import "chrome/browser/ui/cocoa/location_bar/bubble_decoration.h"
9 #include "base/logging.h"
13 // This is used to increase the right margin of this decoration.
14 const CGFloat kRightSideMargin = 1.0;
16 // Padding between the icon/label and bubble edges.
17 const CGFloat kBubblePadding = 3.0;
19 // Padding between the icon and label.
20 const CGFloat kIconLabelPadding = 4.0;
22 // Inset for the background.
23 const CGFloat kBackgroundYInset = 4.0;
27 BubbleDecoration::BubbleDecoration() {
28 attributes_.reset([[NSMutableDictionary alloc] init]);
29 [attributes_ setObject:GetFont() forKey:NSFontAttributeName];
32 BubbleDecoration::~BubbleDecoration() {
35 CGFloat BubbleDecoration::GetWidthForImageAndLabel(NSImage* image,
40 const CGFloat image_width = image ? [image size].width : 0.0;
42 return kBubblePadding + image_width;
44 // The bubble needs to take up an integral number of pixels.
45 // Generally -sizeWithAttributes: seems to overestimate rather than
46 // underestimate, so floor() seems to work better.
47 const CGFloat label_width =
48 std::floor([label sizeWithAttributes:attributes_].width);
49 return kBubblePadding + image_width + kIconLabelPadding + label_width;
52 NSRect BubbleDecoration::GetImageRectInFrame(NSRect frame) {
53 NSRect imageRect = NSInsetRect(frame, 0.0, kBackgroundYInset);
55 // Center the image vertically.
56 const NSSize imageSize = [image_ size];
58 std::floor((NSHeight(frame) - imageSize.height) / 2.0);
59 imageRect.size = imageSize;
64 CGFloat BubbleDecoration::GetWidthForSpace(CGFloat width) {
65 const CGFloat all_width = GetWidthForImageAndLabel(image_, label_);
66 if (all_width <= width)
69 const CGFloat image_width = GetWidthForImageAndLabel(image_, nil);
70 if (image_width <= width)
76 void BubbleDecoration::DrawInFrame(NSRect frame, NSView* control_view) {
77 const NSRect decoration_frame = NSInsetRect(frame, 0.0, kBackgroundYInset);
78 CGFloat textOffset = NSMinX(decoration_frame);
80 // Center the image vertically.
81 const NSSize imageSize = [image_ size];
82 NSRect imageRect = decoration_frame;
84 std::floor((NSHeight(decoration_frame) - imageSize.height) / 2.0);
85 imageRect.size = imageSize;
86 [image_ drawInRect:imageRect
87 fromRect:NSZeroRect // Entire image
88 operation:NSCompositeSourceOver
92 textOffset = NSMaxX(imageRect) + kIconLabelPadding;
96 NSRect textRect = frame;
97 textRect.origin.x = textOffset;
98 textRect.size.width = NSMaxX(decoration_frame) - NSMinX(textRect);
99 DrawLabel(label_, attributes_, textRect);
103 void BubbleDecoration::DrawWithBackgroundInFrame(NSRect background_frame,
105 NSView* control_view) {
106 NSRect rect = NSInsetRect(background_frame, 0, 1);
107 rect.size.width -= kRightSideMargin;
108 ui::DrawNinePartImage(
109 rect, GetBubbleImageIds(), NSCompositeSourceOver, 1.0, true);
111 DrawInFrame(frame, control_view);
114 NSImage* BubbleDecoration::GetImage() {
118 void BubbleDecoration::SetImage(NSImage* image) {
119 image_.reset([image retain]);
122 void BubbleDecoration::SetLabel(NSString* label) {
123 // If the initializer was called with |nil|, then the code cannot
127 label_.reset([label copy]);
130 void BubbleDecoration::SetTextColor(NSColor* text_color) {
131 [attributes_ setObject:text_color forKey:NSForegroundColorAttributeName];