OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 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 #include "ui/views/controls/button/label_button.h" | 5 #include "ui/views/controls/button/label_button.h" |
6 | 6 |
7 #include "base/logging.h" | 7 #include "base/logging.h" |
8 #include "grit/ui_resources.h" | 8 #include "grit/ui_resources.h" |
9 #include "ui/base/resource/resource_bundle.h" | 9 #include "ui/base/resource/resource_bundle.h" |
10 #include "ui/gfx/animation/throb_animation.h" | 10 #include "ui/gfx/animation/throb_animation.h" |
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
94 void LabelButton::SetTextColor(ButtonState for_state, SkColor color) { | 94 void LabelButton::SetTextColor(ButtonState for_state, SkColor color) { |
95 button_state_colors_[for_state] = color; | 95 button_state_colors_[for_state] = color; |
96 if (for_state == STATE_DISABLED) | 96 if (for_state == STATE_DISABLED) |
97 label_->SetDisabledColor(color); | 97 label_->SetDisabledColor(color); |
98 else if (for_state == state()) | 98 else if (for_state == state()) |
99 label_->SetEnabledColor(color); | 99 label_->SetEnabledColor(color); |
100 explicitly_set_colors_[for_state] = true; | 100 explicitly_set_colors_[for_state] = true; |
101 } | 101 } |
102 | 102 |
103 void LabelButton::SetTextShadows(const gfx::ShadowValues& shadows) { | 103 void LabelButton::SetTextShadows(const gfx::ShadowValues& shadows) { |
104 label_->set_shadows(shadows); | 104 label_->SetShadows(shadows); |
105 } | 105 } |
106 | 106 |
107 void LabelButton::SetTextSubpixelRenderingEnabled(bool enabled) { | 107 void LabelButton::SetTextSubpixelRenderingEnabled(bool enabled) { |
108 label_->set_subpixel_rendering_enabled(enabled); | 108 label_->SetSubpixelRenderingEnabled(enabled); |
109 } | 109 } |
110 | 110 |
111 bool LabelButton::GetTextMultiLine() const { | 111 bool LabelButton::GetTextMultiLine() const { |
112 return label_->is_multi_line(); | 112 return label_->multi_line(); |
113 } | 113 } |
114 | 114 |
115 void LabelButton::SetTextMultiLine(bool text_multi_line) { | 115 void LabelButton::SetTextMultiLine(bool text_multi_line) { |
116 label_->SetMultiLine(text_multi_line); | 116 label_->SetMultiLine(text_multi_line); |
117 } | 117 } |
118 | 118 |
119 const gfx::FontList& LabelButton::GetFontList() const { | 119 const gfx::FontList& LabelButton::GetFontList() const { |
120 return label_->font_list(); | 120 return label_->font_list(); |
121 } | 121 } |
122 | 122 |
(...skipping 14 matching lines...) Expand all Loading... |
137 | 137 |
138 gfx::HorizontalAlignment LabelButton::GetHorizontalAlignment() const { | 138 gfx::HorizontalAlignment LabelButton::GetHorizontalAlignment() const { |
139 return label_->GetHorizontalAlignment(); | 139 return label_->GetHorizontalAlignment(); |
140 } | 140 } |
141 | 141 |
142 void LabelButton::SetHorizontalAlignment(gfx::HorizontalAlignment alignment) { | 142 void LabelButton::SetHorizontalAlignment(gfx::HorizontalAlignment alignment) { |
143 label_->SetHorizontalAlignment(alignment); | 143 label_->SetHorizontalAlignment(alignment); |
144 InvalidateLayout(); | 144 InvalidateLayout(); |
145 } | 145 } |
146 | 146 |
147 void LabelButton::SetDirectionalityMode(gfx::DirectionalityMode mode) { | |
148 label_->set_directionality_mode(mode); | |
149 } | |
150 | |
151 void LabelButton::SetIsDefault(bool is_default) { | 147 void LabelButton::SetIsDefault(bool is_default) { |
152 if (is_default == is_default_) | 148 if (is_default == is_default_) |
153 return; | 149 return; |
154 is_default_ = is_default; | 150 is_default_ = is_default; |
155 ui::Accelerator accel(ui::VKEY_RETURN, ui::EF_NONE); | 151 ui::Accelerator accel(ui::VKEY_RETURN, ui::EF_NONE); |
156 is_default_ ? AddAccelerator(accel) : RemoveAccelerator(accel); | 152 is_default_ ? AddAccelerator(accel) : RemoveAccelerator(accel); |
157 | 153 |
158 // STYLE_BUTTON uses bold text to indicate default buttons. | 154 // STYLE_BUTTON uses bold text to indicate default buttons. |
159 if (style_ == STYLE_BUTTON) { | 155 if (style_ == STYLE_BUTTON) { |
160 label_->SetFontList( | 156 label_->SetFontList( |
(...skipping 20 matching lines...) Expand all Loading... |
181 OnNativeThemeChanged(GetNativeTheme()); | 177 OnNativeThemeChanged(GetNativeTheme()); |
182 } | 178 } |
183 | 179 |
184 void LabelButton::SetFocusPainter(scoped_ptr<Painter> focus_painter) { | 180 void LabelButton::SetFocusPainter(scoped_ptr<Painter> focus_painter) { |
185 focus_painter_ = focus_painter.Pass(); | 181 focus_painter_ = focus_painter.Pass(); |
186 } | 182 } |
187 | 183 |
188 gfx::Size LabelButton::GetPreferredSize() const { | 184 gfx::Size LabelButton::GetPreferredSize() const { |
189 // Use a temporary label copy for sizing to avoid calculation side-effects. | 185 // Use a temporary label copy for sizing to avoid calculation side-effects. |
190 Label label(GetText(), cached_normal_font_list_); | 186 Label label(GetText(), cached_normal_font_list_); |
191 label.set_shadows(label_->shadows()); | 187 label.SetShadows(label_->shadows()); |
192 label.SetMultiLine(GetTextMultiLine()); | 188 label.SetMultiLine(GetTextMultiLine()); |
193 | 189 |
194 if (style() == STYLE_BUTTON) { | 190 if (style() == STYLE_BUTTON) { |
195 // Some text appears wider when rendered normally than when rendered bold. | 191 // Some text appears wider when rendered normally than when rendered bold. |
196 // Accommodate the widest, as buttons may show bold and shouldn't resize. | 192 // Accommodate the widest, as buttons may show bold and shouldn't resize. |
197 const int current_width = label.GetPreferredSize().width(); | 193 const int current_width = label.GetPreferredSize().width(); |
198 label.SetFontList(cached_bold_font_list_); | 194 label.SetFontList(cached_bold_font_list_); |
199 if (label.GetPreferredSize().width() < current_width) | 195 if (label.GetPreferredSize().width() < current_width) |
200 label.SetFontList(cached_normal_font_list_); | 196 label.SetFontList(cached_normal_font_list_); |
201 } | 197 } |
202 | 198 |
203 // Resize multi-line labels given the current limited available width. | 199 // Calculate the required size. |
204 const gfx::Size image_size(image_->GetPreferredSize()); | 200 const gfx::Size image_size(image_->GetPreferredSize()); |
205 const int image_width = image_size.width(); | |
206 if (GetTextMultiLine() && (width() > image_width + kSpacing)) | |
207 label.SizeToFit(width() - image_width - (image_width > 0 ? kSpacing : 0)); | |
208 | |
209 // Calculate the required size. | |
210 gfx::Size size(label.GetPreferredSize()); | 201 gfx::Size size(label.GetPreferredSize()); |
211 if (image_width > 0 && size.width() > 0) | 202 if (image_size.width() > 0 && size.width() > 0) |
212 size.Enlarge(kSpacing, 0); | 203 size.Enlarge(kSpacing, 0); |
213 size.SetToMax(gfx::Size(0, image_size.height())); | 204 size.SetToMax(gfx::Size(0, image_size.height())); |
214 const gfx::Insets insets(GetInsets()); | 205 const gfx::Insets insets(GetInsets()); |
215 size.Enlarge(image_size.width() + insets.width(), insets.height()); | 206 size.Enlarge(image_size.width() + insets.width(), insets.height()); |
216 | 207 |
217 // Make the size at least as large as the minimum size needed by the border. | 208 // Make the size at least as large as the minimum size needed by the border. |
218 size.SetToMax(border() ? border()->GetMinimumSize() : gfx::Size()); | 209 size.SetToMax(border() ? border()->GetMinimumSize() : gfx::Size()); |
219 | 210 |
220 // Increase the minimum size monotonically with the preferred size. | 211 // Increase the minimum size monotonically with the preferred size. |
221 size.SetToMax(min_size_); | 212 size.SetToMax(min_size_); |
222 min_size_ = size; | 213 min_size_ = size; |
223 | 214 |
224 // Return the largest known size clamped to the maximum size (if valid). | 215 // Return the largest known size clamped to the maximum size (if valid). |
225 if (max_size_.width() > 0) | 216 if (max_size_.width() > 0) |
226 size.set_width(std::min(max_size_.width(), size.width())); | 217 size.set_width(std::min(max_size_.width(), size.width())); |
227 if (max_size_.height() > 0) | 218 if (max_size_.height() > 0) |
228 size.set_height(std::min(max_size_.height(), size.height())); | 219 size.set_height(std::min(max_size_.height(), size.height())); |
229 return size; | 220 return size; |
230 } | 221 } |
231 | 222 |
| 223 int LabelButton::GetHeightForWidth(int w) const { |
| 224 w -= GetInsets().width(); |
| 225 const gfx::Size image_size(image_->GetPreferredSize()); |
| 226 w -= image_size.width(); |
| 227 if (image_size.width() > 0 && !GetText().empty()) |
| 228 w -= kSpacing; |
| 229 |
| 230 int height = std::max(image_size.height(), label_->GetHeightForWidth(w)); |
| 231 if (border()) |
| 232 height = std::max(height, border()->GetMinimumSize().height()); |
| 233 |
| 234 height = std::max(height, min_size_.height()); |
| 235 if (max_size_.height() > 0) |
| 236 height = std::min(height, max_size_.height()); |
| 237 return height; |
| 238 } |
| 239 |
232 void LabelButton::Layout() { | 240 void LabelButton::Layout() { |
233 gfx::HorizontalAlignment adjusted_alignment = GetHorizontalAlignment(); | 241 gfx::HorizontalAlignment adjusted_alignment = GetHorizontalAlignment(); |
234 if (base::i18n::IsRTL() && adjusted_alignment != gfx::ALIGN_CENTER) | 242 if (base::i18n::IsRTL() && adjusted_alignment != gfx::ALIGN_CENTER) |
235 adjusted_alignment = (adjusted_alignment == gfx::ALIGN_LEFT) ? | 243 adjusted_alignment = (adjusted_alignment == gfx::ALIGN_LEFT) ? |
236 gfx::ALIGN_RIGHT : gfx::ALIGN_LEFT; | 244 gfx::ALIGN_RIGHT : gfx::ALIGN_LEFT; |
237 | 245 |
238 gfx::Rect child_area(GetChildAreaBounds()); | 246 gfx::Rect child_area(GetChildAreaBounds()); |
239 child_area.Inset(GetInsets()); | 247 child_area.Inset(GetInsets()); |
240 | 248 |
241 gfx::Size image_size(image_->GetPreferredSize()); | 249 gfx::Size image_size(image_->GetPreferredSize()); |
242 image_size.SetToMin(child_area.size()); | 250 image_size.SetToMin(child_area.size()); |
243 | 251 |
244 // The label takes any remaining width after sizing the image, unless both | 252 // The label takes any remaining width after sizing the image, unless both |
245 // views are centered. In that case, using the tighter preferred label width | 253 // views are centered. In that case, using the tighter preferred label width |
246 // avoids wasted space within the label that would look like awkward padding. | 254 // avoids wasted space within the label that would look like awkward padding. |
247 gfx::Size label_size(child_area.size()); | 255 gfx::Size label_size(child_area.size()); |
248 if (!image_size.IsEmpty() && !label_size.IsEmpty()) { | 256 if (!image_size.IsEmpty() && !label_size.IsEmpty()) { |
249 label_size.set_width( | 257 label_size.set_width( |
250 std::max(child_area.width() - image_size.width() - kSpacing, 0)); | 258 std::max(child_area.width() - image_size.width() - kSpacing, 0)); |
251 if (adjusted_alignment == gfx::ALIGN_CENTER) { | 259 if (adjusted_alignment == gfx::ALIGN_CENTER) { |
252 // Ensure multi-line labels paired with images use their available width. | 260 // Ensure multi-line labels paired with images use their available width. |
253 if (GetTextMultiLine()) | |
254 label_->SizeToFit(label_size.width()); | |
255 label_size.set_width( | 261 label_size.set_width( |
256 std::min(label_size.width(), label_->GetPreferredSize().width())); | 262 std::min(label_size.width(), label_->GetPreferredSize().width())); |
257 } | 263 } |
258 } | 264 } |
259 | 265 |
260 gfx::Point image_origin(child_area.origin()); | 266 gfx::Point image_origin(child_area.origin()); |
261 image_origin.Offset(0, (child_area.height() - image_size.height()) / 2); | 267 image_origin.Offset(0, (child_area.height() - image_size.height()) / 2); |
262 if (adjusted_alignment == gfx::ALIGN_CENTER) { | 268 if (adjusted_alignment == gfx::ALIGN_CENTER) { |
263 const int total_width = image_size.width() + label_size.width() + | 269 const int total_width = image_size.width() + label_size.width() + |
264 ((image_size.width() > 0 && label_size.width() > 0) ? kSpacing : 0); | 270 ((image_size.width() > 0 && label_size.width() > 0) ? kSpacing : 0); |
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
330 | 336 |
331 // Certain styles do not change text color when hovered or pressed. | 337 // Certain styles do not change text color when hovered or pressed. |
332 bool constant_text_color = false; | 338 bool constant_text_color = false; |
333 // Use hardcoded colors for inverted color scheme support and STYLE_BUTTON. | 339 // Use hardcoded colors for inverted color scheme support and STYLE_BUTTON. |
334 if (gfx::IsInvertedColorScheme()) { | 340 if (gfx::IsInvertedColorScheme()) { |
335 constant_text_color = true; | 341 constant_text_color = true; |
336 colors[STATE_NORMAL] = SK_ColorWHITE; | 342 colors[STATE_NORMAL] = SK_ColorWHITE; |
337 label_->SetBackgroundColor(SK_ColorBLACK); | 343 label_->SetBackgroundColor(SK_ColorBLACK); |
338 label_->set_background(Background::CreateSolidBackground(SK_ColorBLACK)); | 344 label_->set_background(Background::CreateSolidBackground(SK_ColorBLACK)); |
339 label_->SetAutoColorReadabilityEnabled(true); | 345 label_->SetAutoColorReadabilityEnabled(true); |
340 label_->set_shadows(gfx::ShadowValues()); | 346 label_->SetShadows(gfx::ShadowValues()); |
341 } else if (style() == STYLE_BUTTON) { | 347 } else if (style() == STYLE_BUTTON) { |
342 // TODO(erg): This is disabled on desktop linux because of the binary asset | 348 // TODO(erg): This is disabled on desktop linux because of the binary asset |
343 // confusion. These details should either be pushed into ui::NativeThemeWin | 349 // confusion. These details should either be pushed into ui::NativeThemeWin |
344 // or should be obsoleted by rendering buttons with paint calls instead of | 350 // or should be obsoleted by rendering buttons with paint calls instead of |
345 // with static assets. http://crbug.com/350498 | 351 // with static assets. http://crbug.com/350498 |
346 #if !(defined(OS_LINUX) && !defined(OS_CHROMEOS)) | 352 #if !(defined(OS_LINUX) && !defined(OS_CHROMEOS)) |
347 constant_text_color = true; | 353 constant_text_color = true; |
348 colors[STATE_NORMAL] = kStyleButtonTextColor; | 354 colors[STATE_NORMAL] = kStyleButtonTextColor; |
349 label_->SetBackgroundColor(theme->GetSystemColor( | 355 label_->SetBackgroundColor(theme->GetSystemColor( |
350 ui::NativeTheme::kColorId_ButtonBackgroundColor)); | 356 ui::NativeTheme::kColorId_ButtonBackgroundColor)); |
351 label_->SetAutoColorReadabilityEnabled(false); | 357 label_->SetAutoColorReadabilityEnabled(false); |
352 label_->set_shadows(gfx::ShadowValues(1, | 358 label_->SetShadows(gfx::ShadowValues( |
353 gfx::ShadowValue(gfx::Point(0, 1), 0, kStyleButtonShadowColor))); | 359 1, gfx::ShadowValue(gfx::Point(0, 1), 0, kStyleButtonShadowColor))); |
354 #endif | 360 #endif |
355 label_->set_background(NULL); | 361 label_->set_background(NULL); |
356 } else { | 362 } else { |
357 label_->set_background(NULL); | 363 label_->set_background(NULL); |
358 } | 364 } |
359 | 365 |
360 if (constant_text_color) | 366 if (constant_text_color) |
361 colors[STATE_HOVERED] = colors[STATE_PRESSED] = colors[STATE_NORMAL]; | 367 colors[STATE_HOVERED] = colors[STATE_PRESSED] = colors[STATE_NORMAL]; |
362 | 368 |
363 for (size_t state = STATE_NORMAL; state < STATE_COUNT; ++state) { | 369 for (size_t state = STATE_NORMAL; state < STATE_COUNT; ++state) { |
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
446 return ui::NativeTheme::kNormal; | 452 return ui::NativeTheme::kNormal; |
447 } | 453 } |
448 | 454 |
449 ui::NativeTheme::State LabelButton::GetForegroundThemeState( | 455 ui::NativeTheme::State LabelButton::GetForegroundThemeState( |
450 ui::NativeTheme::ExtraParams* params) const { | 456 ui::NativeTheme::ExtraParams* params) const { |
451 GetExtraParams(params); | 457 GetExtraParams(params); |
452 return ui::NativeTheme::kHovered; | 458 return ui::NativeTheme::kHovered; |
453 } | 459 } |
454 | 460 |
455 } // namespace views | 461 } // namespace views |
OLD | NEW |