Commit 08e64c80 authored by David Black's avatar David Black Committed by Commit Bot

Removes views (and related classes) from Assistant standalone UI.

This CL attempts to make minimal changes required to:
- Remove standalone Assistant UI classes from code base
- Clean up remnants of standalone UI from AssistantUiController.

Note that additional clean up work will be done after:
- Removing no longer needed visibility states (e.g. hidden)
- Removing no longer needed UI modes (e.g. main, mini, and web)
- Removing no longer needed caption bar class

Bug: b:148080975
Change-Id: I9ac1ac5caa9399dfd8b5463a0238221d4b8e9bb9
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2032416
Commit-Queue: David Black <dmblack@google.com>
Reviewed-by: default avatarTao Wu <wutao@chromium.org>
Reviewed-by: default avatarXiaohui Chen <xiaohuic@chromium.org>
Cr-Commit-Position: refs/heads/master@{#737569}
parent 51d693c3
...@@ -9,7 +9,6 @@ ...@@ -9,7 +9,6 @@
#include "ash/assistant/ui/assistant_view_delegate.h" #include "ash/assistant/ui/assistant_view_delegate.h"
#include "ash/assistant/ui/assistant_view_ids.h" #include "ash/assistant/ui/assistant_view_ids.h"
#include "ash/assistant/ui/base/assistant_button.h" #include "ash/assistant/ui/base/assistant_button.h"
#include "ash/assistant/ui/dialog_plate/dialog_plate.h"
#include "ash/assistant/ui/dialog_plate/mic_view.h" #include "ash/assistant/ui/dialog_plate/mic_view.h"
#include "ash/assistant/ui/logo_view/logo_view.h" #include "ash/assistant/ui/logo_view/logo_view.h"
#include "ash/assistant/util/animation_util.h" #include "ash/assistant/util/animation_util.h"
......
...@@ -73,13 +73,10 @@ void AssistantSetupController::StartOnboarding(bool relaunch, FlowType type) { ...@@ -73,13 +73,10 @@ void AssistantSetupController::StartOnboarding(bool relaunch, FlowType type) {
assistant_setup->StartAssistantOptInFlow( assistant_setup->StartAssistantOptInFlow(
type, base::BindOnce(&AssistantSetupController::OnOptInFlowFinished, type, base::BindOnce(&AssistantSetupController::OnOptInFlowFinished,
weak_ptr_factory_.GetWeakPtr())); weak_ptr_factory_.GetWeakPtr()));
} else { return;
assistant_setup->StartAssistantOptInFlow(type, base::DoNothing());
} }
// Assistant UI should be hidden while the user onboards. assistant_setup->StartAssistantOptInFlow(type, base::DoNothing());
assistant_controller_->ui_controller()->HideUi(
chromeos::assistant::mojom::AssistantExitPoint::kSetup);
} }
void AssistantSetupController::OnOptInFlowFinished(bool completed) { void AssistantSetupController::OnOptInFlowFinished(bool completed) {
......
This diff is collapsed.
...@@ -12,21 +12,12 @@ ...@@ -12,21 +12,12 @@
#include "ash/ash_export.h" #include "ash/ash_export.h"
#include "ash/assistant/assistant_controller_observer.h" #include "ash/assistant/assistant_controller_observer.h"
#include "ash/assistant/model/assistant_interaction_model_observer.h" #include "ash/assistant/model/assistant_interaction_model_observer.h"
#include "ash/assistant/model/assistant_screen_context_model_observer.h"
#include "ash/assistant/model/assistant_ui_model.h" #include "ash/assistant/model/assistant_ui_model.h"
#include "ash/assistant/model/assistant_ui_model_observer.h" #include "ash/assistant/model/assistant_ui_model_observer.h"
#include "ash/assistant/ui/assistant_view_delegate.h"
#include "ash/assistant/ui/caption_bar.h" #include "ash/assistant/ui/caption_bar.h"
#include "ash/highlighter/highlighter_controller.h" #include "ash/highlighter/highlighter_controller.h"
#include "ash/public/cpp/keyboard/keyboard_controller_observer.h"
#include "base/macros.h" #include "base/macros.h"
#include "base/optional.h" #include "base/optional.h"
#include "base/timer/timer.h"
#include "ui/display/display_observer.h"
#include "ui/events/event_observer.h"
#include "ui/gfx/geometry/rect.h"
#include "ui/views/event_monitor.h"
#include "ui/views/widget/widget_observer.h"
namespace chromeos { namespace chromeos {
namespace assistant { namespace assistant {
...@@ -36,27 +27,16 @@ class Assistant; ...@@ -36,27 +27,16 @@ class Assistant;
} // namespace assistant } // namespace assistant
} // namespace chromeos } // namespace chromeos
namespace views {
class Widget;
} // namespace views
namespace ash { namespace ash {
class AssistantContainerView;
class AssistantController; class AssistantController;
class ASH_EXPORT AssistantUiController class ASH_EXPORT AssistantUiController
: public views::WidgetObserver, : public AssistantControllerObserver,
public AssistantControllerObserver,
public AssistantInteractionModelObserver, public AssistantInteractionModelObserver,
public AssistantScreenContextModelObserver,
public AssistantUiModelObserver, public AssistantUiModelObserver,
public AssistantViewDelegateObserver,
public CaptionBarDelegate, public CaptionBarDelegate,
public HighlighterController::Observer, public HighlighterController::Observer {
public KeyboardControllerObserver,
public display::DisplayObserver,
public ui::EventObserver {
public: public:
explicit AssistantUiController(AssistantController* assistant_controller); explicit AssistantUiController(AssistantController* assistant_controller);
~AssistantUiController() override; ~AssistantUiController() override;
...@@ -71,36 +51,20 @@ class ASH_EXPORT AssistantUiController ...@@ -71,36 +51,20 @@ class ASH_EXPORT AssistantUiController
void AddModelObserver(AssistantUiModelObserver* observer); void AddModelObserver(AssistantUiModelObserver* observer);
void RemoveModelObserver(AssistantUiModelObserver* observer); void RemoveModelObserver(AssistantUiModelObserver* observer);
// views::WidgetObserver:
void OnWidgetActivationChanged(views::Widget* widget, bool active) override;
void OnWidgetVisibilityChanged(views::Widget* widget, bool visible) override;
void OnWidgetDestroying(views::Widget* widget) override;
// AssistantInteractionModelObserver: // AssistantInteractionModelObserver:
void OnInputModalityChanged(InputModality input_modality) override; void OnInputModalityChanged(InputModality input_modality) override;
void OnInteractionStateChanged(InteractionState interaction_state) override; void OnInteractionStateChanged(InteractionState interaction_state) override;
void OnMicStateChanged(MicState mic_state) override; void OnMicStateChanged(MicState mic_state) override;
// AssistantScreenContextModelObserver:
void OnScreenContextRequestStateChanged(
ScreenContextRequestState request_state) override;
// CaptionBarDelegate: // CaptionBarDelegate:
bool OnCaptionButtonPressed(AssistantButtonId id) override; bool OnCaptionButtonPressed(AssistantButtonId id) override;
// AssistantViewDelegateObserver:
void OnDialogPlateButtonPressed(AssistantButtonId id) override;
void OnMiniViewPressed() override;
// HighlighterController::Observer: // HighlighterController::Observer:
void OnHighlighterEnabledChanged(HighlighterEnabledState state) override; void OnHighlighterEnabledChanged(HighlighterEnabledState state) override;
// AssistantControllerObserver: // AssistantControllerObserver:
void OnAssistantControllerConstructed() override; void OnAssistantControllerConstructed() override;
void OnAssistantControllerDestroying() override; void OnAssistantControllerDestroying() override;
void OnDeepLinkReceived(
assistant::util::DeepLinkType type,
const std::map<std::string, std::string>& params) override;
void OnOpeningUrl(const GURL& url, void OnOpeningUrl(const GURL& url,
bool in_background, bool in_background,
bool from_server) override; bool from_server) override;
...@@ -112,24 +76,11 @@ class ASH_EXPORT AssistantUiController ...@@ -112,24 +76,11 @@ class ASH_EXPORT AssistantUiController
base::Optional<AssistantEntryPoint> entry_point, base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) override; base::Optional<AssistantExitPoint> exit_point) override;
// KeyboardControllerObserver:
void OnKeyboardOccludedBoundsChanged(const gfx::Rect& new_bounds) override;
// display::DisplayObserver:
void OnDisplayMetricsChanged(const display::Display& display,
uint32_t changed_metrics) override;
// ui::EventObserver:
void OnEvent(const ui::Event& event) override;
void ShowUi(AssistantEntryPoint entry_point); void ShowUi(AssistantEntryPoint entry_point);
void HideUi(AssistantExitPoint exit_point);
void CloseUi(AssistantExitPoint exit_point); void CloseUi(AssistantExitPoint exit_point);
void ToggleUi(base::Optional<AssistantEntryPoint> entry_point, void ToggleUi(base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point); base::Optional<AssistantExitPoint> exit_point);
AssistantContainerView* GetViewForTest();
private: private:
// Updates UI mode to |ui_mode| if specified. Otherwise UI mode is updated on // Updates UI mode to |ui_mode| if specified. Otherwise UI mode is updated on
// the basis of interaction/widget visibility state. If |due_to_interaction| // the basis of interaction/widget visibility state. If |due_to_interaction|
...@@ -137,16 +88,6 @@ class ASH_EXPORT AssistantUiController ...@@ -137,16 +88,6 @@ class ASH_EXPORT AssistantUiController
void UpdateUiMode(base::Optional<AssistantUiMode> ui_mode = base::nullopt, void UpdateUiMode(base::Optional<AssistantUiMode> ui_mode = base::nullopt,
bool due_to_interaction = false); bool due_to_interaction = false);
// Calculate and update the usable work area.
void UpdateUsableWorkArea(aura::Window* root_window);
// Constructs/resets |container_view_|.
void CreateContainerView();
void ResetContainerView();
// Adds/removes observers used for calculating usable work area as needed.
void UpdateUsableWorkAreaObservers();
AssistantController* const assistant_controller_; // Owned by Shell. AssistantController* const assistant_controller_; // Owned by Shell.
// Owned by AssistantController. // Owned by AssistantController.
...@@ -154,22 +95,6 @@ class ASH_EXPORT AssistantUiController ...@@ -154,22 +95,6 @@ class ASH_EXPORT AssistantUiController
AssistantUiModel model_; AssistantUiModel model_;
// Owned by view hierarchy.
AssistantContainerView* container_view_ = nullptr;
std::unique_ptr<views::EventMonitor> event_monitor_;
gfx::Rect keyboard_workspace_occluded_bounds_;
// When hidden, Assistant automatically closes itself to finish the previous
// session. We delay this behavior to allow the user an opportunity to resume.
base::OneShotTimer auto_close_timer_;
// Whether the UI controller is observing changes to the usable work area.
bool is_observing_usable_work_area_ = false;
base::WeakPtrFactory<AssistantUiController> weak_factory_{this};
DISALLOW_COPY_AND_ASSIGN(AssistantUiController); DISALLOW_COPY_AND_ASSIGN(AssistantUiController);
}; };
......
...@@ -132,11 +132,6 @@ void AssistantViewDelegateImpl::OnDialogPlateContentsCommitted( ...@@ -132,11 +132,6 @@ void AssistantViewDelegateImpl::OnDialogPlateContentsCommitted(
observer.OnDialogPlateContentsCommitted(text); observer.OnDialogPlateContentsCommitted(text);
} }
void AssistantViewDelegateImpl::OnMiniViewPressed() {
for (auto& observer : view_delegate_observers_)
observer.OnMiniViewPressed();
}
void AssistantViewDelegateImpl::OnNotificationButtonPressed( void AssistantViewDelegateImpl::OnNotificationButtonPressed(
const std::string& notification_id, const std::string& notification_id,
int notification_button_index) { int notification_button_index) {
......
...@@ -50,7 +50,6 @@ class AssistantViewDelegateImpl : public AssistantViewDelegate { ...@@ -50,7 +50,6 @@ class AssistantViewDelegateImpl : public AssistantViewDelegate {
bool IsTabletMode() const override; bool IsTabletMode() const override;
void OnDialogPlateButtonPressed(AssistantButtonId id) override; void OnDialogPlateButtonPressed(AssistantButtonId id) override;
void OnDialogPlateContentsCommitted(const std::string& text) override; void OnDialogPlateContentsCommitted(const std::string& text) override;
void OnMiniViewPressed() override;
void OnNotificationButtonPressed(const std::string& notification_id, void OnNotificationButtonPressed(const std::string& notification_id,
int notification_button_index) override; int notification_button_index) override;
void OnOptInButtonPressed() override; void OnOptInButtonPressed() override;
......
...@@ -40,7 +40,7 @@ enum class AssistantButtonId { ...@@ -40,7 +40,7 @@ enum class AssistantButtonId {
kMinimize = 3, kMinimize = 3,
kKeyboardInputToggle = 4, kKeyboardInputToggle = 4,
kVoiceInputToggle = 5, kVoiceInputToggle = 5,
kSettings = 6, kSettingsDeprecated = 6,
kBackInLauncherDeprecated = 7, kBackInLauncherDeprecated = 7,
kMaxValue = kBackInLauncherDeprecated kMaxValue = kBackInLauncherDeprecated
}; };
......
...@@ -32,23 +32,6 @@ component("ui") { ...@@ -32,23 +32,6 @@ component("ui") {
defines = [ "IS_ASSISTANT_UI_IMPL" ] defines = [ "IS_ASSISTANT_UI_IMPL" ]
sources = [ sources = [
"assistant_container_view.cc",
"assistant_container_view.h",
"assistant_container_view_animator.cc",
"assistant_container_view_animator.h",
"assistant_container_view_animator_legacy_impl.cc",
"assistant_container_view_animator_legacy_impl.h",
"assistant_container_view_focus_traversable.cc",
"assistant_container_view_focus_traversable.h",
"assistant_main_view.cc",
"assistant_main_view.h",
"assistant_mini_view.cc",
"assistant_mini_view.h",
"assistant_notification_overlay.cc",
"assistant_notification_overlay.h",
"assistant_notification_view.cc",
"assistant_notification_view.h",
"assistant_overlay.h",
"assistant_view_delegate.h", "assistant_view_delegate.h",
"assistant_view_ids.h", "assistant_view_ids.h",
"assistant_web_container_view.cc", "assistant_web_container_view.cc",
...@@ -65,8 +48,6 @@ component("ui") { ...@@ -65,8 +48,6 @@ component("ui") {
"base/stack_layout.h", "base/stack_layout.h",
"caption_bar.cc", "caption_bar.cc",
"caption_bar.h", "caption_bar.h",
"dialog_plate/dialog_plate.cc",
"dialog_plate/dialog_plate.h",
"dialog_plate/mic_view.cc", "dialog_plate/mic_view.cc",
"dialog_plate/mic_view.h", "dialog_plate/mic_view.h",
"logo_view/logo_view.cc", "logo_view/logo_view.cc",
......
This diff is collapsed.
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_H_
#define ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_H_
#include <memory>
#include "ash/assistant/model/assistant_ui_model_observer.h"
#include "ash/assistant/ui/assistant_container_view_focus_traversable.h"
#include "base/component_export.h"
#include "base/macros.h"
#include "base/optional.h"
#include "ui/aura/window_occlusion_tracker.h"
#include "ui/views/bubble/bubble_dialog_delegate_view.h"
namespace ash {
class AssistantContainerViewAnimator;
class AssistantMainViewDeprecated;
class AssistantMiniView;
class AssistantViewDelegate;
class AssistantWebView;
// TODO(dmblack): Remove after deprecating Assistant standalone UI.
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantContainerView
: public views::BubbleDialogDelegateView,
public AssistantUiModelObserver {
public:
explicit AssistantContainerView(AssistantViewDelegate* delegate);
~AssistantContainerView() override;
// views::BubbleDialogDelegateView:
const char* GetClassName() const override;
void AddedToWidget() override;
ax::mojom::Role GetAccessibleWindowRole() override;
base::string16 GetAccessibleWindowTitle() const override;
views::FocusTraversable* GetFocusTraversable() override;
void ChildPreferredSizeChanged(views::View* child) override;
void ViewHierarchyChanged(
const views::ViewHierarchyChangedDetails& details) override;
void SizeToContents() override;
void OnBeforeBubbleWidgetInit(views::Widget::InitParams* params,
views::Widget* widget) const override;
views::ClientView* CreateClientView(views::Widget* widget) override;
void Init() override;
void RequestFocus() override;
// AssistantUiModelObserver:
void OnUiModeChanged(AssistantUiMode ui_mode,
bool due_to_interaction) override;
void OnUsableWorkAreaChanged(const gfx::Rect& usable_work_area) override;
// Returns the first focusable view or nullptr to defer to views::FocusSearch.
views::View* FindFirstFocusableView();
// Returns background color.
SkColor GetBackgroundColor() const;
// Returns/sets corner radius.
int GetCornerRadius() const;
void SetCornerRadius(int corner_radius);
// Returns the layer for the non-client view.
ui::Layer* GetNonClientViewLayer();
// Invoke to open the specified |url| in Assistant UI.
// Note that this API should only be used when Assistant is in kWebUi mode.
void OpenUrl(const GURL& url);
private:
// Update anchor rect with respect to the current usable work area.
void UpdateAnchor();
AssistantViewDelegate* const delegate_;
AssistantMainViewDeprecated*
assistant_main_view_; // Owned by view hierarchy.
AssistantMiniView* assistant_mini_view_; // Owned by view hierarchy.
AssistantWebView* assistant_web_view_; // Owned by view hierarchy.
std::unique_ptr<AssistantContainerViewAnimator> animator_;
AssistantContainerViewFocusTraversable focus_traversable_;
base::Optional<aura::WindowOcclusionTracker::ScopedExclude>
occlusion_excluder_;
DISALLOW_COPY_AND_ASSIGN(AssistantContainerView);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_H_
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/assistant/ui/assistant_container_view_animator.h"
#include "ash/assistant/ui/assistant_container_view.h"
#include "ash/assistant/ui/assistant_container_view_animator_legacy_impl.h"
#include "ash/assistant/ui/assistant_view_delegate.h"
namespace ash {
AssistantContainerViewAnimator::AssistantContainerViewAnimator(
AssistantViewDelegate* delegate,
AssistantContainerView* assistant_container_view)
: delegate_(delegate), assistant_container_view_(assistant_container_view) {
static_cast<views::View*>(assistant_container_view_)->AddObserver(this);
delegate_->AddUiModelObserver(this);
}
AssistantContainerViewAnimator::~AssistantContainerViewAnimator() {
delegate_->RemoveUiModelObserver(this);
static_cast<views::View*>(assistant_container_view_)->RemoveObserver(this);
}
// static
std::unique_ptr<AssistantContainerViewAnimator>
AssistantContainerViewAnimator::Create(
AssistantViewDelegate* delegate,
AssistantContainerView* assistant_container_view) {
// TODO(wutao): Conditionally provide an alternative implementation.
return std::make_unique<AssistantContainerViewAnimatorLegacyImpl>(
delegate, assistant_container_view);
}
void AssistantContainerViewAnimator::Init() {}
void AssistantContainerViewAnimator::OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) {}
void AssistantContainerViewAnimator::OnBoundsChanged() {}
void AssistantContainerViewAnimator::OnPreferredSizeChanged() {
if (assistant_container_view_->GetWidget())
assistant_container_view_->SizeToContents();
}
void AssistantContainerViewAnimator::OnViewBoundsChanged(views::View* view) {
OnBoundsChanged();
}
void AssistantContainerViewAnimator::OnViewPreferredSizeChanged(
views::View* view) {
if (!assistant_container_view_->GetWidget())
return;
const gfx::Size preferred_size =
assistant_container_view_->GetPreferredSize();
// We currently over-trigger OnViewPreferredSizeChanged. Until that can be
// addressed we filter out events that are superfluous.
if (preferred_size == last_preferred_size_)
return;
last_preferred_size_ = preferred_size;
OnPreferredSizeChanged();
}
} // namespace ash
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_ANIMATOR_H_
#define ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_ANIMATOR_H_
#include <memory>
#include "ash/assistant/model/assistant_ui_model_observer.h"
#include "base/component_export.h"
#include "base/macros.h"
#include "ui/gfx/geometry/size.h"
#include "ui/views/view_observer.h"
namespace views {
class View;
} // namespace views
namespace ash {
class AssistantContainerView;
class AssistantViewDelegate;
// The AssistantContainerViewAnimator is the class responsible for smoothly
// animating bound changes for the AssistantContainerView.
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantContainerViewAnimator
: public views::ViewObserver,
public AssistantUiModelObserver {
public:
~AssistantContainerViewAnimator() override;
// Returns a newly created instance of an AssistantContainerViewAnimator.
static std::unique_ptr<AssistantContainerViewAnimator> Create(
AssistantViewDelegate* delegate,
AssistantContainerView* assistant_container_view);
// Invoked when AssistantContainerView has been fully constructed to give the
// AssistantContainerViewAnimator an opportunity to perform initialization.
virtual void Init();
// AssistantUiModelObserver:
void OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) override;
protected:
AssistantContainerViewAnimator(
AssistantViewDelegate* delegate,
AssistantContainerView* assistant_container_view);
// Invoked when AssistantContainerView's bounds have changed.
virtual void OnBoundsChanged();
// Invoked when AssistantContainerView's preferred size has changed.
virtual void OnPreferredSizeChanged();
AssistantViewDelegate* const delegate_;
// Owned by view hierarchy.
AssistantContainerView* const assistant_container_view_;
private:
// views::Observer:
void OnViewBoundsChanged(views::View* view) override;
void OnViewPreferredSizeChanged(views::View* view) override;
// Cached value of AssistantContainerView's last preferred size. We currently
// over-trigger the OnViewPreferredSizeChanged event so this is used to filter
// out superfluous calls.
gfx::Size last_preferred_size_;
DISALLOW_COPY_AND_ASSIGN(AssistantContainerViewAnimator);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_ANIMATOR_H_
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/assistant/ui/assistant_container_view_animator_legacy_impl.h"
#include <algorithm>
#include "ash/assistant/ui/assistant_container_view.h"
#include "ash/assistant/ui/assistant_ui_constants.h"
#include "ash/assistant/ui/assistant_view_delegate.h"
#include "ash/assistant/util/animation_util.h"
#include "ash/assistant/util/assistant_util.h"
#include "base/metrics/histogram_macros.h"
#include "ui/gfx/animation/slide_animation.h"
#include "ui/views/animation/ink_drop_painted_layer_delegates.h"
#include "ui/wm/core/shadow_types.h"
namespace ash {
namespace {
// Animation.
constexpr auto kAnimationDuration = base::TimeDelta::FromMilliseconds(250);
// Helpers ---------------------------------------------------------------------
int GetCompositorFrameNumber(ui::Layer* layer) {
ui::Compositor* compositor = layer->GetCompositor();
return compositor ? compositor->activated_frame_count() : 0;
}
float GetCompositorRefreshRate(ui::Layer* layer) {
ui::Compositor* compositor = layer->GetCompositor();
return compositor ? compositor->refresh_rate() : 60.0f;
}
} // namespace
// AssistantContainerViewAnimatorLegacyImpl ------------------------------------
AssistantContainerViewAnimatorLegacyImpl::
AssistantContainerViewAnimatorLegacyImpl(
AssistantViewDelegate* delegate,
AssistantContainerView* assistant_container_view)
: AssistantContainerViewAnimator(delegate, assistant_container_view),
views::AnimationDelegateViews(assistant_container_view) {}
AssistantContainerViewAnimatorLegacyImpl::
~AssistantContainerViewAnimatorLegacyImpl() = default;
void AssistantContainerViewAnimatorLegacyImpl::Init() {
// Initialize background layer.
background_layer_.SetFillsBoundsOpaquely(false);
UpdateBackground();
// Add background layer to the non-client view layer.
assistant_container_view_->GetNonClientViewLayer()->Add(&background_layer_);
// The AssistantContainerView layer masks to bounds to ensure clipping of
// child layers during animation.
assistant_container_view_->layer()->SetMasksToBounds(true);
}
void AssistantContainerViewAnimatorLegacyImpl::OnBoundsChanged() {
UpdateBackground();
assistant_container_view_->SchedulePaint();
}
void AssistantContainerViewAnimatorLegacyImpl::OnPreferredSizeChanged() {
if (!assistant_container_view_->GetWidget())
return;
end_radius_ = delegate_->GetUiModel()->ui_mode() == AssistantUiMode::kMiniUi
? kMiniUiCornerRadiusDip
: kCornerRadiusDip;
const bool visible =
delegate_->GetUiModel()->visibility() == AssistantVisibility::kVisible;
// When visible, size changes are animated.
if (visible) {
animation_ = std::make_unique<gfx::SlideAnimation>(this);
animation_->SetSlideDuration(kAnimationDuration);
// Cache start and end animation values.
start_size_ = assistant_container_view_->size();
end_size_ = assistant_container_view_->GetPreferredSize();
start_radius_ = assistant_container_view_->GetCornerRadius();
// Cache start frame number for measuring animation smoothness.
start_frame_number_ =
GetCompositorFrameNumber(assistant_container_view_->layer());
// Start animation.
animation_->Show();
return;
}
// Clear any existing animation.
animation_.reset();
// Update corner radius and resize without animation.
assistant_container_view_->SetCornerRadius(end_radius_);
assistant_container_view_->SizeToContents();
}
void AssistantContainerViewAnimatorLegacyImpl::OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) {
if (!assistant::util::IsStartingSession(new_visibility, old_visibility))
return;
// Start the container open animation on height growth and fade-in when
// Assistant starts a new session.
using assistant::util::CreateLayerAnimationSequence;
using assistant::util::CreateOpacityElement;
animation_.reset();
// Animate the fade in with a delay.
assistant_container_view_->GetNonClientViewLayer()->SetOpacity(0.f);
assistant_container_view_->GetNonClientViewLayer()
->GetAnimator()
->StartAnimation(CreateLayerAnimationSequence(
ui::LayerAnimationElement::CreatePauseElement(
ui::LayerAnimationElement::AnimatableProperty::OPACITY,
base::TimeDelta::FromMilliseconds(17)),
CreateOpacityElement(1.0f, kAnimationDuration,
gfx::Tween::Type::FAST_OUT_SLOW_IN_2)));
// Set the initial animation value of bound with height equals to 0.
gfx::Rect current_bounds = assistant_container_view_->bounds();
assistant_container_view_->SetBounds(
current_bounds.x(), current_bounds.y() + current_bounds.height(),
current_bounds.width(), 0);
// Animate the height growth.
OnPreferredSizeChanged();
}
void AssistantContainerViewAnimatorLegacyImpl::AnimationProgressed(
const gfx::Animation* animation) {
if (!assistant_container_view_->GetWidget())
return;
// Retrieve current bounds.
gfx::Rect bounds =
assistant_container_view_->GetWidget()->GetWindowBoundsInScreen();
// Our view is horizontally centered and bottom aligned. As such, we should
// retain the same |center_x| and |bottom| positions after resizing.
const int bottom = bounds.bottom();
const int center_x = bounds.CenterPoint().x();
// Interpolate size at our current animation value.
bounds.set_size(gfx::Tween::SizeValueBetween(animation->GetCurrentValue(),
start_size_, end_size_));
// Maintain original |center_x| and |bottom| positions.
bounds.set_x(std::max(center_x - (bounds.width() / 2), 0));
bounds.set_y(bottom - bounds.height());
// Interpolate the correct corner radius.
const int corner_radius = gfx::Tween::LinearIntValueBetween(
animation->GetCurrentValue(), start_radius_, end_radius_);
// Update corner radius and bounds.
assistant_container_view_->SetCornerRadius(corner_radius);
assistant_container_view_->GetWidget()->SetBounds(bounds);
}
void AssistantContainerViewAnimatorLegacyImpl::AnimationEnded(
const gfx::Animation* animation) {
const int ideal_frames =
GetCompositorRefreshRate(assistant_container_view_->layer()) *
kAnimationDuration.InSecondsF();
const int actual_frames =
GetCompositorFrameNumber(assistant_container_view_->layer()) -
start_frame_number_;
if (actual_frames <= 0)
return;
// The |actual_frames| could be |ideal_frames| + 1. The reason could be that
// the animation timer is running with interval of 0.016666 sec, which could
// animate one more frame than expected due to rounding error.
const int smoothness = std::min(100 * actual_frames / ideal_frames, 100);
UMA_HISTOGRAM_PERCENTAGE("Assistant.ContainerView.Resize.AnimationSmoothness",
smoothness);
}
void AssistantContainerViewAnimatorLegacyImpl::UpdateBackground() {
gfx::ShadowValues shadow_values =
gfx::ShadowValue::MakeMdShadowValues(wm::kShadowElevationActiveWindow);
shadow_delegate_ = std::make_unique<views::BorderShadowLayerDelegate>(
shadow_values, assistant_container_view_->GetLocalBounds(),
assistant_container_view_->GetBackgroundColor(),
assistant_container_view_->GetCornerRadius());
background_layer_.set_delegate(shadow_delegate_.get());
background_layer_.SetBounds(
gfx::ToEnclosingRect(shadow_delegate_->GetPaintedBounds()));
}
} // namespace ash
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_ANIMATOR_LEGACY_IMPL_H_
#define ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_ANIMATOR_LEGACY_IMPL_H_
#include <memory>
#include "ash/assistant/ui/assistant_container_view_animator.h"
#include "base/component_export.h"
#include "base/macros.h"
#include "ui/compositor/layer.h"
#include "ui/gfx/geometry/size.h"
#include "ui/views/animation/animation_delegate_views.h"
namespace gfx {
class SlideAnimation;
} // namespace gfx
namespace views {
class BorderShadowLayerDelegate;
} // namespace views
namespace ash {
// The AssistantContainerViewAnimatorLegacyImpl is an implementation of
// AssistantContainerViewAnimator that performs rebounding of
// AssistantContainerView at each frame in its resize animation. As such, it is
// not very performant and we are working to deprecate this implementation.
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantContainerViewAnimatorLegacyImpl
: public AssistantContainerViewAnimator,
public views::AnimationDelegateViews {
public:
AssistantContainerViewAnimatorLegacyImpl(
AssistantViewDelegate* delegate,
AssistantContainerView* assistant_container_view);
~AssistantContainerViewAnimatorLegacyImpl() override;
// AssistantContainerViewAnimator:
void Init() override;
void OnBoundsChanged() override;
void OnPreferredSizeChanged() override;
void OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) override;
// views::AnimationDelegatViews:
void AnimationProgressed(const gfx::Animation* animation) override;
void AnimationEnded(const gfx::Animation* animation) override;
private:
void UpdateBackground();
// Background/shadow.
ui::Layer background_layer_;
std::unique_ptr<views::BorderShadowLayerDelegate> shadow_delegate_;
// Animation.
std::unique_ptr<gfx::SlideAnimation> animation_;
gfx::Size start_size_;
gfx::Size end_size_;
int start_radius_ = 0;
int end_radius_ = 0;
int start_frame_number_ = 0;
DISALLOW_COPY_AND_ASSIGN(AssistantContainerViewAnimatorLegacyImpl);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_ANIMATOR_LEGACY_IMPL_H_
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/assistant/ui/assistant_container_view_focus_traversable.h"
#include "ash/assistant/ui/assistant_container_view.h"
namespace ash {
// AssistantContainerViewFocusSearch -------------------------------------------
AssistantContainerViewFocusSearch::AssistantContainerViewFocusSearch(
AssistantContainerView* assistant_container_view)
: views::FocusSearch(/*root=*/assistant_container_view,
/*cycle=*/true,
/*accessibility_mode=*/false),
assistant_container_view_(assistant_container_view) {}
AssistantContainerViewFocusSearch::~AssistantContainerViewFocusSearch() =
default;
views::View* AssistantContainerViewFocusSearch::FindNextFocusableView(
views::View* starting_from,
SearchDirection search_direction,
TraversalDirection traversal_direction,
StartingViewPolicy check_starting_view,
AnchoredDialogPolicy can_go_into_anchored_dialog,
views::FocusTraversable** focus_traversable,
views::View** focus_traversable_view) {
// NOTE: This FocusTraversable should only be used whenever the container does
// not have anything currently focused *and* it has a reasonable default focus
// override via |FindFirstFocusableView()|. This is ensured by
// |AssistantContainerView::GetFocusTraversable()|.
DCHECK(!assistant_container_view_->GetFocusManager() ||
!assistant_container_view_->GetFocusManager()->GetFocusedView());
auto* next_focusable_view =
assistant_container_view_->FindFirstFocusableView();
DCHECK(next_focusable_view);
return next_focusable_view;
}
// AssistantContainerViewFocusTraversable --------------------------------------
AssistantContainerViewFocusTraversable::AssistantContainerViewFocusTraversable(
AssistantContainerView* assistant_container_view)
: assistant_container_view_(assistant_container_view),
focus_search_(assistant_container_view) {}
AssistantContainerViewFocusTraversable::
~AssistantContainerViewFocusTraversable() = default;
views::FocusSearch* AssistantContainerViewFocusTraversable::GetFocusSearch() {
return &focus_search_;
}
views::FocusTraversable*
AssistantContainerViewFocusTraversable::GetFocusTraversableParent() {
return nullptr;
}
views::View*
AssistantContainerViewFocusTraversable::GetFocusTraversableParentView() {
return assistant_container_view_;
}
} // namespace ash
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_FOCUS_TRAVERSABLE_H_
#define ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_FOCUS_TRAVERSABLE_H_
#include <memory>
#include "base/component_export.h"
#include "base/macros.h"
#include "ui/views/focus/focus_manager.h"
#include "ui/views/focus/focus_search.h"
namespace ash {
class AssistantContainerView;
// AssistantContainerViewFocusSearch -------------------------------------------
// AssistantContainerViewFocusSearch is an implementation of views::FocusSearch
// belonging to AssistantContainerViewFocusTraversable. When there is no
// currently focused view, it delegates to AssistantContainerView to find the
// first focusable view for the given UI state.
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantContainerViewFocusSearch
: public views::FocusSearch {
public:
explicit AssistantContainerViewFocusSearch(
AssistantContainerView* assistant_container_view);
~AssistantContainerViewFocusSearch() override;
// views::FocusSearch:
views::View* FindNextFocusableView(
views::View* starting_from,
SearchDirection search_direction,
TraversalDirection traversal_direction,
StartingViewPolicy check_starting_view,
AnchoredDialogPolicy can_go_into_anchored_dialog,
views::FocusTraversable** focus_traversable,
views::View** focus_traversable_view) override;
private:
AssistantContainerView* const assistant_container_view_;
DISALLOW_COPY_AND_ASSIGN(AssistantContainerViewFocusSearch);
};
// AssistantContainerViewFocusTraversable --------------------------------------
// AssistantContainerViewFocusTraversable is an implementation of
// views::FocusTraversable belonging to AssistantContainerView. It wraps an
// AssistantContainerViewFocusSearch instance which allows us to override focus
// behavior as needed.
class AssistantContainerViewFocusTraversable : public views::FocusTraversable {
public:
explicit AssistantContainerViewFocusTraversable(
AssistantContainerView* assistant_container_view);
~AssistantContainerViewFocusTraversable() override;
// views::FocusTraversable:
views::FocusSearch* GetFocusSearch() override;
views::FocusTraversable* GetFocusTraversableParent() override;
views::View* GetFocusTraversableParentView() override;
private:
AssistantContainerView* const assistant_container_view_;
AssistantContainerViewFocusSearch focus_search_;
DISALLOW_COPY_AND_ASSIGN(AssistantContainerViewFocusTraversable);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_CONTAINER_VIEW_FOCUS_TRAVERSABLE_H_
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/assistant/ui/assistant_main_view.h"
#include <algorithm>
#include <utility>
#include "ash/assistant/model/assistant_interaction_model.h"
#include "ash/assistant/model/assistant_ui_model.h"
#include "ash/assistant/ui/assistant_notification_overlay.h"
#include "ash/assistant/ui/assistant_ui_constants.h"
#include "ash/assistant/ui/assistant_view_delegate.h"
#include "ash/assistant/ui/caption_bar.h"
#include "ash/assistant/ui/dialog_plate/dialog_plate.h"
#include "ash/assistant/ui/main_stage/assistant_main_stage.h"
#include "ash/assistant/util/animation_util.h"
#include "ash/assistant/util/assistant_util.h"
#include "base/time/time.h"
#include "chromeos/services/assistant/public/features.h"
#include "ui/aura/window.h"
#include "ui/compositor/layer_animation_element.h"
#include "ui/compositor/layer_animator.h"
#include "ui/display/display.h"
#include "ui/display/screen.h"
#include "ui/views/layout/box_layout.h"
#include "ui/views/widget/widget.h"
namespace ash {
namespace {
// Appearance.
constexpr int kMinHeightDip = 200;
// Caption bar animation.
constexpr base::TimeDelta kCaptionBarAnimationFadeInDelay =
base::TimeDelta::FromMilliseconds(283);
constexpr base::TimeDelta kCaptionBarAnimationFadeInDuration =
base::TimeDelta::FromMilliseconds(167);
// Dialog plate animation.
constexpr base::TimeDelta kDialogPlateAnimationFadeInDelay =
base::TimeDelta::FromMilliseconds(283);
constexpr base::TimeDelta kDialogPlateAnimationFadeInDuration =
base::TimeDelta::FromMilliseconds(167);
} // namespace
AssistantMainViewDeprecated::AssistantMainViewDeprecated(
AssistantViewDelegate* delegate)
: delegate_(delegate), min_height_dip_(kMinHeightDip) {
InitLayout();
// Set delegate/observers.
caption_bar_->set_delegate(delegate_->GetCaptionBarDelegate());
// The AssistantViewDelegate should outlive AssistantMainView.
delegate_->AddUiModelObserver(this);
}
AssistantMainViewDeprecated::~AssistantMainViewDeprecated() {
delegate_->RemoveUiModelObserver(this);
}
const char* AssistantMainViewDeprecated::GetClassName() const {
return "AssistantMainView";
}
gfx::Size AssistantMainViewDeprecated::CalculatePreferredSize() const {
return gfx::Size(kPreferredWidthDip, GetHeightForWidth(kPreferredWidthDip));
}
int AssistantMainViewDeprecated::GetHeightForWidth(int width) const {
// |min_height_dip_| <= |height| <= |kMaxHeightDip|.
int height = views::View::GetHeightForWidth(width);
height = std::min(height, kMaxHeightDip);
height = std::max(height, min_height_dip_);
// |height| should not exceed the height of the usable work area.
// |height| >= |kMinHeightDip|.
gfx::Rect usable_work_area = delegate_->GetUiModel()->usable_work_area();
if (height > usable_work_area.height())
height = std::max(kMinHeightDip, usable_work_area.height());
return height;
}
void AssistantMainViewDeprecated::OnBoundsChanged(
const gfx::Rect& prev_bounds) {
// Until Assistant UI is hidden, the view may grow in height but not shrink.
min_height_dip_ = std::max(min_height_dip_, height());
}
void AssistantMainViewDeprecated::VisibilityChanged(views::View* starting_from,
bool visible) {
// Overlays behave like children of AssistantMainView so they should only be
// visible while AssistantMainView is visible.
for (std::unique_ptr<AssistantOverlay>& overlay : overlays_)
overlay->SetVisible(visible);
}
void AssistantMainViewDeprecated::ChildPreferredSizeChanged(
views::View* child) {
PreferredSizeChanged();
// Even though the preferred size for |main_stage_| may change, its bounds
// may not actually change due to height restrictions imposed by its parent.
// For this reason, we need to explicitly trigger a layout pass so that the
// children of |main_stage_| are properly updated.
if (child == main_stage_) {
Layout();
SchedulePaint();
}
}
void AssistantMainViewDeprecated::ChildVisibilityChanged(views::View* child) {
PreferredSizeChanged();
}
views::View* AssistantMainViewDeprecated::FindFirstFocusableView() {
// In those instances in which we want to override views::FocusSearch
// behavior, DialogPlate will identify the first focusable view.
return dialog_plate_->FindFirstFocusableView();
}
std::vector<AssistantOverlay*> AssistantMainViewDeprecated::GetOverlays() {
std::vector<AssistantOverlay*> overlays;
for (std::unique_ptr<AssistantOverlay>& overlay : overlays_)
overlays.push_back(overlay.get());
return overlays;
}
void AssistantMainViewDeprecated::InitLayout() {
views::BoxLayout* layout_manager =
SetLayoutManager(std::make_unique<views::BoxLayout>(
views::BoxLayout::Orientation::kVertical));
// Caption bar.
caption_bar_ = new CaptionBar();
caption_bar_->SetButtonVisible(AssistantButtonId::kBack, false);
// The caption bar will be animated on its own layer.
caption_bar_->SetPaintToLayer();
caption_bar_->layer()->SetFillsBoundsOpaquely(false);
AddChildView(caption_bar_);
// Main stage.
main_stage_ = new AssistantMainStage(delegate_);
AddChildView(main_stage_);
layout_manager->SetFlexForView(main_stage_, 1);
// Dialog plate.
dialog_plate_ = new DialogPlate(delegate_);
// The dialog plate will be animated on its own layer.
dialog_plate_->SetPaintToLayer();
dialog_plate_->layer()->SetFillsBoundsOpaquely(false);
AddChildView(dialog_plate_);
// Notification overlay.
if (chromeos::assistant::features::IsInAssistantNotificationsEnabled()) {
auto notification_overlay =
std::make_unique<AssistantNotificationOverlay>(delegate_);
notification_overlay->set_owned_by_client();
overlays_.push_back(std::move(notification_overlay));
}
}
void AssistantMainViewDeprecated::OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) {
if (assistant::util::IsStartingSession(new_visibility, old_visibility)) {
// When Assistant is starting a new session, we animate in the appearance of
// the caption bar and dialog plate.
using assistant::util::CreateLayerAnimationSequence;
using assistant::util::CreateOpacityElement;
// Animate the caption bar from 0% to 100% opacity with delay.
caption_bar_->layer()->SetOpacity(0.f);
caption_bar_->layer()->GetAnimator()->StartAnimation(
CreateLayerAnimationSequence(
ui::LayerAnimationElement::CreatePauseElement(
ui::LayerAnimationElement::AnimatableProperty::OPACITY,
kCaptionBarAnimationFadeInDelay),
CreateOpacityElement(1.f, kCaptionBarAnimationFadeInDuration)));
// Animate the dialog plate from 0% to 100% opacity with delay.
dialog_plate_->layer()->SetOpacity(0.f);
dialog_plate_->layer()->GetAnimator()->StartAnimation(
CreateLayerAnimationSequence(
ui::LayerAnimationElement::CreatePauseElement(
ui::LayerAnimationElement::AnimatableProperty::OPACITY,
kDialogPlateAnimationFadeInDelay),
CreateOpacityElement(1.f, kDialogPlateAnimationFadeInDuration)));
return;
}
if (assistant::util::IsFinishingSession(new_visibility)) {
// When Assistant is finishing a session, we need to reset view state.
min_height_dip_ = kMinHeightDip;
PreferredSizeChanged();
}
}
void AssistantMainViewDeprecated::RequestFocus() {
dialog_plate_->RequestFocus();
}
} // namespace ash
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_MAIN_VIEW_H_
#define ASH_ASSISTANT_UI_ASSISTANT_MAIN_VIEW_H_
#include <memory>
#include <vector>
#include "ash/assistant/model/assistant_ui_model_observer.h"
#include "base/component_export.h"
#include "base/macros.h"
#include "ui/views/view.h"
namespace ash {
class AssistantMainStage;
class AssistantOverlay;
class AssistantViewDelegate;
class CaptionBar;
class DialogPlate;
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantMainViewDeprecated
: public views::View,
public AssistantUiModelObserver {
public:
explicit AssistantMainViewDeprecated(AssistantViewDelegate* delegate);
~AssistantMainViewDeprecated() override;
// views::View:
const char* GetClassName() const override;
gfx::Size CalculatePreferredSize() const override;
int GetHeightForWidth(int width) const override;
void ChildPreferredSizeChanged(views::View* child) override;
void ChildVisibilityChanged(views::View* child) override;
void OnBoundsChanged(const gfx::Rect& prev_bounds) override;
void VisibilityChanged(views::View* starting_from, bool visible) override;
void RequestFocus() override;
// AssistantUiModelObserver:
void OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) override;
// Returns the first focusable view or nullptr to defer to views::FocusSearch.
views::View* FindFirstFocusableView();
// Returns the overlays that behave as pseudo-children of AssistantMainView.
std::vector<AssistantOverlay*> GetOverlays();
private:
void InitLayout();
AssistantViewDelegate* const delegate_;
CaptionBar* caption_bar_; // Owned by view hierarchy.
DialogPlate* dialog_plate_; // Owned by view hierarchy.
AssistantMainStage* main_stage_; // Owned by view hierarchy.
// Overlays behave as pseudo-children of AssistantMainView. They paint to a
// higher lever in the layer tree so they are visible over the top of
// Assistant cards.
std::vector<std::unique_ptr<AssistantOverlay>> overlays_;
int min_height_dip_;
DISALLOW_COPY_AND_ASSIGN(AssistantMainViewDeprecated);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_MAIN_VIEW_H_
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/assistant/ui/assistant_mini_view.h"
#include <algorithm>
#include <memory>
#include "ash/assistant/model/assistant_query.h"
#include "ash/assistant/ui/assistant_ui_constants.h"
#include "ash/assistant/ui/assistant_view_delegate.h"
#include "ash/assistant/ui/logo_view/logo_view.h"
#include "ash/assistant/util/assistant_util.h"
#include "ash/strings/grit/ash_strings.h"
#include "base/strings/utf_string_conversions.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/views/background.h"
#include "ui/views/controls/label.h"
#include "ui/views/layout/box_layout.h"
namespace ash {
namespace {
// Appearance.
constexpr int kIconSizeDip = 24;
constexpr int kLineHeightDip = 24;
constexpr int kMaxWidthDip = 452;
constexpr int kPaddingLeftDip = 12;
constexpr int kPaddingRightDip = 24;
constexpr int kPreferredHeightDip = 48;
} // namespace
AssistantMiniView::AssistantMiniView(AssistantViewDelegate* delegate)
: views::Button(this), delegate_(delegate), label_(new views::Label()) {
InitLayout();
// The AssistantViewDelegate should outlive AssistantMiniView.
delegate_->AddInteractionModelObserver(this);
delegate_->AddUiModelObserver(this);
}
AssistantMiniView::~AssistantMiniView() {
delegate_->RemoveUiModelObserver(this);
delegate_->RemoveInteractionModelObserver(this);
}
const char* AssistantMiniView::GetClassName() const {
return "AssistantMiniView";
}
gfx::Size AssistantMiniView::CalculatePreferredSize() const {
const int preferred_width =
std::min(views::View::CalculatePreferredSize().width(), kMaxWidthDip);
return gfx::Size(preferred_width, GetHeightForWidth(preferred_width));
}
int AssistantMiniView::GetHeightForWidth(int width) const {
return kPreferredHeightDip;
}
void AssistantMiniView::ChildPreferredSizeChanged(views::View* child) {
PreferredSizeChanged();
}
void AssistantMiniView::InitLayout() {
views::BoxLayout* layout_manager =
SetLayoutManager(std::make_unique<views::BoxLayout>(
views::BoxLayout::Orientation::kHorizontal,
gfx::Insets(0, kPaddingLeftDip, 0, kPaddingRightDip),
2 * kSpacingDip));
layout_manager->set_cross_axis_alignment(
views::BoxLayout::CrossAxisAlignment::kCenter);
// Molecule icon.
std::unique_ptr<LogoView> molecule_icon = LogoView::Create();
molecule_icon->SetPreferredSize(gfx::Size(kIconSizeDip, kIconSizeDip));
molecule_icon->SetState(LogoView::State::kMoleculeWavy,
/*animate=*/false);
AddChildView(std::move(molecule_icon));
// Label.
label_->SetAutoColorReadabilityEnabled(false);
label_->SetEnabledColor(kTextColorPrimary);
label_->SetFontList(assistant::ui::GetDefaultFontList()
.DeriveWithSizeDelta(1)
.DeriveWithWeight(gfx::Font::Weight::MEDIUM));
label_->SetHorizontalAlignment(gfx::HorizontalAlignment::ALIGN_LEFT);
label_->SetLineHeight(kLineHeightDip);
label_->SetBackground(views::CreateSolidBackground(SK_ColorWHITE));
AddChildView(label_);
// Initialize the prompt.
UpdatePrompt();
}
void AssistantMiniView::ButtonPressed(views::Button* sender,
const ui::Event& event) {
delegate_->OnMiniViewPressed();
}
void AssistantMiniView::OnInputModalityChanged(InputModality input_modality) {
UpdatePrompt();
}
void AssistantMiniView::OnResponseChanged(
const scoped_refptr<AssistantResponse>& response) {
// When a response changes, the committed query becomes active. We'll cache
// the text for that query to use as our prompt when not using the stylus.
const AssistantQuery& committed_query =
delegate_->GetInteractionModel()->committed_query();
switch (committed_query.type()) {
case AssistantQueryType::kText: {
const AssistantTextQuery& text_query =
static_cast<const AssistantTextQuery&>(committed_query);
last_active_query_ = text_query.text();
break;
}
case AssistantQueryType::kVoice: {
const AssistantVoiceQuery& voice_query =
static_cast<const AssistantVoiceQuery&>(committed_query);
last_active_query_ = voice_query.high_confidence_speech() +
voice_query.low_confidence_speech();
break;
}
case AssistantQueryType::kNull:
// It shouldn't be possible to commit a query of type kNull.
NOTREACHED();
break;
}
UpdatePrompt();
}
void AssistantMiniView::OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) {
if (!assistant::util::IsFinishingSession(new_visibility))
return;
// When Assistant is finishing a session, we need to reset view state.
last_active_query_.reset();
UpdatePrompt();
}
void AssistantMiniView::UpdatePrompt() {
InputModality input_modality =
delegate_->GetInteractionModel()->input_modality();
switch (input_modality) {
case InputModality::kStylus:
label_->SetText(
l10n_util::GetStringUTF16(IDS_ASH_ASSISTANT_PROMPT_STYLUS));
break;
case InputModality::kKeyboard:
case InputModality::kVoice:
// If we've cached an active query, we'll use that as our prompt provided
// it is non-empty. If not, we fall back to our default prompt string.
// TODO(dmblack): Once b/112000321 is fixed we should remove empty query
// handling as that should only occur due to an invalid interaction state.
label_->SetText(
last_active_query_.has_value() && !last_active_query_.value().empty()
? base::UTF8ToUTF16(last_active_query_.value())
: l10n_util::GetStringUTF16(IDS_ASH_ASSISTANT_PROMPT_DEFAULT));
break;
}
}
} // namespace ash
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_MINI_VIEW_H_
#define ASH_ASSISTANT_UI_ASSISTANT_MINI_VIEW_H_
#include <memory>
#include <string>
#include "ash/assistant/model/assistant_interaction_model_observer.h"
#include "ash/assistant/model/assistant_ui_model_observer.h"
#include "base/component_export.h"
#include "base/macros.h"
#include "base/memory/scoped_refptr.h"
#include "base/optional.h"
#include "ui/views/controls/button/button.h"
namespace views {
class Label;
} // namespace views
namespace ash {
class AssistantViewDelegate;
// AssistantMiniView -----------------------------------------------------------
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantMiniView
: public views::Button,
public views::ButtonListener,
public AssistantInteractionModelObserver,
public AssistantUiModelObserver {
public:
explicit AssistantMiniView(AssistantViewDelegate* delegate);
~AssistantMiniView() override;
// views::View:
const char* GetClassName() const override;
gfx::Size CalculatePreferredSize() const override;
int GetHeightForWidth(int width) const override;
void ChildPreferredSizeChanged(views::View* child) override;
// views::ButtonListener:
void ButtonPressed(views::Button* sender, const ui::Event& event) override;
// AssistantInteractionModelObserver:
void OnInputModalityChanged(InputModality input_modality) override;
void OnResponseChanged(
const scoped_refptr<AssistantResponse>& response) override;
// AssistantUiModelObserver:
void OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) override;
private:
void InitLayout();
void UpdatePrompt();
AssistantViewDelegate* const delegate_;
views::Label* label_; // Owned by view hierarchy.
// The most recent active query for the current Assistant UI session. If there
// has been no active query for the current UI session, this is empty.
base::Optional<std::string> last_active_query_;
DISALLOW_COPY_AND_ASSIGN(AssistantMiniView);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_MINI_VIEW_H_
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/assistant/ui/assistant_notification_overlay.h"
#include <memory>
#include "ash/assistant/ui/assistant_notification_view.h"
#include "ash/assistant/ui/assistant_view_delegate.h"
#include "chromeos/services/assistant/public/mojom/assistant.mojom.h"
#include "ui/views/layout/fill_layout.h"
namespace ash {
namespace {
// Appearance.
constexpr int kMarginBottomDip = 64;
constexpr int kMarginHorizontalDip = 32;
} // namespace
AssistantNotificationOverlay::AssistantNotificationOverlay(
AssistantViewDelegate* delegate)
: delegate_(delegate) {
InitLayout();
// The AssistantViewDelegate outlives the Assistant view hierarchy.
delegate_->AddNotificationModelObserver(this);
delegate_->AddUiModelObserver(this);
}
AssistantNotificationOverlay::~AssistantNotificationOverlay() {
delegate_->RemoveUiModelObserver(this);
delegate_->RemoveNotificationModelObserver(this);
}
const char* AssistantNotificationOverlay::GetClassName() const {
return "AssistantNotificationOverlay";
}
AssistantOverlay::LayoutParams AssistantNotificationOverlay::GetLayoutParams()
const {
using Gravity = AssistantOverlay::LayoutParams::Gravity;
AssistantOverlay::LayoutParams layout_params;
layout_params.gravity = Gravity::kBottom | Gravity::kCenterHorizontal;
layout_params.margins = gfx::Insets(0, kMarginHorizontalDip, kMarginBottomDip,
kMarginHorizontalDip);
return layout_params;
}
void AssistantNotificationOverlay::ViewHierarchyChanged(
const views::ViewHierarchyChangedDetails& details) {
if (details.parent == this)
PreferredSizeChanged();
}
void AssistantNotificationOverlay::OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) {
if (new_visibility != AssistantVisibility::kVisible)
return;
// We need to create views for any notifications that currently exist of type
// |kInAssistant| as they should be shown within Assistant UI.
using chromeos::assistant::mojom::AssistantNotificationType;
for (const auto* notification :
delegate_->GetNotificationModel()->GetNotificationsByType(
AssistantNotificationType::kInAssistant)) {
AddChildView(new AssistantNotificationView(delegate_, notification));
}
}
void AssistantNotificationOverlay::OnNotificationAdded(
const AssistantNotification* notification) {
// We only show notifications of type |kInAssistant| with Assistant UI.
using chromeos::assistant::mojom::AssistantNotificationType;
if (notification->type == AssistantNotificationType::kInAssistant)
AddChildView(new AssistantNotificationView(delegate_, notification));
}
void AssistantNotificationOverlay::InitLayout() {
SetLayoutManager(std::make_unique<views::FillLayout>());
SetPaintToLayer();
layer()->SetFillsBoundsOpaquely(false);
}
} // namespace ash
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_NOTIFICATION_OVERLAY_H_
#define ASH_ASSISTANT_UI_ASSISTANT_NOTIFICATION_OVERLAY_H_
#include "ash/assistant/model/assistant_notification_model_observer.h"
#include "ash/assistant/model/assistant_ui_model_observer.h"
#include "ash/assistant/ui/assistant_overlay.h"
#include "base/component_export.h"
#include "base/macros.h"
namespace ash {
class AssistantViewDelegate;
// AssistantNotificationOverlay is a pseudo-child of AssistantMainView which is
// responsible for parenting in-Assistant notifications.
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantNotificationOverlay
: public AssistantOverlay,
public AssistantUiModelObserver,
public AssistantNotificationModelObserver {
public:
AssistantNotificationOverlay(AssistantViewDelegate* delegate);
~AssistantNotificationOverlay() override;
// AssistantOverlay:
const char* GetClassName() const override;
LayoutParams GetLayoutParams() const override;
void ViewHierarchyChanged(
const views::ViewHierarchyChangedDetails& details) override;
// AssistantUiModelObserver:
void OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) override;
// AssistantNotificationModelObserver:
void OnNotificationAdded(const AssistantNotification* notification) override;
private:
void InitLayout();
AssistantViewDelegate* const delegate_; // Owned by AssistantController.
DISALLOW_COPY_AND_ASSIGN(AssistantNotificationOverlay);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_NOTIFICATION_OVERLAY_H_
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/assistant/ui/assistant_notification_view.h"
#include "ash/assistant/ui/assistant_ui_constants.h"
#include "ash/assistant/ui/assistant_view_delegate.h"
#include "ash/assistant/ui/main_stage/suggestion_chip_view.h"
#include "base/strings/utf_string_conversions.h"
#include "chromeos/services/assistant/public/mojom/assistant.mojom.h"
#include "ui/compositor/scoped_layer_animation_settings.h"
#include "ui/views/animation/ink_drop_painted_layer_delegates.h"
#include "ui/views/controls/button/button.h"
#include "ui/views/controls/label.h"
#include "ui/views/layout/box_layout.h"
#include "ui/views/layout/fill_layout.h"
namespace ash {
namespace {
// Appearance.
constexpr int kLineHeightDip = 20;
constexpr int kPaddingLeftDip = 16;
constexpr int kPaddingRightDip = 8;
constexpr int kPreferredHeightDip = 48;
constexpr int kShadowElevationDip = 6;
// Animation.
constexpr base::TimeDelta kAnimationDuration =
base::TimeDelta::FromMilliseconds(250);
// Helpers ---------------------------------------------------------------------
views::View* CreateButton(
const chromeos::assistant::mojom::AssistantNotificationButtonPtr& button,
views::ButtonListener* listener) {
SuggestionChipView::Params params;
params.text = base::UTF8ToUTF16(button->label);
return new SuggestionChipView(params, listener);
}
} // namespace
AssistantNotificationView::AssistantNotificationView(
AssistantViewDelegate* delegate,
const AssistantNotification* notification)
: delegate_(delegate), notification_id_(notification->client_id) {
InitLayout(notification);
// The AssistantViewDelegate outlives the Assistant view hierarchy.
delegate_->AddNotificationModelObserver(this);
}
AssistantNotificationView::~AssistantNotificationView() {
delegate_->RemoveNotificationModelObserver(this);
}
const char* AssistantNotificationView::GetClassName() const {
return "AssistantNotificationView";
}
void AssistantNotificationView::AddedToWidget() {
UpdateVisibility(/*visible=*/true);
}
gfx::Size AssistantNotificationView::CalculatePreferredSize() const {
return gfx::Size(INT_MAX, GetHeightForWidth(INT_MAX));
}
int AssistantNotificationView::GetHeightForWidth(int width) const {
return kPreferredHeightDip;
}
void AssistantNotificationView::OnBoundsChanged(
const gfx::Rect& previous_bounds) {
UpdateBackground();
}
void AssistantNotificationView::ButtonPressed(views::Button* sender,
const ui::Event& event) {
const auto it = std::find(buttons_.begin(), buttons_.end(), sender);
const int notification_button_index = std::distance(buttons_.begin(), it);
delegate_->OnNotificationButtonPressed(notification_id_,
notification_button_index);
}
void AssistantNotificationView::OnImplicitAnimationsCompleted() {
// When the view's layer has animated to |0.f| opacity, the underlying
// notification has been removed and our associated view can be deleted. Note
// that we check for opacity within epsilon to avoid exact float comparison.
if (cc::MathUtil::IsWithinEpsilon(layer()->opacity(), 0.f))
delete this;
}
void AssistantNotificationView::OnNotificationUpdated(
const AssistantNotification* notification) {
// We only care about the |notification| being updated if it is the
// notification associated with this view.
if (notification->client_id != notification_id_)
return;
using AssistantNotificationType =
chromeos::assistant::mojom::AssistantNotificationType;
// If the notification associated with this view is no longer of type
// |kInAssistant|, it should not be shown in Assistant UI.
if (notification->type != AssistantNotificationType::kInAssistant) {
UpdateVisibility(/*visible=*/false);
return;
}
// Title/Message.
title_->SetText(base::UTF8ToUTF16(notification->title));
message_->SetText(base::UTF8ToUTF16(notification->message));
// Old buttons.
for (views::View* button : buttons_)
delete button;
buttons_.clear();
// New buttons.
for (const auto& notification_button : notification->buttons) {
views::View* button = CreateButton(notification_button, /*listener=*/this);
container_->AddChildView(button);
buttons_.push_back(button);
}
// Because |container_| has a fixed size, we need to explicitly trigger a
// layout/paint pass ourselves when manipulating child views.
container_->Layout();
container_->SchedulePaint();
}
void AssistantNotificationView::OnNotificationRemoved(
const AssistantNotification* notification,
bool from_server) {
if (notification->client_id == notification_id_)
UpdateVisibility(/*visible=*/false);
}
void AssistantNotificationView::InitLayout(
const AssistantNotification* notification) {
SetLayoutManager(std::make_unique<views::FillLayout>());
SetPaintToLayer();
layer()->SetFillsBoundsOpaquely(false);
// Initialize opacity to |0.f| as the layer for this view will be animated in
// when the view is added to its widget.
layer()->SetOpacity(0.f);
// Background/shadow.
background_layer_.SetFillsBoundsOpaquely(false);
layer()->Add(&background_layer_);
// Container.
container_ = new views::View();
container_->SetPreferredSize(gfx::Size(INT_MAX, INT_MAX));
container_->SetPaintToLayer();
container_->layer()->SetFillsBoundsOpaquely(false);
AddChildView(container_);
auto* layout_manager =
container_->SetLayoutManager(std::make_unique<views::BoxLayout>(
views::BoxLayout::Orientation::kHorizontal,
gfx::Insets(0, kPaddingLeftDip, 0, kPaddingRightDip), kSpacingDip));
layout_manager->set_cross_axis_alignment(
views::BoxLayout::CrossAxisAlignment::kCenter);
gfx::FontList font_list =
assistant::ui::GetDefaultFontList().DeriveWithSizeDelta(1);
// Title.
title_ = new views::Label(base::UTF8ToUTF16(notification->title));
title_->SetAutoColorReadabilityEnabled(false);
title_->SetEnabledColor(kTextColorPrimary);
title_->SetFontList(font_list.DeriveWithWeight(gfx::Font::Weight::MEDIUM));
title_->SetHorizontalAlignment(gfx::HorizontalAlignment::ALIGN_LEFT);
title_->SetLineHeight(kLineHeightDip);
container_->AddChildView(title_);
// Message.
message_ = new views::Label(base::UTF8ToUTF16(notification->message));
message_->SetAutoColorReadabilityEnabled(false);
message_->SetEnabledColor(kTextColorSecondary);
message_->SetFontList(font_list);
message_->SetHorizontalAlignment(gfx::HorizontalAlignment::ALIGN_LEFT);
message_->SetLineHeight(kLineHeightDip);
container_->AddChildView(message_);
layout_manager->SetFlexForView(message_, 1);
// Buttons.
for (const auto& notification_button : notification->buttons) {
views::View* button = CreateButton(notification_button, /*listener=*/this);
container_->AddChildView(button);
buttons_.push_back(button);
}
}
void AssistantNotificationView::UpdateBackground() {
gfx::ShadowValues shadow_values =
gfx::ShadowValue::MakeMdShadowValues(kShadowElevationDip);
shadow_delegate_ = std::make_unique<views::BorderShadowLayerDelegate>(
shadow_values, GetLocalBounds(),
/*fill_color=*/SK_ColorWHITE,
/*corner_radius=*/height() / 2);
background_layer_.set_delegate(shadow_delegate_.get());
background_layer_.SetBounds(
gfx::ToEnclosingRect(shadow_delegate_->GetPaintedBounds()));
}
void AssistantNotificationView::UpdateVisibility(bool visible) {
ui::ScopedLayerAnimationSettings animation(layer()->GetAnimator());
// We observe the animation to receive an event on its completion. When the
// layer for this view has completed animating to a hidden state, this view
// is deleted as the underlying notification has been removed.
animation.AddObserver(this);
// Parameters.
animation.SetPreemptionStrategy(
ui::LayerAnimator::PreemptionStrategy::IMMEDIATELY_ANIMATE_TO_NEW_TARGET);
animation.SetTransitionDuration(kAnimationDuration);
animation.SetTweenType(gfx::Tween::Type::EASE_IN_OUT);
// Animate opacity to a visible/hidden state.
layer()->SetOpacity(visible ? 1.f : 0.f);
}
} // namespace ash
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_NOTIFICATION_VIEW_H_
#define ASH_ASSISTANT_UI_ASSISTANT_NOTIFICATION_VIEW_H_
#include <memory>
#include <string>
#include <vector>
#include "ash/assistant/model/assistant_notification_model_observer.h"
#include "base/component_export.h"
#include "base/macros.h"
#include "ui/compositor/layer.h"
#include "ui/compositor/layer_animation_observer.h"
#include "ui/views/controls/button/button.h"
#include "ui/views/view.h"
namespace views {
class BorderShadowLayerDelegate;
class Label;
} // namespace views
namespace ash {
class AssistantViewDelegate;
// AssistantNotificationView is the view for a mojom::AssistantNotification
// which appears in Assistant UI. Its parent is AssistantNotificationOverlay.
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantNotificationView
: public views::View,
public views::ButtonListener,
public ui::ImplicitAnimationObserver,
public AssistantNotificationModelObserver {
public:
AssistantNotificationView(AssistantViewDelegate* delegate,
const AssistantNotification* notification);
~AssistantNotificationView() override;
// views::View:
const char* GetClassName() const override;
void AddedToWidget() override;
gfx::Size CalculatePreferredSize() const override;
int GetHeightForWidth(int width) const override;
void OnBoundsChanged(const gfx::Rect& previous_bounds) override;
// views::ButtonListener:
void ButtonPressed(views::Button* sender, const ui::Event& event) override;
// ui::ImplicitAnimationObserver:
void OnImplicitAnimationsCompleted() override;
// AssistantNotificationModelObserver:
void OnNotificationUpdated(
const AssistantNotification* notification) override;
void OnNotificationRemoved(const AssistantNotification* notification,
bool from_server) override;
private:
void InitLayout(const AssistantNotification* notification);
void UpdateBackground();
void UpdateVisibility(bool visible);
AssistantViewDelegate* const delegate_; // Owned by AssistantController.
const std::string notification_id_;
views::View* container_; // Owned by view hierarchy.
views::Label* title_; // Owned by view hierarchy.
views::Label* message_; // Owned by view hierarchy.
std::vector<views::View*> buttons_; // Owned by view hierarchy.
// Background/shadow.
ui::Layer background_layer_;
std::unique_ptr<views::BorderShadowLayerDelegate> shadow_delegate_;
DISALLOW_COPY_AND_ASSIGN(AssistantNotificationView);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_NOTIFICATION_VIEW_H_
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_ASSISTANT_OVERLAY_H_
#define ASH_ASSISTANT_UI_ASSISTANT_OVERLAY_H_
#include "base/component_export.h"
#include "base/macros.h"
#include "ui/views/view.h"
namespace ash {
// AssistantOverlays are children of AssistantContainerView's client view that
// behave as pseudo-children of AssistantContainerView's own child views. This
// allows children of AssistantContainerView to pseudo-parent views that paint
// to a layer that is higher up in the layer tree than themselves. In the case
// of AssistantMainView, an overlay is used to parent in-Assistant notification
// views that need to be drawn over top of Assistant cards.
class COMPONENT_EXPORT(ASSISTANT_UI) AssistantOverlay : public views::View {
public:
// Defines parameters for how an overlay should be laid out.
struct LayoutParams {
enum Gravity {
kUnspecified = 0,
kBottom = 1 << 0,
kCenterHorizontal = 1 << 1,
};
int gravity = Gravity::kUnspecified;
gfx::Insets margins;
};
AssistantOverlay() = default;
~AssistantOverlay() override = default;
// Returns parameters for how an overlay should be laid out.
virtual LayoutParams GetLayoutParams() const = 0;
private:
DISALLOW_COPY_AND_ASSIGN(AssistantOverlay);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_ASSISTANT_OVERLAY_H_
...@@ -16,16 +16,12 @@ ...@@ -16,16 +16,12 @@
#include "ash/assistant/model/assistant_suggestions_model_observer.h" #include "ash/assistant/model/assistant_suggestions_model_observer.h"
#include "ash/assistant/model/assistant_ui_model.h" #include "ash/assistant/model/assistant_ui_model.h"
#include "ash/assistant/model/assistant_ui_model_observer.h" #include "ash/assistant/model/assistant_ui_model_observer.h"
#include "ash/assistant/ui/assistant_mini_view.h"
#include "ash/assistant/ui/caption_bar.h" #include "ash/assistant/ui/caption_bar.h"
#include "ash/assistant/ui/dialog_plate/dialog_plate.h"
#include "ash/assistant/ui/main_stage/assistant_opt_in_view.h"
#include "ash/public/cpp/assistant/assistant_image_downloader.h" #include "ash/public/cpp/assistant/assistant_image_downloader.h"
#include "ash/public/cpp/assistant/assistant_state.h" #include "ash/public/cpp/assistant/assistant_state.h"
#include "base/component_export.h" #include "base/component_export.h"
#include "base/observer_list_types.h" #include "base/observer_list_types.h"
#include "chromeos/services/assistant/public/mojom/assistant.mojom.h" #include "chromeos/services/assistant/public/mojom/assistant.mojom.h"
#include "mojo/public/cpp/bindings/pending_receiver.h"
#include "ui/wm/core/cursor_manager.h" #include "ui/wm/core/cursor_manager.h"
namespace ash { namespace ash {
...@@ -47,9 +43,6 @@ class COMPONENT_EXPORT(ASSISTANT_UI) AssistantViewDelegateObserver ...@@ -47,9 +43,6 @@ class COMPONENT_EXPORT(ASSISTANT_UI) AssistantViewDelegateObserver
// Invoked when the dialog plate contents have been committed. // Invoked when the dialog plate contents have been committed.
virtual void OnDialogPlateContentsCommitted(const std::string& text) {} virtual void OnDialogPlateContentsCommitted(const std::string& text) {}
// Invoked when the mini view is pressed.
virtual void OnMiniViewPressed() {}
// Invoked when the opt in button is pressed. // Invoked when the opt in button is pressed.
virtual void OnOptInButtonPressed() {} virtual void OnOptInButtonPressed() {}
...@@ -144,9 +137,6 @@ class COMPONENT_EXPORT(ASSISTANT_UI) AssistantViewDelegate { ...@@ -144,9 +137,6 @@ class COMPONENT_EXPORT(ASSISTANT_UI) AssistantViewDelegate {
// Invoked when the dialog plate contents have been committed. // Invoked when the dialog plate contents have been committed.
virtual void OnDialogPlateContentsCommitted(const std::string& text) = 0; virtual void OnDialogPlateContentsCommitted(const std::string& text) = 0;
// Invoked when the mini view is pressed.
virtual void OnMiniViewPressed() = 0;
// Invoked when an in-Assistant notification button is pressed. // Invoked when an in-Assistant notification button is pressed.
virtual void OnNotificationButtonPressed(const std::string& notification_id, virtual void OnNotificationButtonPressed(const std::string& notification_id,
int notification_button_index) = 0; int notification_button_index) = 0;
......
This diff is collapsed.
// Copyright 2018 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef ASH_ASSISTANT_UI_DIALOG_PLATE_DIALOG_PLATE_H_
#define ASH_ASSISTANT_UI_DIALOG_PLATE_DIALOG_PLATE_H_
#include <memory>
#include <string>
#include "ash/assistant/model/assistant_interaction_model_observer.h"
#include "ash/assistant/model/assistant_query_history.h"
#include "ash/assistant/model/assistant_ui_model_observer.h"
#include "ash/assistant/ui/base/assistant_button_listener.h"
#include "base/component_export.h"
#include "base/macros.h"
#include "ui/views/controls/button/button.h"
#include "ui/views/controls/textfield/textfield_controller.h"
#include "ui/views/view.h"
namespace ui {
class CallbackLayerAnimationObserver;
} // namespace ui
namespace views {
class ImageButton;
} // namespace views
namespace ash {
class AssistantViewDelegate;
class MicView;
// DialogPlate -----------------------------------------------------------------
// DialogPlate is the child of AssistantMainView concerned with providing the
// means by which a user converses with Assistant. To this end, DialogPlate
// provides a textfield for use with the keyboard input modality, and a MicView
// which serves to toggle voice interaction as appropriate for use with the
// voice input modality.
class COMPONENT_EXPORT(ASSISTANT_UI) DialogPlate
: public views::View,
public views::TextfieldController,
public AssistantInteractionModelObserver,
public AssistantUiModelObserver,
public AssistantButtonListener {
public:
explicit DialogPlate(AssistantViewDelegate* delegate);
~DialogPlate() override;
// views::View:
const char* GetClassName() const override;
gfx::Size CalculatePreferredSize() const override;
int GetHeightForWidth(int width) const override;
void RequestFocus() override;
// AssistantButtonListener:
void OnButtonPressed(AssistantButtonId button_id) override;
// views::TextfieldController:
bool HandleKeyEvent(views::Textfield* sender,
const ui::KeyEvent& key_event) override;
// AssistantInteractionModelObserver:
void OnInputModalityChanged(InputModality input_modality) override;
void OnCommittedQueryChanged(const AssistantQuery& committed_query) override;
// AssistantUiModelObserver:
void OnUiVisibilityChanged(
AssistantVisibility new_visibility,
AssistantVisibility old_visibility,
base::Optional<AssistantEntryPoint> entry_point,
base::Optional<AssistantExitPoint> exit_point) override;
// Returns the first focusable view or nullptr to defer to views::FocusSearch.
views::View* FindFirstFocusableView();
private:
void InitLayout();
void InitKeyboardLayoutContainer();
void InitVoiceLayoutContainer();
void OnAnimationStarted(const ui::CallbackLayerAnimationObserver& observer);
bool OnAnimationEnded(const ui::CallbackLayerAnimationObserver& observer);
void SetFocus(InputModality modality);
AssistantViewDelegate* const delegate_;
views::View* input_modality_layout_container_; // Owned by view hierarchy.
views::View* keyboard_layout_container_; // Owned by view hierarchy.
views::View* voice_layout_container_; // Owned by view hierarchy.
views::ImageButton* keyboard_input_toggle_; // Owned by view hierarchy.
views::ImageButton* voice_input_toggle_; // Owned by view hierarchy.
MicView* animated_voice_input_toggle_; // Owned by view hierarchy.
views::ImageButton* settings_button_; // Owned by view hierarchy.
views::Textfield* textfield_; // Owned by view hierarchy.
std::unique_ptr<ui::CallbackLayerAnimationObserver> animation_observer_;
std::unique_ptr<AssistantQueryHistory::Iterator> query_history_iterator_;
DISALLOW_COPY_AND_ASSIGN(DialogPlate);
};
} // namespace ash
#endif // ASH_ASSISTANT_UI_DIALOG_PLATE_DIALOG_PLATE_H_
...@@ -7,7 +7,6 @@ ...@@ -7,7 +7,6 @@
#include <memory> #include <memory>
#include "ash/assistant/model/ui/assistant_card_element.h" #include "ash/assistant/model/ui/assistant_card_element.h"
#include "ash/assistant/ui/assistant_container_view.h"
#include "ash/assistant/ui/assistant_ui_constants.h" #include "ash/assistant/ui/assistant_ui_constants.h"
#include "ash/assistant/ui/assistant_view_delegate.h" #include "ash/assistant/ui/assistant_view_delegate.h"
#include "ash/assistant/util/deep_link_util.h" #include "ash/assistant/util/deep_link_util.h"
...@@ -19,6 +18,7 @@ ...@@ -19,6 +18,7 @@
#include "ui/views/accessibility/view_accessibility.h" #include "ui/views/accessibility/view_accessibility.h"
#include "ui/views/layout/fill_layout.h" #include "ui/views/layout/fill_layout.h"
#include "ui/views/view.h" #include "ui/views/view.h"
#include "ui/views/widget/widget.h"
namespace ash { namespace ash {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment