holding_space_tray_icon_preview.h 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181
  1. // Copyright 2020 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #ifndef ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_TRAY_ICON_PREVIEW_H_
  5. #define ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_TRAY_ICON_PREVIEW_H_
  6. #include <memory>
  7. #include "ash/ash_export.h"
  8. #include "base/callback.h"
  9. #include "base/scoped_observation.h"
  10. #include "ui/compositor/layer_animation_observer.h"
  11. #include "ui/compositor/layer_delegate.h"
  12. #include "ui/views/view.h"
  13. #include "ui/views/view_observer.h"
  14. namespace ui {
  15. class Layer;
  16. } // namespace ui
  17. namespace ash {
  18. class HoldingSpaceItem;
  19. class ProgressIndicator;
  20. class Shelf;
  21. enum class ShelfAlignment;
  22. // Class to visually represent a single holding space item within the holding
  23. // space tray icon in the shelf. While determined to be within the icon's
  24. // viewport, each instance will manage a layer for the holding space tray icon.
  25. class ASH_EXPORT HoldingSpaceTrayIconPreview
  26. : public ui::LayerDelegate,
  27. public ui::ImplicitAnimationObserver,
  28. public views::ViewObserver {
  29. public:
  30. static constexpr char kClassName[] = "HoldingSpaceTrayIconPreview";
  31. static constexpr char kImageLayerName[] =
  32. "HoldingSpaceTrayIconPreview::Image";
  33. HoldingSpaceTrayIconPreview(Shelf* shelf,
  34. views::View* container,
  35. const HoldingSpaceItem* item);
  36. HoldingSpaceTrayIconPreview(const HoldingSpaceTrayIconPreview&) = delete;
  37. HoldingSpaceTrayIconPreview& operator=(const HoldingSpaceTrayIconPreview&) =
  38. delete;
  39. ~HoldingSpaceTrayIconPreview() override;
  40. // Animates this preview in. The item is animated at `*pending_index_`. This
  41. // will move `pending_index_` value to `index_`.
  42. // `additional_delay` - the delay that should be added on top of initial delay
  43. // when starting the animation.
  44. void AnimateIn(base::TimeDelta additional_delay);
  45. // Animates this preview out, invoking the specified closure on completion.
  46. void AnimateOut(base::OnceClosure animate_out_closure);
  47. // Shifts this preview. The item is shifted to `*pending_index_`. This
  48. // will move `pending_index_` value to `index_`.
  49. void AnimateShift(base::TimeDelta delay);
  50. // Updates the preview transform to keep relative position to the end of the
  51. // visible bounds when the icon container size changes.
  52. // Transform is updated without animation.
  53. void AdjustTransformForContainerSizeChange(const gfx::Vector2d& size_change);
  54. // Invoked when the `shelf_` has changed from `old_shelf_alignment` to
  55. // `new_shelf_alignment`.
  56. void OnShelfAlignmentChanged(ShelfAlignment old_shelf_alignment,
  57. ShelfAlignment new_shelf_alignment);
  58. // Invoked when the `shelf_` configuration has changed.
  59. void OnShelfConfigChanged();
  60. // Invoked when the theme of the parent `container_` has changed.
  61. void OnThemeChanged();
  62. ui::Layer* layer() { return layer_owner_.layer(); }
  63. const absl::optional<size_t>& index() const { return index_; }
  64. const absl::optional<size_t>& pending_index() const { return pending_index_; }
  65. void set_pending_index(size_t index) { pending_index_ = index; }
  66. private:
  67. class ImageLayerOwner;
  68. // ui::LayerDelegate:
  69. void OnPaintLayer(const ui::PaintContext& context) override;
  70. void OnDeviceScaleFactorChanged(float old_device_scale_factor,
  71. float new_device_scale_factor) override;
  72. // ui::ImplicitAnimationObserver:
  73. void OnImplicitAnimationsCompleted() override;
  74. // views::ViewObserver:
  75. void OnViewBoundsChanged(views::View* observed_view) override;
  76. void OnViewIsDeleting(views::View* observed_view) override;
  77. // Creates a layer for this preview. The layer will be owned by
  78. // `layer_owner_`. Note that a layer may be created multiple times throughout
  79. // this preview's lifetime as the preview will only have a layer while in the
  80. // viewport for the holding space tray `container_`. |initial_transform| - The
  81. // transform that should be set on the layer.
  82. void CreateLayer(const gfx::Transform& initial_transform);
  83. // Destroys the layer for this preview, if it was previously created.
  84. void DestroyLayer();
  85. // Returns whether this preview needs a layer for its current `transform_`.
  86. // Since 'layer_owner_' has a layer only while the preview appears in the
  87. // viewport for the holding space tray `container_`, this is used to gate
  88. // creation/deletion of the preview layer.
  89. bool NeedsLayer() const;
  90. // Schedules repaint of `layer()`, no-oping if it doesn't exist.
  91. void InvalidateLayer();
  92. // Updates the bounds of `layer()`.
  93. void UpdateLayerBounds();
  94. // Adjusts the specified `vector_2df` for shelf alignment and text direction.
  95. // The given `vector_2df` should specify the desired value for horizontal
  96. // alignment in LTR and will be adjusted for vertical alignment and/or RTL.
  97. void AdjustForShelfAlignmentAndTextDirection(gfx::Vector2dF* vector_2df);
  98. // The shelf whose holding space tray icon this preview belongs.
  99. Shelf* const shelf_;
  100. // The view that contains all preview layers belonging to the holding space
  101. // icon.
  102. views::View* const container_;
  103. // Owns the `ui::Layer` which paints the image representation of the
  104. // associated holding space item.
  105. std::unique_ptr<ImageLayerOwner> image_layer_owner_;
  106. // Owns the `ui::Layer` which paints indicate of progress for the associated
  107. // holding space item. NOTE: The `ui::Layer` is *not* painted if the holding
  108. // space item is not in-progress.
  109. std::unique_ptr<ProgressIndicator> progress_indicator_;
  110. // Whether or not this preview is currently using small dimensions. This is
  111. // done when in tablet mode and an app is in use.
  112. bool use_small_previews_ = false;
  113. // This is a proxy for `layer()`'s transform and represents the target
  114. // position of this preview. Because `layer()` only exists while in
  115. // `container_`'s viewport, we need to manage transform ourselves and continue
  116. // to update it even when `layer()` doesn't exist.
  117. gfx::Transform transform_;
  118. // The layer serving as the visual representation of the associated holding
  119. // space item in the holding space icon in the shelf. This only exists while
  120. // in the `container_`s viewport as determined by the current `transform_`.
  121. ui::LayerOwner layer_owner_;
  122. // Closure to invoke on completion of `AnimateOut()`. It is expected that this
  123. // preview may be deleted during invocation.
  124. base::OnceClosure animate_out_closure_;
  125. // If set, the preview index within the holding space tray icon. May be unset
  126. // during icon update transition before the preview is animated in.
  127. absl::optional<size_t> index_;
  128. // If set, the index within the holding space tray icon to which the preview
  129. // is about to move. Set while the holding space tray icon is updating.
  130. absl::optional<size_t> pending_index_;
  131. // The `layer()` for this preview is parented by `container_`'s layer. It is
  132. // necessary to observe and react to bounds changes in `container_` to keep
  133. // `layer()`'s bounds in sync.
  134. base::ScopedObservation<views::View, views::ViewObserver> container_observer_{
  135. this};
  136. base::WeakPtrFactory<HoldingSpaceTrayIconPreview> weak_factory_{this};
  137. };
  138. } // namespace ash
  139. #endif // ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_TRAY_ICON_PREVIEW_H_