summaryrefslogtreecommitdiffstats
path: root/athena
diff options
context:
space:
mode:
authormukai <mukai@chromium.org>2014-11-06 02:09:06 -0800
committerCommit bot <commit-bot@chromium.org>2014-11-06 10:09:34 +0000
commit6116f294a1c79805f4b9ea880d2e19d89aa5ac4e (patch)
treea4c097fc2a3f34745f79b80bbde14d0ba0992ddd /athena
parent3d1ff77b15cfa7052307e4c035f9ad39dfc44df0 (diff)
downloadchromium_src-6116f294a1c79805f4b9ea880d2e19d89aa5ac4e.zip
chromium_src-6116f294a1c79805f4b9ea880d2e19d89aa5ac4e.tar.gz
chromium_src-6116f294a1c79805f4b9ea880d2e19d89aa5ac4e.tar.bz2
Replace the content of the home card by AppListMainView.
Athena specific AthenaStartPageView is not used anymore. We'll share the same view as the experimental app list. BUG=425717, 425724, 425719 R=calamity@chromium.org, oshima@chromium.org TEST=manually Review URL: https://codereview.chromium.org/683243004 Cr-Commit-Position: refs/heads/master@{#303001}
Diffstat (limited to 'athena')
-rw-r--r--athena/athena.gyp3
-rw-r--r--athena/home/app_list_view_delegate.cc13
-rw-r--r--athena/home/athena_start_page_view.cc476
-rw-r--r--athena/home/athena_start_page_view.h128
-rw-r--r--athena/home/athena_start_page_view_unittest.cc279
-rw-r--r--athena/home/home_card_constants.cc2
-rw-r--r--athena/home/home_card_gesture_manager_unittest.cc8
-rw-r--r--athena/home/home_card_impl.cc138
-rw-r--r--athena/home/home_card_impl.h9
-rw-r--r--athena/home/home_card_unittest.cc35
10 files changed, 111 insertions, 980 deletions
diff --git a/athena/athena.gyp b/athena/athena.gyp
index 25dafb0..2b334e7 100644
--- a/athena/athena.gyp
+++ b/athena/athena.gyp
@@ -55,8 +55,6 @@
'env/public/athena_env.h',
'home/app_list_view_delegate.cc',
'home/app_list_view_delegate.h',
- 'home/athena_start_page_view.cc',
- 'home/athena_start_page_view.h',
'home/home_card_constants.cc',
'home/home_card_constants.h',
'home/home_card_gesture_manager.cc',
@@ -297,7 +295,6 @@
'activity/activity_manager_unittest.cc',
'content/app_activity_unittest.cc',
'env/athena_env_unittest.cc',
- 'home/athena_start_page_view_unittest.cc',
'home/home_card_gesture_manager_unittest.cc',
'home/home_card_unittest.cc',
'input/accelerator_manager_unittest.cc',
diff --git a/athena/home/app_list_view_delegate.cc b/athena/home/app_list_view_delegate.cc
index eead245..06d0bdc8 100644
--- a/athena/home/app_list_view_delegate.cc
+++ b/athena/home/app_list_view_delegate.cc
@@ -22,10 +22,6 @@
#include "ui/app_list/search_result.h"
#include "ui/app_list/speech_ui_model.h"
#include "ui/base/l10n/l10n_util.h"
-#include "ui/base/resource/resource_bundle.h"
-#include "ui/gfx/image/image_skia.h"
-#include "ui/resources/grit/ui_resources.h"
-#include "ui/views/controls/image_view.h"
namespace athena {
@@ -144,14 +140,7 @@ void AppListViewDelegate::ShowForProfileByPath(
views::View* AppListViewDelegate::CreateStartPageWebView(
const gfx::Size& size) {
- // A static image of the logo. This needs to support dynamic Doodles
- // eventually.
- views::ImageView* logo_image = new views::ImageView();
- logo_image->SetImage(ui::ResourceBundle::GetSharedInstance().
- GetImageSkiaNamed(IDR_LOCAL_NTP_IMAGES_LOGO_PNG));
- logo_image->SetHorizontalAlignment(views::ImageView::CENTER);
- logo_image->SetVerticalAlignment(views::ImageView::CENTER);
- return logo_image;
+ return NULL;
}
std::vector<views::View*> AppListViewDelegate::CreateCustomPageWebViews(
diff --git a/athena/home/athena_start_page_view.cc b/athena/home/athena_start_page_view.cc
deleted file mode 100644
index bb78ec2..0000000
--- a/athena/home/athena_start_page_view.cc
+++ /dev/null
@@ -1,476 +0,0 @@
-// Copyright 2014 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 "athena/home/athena_start_page_view.h"
-
-#include "athena/home/home_card_constants.h"
-#include "athena/system/public/system_ui.h"
-#include "base/bind.h"
-#include "base/strings/string_util.h"
-#include "third_party/skia/include/core/SkPaint.h"
-#include "third_party/skia/include/core/SkPath.h"
-#include "ui/app_list/app_list_item.h"
-#include "ui/app_list/app_list_item_list.h"
-#include "ui/app_list/app_list_model.h"
-#include "ui/app_list/app_list_view_delegate.h"
-#include "ui/app_list/search_box_model.h"
-#include "ui/app_list/views/search_box_view.h"
-#include "ui/app_list/views/search_result_list_view.h"
-#include "ui/compositor/closure_animation_observer.h"
-#include "ui/compositor/scoped_layer_animation_settings.h"
-#include "ui/gfx/canvas.h"
-#include "ui/views/background.h"
-#include "ui/views/border.h"
-#include "ui/views/controls/textfield/textfield.h"
-#include "ui/views/layout/box_layout.h"
-#include "ui/views/layout/fill_layout.h"
-#include "ui/views/round_rect_painter.h"
-
-namespace {
-
-const size_t kMaxIconNum = 3;
-const int kIconSize = 50;
-const int kIconMargin = 25;
-
-const int kTopMargin = 100;
-
-// Copied from ui/app_list/views/start_page_view.cc
-const int kInstantContainerSpacing = 20;
-const int kWebViewWidth = 500;
-const int kWebViewHeight = 105;
-const int kSearchBoxBorderWidth = 1;
-const int kSearchBoxCornerRadius = 2;
-
-// Taken from the mock. The width is not specified by pixel but the search box
-// covers 6 icons with margin.
-const int kSearchBoxWidth = kIconSize * 6 + kIconMargin * 7;
-const int kSearchBoxHeight = 40;
-
-gfx::Size GetIconContainerSize() {
- return gfx::Size(kIconSize * kMaxIconNum + kIconMargin * (kMaxIconNum - 1),
- kIconSize);
-}
-
-class PlaceHolderButton : public views::ImageButton,
- public views::ButtonListener {
- public:
- PlaceHolderButton()
- : ImageButton(this) {
- gfx::Canvas canvas(gfx::Size(kIconSize, kIconSize), 1.0f, true);
- SkPaint paint;
- paint.setStyle(SkPaint::kFill_Style);
- paint.setColor(SkColorSetRGB(86, 119, 252));
- paint.setFlags(SkPaint::kAntiAlias_Flag);
- canvas.DrawCircle(
- gfx::Point(kIconSize / 2, kIconSize / 2), kIconSize / 2, paint);
-
- scoped_ptr<gfx::ImageSkia> image(
- new gfx::ImageSkia(canvas.ExtractImageRep()));
- SetImage(STATE_NORMAL, image.get());
- }
-
- private:
- // views::ButtonListener:
- void ButtonPressed(views::Button* sender, const ui::Event& event) override {
- // Do nothing: remove these place holders.
- }
-
- DISALLOW_COPY_AND_ASSIGN(PlaceHolderButton);
-};
-
-class AppIconButton : public views::ImageButton,
- public views::ButtonListener {
- public:
- explicit AppIconButton(app_list::AppListItem* item)
- : ImageButton(this), item_(nullptr) {
- SetItem(item);
- }
-
- void SetItem(app_list::AppListItem* item) {
- item_ = item;
- // TODO(mukai): icon should be resized.
- SetImage(STATE_NORMAL, &item->icon());
- }
-
- private:
- // views::ButtonListener:
- void ButtonPressed(views::Button* sender, const ui::Event& event) override {
- DCHECK_EQ(sender, this);
- item_->Activate(event.flags());
- }
-
- app_list::AppListItem* item_;
-
- DISALLOW_COPY_AND_ASSIGN(AppIconButton);
-};
-
-// The background to paint the round rectangle of the view area.
-class RoundRectBackground : public views::Background {
- public:
- RoundRectBackground(SkColor color, int corner_radius)
- : color_(color),
- corner_radius_(corner_radius) {}
- ~RoundRectBackground() override {}
-
- private:
- // views::Background:
- void Paint(gfx::Canvas* canvas, views::View* view) const override {
- SkPaint paint;
- paint.setStyle(SkPaint::kFill_Style);
- paint.setColor(color_);
- canvas->DrawRoundRect(view->GetContentsBounds(), corner_radius_, paint);
- }
-
- SkColor color_;
- int corner_radius_;
-
- DISALLOW_COPY_AND_ASSIGN(RoundRectBackground);
-};
-
-class SearchBoxContainer : public views::View {
- public:
- explicit SearchBoxContainer(app_list::SearchBoxView* search_box)
- : search_box_(search_box) {
- search_box->set_background(
- new RoundRectBackground(SK_ColorWHITE, kSearchBoxCornerRadius));
- search_box->SetBorder(views::Border::CreateBorderPainter(
- new views::RoundRectPainter(SK_ColorGRAY, kSearchBoxCornerRadius),
- gfx::Insets(kSearchBoxBorderWidth, kSearchBoxBorderWidth,
- kSearchBoxBorderWidth, kSearchBoxBorderWidth)));
- SetLayoutManager(new views::FillLayout());
- AddChildView(search_box_);
- }
- ~SearchBoxContainer() override {}
-
- private:
- // views::View:
- gfx::Size GetPreferredSize() const override {
- return gfx::Size(kSearchBoxWidth, kSearchBoxHeight);
- }
-
- // Owned by the views hierarchy.
- app_list::SearchBoxView* search_box_;
-
- DISALLOW_COPY_AND_ASSIGN(SearchBoxContainer);
-};
-
-} // namespace
-
-namespace athena {
-
-// static
-const char AthenaStartPageView::kViewClassName[] = "AthenaStartPageView";
-
-AthenaStartPageView::LayoutData::LayoutData()
- : system_info_opacity(1.0f), logo_opacity(1.0f) {
-}
-
-AthenaStartPageView::AthenaStartPageView(
- app_list::AppListViewDelegate* view_delegate)
- : delegate_(view_delegate),
- layout_state_(0.0f),
- weak_factory_(this) {
- system_info_view_ =
- SystemUI::Get()->CreateSystemInfoView(SystemUI::COLOR_SCHEME_DARK);
- system_info_view_->SetPaintToLayer(true);
- system_info_view_->SetFillsBoundsOpaquely(false);
- AddChildView(system_info_view_);
-
- logo_ = view_delegate->CreateStartPageWebView(
- gfx::Size(kWebViewWidth, kWebViewHeight));
- logo_->SetPaintToLayer(true);
- logo_->SetFillsBoundsOpaquely(false);
- logo_->SetSize(gfx::Size(kWebViewWidth, kWebViewHeight));
- AddChildView(logo_);
-
- search_results_view_ =
- new app_list::SearchResultListView(nullptr, view_delegate);
- // search_results_view_'s size will shrink after settings results.
- search_results_height_ = static_cast<views::View*>(
- search_results_view_)->GetHeightForWidth(kSearchBoxWidth);
- search_results_view_->SetResults(view_delegate->GetModel()->results());
-
- search_results_view_->SetVisible(false);
- search_results_view_->SetPaintToLayer(true);
- search_results_view_->SetFillsBoundsOpaquely(false);
- AddChildView(search_results_view_);
-
- app_icon_container_ = new views::View();
- AddChildView(app_icon_container_);
- app_icon_container_->SetPaintToLayer(true);
- app_icon_container_->layer()->SetFillsBoundsOpaquely(false);
- app_icon_container_->SetLayoutManager(new views::BoxLayout(
- views::BoxLayout::kHorizontal, 0, 0, kIconMargin));
- app_icon_container_->SetSize(GetIconContainerSize());
- UpdateAppIcons();
- view_delegate->GetModel()->top_level_item_list()->AddObserver(this);
-
- control_icon_container_ = new views::View();
- control_icon_container_->SetPaintToLayer(true);
- control_icon_container_->SetFillsBoundsOpaquely(false);
- AddChildView(control_icon_container_);
- control_icon_container_->SetLayoutManager(new views::BoxLayout(
- views::BoxLayout::kHorizontal, 0, 0, kIconMargin));
- for (size_t i = 0; i < kMaxIconNum; ++i)
- control_icon_container_->AddChildView(new PlaceHolderButton());
- control_icon_container_->SetSize(GetIconContainerSize());
-
- search_box_view_ = new app_list::SearchBoxView(this, view_delegate);
- search_box_view_->set_contents_view(this);
- search_box_view_->search_box()->set_id(kHomeCardSearchBoxId);
- search_box_container_ = new SearchBoxContainer(search_box_view_);
- search_box_container_->SetPaintToLayer(true);
- search_box_container_->SetFillsBoundsOpaquely(false);
- search_box_container_->SetSize(search_box_container_->GetPreferredSize());
- AddChildView(search_box_container_);
-}
-
-AthenaStartPageView::~AthenaStartPageView() {
- delegate_->GetModel()->top_level_item_list()->RemoveObserver(this);
-}
-
-void AthenaStartPageView::RequestFocusOnSearchBox() {
- search_box_view_->search_box()->RequestFocus();
-}
-
-void AthenaStartPageView::SetLayoutState(float layout_state) {
- layout_state_ = layout_state;
- Layout();
- FOR_EACH_OBSERVER(Observer, observers_, OnLayoutStateChanged(layout_state));
-}
-
-void AthenaStartPageView::SetLayoutStateWithAnimation(
- float layout_state,
- gfx::Tween::Type tween_type) {
- ui::ScopedLayerAnimationSettings system_info(
- system_info_view_->layer()->GetAnimator());
- ui::ScopedLayerAnimationSettings logo(logo_->layer()->GetAnimator());
- ui::ScopedLayerAnimationSettings search_box(
- search_box_container_->layer()->GetAnimator());
- ui::ScopedLayerAnimationSettings icons(
- app_icon_container_->layer()->GetAnimator());
- ui::ScopedLayerAnimationSettings controls(
- control_icon_container_->layer()->GetAnimator());
-
- system_info.SetTweenType(tween_type);
- logo.SetTweenType(tween_type);
- search_box.SetTweenType(tween_type);
- icons.SetTweenType(tween_type);
- controls.SetTweenType(tween_type);
-
- SetLayoutState(layout_state);
-}
-
-void AthenaStartPageView::AddObserver(AthenaStartPageView::Observer* observer) {
- observers_.AddObserver(observer);
-}
-
-void AthenaStartPageView::RemoveObserver(
- AthenaStartPageView::Observer* observer) {
- observers_.RemoveObserver(observer);
-}
-
-AthenaStartPageView::LayoutData AthenaStartPageView::CreateBottomBounds(
- int width) {
- LayoutData state;
- state.icons.set_size(app_icon_container_->size());
- state.icons.set_x(kIconMargin);
- state.icons.set_y(kIconMargin);
-
- state.controls.set_size(control_icon_container_->size());
- state.controls.set_x(width - kIconMargin - state.controls.width());
- state.controls.set_y(kIconMargin);
-
- int search_box_max_width =
- state.controls.x() - state.icons.right() - kIconMargin * 2;
- state.search_box.set_width(std::min(search_box_max_width, kSearchBoxWidth));
- state.search_box.set_height(search_box_container_->height());
- state.search_box.set_x((width - state.search_box.width()) / 2);
- state.search_box.set_y((kHomeCardHeight - state.search_box.height()) / 2);
-
- state.system_info_opacity = 0.0f;
- state.logo_opacity = 0.0f;
- return state;
-}
-
-AthenaStartPageView::LayoutData AthenaStartPageView::CreateCenteredBounds(
- int width) {
- LayoutData state;
-
- state.search_box.set_size(search_box_container_->GetPreferredSize());
- state.search_box.set_x((width - state.search_box.width()) / 2);
- state.search_box.set_y(logo_->bounds().bottom() + kInstantContainerSpacing);
-
- state.icons.set_size(app_icon_container_->size());
- state.icons.set_x(width / 2 - state.icons.width() - kIconMargin / 2);
- state.icons.set_y(state.search_box.bottom() + kInstantContainerSpacing);
-
- state.controls.set_size(control_icon_container_->size());
- state.controls.set_x(width / 2 + kIconMargin / 2 + kIconMargin % 2);
- state.controls.set_y(state.icons.y());
-
- state.system_info_opacity = 1.0f;
- state.logo_opacity = 1.0f;
- return state;
-}
-
-void AthenaStartPageView::UpdateAppIcons() {
- app_list::AppListItemList* top_level =
- delegate_->GetModel()->top_level_item_list();
- size_t max_items = std::min(top_level->item_count(), kMaxIconNum);
- for (size_t i = 0; i < max_items; ++i) {
- if (i < static_cast<size_t>(app_icon_container_->child_count())) {
- AppIconButton* button =
- static_cast<AppIconButton*>(app_icon_container_->child_at(i));
- button->SetItem(top_level->item_at(i));
- } else {
- app_icon_container_->AddChildView(
- new AppIconButton(top_level->item_at(i)));
- }
- }
-
- while (max_items < static_cast<size_t>(app_icon_container_->child_count())) {
- scoped_ptr<views::View> remover(
- app_icon_container_->child_at(app_icon_container_->child_count() - 1));
- app_icon_container_->RemoveChildView(remover.get());
- }
-}
-
-void AthenaStartPageView::LayoutSearchResults(bool should_show_search_results) {
- if (should_show_search_results ==
- search_results_view_->layer()->GetTargetVisibility()) {
- return;
- }
- if (should_show_search_results && layout_state_ != 1.0f)
- SetLayoutState(1.0f);
-
- gfx::Rect search_box_bounds = search_box_container_->bounds();
- if (!search_results_view_->visible()) {
- search_results_view_->SetVisible(true);
- search_results_view_->SetBounds(
- search_box_bounds.x(), search_box_bounds.bottom(),
- search_box_bounds.width(), 0);
- }
- logo_->SetVisible(true);
-
- {
- ui::ScopedLayerAnimationSettings logo_settings(
- logo_->layer()->GetAnimator());
- logo_settings.SetTweenType(gfx::Tween::EASE_IN_OUT);
- logo_settings.AddObserver(new ui::ClosureAnimationObserver(
- base::Bind(&AthenaStartPageView::OnSearchResultLayoutAnimationCompleted,
- weak_factory_.GetWeakPtr(),
- should_show_search_results)));
-
- ui::ScopedLayerAnimationSettings search_box_settings(
- search_box_container_->layer()->GetAnimator());
- search_box_settings.SetTweenType(gfx::Tween::EASE_IN_OUT);
-
- ui::ScopedLayerAnimationSettings search_results_settings(
- search_results_view_->layer()->GetAnimator());
- search_results_settings.SetTweenType(gfx::Tween::EASE_IN_OUT);
-
- if (should_show_search_results) {
- logo_->layer()->SetOpacity(0.0f);
- search_box_bounds.set_y(
- search_box_bounds.y() - search_results_height_ -
- kInstantContainerSpacing);
- search_box_container_->SetBoundsRect(search_box_bounds);
- search_results_view_->SetBounds(
- search_box_bounds.x(),
- search_box_bounds.bottom() + kInstantContainerSpacing,
- search_box_bounds.width(),
- search_results_height_);
- } else {
- logo_->layer()->SetOpacity(1.0f);
- search_box_bounds.set_y(
- logo_->bounds().bottom() + kInstantContainerSpacing);
- search_box_container_->SetBoundsRect(search_box_bounds);
-
- gfx::Rect search_results_bounds = search_results_view_->bounds();
- search_results_bounds.set_y(search_results_bounds.bottom());
- search_results_bounds.set_height(0);
- search_results_view_->SetBoundsRect(search_results_bounds);
- }
- }
-}
-
-void AthenaStartPageView::OnSearchResultLayoutAnimationCompleted(
- bool should_show_search_results) {
- logo_->SetVisible(!should_show_search_results);
- search_results_view_->SetVisible(should_show_search_results);
-}
-
-void AthenaStartPageView::Layout() {
- search_results_view_->SetVisible(false);
-
- system_info_view_->SetBounds(
- 0, 0, width(), system_info_view_->GetPreferredSize().height());
-
- gfx::Rect logo_bounds(x() + width() / 2 - kWebViewWidth / 2, y() + kTopMargin,
- kWebViewWidth, kWebViewHeight);
- logo_->SetBoundsRect(logo_bounds);
-
- LayoutData bottom_bounds = CreateBottomBounds(width());
- LayoutData centered_bounds = CreateCenteredBounds(width());
-
- system_info_view_->layer()->SetOpacity(gfx::Tween::FloatValueBetween(
- gfx::Tween::CalculateValue(gfx::Tween::EASE_IN_2, layout_state_),
- bottom_bounds.system_info_opacity, centered_bounds.system_info_opacity));
- system_info_view_->SetVisible(
- system_info_view_->layer()->GetTargetOpacity() != 0.0f);
-
- logo_->layer()->SetOpacity(gfx::Tween::FloatValueBetween(
- gfx::Tween::CalculateValue(gfx::Tween::EASE_IN_2, layout_state_),
- bottom_bounds.logo_opacity, centered_bounds.logo_opacity));
- logo_->SetVisible(logo_->layer()->GetTargetOpacity() != 0.0f);
-
- app_icon_container_->SetBoundsRect(gfx::Tween::RectValueBetween(
- layout_state_, bottom_bounds.icons, centered_bounds.icons));
- control_icon_container_->SetBoundsRect(gfx::Tween::RectValueBetween(
- layout_state_, bottom_bounds.controls, centered_bounds.controls));
- search_box_container_->SetBoundsRect(gfx::Tween::RectValueBetween(
- layout_state_, bottom_bounds.search_box, centered_bounds.search_box));
-}
-
-bool AthenaStartPageView::OnKeyPressed(const ui::KeyEvent& key_event) {
- return search_results_view_->visible() &&
- search_results_view_->OnKeyPressed(key_event);
-}
-
-void AthenaStartPageView::QueryChanged(app_list::SearchBoxView* sender) {
- delegate_->StartSearch();
-
- base::string16 query;
- base::TrimWhitespace(
- delegate_->GetModel()->search_box()->text(), base::TRIM_ALL, &query);
-
- if (!query.empty())
- search_results_view_->SetSelectedIndex(0);
-
- LayoutSearchResults(!query.empty());
-}
-
-void AthenaStartPageView::OnListItemAdded(size_t index,
- app_list::AppListItem* item) {
- UpdateAppIcons();
-}
-
-void AthenaStartPageView::OnListItemRemoved(size_t index,
- app_list::AppListItem* item) {
- UpdateAppIcons();
-}
-
-void AthenaStartPageView::OnListItemMoved(size_t from_index,
- size_t to_index,
- app_list::AppListItem* item) {
- UpdateAppIcons();
-}
-
-// static
-size_t AthenaStartPageView::GetMaxIconNumForTest() {
- return kMaxIconNum;
-}
-
-} // namespace athena
diff --git a/athena/home/athena_start_page_view.h b/athena/home/athena_start_page_view.h
deleted file mode 100644
index fd15dca..0000000
--- a/athena/home/athena_start_page_view.h
+++ /dev/null
@@ -1,128 +0,0 @@
-// Copyright 2014 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 ATHENA_HOME_ATHENA_START_PAGE_VIEW_H_
-#define ATHENA_HOME_ATHENA_START_PAGE_VIEW_H_
-
-#include "athena/athena_export.h"
-#include "base/memory/weak_ptr.h"
-#include "base/observer_list.h"
-#include "ui/app_list/app_list_item_list_observer.h"
-#include "ui/app_list/views/search_box_view_delegate.h"
-#include "ui/gfx/animation/tween.h"
-#include "ui/views/view.h"
-
-namespace app_list {
-class AppListModelObserver;
-class AppListViewDelegate;
-class SearchBoxView;
-class SearchResultListView;
-}
-
-namespace athena {
-
-class ATHENA_EXPORT AthenaStartPageView
- : public views::View,
- public app_list::SearchBoxViewDelegate,
- public app_list::AppListItemListObserver {
- public:
- class Observer {
- public:
- virtual void OnLayoutStateChanged(float new_state) = 0;
- };
-
- explicit AthenaStartPageView(app_list::AppListViewDelegate* delegate);
- ~AthenaStartPageView() override;
-
- // Requests the focus on the search box in the start page view.
- void RequestFocusOnSearchBox();
-
- // Updates the layout state. See the comment of |layout_state_| field.
- void SetLayoutState(float layout_state);
-
- // Updates the layout state and move the subviews to the target location with
- // animation.
- void SetLayoutStateWithAnimation(float layout_state,
- gfx::Tween::Type tween_type);
-
- void AddObserver(Observer* observer);
- void RemoveObserver(Observer* observer);
-
- private:
- friend class AthenaStartPageViewTest;
-
- static const char kViewClassName[];
-
- static size_t GetMaxIconNumForTest();
-
- // A struct which bundles the layout data of subviews.
- struct LayoutData {
- gfx::Rect search_box;
- gfx::Rect icons;
- gfx::Rect controls;
- float system_info_opacity;
- float logo_opacity;
-
- LayoutData();
- };
-
- // Returns the bounds for |VISIBLE_BOTTOM|.
- LayoutData CreateBottomBounds(int width);
-
- // Returns the bounds for |VISIBLE_CENTERED|.
- LayoutData CreateCenteredBounds(int width);
-
- void UpdateAppIcons();
-
- // Schedules the animation for the layout the search box and the search
- // results.
- void LayoutSearchResults(bool should_show_search_results);
-
- // Called when the animation of search box / search results layout has
- // completed.
- void OnSearchResultLayoutAnimationCompleted(bool should_show_search_results);
-
- // views::View:
- void Layout() override;
- bool OnKeyPressed(const ui::KeyEvent& key_event) override;
-
- // app_list::SearchBoxViewDelegate:
- void QueryChanged(app_list::SearchBoxView* sender) override;
-
- // app_list::AppListItemListObserver:
- void OnListItemAdded(size_t index, app_list::AppListItem* item) override;
- void OnListItemRemoved(size_t index, app_list::AppListItem* item) override;
- void OnListItemMoved(size_t from_index,
- size_t to_index,
- app_list::AppListItem* item) override;
-
- // Not owned.
- app_list::AppListViewDelegate* delegate_;
-
- // Views are owned through its hierarchy.
- views::View* system_info_view_;
- views::View* app_icon_container_;
- views::View* search_box_container_;
- views::View* control_icon_container_;
- views::View* logo_;
- app_list::SearchBoxView* search_box_view_;
- app_list::SearchResultListView* search_results_view_;
-
- // The expected height of |search_results_view_|
- int search_results_height_;
-
- // The state to specify how each of the subviews should be laid out, in the
- // range of [0, 1]. 0 means fully BOTTOM state, and 1 is fully CENTERED state.
- float layout_state_;
-
- ObserverList<Observer> observers_;
-
- base::WeakPtrFactory<AthenaStartPageView> weak_factory_;
-
- DISALLOW_COPY_AND_ASSIGN(AthenaStartPageView);
-};
-
-} // namespace athena
-
-#endif // ATHENA_HOME_ATHENA_START_PAGE_VIEW_H_
diff --git a/athena/home/athena_start_page_view_unittest.cc b/athena/home/athena_start_page_view_unittest.cc
deleted file mode 100644
index 9019999..0000000
--- a/athena/home/athena_start_page_view_unittest.cc
+++ /dev/null
@@ -1,279 +0,0 @@
-// Copyright 2014 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 "athena/home/athena_start_page_view.h"
-
-#include "athena/home/home_card_constants.h"
-#include "athena/test/base/athena_test_base.h"
-#include "base/format_macros.h"
-#include "base/strings/stringprintf.h"
-#include "base/strings/utf_string_conversions.h"
-#include "ui/app_list/app_list_switches.h"
-#include "ui/app_list/search_box_model.h"
-#include "ui/app_list/test/app_list_test_model.h"
-#include "ui/app_list/test/app_list_test_view_delegate.h"
-#include "ui/app_list/views/search_box_view.h"
-#include "ui/gfx/geometry/rect.h"
-#include "ui/views/controls/textfield/textfield.h"
-
-namespace athena {
-
-class AthenaTestViewDelegate : public app_list::test::AppListTestViewDelegate {
- public:
- AthenaTestViewDelegate() {}
- ~AthenaTestViewDelegate() override {}
-
- private:
- // app_list::AppListViewDelegate:
- views::View* CreateStartPageWebView(const gfx::Size& size) override {
- return new views::View();
- }
-
- DISALLOW_COPY_AND_ASSIGN(AthenaTestViewDelegate);
-};
-
-class AthenaStartPageViewTest : public test::AthenaTestBase {
- public:
- AthenaStartPageViewTest() {}
- ~AthenaStartPageViewTest() override {}
-
- // testing::Test:
- void SetUp() override {
- test::AthenaTestBase::SetUp();
- for (size_t i = 0; i < GetMaxIconNum(); ++i)
- AddTestItem(i);
-
- view_.reset(new AthenaStartPageView(&view_delegate_));
- SetSize(gfx::Size(1280, 800));
- }
- void TearDown() override {
- view_.reset();
- test::AthenaTestBase::TearDown();
- }
-
- protected:
- void SetSize(const gfx::Size& new_size) {
- view_->SetSize(new_size);
- view_->Layout();
- }
-
- void AddTestItem(size_t index) {
- app_list::test::AppListTestModel* model = view_delegate_.GetTestModel();
- model->AddItem(new app_list::test::AppListTestModel::AppListTestItem(
- GetAppIdFor(index), model));
- }
-
- static size_t GetMaxIconNum() {
- return AthenaStartPageView::GetMaxIconNumForTest();
- }
-
- static std::string GetAppIdFor(size_t index) {
- return base::StringPrintf("id-%" PRIuS, index);
- }
-
- app_list::AppListModel* GetModel() { return view_delegate_.GetTestModel(); }
-
- views::View* GetIconsContainer() { return view_->app_icon_container_; }
-
- gfx::Rect GetIconsBounds() const {
- return view_->app_icon_container_->layer()->GetTargetBounds();
- }
-
- gfx::Rect GetControlBounds() const {
- return view_->control_icon_container_->layer()->GetTargetBounds();
- }
-
- gfx::Rect GetSearchBoxBounds() const {
- return view_->search_box_container_->layer()->GetTargetBounds();
- }
-
- gfx::Rect GetLogoBounds() const {
- return view_->logo_->layer()->GetTargetBounds();
- }
-
- bool IsLogoVisible() const {
- return view_->logo_->layer()->GetTargetOpacity() > 0 &&
- view_->logo_->layer()->GetTargetVisibility();
- }
-
- gfx::Size GetSearchBoxPreferredSize() {
- return view_->search_box_container_->GetPreferredSize();
- }
-
- void SetSearchQuery(const base::string16& query) {
- view_delegate_.GetModel()->search_box()->SetText(query);
- }
-
- base::string16 GetVisibleQuery() {
- return view_->search_box_view_->search_box()->text();
- }
-
- float layout_state() { return view_->layout_state_; }
-
- scoped_ptr<AthenaStartPageView> view_;
-
- private:
- AthenaTestViewDelegate view_delegate_;
-
- DISALLOW_COPY_AND_ASSIGN(AthenaStartPageViewTest);
-};
-
-TEST_F(AthenaStartPageViewTest, BasicLayout) {
- // BOTTOM state. logo is invisible. icons, search box, and controls are
- // arranged horizontally.
- EXPECT_FALSE(IsLogoVisible());
-
- // Three components are aligned at the middle point.
- EXPECT_NEAR(GetIconsBounds().CenterPoint().y(),
- GetControlBounds().CenterPoint().y(),
- 1);
- EXPECT_NEAR(GetIconsBounds().CenterPoint().y(),
- GetSearchBoxBounds().CenterPoint().y(),
- 1);
- EXPECT_NEAR(GetControlBounds().CenterPoint().y(),
- GetSearchBoxBounds().CenterPoint().y(),
- 1);
-
- // Horizonttaly aligned in the order of icons, search_box, and controls.
- EXPECT_LE(GetIconsBounds().right(), GetSearchBoxBounds().x());
- EXPECT_LE(GetSearchBoxBounds().right(), GetControlBounds().x());
- EXPECT_LE(0, GetIconsBounds().y());
-
- // Search box should appear in the middle.
- EXPECT_NEAR(GetSearchBoxBounds().CenterPoint().x(),
- view_->bounds().CenterPoint().x(),
- 1);
-
- // Should fit inside of the home card height.
- EXPECT_GE(kHomeCardHeight, GetIconsBounds().height());
- EXPECT_GE(kHomeCardHeight, GetSearchBoxBounds().height());
- EXPECT_GE(kHomeCardHeight, GetControlBounds().height());
- EXPECT_EQ(GetSearchBoxPreferredSize().ToString(),
- GetSearchBoxBounds().size().ToString());
-
- // CENTERED state. logo is visible. search box appears below the logo,
- // icons and controls are arranged horizontally and below the search box.
- view_->SetLayoutState(1.0f);
- EXPECT_TRUE(IsLogoVisible());
- EXPECT_NEAR(GetLogoBounds().x() + GetLogoBounds().width() / 2,
- GetSearchBoxBounds().x() + GetSearchBoxBounds().width() / 2,
- 1);
- EXPECT_LE(GetLogoBounds().bottom(), GetSearchBoxBounds().y());
- EXPECT_EQ(GetIconsBounds().y(), GetControlBounds().y());
- EXPECT_LE(GetIconsBounds().right(), GetControlBounds().x());
- EXPECT_LE(GetSearchBoxBounds().bottom(), GetIconsBounds().y());
-}
-
-TEST_F(AthenaStartPageViewTest, NarrowLayout) {
- SetSize(gfx::Size(800, 1280));
-
- // BOTTOM state. Similar to BasicLayout.
- EXPECT_FALSE(IsLogoVisible());
- // Three components are aligned at the middle point.
- EXPECT_NEAR(GetIconsBounds().CenterPoint().y(),
- GetControlBounds().CenterPoint().y(),
- 1);
- EXPECT_NEAR(GetIconsBounds().CenterPoint().y(),
- GetSearchBoxBounds().CenterPoint().y(),
- 1);
- EXPECT_NEAR(GetControlBounds().CenterPoint().y(),
- GetSearchBoxBounds().CenterPoint().y(),
- 1);
-
- // Horizonttaly aligned in the order of icons, search_box, and controls.
- EXPECT_LE(GetIconsBounds().right(), GetSearchBoxBounds().x());
- EXPECT_LE(GetSearchBoxBounds().right(), GetControlBounds().x());
- EXPECT_LE(0, GetIconsBounds().y());
-
- // Search box should appear in the middle.
- EXPECT_NEAR(GetSearchBoxBounds().CenterPoint().x(),
- view_->bounds().CenterPoint().x(),
- 1);
-
- // Should fit inside of the home card height.
- EXPECT_GE(kHomeCardHeight, GetIconsBounds().height());
- EXPECT_GE(kHomeCardHeight, GetSearchBoxBounds().height());
- EXPECT_GE(kHomeCardHeight, GetControlBounds().height());
-
- // Search box is narrower because of the size is too narrow.
- EXPECT_GT(GetSearchBoxPreferredSize().width(), GetSearchBoxBounds().width());
- EXPECT_EQ(GetSearchBoxPreferredSize().height(),
- GetSearchBoxBounds().height());
-
- // CENTERED state. Search box should be back to the preferred size.
- view_->SetLayoutState(1.0f);
- EXPECT_EQ(GetSearchBoxPreferredSize().ToString(),
- GetSearchBoxBounds().size().ToString());
-
- // Back to BOTTOM state, the search box shrinks again.
- view_->SetLayoutState(0.0f);
- EXPECT_GT(GetSearchBoxPreferredSize().width(), GetSearchBoxBounds().width());
-
- // Then set back to the original size, now the size is wide enough so the
- // search box bounds becomes as preferred.
- SetSize(gfx::Size(1280, 800));
- EXPECT_EQ(GetSearchBoxPreferredSize().ToString(),
- GetSearchBoxBounds().size().ToString());
-}
-
-TEST_F(AthenaStartPageViewTest, SearchBox) {
- view_->SetLayoutState(1.0f);
- EXPECT_TRUE(IsLogoVisible());
-
- const gfx::Rect base_search_box_bounds = GetSearchBoxBounds();
-
- const base::string16 query = base::UTF8ToUTF16("test");
- SetSearchQuery(query);
-
- EXPECT_FALSE(IsLogoVisible());
- EXPECT_GT(base_search_box_bounds.y(), GetSearchBoxBounds().y());
- EXPECT_EQ(query, GetVisibleQuery());
-
- SetSearchQuery(base::string16());
- EXPECT_TRUE(IsLogoVisible());
- EXPECT_EQ(base_search_box_bounds.ToString(), GetSearchBoxBounds().ToString());
- EXPECT_TRUE(GetVisibleQuery().empty());
-}
-
-TEST_F(AthenaStartPageViewTest, SearchFromBottom) {
- view_->SetLayoutState(0.0f);
-
- const base::string16 query = base::UTF8ToUTF16("test");
- SetSearchQuery(query);
-
- EXPECT_FALSE(IsLogoVisible());
- EXPECT_EQ(query, GetVisibleQuery());
- EXPECT_EQ(1.0f, layout_state());
-
- SetSearchQuery(base::string16());
- EXPECT_TRUE(IsLogoVisible());
- EXPECT_TRUE(GetVisibleQuery().empty());
- EXPECT_EQ(1.0f, layout_state());
-}
-
-TEST_F(AthenaStartPageViewTest, AppAddRemove) {
- gfx::Rect icons_bounds = GetIconsBounds();
- EXPECT_EQ(GetMaxIconNum(),
- static_cast<size_t>(GetIconsContainer()->child_count()));
-
- GetModel()->DeleteItem(GetAppIdFor(1));
-
- // The removed icon disappear, however its bound should not change.
- EXPECT_EQ(GetMaxIconNum() - 1,
- static_cast<size_t>(GetIconsContainer()->child_count()));
- EXPECT_EQ(icons_bounds.size().ToString(), GetIconsBounds().size().ToString());
-
- AddTestItem(GetMaxIconNum() + 1);
- EXPECT_EQ(GetMaxIconNum(),
- static_cast<size_t>(GetIconsContainer()->child_count()));
- EXPECT_EQ(icons_bounds.size().ToString(), GetIconsBounds().size().ToString());
-
- // Adding more doesn't cause any effects.
- AddTestItem(GetMaxIconNum() + 2);
- EXPECT_EQ(GetMaxIconNum(),
- static_cast<size_t>(GetIconsContainer()->child_count()));
- EXPECT_EQ(icons_bounds.size().ToString(), GetIconsBounds().size().ToString());
-}
-
-} // namespace athena
diff --git a/athena/home/home_card_constants.cc b/athena/home/home_card_constants.cc
index 1bf2875..2a951c6 100644
--- a/athena/home/home_card_constants.cc
+++ b/athena/home/home_card_constants.cc
@@ -6,7 +6,7 @@
namespace athena {
-const int kHomeCardHeight = 100;
+const int kHomeCardHeight = 212;
const int kHomeCardDragIndicatorHeight = 2;
const int kHomeCardDragIndicatorWidth = 48;
const int kHomeCardDragIndicatorMarginHeight = 7;
diff --git a/athena/home/home_card_gesture_manager_unittest.cc b/athena/home/home_card_gesture_manager_unittest.cc
index c5c40fc..91d7030 100644
--- a/athena/home/home_card_gesture_manager_unittest.cc
+++ b/athena/home/home_card_gesture_manager_unittest.cc
@@ -186,8 +186,8 @@ TEST_F(HomeCardGestureManagerTest, StartCentered) {
EXPECT_EQ(HomeCard::VISIBLE_CENTERED, last_to_state_);
EXPECT_EQ(1.0f, last_progress_);
- ProcessGestureEvent(ui::ET_GESTURE_SCROLL_UPDATE, 900);
- ProcessGestureEvent(ui::ET_GESTURE_SCROLL_UPDATE, 910);
+ ProcessGestureEvent(ui::ET_GESTURE_SCROLL_UPDATE, 700);
+ ProcessGestureEvent(ui::ET_GESTURE_SCROLL_UPDATE, 710);
EXPECT_EQ(2, GetProgressCountAndReset());
EXPECT_EQ(HomeCard::VISIBLE_BOTTOM, last_from_state_);
EXPECT_EQ(HomeCard::VISIBLE_CENTERED, last_to_state_);
@@ -218,13 +218,13 @@ TEST_F(HomeCardGestureManagerTest, StartBottom) {
EXPECT_EQ(HomeCard::VISIBLE_BOTTOM, final_state_);
// State change for the bigger moves.
- EXPECT_TRUE(ProcessGestureEvent(ui::ET_GESTURE_SCROLL_BEGIN, 950));
+ EXPECT_TRUE(ProcessGestureEvent(ui::ET_GESTURE_SCROLL_BEGIN, 850));
ProcessGestureEvent(ui::ET_GESTURE_SCROLL_UPDATE, 1000);
EXPECT_TRUE(ProcessGestureEvent(ui::ET_GESTURE_SCROLL_END, 1000));
EXPECT_EQ(1, GetEndCountAndReset());
EXPECT_EQ(HomeCard::VISIBLE_MINIMIZED, final_state_);
- EXPECT_TRUE(ProcessGestureEvent(ui::ET_GESTURE_SCROLL_BEGIN, 950));
+ EXPECT_TRUE(ProcessGestureEvent(ui::ET_GESTURE_SCROLL_BEGIN, 850));
ProcessGestureEvent(ui::ET_GESTURE_SCROLL_UPDATE, 300);
EXPECT_TRUE(ProcessGestureEvent(ui::ET_GESTURE_SCROLL_END, 300));
EXPECT_EQ(1, GetEndCountAndReset());
diff --git a/athena/home/home_card_impl.cc b/athena/home/home_card_impl.cc
index f6a64f3..c0603d2 100644
--- a/athena/home/home_card_impl.cc
+++ b/athena/home/home_card_impl.cc
@@ -9,14 +9,14 @@
#include "athena/env/public/athena_env.h"
#include "athena/home/app_list_view_delegate.h"
-#include "athena/home/athena_start_page_view.h"
#include "athena/home/home_card_constants.h"
#include "athena/home/public/app_model_builder.h"
#include "athena/screen/public/screen_manager.h"
#include "athena/util/container_priorities.h"
#include "athena/wm/public/window_manager.h"
+#include "ui/app_list/search_box_model.h"
#include "ui/app_list/views/app_list_main_view.h"
-#include "ui/app_list/views/contents_view.h"
+#include "ui/app_list/views/search_box_view.h"
#include "ui/aura/layout_manager.h"
#include "ui/aura/window.h"
#include "ui/compositor/closure_animation_observer.h"
@@ -36,6 +36,8 @@ namespace {
HomeCard* instance = nullptr;
const float kMinimizedHomeOpacity = 0.65f;
+const int kIndicatorOffset = 24;
+const int kAppListOffset = -128;
gfx::Rect GetBoundsForState(const gfx::Rect& screen_bounds,
HomeCard::State state) {
@@ -122,14 +124,15 @@ class HomeCardLayoutManager : public aura::LayoutManager {
};
// The container view of home card contents of each state.
-class HomeCardView : public views::WidgetDelegateView,
- public AthenaStartPageView::Observer {
+class HomeCardView : public views::WidgetDelegateView {
public:
HomeCardView(app_list::AppListViewDelegate* view_delegate,
aura::Window* container,
HomeCardGestureManager::Delegate* gesture_delegate)
: background_(new views::View),
- main_view_(new AthenaStartPageView(view_delegate)),
+ main_view_(new app_list::AppListMainView(view_delegate)),
+ search_box_view_(
+ new app_list::SearchBoxView(main_view_, view_delegate)),
minimized_background_(new views::View()),
drag_indicator_(new views::View()),
gesture_delegate_(gesture_delegate),
@@ -141,13 +144,16 @@ class HomeCardView : public views::WidgetDelegateView,
background_->SetFillsBoundsOpaquely(false);
AddChildView(background_);
- // Ideally AppListMainView should be used here and have AthenaStartPageView
- // as its child view, so that custom pages and apps grid are available in
- // the home card.
- // TODO(mukai): make it so after the detailed UI has been fixed.
- main_view_->AddObserver(this);
+ main_view_->SetPaintToLayer(true);
+ main_view_->SetFillsBoundsOpaquely(false);
+ main_view_->layer()->SetMasksToBounds(true);
AddChildView(main_view_);
+ search_box_view_->SetPaintToLayer(true);
+ search_box_view_->SetFillsBoundsOpaquely(false);
+ search_box_view_->layer()->SetMasksToBounds(true);
+ AddChildView(search_box_view_);
+
minimized_background_->set_background(
views::Background::CreateSolidBackground(
SkColorSetA(SK_ColorBLACK, 256 * kMinimizedHomeOpacity)));
@@ -162,17 +168,28 @@ class HomeCardView : public views::WidgetDelegateView,
AddChildView(drag_indicator_);
}
- ~HomeCardView() override { main_view_->RemoveObserver(this); }
+ void Init() {
+ main_view_->Init(GetWidget()->GetNativeView(), -1, search_box_view_);
+ }
void SetStateProgress(HomeCard::State from_state,
HomeCard::State to_state,
float progress) {
// TODO(mukai): not clear the focus, but simply close the virtual keyboard.
GetFocusManager()->ClearFocus();
- if (from_state == HomeCard::VISIBLE_CENTERED)
- main_view_->SetLayoutState(1.0f - progress);
- else if (to_state == HomeCard::VISIBLE_CENTERED)
- main_view_->SetLayoutState(progress);
+
+ gfx::Rect from_main_bounds = GetMainViewBounds(from_state);
+ gfx::Rect to_main_bounds = GetMainViewBounds(to_state);
+ if (from_main_bounds != to_main_bounds) {
+ DCHECK_EQ(from_main_bounds.size().ToString(),
+ to_main_bounds.size().ToString());
+ gfx::Rect main_bounds = gfx::Tween::RectValueBetween(
+ progress, from_main_bounds, to_main_bounds);
+ main_view_->SetBoundsRect(main_bounds);
+ main_bounds.set_height(
+ search_box_view_->GetHeightForWidth(main_bounds.width()));
+ search_box_view_->SetBoundsRect(main_bounds);
+ }
float background_opacity = 1.0f;
if (from_state == HomeCard::VISIBLE_MINIMIZED ||
@@ -207,7 +224,8 @@ class HomeCardView : public views::WidgetDelegateView,
}
void SetStateWithAnimation(HomeCard::State state,
- gfx::Tween::Type tween_type) {
+ gfx::Tween::Type tween_type,
+ const base::Closure& on_animation_ended) {
float minimized_opacity =
(state == HomeCard::VISIBLE_MINIMIZED) ? 1.0f : 0.0f;
// |minimized_background_| needs to be visible before scheduling animation.
@@ -241,20 +259,27 @@ class HomeCardView : public views::WidgetDelegateView,
background_->layer()->SetOpacity(background_opacity);
}
- if (state == HomeCard::VISIBLE_CENTERED)
- main_view_->RequestFocusOnSearchBox();
- else
- GetWidget()->GetFocusManager()->ClearFocus();
-
{
ui::ScopedLayerAnimationSettings settings(
drag_indicator_->layer()->GetAnimator());
- settings.SetTweenType(gfx::Tween::EASE_IN_OUT);
+ settings.SetTweenType(tween_type);
drag_indicator_->SetBoundsRect(GetDragIndicatorBounds(state));
}
- main_view_->SetLayoutStateWithAnimation(
- (state == HomeCard::VISIBLE_CENTERED) ? 1.0f : 0.0f, tween_type);
+ {
+ ui::ScopedLayerAnimationSettings settings(
+ main_view_->layer()->GetAnimator());
+ settings.SetTweenType(tween_type);
+ settings.AddObserver(
+ new ui::ClosureAnimationObserver(on_animation_ended));
+ gfx::Rect main_bounds = GetMainViewBounds(state);
+ main_view_->SetBoundsRect(main_bounds);
+ main_bounds.set_height(
+ search_box_view_->GetHeightForWidth(main_bounds.width()));
+ search_box_view_->SetBoundsRect(main_bounds);
+ }
+
+ main_view_->UpdateSearchBoxVisibility();
}
void ClearGesture() {
@@ -282,6 +307,23 @@ class HomeCardView : public views::WidgetDelegateView,
return false;
}
+ void Layout() override {
+ const gfx::Rect contents_bounds = GetContentsBounds();
+ background_->SetBoundsRect(contents_bounds);
+ minimized_background_->SetBoundsRect(contents_bounds);
+ const gfx::Rect drag_indicator_bounds =
+ GetDragIndicatorBounds(HomeCard::Get()->GetState());
+ drag_indicator_->SetBoundsRect(drag_indicator_bounds);
+
+ gfx::Rect main_bounds(GetMainViewBounds(HomeCard::Get()->GetState()));
+ main_view_->SetBoundsRect(main_bounds);
+
+ main_bounds.set_height(
+ search_box_view_->GetHeightForWidth(main_bounds.width()));
+ search_box_view_->SetBoundsRect(main_bounds);
+ }
+
+ private:
gfx::Rect GetDragIndicatorBounds(HomeCard::State state) {
gfx::Rect drag_indicator_bounds(
GetContentsBounds().CenterPoint().x() - kHomeCardDragIndicatorWidth / 2,
@@ -293,13 +335,19 @@ class HomeCardView : public views::WidgetDelegateView,
return drag_indicator_bounds;
}
- void Layout() override {
- gfx::Rect contents_bounds = GetContentsBounds();
- background_->SetBoundsRect(contents_bounds);
- main_view_->SetBoundsRect(contents_bounds);
- minimized_background_->SetBoundsRect(contents_bounds);
- drag_indicator_->SetBoundsRect(
- GetDragIndicatorBounds(HomeCard::Get()->GetState()));
+ gfx::Rect GetMainViewBounds(HomeCard::State state) {
+ const gfx::Rect contents_bounds = GetContentsBounds();
+ const int main_width = main_view_->GetPreferredSize().width();
+ gfx::Rect main_bounds(
+ contents_bounds.CenterPoint().x() - main_width / 2,
+ GetDragIndicatorBounds(state).bottom() + kIndicatorOffset,
+ main_width,
+ contents_bounds.height());
+ // This is a bit hacky but slightly shifting up the main_view to fit
+ // the search box and app icons in the home card.
+ if (state != HomeCard::VISIBLE_CENTERED)
+ main_bounds.set_y(kAppListOffset);
+ return main_bounds;
}
private:
@@ -311,14 +359,9 @@ class HomeCardView : public views::WidgetDelegateView,
// views::WidgetDelegate:
views::View* GetContentsView() override { return this; }
- // AthenaStartPageView::Observer:
- void OnLayoutStateChanged(float new_state) override {
- if (new_state == 1.0f)
- HomeCard::Get()->SetState(HomeCard::VISIBLE_CENTERED);
- }
-
views::View* background_;
- AthenaStartPageView* main_view_;
+ app_list::AppListMainView* main_view_;
+ app_list::SearchBoxView* search_box_view_;
views::View* minimized_background_;
views::View* drag_indicator_;
HomeCard::State state_;
@@ -376,7 +419,9 @@ void HomeCardImpl::Init() {
widget_params.delegate = home_card_view_;
widget_params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW;
home_card_widget_->Init(widget_params);
+ home_card_widget_->GetNativeWindow()->layer()->SetMasksToBounds(true);
+ home_card_view_->Init();
SetState(VISIBLE_MINIMIZED);
home_card_view_->Layout();
@@ -388,6 +433,10 @@ aura::Window* HomeCardImpl::GetHomeCardWindowForTest() const {
return home_card_widget_ ? home_card_widget_->GetNativeWindow() : nullptr;
}
+void HomeCardImpl::ResetQuery() {
+ view_delegate_->GetModel()->search_box()->SetText(base::string16());
+}
+
void HomeCardImpl::InstallAccelerators() {
const AcceleratorData accelerator_data[] = {
{TRIGGER_ON_PRESS, ui::VKEY_L, ui::EF_CONTROL_DOWN,
@@ -413,7 +462,13 @@ void HomeCardImpl::SetState(HomeCard::State state) {
home_card_widget_->ShowInactive();
else
home_card_widget_->Show();
- home_card_view_->SetStateWithAnimation(state, gfx::Tween::EASE_IN_OUT);
+
+ // Query should be reset on state change to reset the main_view. Also it's
+ // not possible to invoke ResetQuery() here, it causes a crash on search.
+ home_card_view_->SetStateWithAnimation(
+ state,
+ gfx::Tween::EASE_IN_OUT,
+ base::Bind(&HomeCardImpl::ResetQuery, base::Unretained(this)));
layout_manager_->Layout(true, gfx::Tween::EASE_IN_OUT);
}
}
@@ -469,7 +524,10 @@ void HomeCardImpl::OnGestureEnded(State final_state, bool is_fling) {
// EASE_OUT is better.
gfx::Tween::Type tween_type =
is_fling ? gfx::Tween::EASE_OUT : gfx::Tween::EASE_IN_OUT;
- home_card_view_->SetStateWithAnimation(state_, tween_type);
+ home_card_view_->SetStateWithAnimation(
+ state_,
+ tween_type,
+ base::Bind(&HomeCardImpl::ResetQuery, base::Unretained(this)));
layout_manager_->Layout(true, tween_type);
}
}
diff --git a/athena/home/home_card_impl.h b/athena/home/home_card_impl.h
index f330b10..a35c31b5 100644
--- a/athena/home/home_card_impl.h
+++ b/athena/home/home_card_impl.h
@@ -12,6 +12,10 @@
#include "athena/input/public/accelerator_manager.h"
#include "athena/wm/public/window_manager_observer.h"
+namespace app_list {
+class AppListViewDelegate;
+}
+
namespace aura {
class Window;
}
@@ -30,7 +34,6 @@ class Widget;
namespace athena {
class AppModelBuilder;
-class AppListViewDelegate;
class HomeCardLayoutManager;
class HomeCardView;
@@ -53,6 +56,8 @@ class ATHENA_EXPORT HomeCardImpl : public HomeCard,
};
void InstallAccelerators();
+ void ResetQuery();
+
// Overridden from HomeCard:
void SetState(HomeCard::State state) override;
State GetState() override;
@@ -86,7 +91,7 @@ class ATHENA_EXPORT HomeCardImpl : public HomeCard,
views::Widget* home_card_widget_;
HomeCardView* home_card_view_;
- scoped_ptr<AppListViewDelegate> view_delegate_;
+ scoped_ptr<app_list::AppListViewDelegate> view_delegate_;
HomeCardLayoutManager* layout_manager_;
DISALLOW_COPY_AND_ASSIGN(HomeCardImpl);
diff --git a/athena/home/home_card_unittest.cc b/athena/home/home_card_unittest.cc
index abbdbdf..d8a630f 100644
--- a/athena/home/home_card_unittest.cc
+++ b/athena/home/home_card_unittest.cc
@@ -28,12 +28,6 @@ aura::Window* GetHomeCardWindow() {
GetHomeCardWindowForTest();
}
-// Returns true if the keyboard focus is on the search box.
-bool IsSearchBoxFocused(aura::Window* home_card) {
- return views::Widget::GetWidgetForNativeWindow(home_card)->
- GetContentsView()->GetViewByID(kHomeCardSearchBoxId)->HasFocus();
-}
-
typedef test::AthenaTestBase HomeCardTest;
TEST_F(HomeCardTest, BasicTransition) {
@@ -265,35 +259,6 @@ TEST_F(HomeCardTest, GesturesToFullDirectly) {
EXPECT_TRUE(WindowManager::Get()->IsOverviewModeActive());
}
-TEST_F(HomeCardTest, KeyboardFocus) {
- ASSERT_EQ(HomeCard::VISIBLE_MINIMIZED, HomeCard::Get()->GetState());
- aura::Window* home_card = GetHomeCardWindow();
- ASSERT_FALSE(IsSearchBoxFocused(home_card));
-
- WindowManager::Get()->EnterOverview();
- ASSERT_FALSE(IsSearchBoxFocused(home_card));
-
- ui::test::EventGenerator generator(root_window());
- gfx::Rect screen_rect(root_window()->bounds());
-
- const int bottom = screen_rect.bottom();
- const int x = screen_rect.x() + 1;
-
- generator.GestureScrollSequence(gfx::Point(x, bottom - 40),
- gfx::Point(x, 10),
- base::TimeDelta::FromSeconds(1),
- 10);
- EXPECT_EQ(HomeCard::VISIBLE_CENTERED, HomeCard::Get()->GetState());
- EXPECT_TRUE(IsSearchBoxFocused(home_card));
-
- generator.GestureScrollSequence(gfx::Point(x, 10),
- gfx::Point(x, bottom - 100),
- base::TimeDelta::FromSeconds(1),
- 10);
- EXPECT_EQ(HomeCard::VISIBLE_BOTTOM, HomeCard::Get()->GetState());
- EXPECT_FALSE(IsSearchBoxFocused(home_card));
-}
-
TEST_F(HomeCardTest, DontMinimizeWithModalWindow) {
aura::Window* home_card = GetHomeCardWindow();