0

De-anonymize code that will call deprecated WidgetDelegate APIs.

These APIs will be locked with passkeys, which requires friending the
caller code, which requires it to be forward-declared, which means it
can't be in an anonymous namespace.

Bug: 407812144
Change-Id: I42c261f08f094badc0fc9f41ee22b485aa00e8c8
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6435150
Commit-Queue: Peter Kasting <pkasting@chromium.org>
Reviewed-by: Mitsuru Oshima <oshima@chromium.org>
Reviewed-by: Nancy Xiao <nancylanxiao@google.com>
Reviewed-by: Dana Fried <dfried@chromium.org>
Reviewed-by: Trevor Perrier <perrier@chromium.org>
Cr-Commit-Position: refs/heads/main@{#1443749}
This commit is contained in:
Peter Kasting
2025-04-07 13:57:45 -07:00
committed by Chromium LUCI CQ
parent ca2b56e91b
commit ca6806f38a
25 changed files with 370 additions and 375 deletions

@@ -177,15 +177,6 @@ bool IsAmbientModeEnabled() {
return IsUserAmbientModeEnabled() || IsAmbientModeManagedScreensaverEnabled(); return IsUserAmbientModeEnabled() || IsAmbientModeManagedScreensaverEnabled();
} }
class AmbientWidgetDelegate : public views::WidgetDelegate {
public:
AmbientWidgetDelegate() {
SetCanFullscreen(true);
SetCanMaximize(true);
SetOwnedByWidget(true);
}
};
void RecordManagedScreensaverEnabledPref() { void RecordManagedScreensaverEnabledPref() {
if (PrefService* pref_service = GetActivePrefService(); if (PrefService* pref_service = GetActivePrefService();
pref_service && pref_service &&
@@ -198,6 +189,15 @@ void RecordManagedScreensaverEnabledPref() {
} // namespace } // namespace
class AmbientWidgetDelegate : public views::WidgetDelegate {
public:
AmbientWidgetDelegate() {
SetCanFullscreen(true);
SetCanMaximize(true);
SetOwnedByWidget(true);
}
};
// static // static
void AmbientController::RegisterProfilePrefs(PrefRegistrySimple* registry) { void AmbientController::RegisterProfilePrefs(PrefRegistrySimple* registry) {
registry->RegisterStringPref(ash::ambient::prefs::kAmbientBackdropClientId, registry->RegisterStringPref(ash::ambient::prefs::kAmbientBackdropClientId,

@@ -70,32 +70,6 @@ std::string GetUserSalt(const AccountId& account_id) {
return {}; return {};
} }
std::unique_ptr<views::Widget> CreateAuthDialogWidget(
std::unique_ptr<views::View> contents_view) {
views::Widget::InitParams params(
views::Widget::InitParams::CLIENT_OWNS_WIDGET,
views::Widget::InitParams::TYPE_WINDOW_FRAMELESS);
params.opacity = views::Widget::InitParams::WindowOpacity::kTranslucent;
params.delegate = new views::WidgetDelegate();
params.show_state = ui::mojom::WindowShowState::kNormal;
CHECK_EQ(Shell::Get()->session_controller()->GetSessionState(),
session_manager::SessionState::ACTIVE);
params.parent = Shell::GetPrimaryRootWindow()->GetChildById(
kShellWindowId_SystemModalContainer);
params.autosize = true;
params.name = "AuthDialogWidget";
params.delegate->SetInitiallyFocusedView(contents_view.get());
params.delegate->SetModalType(ui::mojom::ModalType::kSystem);
params.delegate->SetOwnedByWidget(true);
std::unique_ptr<views::Widget> widget = std::make_unique<views::Widget>();
widget->Init(std::move(params));
widget->SetVisibilityAnimationTransition(views::Widget::ANIMATE_NONE);
widget->SetContentsView(std::move(contents_view));
return widget;
}
const char* ReasonToString(AuthRequest::Reason reason) { const char* ReasonToString(AuthRequest::Reason reason) {
switch (reason) { switch (reason) {
case AuthRequest::Reason::kPasswordManager: case AuthRequest::Reason::kPasswordManager:
@@ -448,7 +422,28 @@ void ActiveSessionAuthControllerImpl::InitUi() {
account_id_, title_, description_, available_factors_); account_id_, title_, description_, available_factors_);
contents_view_ = contents_view.get(); contents_view_ = contents_view.get();
widget_ = CreateAuthDialogWidget(std::move(contents_view)); views::Widget::InitParams params(
views::Widget::InitParams::CLIENT_OWNS_WIDGET,
views::Widget::InitParams::TYPE_WINDOW_FRAMELESS);
params.opacity = views::Widget::InitParams::WindowOpacity::kTranslucent;
params.delegate = new views::WidgetDelegate();
params.show_state = ui::mojom::WindowShowState::kNormal;
CHECK_EQ(Shell::Get()->session_controller()->GetSessionState(),
session_manager::SessionState::ACTIVE);
params.parent = Shell::GetPrimaryRootWindow()->GetChildById(
kShellWindowId_SystemModalContainer);
params.autosize = true;
params.name = "AuthDialogWidget";
params.delegate->SetInitiallyFocusedView(contents_view.get());
params.delegate->SetModalType(ui::mojom::ModalType::kSystem);
params.delegate->SetOwnedByWidget(true);
widget_ = std::make_unique<views::Widget>();
widget_->Init(std::move(params));
widget_->SetVisibilityAnimationTransition(views::Widget::ANIMATE_NONE);
widget_->SetContentsView(std::move(contents_view));
contents_view_observer_.Observe(contents_view_); contents_view_observer_.Observe(contents_view_);
contents_view_->AddObserver(this); contents_view_->AddObserver(this);
SetState(ActiveSessionAuthState::kInitialized); SetState(ActiveSessionAuthState::kInitialized);

@@ -35,8 +35,6 @@
namespace ash { namespace ash {
namespace {
class AuthDialogContentsViewPixelTest : public AshTestBase { class AuthDialogContentsViewPixelTest : public AshTestBase {
public: public:
AuthDialogContentsViewPixelTest() = default; AuthDialogContentsViewPixelTest() = default;
@@ -308,6 +306,4 @@ TEST_F(AuthDialogContentsViewPixelTest, AllFactorAndThemeChange) {
"fingerprint_light", /*revision_number=*/4, widget.get())); "fingerprint_light", /*revision_number=*/4, widget.get()));
} }
} // namespace
} // namespace ash } // namespace ash

@@ -24,8 +24,6 @@
namespace ash { namespace ash {
namespace {
class AuthDialogContentsViewTest : public AshTestBase { class AuthDialogContentsViewTest : public AshTestBase {
public: public:
AuthDialogContentsViewTest() = default; AuthDialogContentsViewTest() = default;
@@ -148,6 +146,4 @@ TEST_F(AuthDialogContentsViewTest, AccessibleProperties) {
EXPECT_EQ(data.role, ax::mojom::Role::kStaticText); EXPECT_EQ(data.role, ax::mojom::Role::kStaticText);
} }
} // namespace
} // namespace ash } // namespace ash

@@ -26,29 +26,6 @@ namespace {
// address bar, for anti-spoofing. // address bar, for anti-spoofing.
constexpr int kTopInsetDp = 36; constexpr int kTopInsetDp = 36;
std::unique_ptr<views::Widget> CreateAuthDialogWidget(
std::unique_ptr<views::View> contents_view,
aura::Window* parent) {
views::Widget::InitParams params(
views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET,
views::Widget::InitParams::TYPE_WINDOW_FRAMELESS);
params.opacity = views::Widget::InitParams::WindowOpacity::kTranslucent;
params.delegate = new views::WidgetDelegate();
params.show_state = ui::mojom::WindowShowState::kNormal;
params.parent = parent;
params.name = "AuthDialogWidget";
params.delegate->SetInitiallyFocusedView(contents_view.get());
params.delegate->SetModalType(ui::mojom::ModalType::kNone);
params.delegate->SetOwnedByWidget(true);
std::unique_ptr<views::Widget> widget = std::make_unique<views::Widget>();
widget->Init(std::move(params));
widget->SetVisibilityAnimationTransition(views::Widget::ANIMATE_NONE);
widget->SetContentsView(std::move(contents_view));
return widget;
}
} // namespace } // namespace
InSessionAuthDialog::InSessionAuthDialog( InSessionAuthDialog::InSessionAuthDialog(
@@ -58,10 +35,26 @@ InSessionAuthDialog::InSessionAuthDialog(
const AuthDialogContentsView::AuthMethodsMetadata& auth_metadata, const AuthDialogContentsView::AuthMethodsMetadata& auth_metadata,
const UserAvatar& avatar) const UserAvatar& avatar)
: auth_methods_(auth_methods) { : auth_methods_(auth_methods) {
widget_ = CreateAuthDialogWidget( views::Widget::InitParams params(
std::make_unique<AuthDialogContentsView>(auth_methods, origin_name, views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET,
auth_metadata, avatar), views::Widget::InitParams::TYPE_WINDOW_FRAMELESS);
parent_window); params.opacity = views::Widget::InitParams::WindowOpacity::kTranslucent;
params.delegate = new views::WidgetDelegate();
params.show_state = ui::mojom::WindowShowState::kNormal;
params.parent = parent_window;
params.name = "AuthDialogWidget";
auto contents_view = std::make_unique<AuthDialogContentsView>(
auth_methods, origin_name, auth_metadata, avatar);
params.delegate->SetInitiallyFocusedView(contents_view.get());
params.delegate->SetModalType(ui::mojom::ModalType::kNone);
params.delegate->SetOwnedByWidget(true);
widget_ = std::make_unique<views::Widget>();
widget_->Init(std::move(params));
widget_->SetVisibilityAnimationTransition(views::Widget::ANIMATE_NONE);
widget_->SetContentsView(std::move(contents_view));
gfx::Rect bounds = parent_window->GetBoundsInScreen(); gfx::Rect bounds = parent_window->GetBoundsInScreen();
gfx::Size preferred_size = widget_->GetContentsView()->GetPreferredSize(); gfx::Size preferred_size = widget_->GetContentsView()->GetPreferredSize();
int horizontal_inset_dp = (bounds.width() - preferred_size.width()) / 2; int horizontal_inset_dp = (bounds.width() - preferred_size.width()) / 2;

@@ -56,28 +56,6 @@ AuthPurpose InSessionAuthReasonToAuthPurpose(
} }
} }
std::unique_ptr<views::Widget> CreateAuthDialogWidget(
std::unique_ptr<views::View> contents_view) {
views::Widget::InitParams params(
views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET,
views::Widget::InitParams::TYPE_WINDOW_FRAMELESS);
params.opacity = views::Widget::InitParams::WindowOpacity::kTranslucent;
params.delegate = new views::WidgetDelegate();
params.show_state = ui::mojom::WindowShowState::kNormal;
params.parent = nullptr;
params.name = "AuthDialogWidget";
params.delegate->SetInitiallyFocusedView(contents_view.get());
params.delegate->SetModalType(ui::mojom::ModalType::kSystem);
params.delegate->SetOwnedByWidget(true);
std::unique_ptr<views::Widget> widget = std::make_unique<views::Widget>();
widget->Init(std::move(params));
widget->SetVisibilityAnimationTransition(views::Widget::ANIMATE_NONE);
widget->SetContentsView(std::move(contents_view));
return widget;
}
// TODO(b/271248452): Subscribe to primary display changes, so that the // TODO(b/271248452): Subscribe to primary display changes, so that the
// authentication dialog correctly changes its location to center on new // authentication dialog correctly changes its location to center on new
// primary displays. We will need to also listen to `work_area` changes and // primary displays. We will need to also listen to `work_area` changes and
@@ -183,8 +161,26 @@ void InSessionAuthDialogControllerImpl::OnUserAuthAttemptConfirmed(
contents_view_ = contents_view.get(); contents_view_ = contents_view.get();
out_consumer = contents_view->GetAuthPanel(); out_consumer = contents_view->GetAuthPanel();
dialog_ = CreateAuthDialogWidget(std::move(contents_view));
views::Widget::InitParams params(
views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET,
views::Widget::InitParams::TYPE_WINDOW_FRAMELESS);
params.opacity = views::Widget::InitParams::WindowOpacity::kTranslucent;
params.delegate = new views::WidgetDelegate();
params.show_state = ui::mojom::WindowShowState::kNormal;
params.parent = nullptr;
params.name = "AuthDialogWidget";
params.delegate->SetInitiallyFocusedView(contents_view.get());
params.delegate->SetModalType(ui::mojom::ModalType::kSystem);
params.delegate->SetOwnedByWidget(true);
dialog_ = std::make_unique<views::Widget>();
dialog_->Init(std::move(params));
dialog_->SetVisibilityAnimationTransition(views::Widget::ANIMATE_NONE);
dialog_->SetContentsView(std::move(contents_view));
dialog_->Show(); dialog_->Show();
state_ = State::kShown; state_ = State::kShown;
AuthParts::Get() AuthParts::Get()
->GetLegacyAuthSurfaceRegistry() ->GetLegacyAuthSurfaceRegistry()

@@ -123,40 +123,6 @@ std::string GetUserSalt(const AccountId& account_id) {
return {}; return {};
} }
std::unique_ptr<views::Widget> CreateAuthDialogWidget(
std::unique_ptr<views::View> contents_view) {
views::Widget::InitParams params(
views::Widget::InitParams::CLIENT_OWNS_WIDGET,
views::Widget::InitParams::TYPE_WINDOW_FRAMELESS);
params.opacity = views::Widget::InitParams::WindowOpacity::kTranslucent;
params.delegate = new views::WidgetDelegate();
params.show_state = ui::mojom::WindowShowState::kNormal;
ShellWindowId parent_window_id =
Shell::Get()->session_controller()->GetSessionState() ==
session_manager::SessionState::ACTIVE
? kShellWindowId_SystemModalContainer
: kShellWindowId_LockSystemModalContainer;
params.parent = Shell::GetPrimaryRootWindow()->GetChildById(parent_window_id);
params.autosize = true;
params.name = "AuthDialogWidget";
params.delegate->SetInitiallyFocusedView(contents_view.get());
// ModalType::kSystem is used to get a semi-transparent background behind the
// local authentication request view, when it is used directly on a widget.
// The overlay consumes all the inputs from the user, so that they can only
// interact with the local authentication request view while it is visible.
params.delegate->SetModalType(ui::mojom::ModalType::kSystem);
params.delegate->SetOwnedByWidget(true);
auto widget = std::make_unique<views::Widget>();
widget->Init(std::move(params));
widget->SetVisibilityAnimationTransition(views::Widget::ANIMATE_NONE);
widget->SetContentsView(std::move(contents_view));
return widget;
}
const char* LocalAuthenticationWithPinStateToString( const char* LocalAuthenticationWithPinStateToString(
LocalAuthenticationWithPinControllerImpl::LocalAuthenticationWithPinState LocalAuthenticationWithPinControllerImpl::LocalAuthenticationWithPinState
state) { state) {
@@ -245,7 +211,36 @@ bool LocalAuthenticationWithPinControllerImpl::ShowWidget(
account_id_, title_, description_, available_factors_); account_id_, title_, description_, available_factors_);
contents_view_ = contents_view.get(); contents_view_ = contents_view.get();
widget_ = CreateAuthDialogWidget(std::move(contents_view)); views::Widget::InitParams params(
views::Widget::InitParams::CLIENT_OWNS_WIDGET,
views::Widget::InitParams::TYPE_WINDOW_FRAMELESS);
params.opacity = views::Widget::InitParams::WindowOpacity::kTranslucent;
params.delegate = new views::WidgetDelegate();
params.show_state = ui::mojom::WindowShowState::kNormal;
ShellWindowId parent_window_id =
Shell::Get()->session_controller()->GetSessionState() ==
session_manager::SessionState::ACTIVE
? kShellWindowId_SystemModalContainer
: kShellWindowId_LockSystemModalContainer;
params.parent = Shell::GetPrimaryRootWindow()->GetChildById(parent_window_id);
params.autosize = true;
params.name = "AuthDialogWidget";
params.delegate->SetInitiallyFocusedView(contents_view.get());
// ModalType::kSystem is used to get a semi-transparent background behind the
// local authentication request view, when it is used directly on a widget.
// The overlay consumes all the inputs from the user, so that they can only
// interact with the local authentication request view while it is visible.
params.delegate->SetModalType(ui::mojom::ModalType::kSystem);
params.delegate->SetOwnedByWidget(true);
widget_ = std::make_unique<views::Widget>();
widget_->Init(std::move(params));
widget_->SetVisibilityAnimationTransition(views::Widget::ANIMATE_NONE);
widget_->SetContentsView(std::move(contents_view));
contents_view_observer_.Observe(contents_view_); contents_view_observer_.Observe(contents_view_);
contents_view_->AddObserver(this); contents_view_->AddObserver(this);
SetState(LocalAuthenticationWithPinState::kInitialized); SetState(LocalAuthenticationWithPinState::kInitialized);

@@ -141,15 +141,6 @@ void ExpectAllContainers() {
EXPECT_FALSE(Shell::GetContainer(root_window, kShellWindowId_PhantomWindow)); EXPECT_FALSE(Shell::GetContainer(root_window, kShellWindowId_PhantomWindow));
} }
std::unique_ptr<views::WidgetDelegateView> CreateModalWidgetDelegate() {
auto delegate = std::make_unique<views::WidgetDelegateView>();
delegate->SetCanResize(true);
delegate->SetModalType(ui::mojom::ModalType::kSystem);
delegate->SetOwnedByWidget(true);
delegate->SetTitle(u"Modal Window");
return delegate;
}
class SimpleMenuDelegate : public ui::SimpleMenuModel::Delegate { class SimpleMenuDelegate : public ui::SimpleMenuModel::Delegate {
public: public:
SimpleMenuDelegate() = default; SimpleMenuDelegate() = default;
@@ -170,6 +161,16 @@ class SimpleMenuDelegate : public ui::SimpleMenuModel::Delegate {
class ShellTest : public AshTestBase { class ShellTest : public AshTestBase {
public: public:
static std::unique_ptr<views::WidgetDelegateView>
CreateModalWidgetDelegate() {
auto delegate = std::make_unique<views::WidgetDelegateView>();
delegate->SetCanResize(true);
delegate->SetModalType(ui::mojom::ModalType::kSystem);
delegate->SetOwnedByWidget(true);
delegate->SetTitle(u"Modal Window");
return delegate;
}
void TestCreateWindow(views::Widget::InitParams::Type type, void TestCreateWindow(views::Widget::InitParams::Type type,
bool always_on_top, bool always_on_top,
aura::Window* expected_container) { aura::Window* expected_container) {

@@ -176,6 +176,30 @@
namespace ash { namespace ash {
// A widget delegate that refuses to close.
class StuckWidgetDelegate : public views::WidgetDelegate {
public:
StuckWidgetDelegate() {
SetCanMaximize(true);
SetCanMinimize(true);
SetCanResize(true);
SetOwnedByWidget(true);
}
StuckWidgetDelegate(const StuckWidgetDelegate& other) = delete;
StuckWidgetDelegate& operator=(const StuckWidgetDelegate& other) = delete;
~StuckWidgetDelegate() override = default;
// Overridden from WidgetDelegate:
std::unique_ptr<views::NonClientFrameView> CreateNonClientFrameView(
views::Widget* widget) override {
return Shell::Get()->CreateDefaultNonClientFrameView(widget);
}
bool OnCloseRequested(views::Widget::ClosedReason close_reason) override {
return false;
}
};
namespace { namespace {
using ::testing::ElementsAre; using ::testing::ElementsAre;
@@ -427,30 +451,6 @@ class FullScreenStateObserver : public ShellObserver {
bool is_fullscreen_ = false; bool is_fullscreen_ = false;
}; };
// A widget delegate that refuses to close.
class StuckWidgetDelegate : public views::WidgetDelegate {
public:
StuckWidgetDelegate() {
SetCanMaximize(true);
SetCanMinimize(true);
SetCanResize(true);
SetOwnedByWidget(true);
}
StuckWidgetDelegate(const StuckWidgetDelegate& other) = delete;
StuckWidgetDelegate& operator=(const StuckWidgetDelegate& other) = delete;
~StuckWidgetDelegate() override = default;
// Overridden from WidgetDelegate:
std::unique_ptr<views::NonClientFrameView> CreateNonClientFrameView(
views::Widget* widget) override {
return Shell::Get()->CreateDefaultNonClientFrameView(widget);
}
bool OnCloseRequested(views::Widget::ClosedReason close_reason) override {
return false;
}
};
struct DesksTestParams { struct DesksTestParams {
bool use_touch_gestures = false; bool use_touch_gestures = false;
bool use_16_desks = false; bool use_16_desks = false;

@@ -27,8 +27,6 @@
namespace ash { namespace ash {
namespace {
// A login implementation of WidgetDelegate. // A login implementation of WidgetDelegate.
class LoginTestWidgetDelegate : public views::WidgetDelegate { class LoginTestWidgetDelegate : public views::WidgetDelegate {
public: public:
@@ -51,8 +49,6 @@ class LoginTestWidgetDelegate : public views::WidgetDelegate {
raw_ptr<views::Widget> widget_; raw_ptr<views::Widget> widget_;
}; };
} // namespace
class LockLayoutManagerTest : public AshTestBase { class LockLayoutManagerTest : public AshTestBase {
public: public:
void SetUp() override { void SetUp() override {

@@ -50,57 +50,6 @@
namespace enterprise_connectors { namespace enterprise_connectors {
namespace {
constexpr base::TimeDelta kNoDelay = base::Seconds(0);
constexpr base::TimeDelta kSmallDelay = base::Milliseconds(300);
constexpr base::TimeDelta kNormalDelay = base::Milliseconds(500);
constexpr char kBlockingScansForDlpAndMalware[] = R"(
{
"service_provider": "google",
"enable": [
{
"url_list": ["*"],
"tags": ["dlp", "malware"]
}
],
"block_until_verdict": 1
})";
constexpr char kBlockingScansForDlp[] = R"(
{
"service_provider": "google",
"enable": [
{
"url_list": ["*"],
"tags": ["dlp"]
}
],
"block_until_verdict": 1
})";
constexpr char kBlockingScansForDlpAndMalwareWithCustomMessage[] = R"(
{
"service_provider": "google",
"enable": [
{
"url_list": ["*"],
"tags": ["dlp", "malware"]
}
],
"block_until_verdict": 1,
"custom_messages": [{
"message": "Custom message",
"learn_more_url": "http://www.example.com/",
"tag": "dlp"
}]
})";
std::string text() {
return std::string(100, 'a');
}
// Tests the behavior of the dialog in the following ways: // Tests the behavior of the dialog in the following ways:
// - It shows the appropriate buttons depending on its state. // - It shows the appropriate buttons depending on its state.
// - It transitions from states in the correct order. // - It transitions from states in the correct order.
@@ -329,6 +278,57 @@ class ContentAnalysisDialogBehaviorBrowserTest
views::test::AXEventCounter ax_event_counter_; views::test::AXEventCounter ax_event_counter_;
}; };
namespace {
constexpr base::TimeDelta kNoDelay = base::Seconds(0);
constexpr base::TimeDelta kSmallDelay = base::Milliseconds(300);
constexpr base::TimeDelta kNormalDelay = base::Milliseconds(500);
constexpr char kBlockingScansForDlpAndMalware[] = R"(
{
"service_provider": "google",
"enable": [
{
"url_list": ["*"],
"tags": ["dlp", "malware"]
}
],
"block_until_verdict": 1
})";
constexpr char kBlockingScansForDlp[] = R"(
{
"service_provider": "google",
"enable": [
{
"url_list": ["*"],
"tags": ["dlp"]
}
],
"block_until_verdict": 1
})";
constexpr char kBlockingScansForDlpAndMalwareWithCustomMessage[] = R"(
{
"service_provider": "google",
"enable": [
{
"url_list": ["*"],
"tags": ["dlp", "malware"]
}
],
"block_until_verdict": 1,
"custom_messages": [{
"message": "Custom message",
"learn_more_url": "http://www.example.com/",
"tag": "dlp"
}]
})";
std::string text() {
return std::string(100, 'a');
}
// Tests the behavior of the dialog in the following ways: // Tests the behavior of the dialog in the following ways:
// - It closes when the "Cancel" button is clicked. // - It closes when the "Cancel" button is clicked.
// - It returns a negative verdict on the scanned content. // - It returns a negative verdict on the scanned content.

@@ -26,6 +26,8 @@ bool UserResizeEnabled() {
return base::FeatureList::IsEnabled(features::kGlicUserResize); return base::FeatureList::IsEnabled(features::kGlicUserResize);
} }
} // namespace
class GlicWidgetDelegate : public views::WidgetDelegate { class GlicWidgetDelegate : public views::WidgetDelegate {
public: public:
GlicWidgetDelegate() { GlicWidgetDelegate() {
@@ -44,7 +46,6 @@ class GlicWidgetDelegate : public views::WidgetDelegate {
private: private:
void Destroy() { delete this; } void Destroy() { delete this; }
}; };
} // namespace
void* kGlicWidgetIdentifier = &kGlicWidgetIdentifier; void* kGlicWidgetIdentifier = &kGlicWidgetIdentifier;

@@ -247,7 +247,7 @@ void AppServiceShelfContextMenu::ExecuteCommand(int command_id,
const bool scaled = command_id == ash::CROSTINI_USE_LOW_DENSITY; const bool scaled = command_id == ash::CROSTINI_USE_LOW_DENSITY;
registry_service->SetAppScaled(item().id.app_id, scaled); registry_service->SetAppScaled(item().id.app_id, scaled);
if (controller()->IsOpen(item().id)) { if (controller()->IsOpen(item().id)) {
crostini::ShowAppRestartDialog(display_id()); crostini::AppRestartDialog::Show(display_id());
} }
return; return;
} }

@@ -41,8 +41,6 @@ namespace views::borealis {
namespace { namespace {
using AllowStatus = ::borealis::BorealisFeatures::AllowStatus;
using MaybeAction = std::optional<std::pair<std::u16string, base::OnceClosure>>; using MaybeAction = std::optional<std::pair<std::u16string, base::OnceClosure>>;
// Views uses tricks like this to ensure singleton-ness of dialogs. // Views uses tricks like this to ensure singleton-ness of dialogs.
@@ -62,6 +60,88 @@ class BehaviourProvider {
} }
}; };
} // namespace
class BorealisDisallowedDialog : public DialogDelegate {
public:
BorealisDisallowedDialog(std::unique_ptr<BehaviourProvider> behaviour,
int title_id) {
DCHECK(!g_instance_);
SetTitle(IDS_BOREALIS_INSTALLER_APP_NAME);
set_internal_name("BorealisDisallowedDialog");
MaybeAction second_action = behaviour->GetAction();
if (second_action.has_value()) {
SetButtons(static_cast<int>(ui::mojom::DialogButton::kOk) |
static_cast<int>(ui::mojom::DialogButton::kCancel));
SetButtonLabel(ui::mojom::DialogButton::kCancel,
l10n_util::GetStringUTF16(IDS_CLOSE));
SetButtonLabel(ui::mojom::DialogButton::kOk,
std::move(second_action.value().first));
SetAcceptCallback(std::move(second_action.value().second));
} else {
SetButtons(static_cast<int>(ui::mojom::DialogButton::kOk));
SetButtonLabel(ui::mojom::DialogButton::kOk,
l10n_util::GetStringUTF16(IDS_CLOSE));
}
InitializeView(*behaviour, title_id);
SetModalType(ui::mojom::ModalType::kSystem);
SetOwnedByWidget(true);
SetShowCloseButton(false);
set_fixed_width(views::LayoutProvider::Get()->GetDistanceMetric(
views::DISTANCE_MODAL_DIALOG_PREFERRED_WIDTH));
}
~BorealisDisallowedDialog() override {
DCHECK(g_instance_);
g_instance_ = nullptr;
}
bool ShouldShowWindowTitle() const override { return false; }
private:
void InitializeView(const BehaviourProvider& behaviour, int title_id) {
auto view = std::make_unique<views::View>();
views::LayoutProvider* provider = views::LayoutProvider::Get();
view->SetLayoutManager(std::make_unique<views::BoxLayout>(
views::BoxLayout::Orientation::kVertical,
provider->GetInsetsMetric(views::InsetsMetric::INSETS_DIALOG),
provider->GetDistanceMetric(views::DISTANCE_RELATED_CONTROL_VERTICAL)));
views::Label* title_label = new views::Label(
l10n_util::GetStringUTF16(title_id), CONTEXT_IPH_BUBBLE_TITLE,
views::style::STYLE_EMPHASIZED);
title_label->SetHorizontalAlignment(gfx::ALIGN_LEFT);
title_label->SetMultiLine(true);
view->AddChildViewRaw(title_label);
views::Label* message_label = new views::Label(behaviour.GetMessage());
message_label->SetMultiLine(true);
message_label->SetHorizontalAlignment(gfx::ALIGN_LEFT);
view->AddChildViewRaw(message_label);
for (const std::pair<std::u16string, GURL>& link : behaviour.GetLinks()) {
views::Link* link_label =
view->AddChildView(std::make_unique<views::Link>(link.first));
link_label->SetHorizontalAlignment(gfx::ALIGN_LEFT);
link_label->SetCallback(base::BindRepeating(
[](GURL url) {
ash::NewWindowDelegate::GetPrimary()->OpenUrl(
url, ash::NewWindowDelegate::OpenUrlFrom::kUserInteraction,
ash::NewWindowDelegate::Disposition::kNewForegroundTab);
},
link.second));
}
SetContentsView(std::move(view));
}
};
namespace {
using AllowStatus = ::borealis::BorealisFeatures::AllowStatus;
class DisallowedHardware : public BehaviourProvider { class DisallowedHardware : public BehaviourProvider {
public: public:
std::u16string GetMessage() const override { std::u16string GetMessage() const override {
@@ -143,82 +223,6 @@ class DisallowedFlag : public BehaviourProvider {
} }
}; };
class BorealisDisallowedDialog : public DialogDelegate {
public:
BorealisDisallowedDialog(std::unique_ptr<BehaviourProvider> behaviour,
int title_id) {
DCHECK(!g_instance_);
SetTitle(IDS_BOREALIS_INSTALLER_APP_NAME);
set_internal_name("BorealisDisallowedDialog");
MaybeAction second_action = behaviour->GetAction();
if (second_action.has_value()) {
SetButtons(static_cast<int>(ui::mojom::DialogButton::kOk) |
static_cast<int>(ui::mojom::DialogButton::kCancel));
SetButtonLabel(ui::mojom::DialogButton::kCancel,
l10n_util::GetStringUTF16(IDS_CLOSE));
SetButtonLabel(ui::mojom::DialogButton::kOk,
std::move(second_action.value().first));
SetAcceptCallback(std::move(second_action.value().second));
} else {
SetButtons(static_cast<int>(ui::mojom::DialogButton::kOk));
SetButtonLabel(ui::mojom::DialogButton::kOk,
l10n_util::GetStringUTF16(IDS_CLOSE));
}
InitializeView(*behaviour, title_id);
SetModalType(ui::mojom::ModalType::kSystem);
SetOwnedByWidget(true);
SetShowCloseButton(false);
set_fixed_width(views::LayoutProvider::Get()->GetDistanceMetric(
views::DISTANCE_MODAL_DIALOG_PREFERRED_WIDTH));
}
~BorealisDisallowedDialog() override {
DCHECK(g_instance_);
g_instance_ = nullptr;
}
bool ShouldShowWindowTitle() const override { return false; }
private:
void InitializeView(const BehaviourProvider& behaviour, int title_id) {
auto view = std::make_unique<views::View>();
views::LayoutProvider* provider = views::LayoutProvider::Get();
view->SetLayoutManager(std::make_unique<views::BoxLayout>(
views::BoxLayout::Orientation::kVertical,
provider->GetInsetsMetric(views::InsetsMetric::INSETS_DIALOG),
provider->GetDistanceMetric(views::DISTANCE_RELATED_CONTROL_VERTICAL)));
views::Label* title_label = new views::Label(
l10n_util::GetStringUTF16(title_id), CONTEXT_IPH_BUBBLE_TITLE,
views::style::STYLE_EMPHASIZED);
title_label->SetHorizontalAlignment(gfx::ALIGN_LEFT);
title_label->SetMultiLine(true);
view->AddChildViewRaw(title_label);
views::Label* message_label = new views::Label(behaviour.GetMessage());
message_label->SetMultiLine(true);
message_label->SetHorizontalAlignment(gfx::ALIGN_LEFT);
view->AddChildViewRaw(message_label);
for (const std::pair<std::u16string, GURL>& link : behaviour.GetLinks()) {
views::Link* link_label =
view->AddChildView(std::make_unique<views::Link>(link.first));
link_label->SetHorizontalAlignment(gfx::ALIGN_LEFT);
link_label->SetCallback(base::BindRepeating(
[](GURL url) {
ash::NewWindowDelegate::GetPrimary()->OpenUrl(
url, ash::NewWindowDelegate::OpenUrlFrom::kUserInteraction,
ash::NewWindowDelegate::Disposition::kNewForegroundTab);
},
link.second));
}
SetContentsView(std::move(view));
}
};
std::unique_ptr<BehaviourProvider> StatusBehaviour(AllowStatus status) { std::unique_ptr<BehaviourProvider> StatusBehaviour(AllowStatus status) {
switch (status) { switch (status) {
case AllowStatus::kAllowed: case AllowStatus::kAllowed:

@@ -40,6 +40,8 @@ namespace {
// Views uses tricks like this to ensure singleton-ness of dialogs. // Views uses tricks like this to ensure singleton-ness of dialogs.
static Widget* g_instance_ = nullptr; static Widget* g_instance_ = nullptr;
} // namespace
class BorealisLaunchErrorDialog : public DialogDelegate { class BorealisLaunchErrorDialog : public DialogDelegate {
public: public:
explicit BorealisLaunchErrorDialog(Profile* profile, explicit BorealisLaunchErrorDialog(Profile* profile,
@@ -215,7 +217,6 @@ class BorealisLaunchErrorDialog : public DialogDelegate {
FailureType failure_; FailureType failure_;
raw_ptr<views::Checkbox> feedback_checkbox_ = nullptr; raw_ptr<views::Checkbox> feedback_checkbox_ = nullptr;
}; };
} // namespace
void ShowBorealisLaunchErrorView(Profile* profile, void ShowBorealisLaunchErrorView(Profile* profile,
BorealisStartupResult error) { BorealisStartupResult error) {

@@ -26,7 +26,29 @@ gfx::NativeWindow GetNativeWindowFromDisplayId(int64_t display_id) {
return screen->GetWindowAtScreenPoint(display.bounds().origin()); return screen->GetWindowAtScreenPoint(display.bounds().origin());
} }
std::unique_ptr<views::View> MakeCrostiniAppRestartView() { } // namespace
// static
void AppRestartDialog::Show(int64_t display_id) {
ShowInternal(GetNativeWindowFromDisplayId(display_id));
}
// static
void AppRestartDialog::ShowForTesting(gfx::NativeWindow context) {
ShowInternal(context);
}
// static
void AppRestartDialog::ShowInternal(gfx::NativeWindow context) {
auto contents = MakeCrostiniAppRestartView();
auto delegate = MakeCrostiniAppRestartDelegate(std::move(contents));
views::DialogDelegate::CreateDialogWidget(std::move(delegate), context,
nullptr)
->Show();
}
// static
std::unique_ptr<views::View> AppRestartDialog::MakeCrostiniAppRestartView() {
auto view = std::make_unique<views::View>(); auto view = std::make_unique<views::View>();
views::LayoutProvider* provider = views::LayoutProvider::Get(); views::LayoutProvider* provider = views::LayoutProvider::Get();
@@ -45,7 +67,9 @@ std::unique_ptr<views::View> MakeCrostiniAppRestartView() {
return view; return view;
} }
std::unique_ptr<views::DialogDelegate> MakeCrostiniAppRestartDelegate( // static
std::unique_ptr<views::DialogDelegate>
AppRestartDialog::MakeCrostiniAppRestartDelegate(
std::unique_ptr<views::View> contents) { std::unique_ptr<views::View> contents) {
auto delegate = std::make_unique<views::DialogDelegate>(); auto delegate = std::make_unique<views::DialogDelegate>();
delegate->set_internal_name("CrostiniAppRestart"); delegate->set_internal_name("CrostiniAppRestart");
@@ -60,22 +84,4 @@ std::unique_ptr<views::DialogDelegate> MakeCrostiniAppRestartDelegate(
return delegate; return delegate;
} }
void ShowInternal(gfx::NativeWindow context) {
auto contents = MakeCrostiniAppRestartView();
auto delegate = MakeCrostiniAppRestartDelegate(std::move(contents));
views::DialogDelegate::CreateDialogWidget(std::move(delegate), context,
nullptr)
->Show();
}
} // namespace
void ShowAppRestartDialog(int64_t display_id) {
ShowInternal(GetNativeWindowFromDisplayId(display_id));
}
void ShowAppRestartDialogForTesting(gfx::NativeWindow context) {
ShowInternal(context);
}
} // namespace crostini } // namespace crostini

@@ -5,12 +5,28 @@
#ifndef CHROME_BROWSER_UI_VIEWS_CROSTINI_CROSTINI_APP_RESTART_DIALOG_H_ #ifndef CHROME_BROWSER_UI_VIEWS_CROSTINI_CROSTINI_APP_RESTART_DIALOG_H_
#define CHROME_BROWSER_UI_VIEWS_CROSTINI_CROSTINI_APP_RESTART_DIALOG_H_ #define CHROME_BROWSER_UI_VIEWS_CROSTINI_CROSTINI_APP_RESTART_DIALOG_H_
#include <memory>
#include "ui/gfx/native_widget_types.h" #include "ui/gfx/native_widget_types.h"
namespace views {
class DialogDelegate;
class View;
} // namespace views
namespace crostini { namespace crostini {
void ShowAppRestartDialog(int64_t display_id); class AppRestartDialog {
void ShowAppRestartDialogForTesting(gfx::NativeWindow context); public:
static void Show(int64_t display_id);
static void ShowForTesting(gfx::NativeWindow context);
private:
static void ShowInternal(gfx::NativeWindow context);
static std::unique_ptr<views::View> MakeCrostiniAppRestartView();
static std::unique_ptr<views::DialogDelegate> MakeCrostiniAppRestartDelegate(
std::unique_ptr<views::View> contents);
};
} // namespace crostini } // namespace crostini

@@ -20,7 +20,7 @@ class CrostiniAppRestartDialogTest : public ChromeViewsTestBase {
views::test::WidgetTest::WidgetAutoclosePtr ShowDialog() { views::test::WidgetTest::WidgetAutoclosePtr ShowDialog() {
views::NamedWidgetShownWaiter waiter(views::test::AnyWidgetTestPasskey{}, views::NamedWidgetShownWaiter waiter(views::test::AnyWidgetTestPasskey{},
"CrostiniAppRestart"); "CrostiniAppRestart");
crostini::ShowAppRestartDialogForTesting(GetContext()); crostini::AppRestartDialog::ShowForTesting(GetContext());
return views::test::WidgetTest::WidgetAutoclosePtr( return views::test::WidgetTest::WidgetAutoclosePtr(
waiter.WaitIfNeededAndGet()); waiter.WaitIfNeededAndGet());
} }

@@ -33,13 +33,13 @@
#include "ui/views/view.h" #include "ui/views/view.h"
#include "ui/views/window/dialog_client_view.h" #include "ui/views/window/dialog_client_view.h"
namespace {
using ::testing::_; using ::testing::_;
using ::testing::NiceMock; using ::testing::NiceMock;
using ::testing::Return; using ::testing::Return;
using ::testing::ReturnRefOfCopy; using ::testing::ReturnRefOfCopy;
namespace {
class MockDownloadBubbleNavigationHandler class MockDownloadBubbleNavigationHandler
: public DownloadBubbleNavigationHandler { : public DownloadBubbleNavigationHandler {
public: public:
@@ -90,6 +90,8 @@ std::unique_ptr<KeyedService> BuildMockDownloadCoreService(
return std::make_unique<MockDownloadCoreService>(); return std::make_unique<MockDownloadCoreService>();
} }
} // namespace
class DownloadBubbleContentsViewTest class DownloadBubbleContentsViewTest
: public ChromeViewsTestBase, : public ChromeViewsTestBase,
public ::testing::WithParamInterface<bool> { public ::testing::WithParamInterface<bool> {
@@ -433,5 +435,3 @@ TEST_P(DownloadBubbleContentsViewTest,
OfflineItemUtils::GetContentIdForDownload(download_items_[0].get()), OfflineItemUtils::GetContentIdForDownload(download_items_[0].get()),
DownloadCommands::Command::DISCARD); DownloadCommands::Command::DISCARD);
} }
} // namespace

@@ -33,10 +33,6 @@
using content::WebContents; using content::WebContents;
namespace {
const int kMessageWidth = 400;
// The external protocol dialog for Chrome OS shown when we have a URL with a // The external protocol dialog for Chrome OS shown when we have a URL with a
// Tel scheme but there are no handlers. // Tel scheme but there are no handlers.
class ExternalProtocolNoHandlersTelSchemeDialog : public views::DialogDelegate { class ExternalProtocolNoHandlersTelSchemeDialog : public views::DialogDelegate {
@@ -53,7 +49,7 @@ class ExternalProtocolNoHandlersTelSchemeDialog : public views::DialogDelegate {
l10n_util::GetStringUTF16(IDS_EXTERNAL_PROTOCOL_CLOSE_BUTTON_TEXT)); l10n_util::GetStringUTF16(IDS_EXTERNAL_PROTOCOL_CLOSE_BUTTON_TEXT));
message_box_view_ = new views::MessageBoxView(); message_box_view_ = new views::MessageBoxView();
message_box_view_->SetMessageWidth(kMessageWidth); message_box_view_->SetMessageWidth(400);
views::DialogDelegate::CreateDialogWidget(this, nullptr, parent_window) views::DialogDelegate::CreateDialogWidget(this, nullptr, parent_window)
->Show(); ->Show();
@@ -121,8 +117,6 @@ void OnArcHandled(const GURL& url,
} }
} }
} // namespace
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// ExternalProtocolHandler // ExternalProtocolHandler

@@ -97,6 +97,8 @@ BEGIN_METADATA(NotificationBarClientView)
ADD_PROPERTY_METADATA(gfx::Rect, ClientRect) ADD_PROPERTY_METADATA(gfx::Rect, ClientRect)
END_METADATA END_METADATA
} // namespace
class ScreenCaptureNotificationUIViews : public views::WidgetDelegateView, class ScreenCaptureNotificationUIViews : public views::WidgetDelegateView,
public views::ViewObserver { public views::ViewObserver {
METADATA_HEADER(ScreenCaptureNotificationUIViews, views::WidgetDelegateView) METADATA_HEADER(ScreenCaptureNotificationUIViews, views::WidgetDelegateView)
@@ -139,34 +141,6 @@ class ScreenCaptureNotificationUIViews : public views::WidgetDelegateView,
raw_ptr<views::View> hide_link_ = nullptr; raw_ptr<views::View> hide_link_ = nullptr;
}; };
// ScreenCaptureNotificationUI implementation using Views.
class ScreenCaptureNotificationUIImpl : public ScreenCaptureNotificationUI {
public:
ScreenCaptureNotificationUIImpl(const std::u16string& text,
content::WebContents* capturing_web_contents);
ScreenCaptureNotificationUIImpl(const ScreenCaptureNotificationUIImpl&) =
delete;
ScreenCaptureNotificationUIImpl& operator=(
const ScreenCaptureNotificationUIImpl&) = delete;
~ScreenCaptureNotificationUIImpl() override = default;
// ScreenCaptureNotificationUI override:
gfx::NativeViewId OnStarted(
base::OnceClosure stop_callback,
content::MediaStreamUI::SourceCallback source_callback,
const std::vector<content::DesktopMediaID>& media_ids) override;
private:
// Helper to set window id to parent browser window id for task bar grouping.
#if BUILDFLAG(IS_WIN)
void SetWindowsAppId(views::Widget* widget);
#endif
std::u16string text_;
base::WeakPtr<content::WebContents> capturing_web_contents_;
std::unique_ptr<views::Widget> widget_;
};
ScreenCaptureNotificationUIViews::ScreenCaptureNotificationUIViews( ScreenCaptureNotificationUIViews::ScreenCaptureNotificationUIViews(
const std::u16string& text, const std::u16string& text,
content::WebContents* capturing_web_contents, content::WebContents* capturing_web_contents,
@@ -300,6 +274,36 @@ void ScreenCaptureNotificationUIViews::NotifyStopped() {
BEGIN_METADATA(ScreenCaptureNotificationUIViews) BEGIN_METADATA(ScreenCaptureNotificationUIViews)
END_METADATA END_METADATA
namespace {
// ScreenCaptureNotificationUI implementation using Views.
class ScreenCaptureNotificationUIImpl : public ScreenCaptureNotificationUI {
public:
ScreenCaptureNotificationUIImpl(const std::u16string& text,
content::WebContents* capturing_web_contents);
ScreenCaptureNotificationUIImpl(const ScreenCaptureNotificationUIImpl&) =
delete;
ScreenCaptureNotificationUIImpl& operator=(
const ScreenCaptureNotificationUIImpl&) = delete;
~ScreenCaptureNotificationUIImpl() override = default;
// ScreenCaptureNotificationUI override:
gfx::NativeViewId OnStarted(
base::OnceClosure stop_callback,
content::MediaStreamUI::SourceCallback source_callback,
const std::vector<content::DesktopMediaID>& media_ids) override;
private:
// Helper to set window id to parent browser window id for task bar grouping.
#if BUILDFLAG(IS_WIN)
void SetWindowsAppId(views::Widget* widget);
#endif
std::u16string text_;
base::WeakPtr<content::WebContents> capturing_web_contents_;
std::unique_ptr<views::Widget> widget_;
};
ScreenCaptureNotificationUIImpl::ScreenCaptureNotificationUIImpl( ScreenCaptureNotificationUIImpl::ScreenCaptureNotificationUIImpl(
const std::u16string& text, const std::u16string& text,
content::WebContents* capturing_web_contents) content::WebContents* capturing_web_contents)

@@ -66,6 +66,8 @@ class WidgetResizeWaiter : public views::WidgetObserver {
base::RunLoop run_loop_; base::RunLoop run_loop_;
}; };
} // namespace
class WebDialogBrowserTest : public InProcessBrowserTest { class WebDialogBrowserTest : public InProcessBrowserTest {
public: public:
WebDialogBrowserTest() = default; WebDialogBrowserTest() = default;
@@ -123,8 +125,6 @@ void WebDialogBrowserTest::SimulateEscapeKey() {
} }
} }
} // namespace
// Windows has some issues resizing windows. An off by one problem, and a // Windows has some issues resizing windows. An off by one problem, and a
// minimum size that seems too big. See http://crbug.com/52602. // minimum size that seems too big. See http://crbug.com/52602.
#if BUILDFLAG(IS_WIN) #if BUILDFLAG(IS_WIN)

@@ -32,16 +32,6 @@ using TokenError = content::IdentityCredentialTokenError;
using DismissReason = content::IdentityRequestDialogController::DismissReason; using DismissReason = content::IdentityRequestDialogController::DismissReason;
class FedCmAccountSelectionViewDesktopTest; class FedCmAccountSelectionViewDesktopTest;
namespace {
constexpr char kTopFrameEtldPlusOne[] = "top-frame-example.com";
constexpr char kIdpEtldPlusOne[] = "idp-example.com";
constexpr char kConfigUrl[] = "https://idp-example.com/fedcm.json";
constexpr char kLoginUrl[] = "https://idp-example.com/login";
constexpr char kAccountId1[] = "account_id1";
constexpr char kAccountId2[] = "account_id2";
// Mock AccountSelectionViewBase which tracks state. // Mock AccountSelectionViewBase which tracks state.
class TestAccountSelectionView : public AccountSelectionViewBase, class TestAccountSelectionView : public AccountSelectionViewBase,
public views::WidgetDelegate { public views::WidgetDelegate {
@@ -127,6 +117,16 @@ class TestAccountSelectionView : public AccountSelectionViewBase,
std::vector<std::string> account_ids_; std::vector<std::string> account_ids_;
}; };
namespace {
constexpr char kTopFrameEtldPlusOne[] = "top-frame-example.com";
constexpr char kIdpEtldPlusOne[] = "idp-example.com";
constexpr char kConfigUrl[] = "https://idp-example.com/fedcm.json";
constexpr char kLoginUrl[] = "https://idp-example.com/login";
constexpr char kAccountId1[] = "account_id1";
constexpr char kAccountId2[] = "account_id2";
// Mock version of FedCmModalDialogView for injection during tests. // Mock version of FedCmModalDialogView for injection during tests.
class MockFedCmModalDialogView : public FedCmModalDialogView { class MockFedCmModalDialogView : public FedCmModalDialogView {
public: public:

@@ -693,6 +693,8 @@ DEFINE_LOCAL_STATE_IDENTIFIER_VALUE(LastHoverEventObserver, kHoverView3State);
BEGIN_METADATA(HoverDetectionView) BEGIN_METADATA(HoverDetectionView)
END_METADATA END_METADATA
} // namespace
class HoverDetectionBubbleView : public views::FlexLayoutView, class HoverDetectionBubbleView : public views::FlexLayoutView,
public views::BubbleDialogDelegate { public views::BubbleDialogDelegate {
METADATA_HEADER(HoverDetectionBubbleView, views::FlexLayoutView) METADATA_HEADER(HoverDetectionBubbleView, views::FlexLayoutView)
@@ -730,8 +732,6 @@ class HoverDetectionBubbleView : public views::FlexLayoutView,
BEGIN_METADATA(HoverDetectionBubbleView) BEGIN_METADATA(HoverDetectionBubbleView)
END_METADATA END_METADATA
} // namespace
class InteractiveBrowserTestHoverUiTest : public InteractiveBrowserTestUiTest { class InteractiveBrowserTestHoverUiTest : public InteractiveBrowserTestUiTest {
public: public:
InteractiveBrowserTestHoverUiTest() = default; InteractiveBrowserTestHoverUiTest() = default;

@@ -78,6 +78,8 @@ class TestFocusRules : public wm::BaseFocusRules {
bool can_activate_ = true; bool can_activate_ = true;
}; };
} // namespace
class NativeWidgetAuraTest : public ViewsTestBase { class NativeWidgetAuraTest : public ViewsTestBase {
public: public:
NativeWidgetAuraTest() = default; NativeWidgetAuraTest() = default;
@@ -1125,5 +1127,4 @@ TEST_F(NativeWidgetAuraWithNoDelegateTest, UpdateVisualStateTest) {
native_widget_->UpdateVisualState(); native_widget_->UpdateVisualState();
} }
} // namespace
} // namespace views } // namespace views