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

Side by Side Diff: ash/common/system/chromeos/power/power_status.cc

Issue 2063633002: Render Ash material design battery image icon without PNGs (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: for review Created 4 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 unified diff | Download patch
OLDNEW
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2013 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 "ash/common/system/chromeos/power/power_status.h" 5 #include "ash/common/system/chromeos/power/power_status.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <cmath> 8 #include <cmath>
9 9
10 #include "base/logging.h" 10 #include "base/logging.h"
11 #include "base/strings/string_number_conversions.h" 11 #include "base/strings/string_number_conversions.h"
12 #include "base/strings/utf_string_conversions.h" 12 #include "base/strings/utf_string_conversions.h"
13 #include "chromeos/dbus/dbus_thread_manager.h" 13 #include "chromeos/dbus/dbus_thread_manager.h"
14 #include "chromeos/dbus/power_manager_client.h" 14 #include "chromeos/dbus/power_manager_client.h"
15 #include "grit/ash_resources.h" 15 #include "grit/ash_resources.h"
16 #include "grit/ash_strings.h" 16 #include "grit/ash_strings.h"
17 #include "ui/base/l10n/l10n_util.h" 17 #include "ui/base/l10n/l10n_util.h"
18 #include "ui/base/l10n/time_format.h" 18 #include "ui/base/l10n/time_format.h"
19 #include "ui/base/resource/resource_bundle.h" 19 #include "ui/base/resource/resource_bundle.h"
20 #include "ui/display/display.h"
21 #include "ui/display/screen.h"
22 #include "ui/gfx/canvas.h"
20 #include "ui/gfx/geometry/rect.h" 23 #include "ui/gfx/geometry/rect.h"
21 #include "ui/gfx/image/image.h" 24 #include "ui/gfx/image/image.h"
22 #include "ui/gfx/image/image_skia_operations.h" 25 #include "ui/gfx/image/image_skia_operations.h"
26 #include "ui/gfx/paint_vector_icon.h"
27 #include "ui/gfx/vector_icons_public.h"
23 28
24 namespace ash { 29 namespace ash {
25 namespace { 30 namespace {
26 31
27 // Updates |proto| to ensure that its fields are consistent. 32 // Updates |proto| to ensure that its fields are consistent.
28 void SanitizeProto(power_manager::PowerSupplyProperties* proto) { 33 void SanitizeProto(power_manager::PowerSupplyProperties* proto) {
29 DCHECK(proto); 34 DCHECK(proto);
30 35
31 if (proto->battery_state() == 36 if (proto->battery_state() ==
32 power_manager::PowerSupplyProperties_BatteryState_FULL) 37 power_manager::PowerSupplyProperties_BatteryState_FULL)
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
86 return IDS_ASH_POWER_SOURCE_PORT_RIGHT_BACK; 91 return IDS_ASH_POWER_SOURCE_PORT_RIGHT_BACK;
87 case power_manager::PowerSupplyProperties_PowerSource_Port_BACK_LEFT: 92 case power_manager::PowerSupplyProperties_PowerSource_Port_BACK_LEFT:
88 return IDS_ASH_POWER_SOURCE_PORT_BACK_LEFT; 93 return IDS_ASH_POWER_SOURCE_PORT_BACK_LEFT;
89 case power_manager::PowerSupplyProperties_PowerSource_Port_BACK_RIGHT: 94 case power_manager::PowerSupplyProperties_PowerSource_Port_BACK_RIGHT:
90 return IDS_ASH_POWER_SOURCE_PORT_BACK_RIGHT; 95 return IDS_ASH_POWER_SOURCE_PORT_BACK_RIGHT;
91 } 96 }
92 NOTREACHED(); 97 NOTREACHED();
93 return 0; 98 return 0;
94 } 99 }
95 100
101 gfx::VectorIconId VectorIconIdForIconBadge(PowerStatus::IconBadge icon_badge) {
102 switch (icon_badge) {
103 case PowerStatus::ICON_BADGE_NONE:
104 return gfx::VectorIconId::VECTOR_ICON_NONE;
105 case PowerStatus::ICON_BADGE_ALERT:
106 return gfx::VectorIconId::SYSTEM_TRAY_BATTERY_ALERT;
107 case PowerStatus::ICON_BADGE_BOLT:
108 return gfx::VectorIconId::SYSTEM_TRAY_BATTERY_BOLT;
109 case PowerStatus::ICON_BADGE_X:
110 return gfx::VectorIconId::SYSTEM_TRAY_BATTERY_X;
111 case PowerStatus::ICON_BADGE_UNRELIABLE:
112 return gfx::VectorIconId::SYSTEM_TRAY_BATTERY_UNRELIABLE;
113 }
114 NOTREACHED();
115 return gfx::VectorIconId::VECTOR_ICON_NONE;
116 }
117
96 static PowerStatus* g_power_status = NULL; 118 static PowerStatus* g_power_status = NULL;
97 119
98 // Minimum battery percentage rendered in UI. 120 // Minimum battery percentage rendered in UI.
99 const int kMinBatteryPercent = 1; 121 const int kMinBatteryPercent = 1;
100 122
101 // Width and height of battery images. 123 // Width and height of battery images.
102 const int kBatteryImageHeight = 25; 124 const int kBatteryImageHeight = 25;
103 const int kBatteryImageWidth = 25; 125 const int kBatteryImageWidth = 25;
104 126
105 // Number of different power states. 127 // Number of different power states.
106 const int kNumPowerImages = 15; 128 const int kNumPowerImages = 15;
107 129
130 // The height of the battery icon in material design (as measured from the
131 // user-visible bottom of the icon to the user-visible top of the icon).
132 const int kBatteryImageHeightMD = 12;
Evan Stade 2016/06/21 02:55:48 nit: s/MD/Md
tdanderson 2016/06/21 22:42:28 Shouldn't we keep it as MD since 'M' and 'D' are t
James Cook 2016/06/21 23:19:00 In general, it's OsHttpUrl over OSHTTPURL. I haven
Evan Stade 2016/06/21 23:25:42 google style guide says "StartRpc(), not StartRPC(
tdanderson 2016/06/22 15:25:00 I will use Md here and in new code going forward.
133
134 // The dimensions of the canvas containing the material design battery icon.
135 const int kBatteryCanvasSizeMD = 16;
136
137 // The empty background color of the battery icon in the system tray. Used
138 // for material design.
139 // TODO(tdanderson): Move these constants to a shared location if they are
140 // shared by more than one material design system icon.
141 const SkColor kBatteryBaseColor = SkColorSetARGB(0x4C, 0xFF, 0xFF, 0xFF);
Evan Stade 2016/06/21 02:55:48 nit: imo easier to read as SkColorSetA(SK_ColorWHI
tdanderson 2016/06/21 22:42:29 Done.
142
143 // The background color of the filled region of the battery in the system
144 // tray. Used for material design.
145 const SkColor kBatteryFillColor = SkColorSetARGB(0xFF, 0xFF, 0xFF, 0xFF);
Evan Stade 2016/06/21 02:55:48 just SK_ColorWHITE
tdanderson 2016/06/21 22:42:28 Done.
146
147 // The color of the battery's badge (bolt, unreliable, X).
148 const SkColor kBatteryBadgeColor = SkColorSetARGB(0xB2, 0x00, 0x00, 0x00);
Evan Stade 2016/06/21 02:55:48 SkColorSetA(SK_ColorBLACK, 0xB2)
tdanderson 2016/06/21 22:42:28 Done.
149
150 // The color used for the battery's badge and fill color when the battery
151 // fill level is critically low.
152 const SkColor kBatteryAlertColor = SkColorSetARGB(0xFF, 0xDA, 0x27, 0x12);
Evan Stade 2016/06/21 02:55:48 just SkColorSetRGB
tdanderson 2016/06/21 22:42:28 Done.
153
108 } // namespace 154 } // namespace
109 155
110 const int PowerStatus::kMaxBatteryTimeToDisplaySec = 24 * 60 * 60; 156 const int PowerStatus::kMaxBatteryTimeToDisplaySec = 24 * 60 * 60;
111 157
112 // static 158 // static
113 void PowerStatus::Initialize() { 159 void PowerStatus::Initialize() {
114 CHECK(!g_power_status); 160 CHECK(!g_power_status);
115 g_power_status = new PowerStatus(); 161 g_power_status = new PowerStatus();
116 } 162 }
117 163
(...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after
253 return sources; 299 return sources;
254 } 300 }
255 301
256 std::string PowerStatus::GetCurrentPowerSourceID() const { 302 std::string PowerStatus::GetCurrentPowerSourceID() const {
257 return proto_.external_power_source_id(); 303 return proto_.external_power_source_id();
258 } 304 }
259 305
260 PowerStatus::BatteryImageInfo PowerStatus::GetBatteryImageInfo( 306 PowerStatus::BatteryImageInfo PowerStatus::GetBatteryImageInfo(
261 IconSet icon_set) const { 307 IconSet icon_set) const {
262 BatteryImageInfo info; 308 BatteryImageInfo info;
309 CalculateBatteryImageInfoMD(&info);
310 CalculateBatteryImageInfoNonMD(&info, icon_set);
311 return info;
312 }
313
314 void PowerStatus::CalculateBatteryImageInfoMD(BatteryImageInfo* info) const {
315 if (!IsUsbChargerConnected() && !IsBatteryPresent()) {
316 info->icon_badge = ICON_BADGE_X;
317 info->fill_level = 0;
318 return;
319 }
263 320
264 if (IsUsbChargerConnected()) { 321 if (IsUsbChargerConnected()) {
265 info.resource_id = 322 info->icon_badge = ICON_BADGE_UNRELIABLE;
323 } else if (IsLinePowerConnected()) {
324 info->icon_badge = ICON_BADGE_BOLT;
325 } else {
326 info->icon_badge = ICON_BADGE_NONE;
327 }
Evan Stade 2016/06/21 02:55:48 nit: I'd make this a series of nested ternaries. I
tdanderson 2016/06/21 22:42:28 Done.
328
329 // |fill_state| is a value between 0 and kBatteryImageHeightMD representing
330 // the number of pixels the battery image should be filled. The exception
331 // is when |fill_state| is 0 (a critically-low battery); in this case, still
332 // draw 1px of fill.
333 int fill_state =
334 static_cast<int>(GetBatteryPercent() / 100.0 * kBatteryImageHeightMD);
335 fill_state = std::max(std::min(fill_state, kBatteryImageHeightMD), 0);
336 info->fill_level = fill_state ? fill_state : 1;
Evan Stade 2016/06/21 02:55:48 implictly casting int to bool is confusing imo. Ca
tdanderson 2016/06/21 22:42:28 I will change to std::max(charge_state, 1). I can'
337
338 // Use ICON_BADGE_ALERT if the battery is critically low and does not already
339 // have a badge assigned.
340 if (!fill_state && info->icon_badge == ICON_BADGE_NONE)
Evan Stade 2016/06/21 02:55:48 I'd say 1 is pretty low so it's ok to change !fill
tdanderson 2016/06/21 22:42:28 Sebastien has asked that that we keep the same app
Evan Stade 2016/06/21 23:25:42 But you're not keeping the same behavior because b
tdanderson 2016/06/22 15:25:00 You are correct that the heights are different, wh
Evan Stade 2016/06/22 16:49:23 If you don't want to block this CL on his response
Daniel Erat 2016/06/22 17:22:43 the chrome os power management perspective: it'd i
tdanderson 2016/06/22 17:27:28 Thanks for taking a look. I'll leave as-is with th
341 info->icon_badge = ICON_BADGE_ALERT;
342 }
343
344 void PowerStatus::CalculateBatteryImageInfoNonMD(
345 BatteryImageInfo* info,
346 const IconSet& icon_set) const {
347 if (IsUsbChargerConnected()) {
348 info->resource_id =
266 (icon_set == ICON_DARK) 349 (icon_set == ICON_DARK)
267 ? IDR_AURA_UBER_TRAY_POWER_SMALL_CHARGING_UNRELIABLE_DARK 350 ? IDR_AURA_UBER_TRAY_POWER_SMALL_CHARGING_UNRELIABLE_DARK
268 : IDR_AURA_UBER_TRAY_POWER_SMALL_CHARGING_UNRELIABLE; 351 : IDR_AURA_UBER_TRAY_POWER_SMALL_CHARGING_UNRELIABLE;
269 } else { 352 } else {
270 info.resource_id = (icon_set == ICON_DARK) 353 info->resource_id = (icon_set == ICON_DARK)
271 ? IDR_AURA_UBER_TRAY_POWER_SMALL_DARK 354 ? IDR_AURA_UBER_TRAY_POWER_SMALL_DARK
272 : IDR_AURA_UBER_TRAY_POWER_SMALL; 355 : IDR_AURA_UBER_TRAY_POWER_SMALL;
273 } 356 }
274 357
275 info.offset = IsUsbChargerConnected() ? 0 : (IsLinePowerConnected() ? 1 : 0); 358 info->offset = IsUsbChargerConnected() ? 0 : (IsLinePowerConnected() ? 1 : 0);
276 359
277 if (GetBatteryPercent() >= 100.0) { 360 if (GetBatteryPercent() >= 100.0) {
278 info.index = kNumPowerImages - 1; 361 info->index = kNumPowerImages - 1;
279 } else if (!IsBatteryPresent()) { 362 } else if (!IsBatteryPresent()) {
280 info.index = kNumPowerImages; 363 info->index = kNumPowerImages;
281 } else { 364 } else {
282 info.index = 365 info->index =
283 static_cast<int>(GetBatteryPercent() / 100.0 * (kNumPowerImages - 1)); 366 static_cast<int>(GetBatteryPercent() / 100.0 * (kNumPowerImages - 1));
284 info.index = std::max(std::min(info.index, kNumPowerImages - 2), 0); 367 info->index = std::max(std::min(info->index, kNumPowerImages - 2), 0);
368 }
369 }
370
371 gfx::ImageSkia PowerStatus::GetBatteryImage(
372 const BatteryImageInfo& info) const {
373 if (!MaterialDesignController::UseMaterialDesignSystemIcons())
374 return GetBatteryImageNonMD(info);
375
376 const bool use_alert_color =
377 (info.fill_level == 1 && info.icon_badge != ICON_BADGE_BOLT);
378 const SkColor badge_color =
379 use_alert_color ? kBatteryAlertColor : kBatteryBadgeColor;
380 const SkColor fill_color =
381 use_alert_color ? kBatteryAlertColor : kBatteryFillColor;
382 gfx::Canvas canvas(
383 gfx::Size(kBatteryCanvasSizeMD, kBatteryCanvasSizeMD),
384 display::Screen::GetScreen()->GetPrimaryDisplay().device_scale_factor(),
385 true);
386
387 // Paint the battery's base (background) color.
388 PaintVectorIcon(&canvas, gfx::VectorIconId::SYSTEM_TRAY_BATTERY,
389 kBatteryCanvasSizeMD, kBatteryBaseColor);
390 canvas.Save();
Evan Stade 2016/06/21 02:55:48 nit: put right above clip call
tdanderson 2016/06/21 22:42:28 Done.
391
392 // Paint the filled portion of the battery. Note that |fill_height| adjusts
393 // for the 2px of padding between the bottom of the battery icon and the
Evan Stade 2016/06/21 02:55:48 nit: here and elsewhere you say px but you mean dp
tdanderson 2016/06/21 22:42:28 Done.
394 // bottom edge of |canvas|.
395 const int fill_height = info.fill_level + 2;
396 gfx::Rect clip_rect(0, kBatteryCanvasSizeMD - fill_height,
397 kBatteryCanvasSizeMD, fill_height);
398 canvas.ClipRect(clip_rect);
399 PaintVectorIcon(&canvas, gfx::VectorIconId::SYSTEM_TRAY_BATTERY,
400 kBatteryCanvasSizeMD, fill_color);
401 canvas.Restore();
402
403 // Paint the badge over top of the battery, if applicable.
404 if (info.icon_badge != ICON_BADGE_NONE) {
405 PaintVectorIcon(&canvas, VectorIconIdForIconBadge(info.icon_badge),
406 kBatteryCanvasSizeMD, badge_color);
285 } 407 }
286 408
287 return info; 409 return gfx::ImageSkia(canvas.ExtractImageRep());
288 } 410 }
289 411
290 gfx::ImageSkia PowerStatus::GetBatteryImage(IconSet icon_set) const { 412 gfx::ImageSkia PowerStatus::GetBatteryImageNonMD(
291 const BatteryImageInfo info = GetBatteryImageInfo(icon_set); 413 const BatteryImageInfo& info) const {
292 gfx::Image all; 414 gfx::Image all;
293 all = ui::ResourceBundle::GetSharedInstance().GetImageNamed(info.resource_id); 415 all = ui::ResourceBundle::GetSharedInstance().GetImageNamed(info.resource_id);
294 gfx::Rect region(info.offset * kBatteryImageWidth, 416 gfx::Rect region(info.offset * kBatteryImageWidth,
295 info.index * kBatteryImageHeight, kBatteryImageWidth, 417 info.index * kBatteryImageHeight, kBatteryImageWidth,
296 kBatteryImageHeight); 418 kBatteryImageHeight);
297 return gfx::ImageSkiaOperations::ExtractSubset(*all.ToImageSkia(), region); 419 return gfx::ImageSkiaOperations::ExtractSubset(*all.ToImageSkia(), region);
298 } 420 }
299 421
300 base::string16 PowerStatus::GetAccessibleNameString( 422 base::string16 PowerStatus::GetAccessibleNameString(
301 bool full_description) const { 423 bool full_description) const {
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
362 } 484 }
363 485
364 void PowerStatus::PowerChanged( 486 void PowerStatus::PowerChanged(
365 const power_manager::PowerSupplyProperties& proto) { 487 const power_manager::PowerSupplyProperties& proto) {
366 proto_ = proto; 488 proto_ = proto;
367 SanitizeProto(&proto_); 489 SanitizeProto(&proto_);
368 FOR_EACH_OBSERVER(Observer, observers_, OnPowerStatusChanged()); 490 FOR_EACH_OBSERVER(Observer, observers_, OnPowerStatusChanged());
369 } 491 }
370 492
371 } // namespace ash 493 } // namespace ash
OLDNEW
« no previous file with comments | « ash/common/system/chromeos/power/power_status.h ('k') | ash/common/system/chromeos/power/power_status_view.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698