Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 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 "components/exo/shell_surface.h" | 5 #include "components/exo/shell_surface.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #include "ash/common/frame/custom_frame_view_ash.h" | 9 #include "ash/common/frame/custom_frame_view_ash.h" |
| 10 #include "ash/common/shelf/wm_shelf.h" | 10 #include "ash/common/shelf/wm_shelf.h" |
| (...skipping 574 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 585 geometry.ToString()); | 585 geometry.ToString()); |
| 586 | 586 |
| 587 if (geometry.IsEmpty()) { | 587 if (geometry.IsEmpty()) { |
| 588 DLOG(WARNING) << "Surface geometry must be non-empty"; | 588 DLOG(WARNING) << "Surface geometry must be non-empty"; |
| 589 return; | 589 return; |
| 590 } | 590 } |
| 591 | 591 |
| 592 pending_geometry_ = geometry; | 592 pending_geometry_ = geometry; |
| 593 } | 593 } |
| 594 | 594 |
| 595 void ShellSurface::SetRectangularShadow(bool enabled) { | 595 void ShellSurface::SetRectangularShadowEnabled(bool enabled) { |
| 596 TRACE_EVENT1("exo", "ShellSurface::SetRectangularShadow", "enabled", enabled); | 596 TRACE_EVENT1("exo", "ShellSurface::SetRectangularShadowEnabled", "enabled", |
| 597 | 597 enabled); |
| 598 shadow_underlay_in_surface_ = false; | |
| 598 shadow_enabled_ = enabled; | 599 shadow_enabled_ = enabled; |
| 599 } | 600 } |
| 600 | 601 |
| 601 void ShellSurface::SetRectangularShadowContentBounds( | 602 void ShellSurface::SetRectangularShadow_DEPRECATED( |
| 602 const gfx::Rect& content_bounds) { | 603 const gfx::Rect& content_bounds) { |
| 603 TRACE_EVENT1("exo", "ShellSurface::SetRectangularShadowContentBounds", | 604 TRACE_EVENT1("exo", "ShellSurface::SetRectangularShadow_DEPRECATED", |
| 604 "content_bounds", content_bounds.ToString()); | 605 "content_bounds", content_bounds.ToString()); |
| 606 shadow_underlay_in_surface_ = false; | |
| 607 shadow_content_bounds_ = content_bounds; | |
| 608 shadow_enabled_ = !content_bounds.IsEmpty(); | |
| 609 } | |
| 605 | 610 |
| 611 void ShellSurface::SetRectangularSurfaceShadow( | |
| 612 const gfx::Rect& content_bounds) { | |
| 613 TRACE_EVENT1("exo", "ShellSurface::SetRectangularSurfaceShadow", | |
| 614 "content_bounds", content_bounds.ToString()); | |
| 615 shadow_underlay_in_surface_ = true; | |
| 606 shadow_content_bounds_ = content_bounds; | 616 shadow_content_bounds_ = content_bounds; |
| 617 shadow_enabled_ = !content_bounds.IsEmpty(); | |
| 607 } | 618 } |
| 608 | 619 |
| 609 void ShellSurface::SetRectangularShadowBackgroundOpacity(float opacity) { | 620 void ShellSurface::SetRectangularShadowBackgroundOpacity(float opacity) { |
| 610 TRACE_EVENT1("exo", "ShellSurface::SetRectangularShadowBackgroundOpacity", | 621 TRACE_EVENT1("exo", "ShellSurface::SetRectangularShadowBackgroundOpacity", |
| 611 "opacity", opacity); | 622 "opacity", opacity); |
| 612 | |
| 613 shadow_background_opacity_ = opacity; | 623 shadow_background_opacity_ = opacity; |
| 614 } | 624 } |
| 615 | 625 |
| 616 void ShellSurface::SetFrame(bool enabled) { | 626 void ShellSurface::SetFrame(bool enabled) { |
| 617 TRACE_EVENT1("exo", "ShellSurface::SetFrame", "enabled", enabled); | 627 TRACE_EVENT1("exo", "ShellSurface::SetFrame", "enabled", enabled); |
| 618 | 628 |
| 619 frame_enabled_ = enabled; | 629 frame_enabled_ = enabled; |
| 620 } | 630 } |
| 621 | 631 |
| 622 void ShellSurface::SetScale(double scale) { | 632 void ShellSurface::SetScale(double scale) { |
| (...skipping 794 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1417 void ShellSurface::UpdateShadow() { | 1427 void ShellSurface::UpdateShadow() { |
| 1418 if (!widget_) | 1428 if (!widget_) |
| 1419 return; | 1429 return; |
| 1420 aura::Window* window = widget_->GetNativeWindow(); | 1430 aura::Window* window = widget_->GetNativeWindow(); |
| 1421 if (!shadow_enabled_) { | 1431 if (!shadow_enabled_) { |
| 1422 wm::SetShadowElevation(window, wm::ShadowElevation::NONE); | 1432 wm::SetShadowElevation(window, wm::ShadowElevation::NONE); |
| 1423 if (shadow_underlay_) | 1433 if (shadow_underlay_) |
| 1424 shadow_underlay_->Hide(); | 1434 shadow_underlay_->Hide(); |
| 1425 } else { | 1435 } else { |
| 1426 wm::SetShadowElevation(window, wm::ShadowElevation::MEDIUM); | 1436 wm::SetShadowElevation(window, wm::ShadowElevation::MEDIUM); |
| 1437 gfx::Rect shadow_content_bounds = | |
| 1438 gfx::ScaleToEnclosedRect(shadow_content_bounds_, 1.f / scale_); | |
| 1439 gfx::Rect shadow_underlay_bounds = shadow_content_bounds_; | |
| 1440 if (shadow_underlay_bounds.IsEmpty()) | |
| 1441 shadow_underlay_bounds = gfx::Rect(surface_->window()->bounds().size()); | |
| 1427 | 1442 |
| 1428 gfx::Rect shadow_content_bounds = shadow_content_bounds_; | 1443 if (!shadow_underlay_in_surface_) { |
| 1429 if (shadow_content_bounds.IsEmpty()) | 1444 shadow_content_bounds = shadow_content_bounds_; |
| 1430 shadow_content_bounds = window->bounds(); | 1445 if (shadow_content_bounds.IsEmpty()) { |
| 1446 shadow_content_bounds = window->bounds(); | |
| 1447 } | |
| 1448 } | |
| 1431 | 1449 |
| 1432 // TODO(oshima): Adjust the coordinates from client screen to | 1450 // TODO(oshima): Adjust the coordinates from client screen to |
| 1433 // chromeos screen when multi displays are supported. | 1451 // chromeos screen when multi displays are supported. |
| 1434 gfx::Point origin = window->bounds().origin(); | 1452 gfx::Point origin = window->bounds().origin(); |
| 1435 gfx::Point shadow_origin = shadow_content_bounds.origin(); | 1453 gfx::Point shadow_origin = shadow_content_bounds.origin(); |
| 1436 shadow_origin -= origin.OffsetFromOrigin(); | 1454 shadow_origin -= origin.OffsetFromOrigin(); |
| 1437 gfx::Rect shadow_bounds(shadow_origin, shadow_content_bounds.size()); | 1455 gfx::Rect shadow_bounds(shadow_origin, shadow_content_bounds.size()); |
| 1438 | 1456 |
| 1439 // Always create and show the underlay, even in maximized/fullscreen. | 1457 // Always create and show the underlay, even in maximized/fullscreen. |
| 1440 if (!shadow_underlay_) { | 1458 if (!shadow_underlay_) { |
| 1441 shadow_underlay_ = new aura::Window(nullptr); | 1459 shadow_underlay_ = new aura::Window(nullptr); |
| 1442 shadow_underlay_event_handler_ = | 1460 shadow_underlay_event_handler_ = |
| 1443 base::MakeUnique<ShadowUnderlayEventHandler>(); | 1461 base::MakeUnique<ShadowUnderlayEventHandler>(); |
| 1444 shadow_underlay_->SetTargetHandler(shadow_underlay_event_handler_.get()); | 1462 shadow_underlay_->SetTargetHandler(shadow_underlay_event_handler_.get()); |
| 1445 DCHECK(shadow_underlay_->owned_by_parent()); | 1463 DCHECK(shadow_underlay_->owned_by_parent()); |
| 1446 // Ensure the background area inside the shadow is solid black. | 1464 // Ensure the background area inside the shadow is solid black. |
| 1447 // Clients that provide translucent contents should not be using | 1465 // Clients that provide translucent contents should not be using |
| 1448 // rectangular shadows as this method requires opaque contents to | 1466 // rectangular shadows as this method requires opaque contents to |
| 1449 // cast a shadow that represent it correctly. | 1467 // cast a shadow that represent it correctly. |
| 1450 shadow_underlay_->Init(ui::LAYER_SOLID_COLOR); | 1468 shadow_underlay_->Init(ui::LAYER_SOLID_COLOR); |
| 1451 shadow_underlay_->layer()->SetColor(SK_ColorBLACK); | 1469 shadow_underlay_->layer()->SetColor(SK_ColorBLACK); |
| 1452 DCHECK(shadow_underlay_->layer()->fills_bounds_opaquely()); | 1470 DCHECK(shadow_underlay_->layer()->fills_bounds_opaquely()); |
| 1453 window->AddChild(shadow_underlay_); | 1471 if (shadow_underlay_in_surface_) { |
| 1454 window->StackChildAtBottom(shadow_underlay_); | 1472 surface_->window()->AddChild(shadow_underlay_); |
| 1473 } else { | |
| 1474 window->AddChild(shadow_underlay_); | |
| 1475 window->StackChildAtBottom(shadow_underlay_); | |
| 1476 } | |
| 1477 } | |
| 1478 | |
| 1479 if (shadow_underlay_in_surface_ && shadow_underlay_ != nullptr && | |
|
reveman
2017/02/07 03:16:53
nit: s/shadow_underlay_ != nullptr/shadow_underlay
| |
| 1480 *(surface_->window()->children().begin()) != shadow_underlay_) { | |
|
reveman
2017/02/07 03:16:53
is this really needed? what results in this not be
| |
| 1481 surface_->window()->StackChildAtBottom(shadow_underlay_); | |
| 1455 } | 1482 } |
| 1456 | 1483 |
| 1457 bool underlay_capture_events = | 1484 bool underlay_capture_events = |
| 1458 WMHelper::GetInstance()->IsSpokenFeedbackEnabled() && | 1485 WMHelper::GetInstance()->IsSpokenFeedbackEnabled() && |
| 1459 widget_->IsActive(); | 1486 widget_->IsActive(); |
| 1460 | 1487 |
| 1461 float shadow_underlay_opacity = shadow_background_opacity_; | 1488 float shadow_underlay_opacity = shadow_background_opacity_; |
| 1462 // Put the black background layer behind the window if | 1489 // Put the black background layer behind the window if |
| 1463 // 1) the window is in immersive fullscreen or is active with | 1490 // 1) the window is in immersive fullscreen or is active with |
| 1464 // spoken feedback enabled. | 1491 // spoken feedback enabled. |
| 1465 // 2) the window can control the bounds of the window in fullscreen ( | 1492 // 2) the window can control the bounds of the window in fullscreen ( |
| 1466 // thus the background can be visible). | 1493 // thus the background can be visible). |
| 1467 // 3) the window has no transform (the transformed background may | 1494 // 3) the window has no transform (the transformed background may |
| 1468 // not cover the entire background, e.g. overview mode). | 1495 // not cover the entire background, e.g. overview mode). |
| 1469 if ((widget_->IsFullscreen() || underlay_capture_events) && | 1496 if ((widget_->IsFullscreen() || underlay_capture_events) && |
| 1470 ash::wm::GetWindowState(window)->allow_set_bounds_in_maximized() && | 1497 ash::wm::GetWindowState(window)->allow_set_bounds_in_maximized() && |
| 1471 window->layer()->GetTargetTransform().IsIdentity()) { | 1498 window->layer()->GetTargetTransform().IsIdentity()) { |
| 1472 gfx::Point origin; | 1499 if (shadow_underlay_in_surface_) { |
| 1473 origin -= window->bounds().origin().OffsetFromOrigin(); | 1500 shadow_underlay_bounds = gfx::Rect(surface_->window()->bounds().size()); |
| 1474 shadow_bounds.set_origin(origin); | 1501 } else { |
| 1475 shadow_bounds.set_size(window->parent()->bounds().size()); | 1502 gfx::Point origin; |
| 1503 origin -= window->bounds().origin().OffsetFromOrigin(); | |
| 1504 shadow_bounds.set_origin(origin); | |
| 1505 shadow_bounds.set_size(window->parent()->bounds().size()); | |
| 1506 } | |
| 1476 shadow_underlay_opacity = 1.0f; | 1507 shadow_underlay_opacity = 1.0f; |
| 1477 } | 1508 } |
| 1478 | 1509 |
| 1479 gfx::Rect shadow_underlay_bounds = shadow_bounds; | 1510 if (!shadow_underlay_in_surface_) |
| 1511 shadow_underlay_bounds = shadow_bounds; | |
| 1480 | 1512 |
| 1481 // Constrain the underlay bounds to the client area in case shell surface | 1513 // Constrain the underlay bounds to the client area in case shell surface |
| 1482 // frame is enabled. | 1514 // frame is enabled. |
| 1483 if (frame_enabled_) { | 1515 if (frame_enabled_) { |
| 1484 shadow_underlay_bounds.Intersect( | 1516 shadow_underlay_bounds.Intersect( |
| 1485 widget_->non_client_view()->frame_view()->GetBoundsForClientView()); | 1517 widget_->non_client_view()->frame_view()->GetBoundsForClientView()); |
| 1486 } | 1518 } |
| 1487 | 1519 |
| 1488 shadow_underlay_->SetBounds(shadow_underlay_bounds); | 1520 shadow_underlay_->SetBounds(shadow_underlay_bounds); |
| 1489 | 1521 |
| (...skipping 11 matching lines...) Expand all Loading... | |
| 1501 if (!shadow) | 1533 if (!shadow) |
| 1502 return; | 1534 return; |
| 1503 | 1535 |
| 1504 if (!shadow_overlay_) { | 1536 if (!shadow_overlay_) { |
| 1505 shadow_overlay_ = new aura::Window(nullptr); | 1537 shadow_overlay_ = new aura::Window(nullptr); |
| 1506 DCHECK(shadow_overlay_->owned_by_parent()); | 1538 DCHECK(shadow_overlay_->owned_by_parent()); |
| 1507 shadow_overlay_->set_ignore_events(true); | 1539 shadow_overlay_->set_ignore_events(true); |
| 1508 shadow_overlay_->Init(ui::LAYER_NOT_DRAWN); | 1540 shadow_overlay_->Init(ui::LAYER_NOT_DRAWN); |
| 1509 shadow_overlay_->layer()->Add(shadow->layer()); | 1541 shadow_overlay_->layer()->Add(shadow->layer()); |
| 1510 window->AddChild(shadow_overlay_); | 1542 window->AddChild(shadow_overlay_); |
| 1511 window->StackChildAbove(shadow_overlay_, shadow_underlay_); | 1543 |
| 1544 if (shadow_underlay_in_surface_) { | |
| 1545 window->StackChildBelow(shadow_overlay_, surface_->window()); | |
| 1546 } else { | |
| 1547 window->StackChildAbove(shadow_overlay_, shadow_underlay_); | |
| 1548 } | |
| 1512 shadow_overlay_->Show(); | 1549 shadow_overlay_->Show(); |
| 1513 } | 1550 } |
| 1514 shadow_overlay_->SetBounds(shadow_bounds); | 1551 shadow_overlay_->SetBounds(shadow_bounds); |
| 1515 shadow->SetContentBounds(gfx::Rect(shadow_bounds.size())); | 1552 shadow->SetContentBounds(gfx::Rect(shadow_bounds.size())); |
| 1516 // Surfaces that can't be activated are usually menus and tooltips. Use a | 1553 // Surfaces that can't be activated are usually menus and tooltips. Use a |
| 1517 // small style shadow for them. | 1554 // small style shadow for them. |
| 1518 if (!activatable_) | 1555 if (!activatable_) |
| 1519 shadow->SetElevation(wm::ShadowElevation::SMALL); | 1556 shadow->SetElevation(wm::ShadowElevation::SMALL); |
| 1520 // We don't have rounded corners unless frame is enabled. | 1557 // We don't have rounded corners unless frame is enabled. |
| 1521 if (!frame_enabled_) | 1558 if (!frame_enabled_) |
| 1522 shadow->SetRoundedCornerRadius(0); | 1559 shadow->SetRoundedCornerRadius(0); |
| 1523 } | 1560 } |
| 1524 } | 1561 } |
| 1525 | 1562 |
| 1526 } // namespace exo | 1563 } // namespace exo |
| OLD | NEW |