Commit 5aa92900 authored by David Black's avatar David Black Committed by Commit Bot

Rough in support for multiple selection in holding space.

Holding space needs to support selection of multiple holding space items
to perform bulk context menu and drag/drop operations on them at a time.

This CL refactors HoldingSpaceItemContextMenu into a shared
HoldingSpaceItemViewDelegate to facilitate these requirements.

Note that this CL does not change any existing behavior, just lays the
groundwork for supporting multiple selection.

Bug: 1129981
Change-Id: If4da6c19ba01bd7104a1b1487350c362d7be1dd4
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2419136
Commit-Queue: David Black <dmblack@google.com>
Reviewed-by: default avatarAhmed Mehfooz <amehfooz@chromium.org>
Cr-Commit-Position: refs/heads/master@{#809625}
parent 6a468257
......@@ -926,12 +926,12 @@ component("ash") {
"system/holding_space/holding_space_item_chip_view.h",
"system/holding_space/holding_space_item_chips_container.cc",
"system/holding_space/holding_space_item_chips_container.h",
"system/holding_space/holding_space_item_context_menu.cc",
"system/holding_space/holding_space_item_context_menu.h",
"system/holding_space/holding_space_item_screenshot_view.cc",
"system/holding_space/holding_space_item_screenshot_view.h",
"system/holding_space/holding_space_item_view.cc",
"system/holding_space/holding_space_item_view.h",
"system/holding_space/holding_space_item_view_delegate.cc",
"system/holding_space/holding_space_item_view_delegate.h",
"system/holding_space/holding_space_item_views_container.cc",
"system/holding_space/holding_space_item_views_container.h",
"system/holding_space/holding_space_tray.cc",
......
......@@ -30,8 +30,10 @@
namespace ash {
HoldingSpaceItemChipView::HoldingSpaceItemChipView(const HoldingSpaceItem* item)
: HoldingSpaceItemView(item) {
HoldingSpaceItemChipView::HoldingSpaceItemChipView(
HoldingSpaceItemViewDelegate* delegate,
const HoldingSpaceItem* item)
: HoldingSpaceItemView(delegate, item) {
auto* layout = SetLayoutManager(std::make_unique<views::BoxLayout>(
views::BoxLayout::Orientation::kHorizontal,
gfx::Insets(kHoldingSpaceChipPadding), kHoldingSpaceChipChildSpacing));
......
......@@ -21,6 +21,7 @@ class ToggleImageButton;
namespace ash {
class HoldingSpaceItem;
class HoldingSpaceItemViewDelegate;
namespace tray {
class RoundedImageView;
......@@ -33,7 +34,8 @@ class ASH_EXPORT HoldingSpaceItemChipView : public HoldingSpaceItemView,
public:
METADATA_HEADER(HoldingSpaceItemChipView);
explicit HoldingSpaceItemChipView(const HoldingSpaceItem* item);
HoldingSpaceItemChipView(HoldingSpaceItemViewDelegate* delegate,
const HoldingSpaceItem* item);
HoldingSpaceItemChipView(const HoldingSpaceItemChipView&) = delete;
HoldingSpaceItemChipView& operator=(const HoldingSpaceItemChipView&) = delete;
~HoldingSpaceItemChipView() override;
......
......@@ -5,9 +5,6 @@
#include "ash/system/holding_space/holding_space_item_chips_container.h"
#include "ash/public/cpp/holding_space/holding_space_constants.h"
#include "ash/public/cpp/holding_space/holding_space_item.h"
#include "ash/system/holding_space/holding_space_item_chip_view.h"
#include "base/debug/stack_trace.h"
#include "ui/views/layout/layout_manager_base.h"
#include "ui/views/layout/proposed_layout.h"
......
......@@ -10,8 +10,7 @@
namespace ash {
// A container view which automatically arranges item chips into a 2 column
// grid.
// A container view which arranges item chips into a 2 column grid.
class HoldingSpaceItemChipsContainer : public views::View {
public:
HoldingSpaceItemChipsContainer();
......
// Copyright 2020 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_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_ITEM_CONTEXT_MENU_H_
#define ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_ITEM_CONTEXT_MENU_H_
#include <memory>
#include "ash/ash_export.h"
#include "ash/public/cpp/holding_space/holding_space_item.h"
#include "ui/base/models/simple_menu_model.h"
#include "ui/views/context_menu_controller.h"
namespace views {
class MenuRunner;
} // namespace views
namespace ash {
// This class handles creation of the context menu view and handling
// commands available in the menu.
class ASH_EXPORT HoldingSpaceItemContextMenu
: public views::ContextMenuController,
public ui::SimpleMenuModel::Delegate {
public:
explicit HoldingSpaceItemContextMenu(const HoldingSpaceItem* item);
HoldingSpaceItemContextMenu(const HoldingSpaceItemContextMenu&) = delete;
HoldingSpaceItemContextMenu& operator=(const HoldingSpaceItemContextMenu&) =
delete;
~HoldingSpaceItemContextMenu() override;
// views::ContextMenuController:
void ShowContextMenuForViewImpl(views::View* source,
const gfx::Point& point,
ui::MenuSourceType source_type) override;
// SimpleMenuModel::Delegate:
void ExecuteCommand(int command_id, int event_flags) override;
private:
ui::SimpleMenuModel* BuildMenuModel();
std::unique_ptr<ui::SimpleMenuModel> context_menu_model_;
std::unique_ptr<views::MenuRunner> context_menu_runner_;
// The holding space item that this context menu's actions will effect.
const HoldingSpaceItem* const item_;
};
} // namespace ash
#endif // ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_ITEM_CONTEXT_MENU_H_
......@@ -16,8 +16,9 @@
namespace ash {
HoldingSpaceItemScreenshotView::HoldingSpaceItemScreenshotView(
HoldingSpaceItemViewDelegate* delegate,
const HoldingSpaceItem* item)
: HoldingSpaceItemView(item) {
: HoldingSpaceItemView(delegate, item) {
SetLayoutManager(std::make_unique<views::FillLayout>());
image_ = AddChildView(
......
......@@ -13,6 +13,7 @@
namespace ash {
class HoldingSpaceItem;
class HoldingSpaceItemViewDelegate;
namespace tray {
class RoundedImageView;
......@@ -22,7 +23,8 @@ class ASH_EXPORT HoldingSpaceItemScreenshotView : public HoldingSpaceItemView {
public:
METADATA_HEADER(HoldingSpaceItemScreenshotView);
explicit HoldingSpaceItemScreenshotView(const HoldingSpaceItem* item);
HoldingSpaceItemScreenshotView(HoldingSpaceItemViewDelegate* delegate,
const HoldingSpaceItem* item);
HoldingSpaceItemScreenshotView(const HoldingSpaceItemScreenshotView&) =
delete;
HoldingSpaceItemScreenshotView& operator=(
......
......@@ -4,41 +4,36 @@
#include "ash/system/holding_space/holding_space_item_view.h"
#include "ash/public/cpp/holding_space/holding_space_client.h"
#include "ash/public/cpp/holding_space/holding_space_constants.h"
#include "ash/public/cpp/holding_space/holding_space_controller.h"
#include "ash/public/cpp/holding_space/holding_space_item.h"
#include "ash/public/cpp/shelf_config.h"
#include "ash/strings/grit/ash_strings.h"
#include "ash/system/holding_space/holding_space_item_context_menu.h"
#include "base/bind_helpers.h"
#include "ui/base/dragdrop/drag_drop_types.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/gfx/text_constants.h"
#include "ash/system/holding_space/holding_space_item_view_delegate.h"
#include "ui/base/class_property.h"
#include "ui/views/accessibility/view_accessibility.h"
#include "ui/views/controls/focus_ring.h"
#include "ui/views/controls/highlight_path_generator.h"
#include "ui/views/controls/menu/menu_runner.h"
namespace ash {
namespace {
// Helpers ---------------------------------------------------------------------
// Attempts to open the specified holding space `item`.
void OpenItem(const HoldingSpaceItem& item) {
HoldingSpaceController::Get()->client()->OpenItem(item, base::DoNothing());
}
// A UI class property used to identify if a view is an instance of
// `HoldingSpaceItemView`. Class name is not an adequate identifier as it may be
// overridden by subclasses.
DEFINE_UI_CLASS_PROPERTY_KEY(bool, kIsHoldingSpaceItemViewProperty, false)
} // namespace
// HoldingSpaceItemView --------------------------------------------------------
HoldingSpaceItemView::HoldingSpaceItemView(const HoldingSpaceItem* item)
: item_(item),
context_menu_(std::make_unique<HoldingSpaceItemContextMenu>(item_)) {
set_context_menu_controller(context_menu_.get());
HoldingSpaceItemView::HoldingSpaceItemView(
HoldingSpaceItemViewDelegate* delegate,
const HoldingSpaceItem* item)
: delegate_(delegate), item_(item) {
SetProperty(kIsHoldingSpaceItemViewProperty, true);
set_context_menu_controller(delegate_);
set_drag_controller(delegate_);
SetPaintToLayer();
layer()->SetFillsBoundsOpaquely(false);
......@@ -54,10 +49,14 @@ HoldingSpaceItemView::HoldingSpaceItemView(const HoldingSpaceItem* item)
kHoldingSpaceCornerRadius);
}
HoldingSpaceItemView::~HoldingSpaceItemView() = default;
HoldingSpaceItemView::~HoldingSpaceItemView() {
delegate_->OnHoldingSpaceItemViewDestroyed(this);
}
int HoldingSpaceItemView::GetDragOperations(const gfx::Point& point) {
return ui::DragDropTypes::DRAG_COPY;
// static
HoldingSpaceItemView* HoldingSpaceItemView::Cast(views::View* view) {
DCHECK(view->GetProperty(kIsHoldingSpaceItemViewProperty));
return static_cast<HoldingSpaceItemView*>(view);
}
SkColor HoldingSpaceItemView::GetInkDropBaseColor() const {
......@@ -65,29 +64,15 @@ SkColor HoldingSpaceItemView::GetInkDropBaseColor() const {
}
void HoldingSpaceItemView::OnGestureEvent(ui::GestureEvent* event) {
if (event->type() == ui::ET_GESTURE_TAP)
OpenItem(*item());
delegate_->OnHoldingSpaceItemViewGestureEvent(this, *event);
}
bool HoldingSpaceItemView::OnKeyPressed(const ui::KeyEvent& event) {
if (event.key_code() == ui::KeyboardCode::VKEY_RETURN) {
OpenItem(*item());
return true;
}
return false;
return delegate_->OnHoldingSpaceItemViewKeyPressed(this, event);
}
bool HoldingSpaceItemView::OnMousePressed(const ui::MouseEvent& event) {
if (event.flags() & ui::EF_IS_DOUBLE_CLICK) {
OpenItem(*item());
return true;
}
return false;
}
void HoldingSpaceItemView::WriteDragData(const gfx::Point& point,
ui::OSExchangeData* data) {
data->SetFilename(item_->file_path());
return delegate_->OnHoldingSpaceItemViewMousePressed(this, event);
}
} // namespace ash
......@@ -5,38 +5,37 @@
#ifndef ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_ITEM_VIEW_H_
#define ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_ITEM_VIEW_H_
#include <memory>
#include "ash/ash_export.h"
#include "ui/base/dragdrop/drag_drop_types.h"
#include "ui/views/animation/ink_drop_host_view.h"
namespace ash {
class HoldingSpaceItem;
class HoldingSpaceItemContextMenu;
class HoldingSpaceItemViewDelegate;
// Base class for HoldingSpaceItemChipView and HoldingSpaceItemScreenshotView.
class ASH_EXPORT HoldingSpaceItemView : public views::InkDropHostView {
public:
explicit HoldingSpaceItemView(const HoldingSpaceItem* item);
HoldingSpaceItemView(HoldingSpaceItemViewDelegate*, const HoldingSpaceItem*);
HoldingSpaceItemView(const HoldingSpaceItemView&) = delete;
HoldingSpaceItemView& operator=(const HoldingSpaceItemView&) = delete;
~HoldingSpaceItemView() override;
// Returns `view` cast as a `HoldingSpaceItemView`. Note that this performs a
// DCHECK to assert that `view` is in fact a `HoldingSpaceItemView` instance.
static HoldingSpaceItemView* Cast(views::View* view);
// views::InkDropHostView:
int GetDragOperations(const gfx::Point& point) override;
SkColor GetInkDropBaseColor() const override;
void OnGestureEvent(ui::GestureEvent* event) override;
bool OnKeyPressed(const ui::KeyEvent& event) override;
bool OnMousePressed(const ui::MouseEvent& event) override;
void WriteDragData(const gfx::Point& point, ui::OSExchangeData*) override;
const HoldingSpaceItem* item() const { return item_; }
private:
HoldingSpaceItemViewDelegate* delegate_;
const HoldingSpaceItem* const item_;
std::unique_ptr<HoldingSpaceItemContextMenu> const context_menu_;
};
} // namespace ash
......
......@@ -2,17 +2,19 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "ash/system/holding_space/holding_space_item_context_menu.h"
#include "ash/system/holding_space/holding_space_item_view_delegate.h"
#include "ash/public/cpp/holding_space/holding_space_client.h"
#include "ash/public/cpp/holding_space/holding_space_constants.h"
#include "ash/public/cpp/holding_space/holding_space_controller.h"
#include "ash/public/cpp/holding_space/holding_space_item.h"
#include "ash/public/cpp/holding_space/holding_space_model.h"
#include "ash/resources/vector_icons/vector_icons.h"
#include "ash/strings/grit/ash_strings.h"
#include "ash/system/holding_space/holding_space_item_view.h"
#include "base/bind.h"
#include "net/base/mime_util.h"
#include "ui/base/dragdrop/drag_drop_types.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/models/simple_menu_model.h"
#include "ui/views/controls/menu/menu_runner.h"
......@@ -21,16 +23,79 @@
namespace ash {
HoldingSpaceItemContextMenu::HoldingSpaceItemContextMenu(
const HoldingSpaceItem* item)
: item_(item) {}
namespace {
HoldingSpaceItemContextMenu::~HoldingSpaceItemContextMenu() = default;
// It is expected that all `HoldingSpaceItemView`s share the same delegate in
// order to support multiple selections. We cache the singleton `instance` in
// order to enforce this requirement.
HoldingSpaceItemViewDelegate* instance = nullptr;
void HoldingSpaceItemContextMenu::ShowContextMenuForViewImpl(
// Helpers ---------------------------------------------------------------------
// Attempts to open the specified holding space `item`.
void OpenItem(const HoldingSpaceItem& item) {
HoldingSpaceController::Get()->client()->OpenItem(item, base::DoNothing());
}
} // namespace
// HoldingSpaceItemViewDelegate ------------------------------------------------
HoldingSpaceItemViewDelegate::HoldingSpaceItemViewDelegate() {
DCHECK_EQ(nullptr, instance);
instance = this;
}
HoldingSpaceItemViewDelegate::~HoldingSpaceItemViewDelegate() {
DCHECK_EQ(instance, this);
instance = nullptr;
}
// TODO(dmblack): Implement multiple selection.
void HoldingSpaceItemViewDelegate::OnHoldingSpaceItemViewGestureEvent(
HoldingSpaceItemView* view,
const ui::GestureEvent& event) {
if (event.type() == ui::ET_GESTURE_TAP)
OpenItem(*view->item());
}
// TODO(dmblack): Handle multiple selection.
bool HoldingSpaceItemViewDelegate::OnHoldingSpaceItemViewKeyPressed(
HoldingSpaceItemView* view,
const ui::KeyEvent& event) {
if (event.key_code() == ui::KeyboardCode::VKEY_RETURN) {
OpenItem(*view->item());
return true;
}
return false;
}
// TODO(dmblack): Handle multiple selection.
bool HoldingSpaceItemViewDelegate::OnHoldingSpaceItemViewMousePressed(
HoldingSpaceItemView* view,
const ui::MouseEvent& event) {
if (event.flags() & ui::EF_IS_DOUBLE_CLICK) {
OpenItem(*view->item());
return true;
}
return false;
}
void HoldingSpaceItemViewDelegate::OnHoldingSpaceItemViewDestroyed(
HoldingSpaceItemView* view) {
selected_views_by_item_id_.erase(view->item()->id());
}
// TODO(dmblack): Handle multiple selection.
void HoldingSpaceItemViewDelegate::ShowContextMenuForViewImpl(
views::View* source,
const gfx::Point& point,
ui::MenuSourceType source_type) {
selected_views_by_item_id_.clear();
HoldingSpaceItemView* selected_view = HoldingSpaceItemView::Cast(source);
selected_views_by_item_id_[selected_view->item()->id()] = selected_view;
int run_types = views::MenuRunner::USE_TOUCHABLE_LAYOUT |
views::MenuRunner::CONTEXT_MENU |
views::MenuRunner::FIXED_ANCHOR;
......@@ -44,27 +109,65 @@ void HoldingSpaceItemContextMenu::ShowContextMenuForViewImpl(
source_type);
}
void HoldingSpaceItemContextMenu::ExecuteCommand(int command_id,
int event_flags) {
// TODO(dmblack): Handle multiple selection.
bool HoldingSpaceItemViewDelegate::CanStartDragForView(
views::View* sender,
const gfx::Point& press_pt,
const gfx::Point& current_pt) {
selected_views_by_item_id_.clear();
HoldingSpaceItemView* selected_view = HoldingSpaceItemView::Cast(sender);
selected_views_by_item_id_[selected_view->item()->id()] = selected_view;
return true;
}
int HoldingSpaceItemViewDelegate::GetDragOperationsForView(
views::View* sender,
const gfx::Point& press_pt) {
return ui::DragDropTypes::DRAG_COPY;
}
// TODO(dmblack): Handle multiple selection.
void HoldingSpaceItemViewDelegate::WriteDragDataForView(
views::View* sender,
const gfx::Point& press_pt,
ui::OSExchangeData* data) {
DCHECK_EQ(1u, selected_views_by_item_id_.size());
auto* selected_view = selected_views_by_item_id_.begin()->second;
data->SetFilename(selected_view->item()->file_path());
}
// TODO(dmblack): Handle multiple selection.
void HoldingSpaceItemViewDelegate::ExecuteCommand(int command_id,
int event_flags) {
DCHECK_EQ(1u, selected_views_by_item_id_.size());
auto* selected_view = selected_views_by_item_id_.begin()->second;
switch (command_id) {
case HoldingSpaceCommandId::kCopyImageToClipboard:
HoldingSpaceController::Get()->client()->CopyImageToClipboard(
*item_, base::DoNothing());
*selected_view->item(), base::DoNothing());
break;
case HoldingSpaceCommandId::kPinItem:
HoldingSpaceController::Get()->client()->PinItem(*item_);
HoldingSpaceController::Get()->client()->PinItem(*selected_view->item());
break;
case HoldingSpaceCommandId::kShowInFolder:
HoldingSpaceController::Get()->client()->ShowItemInFolder(
*item_, base::DoNothing());
*selected_view->item(), base::DoNothing());
break;
case HoldingSpaceCommandId::kUnpinItem:
HoldingSpaceController::Get()->client()->UnpinItem(*item_);
HoldingSpaceController::Get()->client()->UnpinItem(
*selected_view->item());
break;
}
}
ui::SimpleMenuModel* HoldingSpaceItemContextMenu::BuildMenuModel() {
// TODO(dmblack): Handle multiple selection.
ui::SimpleMenuModel* HoldingSpaceItemViewDelegate::BuildMenuModel() {
DCHECK_EQ(1u, selected_views_by_item_id_.size());
auto* selected_view = selected_views_by_item_id_.begin()->second;
context_menu_model_ = std::make_unique<ui::SimpleMenuModel>(this);
context_menu_model_->AddItemWithIcon(
HoldingSpaceCommandId::kShowInFolder,
......@@ -73,9 +176,9 @@ ui::SimpleMenuModel* HoldingSpaceItemContextMenu::BuildMenuModel() {
ui::ImageModel::FromVectorIcon(kFolderIcon));
std::string mime_type;
const bool is_image =
net::GetMimeTypeFromFile(item_->file_path(), &mime_type) &&
net::MatchesMimeType(kMimeTypeImage, mime_type);
const bool is_image = net::GetMimeTypeFromFile(
selected_view->item()->file_path(), &mime_type) &&
net::MatchesMimeType(kMimeTypeImage, mime_type);
if (is_image) {
context_menu_model_->AddItemWithIcon(
......@@ -86,8 +189,10 @@ ui::SimpleMenuModel* HoldingSpaceItemContextMenu::BuildMenuModel() {
}
const bool is_pinned = HoldingSpaceController::Get()->model()->GetItem(
HoldingSpaceItem::GetFileBackedItemId(HoldingSpaceItem::Type::kPinnedFile,
item_->file_path()));
HoldingSpaceItem::GetFileBackedItemId(
HoldingSpaceItem::Type::kPinnedFile,
selected_view->item()->file_path()));
if (!is_pinned) {
context_menu_model_->AddItemWithIcon(
HoldingSpaceCommandId::kPinItem,
......
// Copyright 2020 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_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_ITEM_VIEW_DELEGATE_H_
#define ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_ITEM_VIEW_DELEGATE_H_
#include <map>
#include <memory>
#include <string>
#include "ash/ash_export.h"
#include "ui/base/models/simple_menu_model.h"
#include "ui/views/context_menu_controller.h"
#include "ui/views/drag_controller.h"
namespace ui {
class GestureEvent;
class KeyEvent;
class MouseEvent;
} // namespace ui
namespace views {
class MenuRunner;
} // namespace views
namespace ash {
class HoldingSpaceItemView;
// TODO(dmblack): Implement multiple selection.
// A delegate for `HoldingSpaceItemView`s which implements context menu,
// drag-and-drop, and selection functionality. In order to support multiple
// selections at a time, all `HoldingSpaceItemView`s must share the same
// `HoldingSpaceItemViewDelegate` instance.
class ASH_EXPORT HoldingSpaceItemViewDelegate
: public views::ContextMenuController,
public views::DragController,
public ui::SimpleMenuModel::Delegate {
public:
HoldingSpaceItemViewDelegate();
HoldingSpaceItemViewDelegate(const HoldingSpaceItemViewDelegate&) = delete;
HoldingSpaceItemViewDelegate& operator=(const HoldingSpaceItemViewDelegate&) =
delete;
~HoldingSpaceItemViewDelegate() override;
// Invoked when `view` receives the specified gesture `event`.
void OnHoldingSpaceItemViewGestureEvent(HoldingSpaceItemView* view,
const ui::GestureEvent& event);
// Invoked when `view` receives the specified key pressed `event`.
bool OnHoldingSpaceItemViewKeyPressed(HoldingSpaceItemView* view,
const ui::KeyEvent& event);
// Invoked when `view` receives the specified mouse pressed `event`.
bool OnHoldingSpaceItemViewMousePressed(HoldingSpaceItemView* view,
const ui::MouseEvent& event);
// Invoked when `view` has been destroyed.
void OnHoldingSpaceItemViewDestroyed(HoldingSpaceItemView* view);
private:
// views::ContextMenuController:
void ShowContextMenuForViewImpl(views::View* source,
const gfx::Point& point,
ui::MenuSourceType source_type) override;
// views::DragController:
bool CanStartDragForView(views::View* sender,
const gfx::Point& press_pt,
const gfx::Point& current_pt) override;
int GetDragOperationsForView(views::View* sender,
const gfx::Point& press_pt) override;
void WriteDragDataForView(views::View* sender,
const gfx::Point& press_pt,
ui::OSExchangeData* data) override;
// SimpleMenuModel::Delegate:
void ExecuteCommand(int command_id, int event_flags) override;
// Builds and returns a raw pointer to `context_menu_model_`.
ui::SimpleMenuModel* BuildMenuModel();
std::unique_ptr<ui::SimpleMenuModel> context_menu_model_;
std::unique_ptr<views::MenuRunner> context_menu_runner_;
std::map<std::string, HoldingSpaceItemView*> selected_views_by_item_id_;
};
} // namespace ash
#endif // ASH_SYSTEM_HOLDING_SPACE_HOLDING_SPACE_ITEM_VIEW_DELEGATE_H_
......@@ -149,8 +149,8 @@ void HoldingSpaceTray::ShowBubble(bool show_by_click) {
bubble_view->set_margins(GetSecondaryBubbleInsets());
// Add pinned files container.
pinned_files_container_ =
bubble_view->AddChildView(std::make_unique<PinnedFilesContainer>());
pinned_files_container_ = bubble_view->AddChildView(
std::make_unique<PinnedFilesContainer>(&delegate_));
SetupChildLayer(pinned_files_container_);
// Separator between the two containers, gives illusion of 2 separate bubbles.
......@@ -159,8 +159,8 @@ void HoldingSpaceTray::ShowBubble(bool show_by_click) {
separator->SetBorder(views::CreateEmptyBorder(
gfx::Insets(kHoldingSpaceContainerSpacing, 0, 0, 0)));
recent_files_container_ =
bubble_view->AddChildView(std::make_unique<RecentFilesContainer>());
recent_files_container_ = bubble_view->AddChildView(
std::make_unique<RecentFilesContainer>(&delegate_));
SetupChildLayer(recent_files_container_);
// Show the bubble.
......
......@@ -8,6 +8,7 @@
#include <memory>
#include "ash/ash_export.h"
#include "ash/system/holding_space/holding_space_item_view_delegate.h"
#include "ash/system/tray/tray_background_view.h"
#include "base/memory/weak_ptr.h"
......@@ -60,6 +61,10 @@ class ASH_EXPORT HoldingSpaceTray : public TrayBackgroundView {
std::unique_ptr<TrayBubbleWrapper> bubble_;
// The singleton delegate for `HoldingSpaceItemView`s that implements support
// for context menu, drag-and-drop, and multiple selection.
HoldingSpaceItemViewDelegate delegate_;
PinnedFilesContainer* pinned_files_container_ = nullptr;
RecentFilesContainer* recent_files_container_ = nullptr;
......
......@@ -22,7 +22,9 @@
namespace ash {
PinnedFilesContainer::PinnedFilesContainer() {
PinnedFilesContainer::PinnedFilesContainer(
HoldingSpaceItemViewDelegate* delegate)
: delegate_(delegate) {
SetID(kHoldingSpacePinnedFilesContainerId);
SetLayoutManager(std::make_unique<views::BoxLayout>(
......@@ -52,7 +54,8 @@ void PinnedFilesContainer::AddHoldingSpaceItemView(
if (item->type() == HoldingSpaceItem::Type::kPinnedFile) {
views_by_item_id_[item->id()] = item_chips_container_->AddChildViewAt(
std::make_unique<HoldingSpaceItemChipView>(item), 0 /*index*/);
std::make_unique<HoldingSpaceItemChipView>(delegate_, item),
/*index=*/0);
}
}
......
......@@ -12,11 +12,12 @@
namespace ash {
class HoldingSpaceItemChipsContainer;
class HoldingSpaceItemViewDelegate;
// Container for pinned files that the user adds to the holding space bubble.
class PinnedFilesContainer : public HoldingSpaceItemViewsContainer {
public:
PinnedFilesContainer();
explicit PinnedFilesContainer(HoldingSpaceItemViewDelegate* delegate);
PinnedFilesContainer(const PinnedFilesContainer& other) = delete;
PinnedFilesContainer& operator=(const PinnedFilesContainer& other) = delete;
~PinnedFilesContainer() override;
......@@ -27,6 +28,7 @@ class PinnedFilesContainer : public HoldingSpaceItemViewsContainer {
void RemoveHoldingSpaceItemView(const HoldingSpaceItem* item) override;
private:
HoldingSpaceItemViewDelegate* const delegate_;
HoldingSpaceItemChipsContainer* item_chips_container_ = nullptr;
std::map<std::string, views::View*> views_by_item_id_;
......
......@@ -22,7 +22,9 @@
namespace ash {
RecentFilesContainer::RecentFilesContainer() {
RecentFilesContainer::RecentFilesContainer(
HoldingSpaceItemViewDelegate* delegate)
: delegate_(delegate) {
SetID(kHoldingSpaceRecentFilesContainerId);
SetLayoutManager(std::make_unique<views::BoxLayout>(
......@@ -66,10 +68,12 @@ void RecentFilesContainer::AddHoldingSpaceItemView(
DCHECK(!base::Contains(views_by_item_id_, item->id()));
if (item->type() == HoldingSpaceItem::Type::kScreenshot) {
views_by_item_id_[item->id()] = screenshots_container_->AddChildViewAt(
std::make_unique<HoldingSpaceItemScreenshotView>(item), 0 /*index*/);
std::make_unique<HoldingSpaceItemScreenshotView>(delegate_, item),
/*index=*/0);
} else if (item->type() == HoldingSpaceItem::Type::kDownload) {
views_by_item_id_[item->id()] = recent_downloads_container_->AddChildViewAt(
std::make_unique<HoldingSpaceItemChipView>(item), 0 /*index*/);
std::make_unique<HoldingSpaceItemChipView>(delegate_, item),
/*index=*/0);
}
}
......@@ -84,13 +88,13 @@ void RecentFilesContainer::RemoveHoldingSpaceItemView(
auto it = views_by_item_id_.find(item->id());
if (it == views_by_item_id_.end())
return;
views::View* view = it->second;
if (item->type() == HoldingSpaceItem::Type::kScreenshot) {
screenshots_container_->RemoveChildViewT(view);
screenshots_container_->RemoveChildViewT(it->second);
} else if (item->type() == HoldingSpaceItem::Type::kDownload) {
recent_downloads_container_->RemoveChildViewT(view);
recent_downloads_container_->RemoveChildViewT(it->second);
}
views_by_item_id_.erase(it);
}
......
......@@ -12,11 +12,12 @@
namespace ash {
class HoldingSpaceItemChipsContainer;
class HoldingSpaceItemViewDelegate;
// Container for the recent files (Screenshots, downloads etc).
class RecentFilesContainer : public HoldingSpaceItemViewsContainer {
public:
RecentFilesContainer();
explicit RecentFilesContainer(HoldingSpaceItemViewDelegate* delegate);
RecentFilesContainer(const RecentFilesContainer& other) = delete;
RecentFilesContainer& operator=(const RecentFilesContainer& other) = delete;
~RecentFilesContainer() override;
......@@ -27,6 +28,7 @@ class RecentFilesContainer : public HoldingSpaceItemViewsContainer {
void RemoveHoldingSpaceItemView(const HoldingSpaceItem* item) override;
private:
HoldingSpaceItemViewDelegate* const delegate_;
views::View* screenshots_container_ = nullptr;
HoldingSpaceItemChipsContainer* recent_downloads_container_ = nullptr;
......
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