| // Copyright 2018 The Chromium Authors |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #include "chrome/browser/ui/views/toolbar/toolbar_ink_drop_util.h" |
| |
| #include "base/functional/bind.h" |
| #include "chrome/browser/themes/theme_properties.h" |
| #include "chrome/browser/ui/color/chrome_color_id.h" |
| #include "chrome/browser/ui/color/chrome_color_provider_utils.h" |
| #include "chrome/browser/ui/layout_constants.h" |
| #include "chrome/browser/ui/views/chrome_layout_provider.h" |
| #include "third_party/skia/include/core/SkColor.h" |
| #include "third_party/skia/include/core/SkPath.h" |
| #include "ui/base/ui_base_features.h" |
| #include "ui/color/color_provider.h" |
| #include "ui/gfx/color_palette.h" |
| #include "ui/gfx/color_utils.h" |
| #include "ui/gfx/geometry/rect.h" |
| #include "ui/gfx/geometry/size.h" |
| #include "ui/gfx/geometry/skia_conversions.h" |
| #include "ui/views/animation/flood_fill_ink_drop_ripple.h" |
| #include "ui/views/animation/ink_drop.h" |
| #include "ui/views/animation/ink_drop_host.h" |
| #include "ui/views/animation/ink_drop_impl.h" |
| #include "ui/views/controls/button/button.h" |
| #include "ui/views/controls/highlight_path_generator.h" |
| #include "ui/views/style/platform_style.h" |
| #include "ui/views/view.h" |
| #include "ui/views/view_class_properties.h" |
| |
| namespace { |
| class ToolbarButtonHighlightPathGenerator |
| : public views::HighlightPathGenerator { |
| public: |
| // HighlightPathGenerator: |
| SkPath GetHighlightPath(const views::View* view) override { |
| gfx::Rect rect(view->size()); |
| rect.Inset(GetToolbarInkDropInsets(view)); |
| |
| const int radii = ChromeLayoutProvider::Get()->GetCornerRadiusMetric( |
| views::Emphasis::kMaximum, rect.size()); |
| |
| SkPath path; |
| path.addRoundRect(gfx::RectToSkRect(rect), radii, radii); |
| return path; |
| } |
| }; |
| |
| } // namespace |
| |
| gfx::Insets GetToolbarInkDropInsets(const views::View* host_view) { |
| gfx::Insets margin_insets; |
| gfx::Insets* const internal_padding = |
| host_view->GetProperty(views::kInternalPaddingKey); |
| if (internal_padding) |
| margin_insets = *internal_padding; |
| |
| // Inset the inkdrop insets so that the end result matches the target inkdrop |
| // dimensions. |
| const gfx::Size host_size = host_view->size(); |
| const int inkdrop_dimensions = GetLayoutConstant(LOCATION_BAR_HEIGHT); |
| gfx::Insets inkdrop_insets = |
| margin_insets + |
| gfx::Insets(std::max(0, (host_size.height() - inkdrop_dimensions) / 2)); |
| |
| return inkdrop_insets; |
| } |
| |
| SkColor GetToolbarInkDropBaseColor(const views::View* host_view) { |
| const auto* color_provider = host_view->GetColorProvider(); |
| // There may be no color provider in unit tests. |
| return color_provider ? color_provider->GetColor(kColorToolbarInkDrop) |
| : gfx::kPlaceholderColor; |
| } |
| |
| void ConfigureInkDropForToolbar(views::Button* host) { |
| host->SetHasInkDropActionOnClick(true); |
| views::HighlightPathGenerator::Install( |
| host, std::make_unique<ToolbarButtonHighlightPathGenerator>()); |
| views::InkDrop::Get(host)->SetMode(views::InkDropHost::InkDropMode::ON); |
| views::InkDrop::Get(host)->SetVisibleOpacity(kToolbarInkDropVisibleOpacity); |
| views::InkDrop::Get(host)->SetHighlightOpacity( |
| kToolbarInkDropHighlightVisibleAlpha / float{SK_AlphaOPAQUE}); |
| views::InkDrop::Get(host)->SetBaseColorCallback( |
| base::BindRepeating(&GetToolbarInkDropBaseColor, host)); |
| |
| if (features::IsChromeRefresh2023()) { |
| ConfigureToolbarInkdropForRefresh2023(host, kColorToolbarInkDropHover, |
| kColorToolbarInkDropRipple); |
| } |
| } |
| |
| void ConfigureToolbarInkdropForRefresh2023( |
| views::View* const host, |
| const ChromeColorIds hover_color_id, |
| const ChromeColorIds ripple_color_id) { |
| CHECK(features::IsChromeRefresh2023()); |
| views::InkDrop::Get(host)->SetLayerRegion(views::LayerRegion::kAbove); |
| views::InkDrop::Get(host)->SetCreateRippleCallback(base::BindRepeating( |
| [](views::View* host, ChromeColorIds ripple_color_id) |
| -> std::unique_ptr<views::InkDropRipple> { |
| const auto* color_provider = host->GetColorProvider(); |
| const SkColor pressed_color = |
| color_provider ? color_provider->GetColor(ripple_color_id) |
| : gfx::kPlaceholderColor; |
| const float pressed_alpha = SkColorGetA(pressed_color); |
| |
| return std::make_unique<views::FloodFillInkDropRipple>( |
| views::InkDrop::Get(host), host->size(), |
| host->GetLocalBounds().CenterPoint(), |
| SkColorSetA(pressed_color, SK_AlphaOPAQUE), |
| pressed_alpha / SK_AlphaOPAQUE); |
| }, |
| host, ripple_color_id)); |
| |
| views::InkDrop::Get(host)->SetCreateHighlightCallback(base::BindRepeating( |
| [](views::View* host, ChromeColorIds hover_color_id) { |
| const auto* color_provider = host->GetColorProvider(); |
| const SkColor hover_color = |
| color_provider ? color_provider->GetColor(hover_color_id) |
| : gfx::kPlaceholderColor; |
| const float hover_alpha = SkColorGetA(hover_color); |
| |
| auto ink_drop_highlight = std::make_unique<views::InkDropHighlight>( |
| host->size(), host->height() / 2, |
| gfx::PointF(host->GetLocalBounds().CenterPoint()), |
| SkColorSetA(hover_color, SK_AlphaOPAQUE)); |
| ink_drop_highlight->set_visible_opacity(hover_alpha / SK_AlphaOPAQUE); |
| return ink_drop_highlight; |
| }, |
| host, hover_color_id)); |
| } |