1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216
|
// Copyright 2017 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_UI_VIEWS_TABS_TAB_ICON_H_
#define CHROME_BROWSER_UI_VIEWS_TABS_TAB_ICON_H_
#include "base/gtest_prod_util.h"
#include "base/memory/raw_ptr.h"
#include "base/time/time.h"
#include "chrome/browser/ui/tabs/tab_network_state.h"
#include "components/performance_manager/public/features.h"
#include "ui/base/interaction/element_tracker.h"
#include "ui/base/metadata/metadata_header_macros.h"
#include "ui/base/models/image_model.h"
#include "ui/gfx/animation/linear_animation.h"
#include "ui/gfx/animation/slide_animation.h"
#include "ui/gfx/image/image_skia.h"
#include "ui/gfx/paint_throbber.h"
#include "ui/views/animation/animation_delegate_views.h"
#include "ui/views/view.h"
namespace base {
class TickClock;
}
struct TabRendererData;
DECLARE_CUSTOM_ELEMENT_EVENT_TYPE(kDiscardAnimationFinishes);
// View that displays the favicon, sad tab, throbber, and attention indicator
// in a tab.
//
// The icon will be drawn in the upper left (upper right for RTL). Normally you
// would lay this out so the top is where you want the icon to be positioned,
// the width is TabIcon::GetIdealWidth(), and the height goes down to the
// bottom of the enclosing view (this is so the crashed tab can animate out of
// the bottom).
class TabIcon : public views::View, public views::AnimationDelegateViews {
METADATA_HEADER(TabIcon, views::View)
public:
// Attention indicator types (use as a bitmask). There is only one visual
// representation, but the state of each of these is tracked separately and
// the indicator is shown as long as one is enabled.
enum class AttentionType {
kBlockedWebContents = 1 << 0, // The WebContents is marked as blocked.
kTabWantsAttentionStatus = 1 << 1, // Tab::SetTabNeedsAttention() called.
};
TabIcon();
TabIcon(const TabIcon&) = delete;
TabIcon& operator=(const TabIcon&) = delete;
~TabIcon() override;
// Sets the tab data (network state, favicon, load progress, etc.) that are
// used to render the tab icon.
void SetData(const TabRendererData& data);
// Sets whether this tab is currently active.
void SetActiveState(bool is_active);
// Enables or disables the given attention type. The attention indicator
// will be shown as long as any of the types are enabled.
void SetAttention(AttentionType type, bool enabled);
bool GetShowingLoadingAnimation() const;
bool GetShowingAttentionIndicator() const;
bool GetShowingDiscardIndicator() const;
// Sets whether this object can paint to a layer. When the loading animation
// is running, painting to a layer saves painting overhead. But if the tab is
// being painted to some other context than the window, the layered painting
// won't work.
void SetCanPaintToLayer(bool can_paint_to_layer);
// The loading animation only steps when this function is called. The
// `elapsed_time` parameter is expected to be the same among all tabs in a tab
// strip in order to keep the throbbers in sync.
void StepLoadingAnimation(const base::TimeDelta& elapsed_time);
gfx::ImageSkia GetThemedIconForTesting() { return themed_favicon_; }
bool GetActiveStateForTesting() { return is_active_tab_; }
void EnlargeDiscardIndicatorRadius(int radius);
void SetShouldShowDiscardIndicator(bool enabled);
private:
class CrashAnimation;
friend CrashAnimation;
friend class TabTest;
FRIEND_TEST_ALL_PREFIXES(TabTest, DiscardIndicatorResponsiveness);
// views::View:
void OnPaint(gfx::Canvas* canvas) override;
views::PaintInfo::ScaleType GetPaintScaleType() const override;
void OnThemeChanged() override;
// views::AnimationDelegateViews:
void AnimationProgressed(const gfx::Animation* animation) override;
void AnimationEnded(const gfx::Animation* animation) override;
// Paints the attention indicator and `favicon_` at the given location.
void PaintAttentionIndicatorAndIcon(gfx::Canvas* canvas,
const gfx::ImageSkia& icon,
const gfx::Rect& bounds);
// Paints a dimmed and shrunken favicon surrounded by the discard ring
void PaintDiscardRingAndIcon(gfx::Canvas* canvas,
const gfx::ImageSkia& icon,
const gfx::Rect& bounds);
// Paint either the indeterimate throbber or progress indicator according to
// current tab state.
void PaintLoadingAnimation(gfx::Canvas* canvas, gfx::Rect bounds);
// Gets either the crashed icon or favicon to be rendered for the tab.
gfx::ImageSkia GetIconToPaint();
// Paint the favicon if it's available.
void MaybePaintFavicon(gfx::Canvas* canvas,
const gfx::ImageSkia& icon,
const gfx::Rect& bounds);
bool GetNonDefaultFavicon() const;
// Sets the icon.
void SetIcon(const ui::ImageModel& icon, bool should_themify_favicon);
// Start or stops the favicon fade animation for discard tabs
void SetDiscarded(bool show_discard_status);
// For certain types of tabs the loading animation is not desired so the
// caller can set inhibit_loading_animation to true. When false, the loading
// animation state will be derived from the network state.
void SetNetworkState(TabNetworkState network_state);
// Sets whether the tab should paint as crashed or not.
void SetCrashed(bool crashed);
bool GetCrashed() const;
// Creates or destroys the layer according to the current animation state and
// whether a layer can be used.
void RefreshLayer();
gfx::ImageSkia ThemeFavicon(const gfx::ImageSkia& source);
gfx::ImageSkia ThemeMonochromeFavicon(const gfx::ImageSkia& source);
// Updates the themed favicon if necessary.
void UpdateThemedFavicon();
raw_ptr<const base::TickClock> clock_;
ui::ImageModel favicon_;
bool should_themify_favicon_ = false;
TabNetworkState network_state_ = TabNetworkState::kNone;
bool crashed_ = false;
int attention_types_ = 0; // Bitmask of AttentionType.
// Value from last call to SetNetworkState. When true, the network loading
// animation will not be shown.
bool inhibit_loading_animation_ = false;
// The point in time when the tab icon was first painted in the loading state.
base::TimeTicks loading_animation_start_time_;
// When the favicon_ has theming applied to it, the themed version will be
// cached here. If this isNull(), then there is no theming and favicon_
// should be used.
gfx::ImageSkia themed_favicon_;
// May be different than is_crashed when the crashed icon is animating in.
bool should_display_crashed_favicon_ = false;
// Drawn when should_display_crashed_favicon_ is set. Created lazily.
gfx::ImageSkia crashed_icon_;
// The fraction the icon is hidden by for the crashed tab animation.
// When this is 0 it will be drawn at the normal location, and when this is 1
// it will be drawn off the bottom.
double hiding_fraction_ = 0.0;
// Animation used when the favicon grows or shrinks in size. `Show` will
// represent the favicon growing to full size, while `Hide` will represent the
// favicon shrinking which happens when the loading spinner or discard
// indicator is present.
gfx::SlideAnimation favicon_size_animation_;
// Animation used when a tab is discarded so the favicon will partially
// fade out
gfx::LinearAnimation tab_discard_animation_;
// The discard indicator will be shown only if the tab is discarded and the
// discard ring treatment pref is enabled. Keep track of both of the component
// booleans, in order to determine if the discard indicator is shown/unshown
// due to a change in the discard status or a change to the pref, because
// we don't want to animate the discard ring in the latter case.
bool is_discarded_ = false;
bool should_show_discard_indicator_ = true;
bool was_discard_indicator_shown_ = false;
// Crash animation (in place of favicon). Lazily created since most of the
// time it will be unneeded.
std::unique_ptr<CrashAnimation> crash_animation_;
bool can_paint_to_layer_ = false;
bool has_tab_renderer_data_ = false;
bool is_active_tab_ = false;
bool is_monochrome_favicon_ = false;
int increased_discard_indicator_radius_ = 0;
};
#endif // CHROME_BROWSER_UI_VIEWS_TABS_TAB_ICON_H_
|