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 "ash/system/tray/system_tray.h" | 5 #include "ash/system/tray/system_tray.h" |
6 | 6 |
7 #include "ash/shell.h" | 7 #include "ash/shell.h" |
8 #include "ash/shell/panel_window.h" | 8 #include "ash/shell/panel_window.h" |
9 #include "ash/shell_window_ids.h" | 9 #include "ash/shell_window_ids.h" |
10 #include "ash/system/audio/tray_volume.h" | 10 #include "ash/system/audio/tray_volume.h" |
(...skipping 225 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
236 } | 236 } |
237 | 237 |
238 void SystemTray::AddTrayItem(SystemTrayItem* item) { | 238 void SystemTray::AddTrayItem(SystemTrayItem* item) { |
239 items_.push_back(item); | 239 items_.push_back(item); |
240 | 240 |
241 SystemTrayDelegate* delegate = Shell::GetInstance()->tray_delegate(); | 241 SystemTrayDelegate* delegate = Shell::GetInstance()->tray_delegate(); |
242 views::View* tray_item = item->CreateTrayView(delegate->GetUserLoginStatus()); | 242 views::View* tray_item = item->CreateTrayView(delegate->GetUserLoginStatus()); |
243 if (tray_item) { | 243 if (tray_item) { |
244 tray_container_->AddChildViewAt(tray_item, 0); | 244 tray_container_->AddChildViewAt(tray_item, 0); |
245 PreferredSizeChanged(); | 245 PreferredSizeChanged(); |
246 tray_item_map_[item] = tray_item; | |
246 } | 247 } |
247 } | 248 } |
248 | 249 |
249 void SystemTray::RemoveTrayItem(SystemTrayItem* item) { | 250 void SystemTray::RemoveTrayItem(SystemTrayItem* item) { |
250 NOTIMPLEMENTED(); | 251 NOTIMPLEMENTED(); |
251 } | 252 } |
252 | 253 |
253 void SystemTray::ShowDefaultView() { | 254 void SystemTray::ShowDefaultView() { |
254 ShowItems(items_.get(), false, true); | 255 ShowDefaultViewWithOffset(-1); |
256 } | |
257 | |
258 void SystemTray::ShowDefaultViewWithOffset(int arrow_offset) { | |
sadrul
2012/05/15 02:18:15
The order of the functions in the .cc file should
Jun Mukai
2012/05/15 02:43:05
Done.
| |
259 ShowItems(items_.get(), false, true, arrow_offset); | |
255 } | 260 } |
256 | 261 |
257 void SystemTray::ShowDetailedView(SystemTrayItem* item, | 262 void SystemTray::ShowDetailedView(SystemTrayItem* item, |
258 int close_delay, | 263 int close_delay, |
259 bool activate) { | 264 bool activate) { |
260 std::vector<SystemTrayItem*> items; | 265 std::vector<SystemTrayItem*> items; |
261 items.push_back(item); | 266 items.push_back(item); |
262 ShowItems(items, true, activate); | 267 ShowItems(items, true, activate, GetTrayXOffset(item)); |
263 bubble_->StartAutoCloseTimer(close_delay); | 268 bubble_->StartAutoCloseTimer(close_delay); |
264 } | 269 } |
265 | 270 |
266 void SystemTray::ShowNotificationView(SystemTrayItem* item) { | 271 void SystemTray::ShowNotificationView(SystemTrayItem* item) { |
267 if (std::find(notification_items_.begin(), notification_items_.end(), item) | 272 if (std::find(notification_items_.begin(), notification_items_.end(), item) |
268 != notification_items_.end()) | 273 != notification_items_.end()) |
269 return; | 274 return; |
270 notification_items_.push_back(item); | 275 notification_items_.push_back(item); |
271 UpdateNotificationBubble(); | 276 UpdateNotificationBubble(); |
272 } | 277 } |
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
327 NOTREACHED(); | 332 NOTREACHED(); |
328 } | 333 } |
329 } | 334 } |
330 | 335 |
331 void SystemTray::SetPaintsBackground( | 336 void SystemTray::SetPaintsBackground( |
332 bool value, | 337 bool value, |
333 internal::BackgroundAnimator::ChangeType change_type) { | 338 internal::BackgroundAnimator::ChangeType change_type) { |
334 hide_background_animator_.SetPaintsBackground(value, change_type); | 339 hide_background_animator_.SetPaintsBackground(value, change_type); |
335 } | 340 } |
336 | 341 |
342 int SystemTray::GetTrayXOffset(SystemTrayItem* item) const { | |
343 std::map<SystemTrayItem*, views::View*>::const_iterator it = | |
344 tray_item_map_.find(item); | |
345 if (it == tray_item_map_.end()) | |
346 return -1; | |
347 | |
348 const views::View* item_view = it->second; | |
349 gfx::Rect item_bounds = item_view->bounds(); | |
350 if (!item_bounds.IsEmpty()) { | |
351 int x_offset = item_bounds.x() + item_bounds.width() / 2; | |
352 return base::i18n::IsRTL() ? x_offset : tray_container_->width() - x_offset; | |
353 } | |
354 | |
355 // Sometimes the bounds of item is still empty. In that case, we | |
356 // want to guess the offset from the position of its parent. | |
sadrul
2012/05/15 02:18:15
I guess this happens when the tray-view for an ite
Jun Mukai
2012/05/15 02:43:05
No... It happens first time the user presses caps
sadrul
2012/05/15 02:58:16
Ah, cool. Thanks for explaining.
| |
357 int x_offset = 0; | |
358 for (int i = 0; i < tray_container_->child_count(); ++i) { | |
359 const views::View* child = tray_container_->child_at(i); | |
360 if (child == item_view) | |
361 return base::i18n::IsRTL() ? | |
362 x_offset : tray_container_->width() - x_offset; | |
363 | |
364 if (!child->visible()) | |
365 continue; | |
366 x_offset = child->bounds().right(); | |
367 } | |
368 | |
369 return -1; | |
370 } | |
371 | |
337 void SystemTray::ShowItems(const std::vector<SystemTrayItem*>& items, | 372 void SystemTray::ShowItems(const std::vector<SystemTrayItem*>& items, |
338 bool detailed, | 373 bool detailed, |
339 bool can_activate) { | 374 bool can_activate, |
375 int arrow_offset) { | |
340 // Destroy any existing bubble and create a new one. | 376 // Destroy any existing bubble and create a new one. |
341 SystemTrayBubble::BubbleType bubble_type = detailed ? | 377 SystemTrayBubble::BubbleType bubble_type = detailed ? |
342 SystemTrayBubble::BUBBLE_TYPE_DETAILED : | 378 SystemTrayBubble::BUBBLE_TYPE_DETAILED : |
343 SystemTrayBubble::BUBBLE_TYPE_DEFAULT; | 379 SystemTrayBubble::BUBBLE_TYPE_DEFAULT; |
344 bubble_.reset(new SystemTrayBubble(this, items, bubble_type)); | 380 bubble_.reset(new SystemTrayBubble(this, items, bubble_type)); |
345 ash::SystemTrayDelegate* delegate = | 381 ash::SystemTrayDelegate* delegate = |
346 ash::Shell::GetInstance()->tray_delegate(); | 382 ash::Shell::GetInstance()->tray_delegate(); |
347 views::View* anchor = tray_container_; | 383 views::View* anchor = tray_container_; |
348 bubble_->InitView(anchor, SystemTrayBubble::ANCHOR_TYPE_TRAY, | 384 SystemTrayBubble::InitParams init_params(SystemTrayBubble::ANCHOR_TYPE_TRAY); |
349 can_activate, delegate->GetUserLoginStatus()); | 385 init_params.anchor = anchor; |
386 init_params.can_activate = can_activate; | |
387 init_params.login_status = delegate->GetUserLoginStatus(); | |
388 init_params.arrow_offset = arrow_offset; | |
389 bubble_->InitView(init_params); | |
350 // If we have focus the shelf should be visible and we need to continue | 390 // If we have focus the shelf should be visible and we need to continue |
351 // showing the shelf when the popup is shown. | 391 // showing the shelf when the popup is shown. |
352 if (GetWidget()->IsActive()) | 392 if (GetWidget()->IsActive()) |
353 should_show_launcher_ = true; | 393 should_show_launcher_ = true; |
354 UpdateNotificationBubble(); // State changed, re-create notifications. | 394 UpdateNotificationBubble(); // State changed, re-create notifications. |
355 } | 395 } |
356 | 396 |
357 void SystemTray::UpdateNotificationBubble() { | 397 void SystemTray::UpdateNotificationBubble() { |
358 // Only show the notification buble if we have notifications and we are not | 398 // Only show the notification buble if we have notifications and we are not |
359 // showing the default bubble. | 399 // showing the default bubble. |
360 if (notification_items_.empty() || | 400 if (notification_items_.empty() || |
361 (bubble_.get() && | 401 (bubble_.get() && |
362 bubble_->bubble_type() == SystemTrayBubble::BUBBLE_TYPE_DEFAULT)) { | 402 bubble_->bubble_type() == SystemTrayBubble::BUBBLE_TYPE_DEFAULT)) { |
363 notification_bubble_.reset(); | 403 notification_bubble_.reset(); |
364 return; | 404 return; |
365 } | 405 } |
366 notification_bubble_.reset( | 406 notification_bubble_.reset( |
367 new SystemTrayBubble(this, notification_items_, | 407 new SystemTrayBubble(this, notification_items_, |
368 SystemTrayBubble::BUBBLE_TYPE_NOTIFICATION)); | 408 SystemTrayBubble::BUBBLE_TYPE_NOTIFICATION)); |
369 views::View* anchor; | 409 views::View* anchor; |
370 SystemTrayBubble::AnchorType anchor_type; | 410 SystemTrayBubble::AnchorType anchor_type; |
371 if (bubble_.get()) { | 411 if (bubble_.get()) { |
372 anchor = bubble_->bubble_view(); | 412 anchor = bubble_->bubble_view(); |
373 anchor_type = SystemTrayBubble::ANCHOR_TYPE_BUBBLE; | 413 anchor_type = SystemTrayBubble::ANCHOR_TYPE_BUBBLE; |
374 } else { | 414 } else { |
375 anchor = tray_container_; | 415 anchor = tray_container_; |
376 anchor_type = SystemTrayBubble::ANCHOR_TYPE_TRAY; | 416 anchor_type = SystemTrayBubble::ANCHOR_TYPE_TRAY; |
377 } | 417 } |
378 notification_bubble_->InitView( | 418 SystemTrayBubble::InitParams init_params(anchor_type); |
379 anchor, anchor_type, | 419 init_params.anchor = anchor; |
380 false /* can_activate */, | 420 init_params.login_status = |
381 ash::Shell::GetInstance()->tray_delegate()->GetUserLoginStatus()); | 421 ash::Shell::GetInstance()->tray_delegate()->GetUserLoginStatus(); |
422 init_params.arrow_offset = GetTrayXOffset(notification_items_[0]); | |
423 notification_bubble_->InitView(init_params); | |
382 } | 424 } |
383 | 425 |
384 void SystemTray::UpdateNotificationAnchor() { | 426 void SystemTray::UpdateNotificationAnchor() { |
385 if (!notification_bubble_.get()) | 427 if (!notification_bubble_.get()) |
386 return; | 428 return; |
387 notification_bubble_->bubble_view()->UpdateAnchor(); | 429 notification_bubble_->bubble_view()->UpdateAnchor(); |
388 // Ensure that the notification buble is above the launcher/status area. | 430 // Ensure that the notification buble is above the launcher/status area. |
389 notification_bubble_->bubble_view()->GetWidget()->StackAtTop(); | 431 notification_bubble_->bubble_view()->GetWidget()->StackAtTop(); |
390 } | 432 } |
391 | 433 |
392 bool SystemTray::PerformAction(const views::Event& event) { | 434 bool SystemTray::PerformAction(const views::Event& event) { |
393 // If we're already showing the default view, hide it; otherwise, show it | 435 // If we're already showing the default view, hide it; otherwise, show it |
394 // (and hide any popup that's currently shown). | 436 // (and hide any popup that's currently shown). |
395 if (bubble_.get() && | 437 if (bubble_.get() && |
396 bubble_->bubble_type() == SystemTrayBubble::BUBBLE_TYPE_DEFAULT) { | 438 bubble_->bubble_type() == SystemTrayBubble::BUBBLE_TYPE_DEFAULT) { |
397 bubble_->Close(); | 439 bubble_->Close(); |
398 } else { | 440 } else { |
399 ShowDefaultView(); | 441 int arrow_offset = -1; |
442 if (event.IsMouseEvent() || event.IsTouchEvent()) { | |
443 const views::LocatedEvent& located_event = | |
444 static_cast<const views::LocatedEvent&>(event); | |
445 arrow_offset = base::i18n::IsRTL() ? | |
446 located_event.x() : tray_container_->width() - located_event.x(); | |
447 } | |
448 ShowDefaultViewWithOffset(arrow_offset); | |
400 } | 449 } |
401 return true; | 450 return true; |
402 } | 451 } |
403 | 452 |
404 void SystemTray::OnMouseEntered(const views::MouseEvent& event) { | 453 void SystemTray::OnMouseEntered(const views::MouseEvent& event) { |
405 should_show_launcher_ = true; | 454 should_show_launcher_ = true; |
406 hover_background_animator_.SetPaintsBackground(true, | 455 hover_background_animator_.SetPaintsBackground(true, |
407 internal::BackgroundAnimator::CHANGE_ANIMATE); | 456 internal::BackgroundAnimator::CHANGE_ANIMATE); |
408 } | 457 } |
409 | 458 |
(...skipping 25 matching lines...) Expand all Loading... | |
435 canvas->DrawFocusRect(tray_container_->bounds()); | 484 canvas->DrawFocusRect(tray_container_->bounds()); |
436 } | 485 } |
437 | 486 |
438 void SystemTray::UpdateBackground(int alpha) { | 487 void SystemTray::UpdateBackground(int alpha) { |
439 background_->set_alpha(hide_background_animator_.alpha() + | 488 background_->set_alpha(hide_background_animator_.alpha() + |
440 hover_background_animator_.alpha()); | 489 hover_background_animator_.alpha()); |
441 SchedulePaint(); | 490 SchedulePaint(); |
442 } | 491 } |
443 | 492 |
444 } // namespace ash | 493 } // namespace ash |
OLD | NEW |