diff --git a/DEPS b/DEPS index 98b1b9a..31e22cc 100644 --- a/DEPS +++ b/DEPS
@@ -306,15 +306,15 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling Skia # and whatever else without interference from each other. - 'skia_revision': '053490edfa703f3433d97a299ee80f2acc93de71', + 'skia_revision': 'f82251f0091c52eee7125c06786d3c7e72c15327', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling V8 # and whatever else without interference from each other. - 'v8_revision': 'ba99d7f61f605e0c4c5131f01ff9d4fc36ab269b', + 'v8_revision': 'b057218023961f8b94b0313dd6ddbcc274c06e74', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling ANGLE # and whatever else without interference from each other. - 'angle_revision': '398cfb4b1421901b8c18be07faf5f54bf14c7633', + 'angle_revision': 'f8fae1ff4fae14fc6ba0aa1dc3af2e13a6e9a597', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling SwiftShader # and whatever else without interference from each other. @@ -821,7 +821,7 @@ 'src/clank': { 'url': Var('chrome_git') + '/clank/internal/apps.git' + '@' + - '3d55fc4f1877714a5aefaf5ca58e533d53b61244', + 'b570761166a159d8217203052bdfc29ec90ebef9', 'condition': 'checkout_android and checkout_src_internal', }, @@ -1664,7 +1664,7 @@ Var('pdfium_git') + '/pdfium.git' + '@' + Var('pdfium_revision'), 'src/third_party/perfetto': - Var('android_git') + '/platform/external/perfetto.git' + '@' + 'ff3b6318208109a97dc91f5f653edfca466d3cca', + Var('android_git') + '/platform/external/perfetto.git' + '@' + '0c152157409b6d7ba49a83eeeab1a358a1098d20', 'src/third_party/perl': { 'url': Var('chromium_git') + '/chromium/deps/perl.git' + '@' + '6f3e5028eb65d0b4c5fdd792106ac4c84eee1eb3', @@ -1972,7 +1972,7 @@ 'packages': [ { 'package': 'chromeos_internal/apps/help_app/app', - 'version': 'iTUrC08IXdr3eB2cSDBci-X0GlkLFUlGHp3ZFIv9YFQC', + 'version': '3Qbtr1ROVR8xYc3CYHk5WdgZ3HQLPITOB2NICHFQMG8C', }, ], 'condition': 'checkout_chromeos and checkout_src_internal',
diff --git a/android_webview/browser/aw_permission_manager.cc b/android_webview/browser/aw_permission_manager.cc index b317281..2629922 100644 --- a/android_webview/browser/aw_permission_manager.cc +++ b/android_webview/browser/aw_permission_manager.cc
@@ -509,7 +509,7 @@ } AwPermissionManager::SubscriptionId -AwPermissionManager::SubscribePermissionStatusChange( +AwPermissionManager::SubscribeToPermissionStatusChange( PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, @@ -518,7 +518,7 @@ return SubscriptionId(); } -void AwPermissionManager::UnsubscribePermissionStatusChange( +void AwPermissionManager::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) {} void AwPermissionManager::CancelPermissionRequest(int request_id) {
diff --git a/android_webview/browser/aw_permission_manager.h b/android_webview/browser/aw_permission_manager.h index ac133ed..eb7f5a13 100644 --- a/android_webview/browser/aw_permission_manager.h +++ b/android_webview/browser/aw_permission_manager.h
@@ -67,14 +67,14 @@ blink::PermissionType permission, content::RenderFrameHost* render_frame_host, const url::Origin& requesting_origin) override; - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, const GURL& requesting_origin, base::RepeatingCallback<void(blink::mojom::PermissionStatus)> callback) override; - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; void SetOriginCanReadEnumerateDevicesAudioLabels(const url::Origin& origin, bool audio);
diff --git a/ash/accelerators/accelerator_commands.cc b/ash/accelerators/accelerator_commands.cc index 27a27b4..2fb83e8 100644 --- a/ash/accelerators/accelerator_commands.cc +++ b/ash/accelerators/accelerator_commands.cc
@@ -1326,7 +1326,7 @@ DockedMagnifierController* docked_magnifier_controller = shell->docked_magnifier_controller(); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = shell->accessibility_controller(); const bool current_enabled = docked_magnifier_controller->GetEnabled(); @@ -1394,7 +1394,7 @@ FullscreenMagnifierController* magnification_controller = shell->fullscreen_magnifier_controller(); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = shell->accessibility_controller(); const bool current_enabled = magnification_controller->IsEnabled(); @@ -1442,7 +1442,7 @@ return; } - AccessibilityControllerImpl* controller = shell->accessibility_controller(); + AccessibilityController* controller = shell->accessibility_controller(); const bool current_enabled = controller->high_contrast().enabled(); const bool dialog_ever_accepted = controller->high_contrast().WasDialogAccepted();
diff --git a/ash/accelerators/accelerator_controller_unittest.cc b/ash/accelerators/accelerator_controller_unittest.cc index ecd76e4..a4701b0 100644 --- a/ash/accelerators/accelerator_controller_unittest.cc +++ b/ash/accelerators/accelerator_controller_unittest.cc
@@ -993,7 +993,7 @@ display::Display display = display::Screen::GetScreen()->GetPrimaryDisplay(); display::Display::Rotation initial_rotation = GetActiveDisplayRotation(display.id()); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(accessibility_controller @@ -1459,7 +1459,7 @@ } TEST_F(AcceleratorControllerTest, GlobalAcceleratorsToggleAppList) { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); // The press event should not toggle the AppList, the release should instead. @@ -2235,7 +2235,7 @@ } TEST_F(AcceleratorControllerTest, DisallowedWithNoWindow) { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); TestAccessibilityControllerClient client; @@ -2294,7 +2294,7 @@ TEST_F(AcceleratorControllerTest, TestDialogCancel) { ui::Accelerator accelerator(ui::VKEY_H, ui::EF_COMMAND_DOWN | ui::EF_CONTROL_DOWN); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); // Pressing cancel on the dialog should have no effect. EXPECT_FALSE(accessibility_controller->high_contrast().WasDialogAccepted()); @@ -2316,7 +2316,7 @@ ui::EF_COMMAND_DOWN | ui::EF_CONTROL_DOWN); // High Contrast Mode Enabled dialog and notification should be shown. EXPECT_FALSE(IsConfirmationDialogOpen()); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(accessibility_controller->high_contrast().WasDialogAccepted()); EXPECT_TRUE(ProcessInController(accelerator)); @@ -2751,7 +2751,7 @@ EXPECT_FALSE(fullscreen_magnifier_controller()->IsEnabled()); EXPECT_FALSE(IsConfirmationDialogOpen()); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); // Toggle the fullscreen magnifier on/off, dialog should be shown on first use // of accelerator. @@ -2799,7 +2799,7 @@ EXPECT_FALSE(fullscreen_magnifier_controller()->IsEnabled()); EXPECT_FALSE(IsConfirmationDialogOpen()); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); // Toggle the docked magnifier on/off, dialog should be shown on first use of // accelerator.
diff --git a/ash/accelerators/spoken_feedback_toggler.cc b/ash/accelerators/spoken_feedback_toggler.cc index 3924a9fc..bf1bed8 100644 --- a/ash/accelerators/spoken_feedback_toggler.cc +++ b/ash/accelerators/spoken_feedback_toggler.cc
@@ -52,7 +52,7 @@ void SpokenFeedbackToggler::OnKeyHold(const ui::KeyEvent* event) { if (!toggled_) { toggled_ = true; - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSpokenFeedbackEnabled( !controller->spoken_feedback().enabled(), A11Y_NOTIFICATION_SHOW);
diff --git a/ash/accelerators/spoken_feedback_toggler_unittest.cc b/ash/accelerators/spoken_feedback_toggler_unittest.cc index 548e848..791e196 100644 --- a/ash/accelerators/spoken_feedback_toggler_unittest.cc +++ b/ash/accelerators/spoken_feedback_toggler_unittest.cc
@@ -17,7 +17,7 @@ TEST_F(SpokenFeedbackTogglerTest, Basic) { SpokenFeedbackToggler::ScopedEnablerForTest scoped; - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); ui::test::EventGenerator* generator = GetEventGenerator(); EXPECT_FALSE(controller->spoken_feedback().enabled());
diff --git a/ash/accessibility/accessibility_controller_impl.cc b/ash/accessibility/accessibility_controller_impl.cc index ea61aed..996a8f2 100644 --- a/ash/accessibility/accessibility_controller_impl.cc +++ b/ash/accessibility/accessibility_controller_impl.cc
@@ -31,7 +31,6 @@ #include "ash/keyboard/ui/keyboard_util.h" #include "ash/login_status.h" #include "ash/policy/policy_recommendation_restorer.h" -#include "ash/public/cpp/accessibility_controller.h" #include "ash/public/cpp/accessibility_controller_client.h" #include "ash/public/cpp/ash_constants.h" #include "ash/public/cpp/notification_utils.h" @@ -55,6 +54,7 @@ #include "ash/system/power/backlights_forced_off_setter.h" #include "ash/system/power/power_status.h" #include "ash/system/power/scoped_backlights_forced_off.h" +#include "base/check_op.h" #include "base/feature_list.h" #include "base/functional/bind.h" #include "base/functional/callback_helpers.h" @@ -90,6 +90,8 @@ namespace ash { namespace { +AccessibilityController* g_instance = nullptr; + using FeatureType = A11yFeatureType; // These classes are used to store the static configuration for a11y features. @@ -392,7 +394,7 @@ } void ShowAccessibilityNotification( - const AccessibilityControllerImpl::A11yNotificationWrapper& wrapper) { + const AccessibilityController::A11yNotificationWrapper& wrapper) { A11yNotificationType type = wrapper.type; const auto& replacements = wrapper.replacements; message_center::MessageCenter* message_center = @@ -498,7 +500,7 @@ void RemoveAccessibilityNotification() { ShowAccessibilityNotification( - AccessibilityControllerImpl::A11yNotificationWrapper( + AccessibilityController::A11yNotificationWrapper( A11yNotificationType::kNone, std::vector<std::u16string>())); } @@ -807,13 +809,13 @@ } // namespace -AccessibilityControllerImpl::Feature::Feature( +AccessibilityController::Feature::Feature( FeatureType type, const std::string& pref_name, const gfx::VectorIcon* icon, const int name_resource_id, const bool toggleable_in_quicksettings, - AccessibilityControllerImpl* controller) + AccessibilityController* controller) : type_(type), pref_name_(pref_name), icon_(icon), @@ -827,9 +829,9 @@ } } -AccessibilityControllerImpl::Feature::~Feature() = default; +AccessibilityController::Feature::~Feature() = default; -void AccessibilityControllerImpl::Feature::SetEnabled(bool enabled) { +void AccessibilityController::Feature::SetEnabled(bool enabled) { PrefService* prefs = owner_->active_user_prefs_; if (!prefs) return; @@ -837,24 +839,24 @@ prefs->CommitPendingWrite(); } -bool AccessibilityControllerImpl::Feature::IsVisibleInTray() const { +bool AccessibilityController::Feature::IsVisibleInTray() const { return (conflicting_feature_ == FeatureType::kNoConflictingFeature || !owner_->GetFeature(conflicting_feature_).enabled()) && owner_->IsAccessibilityFeatureVisibleInTrayMenu(pref_name_); } -bool AccessibilityControllerImpl::Feature::IsEnterpriseIconVisible() const { +bool AccessibilityController::Feature::IsEnterpriseIconVisible() const { return owner_->IsEnterpriseIconVisibleInTrayMenu(pref_name_); } -const gfx::VectorIcon& AccessibilityControllerImpl::Feature::icon() const { +const gfx::VectorIcon& AccessibilityController::Feature::icon() const { DCHECK(icon_); if (icon_) return *icon_; return kPaletteTrayIconDefaultIcon; } -void AccessibilityControllerImpl::Feature::UpdateFromPref() { +void AccessibilityController::Feature::UpdateFromPref() { PrefService* prefs = owner_->active_user_prefs_; DCHECK(prefs); @@ -872,13 +874,13 @@ owner_->UpdateFeatureFromPref(type_); } -void AccessibilityControllerImpl::Feature::SetConflictingFeature( +void AccessibilityController::Feature::SetConflictingFeature( FeatureType feature) { DCHECK_EQ(conflicting_feature_, FeatureType::kNoConflictingFeature); conflicting_feature_ = feature; } -void AccessibilityControllerImpl::Feature::ObserveConflictingFeature() { +void AccessibilityController::Feature::ObserveConflictingFeature() { std::string conflicting_pref_name = ""; switch (conflicting_feature_) { case A11yFeatureType::kSpokenFeedback: @@ -894,28 +896,28 @@ pref_change_registrar_->Init(owner_->active_user_prefs_); pref_change_registrar_->Add( conflicting_pref_name, - base::BindRepeating(&AccessibilityControllerImpl::Feature::UpdateFromPref, + base::BindRepeating(&AccessibilityController::Feature::UpdateFromPref, base::Unretained(this))); } -AccessibilityControllerImpl::FeatureWithDialog::FeatureWithDialog( +AccessibilityController::FeatureWithDialog::FeatureWithDialog( FeatureType type, const std::string& pref_name, const gfx::VectorIcon* icon, const int name_resource_id, const bool toggleable_in_quicksettings, const Dialog& dialog, - AccessibilityControllerImpl* controller) - : AccessibilityControllerImpl::Feature(type, - pref_name, - icon, - name_resource_id, - toggleable_in_quicksettings, - controller), + AccessibilityController* controller) + : AccessibilityController::Feature(type, + pref_name, + icon, + name_resource_id, + toggleable_in_quicksettings, + controller), dialog_(dialog) {} -AccessibilityControllerImpl::FeatureWithDialog::~FeatureWithDialog() = default; +AccessibilityController::FeatureWithDialog::~FeatureWithDialog() = default; -void AccessibilityControllerImpl::FeatureWithDialog::SetDialogAccepted() { +void AccessibilityController::FeatureWithDialog::SetDialogAccepted() { PrefService* prefs = owner_->active_user_prefs_; if (!prefs) return; @@ -923,13 +925,13 @@ prefs->CommitPendingWrite(); } -bool AccessibilityControllerImpl::FeatureWithDialog::WasDialogAccepted() const { +bool AccessibilityController::FeatureWithDialog::WasDialogAccepted() const { PrefService* prefs = owner_->active_user_prefs_; DCHECK(prefs); return prefs->GetBoolean(dialog_.pref_name); } -void AccessibilityControllerImpl::FeatureWithDialog::SetEnabledWithDialog( +void AccessibilityController::FeatureWithDialog::SetEnabledWithDialog( bool enabled, base::OnceClosure completion_callback) { PrefService* prefs = owner_->active_user_prefs_; @@ -943,8 +945,8 @@ l10n_util::GetStringUTF16(IDS_APP_CANCEL), // Callback for if the user accepts the dialog base::BindOnce( - [](base::WeakPtr<AccessibilityControllerImpl> owner, - FeatureType type, base::OnceClosure completion_callback) { + [](base::WeakPtr<AccessibilityController> owner, FeatureType type, + base::OnceClosure completion_callback) { if (!owner) return; @@ -965,15 +967,23 @@ std::move(completion_callback).Run(); } -void AccessibilityControllerImpl::FeatureWithDialog::SetEnabled(bool enabled) { +void AccessibilityController::FeatureWithDialog::SetEnabled(bool enabled) { if (dialog_.mandatory) SetEnabledWithDialog(enabled, base::DoNothing()); else Feature::SetEnabled(enabled); } -AccessibilityControllerImpl::AccessibilityControllerImpl() +// static +AccessibilityController* AccessibilityController::Get() { + return g_instance; +} + +AccessibilityController::AccessibilityController() : autoclick_delay_(AutoclickController::GetDefaultAutoclickDelay()) { + DCHECK_EQ(nullptr, g_instance); + g_instance = this; + Shell::Get()->session_controller()->AddObserver(this); display::Screen::GetScreen()->AddObserver(this); CreateAccessibilityFeatures(); @@ -982,12 +992,15 @@ std::make_unique<AccessibilityNotificationController>(); } -AccessibilityControllerImpl::~AccessibilityControllerImpl() { +AccessibilityController::~AccessibilityController() { floating_menu_controller_.reset(); accessibility_notification_controller_.reset(); + + DCHECK_EQ(this, g_instance); + g_instance = nullptr; } -void AccessibilityControllerImpl::CreateAccessibilityFeatures() { +void AccessibilityController::CreateAccessibilityFeatures() { DCHECK(VerifyFeaturesData()); // First, build all features with dialog. std::map<FeatureType, Dialog> dialogs; @@ -1019,7 +1032,7 @@ } // static -void AccessibilityControllerImpl::RegisterProfilePrefs( +void AccessibilityController::RegisterProfilePrefs( PrefRegistrySimple* registry) { // // Non-syncable prefs. @@ -1282,7 +1295,7 @@ user_prefs::PrefRegistrySyncable::SYNCABLE_OS_PREF); } -void AccessibilityControllerImpl::Shutdown() { +void AccessibilityController::Shutdown() { display::Screen::GetScreen()->RemoveObserver(this); Shell::Get()->session_controller()->RemoveObserver(this); @@ -1294,14 +1307,14 @@ observer.OnAccessibilityControllerShutdown(); } -bool AccessibilityControllerImpl:: - HasDisplayRotationAcceleratorDialogBeenAccepted() const { +bool AccessibilityController::HasDisplayRotationAcceleratorDialogBeenAccepted() + const { return active_user_prefs_ && active_user_prefs_->GetBoolean( prefs::kDisplayRotationAcceleratorDialogHasBeenAccepted2); } -void AccessibilityControllerImpl:: +void AccessibilityController:: SetDisplayRotationAcceleratorDialogBeenAccepted() { if (!active_user_prefs_) return; @@ -1310,24 +1323,23 @@ active_user_prefs_->CommitPendingWrite(); } -void AccessibilityControllerImpl::AddObserver(AccessibilityObserver* observer) { +void AccessibilityController::AddObserver(AccessibilityObserver* observer) { observers_.AddObserver(observer); } -void AccessibilityControllerImpl::RemoveObserver( - AccessibilityObserver* observer) { +void AccessibilityController::RemoveObserver(AccessibilityObserver* observer) { observers_.RemoveObserver(observer); } -AccessibilityControllerImpl::Feature& AccessibilityControllerImpl::GetFeature( +AccessibilityController::Feature& AccessibilityController::GetFeature( FeatureType type) const { size_t feature_index = static_cast<size_t>(type); DCHECK(features_[feature_index].get()); return *features_[feature_index].get(); } -std::vector<AccessibilityControllerImpl::Feature*> -AccessibilityControllerImpl::GetEnabledFeaturesInQuickSettings() const { +std::vector<AccessibilityController::Feature*> +AccessibilityController::GetEnabledFeaturesInQuickSettings() const { std::vector<Feature*> enabled_features; for (auto& feature : features_) { @@ -1338,123 +1350,117 @@ return enabled_features; } -base::WeakPtr<AccessibilityControllerImpl> -AccessibilityControllerImpl::GetWeakPtr() { +base::WeakPtr<AccessibilityController> AccessibilityController::GetWeakPtr() { return weak_ptr_factory_.GetWeakPtr(); } -AccessibilityControllerImpl::Feature& AccessibilityControllerImpl::autoclick() - const { +AccessibilityController::Feature& AccessibilityController::autoclick() const { return GetFeature(FeatureType::kAutoclick); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::caret_highlight() const { +AccessibilityController::Feature& AccessibilityController::caret_highlight() + const { return GetFeature(FeatureType::kCaretHighlight); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::cursor_highlight() const { +AccessibilityController::Feature& AccessibilityController::cursor_highlight() + const { return GetFeature(FeatureType::kCursorHighlight); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::cursor_color() const { +AccessibilityController::Feature& AccessibilityController::cursor_color() + const { return GetFeature(FeatureType::kCursorColor); } -AccessibilityControllerImpl::Feature& AccessibilityControllerImpl::dictation() - const { +AccessibilityController::Feature& AccessibilityController::dictation() const { return GetFeature(FeatureType::kDictation); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::color_correction() const { +AccessibilityController::Feature& AccessibilityController::color_correction() + const { return GetFeature(FeatureType::kColorCorrection); } -AccessibilityControllerImpl::Feature& AccessibilityControllerImpl::face_gaze() - const { +AccessibilityController::Feature& AccessibilityController::face_gaze() const { return GetFeature(FeatureType::kFaceGaze); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::focus_highlight() const { +AccessibilityController::Feature& AccessibilityController::focus_highlight() + const { return GetFeature(FeatureType::kFocusHighlight); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::floating_menu() const { +AccessibilityController::Feature& AccessibilityController::floating_menu() + const { return GetFeature(FeatureType::kFloatingMenu); } -AccessibilityControllerImpl::FeatureWithDialog& -AccessibilityControllerImpl::fullscreen_magnifier() const { +AccessibilityController::FeatureWithDialog& +AccessibilityController::fullscreen_magnifier() const { return static_cast<FeatureWithDialog&>( GetFeature(FeatureType::kFullscreenMagnifier)); } -AccessibilityControllerImpl::FeatureWithDialog& -AccessibilityControllerImpl::docked_magnifier() const { +AccessibilityController::FeatureWithDialog& +AccessibilityController::docked_magnifier() const { return static_cast<FeatureWithDialog&>( GetFeature(FeatureType::kDockedMagnifier)); } -AccessibilityControllerImpl::FeatureWithDialog& -AccessibilityControllerImpl::high_contrast() const { +AccessibilityController::FeatureWithDialog& +AccessibilityController::high_contrast() const { return static_cast<FeatureWithDialog&>( GetFeature(FeatureType::kHighContrast)); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::large_cursor() const { +AccessibilityController::Feature& AccessibilityController::large_cursor() + const { return GetFeature(FeatureType::kLargeCursor); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::live_caption() const { +AccessibilityController::Feature& AccessibilityController::live_caption() + const { return GetFeature(FeatureType::kLiveCaption); } -AccessibilityControllerImpl::Feature& AccessibilityControllerImpl::mono_audio() - const { +AccessibilityController::Feature& AccessibilityController::mono_audio() const { return GetFeature(FeatureType::kMonoAudio); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::spoken_feedback() const { +AccessibilityController::Feature& AccessibilityController::spoken_feedback() + const { return GetFeature(FeatureType::kSpokenFeedback); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::select_to_speak() const { +AccessibilityController::Feature& AccessibilityController::select_to_speak() + const { return GetFeature(FeatureType::kSelectToSpeak); } -AccessibilityControllerImpl::Feature& AccessibilityControllerImpl::sticky_keys() - const { +AccessibilityController::Feature& AccessibilityController::sticky_keys() const { return GetFeature(FeatureType::kStickyKeys); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::switch_access() const { +AccessibilityController::Feature& AccessibilityController::switch_access() + const { return GetFeature(FeatureType::kSwitchAccess); } -AccessibilityControllerImpl::Feature& -AccessibilityControllerImpl::virtual_keyboard() const { +AccessibilityController::Feature& AccessibilityController::virtual_keyboard() + const { return GetFeature(FeatureType::kVirtualKeyboard); } -bool AccessibilityControllerImpl::IsAutoclickSettingVisibleInTray() { +bool AccessibilityController::IsAutoclickSettingVisibleInTray() { return autoclick().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForAutoclick() { +bool AccessibilityController::IsEnterpriseIconVisibleForAutoclick() { return autoclick().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsPrimarySettingsViewVisibleInTray() { +bool AccessibilityController::IsPrimarySettingsViewVisibleInTray() { return (IsSpokenFeedbackSettingVisibleInTray() || IsSelectToSpeakSettingVisibleInTray() || IsDictationSettingVisibleInTray() || @@ -1469,72 +1475,71 @@ IsLiveCaptionSettingVisibleInTray()); } -bool AccessibilityControllerImpl::IsCaretHighlightSettingVisibleInTray() { +bool AccessibilityController::IsCaretHighlightSettingVisibleInTray() { return caret_highlight().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForCaretHighlight() { +bool AccessibilityController::IsEnterpriseIconVisibleForCaretHighlight() { return caret_highlight().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsCursorHighlightSettingVisibleInTray() { +bool AccessibilityController::IsCursorHighlightSettingVisibleInTray() { return cursor_highlight().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForCursorHighlight() { +bool AccessibilityController::IsEnterpriseIconVisibleForCursorHighlight() { return cursor_highlight().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsDictationSettingVisibleInTray() { +bool AccessibilityController::IsDictationSettingVisibleInTray() { return dictation().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForDictation() { +bool AccessibilityController::IsEnterpriseIconVisibleForDictation() { return dictation().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsFaceGazeSettingVisibleInTray() { +bool AccessibilityController::IsFaceGazeSettingVisibleInTray() { return face_gaze().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForFaceGaze() { +bool AccessibilityController::IsEnterpriseIconVisibleForFaceGaze() { return face_gaze().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsFocusHighlightSettingVisibleInTray() { +bool AccessibilityController::IsFocusHighlightSettingVisibleInTray() { return focus_highlight().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForFocusHighlight() { +bool AccessibilityController::IsEnterpriseIconVisibleForFocusHighlight() { return focus_highlight().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsFullScreenMagnifierSettingVisibleInTray() { +bool AccessibilityController::IsFullScreenMagnifierSettingVisibleInTray() { return fullscreen_magnifier().IsVisibleInTray(); } -bool AccessibilityControllerImpl:: - IsEnterpriseIconVisibleForFullScreenMagnifier() { +bool AccessibilityController::IsEnterpriseIconVisibleForFullScreenMagnifier() { return fullscreen_magnifier().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsDockedMagnifierSettingVisibleInTray() { +bool AccessibilityController::IsDockedMagnifierSettingVisibleInTray() { return docked_magnifier().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForDockedMagnifier() { +bool AccessibilityController::IsEnterpriseIconVisibleForDockedMagnifier() { return docked_magnifier().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsHighContrastSettingVisibleInTray() { +bool AccessibilityController::IsHighContrastSettingVisibleInTray() { return high_contrast().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForHighContrast() { +bool AccessibilityController::IsEnterpriseIconVisibleForHighContrast() { return high_contrast().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsColorCorrectionSettingVisibleInTray() { +bool AccessibilityController::IsColorCorrectionSettingVisibleInTray() { if (!color_correction().enabled() && Shell::Get()->session_controller()->login_status() == ash::LoginStatus::NOT_LOGGED_IN) { @@ -1545,41 +1550,41 @@ return color_correction().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForColorCorrection() { +bool AccessibilityController::IsEnterpriseIconVisibleForColorCorrection() { return color_correction().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsLargeCursorSettingVisibleInTray() { +bool AccessibilityController::IsLargeCursorSettingVisibleInTray() { return large_cursor().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForLargeCursor() { +bool AccessibilityController::IsEnterpriseIconVisibleForLargeCursor() { return large_cursor().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsLiveCaptionSettingVisibleInTray() { +bool AccessibilityController::IsLiveCaptionSettingVisibleInTray() { return captions::IsLiveCaptionFeatureSupported() && base::FeatureList::IsEnabled( media::kLiveCaptionSystemWideOnChromeOS) && live_caption().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForLiveCaption() { +bool AccessibilityController::IsEnterpriseIconVisibleForLiveCaption() { return captions::IsLiveCaptionFeatureSupported() && base::FeatureList::IsEnabled( media::kLiveCaptionSystemWideOnChromeOS) && live_caption().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsMonoAudioSettingVisibleInTray() { +bool AccessibilityController::IsMonoAudioSettingVisibleInTray() { return mono_audio().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForMonoAudio() { +bool AccessibilityController::IsEnterpriseIconVisibleForMonoAudio() { return mono_audio().IsEnterpriseIconVisible(); } -void AccessibilityControllerImpl::SetSpokenFeedbackEnabled( +void AccessibilityController::SetSpokenFeedbackEnabled( bool enabled, AccessibilityNotificationVisibility notify) { spoken_feedback().SetEnabled(enabled); @@ -1596,28 +1601,27 @@ A11yNotificationWrapper(type, std::vector<std::u16string>())); } -bool AccessibilityControllerImpl::IsSpokenFeedbackSettingVisibleInTray() { +bool AccessibilityController::IsSpokenFeedbackSettingVisibleInTray() { return spoken_feedback().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForSpokenFeedback() { +bool AccessibilityController::IsEnterpriseIconVisibleForSpokenFeedback() { return spoken_feedback().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsSelectToSpeakSettingVisibleInTray() { +bool AccessibilityController::IsSelectToSpeakSettingVisibleInTray() { return select_to_speak().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForSelectToSpeak() { +bool AccessibilityController::IsEnterpriseIconVisibleForSelectToSpeak() { return select_to_speak().IsEnterpriseIconVisible(); } -void AccessibilityControllerImpl::RequestSelectToSpeakStateChange() { +void AccessibilityController::RequestSelectToSpeakStateChange() { client_->RequestSelectToSpeakStateChange(); } -void AccessibilityControllerImpl::SetSelectToSpeakState( - SelectToSpeakState state) { +void AccessibilityController::SetSelectToSpeakState(SelectToSpeakState state) { select_to_speak_state_ = state; // Forward the state change event to select_to_speak_event_handler_. @@ -1630,20 +1634,19 @@ NotifyAccessibilityStatusChanged(); } -void AccessibilityControllerImpl::SetSelectToSpeakEventHandlerDelegate( +void AccessibilityController::SetSelectToSpeakEventHandlerDelegate( SelectToSpeakEventHandlerDelegate* delegate) { select_to_speak_event_handler_delegate_ = delegate; MaybeCreateSelectToSpeakEventHandler(); } -SelectToSpeakState AccessibilityControllerImpl::GetSelectToSpeakState() const { +SelectToSpeakState AccessibilityController::GetSelectToSpeakState() const { return select_to_speak_state_; } -void AccessibilityControllerImpl::ShowSelectToSpeakPanel( - const gfx::Rect& anchor, - bool is_paused, - double speech_rate) { +void AccessibilityController::ShowSelectToSpeakPanel(const gfx::Rect& anchor, + bool is_paused, + double speech_rate) { if (!select_to_speak_bubble_controller_) { select_to_speak_bubble_controller_ = std::make_unique<SelectToSpeakMenuBubbleController>(); @@ -1651,14 +1654,14 @@ select_to_speak_bubble_controller_->Show(anchor, is_paused, speech_rate); } -void AccessibilityControllerImpl::HideSelectToSpeakPanel() { +void AccessibilityController::HideSelectToSpeakPanel() { if (!select_to_speak_bubble_controller_) { return; } select_to_speak_bubble_controller_->Hide(); } -void AccessibilityControllerImpl::OnSelectToSpeakPanelAction( +void AccessibilityController::OnSelectToSpeakPanelAction( SelectToSpeakPanelAction action, double value) { if (!client_) { @@ -1667,11 +1670,11 @@ client_->OnSelectToSpeakPanelAction(action, value); } -bool AccessibilityControllerImpl::IsSwitchAccessRunning() const { +bool AccessibilityController::IsSwitchAccessRunning() const { return switch_access().enabled() || switch_access_disable_dialog_showing_; } -bool AccessibilityControllerImpl::IsSwitchAccessSettingVisibleInTray() { +bool AccessibilityController::IsSwitchAccessSettingVisibleInTray() { // Switch Access cannot be enabled on the sign-in page because there is no way // to configure switches while the device is locked. if (!switch_access().enabled() && @@ -1682,57 +1685,57 @@ return switch_access().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForSwitchAccess() { +bool AccessibilityController::IsEnterpriseIconVisibleForSwitchAccess() { return switch_access().IsEnterpriseIconVisible(); } -void AccessibilityControllerImpl::SetAccessibilityEventRewriter( +void AccessibilityController::SetAccessibilityEventRewriter( AccessibilityEventRewriter* accessibility_event_rewriter) { accessibility_event_rewriter_ = accessibility_event_rewriter; } -void AccessibilityControllerImpl::HideSwitchAccessBackButton() { +void AccessibilityController::HideSwitchAccessBackButton() { if (IsSwitchAccessRunning()) switch_access_bubble_controller_->HideBackButton(); } -void AccessibilityControllerImpl::HideSwitchAccessMenu() { +void AccessibilityController::HideSwitchAccessMenu() { if (IsSwitchAccessRunning()) switch_access_bubble_controller_->HideMenuBubble(); } -void AccessibilityControllerImpl::ShowSwitchAccessBackButton( +void AccessibilityController::ShowSwitchAccessBackButton( const gfx::Rect& anchor) { switch_access_bubble_controller_->ShowBackButton(anchor); } -void AccessibilityControllerImpl::ShowSwitchAccessMenu( +void AccessibilityController::ShowSwitchAccessMenu( const gfx::Rect& anchor, std::vector<std::string> actions_to_show) { switch_access_bubble_controller_->ShowMenu(anchor, actions_to_show); } -bool AccessibilityControllerImpl::IsPointScanEnabled() { +bool AccessibilityController::IsPointScanEnabled() { return point_scan_controller_.get() && point_scan_controller_->IsPointScanEnabled(); } -void AccessibilityControllerImpl::StartPointScan() { +void AccessibilityController::StartPointScan() { point_scan_controller_->Start(); } -void AccessibilityControllerImpl::SetA11yOverrideWindow( +void AccessibilityController::SetA11yOverrideWindow( aura::Window* a11y_override_window) { if (client_) client_->SetA11yOverrideWindow(a11y_override_window); } -void AccessibilityControllerImpl::StopPointScan() { +void AccessibilityController::StopPointScan() { if (point_scan_controller_) point_scan_controller_->HideAll(); } -void AccessibilityControllerImpl::SetPointScanSpeedDipsPerSecond( +void AccessibilityController::SetPointScanSpeedDipsPerSecond( int point_scan_speed_dips_per_second) { if (point_scan_controller_) { point_scan_controller_->SetSpeedDipsPerSecond( @@ -1740,28 +1743,27 @@ } } -void AccessibilityControllerImpl:: - DisablePolicyRecommendationRestorerForTesting() { +void AccessibilityController::DisablePolicyRecommendationRestorerForTesting() { Shell::Get()->policy_recommendation_restorer()->DisableForTesting(); } -bool AccessibilityControllerImpl::IsStickyKeysSettingVisibleInTray() { +bool AccessibilityController::IsStickyKeysSettingVisibleInTray() { return sticky_keys().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForStickyKeys() { +bool AccessibilityController::IsEnterpriseIconVisibleForStickyKeys() { return sticky_keys().IsEnterpriseIconVisible(); } -bool AccessibilityControllerImpl::IsVirtualKeyboardSettingVisibleInTray() { +bool AccessibilityController::IsVirtualKeyboardSettingVisibleInTray() { return virtual_keyboard().IsVisibleInTray(); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleForVirtualKeyboard() { +bool AccessibilityController::IsEnterpriseIconVisibleForVirtualKeyboard() { return virtual_keyboard().IsEnterpriseIconVisible(); } -void AccessibilityControllerImpl::ShowFloatingMenuIfEnabled() { +void AccessibilityController::ShowFloatingMenuIfEnabled() { if (floating_menu().enabled() && !floating_menu_controller_) { floating_menu_controller_ = std::make_unique<FloatingAccessibilityController>(this); @@ -1772,15 +1774,15 @@ } FloatingAccessibilityController* -AccessibilityControllerImpl::GetFloatingMenuController() { +AccessibilityController::GetFloatingMenuController() { return floating_menu_controller_.get(); } -PointScanController* AccessibilityControllerImpl::GetPointScanController() { +PointScanController* AccessibilityController::GetPointScanController() { return point_scan_controller_.get(); } -void AccessibilityControllerImpl::SetTabletModeShelfNavigationButtonsEnabled( +void AccessibilityController::SetTabletModeShelfNavigationButtonsEnabled( bool enabled) { if (!active_user_prefs_) return; @@ -1790,35 +1792,35 @@ active_user_prefs_->CommitPendingWrite(); } -void AccessibilityControllerImpl::TriggerAccessibilityAlert( +void AccessibilityController::TriggerAccessibilityAlert( AccessibilityAlert alert) { if (client_) client_->TriggerAccessibilityAlert(alert); } -void AccessibilityControllerImpl::TriggerAccessibilityAlertWithMessage( +void AccessibilityController::TriggerAccessibilityAlertWithMessage( const std::string& message) { if (client_) client_->TriggerAccessibilityAlertWithMessage(message); } -void AccessibilityControllerImpl::PlayEarcon(Sound sound_key) { +void AccessibilityController::PlayEarcon(Sound sound_key) { if (client_) client_->PlayEarcon(sound_key); } -base::TimeDelta AccessibilityControllerImpl::PlayShutdownSound() { +base::TimeDelta AccessibilityController::PlayShutdownSound() { return client_ ? client_->PlayShutdownSound() : base::TimeDelta(); } -void AccessibilityControllerImpl::HandleAccessibilityGesture( +void AccessibilityController::HandleAccessibilityGesture( ax::mojom::Gesture gesture, gfx::PointF location) { if (client_) client_->HandleAccessibilityGesture(gesture, location); } -void AccessibilityControllerImpl::ToggleDictation() { +void AccessibilityController::ToggleDictation() { // Do nothing if dictation is not enabled. if (!dictation().enabled()) return; @@ -1833,11 +1835,11 @@ } } -void AccessibilityControllerImpl::SetDictationActive(bool is_active) { +void AccessibilityController::SetDictationActive(bool is_active) { dictation_active_ = is_active; } -void AccessibilityControllerImpl::ToggleDictationFromSource( +void AccessibilityController::ToggleDictationFromSource( DictationToggleSource source) { base::RecordAction(base::UserMetricsAction("Accel_Toggle_Dictation")); UMA_HISTOGRAM_ENUMERATION("Accessibility.CrosDictation.ToggleDictationMethod", @@ -1847,7 +1849,7 @@ ToggleDictation(); } -void AccessibilityControllerImpl::EnableOrToggleDictationFromSource( +void AccessibilityController::EnableOrToggleDictationFromSource( DictationToggleSource source) { if (::features::IsAccessibilityDictationKeyboardImprovementsEnabled()) { if (dictation().enabled()) { @@ -1872,7 +1874,7 @@ } } -void AccessibilityControllerImpl::ShowDictationKeyboardDialog() { +void AccessibilityController::ShowDictationKeyboardDialog() { if (!::features::IsAccessibilityDictationKeyboardImprovementsEnabled() || !client_) { return; @@ -1906,17 +1908,17 @@ ShowConfirmationDialog( title, description, l10n_util::GetStringUTF16(IDS_APP_CANCEL), base::BindOnce( - &AccessibilityControllerImpl::OnDictationKeyboardDialogAccepted, + &AccessibilityController::OnDictationKeyboardDialogAccepted, GetWeakPtr()), base::BindOnce( - &AccessibilityControllerImpl::OnDictationKeyboardDialogDismissed, + &AccessibilityController::OnDictationKeyboardDialogDismissed, GetWeakPtr()), base::BindOnce( - &AccessibilityControllerImpl::OnDictationKeyboardDialogDismissed, + &AccessibilityController::OnDictationKeyboardDialogDismissed, GetWeakPtr())); } -void AccessibilityControllerImpl::OnDictationKeyboardDialogAccepted() { +void AccessibilityController::OnDictationKeyboardDialogAccepted() { if (!::features::IsAccessibilityDictationKeyboardImprovementsEnabled()) { return; } @@ -1929,7 +1931,7 @@ dictation().SetEnabled(true); } -void AccessibilityControllerImpl::OnDictationKeyboardDialogDismissed() { +void AccessibilityController::OnDictationKeyboardDialogDismissed() { if (!::features::IsAccessibilityDictationKeyboardImprovementsEnabled()) { return; } @@ -1937,7 +1939,7 @@ dictation_keyboard_dialog_showing_for_testing_ = false; } -void AccessibilityControllerImpl::ShowDictationLanguageUpgradedNudge( +void AccessibilityController::ShowDictationLanguageUpgradedNudge( const std::string& dictation_locale, const std::string& application_locale) { if (features::IsSystemNudgeMigrationEnabled()) { @@ -1960,43 +1962,42 @@ dictation_nudge_controller_->ShowNudge(); } -void AccessibilityControllerImpl::SilenceSpokenFeedback() { +void AccessibilityController::SilenceSpokenFeedback() { if (client_) client_->SilenceSpokenFeedback(); } -void AccessibilityControllerImpl::OnTwoFingerTouchStart() { +void AccessibilityController::OnTwoFingerTouchStart() { if (client_) client_->OnTwoFingerTouchStart(); } -void AccessibilityControllerImpl::OnTwoFingerTouchStop() { +void AccessibilityController::OnTwoFingerTouchStop() { if (client_) client_->OnTwoFingerTouchStop(); } -bool AccessibilityControllerImpl::ShouldToggleSpokenFeedbackViaTouch() const { +bool AccessibilityController::ShouldToggleSpokenFeedbackViaTouch() const { return client_ && client_->ShouldToggleSpokenFeedbackViaTouch(); } -void AccessibilityControllerImpl::PlaySpokenFeedbackToggleCountdown( +void AccessibilityController::PlaySpokenFeedbackToggleCountdown( int tick_count) { if (client_) client_->PlaySpokenFeedbackToggleCountdown(tick_count); } -bool AccessibilityControllerImpl::IsEnterpriseIconVisibleInTrayMenu( +bool AccessibilityController::IsEnterpriseIconVisibleInTrayMenu( const std::string& path) { return active_user_prefs_ && active_user_prefs_->FindPreference(path)->IsManaged(); } -void AccessibilityControllerImpl::SetClient( - AccessibilityControllerClient* client) { +void AccessibilityController::SetClient(AccessibilityControllerClient* client) { client_ = client; } -void AccessibilityControllerImpl::SetDarkenScreen(bool darken) { +void AccessibilityController::SetDarkenScreen(bool darken) { if (darken && !scoped_backlights_forced_off_) { scoped_backlights_forced_off_ = Shell::Get()->backlights_forced_off_setter()->ForceBacklightsOff(); @@ -2005,7 +2006,7 @@ } } -void AccessibilityControllerImpl::BrailleDisplayStateChanged(bool connected) { +void AccessibilityController::BrailleDisplayStateChanged(bool connected) { A11yNotificationType type = A11yNotificationType::kNone; if (connected && spoken_feedback().enabled()) type = A11yNotificationType::kBrailleDisplayConnected; @@ -2020,32 +2021,32 @@ A11yNotificationWrapper(type, std::vector<std::u16string>())); } -void AccessibilityControllerImpl::SetFocusHighlightRect( +void AccessibilityController::SetFocusHighlightRect( const gfx::Rect& bounds_in_screen) { if (!accessibility_highlight_controller_) return; accessibility_highlight_controller_->SetFocusHighlightRect(bounds_in_screen); } -void AccessibilityControllerImpl::SetCaretBounds( +void AccessibilityController::SetCaretBounds( const gfx::Rect& bounds_in_screen) { if (!accessibility_highlight_controller_) return; accessibility_highlight_controller_->SetCaretBounds(bounds_in_screen); } -void AccessibilityControllerImpl::SetAccessibilityPanelAlwaysVisible( +void AccessibilityController::SetAccessibilityPanelAlwaysVisible( bool always_visible) { GetLayoutManager()->SetAlwaysVisible(always_visible); } -void AccessibilityControllerImpl::SetAccessibilityPanelBounds( +void AccessibilityController::SetAccessibilityPanelBounds( const gfx::Rect& bounds, AccessibilityPanelState state) { GetLayoutManager()->SetPanelBounds(bounds, state); } -void AccessibilityControllerImpl::OnSigninScreenPrefServiceInitialized( +void AccessibilityController::OnSigninScreenPrefServiceInitialized( PrefService* prefs) { // Make |kA11yPrefsForRecommendedValueOnSignin| observing recommended values // on signin screen. See PolicyRecommendationRestorer. @@ -2058,7 +2059,7 @@ ObservePrefs(prefs); } -void AccessibilityControllerImpl::OnActiveUserPrefServiceChanged( +void AccessibilityController::OnActiveUserPrefServiceChanged( PrefService* prefs) { // This is guaranteed to be received after // OnSigninScreenPrefServiceInitialized() so only copy the signin prefs if @@ -2067,7 +2068,7 @@ ObservePrefs(prefs); } -void AccessibilityControllerImpl::OnSessionStateChanged( +void AccessibilityController::OnSessionStateChanged( session_manager::SessionState state) { // Everything behind the lock screen is in // kShellWindowId_NonLockScreenContainersContainer. If the session state is @@ -2084,21 +2085,20 @@ } AccessibilityEventRewriter* -AccessibilityControllerImpl::GetAccessibilityEventRewriterForTest() { +AccessibilityController::GetAccessibilityEventRewriterForTest() { return accessibility_event_rewriter_; } -void AccessibilityControllerImpl:: +void AccessibilityController:: DisableSwitchAccessDisableConfirmationDialogTesting() { no_switch_access_disable_confirmation_dialog_for_testing_ = true; } -void AccessibilityControllerImpl:: - DisableSwitchAccessEnableNotificationTesting() { +void AccessibilityController::DisableSwitchAccessEnableNotificationTesting() { skip_switch_access_notification_ = true; } -void AccessibilityControllerImpl::OnDisplayTabletStateChanged( +void AccessibilityController::OnDisplayTabletStateChanged( display::TabletState state) { if (spoken_feedback().enabled()) { // Show accessibility notification when tablet mode transition is completed. @@ -2111,7 +2111,7 @@ } } -void AccessibilityControllerImpl::ObservePrefs(PrefService* prefs) { +void AccessibilityController::ObservePrefs(PrefService* prefs) { DCHECK(prefs); active_user_prefs_ = prefs; @@ -2125,9 +2125,8 @@ DCHECK(feature); pref_change_registrar_->Add( feature->pref_name(), - base::BindRepeating( - &AccessibilityControllerImpl::Feature::UpdateFromPref, - base::Unretained(feature.get()))); + base::BindRepeating(&AccessibilityController::Feature::UpdateFromPref, + base::Unretained(feature.get()))); if (feature->conflicting_feature() != FeatureType::kNoConflictingFeature) { feature->ObserveConflictingFeature(); } @@ -2137,102 +2136,100 @@ pref_change_registrar_->Add( prefs::kAccessibilityAutoclickDelayMs, base::BindRepeating( - &AccessibilityControllerImpl::UpdateAutoclickDelayFromPref, + &AccessibilityController::UpdateAutoclickDelayFromPref, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityAutoclickEventType, base::BindRepeating( - &AccessibilityControllerImpl::UpdateAutoclickEventTypeFromPref, + &AccessibilityController::UpdateAutoclickEventTypeFromPref, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityAutoclickRevertToLeftClick, - base::BindRepeating(&AccessibilityControllerImpl:: - UpdateAutoclickRevertToLeftClickFromPref, - base::Unretained(this))); + base::BindRepeating( + &AccessibilityController::UpdateAutoclickRevertToLeftClickFromPref, + base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityAutoclickStabilizePosition, - base::BindRepeating(&AccessibilityControllerImpl:: - UpdateAutoclickStabilizePositionFromPref, - base::Unretained(this))); + base::BindRepeating( + &AccessibilityController::UpdateAutoclickStabilizePositionFromPref, + base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityAutoclickMovementThreshold, - base::BindRepeating(&AccessibilityControllerImpl:: - UpdateAutoclickMovementThresholdFromPref, - base::Unretained(this))); + base::BindRepeating( + &AccessibilityController::UpdateAutoclickMovementThresholdFromPref, + base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityAutoclickMenuPosition, base::BindRepeating( - &AccessibilityControllerImpl::UpdateAutoclickMenuPositionFromPref, + &AccessibilityController::UpdateAutoclickMenuPositionFromPref, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityFloatingMenuPosition, base::BindRepeating( - &AccessibilityControllerImpl::UpdateFloatingMenuPositionFromPref, + &AccessibilityController::UpdateFloatingMenuPositionFromPref, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityLargeCursorDipSize, - base::BindRepeating( - &AccessibilityControllerImpl::UpdateLargeCursorFromPref, - base::Unretained(this))); + base::BindRepeating(&AccessibilityController::UpdateLargeCursorFromPref, + base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityShortcutsEnabled, base::BindRepeating( - &AccessibilityControllerImpl::UpdateShortcutsEnabledFromPref, + &AccessibilityController::UpdateShortcutsEnabledFromPref, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilitySwitchAccessSelectDeviceKeyCodes, base::BindRepeating( - &AccessibilityControllerImpl::UpdateSwitchAccessKeyCodesFromPref, + &AccessibilityController::UpdateSwitchAccessKeyCodesFromPref, base::Unretained(this), SwitchAccessCommand::kSelect)); pref_change_registrar_->Add( prefs::kAccessibilitySwitchAccessNextDeviceKeyCodes, base::BindRepeating( - &AccessibilityControllerImpl::UpdateSwitchAccessKeyCodesFromPref, + &AccessibilityController::UpdateSwitchAccessKeyCodesFromPref, base::Unretained(this), SwitchAccessCommand::kNext)); pref_change_registrar_->Add( prefs::kAccessibilitySwitchAccessPreviousDeviceKeyCodes, base::BindRepeating( - &AccessibilityControllerImpl::UpdateSwitchAccessKeyCodesFromPref, + &AccessibilityController::UpdateSwitchAccessKeyCodesFromPref, base::Unretained(this), SwitchAccessCommand::kPrevious)); pref_change_registrar_->Add( prefs::kAccessibilitySwitchAccessAutoScanEnabled, - base::BindRepeating(&AccessibilityControllerImpl:: - UpdateSwitchAccessAutoScanEnabledFromPref, - base::Unretained(this))); + base::BindRepeating( + &AccessibilityController::UpdateSwitchAccessAutoScanEnabledFromPref, + base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilitySwitchAccessAutoScanSpeedMs, base::BindRepeating( - &AccessibilityControllerImpl::UpdateSwitchAccessAutoScanSpeedFromPref, + &AccessibilityController::UpdateSwitchAccessAutoScanSpeedFromPref, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilitySwitchAccessAutoScanKeyboardSpeedMs, - base::BindRepeating(&AccessibilityControllerImpl:: + base::BindRepeating(&AccessibilityController:: UpdateSwitchAccessAutoScanKeyboardSpeedFromPref, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilitySwitchAccessPointScanSpeedDipsPerSecond, - base::BindRepeating(&AccessibilityControllerImpl:: - UpdateSwitchAccessPointScanSpeedFromPref, - base::Unretained(this))); + base::BindRepeating( + &AccessibilityController::UpdateSwitchAccessPointScanSpeedFromPref, + base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityTabletModeShelfNavigationButtonsEnabled, - base::BindRepeating(&AccessibilityControllerImpl:: + base::BindRepeating(&AccessibilityController:: UpdateTabletModeShelfNavigationButtonsFromPref, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityCursorColor, - base::BindRepeating( - &AccessibilityControllerImpl::UpdateCursorColorFromPrefs, - base::Unretained(this))); + base::BindRepeating(&AccessibilityController::UpdateCursorColorFromPrefs, + base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityColorVisionCorrectionAmount, base::BindRepeating( - &AccessibilityControllerImpl::UpdateColorCorrectionFromPrefs, + &AccessibilityController::UpdateColorCorrectionFromPrefs, base::Unretained(this))); pref_change_registrar_->Add( prefs::kAccessibilityColorVisionCorrectionType, base::BindRepeating( - &AccessibilityControllerImpl::UpdateColorCorrectionFromPrefs, + &AccessibilityController::UpdateColorCorrectionFromPrefs, base::Unretained(this))); // Load current state. @@ -2258,7 +2255,7 @@ } } -void AccessibilityControllerImpl::UpdateAutoclickDelayFromPref() { +void AccessibilityController::UpdateAutoclickDelayFromPref() { DCHECK(active_user_prefs_); base::TimeDelta autoclick_delay = base::Milliseconds(int64_t{ active_user_prefs_->GetInteger(prefs::kAccessibilityAutoclickDelayMs)}); @@ -2270,12 +2267,12 @@ Shell::Get()->autoclick_controller()->SetAutoclickDelay(autoclick_delay_); } -void AccessibilityControllerImpl::UpdateAutoclickEventTypeFromPref() { +void AccessibilityController::UpdateAutoclickEventTypeFromPref() { Shell::Get()->autoclick_controller()->SetAutoclickEventType( GetAutoclickEventType()); } -void AccessibilityControllerImpl::SetAutoclickEventType( +void AccessibilityController::SetAutoclickEventType( AutoclickEventType event_type) { if (!active_user_prefs_) return; @@ -2285,13 +2282,13 @@ Shell::Get()->autoclick_controller()->SetAutoclickEventType(event_type); } -AutoclickEventType AccessibilityControllerImpl::GetAutoclickEventType() { +AutoclickEventType AccessibilityController::GetAutoclickEventType() { DCHECK(active_user_prefs_); return static_cast<AutoclickEventType>( active_user_prefs_->GetInteger(prefs::kAccessibilityAutoclickEventType)); } -void AccessibilityControllerImpl::UpdateAutoclickRevertToLeftClickFromPref() { +void AccessibilityController::UpdateAutoclickRevertToLeftClickFromPref() { DCHECK(active_user_prefs_); bool revert_to_left_click = active_user_prefs_->GetBoolean( prefs::kAccessibilityAutoclickRevertToLeftClick); @@ -2300,7 +2297,7 @@ revert_to_left_click); } -void AccessibilityControllerImpl::UpdateAutoclickStabilizePositionFromPref() { +void AccessibilityController::UpdateAutoclickStabilizePositionFromPref() { DCHECK(active_user_prefs_); bool stabilize_position = active_user_prefs_->GetBoolean( prefs::kAccessibilityAutoclickStabilizePosition); @@ -2309,7 +2306,7 @@ stabilize_position); } -void AccessibilityControllerImpl::UpdateAutoclickMovementThresholdFromPref() { +void AccessibilityController::UpdateAutoclickMovementThresholdFromPref() { DCHECK(active_user_prefs_); int movement_threshold = active_user_prefs_->GetInteger( prefs::kAccessibilityAutoclickMovementThreshold); @@ -2318,12 +2315,12 @@ movement_threshold); } -void AccessibilityControllerImpl::UpdateAutoclickMenuPositionFromPref() { +void AccessibilityController::UpdateAutoclickMenuPositionFromPref() { Shell::Get()->autoclick_controller()->SetMenuPosition( GetAutoclickMenuPosition()); } -void AccessibilityControllerImpl::SetAutoclickMenuPosition( +void AccessibilityController::SetAutoclickMenuPosition( FloatingMenuPosition position) { if (!active_user_prefs_) return; @@ -2333,25 +2330,25 @@ Shell::Get()->autoclick_controller()->SetMenuPosition(position); } -FloatingMenuPosition AccessibilityControllerImpl::GetAutoclickMenuPosition() { +FloatingMenuPosition AccessibilityController::GetAutoclickMenuPosition() { DCHECK(active_user_prefs_); return static_cast<FloatingMenuPosition>(active_user_prefs_->GetInteger( prefs::kAccessibilityAutoclickMenuPosition)); } -void AccessibilityControllerImpl::RequestAutoclickScrollableBoundsForPoint( +void AccessibilityController::RequestAutoclickScrollableBoundsForPoint( const gfx::Point& point_in_screen) { if (client_) client_->RequestAutoclickScrollableBoundsForPoint(point_in_screen); } -void AccessibilityControllerImpl::MagnifierBoundsChanged( +void AccessibilityController::MagnifierBoundsChanged( const gfx::Rect& bounds_in_screen) { if (client_) client_->MagnifierBoundsChanged(bounds_in_screen); } -void AccessibilityControllerImpl::UpdateFloatingPanelBoundsIfNeeded() { +void AccessibilityController::UpdateFloatingPanelBoundsIfNeeded() { Shell* shell = Shell::Get(); if (shell->accessibility_controller()->autoclick().enabled()) shell->autoclick_controller()->UpdateAutoclickMenuBoundsIfNeeded(); @@ -2359,17 +2356,17 @@ shell->sticky_keys_controller()->UpdateStickyKeysOverlayBoundsIfNeeded(); } -void AccessibilityControllerImpl::UpdateAutoclickMenuBoundsIfNeeded() { +void AccessibilityController::UpdateAutoclickMenuBoundsIfNeeded() { Shell::Get()->autoclick_controller()->UpdateAutoclickMenuBoundsIfNeeded(); } -void AccessibilityControllerImpl::HandleAutoclickScrollableBoundsFound( +void AccessibilityController::HandleAutoclickScrollableBoundsFound( const gfx::Rect& bounds_in_screen) { Shell::Get()->autoclick_controller()->HandleAutoclickScrollableBoundsFound( bounds_in_screen); } -void AccessibilityControllerImpl::SetFloatingMenuPosition( +void AccessibilityController::SetFloatingMenuPosition( FloatingMenuPosition position) { if (!active_user_prefs_) return; @@ -2378,18 +2375,18 @@ active_user_prefs_->CommitPendingWrite(); } -void AccessibilityControllerImpl::UpdateFloatingMenuPositionFromPref() { +void AccessibilityController::UpdateFloatingMenuPositionFromPref() { if (floating_menu_controller_) floating_menu_controller_->SetMenuPosition(GetFloatingMenuPosition()); } -FloatingMenuPosition AccessibilityControllerImpl::GetFloatingMenuPosition() { +FloatingMenuPosition AccessibilityController::GetFloatingMenuPosition() { DCHECK(active_user_prefs_); return static_cast<FloatingMenuPosition>(active_user_prefs_->GetInteger( prefs::kAccessibilityFloatingMenuPosition)); } -void AccessibilityControllerImpl::UpdateLargeCursorFromPref() { +void AccessibilityController::UpdateLargeCursorFromPref() { DCHECK(active_user_prefs_); const bool enabled = active_user_prefs_->GetBoolean(prefs::kAccessibilityLargeCursorEnabled); @@ -2414,7 +2411,7 @@ shell->UpdateCursorCompositingEnabled(); } -void AccessibilityControllerImpl::UpdateCursorColorFromPrefs() { +void AccessibilityController::UpdateCursorColorFromPrefs() { DCHECK(active_user_prefs_); const bool enabled = @@ -2427,14 +2424,14 @@ shell->UpdateCursorCompositingEnabled(); } -void AccessibilityControllerImpl::UpdateFaceGazeFromPrefs() { +void AccessibilityController::UpdateFaceGazeFromPrefs() { if (!::features::IsAccessibilityFaceGazeEnabled()) { return; } // TODO(b/309121742): Start getting camera data. } -void AccessibilityControllerImpl::UpdateColorCorrectionFromPrefs() { +void AccessibilityController::UpdateColorCorrectionFromPrefs() { DCHECK(active_user_prefs_); auto* color_enhancement_controller = @@ -2462,7 +2459,7 @@ true); } -void AccessibilityControllerImpl::UpdateAccessibilityHighlightingFromPrefs() { +void AccessibilityController::UpdateAccessibilityHighlightingFromPrefs() { if (!caret_highlight().enabled() && !cursor_highlight().enabled() && !focus_highlight().enabled()) { accessibility_highlight_controller_.reset(); @@ -2482,7 +2479,7 @@ focus_highlight().enabled()); } -void AccessibilityControllerImpl::MaybeCreateSelectToSpeakEventHandler() { +void AccessibilityController::MaybeCreateSelectToSpeakEventHandler() { // Construct the handler as needed when Select-to-Speak is enabled and the // delegate is set. Otherwise, destroy the handler when Select-to-Speak is // disabled or the delegate has been destroyed. @@ -2499,7 +2496,7 @@ select_to_speak_event_handler_delegate_); } -void AccessibilityControllerImpl::UpdateSwitchAccessKeyCodesFromPref( +void AccessibilityController::UpdateSwitchAccessKeyCodesFromPref( SwitchAccessCommand command) { if (!active_user_prefs_) return; @@ -2541,7 +2538,7 @@ command); } -void AccessibilityControllerImpl::UpdateSwitchAccessAutoScanEnabledFromPref() { +void AccessibilityController::UpdateSwitchAccessAutoScanEnabledFromPref() { DCHECK(active_user_prefs_); const bool enabled = active_user_prefs_->GetBoolean( prefs::kAccessibilitySwitchAccessAutoScanEnabled); @@ -2550,7 +2547,7 @@ SyncSwitchAccessPrefsToSignInProfile(); } -void AccessibilityControllerImpl::UpdateSwitchAccessAutoScanSpeedFromPref() { +void AccessibilityController::UpdateSwitchAccessAutoScanSpeedFromPref() { DCHECK(active_user_prefs_); const int speed_ms = active_user_prefs_->GetInteger( prefs::kAccessibilitySwitchAccessAutoScanSpeedMs); @@ -2561,7 +2558,7 @@ SyncSwitchAccessPrefsToSignInProfile(); } -void AccessibilityControllerImpl:: +void AccessibilityController:: UpdateSwitchAccessAutoScanKeyboardSpeedFromPref() { DCHECK(active_user_prefs_); const int speed_ms = active_user_prefs_->GetInteger( @@ -2573,7 +2570,7 @@ SyncSwitchAccessPrefsToSignInProfile(); } -void AccessibilityControllerImpl::UpdateSwitchAccessPointScanSpeedFromPref() { +void AccessibilityController::UpdateSwitchAccessPointScanSpeedFromPref() { // TODO(accessibility): Log histogram for point scan speed DCHECK(active_user_prefs_); const int point_scan_speed_dips_per_second = active_user_prefs_->GetInteger( @@ -2583,7 +2580,7 @@ SyncSwitchAccessPrefsToSignInProfile(); } -void AccessibilityControllerImpl::SwitchAccessDisableDialogClosed( +void AccessibilityController::SwitchAccessDisableDialogClosed( bool disable_dialog_accepted) { switch_access_disable_dialog_showing_ = false; // Always deactivate switch access. Turning switch access off ensures it is @@ -2603,13 +2600,13 @@ } } -void AccessibilityControllerImpl::UpdateKeyCodesAfterSwitchAccessEnabled() { +void AccessibilityController::UpdateKeyCodesAfterSwitchAccessEnabled() { UpdateSwitchAccessKeyCodesFromPref(SwitchAccessCommand::kSelect); UpdateSwitchAccessKeyCodesFromPref(SwitchAccessCommand::kNext); UpdateSwitchAccessKeyCodesFromPref(SwitchAccessCommand::kPrevious); } -void AccessibilityControllerImpl::ActivateSwitchAccess() { +void AccessibilityController::ActivateSwitchAccess() { switch_access_bubble_controller_ = std::make_unique<SwitchAccessMenuBubbleController>(); point_scan_controller_ = std::make_unique<PointScanController>(); @@ -2625,14 +2622,14 @@ std::vector<std::u16string>())); } -void AccessibilityControllerImpl::DeactivateSwitchAccess() { +void AccessibilityController::DeactivateSwitchAccess() { if (client_) client_->OnSwitchAccessDisabled(); point_scan_controller_.reset(); switch_access_bubble_controller_.reset(); } -void AccessibilityControllerImpl::SyncSwitchAccessPrefsToSignInProfile() { +void AccessibilityController::SyncSwitchAccessPrefsToSignInProfile() { if (!active_user_prefs_ || IsSigninPrefService(active_user_prefs_)) return; @@ -2654,7 +2651,7 @@ } } -void AccessibilityControllerImpl::UpdateShortcutsEnabledFromPref() { +void AccessibilityController::UpdateShortcutsEnabledFromPref() { DCHECK(active_user_prefs_); const bool enabled = active_user_prefs_->GetBoolean(prefs::kAccessibilityShortcutsEnabled); @@ -2667,8 +2664,7 @@ NotifyAccessibilityStatusChanged(); } -void AccessibilityControllerImpl:: - UpdateTabletModeShelfNavigationButtonsFromPref() { +void AccessibilityController::UpdateTabletModeShelfNavigationButtonsFromPref() { DCHECK(active_user_prefs_); const bool enabled = active_user_prefs_->GetBoolean( prefs::kAccessibilityTabletModeShelfNavigationButtonsEnabled); @@ -2681,31 +2677,31 @@ NotifyAccessibilityStatusChanged(); } -std::u16string AccessibilityControllerImpl::GetBatteryDescription() const { +std::u16string AccessibilityController::GetBatteryDescription() const { // Pass battery status as string to callback function. return PowerStatus::Get()->GetAccessibleNameString( /*full_description=*/true); } -void AccessibilityControllerImpl::SetVirtualKeyboardVisible(bool is_visible) { +void AccessibilityController::SetVirtualKeyboardVisible(bool is_visible) { if (is_visible) Shell::Get()->keyboard_controller()->ShowKeyboard(); else Shell::Get()->keyboard_controller()->HideKeyboard(HideReason::kUser); } -void AccessibilityControllerImpl::PerformAcceleratorAction( +void AccessibilityController::PerformAcceleratorAction( AcceleratorAction accelerator_action) { AcceleratorController::Get()->PerformActionIfEnabled(accelerator_action, /* accelerator = */ {}); } -void AccessibilityControllerImpl::NotifyAccessibilityStatusChanged() { +void AccessibilityController::NotifyAccessibilityStatusChanged() { for (auto& observer : observers_) observer.OnAccessibilityStatusChanged(); } -bool AccessibilityControllerImpl::IsAccessibilityFeatureVisibleInTrayMenu( +bool AccessibilityController::IsAccessibilityFeatureVisibleInTrayMenu( const std::string& path) { if (!active_user_prefs_) return true; @@ -2716,16 +2712,16 @@ return true; } -void AccessibilityControllerImpl::SuspendSwitchAccessKeyHandling(bool suspend) { +void AccessibilityController::SuspendSwitchAccessKeyHandling(bool suspend) { accessibility_event_rewriter_->set_suspend_switch_access_key_handling( suspend); } -void AccessibilityControllerImpl::EnableChromeVoxVolumeSlideGesture() { +void AccessibilityController::EnableChromeVoxVolumeSlideGesture() { enable_chromevox_volume_slide_gesture_ = true; } -void AccessibilityControllerImpl::ShowConfirmationDialog( +void AccessibilityController::ShowConfirmationDialog( const std::u16string& title, const std::u16string& description, const std::u16string& cancel_name, @@ -2751,7 +2747,7 @@ } } -void AccessibilityControllerImpl:: +void AccessibilityController:: UpdateDictationButtonOnSpeechRecognitionDownloadChanged( int download_progress) { dictation_soda_download_progress_ = download_progress; @@ -2762,7 +2758,7 @@ ->UpdateOnSpeechRecognitionDownloadChanged(download_progress); } -void AccessibilityControllerImpl::ShowNotificationForDictation( +void AccessibilityController::ShowNotificationForDictation( DictationNotificationType type, const std::u16string& display_language) { A11yNotificationType notification_type; @@ -2785,18 +2781,18 @@ notification_type, std::vector<std::u16string>{display_language})); } -AccessibilityControllerImpl::A11yNotificationWrapper:: - A11yNotificationWrapper() = default; -AccessibilityControllerImpl::A11yNotificationWrapper::A11yNotificationWrapper( +AccessibilityController::A11yNotificationWrapper::A11yNotificationWrapper() = + default; +AccessibilityController::A11yNotificationWrapper::A11yNotificationWrapper( A11yNotificationType type_in, std::vector<std::u16string> replacements_in) : type(type_in), replacements(replacements_in) {} -AccessibilityControllerImpl::A11yNotificationWrapper:: - ~A11yNotificationWrapper() = default; -AccessibilityControllerImpl::A11yNotificationWrapper::A11yNotificationWrapper( +AccessibilityController::A11yNotificationWrapper::~A11yNotificationWrapper() = + default; +AccessibilityController::A11yNotificationWrapper::A11yNotificationWrapper( const A11yNotificationWrapper&) = default; -void AccessibilityControllerImpl::UpdateFeatureFromPref(FeatureType feature) { +void AccessibilityController::UpdateFeatureFromPref(FeatureType feature) { size_t feature_index = static_cast<size_t>(feature); bool enabled = features_[feature_index]->enabled(); bool is_managed = active_user_prefs_->IsManagedPreference( @@ -2887,10 +2883,10 @@ new AccessibilityFeatureDisableDialog( IDS_ASH_SWITCH_ACCESS_DISABLE_CONFIRMATION_TEXT, base::BindOnce( - &AccessibilityControllerImpl::SwitchAccessDisableDialogClosed, + &AccessibilityController::SwitchAccessDisableDialogClosed, weak_ptr_factory_.GetWeakPtr(), true), base::BindOnce( - &AccessibilityControllerImpl::SwitchAccessDisableDialogClosed, + &AccessibilityController::SwitchAccessDisableDialogClosed, weak_ptr_factory_.GetWeakPtr(), false)); switch_access_disable_dialog_showing_ = true; } @@ -2930,7 +2926,7 @@ NotifyAccessibilityStatusChanged(); } -void AccessibilityControllerImpl::UpdateDictationBubble( +void AccessibilityController::UpdateDictationBubble( bool visible, DictationBubbleIconType icon, const std::optional<std::u16string>& text, @@ -2942,7 +2938,7 @@ } DictationBubbleController* -AccessibilityControllerImpl::GetDictationBubbleControllerForTest() { +AccessibilityController::GetDictationBubbleControllerForTest() { if (!dictation_bubble_controller_) { dictation_bubble_controller_ = std::make_unique<DictationBubbleController>(); @@ -2951,17 +2947,17 @@ return dictation_bubble_controller_.get(); } -void AccessibilityControllerImpl::ShowToast(AccessibilityToastType type) { +void AccessibilityController::ShowToast(AccessibilityToastType type) { accessibility_notification_controller_->ShowToast(type); } -void AccessibilityControllerImpl::AddShowToastCallbackForTesting( +void AccessibilityController::AddShowToastCallbackForTesting( base::RepeatingCallback<void(AccessibilityToastType)> callback) { accessibility_notification_controller_->AddShowToastCallbackForTesting( std::move(callback)); } -void AccessibilityControllerImpl::AddShowConfirmationDialogCallbackForTesting( +void AccessibilityController::AddShowConfirmationDialogCallbackForTesting( base::RepeatingCallback<void()> callback) { show_confirmation_dialog_callback_for_testing_ = std::move(callback); }
diff --git a/ash/accessibility/accessibility_controller_impl.h b/ash/accessibility/accessibility_controller_impl.h index 56d9910..9ec7d30 100644 --- a/ash/accessibility/accessibility_controller_impl.h +++ b/ash/accessibility/accessibility_controller_impl.h
@@ -6,12 +6,13 @@ #define ASH_ACCESSIBILITY_ACCESSIBILITY_CONTROLLER_IMPL_H_ #include <memory> +#include <optional> #include "ash/accessibility/a11y_feature_type.h" #include "ash/accessibility/accessibility_notification_controller.h" #include "ash/ash_export.h" #include "ash/constants/ash_constants.h" -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/public/cpp/accelerator_actions.h" #include "ash/public/cpp/session/session_observer.h" #include "base/functional/callback_forward.h" #include "base/memory/raw_ptr.h" @@ -19,6 +20,7 @@ #include "base/observer_list.h" #include "base/time/time.h" #include "ui/display/display_observer.h" +#include "ui/gfx/geometry/rect.h" class PrefChangeRegistrar; class PrefRegistrySimple; @@ -47,18 +49,26 @@ namespace ash { class AccessibilityConfirmationDialog; +class AccessibilityControllerClient; class AccessibilityEventRewriter; class AccessibilityHighlightController; class AccessibilityObserver; +enum class AccessibilityPanelState; +enum class DictationToggleSource; class DictationBubbleController; +enum class DictationBubbleHintType; +enum class DictationBubbleIconType; +enum class DictationNotificationType; class DictationNudgeController; class FloatingAccessibilityController; class PointScanController; class ScopedBacklightsForcedOff; class SelectToSpeakEventHandler; +class SelectToSpeakEventHandlerDelegate; class SelectToSpeakMenuBubbleController; -class SwitchAccessMenuBubbleController; +enum class SelectToSpeakState; enum class Sound; +class SwitchAccessMenuBubbleController; enum AccessibilityNotificationVisibility { A11Y_NOTIFICATION_NONE, @@ -92,9 +102,8 @@ // The controller for accessibility features in ash. Features can be enabled // in chrome's webui settings or the system tray menu (see TrayAccessibility). // Uses preferences to communicate with chrome to support mash. -class ASH_EXPORT AccessibilityControllerImpl : public AccessibilityController, - public SessionObserver, - public display::DisplayObserver { +class ASH_EXPORT AccessibilityController : public SessionObserver, + public display::DisplayObserver { public: // Common interface for all features. class Feature { @@ -104,7 +113,7 @@ const gfx::VectorIcon* icon, const int name_resource_id, const bool toggleable_in_quicksettings, - AccessibilityControllerImpl* controller); + AccessibilityController* controller); Feature(const Feature&) = delete; Feature& operator=(Feature const&) = delete; virtual ~Feature(); @@ -153,7 +162,7 @@ // available in the quicksettings menu. const bool toggleable_in_quicksettings_; - const raw_ptr<AccessibilityControllerImpl, ExperimentalAsh> owner_; + const raw_ptr<AccessibilityController, ExperimentalAsh> owner_; }; // Helper struct to store information about a11y dialog -- pref name, resource @@ -178,7 +187,7 @@ const int name_resource_id, const bool toggleable_in_quicksettings, const Dialog& dialog, - AccessibilityControllerImpl* controller); + AccessibilityController* controller); ~FeatureWithDialog() override; // Tries to set the feature enabled, if its dialog is mandatory, shows the @@ -207,13 +216,14 @@ std::vector<std::u16string> replacements; }; - AccessibilityControllerImpl(); + static AccessibilityController* Get(); - AccessibilityControllerImpl(const AccessibilityControllerImpl&) = delete; - AccessibilityControllerImpl& operator=(const AccessibilityControllerImpl&) = - delete; + AccessibilityController(); - ~AccessibilityControllerImpl() override; + AccessibilityController(const AccessibilityController&) = delete; + AccessibilityController& operator=(const AccessibilityController&) = delete; + + ~AccessibilityController() override; // See Shell::RegisterProfilePrefs(). static void RegisterProfilePrefs(PrefRegistrySimple* registry); @@ -229,7 +239,7 @@ // enabled. std::vector<Feature*> GetEnabledFeaturesInQuickSettings() const; - base::WeakPtr<AccessibilityControllerImpl> GetWeakPtr(); + base::WeakPtr<AccessibilityController> GetWeakPtr(); // Getters for the corresponding features. Feature& autoclick() const; @@ -350,7 +360,8 @@ return tablet_mode_shelf_navigation_buttons_enabled_; } - void ShowFloatingMenuIfEnabled() override; + // Shows floating accessibility menu if it was enabled by policy. + void ShowFloatingMenuIfEnabled(); bool dictation_active() const { return dictation_active_; } @@ -415,64 +426,155 @@ // set the a11y override window back to null. void SetA11yOverrideWindow(aura::Window* a11y_override_window); - // AccessibilityController: - void SetClient(AccessibilityControllerClient* client) override; - void SetDarkenScreen(bool darken) override; - void BrailleDisplayStateChanged(bool connected) override; - void SetFocusHighlightRect(const gfx::Rect& bounds_in_screen) override; - void SetCaretBounds(const gfx::Rect& bounds_in_screen) override; - void SetAccessibilityPanelAlwaysVisible(bool always_visible) override; + // Sets the client interface. + void SetClient(AccessibilityControllerClient* client); + + // Starts or stops darkening the screen (e.g. to allow chrome a11y extensions + // to darken the screen). + void SetDarkenScreen(bool darken); + + // Called when braille display state is changed. + void BrailleDisplayStateChanged(bool connected); + + // Sets the focus highlight rect using |bounds_in_screen|. Called when focus + // changed in page and a11y focus highlight feature is enabled. + void SetFocusHighlightRect(const gfx::Rect& bounds_in_screen); + + // Sets the text input caret bounds used to draw the caret highlight effect. + // For effciency, only sent when the caret highlight feature is enabled. + // Setting off-screen or empty bounds suppresses the highlight. + void SetCaretBounds(const gfx::Rect& bounds_in_screen); + + // Sets whether the accessibility panel should always be visible, regardless + // of whether the window is fullscreen. + void SetAccessibilityPanelAlwaysVisible(bool always_visible); + + // Sets the bounds for the accessibility panel. Overrides current + // configuration (i.e. fullscreen, full-width). void SetAccessibilityPanelBounds(const gfx::Rect& bounds, - AccessibilityPanelState state) override; - void SetSelectToSpeakState(SelectToSpeakState state) override; + AccessibilityPanelState state); + + // Sets the current Select-to-Speak state. This should be used by the Select- + // to-Speak extension to inform ash of its updated state. + void SetSelectToSpeakState(SelectToSpeakState state); + + // Set the delegate used by the Select-to-Speak event handler. void SetSelectToSpeakEventHandlerDelegate( - SelectToSpeakEventHandlerDelegate* delegate) override; + SelectToSpeakEventHandlerDelegate* delegate); + + // Displays the Select-to-Speak panel. void ShowSelectToSpeakPanel(const gfx::Rect& anchor, bool is_paused, - double speech_rate) override; - void HideSelectToSpeakPanel() override; + double speech_rate); + + // Hides the Select-to-Speak panel. + void HideSelectToSpeakPanel(); + + // Dispatches event to notify Select-to-speak that a panel action occurred, + // with an optional value. void OnSelectToSpeakPanelAction(SelectToSpeakPanelAction action, - double value) override; - void HideSwitchAccessBackButton() override; - void HideSwitchAccessMenu() override; - void ShowSwitchAccessBackButton(const gfx::Rect& anchor) override; + double value); + + // Hides the Switch Access back button. + void HideSwitchAccessBackButton(); + + // Hides the Switch Access menu. + void HideSwitchAccessMenu(); + + // Show the Switch Access back button next to the specified rectangle. + void ShowSwitchAccessBackButton(const gfx::Rect& anchor); + + // Show the Switch Access menu with the specified actions. void ShowSwitchAccessMenu(const gfx::Rect& anchor, - std::vector<std::string> actions_to_show) override; - void StartPointScan() override; - void StopPointScan() override; - void SetPointScanSpeedDipsPerSecond( - int point_scan_speed_dips_per_second) override; - void SetDictationActive(bool is_active) override; - void ToggleDictationFromSource(DictationToggleSource source) override; - void EnableOrToggleDictationFromSource(DictationToggleSource source) override; + std::vector<std::string> actions_to_show); + + // Starts point scanning in Switch Access. + void StartPointScan(); + + // Stops point scanning in Switch Access. + void StopPointScan(); + + // Sets point scanning speed in Switch Access. + void SetPointScanSpeedDipsPerSecond(int point_scan_speed_dips_per_second); + + // Set whether dictation is active. + void SetDictationActive(bool is_active); + + // Starts or stops dictation. Records metrics for toggling via SwitchAccess. + void ToggleDictationFromSource(DictationToggleSource source); + + // Enables Dictation if the feature is currently disabled. Toggles (starts or + // stops) Dictation if the feature is currently enabled. Note: this behavior + // is currently behind a feature flag - if the feature flag is off, then this + // method behaves like ToggleDictationFromSource. + void EnableOrToggleDictationFromSource(DictationToggleSource source); + + // Shows a nudge explaining that a user's dictation language was upgraded to + // work offline. void ShowDictationLanguageUpgradedNudge( const std::string& dictation_locale, - const std::string& application_locale) override; - void HandleAutoclickScrollableBoundsFound( - const gfx::Rect& bounds_in_screen) override; - std::u16string GetBatteryDescription() const override; - void SetVirtualKeyboardVisible(bool is_visible) override; - void PerformAcceleratorAction(AcceleratorAction accelerator_action) override; - void NotifyAccessibilityStatusChanged() override; - bool IsAccessibilityFeatureVisibleInTrayMenu( - const std::string& path) override; - void DisablePolicyRecommendationRestorerForTesting() override; - void SuspendSwitchAccessKeyHandling(bool suspend) override; - void EnableChromeVoxVolumeSlideGesture() override; + const std::string& application_locale); + + // Called when the Automatic Clicks extension finds scrollable bounds. + void HandleAutoclickScrollableBoundsFound(const gfx::Rect& bounds_in_screen); + + // Retrieves a string description of the current battery status. + std::u16string GetBatteryDescription() const; + + // Shows or hides the virtual keyboard. + void SetVirtualKeyboardVisible(bool is_visible); + + // Performs the given accelerator action. + void PerformAcceleratorAction(AcceleratorAction accelerator_action); + + // Notify observers that the accessibility status has changed. This is part of + // the public interface because a11y features like screen magnifier are + // managed outside of this accessibility controller. + void NotifyAccessibilityStatusChanged(); + + // Returns true if the |path| pref is being controlled by a policy which + // enforces turning it on or its not being controlled by any type of policy + // and false otherwise. + bool IsAccessibilityFeatureVisibleInTrayMenu(const std::string& path); + + // Disables restoring of recommended policy values. + void DisablePolicyRecommendationRestorerForTesting(); + + // Suspends (or resumes) key handling for Switch Access. + void SuspendSwitchAccessKeyHandling(bool suspend); + + // Enables ChromeVox's volume slide gesture. + void EnableChromeVoxVolumeSlideGesture(); + + // Updates the enabled state, tooltip, and progress ring of the dictation + // button in the status tray when speech recognition file download state + // changes. `download_progress` indicates SODA download progress and is + // guaranteed to be between 0 and 100 (inclusive). void UpdateDictationButtonOnSpeechRecognitionDownloadChanged( - int download_progress) override; - void ShowNotificationForDictation( - DictationNotificationType type, - const std::u16string& display_language) override; + int download_progress); + + // Shows a notification card in the message center informing the user that + // speech recognition files have either downloaded successfully or failed. + // Specific to the Dictation feature. + void ShowNotificationForDictation(DictationNotificationType type, + const std::u16string& display_language); + // Updates the Dictation UI bubble. `text` is optional to allow clients to + // clear the bubble's text. void UpdateDictationBubble( bool visible, DictationBubbleIconType icon, const std::optional<std::u16string>& text, - const std::optional<std::vector<DictationBubbleHintType>>& hints) - override; - void SilenceSpokenFeedback() override; - void ShowToast(AccessibilityToastType type) override; + const std::optional<std::vector<DictationBubbleHintType>>& hints); + // Cancels all of spoken feedback's current and queued speech immediately. + void SilenceSpokenFeedback(); + + // Shows an accessibility-related toast. + void ShowToast(AccessibilityToastType type); + + // Shows a confirmation dialog with the given text, description, + // and cancel button name, and calls the relevant callback when the + // dialog is confirmed, canceled or closed. // A confirmation dialog will be shown the first time an accessibility feature // is enabled using the specified accelerator key sequence. Only one dialog // will be shown at a time, and will not be shown again if the user has @@ -490,7 +592,7 @@ const std::u16string& cancel_name, base::OnceClosure on_accept_callback, base::OnceClosure on_cancel_callback, - base::OnceClosure on_close_callback) override; + base::OnceClosure on_close_callback); // SessionObserver: void OnSigninScreenPrefServiceInitialized(PrefService* prefs) override; @@ -502,8 +604,13 @@ SwitchAccessMenuBubbleController* GetSwitchAccessBubbleControllerForTest() { return switch_access_bubble_controller_.get(); } - void DisableSwitchAccessDisableConfirmationDialogTesting() override; - void DisableSwitchAccessEnableNotificationTesting() override; + + // Disables the dialog shown when Switch Access is turned off. + // Used in tests. + void DisableSwitchAccessDisableConfirmationDialogTesting(); + // Disables the dialog shown when Switch Access is turned off. + // Used in tests. + void DisableSwitchAccessEnableNotificationTesting(); SelectToSpeakMenuBubbleController* GetSelectToSpeakMenuBubbleControllerForTest() { return select_to_speak_bubble_controller_.get(); @@ -677,7 +784,7 @@ base::RepeatingCallback<void()> show_confirmation_dialog_callback_for_testing_; - base::WeakPtrFactory<AccessibilityControllerImpl> weak_ptr_factory_{this}; + base::WeakPtrFactory<AccessibilityController> weak_ptr_factory_{this}; }; } // namespace ash
diff --git a/ash/accessibility/accessibility_controller_test_api_impl.cc b/ash/accessibility/accessibility_controller_test_api_impl.cc index ef495c7..f8acb69 100644 --- a/ash/accessibility/accessibility_controller_test_api_impl.cc +++ b/ash/accessibility/accessibility_controller_test_api_impl.cc
@@ -13,7 +13,7 @@ namespace { -AccessibilityControllerImpl* GetController() { +AccessibilityController* GetController() { return Shell::Get()->accessibility_controller(); }
diff --git a/ash/accessibility/accessibility_controller_unittest.cc b/ash/accessibility/accessibility_controller_unittest.cc index a5e01bd..481d4228 100644 --- a/ash/accessibility/accessibility_controller_unittest.cc +++ b/ash/accessibility/accessibility_controller_unittest.cc
@@ -194,7 +194,7 @@ } TEST_F(AccessibilityControllerTest, SetAutoclickEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->autoclick().enabled()); @@ -214,7 +214,7 @@ } TEST_F(AccessibilityControllerTest, SetCaretHighlightEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->caret_highlight().enabled()); @@ -234,7 +234,7 @@ } TEST_F(AccessibilityControllerTest, SetColorCorrectionEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->color_correction().enabled()); @@ -270,7 +270,7 @@ } TEST_F(AccessibilityControllerTest, SetCursorHighlightEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->cursor_highlight().enabled()); @@ -290,7 +290,7 @@ } TEST_F(AccessibilityControllerTest, SetFaceGazeEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->face_gaze().enabled()); @@ -314,7 +314,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. @@ -350,7 +350,7 @@ } TEST_F(AccessibilityControllerTest, SetFocusHighlightEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->focus_highlight().enabled()); @@ -370,7 +370,7 @@ } TEST_F(AccessibilityControllerTest, SetHighContrastEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->high_contrast().enabled()); @@ -390,7 +390,7 @@ } TEST_F(AccessibilityControllerTest, SetLargeCursorEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->large_cursor().enabled()); @@ -414,7 +414,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->large_cursor().SetEnabled(true); @@ -450,7 +450,7 @@ } TEST_F(AccessibilityControllerTest, SetLiveCaptionEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->live_caption().enabled()); @@ -474,7 +474,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->live_caption().SetEnabled(true); @@ -508,7 +508,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->high_contrast().SetEnabled(true); @@ -547,7 +547,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->mono_audio().SetEnabled(true); @@ -586,10 +586,10 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Required to set the dialog to be true to change the value of the pref from - // the |AccessibilityControllerImpl|. + // the |AccessibilityController|. prefs->SetBoolean(prefs::kDictationAcceleratorDialogHasBeenAccepted, true); // Check when the value is true and not being controlled by any policy. controller->dictation().SetEnabled(true); @@ -628,7 +628,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->cursor_highlight().SetEnabled(true); @@ -667,7 +667,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->fullscreen_magnifier().SetEnabled(true); @@ -706,7 +706,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->docked_magnifier().SetEnabled(true); @@ -738,7 +738,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->caret_highlight().SetEnabled(true); @@ -777,7 +777,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->select_to_speak().SetEnabled(true); @@ -816,7 +816,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->autoclick().SetEnabled(true); @@ -855,7 +855,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->SetSpokenFeedbackEnabled(true, A11Y_NOTIFICATION_NONE); @@ -894,7 +894,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->virtual_keyboard().SetEnabled(true); @@ -933,7 +933,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->switch_access().SetEnabled(true); @@ -972,7 +972,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->color_correction().SetEnabled(true); @@ -1012,7 +1012,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->focus_highlight().SetEnabled(true); @@ -1051,7 +1051,7 @@ // visible in the accessibility tray menu despite its value. PrefService* prefs = Shell::Get()->session_controller()->GetLastActiveUserPrefService(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Check when the value is true and not being controlled by any policy. controller->sticky_keys().SetEnabled(true); @@ -1132,7 +1132,7 @@ } TEST_F(AccessibilityControllerTest, SetMonoAudioEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->mono_audio().enabled()); @@ -1152,7 +1152,7 @@ } TEST_F(AccessibilityControllerTest, SetSpokenFeedbackEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->spoken_feedback().enabled()); @@ -1172,7 +1172,7 @@ } TEST_F(AccessibilityControllerTest, FeaturesConflictingWithChromeVox) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->spoken_feedback().enabled()); EXPECT_FALSE(controller->sticky_keys().enabled()); @@ -1211,7 +1211,7 @@ } TEST_F(AccessibilityControllerTest, SetStickyKeysEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->sticky_keys().enabled()); @@ -1235,7 +1235,7 @@ } TEST_F(AccessibilityControllerTest, SetVirtualKeyboardEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->virtual_keyboard().enabled()); @@ -1278,7 +1278,7 @@ ASSERT_FALSE( chromeos::FakePowerManagerClient::Get()->backlights_forced_off()); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetDarkenScreen(true); EXPECT_TRUE(chromeos::FakePowerManagerClient::Get()->backlights_forced_off()); @@ -1292,7 +1292,7 @@ const std::u16string kChromeVoxEnabledTitle = u"ChromeVox enabled"; const std::u16string kChromeVoxEnabled = u"Press Ctrl + Alt + Z to disable spoken feedback."; - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Enabling spoken feedback should show the notification if specified to show @@ -1324,7 +1324,7 @@ u"Press Ctrl + Alt + Z to disable spoken feedback."; const std::u16string kBrailleConnectedAndChromeVoxEnabledTitle = u"Braille and ChromeVox are enabled"; - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSpokenFeedbackEnabled(true, A11Y_NOTIFICATION_SHOW); @@ -1360,7 +1360,7 @@ } TEST_F(AccessibilityControllerTest, SelectToSpeakStateChanges) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); TestAccessibilityObserver observer; controller->AddObserver(&observer); @@ -1387,7 +1387,7 @@ const std::u16string kSucceededDescription = u"Speech is processed locally and dictation works offline, but some " u"voice commands won’t work."; - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->ShowNotificationForDictation( @@ -1408,7 +1408,7 @@ const std::u16string kFailedDescription = u"Download will be attempted later. Speech will be sent to Google for " u"processing for now."; - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->ShowNotificationForDictation( @@ -1444,7 +1444,7 @@ // Verifies the behavior of EnableOrToggleDictation without the keyboard // improvements feature (current behavior). TEST_F(AccessibilityControllerTest, EnableOrToggleDictation) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); TestAccessibilityControllerClient client; controller->SetClient(&client); @@ -1514,7 +1514,7 @@ // improvements feature (new behavior). TEST_F(AccessibilityControllerDictationKeyboardImprovementsTest, EnableOrToggleDictation) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); TestAccessibilityControllerClient client; controller->SetClient(&client); @@ -1616,7 +1616,7 @@ TEST_P(AccessibilityControllerSigninTest, EnableOnLoginScreenAndLogin) { constexpr float kMagnifierScale = 4.3f; - AccessibilityControllerImpl* accessibility = + AccessibilityController* accessibility = Shell::Get()->accessibility_controller(); DockedMagnifierController* docked_magnifier = Shell::Get()->docked_magnifier_controller(); @@ -1710,7 +1710,7 @@ } TEST_P(AccessibilityControllerSigninTest, SwitchAccessPrefsSyncToSignIn) { - AccessibilityControllerImpl* accessibility = + AccessibilityController* accessibility = Shell::Get()->accessibility_controller(); SessionControllerImpl* session = Shell::Get()->session_controller();
diff --git a/ash/accessibility/autoclick/autoclick_unittest.cc b/ash/accessibility/autoclick/autoclick_unittest.cc index c51b221..a6c1d009 100644 --- a/ash/accessibility/autoclick/autoclick_unittest.cc +++ b/ash/accessibility/autoclick/autoclick_unittest.cc
@@ -814,7 +814,7 @@ } TEST_F(AutoclickTest, DoesActionOnBubbleWhenInDifferentModes) { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); // Enable autoclick from the accessibility controller so that the bubble is // constructed too.
diff --git a/ash/accessibility/chromevox/key_accessibility_enabler_unittest.cc b/ash/accessibility/chromevox/key_accessibility_enabler_unittest.cc index e964453..f3277714 100644 --- a/ash/accessibility/chromevox/key_accessibility_enabler_unittest.cc +++ b/ash/accessibility/chromevox/key_accessibility_enabler_unittest.cc
@@ -68,7 +68,7 @@ ui::KeyEvent vol_up_release(ui::ET_KEY_RELEASED, ui::VKEY_VOLUME_UP, ui::EF_NONE); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); ASSERT_FALSE(controller->spoken_feedback().enabled());
diff --git a/ash/accessibility/chromevox/spoken_feedback_enabler.cc b/ash/accessibility/chromevox/spoken_feedback_enabler.cc index 7786913..d28d450b 100644 --- a/ash/accessibility/chromevox/spoken_feedback_enabler.cc +++ b/ash/accessibility/chromevox/spoken_feedback_enabler.cc
@@ -35,7 +35,7 @@ base::TimeTicks now = ui::EventTimeForNow(); int tick_count = base::ClampRound((now - start_time_) / kTimerDelay); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); CHECK(controller); if (tick_count >= kTimerTicksOfFirstSoundFeedback &&
diff --git a/ash/accessibility/chromevox/touch_exploration_manager.cc b/ash/accessibility/chromevox/touch_exploration_manager.cc index a013696..8c65edb 100644 --- a/ash/accessibility/chromevox/touch_exploration_manager.cc +++ b/ash/accessibility/chromevox/touch_exploration_manager.cc
@@ -30,7 +30,7 @@ namespace { -AccessibilityControllerImpl* GetA11yController() { +AccessibilityController* GetA11yController() { return Shell::Get()->accessibility_controller(); } @@ -154,8 +154,9 @@ void TouchExplorationManager::OnTwoFingerTouchStop() { // Can be null during shutdown. - if (AccessibilityControllerImpl* controller = GetA11yController()) + if (AccessibilityController* controller = GetA11yController()) { controller->OnTwoFingerTouchStop(); + } } void TouchExplorationManager::PlaySpokenFeedbackToggleCountdown(
diff --git a/ash/accessibility/default_accessibility_delegate.cc b/ash/accessibility/default_accessibility_delegate.cc index 3ca53ac..bfcb51e 100644 --- a/ash/accessibility/default_accessibility_delegate.cc +++ b/ash/accessibility/default_accessibility_delegate.cc
@@ -24,7 +24,7 @@ } bool DefaultAccessibilityDelegate::ShouldShowAccessibilityMenu() const { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); return controller->spoken_feedback().enabled() || screen_magnifier_enabled_ || controller->autoclick().enabled() ||
diff --git a/ash/accessibility/test_accessibility_controller_client.cc b/ash/accessibility/test_accessibility_controller_client.cc index f4ae4e50..0612f13 100644 --- a/ash/accessibility/test_accessibility_controller_client.cc +++ b/ash/accessibility/test_accessibility_controller_client.cc
@@ -6,7 +6,7 @@ #include <utility> -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "base/time/time.h" #include "ui/gfx/geometry/point_f.h"
diff --git a/ash/accessibility/ui/accessibility_highlight_controller_unittest.cc b/ash/accessibility/ui/accessibility_highlight_controller_unittest.cc index 71bc3bd..be74242 100644 --- a/ash/accessibility/ui/accessibility_highlight_controller_unittest.cc +++ b/ash/accessibility/ui/accessibility_highlight_controller_unittest.cc
@@ -311,7 +311,7 @@ std::unique_ptr<views::Widget> window = CreateTestWidget(); window->SetBounds(gfx::Rect(5, 5, 300, 300)); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); accessibility_controller->caret_highlight().SetEnabled(true);
diff --git a/ash/app_list/views/assistant/assistant_page_view_unittest.cc b/ash/app_list/views/assistant/assistant_page_view_unittest.cc index 9440d61..1ab0acdb 100644 --- a/ash/app_list/views/assistant/assistant_page_view_unittest.cc +++ b/ash/app_list/views/assistant/assistant_page_view_unittest.cc
@@ -623,13 +623,12 @@ EXPECT_FALSE(page_view_layer->fills_bounds_opaquely()); EXPECT_EQ(page_view_layer->background_blur(), ColorProvider::kBackgroundBlurSigma); - EXPECT_EQ(page_view_layer->GetTargetColor(), - ColorProvider::Get()->GetBaseLayerColor( - ColorProvider::BaseLayerType::kTransparent80)); + EXPECT_EQ( + page_view_layer->GetTargetColor(), + page_view()->GetColorProvider()->GetColor(kColorAshShieldAndBase80)); } TEST_F(AssistantPageViewTest, BackgroundColorInDarkLightMode) { - auto* color_provider = AshColorProvider::Get(); auto* dark_light_mode_controller = DarkLightModeControllerImpl::Get(); dark_light_mode_controller->OnActiveUserPrefServiceChanged( Shell::Get()->session_controller()->GetActivePrefService()); @@ -641,18 +640,18 @@ const bool initial_dark_mode_status = dark_light_mode_controller->IsDarkModeEnabled(); - EXPECT_EQ(page_view()->layer()->GetTargetColor(), - color_provider->GetBaseLayerColor( - ColorProvider::BaseLayerType::kTransparent80)); + EXPECT_EQ( + page_view()->layer()->GetTargetColor(), + page_view()->GetColorProvider()->GetColor(kColorAshShieldAndBase80)); // Switch the color mode. dark_light_mode_controller->ToggleColorMode(); ASSERT_NE(initial_dark_mode_status, dark_light_mode_controller->IsDarkModeEnabled()); - EXPECT_EQ(page_view()->layer()->GetTargetColor(), - color_provider->GetBaseLayerColor( - ColorProvider::BaseLayerType::kTransparent80)); + EXPECT_EQ( + page_view()->layer()->GetTargetColor(), + page_view()->GetColorProvider()->GetColor(kColorAshShieldAndBase80)); } //------------------------------------------------------------------------------
diff --git a/ash/ash_prefs.cc b/ash/ash_prefs.cc index 3de5b2a2..0b73e57 100644 --- a/ash/ash_prefs.cc +++ b/ash/ash_prefs.cc
@@ -97,7 +97,7 @@ std::string_view country, bool for_test) { AcceleratorPrefs::RegisterProfilePrefs(registry); - AccessibilityControllerImpl::RegisterProfilePrefs(registry); + AccessibilityController::RegisterProfilePrefs(registry); AppListControllerImpl::RegisterProfilePrefs(registry); AppListNudgeController::RegisterProfilePrefs(registry); AshAcceleratorConfiguration::RegisterProfilePrefs(registry);
diff --git a/ash/capture_mode/capture_mode_camera_preview_view.h b/ash/capture_mode/capture_mode_camera_preview_view.h index bfaa93ab..a6b7ee0 100644 --- a/ash/capture_mode/capture_mode_camera_preview_view.h +++ b/ash/capture_mode/capture_mode_camera_preview_view.h
@@ -199,7 +199,7 @@ // True only while handling a gesture tap event on this view. bool has_been_tapped_ = false; - base::ScopedObservation<AccessibilityControllerImpl, AccessibilityObserver> + base::ScopedObservation<AccessibilityController, AccessibilityObserver> accessibility_observation_{this}; // Helps to update the current a11y override window. It will be the native
diff --git a/ash/capture_mode/capture_mode_camera_unittests.cc b/ash/capture_mode/capture_mode_camera_unittests.cc index 72bf65df..aa89f0f 100644 --- a/ash/capture_mode/capture_mode_camera_unittests.cc +++ b/ash/capture_mode/capture_mode_camera_unittests.cc
@@ -4024,7 +4024,7 @@ auto* event_generator = GetEventGenerator(); for (const bool switch_access_enabled : {false, true}) { - AccessibilityControllerImpl* a11y_controller = + AccessibilityController* a11y_controller = Shell::Get()->accessibility_controller(); a11y_controller->switch_access().SetEnabled(switch_access_enabled); EXPECT_EQ(switch_access_enabled, a11y_controller->IsSwitchAccessRunning()); @@ -4088,7 +4088,7 @@ auto* event_generator = GetEventGenerator(); for (const bool switch_access_enabled : {false, true}) { - AccessibilityControllerImpl* a11y_controller = + AccessibilityController* a11y_controller = Shell::Get()->accessibility_controller(); a11y_controller->switch_access().SetEnabled(switch_access_enabled); EXPECT_EQ(switch_access_enabled, a11y_controller->IsSwitchAccessRunning());
diff --git a/ash/capture_mode/capture_mode_util.cc b/ash/capture_mode/capture_mode_util.cc index 250ffb9d2..4d381a7 100644 --- a/ash/capture_mode/capture_mode_util.cc +++ b/ash/capture_mode/capture_mode_util.cc
@@ -238,7 +238,7 @@ base::SingleThreadTaskRunner::GetCurrentDefault()->PostTask( FROM_HERE, base::BindOnce( - &AccessibilityControllerImpl::TriggerAccessibilityAlertWithMessage, + &AccessibilityController::TriggerAccessibilityAlertWithMessage, Shell::Get()->accessibility_controller()->GetWeakPtr(), message)); }
diff --git a/ash/constants/ash_features.cc b/ash/constants/ash_features.cc index fbb2f894a..f059c33 100644 --- a/ash/constants/ash_features.cc +++ b/ash/constants/ash_features.cc
@@ -289,6 +289,9 @@ "CrosBatterySaverAlwaysOn", base::FEATURE_DISABLED_BY_DEFAULT); +// Controls enabling/disabling the birch feature. +BASE_FEATURE(kBirchFeature, "BirchFeature", base::FEATURE_DISABLED_BY_DEFAULT); + // Enables or disables the usage of fixed Bluetooth A2DP packet size to improve // audio performance in noisy environment. BASE_FEATURE(kBluetoothFixA2dpPacketSize, @@ -1762,13 +1765,6 @@ "MicMuteNotifications", base::FEATURE_ENABLED_BY_DEFAULT); -// Enable migration of the owner key from the public to the private slot. This -// experiment represents the second stage of `kStoreOwnerKeyInPrivateSlot` and -// is only respected if kStoreOwnerKeyInPrivateSlot is enabled. -BASE_FEATURE(kMigrateOwnerKeyToPrivateSlot, - "MigrateOwnerKeyToPrivateSlot", - base::FEATURE_DISABLED_BY_DEFAULT); - // Controls whether to enable the requirement of a minimum chrome version on the // device through the policy DeviceMinimumVersion. If the requirement is // not met and the warning time in the policy has expired, the user is @@ -2521,7 +2517,7 @@ // Shows live caption in the video conference tray. BASE_FEATURE(kShowLiveCaptionInVideoConferenceTray, "ShowLiveCaptionInVideoConferenceTray", - base::FEATURE_DISABLED_BY_DEFAULT); + base::FEATURE_ENABLED_BY_DEFAULT); // Shows the Play Store icon in Demo Mode. BASE_FEATURE(kShowPlayInDemoMode, @@ -2584,11 +2580,6 @@ // Controls whether the snap group feature is enabled or not. BASE_FEATURE(kSnapGroup, "SnapGroup", base::FEATURE_DISABLED_BY_DEFAULT); -// Enable storing a newly created owner key in the private slot. -BASE_FEATURE(kStoreOwnerKeyInPrivateSlot, - "StoreOwnerKeyInPrivateSlot", - base::FEATURE_ENABLED_BY_DEFAULT); - // Enables battery indicator for styluses in the palette tray BASE_FEATURE(kStylusBatteryStatus, "StylusBatteryStatus", @@ -3172,6 +3163,10 @@ return base::FeatureList::IsEnabled(kBatterySaverAlwaysOn); } +bool IsBirchFeatureEnabled() { + return base::FeatureList::IsEnabled(kBirchFeature); +} + bool IsBluetoothQualityReportEnabled() { return base::FeatureList::IsEnabled(kBluetoothQualityReport); } @@ -3608,10 +3603,6 @@ return base::FeatureList::IsEnabled(kStartAssistantAudioDecoderOnDemand); } -bool IsStoreOwnerKeyInPrivateSlotEnabled() { - return base::FeatureList::IsEnabled(kStoreOwnerKeyInPrivateSlot); -} - bool IsImeTrayHideVoiceButtonEnabled() { return base::FeatureList::IsEnabled(kImeTrayHideVoiceButton); } @@ -3767,11 +3758,6 @@ return base::FeatureList::IsEnabled(kMinimumChromeVersion); } -bool ShouldMigrateOwnerKeyToPrivateSlot() { - return base::FeatureList::IsEnabled(kStoreOwnerKeyInPrivateSlot) && - base::FeatureList::IsEnabled(kMigrateOwnerKeyToPrivateSlot); -} - bool IsMultiZoneRgbKeyboardEnabled() { return base::FeatureList::IsEnabled(kMultiZoneRgbKeyboard); }
diff --git a/ash/constants/ash_features.h b/ash/constants/ash_features.h index 8dd64001..53925f1 100644 --- a/ash/constants/ash_features.h +++ b/ash/constants/ash_features.h
@@ -82,6 +82,7 @@ COMPONENT_EXPORT(ASH_CONSTANTS) extern const base::FeatureParam<double> kBatterySaverActivationChargePercent; COMPONENT_EXPORT(ASH_CONSTANTS) BASE_DECLARE_FEATURE(kBatterySaverAlwaysOn); +COMPONENT_EXPORT(ASH_CONSTANTS) BASE_DECLARE_FEATURE(kBirchFeature); COMPONENT_EXPORT(ASH_CONSTANTS) BASE_DECLARE_FEATURE(kBluetoothFixA2dpPacketSize); COMPONENT_EXPORT(ASH_CONSTANTS) BASE_DECLARE_FEATURE(kBluetoothQualityReport); @@ -925,6 +926,7 @@ COMPONENT_EXPORT(ASH_CONSTANTS) bool IsBackgroundBlurEnabled(); COMPONENT_EXPORT(ASH_CONSTANTS) bool IsBatterySaverAvailable(); COMPONENT_EXPORT(ASH_CONSTANTS) bool IsBatterySaverAlwaysOn(); +COMPONENT_EXPORT(ASH_CONSTANTS) bool IsBirchFeatureEnabled(); COMPONENT_EXPORT(ASH_CONSTANTS) bool IsBluetoothQualityReportEnabled(); COMPONENT_EXPORT(ASH_CONSTANTS) bool IsCaptureModeAudioMixingEnabled(); COMPONENT_EXPORT(ASH_CONSTANTS) bool IsCaptureModeEducationEnabled();
diff --git a/ash/constants/ash_switches.cc b/ash/constants/ash_switches.cc index 5f6514ac..97026bb 100644 --- a/ash/constants/ash_switches.cc +++ b/ash/constants/ash_switches.cc
@@ -8,6 +8,7 @@ #include <string> #include "base/command_line.h" +#include "base/hash/sha1.h" #include "base/metrics/field_trial.h" #include "base/strings/string_number_conversions.h" #include "base/time/time.h" @@ -22,6 +23,11 @@ constexpr base::TimeDelta kAshContextualNudgesMinInterval = base::Seconds(0); constexpr base::TimeDelta kAshContextualNudgesMaxInterval = base::Seconds(60); +// The hash value for the secret key of the birch feature. +constexpr char kBirchHashKey[] = + "\x1a\x93\x5f\x64\x0d\x7f\x0c\x2f\x88\xe8\x80\x9a\x5f\x16\xbb\xd8\x74\x06" + "\x8a\xb1"; + } // namespace // Please keep the order of these switches synchronized with the header file @@ -295,6 +301,9 @@ // instead of displaying an interactive animation. const char kAuraLegacyPowerButton[] = "aura-legacy-power-button"; +// Supply secret key for the Birch feature. +const char kBirchFeatureKey[] = "birch-feature-key"; + // If this flag is set, it indicates that this device is a "Cellular First" // device. Cellular First devices use cellular telephone data networks as // their primary means of connecting to the internet. @@ -1305,5 +1314,21 @@ kAllowDefaultShelfPinLayoutIgnoringSync); } +bool IsBirchSecretKeyMatched() { + // Commandline looks like: + // out/Default/chrome --user-data-dir=/tmp/tmp123 + // --birch-feature-key="INSERT KEY HERE" --enable-features=BirchFeature + const std::string provided_key_hash = base::SHA1HashString( + base::CommandLine::ForCurrentProcess()->GetSwitchValueASCII( + switches::kBirchFeatureKey)); + + bool birch_key_matched = (provided_key_hash == kBirchHashKey); + if (!birch_key_matched) { + LOG(ERROR) << "Provided secret key does not match with the expected one."; + } + + return birch_key_matched; +} + } // namespace switches } // namespace ash
diff --git a/ash/constants/ash_switches.h b/ash/constants/ash_switches.h index d3c2a34..7c006bd 100644 --- a/ash/constants/ash_switches.h +++ b/ash/constants/ash_switches.h
@@ -95,6 +95,7 @@ COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kAshUiModeClamshell[]; COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kAshUiModeTablet[]; COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kAuraLegacyPowerButton[]; +COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kBirchFeatureKey[]; COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kCellularFirst[]; COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kChildWallpaperLarge[]; COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kChildWallpaperSmall[]; @@ -495,6 +496,9 @@ COMPONENT_EXPORT(ASH_CONSTANTS) bool ShouldAllowDefaultShelfPinLayoutIgnoringSync(); +COMPONENT_EXPORT(ASH_CONSTANTS) +bool IsBirchSecretKeyMatched(); + } // namespace ash::switches #endif // ASH_CONSTANTS_ASH_SWITCHES_H_
diff --git a/ash/events/accessibility_event_rewriter.cc b/ash/events/accessibility_event_rewriter.cc index 7752d21..6fd032ce 100644 --- a/ash/events/accessibility_event_rewriter.cc +++ b/ash/events/accessibility_event_rewriter.cc
@@ -212,7 +212,7 @@ } if (key_event->type() == ui::ET_KEY_PRESSED) { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); if (accessibility_controller->IsPointScanEnabled()) { @@ -301,7 +301,7 @@ void AccessibilityEventRewriter::MaybeSendMouseEvent(const ui::Event& event) { // Mouse moves are the only pertinent event for accessibility component // extensions. - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); if (send_mouse_events_ && (event.type() == ui::ET_MOUSE_MOVED ||
diff --git a/ash/events/accessibility_event_rewriter_unittest.cc b/ash/events/accessibility_event_rewriter_unittest.cc index 5743cf9..07a9aaff 100644 --- a/ash/events/accessibility_event_rewriter_unittest.cc +++ b/ash/events/accessibility_event_rewriter_unittest.cc
@@ -247,7 +247,7 @@ // The delegate should not intercept events when spoken feedback is disabled. TEST_F(ChromeVoxAccessibilityEventRewriterTest, EventsNotConsumedWhenDisabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->spoken_feedback().enabled()); @@ -269,7 +269,7 @@ // The delegate should intercept key events when spoken feedback is enabled. TEST_F(ChromeVoxAccessibilityEventRewriterTest, KeyEventsConsumedWhenEnabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSpokenFeedbackEnabled(true, A11Y_NOTIFICATION_NONE); EXPECT_TRUE(controller->spoken_feedback().enabled()); @@ -316,7 +316,7 @@ TEST_F(ChromeVoxAccessibilityEventRewriterTest, KeysNotEatenWithChromeVoxDisabled) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->spoken_feedback().enabled()); @@ -347,7 +347,7 @@ } TEST_F(ChromeVoxAccessibilityEventRewriterTest, KeyEventsCaptured) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSpokenFeedbackEnabled(true, A11Y_NOTIFICATION_NONE); EXPECT_TRUE(controller->spoken_feedback().enabled()); @@ -392,7 +392,7 @@ TEST_F(ChromeVoxAccessibilityEventRewriterTest, KeyEventsCapturedWithModifierRemapping) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSpokenFeedbackEnabled(true, A11Y_NOTIFICATION_NONE); EXPECT_TRUE(controller->spoken_feedback().enabled()); @@ -450,7 +450,7 @@ TEST_F(ChromeVoxAccessibilityEventRewriterTest, PositionalInputMethodKeysMightBeRewritten) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSpokenFeedbackEnabled(true, A11Y_NOTIFICATION_NONE); EXPECT_TRUE(controller->spoken_feedback().enabled()); @@ -677,7 +677,7 @@ protected: raw_ptr<ui::test::EventGenerator, ExperimentalAsh> generator_ = nullptr; EventCapturer event_capturer_; - raw_ptr<AccessibilityControllerImpl, ExperimentalAsh> controller_ = nullptr; + raw_ptr<AccessibilityController, ExperimentalAsh> controller_ = nullptr; std::unique_ptr<SwitchAccessTestDelegate> delegate_; input_method::FakeImeKeyboard fake_ime_keyboard_; std::unique_ptr<AccessibilityEventRewriter> accessibility_event_rewriter_; @@ -999,7 +999,7 @@ protected: raw_ptr<ui::test::EventGenerator, ExperimentalAsh> generator_ = nullptr; EventCapturer event_capturer_; - raw_ptr<AccessibilityControllerImpl, ExperimentalAsh> controller_ = nullptr; + raw_ptr<AccessibilityController, ExperimentalAsh> controller_ = nullptr; std::unique_ptr<MagnifierTestDelegate> delegate_; input_method::FakeImeKeyboard fake_ime_keyboard_; std::unique_ptr<AccessibilityEventRewriter> accessibility_event_rewriter_;
diff --git a/ash/events/select_to_speak_event_handler_unittest.cc b/ash/events/select_to_speak_event_handler_unittest.cc index 1d38700..5aebee5 100644 --- a/ash/events/select_to_speak_event_handler_unittest.cc +++ b/ash/events/select_to_speak_event_handler_unittest.cc
@@ -145,7 +145,7 @@ protected: raw_ptr<ui::test::EventGenerator, ExperimentalAsh> generator_ = nullptr; EventCapturer event_capturer_; - raw_ptr<AccessibilityControllerImpl, ExperimentalAsh> controller_ = nullptr; + raw_ptr<AccessibilityController, ExperimentalAsh> controller_ = nullptr; std::unique_ptr<TestDelegate> delegate_; };
diff --git a/ash/keyboard/virtual_keyboard_controller_unittest.cc b/ash/keyboard/virtual_keyboard_controller_unittest.cc index 5115f45..f715ee4 100644 --- a/ash/keyboard/virtual_keyboard_controller_unittest.cc +++ b/ash/keyboard/virtual_keyboard_controller_unittest.cc
@@ -92,7 +92,7 @@ TEST_F(VirtualKeyboardControllerTest, ForceToShowKeyboardWithKeysetWhenAccessibilityKeyboardIsEnabled) { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); accessibility_controller->virtual_keyboard().SetEnabled(true); ASSERT_TRUE(accessibility_controller->virtual_keyboard().enabled());
diff --git a/ash/login/ui/local_authentication_request_view.cc b/ash/login/ui/local_authentication_request_view.cc index 73dda64..3702727 100644 --- a/ash/login/ui/local_authentication_request_view.cc +++ b/ash/login/ui/local_authentication_request_view.cc
@@ -9,7 +9,6 @@ #include "ash/login/ui/arrow_button_view.h" #include "ash/login/ui/local_authentication_request_widget.h" #include "ash/login/ui/non_accessible_view.h" -#include "ash/public/cpp/accessibility_controller.h" #include "ash/public/cpp/login/local_authentication_request_controller.h" #include "ash/public/cpp/login/login_utils.h" #include "ash/public/cpp/session/user_info.h"
diff --git a/ash/login/ui/pin_request_view_unittest.cc b/ash/login/ui/pin_request_view_unittest.cc index 7fe7045..901a363 100644 --- a/ash/login/ui/pin_request_view_unittest.cc +++ b/ash/login/ui/pin_request_view_unittest.cc
@@ -689,7 +689,7 @@ TEST_F(PinRequestWidgetTest, SpokenFeedbackKeyCombo) { ShowWidget(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); EXPECT_FALSE(controller->spoken_feedback().enabled());
diff --git a/ash/public/cpp/BUILD.gn b/ash/public/cpp/BUILD.gn index fcf87d4..0d05cca 100644 --- a/ash/public/cpp/BUILD.gn +++ b/ash/public/cpp/BUILD.gn
@@ -18,8 +18,6 @@ "accelerators.h", "accelerators_util.cc", "accelerators_util.h", - "accessibility_controller.cc", - "accessibility_controller.h", "accessibility_controller_client.h", "accessibility_controller_enums.h", "accessibility_event_rewriter_delegate.h",
diff --git a/ash/public/cpp/accessibility_controller.cc b/ash/public/cpp/accessibility_controller.cc deleted file mode 100644 index 07f16cf8..0000000 --- a/ash/public/cpp/accessibility_controller.cc +++ /dev/null
@@ -1,29 +0,0 @@ -// Copyright 2019 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ash/public/cpp/accessibility_controller.h" - -#include "base/check_op.h" - -namespace ash { - -namespace { -AccessibilityController* g_instance = nullptr; -} - -AccessibilityController* AccessibilityController::Get() { - return g_instance; -} - -AccessibilityController::AccessibilityController() { - DCHECK_EQ(nullptr, g_instance); - g_instance = this; -} - -AccessibilityController::~AccessibilityController() { - DCHECK_EQ(this, g_instance); - g_instance = nullptr; -} - -} // namespace ash
diff --git a/ash/public/cpp/accessibility_controller.h b/ash/public/cpp/accessibility_controller.h deleted file mode 100644 index 4ef2cb9..0000000 --- a/ash/public/cpp/accessibility_controller.h +++ /dev/null
@@ -1,223 +0,0 @@ -// Copyright 2019 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef ASH_PUBLIC_CPP_ACCESSIBILITY_CONTROLLER_H_ -#define ASH_PUBLIC_CPP_ACCESSIBILITY_CONTROLLER_H_ - -#include <optional> -#include <string> -#include <vector> - -#include "ash/public/cpp/accelerators.h" -#include "ash/public/cpp/accessibility_controller_enums.h" -#include "ash/public/cpp/ash_public_export.h" -#include "base/functional/callback.h" - -namespace gfx { -class Rect; -} // namespace gfx - -namespace ash { - -class AccessibilityControllerClient; -enum class AccessibilityPanelState; -enum class DictationToggleSource; -enum class DictationBubbleHintType; -enum class DictationBubbleIconType; -enum class DictationNotificationType; -class SelectToSpeakEventHandlerDelegate; -enum class SelectToSpeakState; - -// Interface for ash client (e.g. Chrome) to control and query accessibility -// features. -class ASH_PUBLIC_EXPORT AccessibilityController { - public: - static AccessibilityController* Get(); - - AccessibilityController(const AccessibilityController&) = delete; - AccessibilityController& operator=(const AccessibilityController&) = delete; - - // Sets the client interface. - virtual void SetClient(AccessibilityControllerClient* client) = 0; - - // Starts or stops darkening the screen (e.g. to allow chrome a11y extensions - // to darken the screen). - virtual void SetDarkenScreen(bool darken) = 0; - - // Called when braille display state is changed. - virtual void BrailleDisplayStateChanged(bool connected) = 0; - - // Sets the focus highlight rect using |bounds_in_screen|. Called when focus - // changed in page and a11y focus highlight feature is enabled. - virtual void SetFocusHighlightRect(const gfx::Rect& bounds_in_screen) = 0; - - // Sets the text input caret bounds used to draw the caret highlight effect. - // For effciency, only sent when the caret highlight feature is enabled. - // Setting off-screen or empty bounds suppresses the highlight. - virtual void SetCaretBounds(const gfx::Rect& bounds_in_screen) = 0; - - // Sets whether the accessibility panel should always be visible, regardless - // of whether the window is fullscreen. - virtual void SetAccessibilityPanelAlwaysVisible(bool always_visible) = 0; - - // Sets the bounds for the accessibility panel. Overrides current - // configuration (i.e. fullscreen, full-width). - virtual void SetAccessibilityPanelBounds(const gfx::Rect& bounds, - AccessibilityPanelState state) = 0; - - // Sets the current Select-to-Speak state. This should be used by the Select- - // to-Speak extension to inform ash of its updated state. - virtual void SetSelectToSpeakState(SelectToSpeakState state) = 0; - - // Set the delegate used by the Select-to-Speak event handler. - virtual void SetSelectToSpeakEventHandlerDelegate( - SelectToSpeakEventHandlerDelegate* delegate) = 0; - - // Displays the Select-to-Speak panel. - virtual void ShowSelectToSpeakPanel(const gfx::Rect& anchor, - bool is_paused, - double speech_rate) = 0; - - // Hides the Select-to-Speak panel. - virtual void HideSelectToSpeakPanel() = 0; - - // Dispatches event to notify Select-to-speak that a panel action occurred, - // with an optional value. - virtual void OnSelectToSpeakPanelAction(SelectToSpeakPanelAction action, - double value) = 0; - - // Hides the Switch Access back button. - virtual void HideSwitchAccessBackButton() = 0; - - // Hides the Switch Access menu. - virtual void HideSwitchAccessMenu() = 0; - - // Show the Switch Access back button next to the specified rectangle. - virtual void ShowSwitchAccessBackButton(const gfx::Rect& bounds) = 0; - - // Show the Switch Access menu with the specified actions. - virtual void ShowSwitchAccessMenu( - const gfx::Rect& bounds, - std::vector<std::string> actions_to_show) = 0; - - // Starts point scanning in Switch Access. - virtual void StartPointScan() = 0; - - // Stops point scanning in Switch Access. - virtual void StopPointScan() = 0; - - // Sets point scanning speed in Switch Access. - virtual void SetPointScanSpeedDipsPerSecond( - int point_scan_speed_dips_per_second) = 0; - - // Set whether dictation is active. - virtual void SetDictationActive(bool is_active) = 0; - - // Starts or stops dictation. Records metrics for toggling via SwitchAccess. - virtual void ToggleDictationFromSource(DictationToggleSource source) = 0; - - // Enables Dictation if the feature is currently disabled. Toggles (starts or - // stops) Dictation if the feature is currently enabled. Note: this behavior - // is currently behind a feature flag - if the feature flag is off, then this - // method behaves like ToggleDictationFromSource. - virtual void EnableOrToggleDictationFromSource( - DictationToggleSource source) = 0; - - // Shows a nudge explaining that a user's dictation language was upgraded to - // work offline. - virtual void ShowDictationLanguageUpgradedNudge( - const std::string& dictation_locale, - const std::string& application_locale) = 0; - - // Called when the Automatic Clicks extension finds scrollable bounds. - virtual void HandleAutoclickScrollableBoundsFound( - const gfx::Rect& bounds_in_screen) = 0; - - // Retrieves a string description of the current battery status. - virtual std::u16string GetBatteryDescription() const = 0; - - // Shows or hides the virtual keyboard. - virtual void SetVirtualKeyboardVisible(bool is_visible) = 0; - - // Performs the given accelerator action. - virtual void PerformAcceleratorAction( - AcceleratorAction accelerator_action) = 0; - - // Notify observers that the accessibility status has changed. This is part of - // the public interface because a11y features like screen magnifier are - // managed outside of this accessibility controller. - virtual void NotifyAccessibilityStatusChanged() = 0; - - // Returns true if the |path| pref is being controlled by a policy which - // enforces turning it on or its not being controlled by any type of policy - // and false otherwise. - virtual bool IsAccessibilityFeatureVisibleInTrayMenu( - const std::string& path) = 0; - - // Disables restoring of recommended policy values. - virtual void DisablePolicyRecommendationRestorerForTesting() {} - - // Disables the dialog shown when Switch Access is turned off. - // Used in tests. - virtual void DisableSwitchAccessDisableConfirmationDialogTesting() = 0; - - // Disables the dialog shown when Switch Access is turned on. - // Used in tests. - virtual void DisableSwitchAccessEnableNotificationTesting() = 0; - - // Shows floating accessibility menu if it was enabled by policy. - virtual void ShowFloatingMenuIfEnabled() {} - - // Suspends (or resumes) key handling for Switch Access. - virtual void SuspendSwitchAccessKeyHandling(bool suspend) {} - - // Enables ChromeVox's volume slide gesture. - virtual void EnableChromeVoxVolumeSlideGesture() {} - - // Shows a confirmation dialog with the given text, description, - // and cancel button name, and calls the relevant callback when the - // dialog is confirmed, canceled or closed. - virtual void ShowConfirmationDialog(const std::u16string& title, - const std::u16string& description, - const std::u16string& cancel_name, - base::OnceClosure on_accept_callback, - base::OnceClosure on_cancel_callback, - base::OnceClosure on_close_callback) {} - - // Updates the enabled state, tooltip, and progress ring of the dictation - // button in the status tray when speech recognition file download state - // changes. `download_progress` indicates SODA download progress and is - // guaranteed to be between 0 and 100 (inclusive). - virtual void UpdateDictationButtonOnSpeechRecognitionDownloadChanged( - int download_progress) = 0; - - // Shows a notification card in the message center informing the user that - // speech recognition files have either downloaded successfully or failed. - // Specific to the Dictation feature. - virtual void ShowNotificationForDictation( - DictationNotificationType type, - const std::u16string& display_language) = 0; - - // Updates the Dictation UI bubble. `text` is optional to allow clients to - // clear the bubble's text. - virtual void UpdateDictationBubble( - bool visible, - DictationBubbleIconType icon, - const std::optional<std::u16string>& text, - const std::optional<std::vector<DictationBubbleHintType>>& hints) = 0; - - // Cancels all of spoken feedback's current and queued speech immediately. - virtual void SilenceSpokenFeedback() = 0; - - // Shows an accessibility-related toast. - virtual void ShowToast(AccessibilityToastType type) = 0; - - protected: - AccessibilityController(); - virtual ~AccessibilityController(); -}; - -} // namespace ash - -#endif // ASH_PUBLIC_CPP_ACCESSIBILITY_CONTROLLER_H_
diff --git a/ash/public/cpp/external_arc/message_center/arc_notification_view.cc b/ash/public/cpp/external_arc/message_center/arc_notification_view.cc index 2dfe0ac..1b710f1 100644 --- a/ash/public/cpp/external_arc/message_center/arc_notification_view.cc +++ b/ash/public/cpp/external_arc/message_center/arc_notification_view.cc
@@ -9,7 +9,7 @@ #include "ash/public/cpp/external_arc/message_center/arc_notification_content_view.h" #include "ash/public/cpp/external_arc/message_center/arc_notification_item.h" #include "ash/public/cpp/message_center/arc_notification_constants.h" -#include "ash/style/ash_color_provider.h" +#include "ash/public/cpp/style/color_provider.h" #include "ash/system/message_center/message_center_constants.h" #include "base/time/time.h" #include "chromeos/constants/chromeos_features.h" @@ -71,12 +71,6 @@ AddChildView(content_view_.get()); - if (content_view_->background()) { - background()->SetNativeControlColor( - AshColorProvider::Get()->GetBaseLayerColor( - AshColorProvider::BaseLayerType::kTransparent80)); - } - if (shown_in_popup) { layer()->SetBackgroundBlur(ColorProvider::kBackgroundBlurSigma); layer()->SetBackdropFilterQuality(ColorProvider::kBackgroundBlurQuality); @@ -147,20 +141,11 @@ return; } - const auto* ash_color_provider = AshColorProvider::Get(); const auto* color_provider = GetColorProvider(); - const SkColor color_in_popup = - chromeos::features::IsJellyEnabled() - ? color_provider->GetColor(cros_tokens::kCrosSysSystemBaseElevated) - : ash_color_provider->GetBaseLayerColor( - AshColorProvider::BaseLayerType::kTransparent80); + color_provider->GetColor(cros_tokens::kCrosSysSystemBaseElevated); const SkColor color_in_message_center = - chromeos::features::IsJellyEnabled() - ? color_provider->GetColor(cros_tokens::kCrosSysSystemOnBase) - : ash_color_provider->GetControlsLayerColor( - AshColorProvider::ControlsLayerType:: - kControlBackgroundColorInactive); + color_provider->GetColor(cros_tokens::kCrosSysSystemOnBase); SetBackground(views::CreateBackgroundFromPainter( std::make_unique<message_center::NotificationBackgroundPainter>( top_radius(), bottom_radius(), @@ -313,6 +298,15 @@ return false; } +void ArcNotificationView::OnThemeChanged() { + message_center::MessageView::OnThemeChanged(); + + if (content_view_->background()) { + background()->SetNativeControlColor( + GetColorProvider()->GetColor(cros_tokens::kCrosSysSystemBaseElevated)); + } +} + void ArcNotificationView::OnItemDestroying() { DCHECK(item_); item_->RemoveObserver(this);
diff --git a/ash/public/cpp/external_arc/message_center/arc_notification_view.h b/ash/public/cpp/external_arc/message_center/arc_notification_view.h index 19a09755..872f94e 100644 --- a/ash/public/cpp/external_arc/message_center/arc_notification_view.h +++ b/ash/public/cpp/external_arc/message_center/arc_notification_view.h
@@ -77,6 +77,7 @@ bool OnKeyPressed(const ui::KeyEvent& event) override; void ChildPreferredSizeChanged(View* child) override; bool HandleAccessibleAction(const ui::AXActionData& action) override; + void OnThemeChanged() override; // ArcNotificationItem::Observer void OnItemDestroying() override;
diff --git a/ash/public/cpp/style/color_provider.h b/ash/public/cpp/style/color_provider.h index 3092732..4ee0847 100644 --- a/ash/public/cpp/style/color_provider.h +++ b/ash/public/cpp/style/color_provider.h
@@ -14,17 +14,6 @@ // An interface implemented by Ash that provides colors for the system UI. class ASH_PUBLIC_EXPORT ColorProvider { public: - // Types of Shield layer. Number at the end of each type indicates the alpha - // value. - enum class ShieldLayerType { - kShield20 = 0, - kShield40, - kShield60, - kShield80, - kShield90, - kShield95, - }; - // Blur sigma for system UI layers. static constexpr float kBackgroundBlurSigma = 30.f; @@ -32,21 +21,6 @@ // improves performance. static constexpr float kBackgroundBlurQuality = 0.33f; - // Types of Base layer. - enum class BaseLayerType { - // Number at the end of each transparent type indicates the alpha value. - kTransparent20 = 0, - kTransparent40, - kTransparent60, - kTransparent80, - kInvertedTransparent80, - kTransparent90, - kTransparent95, - - // Base layer is opaque. - kOpaque, - }; - // Types of Controls layer. enum class ControlsLayerType { kHairlineBorderColor, @@ -146,7 +120,6 @@ // Gets the color of |type| of the corresponding layer based on the current // color mode. - virtual SkColor GetBaseLayerColor(BaseLayerType type) const = 0; virtual SkColor GetControlsLayerColor(ControlsLayerType type) const = 0; virtual SkColor GetContentLayerColor(ContentLayerType type) const = 0;
diff --git a/ash/shelf/shelf_config.cc b/ash/shelf/shelf_config.cc index adc994d..e6112ab 100644 --- a/ash/shelf/shelf_config.cc +++ b/ash/shelf/shelf_config.cc
@@ -73,7 +73,7 @@ private: base::RepeatingClosure accessibility_state_changed_callback_; - base::ScopedObservation<AccessibilityControllerImpl, AccessibilityObserver> + base::ScopedObservation<AccessibilityController, AccessibilityObserver> observation_{this}; };
diff --git a/ash/shell.cc b/ash/shell.cc index ff434aa0..33c3c2a3 100644 --- a/ash/shell.cc +++ b/ash/shell.cc
@@ -1249,7 +1249,7 @@ accessibility_focus_ring_controller_ = std::make_unique<AccessibilityFocusRingControllerImpl>(); accessibility_delegate_.reset(shell_delegate_->CreateAccessibilityDelegate()); - accessibility_controller_ = std::make_unique<AccessibilityControllerImpl>(); + accessibility_controller_ = std::make_unique<AccessibilityController>(); toast_manager_ = std::make_unique<ToastManagerImpl>(); anchored_nudge_manager_ = std::make_unique<AnchoredNudgeManagerImpl>(); system_nudge_pause_manager_ = std::make_unique<SystemNudgePauseManagerImpl>();
diff --git a/ash/shell.h b/ash/shell.h index 1174167e..dc4b81df 100644 --- a/ash/shell.h +++ b/ash/shell.h
@@ -96,7 +96,7 @@ class AcceleratorKeycodeLookupCache; class AcceleratorPrefs; class AcceleratorTracker; -class AccessibilityControllerImpl; +class AccessibilityController; class AccessibilityDelegate; class AccessibilityEventHandlerManager; class AccessibilityFocusRingControllerImpl; @@ -407,7 +407,7 @@ AcceleratorTracker* accelerator_tracker() { return accelerator_tracker_.get(); } - AccessibilityControllerImpl* accessibility_controller() { + AccessibilityController* accessibility_controller() { return accessibility_controller_.get(); } AccessibilityDelegate* accessibility_delegate() { @@ -971,7 +971,7 @@ std::unique_ptr<AcceleratorControllerImpl> accelerator_controller_; std::unique_ptr<AcceleratorKeycodeLookupCache> accelerator_keycode_lookup_cache_; - std::unique_ptr<AccessibilityControllerImpl> accessibility_controller_; + std::unique_ptr<AccessibilityController> accessibility_controller_; std::unique_ptr<AccessibilityDelegate> accessibility_delegate_; std::unique_ptr<AccessibilityFocusRingControllerImpl> accessibility_focus_ring_controller_;
diff --git a/ash/style/ash_color_provider.cc b/ash/style/ash_color_provider.cc index 07db324..9b06cc2 100644 --- a/ash/style/ash_color_provider.cc +++ b/ash/style/ash_color_provider.cc
@@ -45,31 +45,6 @@ return g_instance; } -SkColor AshColorProvider::GetBaseLayerColor(BaseLayerType type) const { - // TODO(crbug.com/1350510): Delete this function after all clients migrate. - auto* color_provider = GetColorProvider(); - DCHECK(color_provider); - - switch (type) { - case BaseLayerType::kTransparent20: - return color_provider->GetColor(kColorAshShieldAndBase20); - case BaseLayerType::kTransparent40: - return color_provider->GetColor(kColorAshShieldAndBase40); - case BaseLayerType::kTransparent60: - return color_provider->GetColor(kColorAshShieldAndBase60); - case BaseLayerType::kTransparent80: - return color_provider->GetColor(kColorAshShieldAndBase80); - case BaseLayerType::kInvertedTransparent80: - return color_provider->GetColor(kColorAshInvertedShieldAndBase80); - case BaseLayerType::kTransparent90: - return color_provider->GetColor(kColorAshShieldAndBase90); - case BaseLayerType::kTransparent95: - return color_provider->GetColor(kColorAshShieldAndBase95); - case BaseLayerType::kOpaque: - return color_provider->GetColor(kColorAshShieldAndBaseOpaque); - } -} - SkColor AshColorProvider::GetControlsLayerColor(ControlsLayerType type) const { // TODO(crbug.com/1292244): Delete this function after all callers migrate. auto* color_provider = GetColorProvider();
diff --git a/ash/style/ash_color_provider.h b/ash/style/ash_color_provider.h index 168496a..f46531c 100644 --- a/ash/style/ash_color_provider.h +++ b/ash/style/ash_color_provider.h
@@ -38,7 +38,6 @@ static AshColorProvider* Get(); // ColorProvider: - SkColor GetBaseLayerColor(BaseLayerType type) const override; SkColor GetControlsLayerColor(ControlsLayerType type) const override; SkColor GetContentLayerColor(ContentLayerType type) const override; std::pair<SkColor, float> GetInkDropBaseColorAndOpacity(
diff --git a/ash/style/ash_color_provider_unittest.cc b/ash/style/ash_color_provider_unittest.cc index 2bc6faf0..71f1addf 100644 --- a/ash/style/ash_color_provider_unittest.cc +++ b/ash/style/ash_color_provider_unittest.cc
@@ -83,61 +83,6 @@ color_provider_; }; -using AshColorProviderBaseLayerTest = - AshColorProviderBase<ColorProvider::BaseLayerType>; - -TEST_P(AshColorProviderBaseLayerTest, TestBaseColors) { - const auto& test_case = GetParam(); - bool dark = test_case.color_mode == ColorMode::kDark; - DarkLightModeController::Get()->SetDarkModeEnabledForTest(dark); - EXPECT_EQ(test_case.expected_color, - color_provider_->GetBaseLayerColor(test_case.type)) - << "Colors do not match. Expected " << test_case << " Actual: " - << ColorToString(color_provider_->GetBaseLayerColor(test_case.type)); -} - -INSTANTIATE_TEST_SUITE_P( - AshColorProviderTests, - AshColorProviderBaseLayerTest, - testing::ValuesIn<ColorsTestCase<ColorProvider::BaseLayerType>>( - {// Light mode values - {ColorMode::kLight, ColorProvider::BaseLayerType::kTransparent20, - SkColorSetARGB(0x33, 0xF8, 0xF8, 0xF8)}, - {ColorMode::kLight, ColorProvider::BaseLayerType::kTransparent40, - SkColorSetARGB(0x66, 0xF8, 0xF8, 0xF8)}, - {ColorMode::kLight, ColorProvider::BaseLayerType::kTransparent60, - SkColorSetARGB(0x99, 0xF8, 0xF8, 0xF8)}, - {ColorMode::kLight, ColorProvider::BaseLayerType::kTransparent80, - SkColorSetARGB(0xCC, 0xF8, 0xF8, 0xF8)}, - {ColorMode::kLight, - ColorProvider::BaseLayerType::kInvertedTransparent80, - SkColorSetARGB(0xCC, 0x07, 0x07, 0x07)}, - {ColorMode::kLight, ColorProvider::BaseLayerType::kTransparent90, - SkColorSetARGB(0xE5, 0xF8, 0xF8, 0xF8)}, - {ColorMode::kLight, ColorProvider::BaseLayerType::kTransparent95, - SkColorSetARGB(0xF2, 0xF8, 0xF8, 0xF8)}, - {ColorMode::kLight, ColorProvider::BaseLayerType::kOpaque, - SkColorSetARGB(0xFF, 0xF8, 0xF8, 0xF8)}, - - // Dark mode values - {ColorMode::kDark, ColorProvider::BaseLayerType::kTransparent20, - SkColorSetARGB(0x33, 0x5A, 0x5A, 0x5A)}, - {ColorMode::kDark, ColorProvider::BaseLayerType::kTransparent40, - SkColorSetARGB(0x66, 0x5A, 0x5A, 0x5A)}, - {ColorMode::kDark, ColorProvider::BaseLayerType::kTransparent60, - SkColorSetARGB(0x99, 0x5A, 0x5A, 0x5A)}, - {ColorMode::kDark, ColorProvider::BaseLayerType::kTransparent80, - SkColorSetARGB(0xCC, 0x5A, 0x5A, 0x5A)}, - {ColorMode::kDark, - ColorProvider::BaseLayerType::kInvertedTransparent80, - SkColorSetARGB(0xCC, 0xA5, 0xA5, 0xA5)}, - {ColorMode::kDark, ColorProvider::BaseLayerType::kTransparent90, - SkColorSetARGB(0xE5, 0x5A, 0x5A, 0x5A)}, - {ColorMode::kDark, ColorProvider::BaseLayerType::kTransparent95, - SkColorSetARGB(0xF2, 0x5A, 0x5A, 0x5A)}, - {ColorMode::kDark, ColorProvider::BaseLayerType::kOpaque, - SkColorSetARGB(0xFF, 0x5A, 0x5A, 0x5A)}})); - using AshColorProviderControlsLayerTest = AshColorProviderBase<ColorProvider::ControlsLayerType>;
diff --git a/ash/system/accessibility/accessibility_detailed_view.cc b/ash/system/accessibility/accessibility_detailed_view.cc index 30d47ac..8e54745a 100644 --- a/ash/system/accessibility/accessibility_detailed_view.cc +++ b/ash/system/accessibility/accessibility_detailed_view.cc
@@ -67,7 +67,7 @@ } bool IsSodaFeatureEnabled(SodaFeature feature) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); switch (feature) { case SodaFeature::kDictation: @@ -155,7 +155,7 @@ void AccessibilityDetailedView::OnAccessibilityStatusChanged() { AccessibilityDelegate* delegate = Shell::Get()->accessibility_delegate(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); if (controller->IsSpokenFeedbackSettingVisibleInTray()) { @@ -277,7 +277,7 @@ } void AccessibilityDetailedView::AddEnabledFeatures(views::View* container) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); if (controller->IsSpokenFeedbackSettingVisibleInTray() && @@ -356,7 +356,7 @@ } void AccessibilityDetailedView::AddAllFeatures(views::View* container) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); if (controller->IsSpokenFeedbackSettingVisibleInTray()) { @@ -676,7 +676,7 @@ void AccessibilityDetailedView::HandleViewClicked(views::View* view) { AccessibilityDelegate* delegate = Shell::Get()->accessibility_delegate(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); using base::RecordAction; using base::UserMetricsAction; @@ -905,7 +905,7 @@ } bool AccessibilityDetailedView::IsSodaFeatureInTray(SodaFeature feature) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); switch (feature) { case SodaFeature::kDictation:
diff --git a/ash/system/accessibility/accessibility_detailed_view_unittest.cc b/ash/system/accessibility/accessibility_detailed_view_unittest.cc index fd1a06d..805b8d5d 100644 --- a/ash/system/accessibility/accessibility_detailed_view_unittest.cc +++ b/ash/system/accessibility/accessibility_detailed_view_unittest.cc
@@ -476,7 +476,7 @@ return detailed_menu_->GetClassName(); } - AccessibilityControllerImpl* controller() { return controller_; } + AccessibilityController* controller() { return controller_; } AccessibilityDetailedView* detailed_menu() { return detailed_menu_; } views::View* scroll_content() { return detailed_menu_->scroll_content(); } @@ -601,7 +601,7 @@ } } - raw_ptr<AccessibilityControllerImpl, ExperimentalAsh> controller_ = nullptr; + raw_ptr<AccessibilityController, ExperimentalAsh> controller_ = nullptr; std::unique_ptr<views::Widget> widget_; std::unique_ptr<DetailedViewDelegate> delegate_; raw_ptr<AccessibilityDetailedView, DanglingUntriaged | ExperimentalAsh> @@ -1039,7 +1039,7 @@ } TEST_F(AccessibilityDetailedViewTest, ClickDetailMenu) { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); // Confirms that the check item toggles the spoken feedback. EXPECT_FALSE(accessibility_controller->spoken_feedback().enabled());
diff --git a/ash/system/accessibility/accessibility_feature_pod_controller.cc b/ash/system/accessibility/accessibility_feature_pod_controller.cc index ab6f873..608a629 100644 --- a/ash/system/accessibility/accessibility_feature_pod_controller.cc +++ b/ash/system/accessibility/accessibility_feature_pod_controller.cc
@@ -31,7 +31,7 @@ namespace { std::u16string GenerateSublabelText( - std::vector<AccessibilityControllerImpl::Feature*> enabled_features, + std::vector<AccessibilityController::Feature*> enabled_features, int max_width, gfx::FontList font_list) { CHECK(!enabled_features.empty()); @@ -61,7 +61,7 @@ } std::u16string GenerateTooltipText( - std::vector<AccessibilityControllerImpl::Feature*> enabled_features) { + std::vector<AccessibilityController::Feature*> enabled_features) { if (enabled_features.empty()) { return l10n_util::GetStringUTF16(IDS_ASH_STATUS_TRAY_ACCESSIBILITY_TOOLTIP); }
diff --git a/ash/system/accessibility/accessibility_feature_pod_controller_unittest.cc b/ash/system/accessibility/accessibility_feature_pod_controller_unittest.cc index d2431d1c..ec1bf252 100644 --- a/ash/system/accessibility/accessibility_feature_pod_controller_unittest.cc +++ b/ash/system/accessibility/accessibility_feature_pod_controller_unittest.cc
@@ -50,7 +50,7 @@ tile_ = controller_->CreateTile(); } - AccessibilityControllerImpl* GetAccessibilityController() { + AccessibilityController* GetAccessibilityController() { return Shell::Get()->accessibility_controller(); }
diff --git a/ash/system/accessibility/autoclick_menu_bubble_controller_unittest.cc b/ash/system/accessibility/autoclick_menu_bubble_controller_unittest.cc index 734a19e..9c7de5b9 100644 --- a/ash/system/accessibility/autoclick_menu_bubble_controller_unittest.cc +++ b/ash/system/accessibility/autoclick_menu_bubble_controller_unittest.cc
@@ -117,7 +117,7 @@ } TEST_F(AutoclickMenuBubbleControllerTest, CanSelectAutoclickTypeFromBubble) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Set to a different event type than the first event in kTestCases. controller->SetAutoclickEventType(AutoclickEventType::kRightClick); @@ -152,7 +152,7 @@ } TEST_F(AutoclickMenuBubbleControllerTest, UnpausesWhenPauseAlreadySelected) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); views::View* pause_button = GetMenuButton(AutoclickMenuView::ButtonId::kPause); @@ -181,7 +181,7 @@ } TEST_F(AutoclickMenuBubbleControllerTest, CanChangePosition) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Set to a known position for than the first event in kTestCases. @@ -247,7 +247,7 @@ } TEST_F(AutoclickMenuBubbleControllerTest, ScrollBubbleShowsAndCloses) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetAutoclickEventType(AutoclickEventType::kLeftClick); // No scroll view yet. @@ -268,7 +268,7 @@ } TEST_F(AutoclickMenuBubbleControllerTest, ScrollBubbleDefaultPositioning) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetAutoclickEventType(AutoclickEventType::kScroll); @@ -314,7 +314,7 @@ TEST_F(AutoclickMenuBubbleControllerTest, ScrollBubbleManualPositioningLargeScrollBounds) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetAutoclickEventType(AutoclickEventType::kScroll); @@ -388,7 +388,7 @@ TEST_F(AutoclickMenuBubbleControllerTest, ScrollBubbleManualPositioningSmallScrollBounds) { UpdateDisplay("1200x1000"); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetAutoclickEventType(AutoclickEventType::kScroll);
diff --git a/ash/system/accessibility/dictation_button_tray_unittest.cc b/ash/system/accessibility/dictation_button_tray_unittest.cc index c70ec8f1..61eab445 100644 --- a/ash/system/accessibility/dictation_button_tray_unittest.cc +++ b/ash/system/accessibility/dictation_button_tray_unittest.cc
@@ -142,7 +142,7 @@ // Ensures that creation doesn't cause any crashes and adds the image icon. // Also checks that the tray is visible. TEST_F(DictationButtonTrayTest, BasicConstruction) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->dictation().SetEnabled(true); EXPECT_TRUE(GetImageView(GetTray())); @@ -151,7 +151,7 @@ // Test that clicking the button activates dictation. TEST_F(DictationButtonTrayTest, ButtonActivatesDictation) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); TestAccessibilityControllerClient client; controller->dictation().SetEnabled(true); @@ -166,7 +166,7 @@ // Test that activating dictation causes the button to activate. TEST_F(DictationButtonTrayTest, ActivatingDictationActivatesButton) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->dictation().SetEnabled(true); Shell::Get()->OnDictationStarted(); @@ -179,7 +179,7 @@ // Tests that the tray only renders as active while dictation is listening. Any // termination of dictation clears the active state. TEST_F(DictationButtonTrayTest, ActiveStateOnlyDuringDictation) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); TestAccessibilityControllerClient client; controller->dictation().SetEnabled(true); @@ -201,7 +201,7 @@ } TEST_F(DictationButtonTrayTest, ImageIcons) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); TestAccessibilityControllerClient client; controller->dictation().SetEnabled(true); @@ -236,7 +236,7 @@ TEST_F(DictationButtonTrayTest, DisabledWhenNoInputFocused) { DetachTextInputClient(); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->dictation().SetEnabled(true); DictationButtonTray* tray = GetTray(); @@ -318,7 +318,7 @@ // Tests the behavior of the UpdateOnSpeechRecognitionDownloadChanged() method. TEST_F(DictationButtonTraySodaTest, UpdateOnSpeechRecognitionDownloadChanged) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->dictation().SetEnabled(true); DictationButtonTray* tray = GetTray();
diff --git a/ash/system/accessibility/floating_accessibility_controller.cc b/ash/system/accessibility/floating_accessibility_controller.cc index 3e58ca9..1ac5b86 100644 --- a/ash/system/accessibility/floating_accessibility_controller.cc +++ b/ash/system/accessibility/floating_accessibility_controller.cc
@@ -54,7 +54,7 @@ } // namespace FloatingAccessibilityController::FloatingAccessibilityController( - AccessibilityControllerImpl* accessibility_controller) + AccessibilityController* accessibility_controller) : accessibility_controller_(accessibility_controller) { Shell::Get()->locale_update_controller()->AddObserver(this); accessibility_controller_->AddObserver(this);
diff --git a/ash/system/accessibility/floating_accessibility_controller.h b/ash/system/accessibility/floating_accessibility_controller.h index 0be2523..c98f072 100644 --- a/ash/system/accessibility/floating_accessibility_controller.h +++ b/ash/system/accessibility/floating_accessibility_controller.h
@@ -18,7 +18,7 @@ namespace ash { -class AccessibilityControllerImpl; +class AccessibilityController; class FloatingAccessibilityView; // Controls the floating accessibility menu. @@ -31,7 +31,7 @@ public display::DisplayObserver { public: explicit FloatingAccessibilityController( - AccessibilityControllerImpl* accessibility_controller); + AccessibilityController* accessibility_controller); FloatingAccessibilityController(const FloatingAccessibilityController&) = delete; FloatingAccessibilityController& operator=( @@ -88,7 +88,7 @@ display::ScopedDisplayObserver display_observer_{this}; - const raw_ptr<AccessibilityControllerImpl, ExperimentalAsh> + const raw_ptr<AccessibilityController, ExperimentalAsh> accessibility_controller_; // Owns us. };
diff --git a/ash/system/accessibility/floating_accessibility_controller_unittest.cc b/ash/system/accessibility/floating_accessibility_controller_unittest.cc index 19b0115..2b6c071 100644 --- a/ash/system/accessibility/floating_accessibility_controller_unittest.cc +++ b/ash/system/accessibility/floating_accessibility_controller_unittest.cc
@@ -45,7 +45,7 @@ SetTwoAvailableImes(); } - AccessibilityControllerImpl* accessibility_controller() { + AccessibilityController* accessibility_controller() { return Shell::Get()->accessibility_controller(); }
diff --git a/ash/system/accessibility/select_to_speak/select_to_speak_menu_bubble_controller_unittest.cc b/ash/system/accessibility/select_to_speak/select_to_speak_menu_bubble_controller_unittest.cc index 498e53f..931e3a62 100644 --- a/ash/system/accessibility/select_to_speak/select_to_speak_menu_bubble_controller_unittest.cc +++ b/ash/system/accessibility/select_to_speak/select_to_speak_menu_bubble_controller_unittest.cc
@@ -38,7 +38,7 @@ void TearDown() override { AshTestBase::TearDown(); } - AccessibilityControllerImpl* GetAccessibilitController() { + AccessibilityController* GetAccessibilitController() { return Shell::Get()->accessibility_controller(); }
diff --git a/ash/system/accessibility/select_to_speak/select_to_speak_speed_bubble_controller_unittest.cc b/ash/system/accessibility/select_to_speak/select_to_speak_speed_bubble_controller_unittest.cc index eb0bab81..096644a3 100644 --- a/ash/system/accessibility/select_to_speak/select_to_speak_speed_bubble_controller_unittest.cc +++ b/ash/system/accessibility/select_to_speak/select_to_speak_speed_bubble_controller_unittest.cc
@@ -45,7 +45,7 @@ AshTestBase::TearDown(); } - AccessibilityControllerImpl* GetAccessibilitController() { + AccessibilityController* GetAccessibilitController() { return Shell::Get()->accessibility_controller(); }
diff --git a/ash/system/accessibility/select_to_speak/select_to_speak_tray_unittest.cc b/ash/system/accessibility/select_to_speak/select_to_speak_tray_unittest.cc index 24fbe32..98c1aaa6 100644 --- a/ash/system/accessibility/select_to_speak/select_to_speak_tray_unittest.cc +++ b/ash/system/accessibility/select_to_speak/select_to_speak_tray_unittest.cc
@@ -121,7 +121,7 @@ // Test that changing the SelectToSpeakState in the AccessibilityController // results in a change of icon and activation in the tray. TEST_F(SelectToSpeakTrayTest, SelectToSpeakStateImpactsImageAndActivation) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSelectToSpeakState( SelectToSpeakState::kSelectToSpeakStateSelecting); @@ -161,7 +161,7 @@ feature_list.InitAndEnableFeature( ::features::kAccessibilitySelectToSpeakHoverTextImprovements); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSelectToSpeakState( SelectToSpeakState::kSelectToSpeakStateSelecting); @@ -194,7 +194,7 @@ feature_list.InitAndDisableFeature( ::features::kAccessibilitySelectToSpeakHoverTextImprovements); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->SetSelectToSpeakState( SelectToSpeakState::kSelectToSpeakStateSelecting);
diff --git a/ash/system/audio/audio_detailed_view.cc b/ash/system/audio/audio_detailed_view.cc index 300de2a..3cc4039 100644 --- a/ash/system/audio/audio_detailed_view.cc +++ b/ash/system/audio/audio_detailed_view.cc
@@ -254,7 +254,7 @@ } void AudioDetailedView::OnAccessibilityStatusChanged() { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // The live caption state has been updated. UpdateLiveCaptionView(controller->live_caption().enabled()); @@ -582,7 +582,7 @@ void AudioDetailedView::MaybeShowSodaMessage(speech::LanguageCode language_code, std::u16string message) { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); const bool is_live_caption_enabled = controller->live_caption().enabled(); // Only show updates for this feature if the language code applies to the SODA @@ -615,7 +615,7 @@ } void AudioDetailedView::ToggleLiveCaptionState() { - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); // Updates the enable state for live caption. controller->live_caption().SetEnabled(!controller->live_caption().enabled());
diff --git a/ash/system/audio/audio_effects_controller.cc b/ash/system/audio/audio_effects_controller.cc index af18b3d..881d034 100644 --- a/ash/system/audio/audio_effects_controller.cc +++ b/ash/system/audio/audio_effects_controller.cc
@@ -94,7 +94,7 @@ } case VcEffectId::kLiveCaption: { // Toggle live caption. - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->live_caption().SetEnabled( !controller->live_caption().enabled());
diff --git a/ash/system/audio/audio_effects_controller_unittest.cc b/ash/system/audio/audio_effects_controller_unittest.cc index cf657d07..0a59cc4 100644 --- a/ash/system/audio/audio_effects_controller_unittest.cc +++ b/ash/system/audio/audio_effects_controller_unittest.cc
@@ -518,7 +518,7 @@ SimulateUserLogin("testuser1@gmail.com"); // Explicitly disable live caption, confirm that it is disabled. - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->live_caption().SetEnabled(false); EXPECT_FALSE(controller->live_caption().enabled()); @@ -541,7 +541,7 @@ SimulateUserLogin("testuser1@gmail.com"); // Explicitly enable live caption, confirm that it is enabled. - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->live_caption().SetEnabled(true); EXPECT_TRUE(controller->live_caption().enabled()); @@ -564,7 +564,7 @@ SimulateUserLogin("testuser1@gmail.com"); // Explicitly enable live caption, confirm that it is enabled. - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->live_caption().SetEnabled(true); EXPECT_TRUE(controller->live_caption().enabled()); @@ -588,7 +588,7 @@ SimulateUserLogin("testuser1@gmail.com"); // Explicitly disable live caption, confirm that it is disabled. - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->live_caption().SetEnabled(false); EXPECT_FALSE(controller->live_caption().enabled());
diff --git a/ash/system/audio/unified_volume_view.cc b/ash/system/audio/unified_volume_view.cc index cf404c2..26de3e8 100644 --- a/ash/system/audio/unified_volume_view.cc +++ b/ash/system/audio/unified_volume_view.cc
@@ -47,7 +47,6 @@ &kQuickSettingsRightArrowIcon, IDS_ASH_STATUS_TRAY_AUDIO))), is_active_output_node_(is_active_output_node), - a11y_controller_(Shell::Get()->accessibility_controller()), device_id_(CrasAudioHandler::Get()->GetPrimaryActiveOutputNode()) { CrasAudioHandler::Get()->AddAudioObserver(this); @@ -62,8 +61,9 @@ more_button_->SetIconColor(cros_tokens::kCrosSysSecondary); // TODO(b/257151067): Update the a11y name id. // Adds the live caption button before `more_button_`. - a11y_controller_->AddObserver(this); - const bool enabled = a11y_controller_->live_caption().enabled(); + Shell::Get()->accessibility_controller()->AddObserver(this); + const bool enabled = + Shell::Get()->accessibility_controller()->live_caption().enabled(); live_caption_button_ = AddChildViewAt( std::make_unique<IconButton>( base::BindRepeating(&UnifiedVolumeView::OnLiveCaptionButtonPressed, @@ -112,7 +112,6 @@ Style::kRadioActive), more_button_(nullptr), is_active_output_node_(is_active_output_node), - a11y_controller_(Shell::Get()->accessibility_controller()), device_id_(device_id) { CrasAudioHandler::Get()->AddAudioObserver(this); @@ -131,7 +130,7 @@ UnifiedVolumeView::~UnifiedVolumeView() { CrasAudioHandler::Get()->RemoveAudioObserver(this); - a11y_controller_->RemoveObserver(this); + Shell::Get()->accessibility_controller()->RemoveObserver(this); } void UnifiedVolumeView::Update(bool by_user) { @@ -221,8 +220,8 @@ } void UnifiedVolumeView::OnLiveCaptionButtonPressed() { - a11y_controller_->live_caption().SetEnabled( - !a11y_controller_->live_caption().enabled()); + Shell::Get()->accessibility_controller()->live_caption().SetEnabled( + !Shell::Get()->accessibility_controller()->live_caption().enabled()); } void UnifiedVolumeView::OnOutputNodeVolumeChanged(uint64_t node_id, @@ -253,7 +252,8 @@ } void UnifiedVolumeView::OnAccessibilityStatusChanged() { - const bool enabled = a11y_controller_->live_caption().enabled(); + const bool enabled = + Shell::Get()->accessibility_controller()->live_caption().enabled(); // Sets `live_caption_button_` toggle state to update its icon, icon color, // and background color.
diff --git a/ash/system/audio/unified_volume_view.h b/ash/system/audio/unified_volume_view.h index 74ef813..dac3f2f7 100644 --- a/ash/system/audio/unified_volume_view.h +++ b/ash/system/audio/unified_volume_view.h
@@ -91,7 +91,6 @@ // Whether this `UnifiedVolumeView` is the view for the active output node. bool const is_active_output_node_; - const raw_ptr<AccessibilityControllerImpl, ExperimentalAsh> a11y_controller_; uint64_t device_id_ = 0; // Owned by the views hierarchy. raw_ptr<IconButton, ExperimentalAsh> live_caption_button_ = nullptr;
diff --git a/ash/system/focus_mode/focus_mode_chip_carousel.cc b/ash/system/focus_mode/focus_mode_chip_carousel.cc index 2a7e2be6..20491c9 100644 --- a/ash/system/focus_mode/focus_mode_chip_carousel.cc +++ b/ash/system/focus_mode/focus_mode_chip_carousel.cc
@@ -7,6 +7,7 @@ #include "ash/api/tasks/tasks_types.h" #include "ash/resources/vector_icons/vector_icons.h" #include "base/containers/adapters.h" +#include "base/i18n/rtl.h" #include "ui/base/metadata/metadata_impl_macros.h" #include "ui/chromeos/styles/cros_tokens_color_mappings.h" #include "ui/compositor/layer.h" @@ -139,7 +140,6 @@ right_overflow_icon_->SetBoundsRect( gfx::Rect(contents_bounds.right() - kOverflowButtonWidth, y, kOverflowButtonWidth, h)); - scroll_view_->SetBoundsRect(contents_bounds); UpdateGradient(); } @@ -202,8 +202,9 @@ const float gradient_end_position = (chevron_space + kGradientWidth) / scroll_view_->bounds().width(); - // Left fade in section. - if (show_left_gradient) { + // Left fade in section. Gradients don't account for RTL like other `Views` + // coordinates do, so we need to flip to account for RTL ourselves. + if (base::i18n::IsRTL() ? show_right_gradient : show_left_gradient) { gradient_mask.AddStep(/*fraction=*/0, /*alpha=*/0); if (hovered) { gradient_mask.AddStep(gradient_start_position, 0); @@ -212,7 +213,7 @@ } // Right fade out section. - if (show_right_gradient) { + if (base::i18n::IsRTL() ? show_left_gradient : show_right_gradient) { gradient_mask.AddStep(/*fraction=*/(1 - gradient_end_position), /*alpha=*/255); if (hovered) {
diff --git a/ash/system/focus_mode/focus_mode_chip_carousel_unittest.cc b/ash/system/focus_mode/focus_mode_chip_carousel_unittest.cc index 9d92f57..471b99f 100644 --- a/ash/system/focus_mode/focus_mode_chip_carousel_unittest.cc +++ b/ash/system/focus_mode/focus_mode_chip_carousel_unittest.cc
@@ -7,6 +7,7 @@ #include "ash/api/tasks/tasks_types.h" #include "ash/constants/ash_features.h" #include "ash/test/ash_test_base.h" +#include "base/i18n/rtl.h" #include "base/test/scoped_feature_list.h" #include "testing/gmock/include/gmock/gmock.h" #include "ui/compositor/layer.h" @@ -25,6 +26,9 @@ "Podcast interview Script", "Book a flight to Seoul"}; +constexpr int kWidgetWidth = 320; +constexpr float kGradientWidth = 16; + } // namespace namespace ash { @@ -38,7 +42,7 @@ void SetUp() override { AshTestBase::SetUp(); widget_ = CreateFramelessTestWidget(); - widget_->SetBounds(gfx::Rect(/*width=*/320, /*height=*/48)); + widget_->SetBounds(gfx::Rect(/*width=*/kWidgetWidth, /*height=*/48)); focus_mode_chip_carousel_ = widget_->SetContentsView( std::make_unique<FocusModeChipCarousel>(base::DoNothing())); @@ -185,7 +189,8 @@ EXPECT_TRUE(GetRightOverflowIcon()->GetVisible()); // Both overflow icons should be shown on top of the scroll view. - EXPECT_EQ(gfx::Size(320, 32), GetScrollView()->GetBoundsInScreen().size()); + EXPECT_EQ(gfx::Size(kWidgetWidth, 32), + GetScrollView()->GetBoundsInScreen().size()); EXPECT_EQ(gfx::Size(28, 32), GetLeftOverflowIcon()->GetBoundsInScreen().size()); EXPECT_EQ(gfx::Size(28, 32), @@ -200,4 +205,27 @@ GetScrollView()->GetVisibleRect()))); } +// Tests that the gradient shows up on the correct side in RTL. +TEST_F(FocusModeChipCarouselTest, GradientInRTL) { + base::i18n::SetRTLForTesting(true); + + auto tasks = MakeTasks(kTestTaskTitles); + focus_mode_chip_carousel()->SetTasks(GetTaskPtrs(tasks)); + views::test::RunScheduledLayout(focus_mode_chip_carousel()); + EXPECT_TRUE(GetScrollView()->layer()->HasGradientMask()); + + // In RTL the carousel starts on the right side, so we can only scroll to the + // left and not to the right. Because of this the gradient should only be + // shown on the left side. + ASSERT_EQ(2u, GetScrollView()->layer()->gradient_mask().step_count()); + auto steps = GetScrollView()->layer()->gradient_mask().steps(); + const float allowed_difference = 0.0001f; + + EXPECT_FLOAT_EQ(0.0f, steps.front().fraction); + EXPECT_EQ(0u, steps.front().alpha); + EXPECT_NEAR(kGradientWidth / kWidgetWidth, steps[1].fraction, + allowed_difference); + EXPECT_EQ(255u, steps[1].alpha); +} + } // namespace ash
diff --git a/ash/system/phonehub/camera_roll_thumbnail_unittest.cc b/ash/system/phonehub/camera_roll_thumbnail_unittest.cc index a94531e..d5b2e94 100644 --- a/ash/system/phonehub/camera_roll_thumbnail_unittest.cc +++ b/ash/system/phonehub/camera_roll_thumbnail_unittest.cc
@@ -7,6 +7,7 @@ #include "ash/constants/ash_features.h" #include "ash/resources/vector_icons/vector_icons.h" #include "ash/strings/grit/ash_strings.h" +#include "ash/style/ash_color_id.h" #include "ash/style/ash_color_provider.h" #include "base/logging.h" #include "base/strings/string_number_conversions.h" @@ -134,9 +135,9 @@ if (is_video) { cc::PaintFlags flags; flags.setAntiAlias(true); - flags.setColor(provider->GetBaseLayerColor( - AshColorProvider::BaseLayerType::kTransparent80)); flags.setStyle(cc::PaintFlags::kFill_Style); + flags.setColor(camera_roll_thumbnail()->GetColorProvider()->GetColor( + kColorAshShieldAndBase80)); expected.DrawCircle(kExpectedCameraRollThumbnailVideoCircleOrigin, kExpectedCameraRollThumbnailVideoCircleRadius, flags); expected.DrawImageInt(
diff --git a/ash/system/tray/tray_background_view_unittest.cc b/ash/system/tray/tray_background_view_unittest.cc index 217b08ab..a6b4055 100644 --- a/ash/system/tray/tray_background_view_unittest.cc +++ b/ash/system/tray/tray_background_view_unittest.cc
@@ -158,7 +158,7 @@ std::unique_ptr<TrayBackgroundView>(std::move(tmp)))); // Set Dictation button to be visible. - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); controller->dictation().SetEnabled(true); }
diff --git a/ash/system/tray/tray_bubble_view.cc b/ash/system/tray/tray_bubble_view.cc index 6189613f..6d9a557 100644 --- a/ash/system/tray/tray_bubble_view.cc +++ b/ash/system/tray/tray_bubble_view.cc
@@ -272,7 +272,7 @@ DCHECK((init_params.anchor_mode != TrayBubbleView::AnchorMode::kView) || anchor_widget()); set_parent_window(params_.parent_window); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); SetCanActivate(controller->spoken_feedback().enabled() || controller->dictation().enabled());
diff --git a/ash/user_education/welcome_tour/welcome_tour_controller.h b/ash/user_education/welcome_tour/welcome_tour_controller.h index 5739c22..a9b95620 100644 --- a/ash/user_education/welcome_tour/welcome_tour_controller.h +++ b/ash/user_education/welcome_tour/welcome_tour_controller.h
@@ -27,7 +27,7 @@ namespace ash { -class AccessibilityControllerImpl; +class AccessibilityController; class ScopedNudgePause; class ScopedToastPause; class SessionController; @@ -141,7 +141,7 @@ // The accessibility controller is observed only while the Welcome Tour is in // progress, and will trigger an abort of the tour if ChromeVox is enabled. - base::ScopedObservation<AccessibilityControllerImpl, AccessibilityObserver> + base::ScopedObservation<AccessibilityController, AccessibilityObserver> accessibility_observation_{this}; // Sessions are observed only until the primary user session is activated for
diff --git a/ash/webui/common/backend/accessibility_features.cc b/ash/webui/common/backend/accessibility_features.cc index 147103c..bab5e918 100644 --- a/ash/webui/common/backend/accessibility_features.cc +++ b/ash/webui/common/backend/accessibility_features.cc
@@ -20,7 +20,7 @@ namespace { bool ShouldForceHiddenElementsVisible() { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); if (!accessibility_controller) { return false; @@ -34,7 +34,7 @@ } // namespace AccessibilityFeatures::AccessibilityFeatures() { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); if (!accessibility_controller) { return; @@ -47,7 +47,7 @@ } AccessibilityFeatures::~AccessibilityFeatures() { - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); if (!accessibility_controller) { return;
diff --git a/ash/webui/common/backend/accessibility_features_unittest.cc b/ash/webui/common/backend/accessibility_features_unittest.cc index 29ffcf4..deeace1 100644 --- a/ash/webui/common/backend/accessibility_features_unittest.cc +++ b/ash/webui/common/backend/accessibility_features_unittest.cc
@@ -105,7 +105,7 @@ // Verify the observer is initialized with |force_visible| as false. ASSERT_FALSE(fake_observer_.force_visible()); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); // Spoken feedback.
diff --git a/ash/wm/desks/desks_controller.cc b/ash/wm/desks/desks_controller.cc index d49e03a..23e90f7 100644 --- a/ash/wm/desks/desks_controller.cc +++ b/ash/wm/desks/desks_controller.cc
@@ -11,7 +11,6 @@ #include "ash/app_list/app_list_controller_impl.h" #include "ash/constants/ash_features.h" #include "ash/constants/notifier_catalogs.h" -#include "ash/public/cpp/accessibility_controller.h" #include "ash/public/cpp/shelf_model.h" #include "ash/public/cpp/shelf_prefs.h" #include "ash/public/cpp/shelf_types.h" @@ -1984,7 +1983,7 @@ // We should only announce desks are being merged if we are combining desks. // Otherwise, we tell the user that the desk has closed with its windows. - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = shell->accessibility_controller(); if (close_type == DeskCloseType::kCombineDesks) { accessibility_controller->TriggerAccessibilityAlertWithMessage(
diff --git a/ash/wm/desks/templates/saved_desk_dialog_controller.cc b/ash/wm/desks/templates/saved_desk_dialog_controller.cc index 10caca6..640e3aa 100644 --- a/ash/wm/desks/templates/saved_desk_dialog_controller.cc +++ b/ash/wm/desks/templates/saved_desk_dialog_controller.cc
@@ -221,7 +221,7 @@ dialog_widget_observation_.Observe(dialog_widget_.get()); // Ensure that if ChromeVox is enabled, it focuses on the dialog. - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); if (accessibility_controller->spoken_feedback().enabled()) { accessibility_controller->SetA11yOverrideWindow(
diff --git a/ash/wm/desks/templates/saved_desk_save_desk_button_container.cc b/ash/wm/desks/templates/saved_desk_save_desk_button_container.cc index 8c971b4..aabe4beb 100644 --- a/ash/wm/desks/templates/saved_desk_save_desk_button_container.cc +++ b/ash/wm/desks/templates/saved_desk_save_desk_button_container.cc
@@ -137,7 +137,7 @@ private: base::RepeatingClosure accessibility_state_changed_callback_; - base::ScopedObservation<AccessibilityControllerImpl, AccessibilityObserver> + base::ScopedObservation<AccessibilityController, AccessibilityObserver> observation_{this}; };
diff --git a/ash/wm/desks/templates/saved_desk_unittest.cc b/ash/wm/desks/templates/saved_desk_unittest.cc index 01d50c6..f7b8a92 100644 --- a/ash/wm/desks/templates/saved_desk_unittest.cc +++ b/ash/wm/desks/templates/saved_desk_unittest.cc
@@ -4508,7 +4508,7 @@ ui::ScopedAnimationDurationScaleMode animation_scale( ui::ScopedAnimationDurationScaleMode::NON_ZERO_DURATION); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); accessibility_controller->spoken_feedback().SetEnabled(true); EXPECT_TRUE(accessibility_controller->spoken_feedback().enabled());
diff --git a/ash/wm/overview/overview_session_unittest.cc b/ash/wm/overview/overview_session_unittest.cc index c5f2209..c1fc472 100644 --- a/ash/wm/overview/overview_session_unittest.cc +++ b/ash/wm/overview/overview_session_unittest.cc
@@ -1107,7 +1107,7 @@ TEST_P(OverviewSessionTest, DesksWidgetBoundsChangeWhenDisableChromeVox) { std::unique_ptr<aura::Window> window1 = CreateTestWindow(); - AccessibilityControllerImpl* accessibility_controller = + AccessibilityController* accessibility_controller = Shell::Get()->accessibility_controller(); // Enable ChromeVox.
diff --git a/ash/wm/tablet_mode/tablet_mode_controller_unittest.cc b/ash/wm/tablet_mode/tablet_mode_controller_unittest.cc index 9819be1..46c705a 100644 --- a/ash/wm/tablet_mode/tablet_mode_controller_unittest.cc +++ b/ash/wm/tablet_mode/tablet_mode_controller_unittest.cc
@@ -13,13 +13,11 @@ #include "ash/accelerometer/accelerometer_reader.h" #include "ash/accelerometer/accelerometer_types.h" -#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/accessibility/test_accessibility_controller_client.h" #include "ash/app_list/app_list_controller_impl.h" #include "ash/constants/app_types.h" #include "ash/constants/ash_switches.h" #include "ash/display/screen_orientation_controller.h" -#include "ash/public/cpp/accessibility_controller.h" #include "ash/public/cpp/shell_window_ids.h" #include "ash/public/cpp/tablet_mode.h" #include "ash/public/cpp/test/shell_test_api.h"
diff --git a/ash/wm/workspace/workspace_layout_manager_unittest.cc b/ash/wm/workspace/workspace_layout_manager_unittest.cc index 49532b8..23ab272e 100644 --- a/ash/wm/workspace/workspace_layout_manager_unittest.cc +++ b/ash/wm/workspace/workspace_layout_manager_unittest.cc
@@ -171,8 +171,7 @@ } private: - raw_ptr<AccessibilityControllerImpl, ExperimentalAsh> - accessibility_controller_; + raw_ptr<AccessibilityController, ExperimentalAsh> accessibility_controller_; const bool enabled_; }; @@ -1972,7 +1971,7 @@ TEST_F(WorkspaceLayoutManagerBackdropTest, SpokenFeedbackFullscreenBackground) { WorkspaceController* wc = ShellTestApi().workspace_controller(); WorkspaceControllerTestApi test_helper(wc); - AccessibilityControllerImpl* controller = + AccessibilityController* controller = Shell::Get()->accessibility_controller(); TestAccessibilityControllerClient client;
diff --git a/base/process/process_mac.cc b/base/process/process_mac.cc index b8659de..9331a05 100644 --- a/base/process/process_mac.cc +++ b/base/process/process_mac.cc
@@ -28,7 +28,7 @@ // TASK_DEFAULT_APPLICATION. BASE_FEATURE(kMacSetDefaultTaskRole, "MacSetDefaultTaskRole", - FEATURE_DISABLED_BY_DEFAULT); + FEATURE_ENABLED_BY_DEFAULT); // Returns the `task_role_t` of the process whose task port is `task_port`. absl::optional<task_role_t> GetTaskCategoryPolicyRole(mach_port_t task_port) {
diff --git a/build/android/pylib/gtest/gtest_test_instance.py b/build/android/pylib/gtest/gtest_test_instance.py index f1a150d..7d41f7e 100644 --- a/build/android/pylib/gtest/gtest_test_instance.py +++ b/build/android/pylib/gtest/gtest_test_instance.py
@@ -110,6 +110,10 @@ _RE_DISABLED = re.compile(r'DISABLED_') _RE_FLAKY = re.compile(r'FLAKY_') +# Regex that matches the printout when there are test failures. +# matches "[ FAILED ] 1 test, listed below:" +_RE_ANY_TESTS_FAILED = re.compile(r'\[ +FAILED +\].*listed below') + # Detect stack line in stdout. _STACK_LINE_RE = re.compile(r'\s*#\d+') @@ -229,6 +233,9 @@ else: log.append(l) + if _RE_ANY_TESTS_FAILED.match(l): + break + if result_type and test_name: # Don't bother symbolizing output if the test passed. if result_type == base_test_result.ResultType.PASS: @@ -238,7 +245,10 @@ log=symbolize_stack_and_merge_with_log())) test_name = None - handle_possibly_unknown_test() + else: + # Executing this after tests have finished with a failure causes a + # duplicate test entry to be added to results. crbug/1380825 + handle_possibly_unknown_test() return results
diff --git a/build/rust/cargo_crate.gni b/build/rust/cargo_crate.gni index 61ecfe2..cf16a68 100644 --- a/build/rust/cargo_crate.gni +++ b/build/rust/cargo_crate.gni
@@ -195,6 +195,11 @@ } } + _testonly = false + if (defined(invoker.testonly)) { + _testonly = invoker.testonly + } + # The main target, either a Rust source set or an executable. target(_target_type, target_name) { forward_variables_from(invoker, @@ -214,7 +219,11 @@ "rustenv", "dev_deps", ]) - forward_variables_from(invoker, TESTONLY_AND_VISIBILITY) + + testonly = _testonly + if (defined(invoker.visibility)) { + visibility = invoker.visibility + } if (defined(crate_type) && crate_type == "cdylib") { # See comments above about cdylib. crate_type = "rlib" @@ -327,6 +336,10 @@ script = rebase_path("//build/rust/run_build_script.py") build_script_target = ":${_build_script_name}($rust_macro_toolchain)" deps = [ build_script_target ] + testonly = _testonly + if (defined(invoker.visibility)) { + visibility = invoker.visibility + } # The build script may be built with a different toolchain when # cross-compiling (the host toolchain) so we must find the path relative @@ -391,6 +404,10 @@ rust_executable(_build_script_name) { sources = invoker.build_sources crate_root = invoker.build_root + testonly = _testonly + if (defined(invoker.visibility)) { + visibility = invoker.visibility + } if (defined(invoker.build_deps)) { deps = invoker.build_deps }
diff --git a/build/rust/tests/BUILD.gn b/build/rust/tests/BUILD.gn index 6514fdac..9e9ec8e 100644 --- a/build/rust/tests/BUILD.gn +++ b/build/rust/tests/BUILD.gn
@@ -30,6 +30,7 @@ "test_rlib_crate:target1", "test_rlib_crate:target2", "test_rlib_crate:test_rlib_crate_associated_bin", + "test_rlib_crate_testonly:testonly_target", "test_rust_metadata:test_rust_metadata_cc_exe", "test_rust_metadata:test_rust_metadata_exe", "test_rust_multiple_dep_versions_exe",
diff --git a/build/rust/tests/test_rlib_crate_testonly/BUILD.gn b/build/rust/tests/test_rlib_crate_testonly/BUILD.gn new file mode 100644 index 0000000..d246702 --- /dev/null +++ b/build/rust/tests/test_rlib_crate_testonly/BUILD.gn
@@ -0,0 +1,22 @@ +# Copyright 2023 The Chromium Authors +# Use of this source code is governed by a BSD-style license that can be +# found in the LICENSE file. + +import("//build/rust/cargo_crate.gni") + +cargo_crate("testonly_target") { + testonly = true + crate_root = "crate/src/main.rs" + crate_type = "bin" + sources = [ "crate/src/main.rs" ] + build_sources = [ "crate/build.rs" ] + build_root = "crate/build.rs" + build_deps = [ ":testonly_build_dep" ] +} + +cargo_crate("testonly_build_dep") { + testonly = true + crate_name = "test_only_build_dep" + crate_root = "crate/src/lib.rs" + sources = [ "crate/src/lib.rs" ] +}
diff --git a/build/rust/tests/test_rlib_crate_testonly/crate/build.rs b/build/rust/tests/test_rlib_crate_testonly/crate/build.rs new file mode 100644 index 0000000..6d03310 --- /dev/null +++ b/build/rust/tests/test_rlib_crate_testonly/crate/build.rs
@@ -0,0 +1,5 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +fn main() {}
diff --git a/build/rust/tests/test_rlib_crate_testonly/crate/src/lib.rs b/build/rust/tests/test_rlib_crate_testonly/crate/src/lib.rs new file mode 100644 index 0000000..2c54a522 --- /dev/null +++ b/build/rust/tests/test_rlib_crate_testonly/crate/src/lib.rs
@@ -0,0 +1,3 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file.
diff --git a/build/rust/tests/test_rlib_crate_testonly/crate/src/main.rs b/build/rust/tests/test_rlib_crate_testonly/crate/src/main.rs new file mode 100644 index 0000000..9d78366 --- /dev/null +++ b/build/rust/tests/test_rlib_crate_testonly/crate/src/main.rs
@@ -0,0 +1,5 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +pub fn main() {}
diff --git a/chrome/android/chrome_java_resources.gni b/chrome/android/chrome_java_resources.gni index 1775ea5c..7bf4e528 100644 --- a/chrome/android/chrome_java_resources.gni +++ b/chrome/android/chrome_java_resources.gni
@@ -410,7 +410,6 @@ "java/res/drawable/qr_code.xml", "java/res/drawable/reading_list_empty_state_illustration.xml", "java/res/drawable/safety_check.xml", - "java/res/drawable/screenshot.xml", "java/res/drawable/section_tab_background.xml", "java/res/drawable/send_tab.xml", "java/res/drawable/shared_clipboard_zero_state_dark.xml",
diff --git a/chrome/android/chrome_test_java_sources.gni b/chrome/android/chrome_test_java_sources.gni index 887aeeda..dff1413a 100644 --- a/chrome/android/chrome_test_java_sources.gni +++ b/chrome/android/chrome_test_java_sources.gni
@@ -151,6 +151,7 @@ "javatests/src/org/chromium/chrome/browser/customtabs/CustomTabDeferredStartupTest.java", "javatests/src/org/chromium/chrome/browser/customtabs/CustomTabExternalNavigationTest.java", "javatests/src/org/chromium/chrome/browser/customtabs/CustomTabFromChromeExternalNavigationTest.java", + "javatests/src/org/chromium/chrome/browser/customtabs/CustomTabModalDialogTest.java", "javatests/src/org/chromium/chrome/browser/customtabs/CustomTabPostMessageTest.java", "javatests/src/org/chromium/chrome/browser/customtabs/CustomTabPrivacySandboxDialogTest.java", "javatests/src/org/chromium/chrome/browser/customtabs/CustomTabTabPersistenceIntegrationTest.java",
diff --git a/chrome/android/features/tab_ui/javatests/src/org/chromium/chrome/browser/tasks/tab_management/TabGridIphTest.java b/chrome/android/features/tab_ui/javatests/src/org/chromium/chrome/browser/tasks/tab_management/TabGridIphTest.java index 3ff9e92e..857495c 100644 --- a/chrome/android/features/tab_ui/javatests/src/org/chromium/chrome/browser/tasks/tab_management/TabGridIphTest.java +++ b/chrome/android/features/tab_ui/javatests/src/org/chromium/chrome/browser/tasks/tab_management/TabGridIphTest.java
@@ -55,6 +55,7 @@ import org.chromium.base.test.util.Feature; import org.chromium.base.test.util.Restriction; import org.chromium.chrome.browser.ChromeTabbedActivity; +import org.chromium.chrome.browser.feature_engagement.TrackerFactory; import org.chromium.chrome.browser.flags.ChromeFeatureList; import org.chromium.chrome.browser.flags.ChromeSwitches; import org.chromium.chrome.browser.multiwindow.MultiWindowUtils; @@ -65,6 +66,8 @@ import org.chromium.chrome.test.util.ChromeRenderTestRule; import org.chromium.chrome.test.util.ChromeTabUtils; import org.chromium.chrome.test.util.browser.Features.DisableFeatures; +import org.chromium.components.feature_engagement.FeatureConstants; +import org.chromium.components.feature_engagement.Tracker; import org.chromium.content_public.browser.test.util.TestThreadUtils; import org.chromium.ui.modaldialog.ModalDialogManager; import org.chromium.ui.modaldialog.ModalDialogProperties; @@ -93,6 +96,7 @@ @DisableFeatures({ChromeFeatureList.ARCHIVE_TAB_SERVICE, ChromeFeatureList.START_SURFACE_ANDROID}) public class TabGridIphTest { private ModalDialogManager mModalDialogManager; + private Tracker mTracker; @Rule public ChromeTabbedActivityTestRule mActivityTestRule = new ChromeTabbedActivityTestRule(); @@ -113,6 +117,18 @@ mModalDialogManager = TestThreadUtils.runOnUiThreadBlockingNoException( mActivityTestRule.getActivity()::getModalDialogManager); + TestThreadUtils.runOnUiThreadBlocking( + () -> { + mTracker = + TrackerFactory.getTrackerForProfile( + mActivityTestRule.getProfile(false)); + }); + CriteriaHelper.pollUiThread(mTracker::isInitialized); + CriteriaHelper.pollUiThread( + () -> { + return mTracker.wouldTriggerHelpUI( + FeatureConstants.TAB_GROUPS_DRAG_AND_DROP_FEATURE); + }); } @After
diff --git a/chrome/android/features/tab_ui/javatests/src/org/chromium/chrome/browser/tasks/tab_management/TabSwitcherAndStartSurfaceLayoutTest.java b/chrome/android/features/tab_ui/javatests/src/org/chromium/chrome/browser/tasks/tab_management/TabSwitcherAndStartSurfaceLayoutTest.java index 222e889..5b7dba6 100644 --- a/chrome/android/features/tab_ui/javatests/src/org/chromium/chrome/browser/tasks/tab_management/TabSwitcherAndStartSurfaceLayoutTest.java +++ b/chrome/android/features/tab_ui/javatests/src/org/chromium/chrome/browser/tasks/tab_management/TabSwitcherAndStartSurfaceLayoutTest.java
@@ -879,10 +879,6 @@ @UseMethodParameter(RefactorTestParams.class) @EnableFeatures({ChromeFeatureList.TAB_TO_GTS_ANIMATION + "<Study"}) @CommandLineFlags.Add({BASE_PARAMS}) - @DisableIf.Build( - message = "Flaky on Android P, see https://crbug.com/1063991", - sdk_is_greater_than = VERSION_CODES.O_MR1, - sdk_is_less_than = VERSION_CODES.Q) public void testIncognitoToggle_tabCount(boolean isStartSurfaceRefactorEnabled) throws InterruptedException { mActivityTestRule.loadUrl(mUrl);
diff --git a/chrome/android/java/res/drawable/screenshot.xml b/chrome/android/java/res/drawable/screenshot.xml deleted file mode 100644 index 2ac9efbf9..0000000 --- a/chrome/android/java/res/drawable/screenshot.xml +++ /dev/null
@@ -1,44 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -Copyright 2020 The Chromium Authors -Use of this source code is governed by a BSD-style license that can be -found in the LICENSE file. ---> - -<vector xmlns:android="http://schemas.android.com/apk/res/android" - android:width="24dp" - android:height="24dp" - android:viewportWidth="24" - android:viewportHeight="24" - android:tint="@macro/default_icon_color"> - <path - android:pathData="m8.6,2h-4.192c-0.7776,0 -1.408,0.6304 -1.408,1.408v4.192" - android:strokeWidth="1.8" - android:fillColor="#00000000" - android:strokeColor="@android:color/white" - android:strokeLineCap="square"/> - <path - android:pathData="m8.6,18.8l-4.192,-0c-0.7776,-0 -1.408,-0.6304 -1.408,-1.408l0,-4.192" - android:strokeWidth="1.8" - android:fillColor="#00000000" - android:strokeColor="@android:color/white" - android:strokeLineCap="square"/> - <path - android:pathData="m14.2,2l4.192,0c0.7776,0 1.408,0.6304 1.408,1.408l-0,4.192" - android:strokeWidth="1.8" - android:fillColor="#00000000" - android:strokeColor="@android:color/white" - android:strokeLineCap="square"/> - <path - android:pathData="m19.8,12.5v9.8" - android:strokeWidth="1.8" - android:fillColor="#00000000" - android:strokeColor="@android:color/white" - android:strokeLineCap="square"/> - <path - android:pathData="m13.5,18.8l9.8,-0" - android:strokeWidth="1.8" - android:fillColor="#00000000" - android:strokeColor="@android:color/white" - android:strokeLineCap="square"/> -</vector>
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java b/chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java index 486221c..6183dac 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java
@@ -128,7 +128,6 @@ import org.chromium.chrome.browser.metrics.MainIntentBehaviorMetrics; import org.chromium.chrome.browser.metrics.SimpleStartupForegroundSessionDetector; import org.chromium.chrome.browser.modaldialog.ChromeTabModalPresenter; -import org.chromium.chrome.browser.modaldialog.TabModalLifetimeHandler; import org.chromium.chrome.browser.multiwindow.MultiInstanceChromeTabbedActivity; import org.chromium.chrome.browser.multiwindow.MultiInstanceManager; import org.chromium.chrome.browser.multiwindow.MultiWindowUtils; @@ -241,7 +240,6 @@ import org.chromium.ui.base.PageTransition; import org.chromium.ui.dragdrop.DragAndDropDelegate; import org.chromium.ui.dragdrop.DragAndDropDelegateImpl; -import org.chromium.ui.modaldialog.ModalDialogManager; import org.chromium.ui.widget.Toast; import org.chromium.url.GURL; @@ -331,7 +329,6 @@ private HistoricalTabModelObserver mHistoricalTabModelObserver; private BrowserControlsVisibilityDelegate mVrBrowserControlsVisibilityDelegate; - private TabModalLifetimeHandler mTabModalHandler; private boolean mUIWithNativeInitialized; @@ -2851,7 +2848,7 @@ } private void onOmniboxFocusChanged(boolean hasFocus) { - mTabModalHandler.onOmniboxFocusChanged(hasFocus); + getTabModalLifetimeHandler().onOmniboxFocusChanged(hasFocus); } private void recordLauncherShortcutAction(boolean isIncognito) { @@ -2876,7 +2873,7 @@ return true; } - if (mTabModalHandler.onBackPressed()) { + if (getTabModalLifetimeHandler().onBackPressed()) { BackPressManager.record(BackPressHandler.Type.TAB_MODAL_HANDLER); return true; } @@ -3443,6 +3440,11 @@ } @Override + protected boolean supportsTabModalDialogs() { + return true; + } + + @Override public boolean dispatchKeyEvent(KeyEvent event) { Boolean result = KeyboardShortcuts.dispatchKeyEvent( @@ -3540,29 +3542,7 @@ } private ComposedBrowserControlsVisibilityDelegate getAppBrowserControlsVisibilityDelegate() { - // TODO(jinsukkim): Move this to RootUiCoordinator. - return ((TabbedRootUiCoordinator) mRootUiCoordinator) - .getAppBrowserControlsVisibilityDelegate(); - } - - @Override - protected ModalDialogManager createModalDialogManager() { - ModalDialogManager manager = super.createModalDialogManager(); - // TODO(crbug.com/1157310): Transition this::method refs to dedicated suppliers. - mTabModalHandler = - new TabModalLifetimeHandler( - this, - getLifecycleDispatcher(), - manager, - this::getAppBrowserControlsVisibilityDelegate, - this::getTabObscuringHandler, - this::getToolbarManager, - getContextualSearchManagerSupplier(), - getTabModelSelectorSupplier(), - this::getBrowserControlsManager, - this::getFullscreenManager, - mBackPressManager); - return manager; + return mRootUiCoordinator.getAppBrowserControlsVisibilityDelegate(); } // App Menu related code -----------------------------------------------------------------------
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/app/ChromeActivity.java b/chrome/android/java/src/org/chromium/chrome/browser/app/ChromeActivity.java index d20186ca..39988c451 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/app/ChromeActivity.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/app/ChromeActivity.java
@@ -129,6 +129,7 @@ import org.chromium.chrome.browser.metrics.ActivityTabStartupMetricsTracker; import org.chromium.chrome.browser.metrics.LaunchMetrics; import org.chromium.chrome.browser.metrics.UmaSessionStats; +import org.chromium.chrome.browser.modaldialog.TabModalLifetimeHandler; import org.chromium.chrome.browser.multiwindow.MultiWindowUtils; import org.chromium.chrome.browser.night_mode.SystemNightModeMonitor; import org.chromium.chrome.browser.night_mode.WebContentsDarkModeController; @@ -402,6 +403,8 @@ private boolean mIsRecreatingForTabletModeChange; // This is only used on automotive. private @Nullable MissingDeviceLockLauncher mMissingDeviceLockLauncher; + // Handling the dismissal of tab modal dialog. + private TabModalLifetimeHandler mTabModalLifetimeHandler; protected ChromeActivity() { mManualFillingComponentSupplier.set(ManualFillingComponentFactory.createComponent()); @@ -1785,8 +1788,40 @@ @Override protected ModalDialogManager createModalDialogManager() { - return new ModalDialogManager( - new AppModalPresenter(this), ModalDialogManager.ModalDialogType.APP); + var dialogManager = + new ModalDialogManager( + new AppModalPresenter(this), ModalDialogManager.ModalDialogType.APP); + // TODO(crbug.com/1157310): Transition this::method refs to dedicated suppliers. + if (supportsTabModalDialogs()) { + mTabModalLifetimeHandler = + new TabModalLifetimeHandler( + this, + getLifecycleDispatcher(), + dialogManager, + () -> mRootUiCoordinator.getAppBrowserControlsVisibilityDelegate(), + this::getTabObscuringHandler, + this::getToolbarManager, + getContextualSearchManagerSupplier(), + getTabModelSelectorSupplier(), + this::getBrowserControlsManager, + this::getFullscreenManager, + mBackPressManager); + } + return dialogManager; + } + + /** + * Whether tab modal dialog is supported. If not, a dialog will be shown as a App modal dialog. + * + * @return True if tab modal dialog is supported. + */ + protected boolean supportsTabModalDialogs() { + return false; + } + + @Nullable + protected TabModalLifetimeHandler getTabModalLifetimeHandler() { + return mTabModalLifetimeHandler; } protected Drawable getBackgroundDrawable() {
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabActivity.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabActivity.java index 8ece752..dc07728 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabActivity.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabActivity.java
@@ -571,6 +571,12 @@ @Override protected boolean handleBackPressed() { + if (!BackPressManager.isEnabled() + && getTabModalLifetimeHandler() != null + && getTabModalLifetimeHandler().onBackPressed()) { + BackPressManager.record(BackPressHandler.Type.TAB_MODAL_HANDLER); + return true; + } if (BackPressManager.correctTabNavigationOnFallback()) { if (getToolbarManager() != null && getToolbarManager().back()) { return true;
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabRootUiCoordinator.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabRootUiCoordinator.java index 03464dfd..a763b26 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabRootUiCoordinator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabRootUiCoordinator.java
@@ -241,6 +241,11 @@ } mTabController = tabController; mMinimizeDelegateSupplier = minimizeDelegateSupplier; + // TODO(https://crbug.com/1509163): move this RootUiCoordinator once this flag is removed. + if (ChromeFeatureList.sCctTabModalDialog.isEnabled()) { + getAppBrowserControlsVisibilityDelegate() + .addDelegate(browserControlsManager.getBrowserVisibilityDelegate()); + } } @Override
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/CustomTabActivity.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/CustomTabActivity.java index e2cd01f2..04ae8322 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/CustomTabActivity.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/CustomTabActivity.java
@@ -377,6 +377,11 @@ return new CustomTabLaunchCauseMetrics(this); } + @Override + protected boolean supportsTabModalDialogs() { + return ChromeFeatureList.sCctTabModalDialog.isEnabled(); + } + public NightModeStateProvider getNightModeStateProviderForTesting() { return super.getNightModeStateProvider(); }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/RealtimeEngagementSignalObserver.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/RealtimeEngagementSignalObserver.java index b9108d2c5..aac2454b 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/RealtimeEngagementSignalObserver.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/RealtimeEngagementSignalObserver.java
@@ -4,10 +4,8 @@ package org.chromium.chrome.browser.customtabs.content; -import static org.chromium.cc.mojom.RootScrollOffsetUpdateFrequency.NONE; import static org.chromium.cc.mojom.RootScrollOffsetUpdateFrequency.ON_SCROLL_END; -import android.graphics.Point; import android.os.Bundle; import android.os.SystemClock; @@ -21,8 +19,6 @@ import org.chromium.base.ResettersForTesting; import org.chromium.base.UserData; import org.chromium.base.metrics.RecordHistogram; -import org.chromium.cc.mojom.RootScrollOffsetUpdateFrequency; -import org.chromium.cc.mojom.RootScrollOffsetUpdateFrequency.EnumType; import org.chromium.chrome.browser.customtabs.CustomTabsConnection; import org.chromium.chrome.browser.customtabs.content.TabObserverRegistrar.CustomTabTabObserver; import org.chromium.chrome.browser.customtabs.features.TabInteractionRecorder; @@ -62,13 +58,9 @@ @VisibleForTesting protected static final String REAL_VALUES = "real_values"; private static final int STUB_PERCENT = 0; - // Feature param for the time after the scroll-end a scroll update is allowed. - @VisibleForTesting - protected static final String TIME_CAN_UPDATE_AFTER_END = "time_can_update_after_end"; - // This value was chosen based on experiment data. 300ms covers about 98% of the scrolls while // trying to increase coverage further would require an unreasonably high threshold. - private static final int DEFAULT_AFTER_SCROLL_END_THRESHOLD_MS = 300; + @VisibleForTesting static final int DEFAULT_AFTER_SCROLL_END_THRESHOLD_MS = 300; private static final String TIME_SCROLL_UPDATE_RECEIVED_AFTER_SCROLL_END = "CustomTabs.TimeScrollUpdateReceivedAfterScrollEnd"; @@ -84,8 +76,7 @@ @Nullable private GestureStateListener mGestureStateListener; @Nullable private WebContentsObserver mEngagementSignalWebContentsObserver; @Nullable private ScrollState mScrollState; - private @RootScrollOffsetUpdateFrequency.EnumType int mScrollOffsetUpdateFrequency; - private int mAfterScrollEndThresholdMs; + // Tracks the user interaction state across multiple tabs and WebContents. private boolean mDidGetUserInteraction; // Prevents sending Engagement Signals temporarily. @@ -114,16 +105,6 @@ mTabObserverRegistrar = tabObserverRegistrar; mCallback = callback; - mScrollOffsetUpdateFrequency = - ChromeFeatureList.isEnabled( - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL) - ? ON_SCROLL_END - : NONE; - mAfterScrollEndThresholdMs = - ChromeFeatureList.getFieldTrialParamByFeatureAsInt( - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL, - TIME_CAN_UPDATE_AFTER_END, - DEFAULT_AFTER_SCROLL_END_THRESHOLD_MS); mShouldSendRealValues = shouldSendRealValues(); mPendingInitialUpdate = hadScrollDown; @@ -229,7 +210,6 @@ mWebContents = tab.getWebContents(); mScrollState = ScrollState.from(tab); - mScrollState.setParams(mScrollOffsetUpdateFrequency, mAfterScrollEndThresholdMs); mGestureStateListener = new GestureStateListener() { @@ -245,26 +225,8 @@ } @Override - public void onScrollUpdateGestureConsumed(@Nullable Point rootScrollOffset) { - if (mScrollOffsetUpdateFrequency == ON_SCROLL_END) return; - - if (rootScrollOffset != null) { - RenderCoordinates renderCoordinates = - RenderCoordinates.fromWebContents(tab.getWebContents()); - // We don't care about the return value of #onScrollUpdate here because - // this method will always be called before #onScrollEnded. - mScrollState.onScrollUpdate( - rootScrollOffset.y, - renderCoordinates.getMaxVerticalScrollPixInt(), - false); - } - } - - @Override public void onScrollOffsetOrExtentChanged( int scrollOffsetY, int scrollExtentY) { - if (mScrollOffsetUpdateFrequency == NONE && !mPendingInitialUpdate) return; - assert tab != null; RenderCoordinates renderCoordinates = RenderCoordinates.fromWebContents(tab.getWebContents()); @@ -330,7 +292,7 @@ GestureListenerManager gestureListenerManager = GestureListenerManager.fromWebContents(mWebContents); if (!gestureListenerManager.hasListener(mGestureStateListener)) { - gestureListenerManager.addListener(mGestureStateListener, mScrollOffsetUpdateFrequency); + gestureListenerManager.addListener(mGestureStateListener, ON_SCROLL_END); } mWebContents.addObserver(mEngagementSignalWebContentsObserver); } @@ -428,23 +390,10 @@ boolean mIsDirectionUp; int mMaxScrollPercentage; int mMaxReportedScrollPercentage; - @RootScrollOffsetUpdateFrequency.EnumType int mScrollOffsetUpdateFrequency = NONE; - int mAfterScrollEndThresholdMs = DEFAULT_AFTER_SCROLL_END_THRESHOLD_MS; Long mTimeLastOnScrollEnded; boolean mHadFirstDownScroll; /** - * @param frequency The {@link RootScrollOffsetUpdateFrequency.EnumType}, can be |NONE| or - * |ON_SCROLL_END|. - * @param afterScrollEndThreshold The after scroll-end threshold in ms, ignored if the - * frequency isn't |ON_SCROLL_END|. - */ - void setParams(@EnumType int frequency, int afterScrollEndThreshold) { - mScrollOffsetUpdateFrequency = frequency; - mAfterScrollEndThresholdMs = afterScrollEndThreshold; - } - - /** * @param isDirectionUp Whether the scroll direction is up. * @return Whether there has been a down scroll. */ @@ -516,7 +465,7 @@ mMaxReportedScrollPercentage = maxScrollPercentageFivesMultiple; reportedPercentage = mMaxReportedScrollPercentage; } - if (mScrollOffsetUpdateFrequency == ON_SCROLL_END && allowUpdateAfter) { + if (allowUpdateAfter) { mTimeLastOnScrollEnded = SystemClock.elapsedRealtime(); } mIsScrollActive = false; @@ -543,7 +492,7 @@ private boolean isValidUpdateAfterScrollEnd() { return !mIsScrollActive && mTimeLastOnScrollEnded != null - && timeSinceLastOnScrollEndedMillis() <= mAfterScrollEndThresholdMs; + && timeSinceLastOnScrollEndedMillis() <= DEFAULT_AFTER_SCROLL_END_THRESHOLD_MS; } private long timeSinceLastOnScrollEndedMillis() {
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/features/toolbar/CustomTabToolbar.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/features/toolbar/CustomTabToolbar.java index 5d736b26..52e84bb 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/features/toolbar/CustomTabToolbar.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/features/toolbar/CustomTabToolbar.java
@@ -946,9 +946,7 @@ @Override public CaptureReadinessResult isReadyForTextureCapture() { - if (ToolbarFeatures.shouldBlockCapturesForAblation()) { - return CaptureReadinessResult.notReady(TopToolbarBlockCaptureReason.SCROLL_ABLATION); - } else if (ToolbarFeatures.shouldSuppressCaptures()) { + if (ToolbarFeatures.shouldSuppressCaptures()) { CustomTabCaptureStateToken currentToken = generateCaptureStateToken(); final @ToolbarSnapshotDifference int difference = currentToken.getAnyDifference(mLastCustomTabCaptureStateToken);
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/tabbed_mode/TabbedRootUiCoordinator.java b/chrome/android/java/src/org/chromium/chrome/browser/tabbed_mode/TabbedRootUiCoordinator.java index 79e61da7..b3c701c 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/tabbed_mode/TabbedRootUiCoordinator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/tabbed_mode/TabbedRootUiCoordinator.java
@@ -119,7 +119,6 @@ import org.chromium.chrome.features.start_surface.StartSurfaceUserData; import org.chromium.components.browser_ui.accessibility.PageZoomCoordinator; import org.chromium.components.browser_ui.bottomsheet.EmptyBottomSheetObserver; -import org.chromium.components.browser_ui.util.ComposedBrowserControlsVisibilityDelegate; import org.chromium.components.browser_ui.widget.InsetObserver; import org.chromium.components.browser_ui.widget.MenuOrKeyboardActionController; import org.chromium.components.browser_ui.widget.TouchEventObserver; @@ -159,7 +158,6 @@ private NotificationPermissionController mNotificationPermissionController; private HistoryNavigationCoordinator mHistoryNavigationCoordinator; private NavigationSheet mNavigationSheet; - private ComposedBrowserControlsVisibilityDelegate mAppBrowserControlsVisibilityDelegate; private LayoutManagerImpl mLayoutManager; private CommerceSubscriptionsService mCommerceSubscriptionsService; private UndoGroupSnackbarController mUndoGroupSnackbarController; @@ -1070,16 +1068,6 @@ return EdgeToEdgeControllerFactory.isSupportedConfiguration(mActivity); } - /** - * @return {@link ComposedBrowserControlsVisibilityDelegate} object for tabbed activity. - */ - public ComposedBrowserControlsVisibilityDelegate getAppBrowserControlsVisibilityDelegate() { - if (mAppBrowserControlsVisibilityDelegate == null) { - mAppBrowserControlsVisibilityDelegate = new ComposedBrowserControlsVisibilityDelegate(); - } - return mAppBrowserControlsVisibilityDelegate; - } - public StatusIndicatorCoordinator getStatusIndicatorCoordinatorForTesting() { return mStatusIndicatorCoordinator; }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java b/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java index 364389c..15ee19d39 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java
@@ -164,6 +164,7 @@ import org.chromium.components.browser_ui.bottomsheet.ManagedBottomSheetController; import org.chromium.components.browser_ui.device_lock.DeviceLockActivityLauncher; import org.chromium.components.browser_ui.device_lock.DeviceLockActivityLauncherSupplier; +import org.chromium.components.browser_ui.util.ComposedBrowserControlsVisibilityDelegate; import org.chromium.components.browser_ui.widget.MenuOrKeyboardActionController; import org.chromium.components.browser_ui.widget.gesture.BackPressHandler; import org.chromium.components.browser_ui.widget.scrim.ScrimCoordinator; @@ -331,6 +332,7 @@ private FoldTransitionController mFoldTransitionController; private RestoreTabsFeatureHelper mRestoreTabsFeatureHelper; private @Nullable EdgeToEdgeController mE2eController; + private ComposedBrowserControlsVisibilityDelegate mAppBrowserControlsVisibilityDelegate; private @Nullable BoardingPassController mBoardingPassController; /** @@ -1789,6 +1791,16 @@ } /** + * @return {@link ComposedBrowserControlsVisibilityDelegate} object for tabbed activity. + */ + public ComposedBrowserControlsVisibilityDelegate getAppBrowserControlsVisibilityDelegate() { + if (mAppBrowserControlsVisibilityDelegate == null) { + mAppBrowserControlsVisibilityDelegate = new ComposedBrowserControlsVisibilityDelegate(); + } + return mAppBrowserControlsVisibilityDelegate; + } + + /** * Gets the browser controls manager, creates it unless already created. * @deprecated Instead, inject this directly to your constructor. If that's not possible, then * use {@link BrowserControlsManagerSupplier}.
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabModalDialogTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabModalDialogTest.java new file mode 100644 index 0000000..3737c71 --- /dev/null +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabModalDialogTest.java
@@ -0,0 +1,287 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +package org.chromium.chrome.browser.customtabs; + +import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation; + +import static org.hamcrest.Matchers.is; + +import android.content.Context; +import android.content.Intent; + +import androidx.test.filters.SmallTest; +import androidx.test.platform.app.InstrumentationRegistry; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Rule; +import org.junit.Test; +import org.junit.runner.RunWith; + +import org.chromium.base.library_loader.LibraryLoader; +import org.chromium.base.test.util.Batch; +import org.chromium.base.test.util.Criteria; +import org.chromium.base.test.util.CriteriaHelper; +import org.chromium.base.test.util.HistogramWatcher; +import org.chromium.cc.input.BrowserControlsState; +import org.chromium.chrome.browser.back_press.BackPressManager; +import org.chromium.chrome.browser.firstrun.FirstRunStatus; +import org.chromium.chrome.browser.flags.ChromeFeatureList; +import org.chromium.chrome.browser.tab.Tab; +import org.chromium.chrome.browser.ui.appmenu.AppMenuCoordinator; +import org.chromium.chrome.browser.ui.appmenu.AppMenuHandler; +import org.chromium.chrome.test.ChromeJUnit4ClassRunner; +import org.chromium.chrome.test.util.ChromeTabUtils; +import org.chromium.chrome.test.util.browser.Features; +import org.chromium.components.browser_ui.widget.gesture.BackPressHandler; +import org.chromium.content_public.browser.LoadUrlParams; +import org.chromium.content_public.browser.test.util.TestThreadUtils; +import org.chromium.content_public.browser.test.util.UiUtils; +import org.chromium.net.test.EmbeddedTestServer; +import org.chromium.ui.modaldialog.DialogDismissalCause; +import org.chromium.ui.modaldialog.ModalDialogManager; +import org.chromium.ui.modaldialog.ModalDialogProperties; +import org.chromium.ui.modelutil.PropertyModel; + +@Batch(Batch.PER_CLASS) +@RunWith(ChromeJUnit4ClassRunner.class) +public class CustomTabModalDialogTest { + + @Rule + public CustomTabActivityTestRule mCustomTabActivityTestRule = new CustomTabActivityTestRule(); + + private static final String TEST_PAGE = "/chrome/test/data/android/google.html"; + private static final String TEST_PAGE_2 = "/chrome/test/data/android/test.html"; + private String mTestPage; + private String mTestPage2; + private EmbeddedTestServer mTestServer; + + @Before + public void setUp() throws Exception { + TestThreadUtils.runOnUiThreadBlocking(() -> FirstRunStatus.setFirstRunFlowComplete(true)); + Context appContext = getInstrumentation().getTargetContext().getApplicationContext(); + mTestServer = EmbeddedTestServer.createAndStartServer(appContext); + mTestPage = mTestServer.getURL(TEST_PAGE); + mTestPage2 = mTestServer.getURL(TEST_PAGE_2); + LibraryLoader.getInstance().ensureInitialized(); + } + + @After + public void tearDown() { + TestThreadUtils.runOnUiThreadBlocking(() -> FirstRunStatus.setFirstRunFlowComplete(false)); + + // finish() is called on a non-UI thread by the testing harness. Must hide the menu + // first, otherwise the UI is manipulated on a non-UI thread. + TestThreadUtils.runOnUiThreadBlocking( + () -> { + if (getActivity() == null) return; + AppMenuCoordinator coordinator = + mCustomTabActivityTestRule.getAppMenuCoordinator(); + // CCT doesn't always have a menu (ex. in the media viewer). + if (coordinator == null) return; + AppMenuHandler handler = coordinator.getAppMenuHandler(); + if (handler != null) handler.hideAppMenu(); + }); + } + + private CustomTabActivity getActivity() { + return mCustomTabActivityTestRule.getActivity(); + } + + @Test + @SmallTest + @Features.EnableFeatures(ChromeFeatureList.CCT_TAB_MODAL_DIALOG) + public void testShowAndDismissTabModalDialog() throws InterruptedException { + Context context = getInstrumentation().getTargetContext().getApplicationContext(); + Intent intent = CustomTabsIntentTestUtils.createMinimalCustomTabIntent(context, mTestPage); + mCustomTabActivityTestRule.startCustomTabActivityWithIntent(intent); + + var visibilityDelegate = + mCustomTabActivityTestRule + .getActivity() + .getRootUiCoordinatorForTesting() + .getAppBrowserControlsVisibilityDelegate(); + + ModalDialogManager dialogManager = + mCustomTabActivityTestRule.getActivity().getModalDialogManagerSupplier().get(); + TestThreadUtils.runOnUiThreadBlocking( + () -> { + PropertyModel dialog = + new PropertyModel.Builder(ModalDialogProperties.ALL_KEYS) + .with(ModalDialogProperties.TITLE, "test") + .with( + ModalDialogProperties.POSITIVE_BUTTON_TEXT, + context.getString( + org.chromium.chrome.test.R.string.delete)) + .with( + ModalDialogProperties.NEGATIVE_BUTTON_TEXT, + context.getString( + org.chromium.chrome.test.R.string.cancel)) + .with( + ModalDialogProperties.CONTROLLER, + new ModalDialogProperties.Controller() { + @Override + public void onClick( + PropertyModel model, int buttonType) {} + + @Override + public void onDismiss( + PropertyModel model, int dismissalCause) {} + }) + .build(); + + dialogManager.showDialog(dialog, ModalDialogManager.ModalDialogType.TAB); + }); + + Assert.assertNotNull(visibilityDelegate.get()); + Assert.assertEquals( + "Browser Control should be SHOWN when dialog is being displayed.", + BrowserControlsState.SHOWN, + (int) visibilityDelegate.get()); + + TestThreadUtils.runOnUiThreadBlocking( + () -> dialogManager.dismissAllDialogs(DialogDismissalCause.DISMISSED_BY_NATIVE)); + + UiUtils.settleDownUI(InstrumentationRegistry.getInstrumentation()); + Assert.assertEquals( + "Browser Control State should be BOTH when dialog becomes hidden.", + BrowserControlsState.BOTH, + (int) visibilityDelegate.get()); + } + + @Test + @SmallTest + public void testNavigationDismissTabModalDialog() { + Context context = getInstrumentation().getTargetContext().getApplicationContext(); + Intent intent = CustomTabsIntentTestUtils.createMinimalCustomTabIntent(context, mTestPage); + mCustomTabActivityTestRule.startCustomTabActivityWithIntent(intent); + final Tab tab = mCustomTabActivityTestRule.getActivity().getActivityTab(); + + ModalDialogManager dialogManager = + mCustomTabActivityTestRule.getActivity().getModalDialogManagerSupplier().get(); + TestThreadUtils.runOnUiThreadBlocking( + () -> { + PropertyModel dialog = + new PropertyModel.Builder(ModalDialogProperties.ALL_KEYS) + .with(ModalDialogProperties.TITLE, "test") + .with( + ModalDialogProperties.POSITIVE_BUTTON_TEXT, + context.getString( + org.chromium.chrome.test.R.string.delete)) + .with( + ModalDialogProperties.NEGATIVE_BUTTON_TEXT, + context.getString( + org.chromium.chrome.test.R.string.cancel)) + .with( + ModalDialogProperties.CONTROLLER, + new ModalDialogProperties.Controller() { + @Override + public void onClick( + PropertyModel model, int buttonType) {} + + @Override + public void onDismiss( + PropertyModel model, int dismissalCause) {} + }) + .build(); + + dialogManager.showDialog(dialog, ModalDialogManager.ModalDialogType.TAB); + }); + + CriteriaHelper.pollUiThread(() -> dialogManager.isShowing()); + + TestThreadUtils.runOnUiThreadBlocking( + (Runnable) () -> tab.loadUrl(new LoadUrlParams(mTestPage2))); + ChromeTabUtils.waitForTabPageLoaded(tab, mTestPage2); + + Assert.assertTrue(tab.canGoBack()); + Assert.assertFalse(tab.canGoForward()); + + CriteriaHelper.pollUiThread(() -> !dialogManager.isShowing()); + } + + @Test + @SmallTest + @Features.DisableFeatures(ChromeFeatureList.BACK_GESTURE_REFACTOR) + public void testBackPressDismissTabModalDialog() { + Context context = getInstrumentation().getTargetContext().getApplicationContext(); + Intent intent = CustomTabsIntentTestUtils.createMinimalCustomTabIntent(context, mTestPage); + mCustomTabActivityTestRule.startCustomTabActivityWithIntent(intent); + final Tab tab = mCustomTabActivityTestRule.getActivity().getActivityTab(); + + ModalDialogManager dialogManager = + mCustomTabActivityTestRule.getActivity().getModalDialogManagerSupplier().get(); + + TestThreadUtils.runOnUiThreadBlocking( + (Runnable) () -> tab.loadUrl(new LoadUrlParams(mTestPage2))); + ChromeTabUtils.waitForTabPageLoaded(tab, mTestPage2); + + TestThreadUtils.runOnUiThreadBlocking( + () -> { + PropertyModel dialog = + new PropertyModel.Builder(ModalDialogProperties.ALL_KEYS) + .with(ModalDialogProperties.TITLE, "test") + .with( + ModalDialogProperties.POSITIVE_BUTTON_TEXT, + context.getString( + org.chromium.chrome.test.R.string.delete)) + .with( + ModalDialogProperties.NEGATIVE_BUTTON_TEXT, + context.getString( + org.chromium.chrome.test.R.string.cancel)) + .with( + ModalDialogProperties.CONTROLLER, + new ModalDialogProperties.Controller() { + @Override + public void onClick( + PropertyModel model, int buttonType) {} + + @Override + public void onDismiss( + PropertyModel model, int dismissalCause) {} + }) + .build(); + + dialogManager.showDialog(dialog, ModalDialogManager.ModalDialogType.TAB); + }); + CriteriaHelper.pollUiThread(() -> dialogManager.isShowing(), "Dialog should be displayed"); + + HistogramWatcher histogramWatcher = + HistogramWatcher.newSingleRecordWatcher( + "Android.BackPress.Intercept", + BackPressManager.getHistogramValueForTesting( + BackPressHandler.Type.TAB_MODAL_HANDLER)); + + TestThreadUtils.runOnUiThreadBlocking( + () -> { + mCustomTabActivityTestRule + .getActivity() + .getOnBackPressedDispatcher() + .onBackPressed(); + }); + + Assert.assertTrue("Should be able to navigate back after navigation", tab.canGoBack()); + Assert.assertFalse("Should be unable to navigate forward", tab.canGoForward()); + CriteriaHelper.pollInstrumentationThread( + () -> { + Criteria.checkThat( + "Tab should not be navigated when dialog is dismissed", + ChromeTabUtils.getUrlStringOnUiThread(getActivity().getActivityTab()), + is(mTestPage2)); + }); + + histogramWatcher.assertExpected("Dialog should be dismissed by back press"); + CriteriaHelper.pollUiThread( + () -> !dialogManager.isShowing(), "Dialog should be dismissed by back press"); + } + + @Test + @SmallTest + @Features.EnableFeatures(ChromeFeatureList.BACK_GESTURE_REFACTOR) + public void testBackPressDismissTabModalDialog_BackGestureRefactor() { + testBackPressDismissTabModalDialog(); + } +}
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/OWNERS b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/OWNERS index c8486c8..cc0884a9 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/OWNERS +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/OWNERS
@@ -1,2 +1,3 @@ file://chrome/android/java/src/org/chromium/chrome/browser/customtabs/OWNERS per-file CustomTabPrivacySandboxDialogTest.java=file://components/privacy_sandbox/OWNERS +per-file CustomTabModalDialogTest.java=file://ui/android/java/src/org/chromium/ui/modaldialog/OWNERS
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/identity_disc/IdentityDiscControllerTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/identity_disc/IdentityDiscControllerTest.java index 121d533d..df2ad3b6 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/identity_disc/IdentityDiscControllerTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/identity_disc/IdentityDiscControllerTest.java
@@ -35,7 +35,6 @@ import org.mockito.junit.MockitoRule; import org.mockito.quality.Strictness; -import org.chromium.base.Callback; import org.chromium.base.supplier.ObservableSupplier; import org.chromium.base.test.util.CommandLineFlags; import org.chromium.chrome.browser.feature_engagement.TrackerFactory; @@ -74,21 +73,6 @@ private static final String EMAIL = "email@gmail.com"; private static final String NAME = "Email Emailson"; private static final String FULL_NAME = NAME + ".full"; - private static final ObservableSupplier<Profile> EMPTY_PROFILE_SUPPLIER = - new ObservableSupplier<>() { - @Override - public Profile addObserver(Callback<Profile> obs) { - return null; - } - - @Override - public void removeObserver(Callback<Profile> obs) {} - - @Override - public Profile get() { - return null; - } - }; private final ChromeTabbedActivityTestRule mActivityTestRule = new ChromeTabbedActivityTestRule(); @@ -373,7 +357,7 @@ TrackerFactory.setTrackerForTests(mTracker); IdentityDiscController identityDiscController = new IdentityDiscController( - mActivityTestRule.getActivity(), mDispatcher, EMPTY_PROFILE_SUPPLIER); + mActivityTestRule.getActivity(), mDispatcher, mProfileSupplier); // If the button is tapped before the profile is set, the click shouldn't be recorded. identityDiscController.onClick(); @@ -397,7 +381,7 @@ ButtonDataProvider.ButtonDataObserver observer) { IdentityDiscController controller = new IdentityDiscController( - mActivityTestRule.getActivity(), mDispatcher, EMPTY_PROFILE_SUPPLIER); + mActivityTestRule.getActivity(), mDispatcher, mProfileSupplier); controller.addObserver(observer); return controller;
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/page_info/PageInfoViewTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/page_info/PageInfoViewTest.java index f194eba..84f4a1c9 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/page_info/PageInfoViewTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/page_info/PageInfoViewTest.java
@@ -632,6 +632,7 @@ @Test @MediumTest @Feature({"RenderTest"}) + @DisabledTest(message = "https://crbug.com/1510968") public void testShowCookiesSubpageUserBypassOn() throws IOException { setThirdPartyCookieBlocking(CookieControlsMode.BLOCK_THIRD_PARTY); loadUrlAndOpenPageInfo(mTestServerRule.getServer().getURL(sSimpleHtml)); @@ -658,6 +659,7 @@ @Test @MediumTest @Feature({"RenderTest"}) + @DisabledTest(message = "https://crbug.com/1510968") public void testShowCookiesSubpageTrackingProtection() throws IOException { enableTrackingProtection(); setThirdPartyCookieBlocking(CookieControlsMode.BLOCK_THIRD_PARTY); @@ -685,6 +687,7 @@ @Test @MediumTest @Feature({"RenderTest"}) + @DisabledTest(message = "https://crbug.com/1510968") public void testShowCookiesSubpageTrackingProtectionBlockAll() throws IOException { enableTrackingProtection(); blockAll3PC();
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhoneTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhoneTest.java index 327dac1..a3a18cd 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhoneTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhoneTest.java
@@ -50,8 +50,7 @@ import org.mockito.Mockito; import org.mockito.MockitoAnnotations; -import org.chromium.base.Callback; -import org.chromium.base.supplier.ObservableSupplier; +import org.chromium.base.supplier.ObservableSupplierImpl; import org.chromium.base.supplier.OneshotSupplierImpl; import org.chromium.base.test.params.ParameterAnnotations; import org.chromium.base.test.params.ParameterizedRunner; @@ -1126,21 +1125,7 @@ private static class TestControlsVisibilityDelegate extends BrowserStateBrowserControlsVisibilityDelegate { public TestControlsVisibilityDelegate() { - super( - new ObservableSupplier<Boolean>() { - @Override - public Boolean addObserver(Callback<Boolean> obs) { - return false; - } - - @Override - public void removeObserver(Callback<Boolean> obs) {} - - @Override - public Boolean get() { - return false; - } - }); + super(new ObservableSupplierImpl<>(false)); } } }
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebApkActivityTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebApkActivityTest.java index 74ba777..f9f4e2aa 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebApkActivityTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebApkActivityTest.java
@@ -14,6 +14,7 @@ import androidx.test.filters.LargeTest; import androidx.test.runner.lifecycle.Stage; +import org.junit.Assert; import org.junit.Before; import org.junit.Rule; import org.junit.Test; @@ -22,6 +23,7 @@ import org.chromium.base.ContextUtils; import org.chromium.base.test.util.ApplicationTestUtils; import org.chromium.base.test.util.CommandLineFlags; +import org.chromium.base.test.util.CriteriaHelper; import org.chromium.base.test.util.Feature; import org.chromium.cc.input.BrowserControlsState; import org.chromium.chrome.browser.ChromeTabbedActivity; @@ -34,9 +36,14 @@ import org.chromium.chrome.test.ChromeJUnit4ClassRunner; import org.chromium.chrome.test.util.ChromeTabUtils; import org.chromium.chrome.test.util.browser.webapps.WebApkIntentDataProviderBuilder; +import org.chromium.components.permissions.PermissionDialogController; import org.chromium.content_public.browser.test.util.TestThreadUtils; +import org.chromium.net.test.EmbeddedTestServer; +import org.chromium.ui.modaldialog.ModalDialogManager; import org.chromium.webapk.lib.common.WebApkConstants; +import java.util.concurrent.TimeoutException; + /** Tests for WebAPK {@link WebappActivity}. */ @RunWith(ChromeJUnit4ClassRunner.class) @CommandLineFlags.Add({ChromeSwitches.DISABLE_FIRST_RUN_EXPERIENCE}) @@ -124,6 +131,26 @@ ChromeActivityTestRule.waitFor(WebappActivity.class); } + /** Test a permission dialog can be correctly presented. */ + @Test + @LargeTest + public void testShowPermissionPrompt() throws TimeoutException { + EmbeddedTestServer server = mActivityTestRule.getEmbeddedTestServerRule().getServer(); + String url = server.getURL("/content/test/data/android/permission_navigation.html"); + String baseUrl = server.getURL("/content/test/data/android/"); + WebappActivity activity = + mActivityTestRule.startWebApkActivity(createIntentDataProvider(url, baseUrl)); + mActivityTestRule.runJavaScriptCodeInCurrentTab("requestGeolocationPermission()"); + CriteriaHelper.pollUiThread( + () -> PermissionDialogController.getInstance().isDialogShownForTest(), + "Permission prompt did not appear in allotted time"); + Assert.assertEquals( + "Only App modal dialog is supported on web apk", + activity.getModalDialogManager() + .getPresenterForTest(ModalDialogManager.ModalDialogType.APP), + activity.getModalDialogManager().getCurrentPresenterForTest()); + } + private BrowserServicesIntentDataProvider createIntentDataProvider( String startUrl, String scopeUrl) { WebApkIntentDataProviderBuilder intentDataProviderBuilder =
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappNavigationTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappNavigationTest.java index 62cc2f7..4852f47 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappNavigationTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappNavigationTest.java
@@ -22,6 +22,7 @@ import androidx.test.platform.app.InstrumentationRegistry; import org.hamcrest.Matchers; +import org.junit.Assert; import org.junit.Before; import org.junit.Rule; import org.junit.Test; @@ -62,14 +63,19 @@ import org.chromium.chrome.test.util.browser.contextmenu.ContextMenuUtils; import org.chromium.chrome.test.util.browser.webapps.WebappTestPage; import org.chromium.components.browser_ui.styles.ChromeColors; +import org.chromium.components.permissions.PermissionDialogController; import org.chromium.content_public.browser.test.NativeLibraryTestUtils; import org.chromium.content_public.browser.test.util.DOMUtils; import org.chromium.content_public.browser.test.util.TestThreadUtils; import org.chromium.content_public.common.ContentSwitches; import org.chromium.net.test.EmbeddedTestServer; import org.chromium.ui.base.PageTransition; +import org.chromium.ui.modaldialog.ModalDialogManager; import org.chromium.ui.test.util.UiRestriction; +import java.util.concurrent.ExecutionException; +import java.util.concurrent.TimeoutException; + /** Tests web navigations originating from a WebappActivity. */ @RunWith(ChromeJUnit4ClassRunner.class) @DoNotBatch(reason = "tests run on startup.") @@ -419,6 +425,50 @@ ChromeTabUtils.waitForTabPageLoaded(activity.getActivityTab(), initialInScopeUrl); } + /** Test a permission dialog can be correctly presented and dismissed by navigation. */ + @Test + @LargeTest + @Feature({"Webapps"}) + public void testShowPermissionPrompt() throws TimeoutException, ExecutionException { + Intent launchIntent = mActivityTestRule.createIntent(); + mActivityTestRule.addTwaExtrasToIntent(launchIntent); + + WebappActivity activity = + runWebappActivityAndWaitForIdleWithUrl( + launchIntent, + mActivityTestRule + .getTestServer() + .getURL("/content/test/data/android/permission_navigation.html")); + mActivityTestRule.runJavaScriptCodeInCurrentTab("requestGeolocationPermission()"); + CriteriaHelper.pollUiThread( + () -> PermissionDialogController.getInstance().isDialogShownForTest(), + "Permission prompt did not appear in allotted time"); + Assert.assertEquals( + "Only App modal dialog is supported on web apk", + activity.getModalDialogManager() + .getPresenterForTest(ModalDialogManager.ModalDialogType.APP), + activity.getModalDialogManager().getCurrentPresenterForTest()); + // Launch a new page, which should be in CCT + mActivityTestRule.runJavaScriptCodeInCurrentTab("navigate()"); + CriteriaHelper.pollUiThread( + () -> !PermissionDialogController.getInstance().isDialogShownForTest(), + "Permission prompt is not dismissed."); + + // Toolbar with the close button should be visible. + WebappActivityTestRule.assertToolbarShownMaybeHideable(activity); + + // Navigate back to in-scope through a close button. + TestThreadUtils.runOnUiThreadBlocking( + () -> + activity.getToolbarManager() + .getToolbarLayoutForTesting() + .findViewById(R.id.close_button) + .callOnClick()); + CriteriaHelper.pollUiThread( + () -> !PermissionDialogController.getInstance().isDialogShownForTest(), + "Permission prompt is not dismissed."); + } + private WebappActivity runWebappActivityAndWaitForIdle(Intent intent) { return runWebappActivityAndWaitForIdleWithUrl( intent, WebappTestPage.getServiceWorkerUrl(mActivityTestRule.getTestServer()));
diff --git a/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/EngagementSignalsHandlerUnitTest.java b/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/EngagementSignalsHandlerUnitTest.java index 5c290fa..f683cbe1 100644 --- a/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/EngagementSignalsHandlerUnitTest.java +++ b/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/EngagementSignalsHandlerUnitTest.java
@@ -31,16 +31,13 @@ import org.chromium.base.test.BaseRobolectricTestRunner; import org.chromium.chrome.browser.customtabs.CustomTabsConnection; import org.chromium.chrome.browser.customtabs.content.TabObserverRegistrar.CustomTabTabObserver; -import org.chromium.chrome.browser.flags.ChromeFeatureList; import org.chromium.chrome.browser.privacy.settings.PrivacyPreferencesManager; import org.chromium.chrome.browser.privacy.settings.PrivacyPreferencesManager.Observer; import org.chromium.chrome.browser.privacy.settings.PrivacyPreferencesManagerImpl; import org.chromium.chrome.test.util.browser.Features; -import org.chromium.chrome.test.util.browser.Features.EnableFeatures; /** Unit tests for {@link EngagementSignalsHandler}. */ @RunWith(BaseRobolectricTestRunner.class) -@EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public class EngagementSignalsHandlerUnitTest { @Rule public Features.JUnitProcessor processor = new Features.JUnitProcessor(); @Rule public MockitoRule mMockitoRule = MockitoJUnit.rule();
diff --git a/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/EngagementSignalsInitialScrollObserverUnitTest.java b/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/EngagementSignalsInitialScrollObserverUnitTest.java index 11251a1..59ac8462 100644 --- a/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/EngagementSignalsInitialScrollObserverUnitTest.java +++ b/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/EngagementSignalsInitialScrollObserverUnitTest.java
@@ -40,10 +40,7 @@ /** Unit tests for {@link EngagementSignalsInitialScrollObserver}. */ @RunWith(BaseRobolectricTestRunner.class) @Config(manifest = Config.NONE) -@EnableFeatures({ - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS, - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL -}) +@EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS}) public class EngagementSignalsInitialScrollObserverUnitTest { private static final int SCROLL_EXTENT = 100;
diff --git a/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/RealtimeEngagementSignalObserverUnitTest.java b/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/RealtimeEngagementSignalObserverUnitTest.java index 8d11db5..6cfd2a5 100644 --- a/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/RealtimeEngagementSignalObserverUnitTest.java +++ b/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/RealtimeEngagementSignalObserverUnitTest.java
@@ -20,10 +20,9 @@ import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; -import static org.chromium.cc.mojom.RootScrollOffsetUpdateFrequency.NONE; import static org.chromium.cc.mojom.RootScrollOffsetUpdateFrequency.ON_SCROLL_END; +import static org.chromium.chrome.browser.customtabs.content.RealtimeEngagementSignalObserver.DEFAULT_AFTER_SCROLL_END_THRESHOLD_MS; import static org.chromium.chrome.browser.customtabs.content.RealtimeEngagementSignalObserver.REAL_VALUES; -import static org.chromium.chrome.browser.customtabs.content.RealtimeEngagementSignalObserver.TIME_CAN_UPDATE_AFTER_END; import android.graphics.Point; import android.os.Bundle; @@ -57,7 +56,6 @@ import org.chromium.chrome.browser.tab.TabHidingType; import org.chromium.chrome.browser.tab.TabObserver; import org.chromium.chrome.test.util.browser.Features; -import org.chromium.chrome.test.util.browser.Features.DisableFeatures; import org.chromium.chrome.test.util.browser.Features.EnableFeatures; import org.chromium.content.browser.GestureListenerManagerImpl; import org.chromium.content.browser.RenderCoordinatesImpl; @@ -73,10 +71,7 @@ /** Unit test for {@link RealtimeEngagementSignalObserver}. */ @RunWith(BaseRobolectricTestRunner.class) @Config(shadows = {ShadowSystemClock.class}) -@EnableFeatures({ - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS, - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL -}) +@EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS}) public class RealtimeEngagementSignalObserverUnitTest { @Rule public final CustomTabActivityContentTestEnvironment env = @@ -124,16 +119,8 @@ } @Test - @DisableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) - public void addsListenersForSignalsIfFeatureIsEnabled() { - initializeTabForTest(); - - verify(mGestureListenerManagerImpl).addListener(any(GestureStateListener.class), eq(NONE)); - } - - @Test public void addsListenersForSignalsIfFeatureIsEnabled_alternativeImpl() { - setFeatureParams(null, 100); + setFeatureParams(null); initializeTabForTest(); verify(mGestureListenerManagerImpl) @@ -559,7 +546,7 @@ @Test public void sendsFalseForScrollDirectionIfSendingFakeValues() { - setFeatureParams(false, null); + setFeatureParams(false); initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(); @@ -583,7 +570,7 @@ @Test public void sendsZeroForMaxScrollSignalsIfSendingFakeValues() { - setFeatureParams(false, null); + setFeatureParams(false); initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(); @@ -625,7 +612,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void sendsSignalWithAlternativeImpl_updateBeforeEnd() { initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(ON_SCROLL_END); @@ -643,9 +629,8 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void sendsSignalWithAlternativeImpl_updateAfterEnd() { - setFeatureParams(null, 25); + setFeatureParams(null); initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(ON_SCROLL_END); @@ -668,28 +653,8 @@ } @Test - @DisableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) - public void doesNotSendSignalUpdateAfterEndWithAlternativeImplDisabled() { - initializeTabForTest(); - GestureStateListener listener = captureGestureStateListener(NONE); - - // Start by scrolling down. - listener.onScrollStarted(0, SCROLL_EXTENT, false); - // End scrolling. - listener.onScrollEnded(0, SCROLL_EXTENT); - // Send the signal for 24% 10ms after the scroll ended. - advanceTime(10); - when(mRenderCoordinatesImpl.getScrollYPixInt()).thenReturn(24); - listener.onScrollOffsetOrExtentChanged(24, SCROLL_EXTENT); - // We shouldn't make any call. - verify(mEngagementSignalsCallback, never()) - .onGreatestScrollPercentageIncreased(anyInt(), any(Bundle.class)); - } - - @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void doesNotSendLowerPercentWithAlternativeImpl() { - setFeatureParams(null, 20); + setFeatureParams(null); initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(ON_SCROLL_END); @@ -716,9 +681,8 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void doNotSendSignalWithAlternativeImplAfterThreshold() { - setFeatureParams(null, 10); + setFeatureParams(null); initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(ON_SCROLL_END); @@ -726,8 +690,8 @@ listener.onScrollStarted(59, SCROLL_EXTENT, false); // End scrolling. listener.onScrollEnded(59, SCROLL_EXTENT); - // Send the signal for 59% 18ms after the scroll ended. - advanceTime(18); + // Send the signal for 59% 18ms outside the threshold. + advanceTime(DEFAULT_AFTER_SCROLL_END_THRESHOLD_MS + 18); when(mRenderCoordinatesImpl.getScrollYPixInt()).thenReturn(59); listener.onScrollOffsetOrExtentChanged(59, SCROLL_EXTENT); // We shouldn't make a call since the call was outside the threshold. @@ -736,9 +700,8 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void doNotSendSignalWithAlternativeImplIfScrollStartReceived() { - setFeatureParams(null, 25); + setFeatureParams(null); initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(ON_SCROLL_END); @@ -758,7 +721,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void sendOnSessionEnded_HadInteraction() { initializeTabForTest(); doReturn(false).when(mTabInteractionRecorder).didGetUserInteraction(); @@ -778,7 +740,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void sendOnSessionEnded_HadNoInteraction() { initializeTabForTest(); doReturn(false).when(mTabInteractionRecorder).didGetUserInteraction(); @@ -796,7 +757,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void doNotSendOnSessionEndedWhenSuspended() { initializeTabForTest(); mEngagementSignalObserver.suppressNextSessionEndedCall(); @@ -818,7 +778,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void pauseAndUnpauseSignalsOnPageWithTextFragment() { initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(ON_SCROLL_END); @@ -858,7 +817,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void doesNotSendSignalsBeforeDownScroll() { initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(ON_SCROLL_END); @@ -885,7 +843,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void doesNotSendSignalsBeforeDownScroll_AfterNavigation() { initializeTabForTest(); GestureStateListener listener = captureGestureStateListener(ON_SCROLL_END); @@ -919,24 +876,6 @@ } @Test - @DisableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) - public void sendInitialOffsetUpdate_AltImplDisabled() { - initializeTabForTest(/* hadScrollDown= */ true); - // When the alternative impl flag is enabled, the listener should be added with `NONE`. - var listener = captureGestureStateListener(NONE); - - // Simulate renderer sending the offset update. - when(mRenderCoordinatesImpl.getScrollYPixInt()).thenReturn(42); - listener.onScrollOffsetOrExtentChanged(42, SCROLL_EXTENT); - - // We should get a notification since we initialized the observer class with true for - // hadScrollDown. - verify(mEngagementSignalsCallback) - .onGreatestScrollPercentageIncreased(eq(40), any(Bundle.class)); - } - - @Test - @EnableFeatures({ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL}) public void sendInitialOffsetUpdate_AltImplEnabled() { initializeTabForTest(/* hadScrollDown= */ true); // When the alternative impl flag is enabled, the listener should be added with @@ -959,27 +898,16 @@ /** * @param realValues CCT_REAL_TIME_ENGAGEMENT_SIGNALS real_values. - * @param threshold CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL time_can_update_after_end. */ - private void setFeatureParams(Boolean realValues, Integer threshold) { - if (realValues == null && threshold == null) return; + private void setFeatureParams(Boolean realValues) { + if (realValues == null) return; TestValues testValues = new TestValues(); testValues.addFeatureFlagOverride(ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS, true); - testValues.addFeatureFlagOverride( - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL, true); - if (realValues != null) { - testValues.addFieldTrialParamOverride( - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS, - REAL_VALUES, - realValues.toString()); - } - if (threshold != null) { - testValues.addFieldTrialParamOverride( - ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL, - TIME_CAN_UPDATE_AFTER_END, - Integer.toString(threshold)); - } + testValues.addFieldTrialParamOverride( + ChromeFeatureList.CCT_REAL_TIME_ENGAGEMENT_SIGNALS, + REAL_VALUES, + realValues.toString()); FeatureList.setTestValues(testValues); }
diff --git a/chrome/android/junit/src/org/chromium/chrome/browser/messages/ChromeMessageQueueMediatorTest.java b/chrome/android/junit/src/org/chromium/chrome/browser/messages/ChromeMessageQueueMediatorTest.java index 63b98b9..2b5f248f 100644 --- a/chrome/android/junit/src/org/chromium/chrome/browser/messages/ChromeMessageQueueMediatorTest.java +++ b/chrome/android/junit/src/org/chromium/chrome/browser/messages/ChromeMessageQueueMediatorTest.java
@@ -29,7 +29,6 @@ import org.chromium.base.Callback; import org.chromium.base.UserDataHost; -import org.chromium.base.supplier.ObservableSupplier; import org.chromium.base.supplier.ObservableSupplierImpl; import org.chromium.base.supplier.OneshotSupplierImpl; import org.chromium.base.test.BaseRobolectricTestRunner; @@ -170,20 +169,7 @@ when(mBrowserControlsManager.getBrowserVisibilityDelegate()) .thenReturn( new BrowserStateBrowserControlsVisibilityDelegate( - new ObservableSupplier<Boolean>() { - @Override - public Boolean addObserver(Callback<Boolean> obs) { - return null; - } - - @Override - public void removeObserver(Callback<Boolean> obs) {} - - @Override - public Boolean get() { - return false; - } - })); + new ObservableSupplierImpl<>(false))); mMediator = new ChromeMessageQueueMediator( mBrowserControlsManager,
diff --git a/chrome/app/generated_resources.grd b/chrome/app/generated_resources.grd index 9e1f814..2720fab 100644 --- a/chrome/app/generated_resources.grd +++ b/chrome/app/generated_resources.grd
@@ -9101,7 +9101,7 @@ Right-click on the tab group name to edit this group or click to collapse </message> <message name="IDS_TAB_ORGANIZATION_SUCCESS_IPH_SCREENREADER" desc="The screen reader text of the IPH describing how to interact with a tab group resulting from tab organization." translateable="false"> - Select the tab group and activate the context menu to edit, or select the tab group and press enter to collapse + Select the tab group and activate the context menu to edit </message> <!-- Strings for intent picker --> @@ -10695,7 +10695,7 @@ Show me how </message> <message name="IDS_TAB_ORGANIZATION_LEARN_MORE" desc="The actionable text in the tab organization UI results state for getting more information" translateable="false"> - Learn more + Learn more about using AI tools </message> <!-- Strings for Window Titles in Menus -->
diff --git a/chrome/app/os_settings_strings.grdp b/chrome/app/os_settings_strings.grdp index ef8ae3be..3212322 100644 --- a/chrome/app/os_settings_strings.grdp +++ b/chrome/app/os_settings_strings.grdp
@@ -2820,6 +2820,9 @@ <message name="IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_DESCRIPTION" desc="Description of dialog that allows the user to input shortcuts that will be used as the action on a button."> Press 1-4 modifier keys (ctrl, alt, shift, search, or launcher) and 1 more key. You can also select a single key. </message> + <message name="IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_CHANGE" desc="Label of change button on dialogs in customize device buttons pages."> + Change + </message> <message name="IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_CANCEL" desc="Label of cancel button on dialogs in customize device buttons pages."> Cancel </message>
diff --git a/chrome/app/os_settings_strings_grdp/IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_CHANGE.png.sha1 b/chrome/app/os_settings_strings_grdp/IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_CHANGE.png.sha1 new file mode 100644 index 0000000..68714e9 --- /dev/null +++ b/chrome/app/os_settings_strings_grdp/IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_CHANGE.png.sha1
@@ -0,0 +1 @@ +ad2e40375a43a66d949ac408a58956103309f535 \ No newline at end of file
diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn index 599460f..926a9b6 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn
@@ -317,6 +317,8 @@ "component_updater/mei_preload_component_installer.h", "component_updater/network_quality_observer.cc", "component_updater/network_quality_observer.h", + "component_updater/optimization_guide_on_device_model_installer.cc", + "component_updater/optimization_guide_on_device_model_installer.h", "component_updater/payload_test_component_installer.cc", "component_updater/payload_test_component_installer.h", "component_updater/pki_metadata_component_installer.cc",
diff --git a/chrome/browser/about_flags.cc b/chrome/browser/about_flags.cc index f24e762..0ab4fe45 100644 --- a/chrome/browser/about_flags.cc +++ b/chrome/browser/about_flags.cc
@@ -138,7 +138,6 @@ #include "components/performance_manager/public/features.h" #include "components/permissions/features.h" #include "components/policy/core/common/features.h" -#include "components/power_bookmarks/core/flag_descriptions.h" #include "components/power_bookmarks/core/power_bookmark_features.h" #include "components/privacy_sandbox/privacy_sandbox_features.h" #include "components/query_tiles/switches.h" @@ -574,26 +573,6 @@ {"Send fake values", kCCTRealTimeEngagementSignalsParamFakeValues, std::size(kCCTRealTimeEngagementSignalsParamFakeValues), nullptr}}; -const FeatureEntry::FeatureParam - kCCTRealTimeEngagementSignalsAlternativeImplParam300[] = { - {"time_can_update_after_end", "300"} // 300ms -}; -const FeatureEntry::FeatureParam - kCCTRealTimeEngagementSignalsAlternativeImplParam100[] = { - {"time_can_update_after_end", "100"} // 100ms -}; - -const FeatureEntry::FeatureVariation - kCCTRealTimeEngagementSignalsAlternativeImplVariations[] = { - {"Allow 300ms for scroll updates after scroll-end", - kCCTRealTimeEngagementSignalsAlternativeImplParam300, - std::size(kCCTRealTimeEngagementSignalsAlternativeImplParam300), - nullptr}, - {"Allow 100ms for scroll updates after scroll-end", - kCCTRealTimeEngagementSignalsAlternativeImplParam100, - std::size(kCCTRealTimeEngagementSignalsAlternativeImplParam100), - nullptr}}; - const FeatureEntry::Choice kReaderModeHeuristicsChoices[] = { {flags_ui::kGenericExperimentChoiceDefault, "", ""}, {flag_descriptions::kReaderModeHeuristicsMarkup, @@ -5325,10 +5304,6 @@ flag_descriptions::kShareSheetMigrationAndroidName, flag_descriptions::kShareSheetMigrationAndroidDescription, kOsAndroid, FEATURE_VALUE_TYPE(chrome::android::kShareSheetMigrationAndroid)}, - {"share-sheet-custom-actions-polish", - flag_descriptions::kShareSheetCustomActionsPolishName, - flag_descriptions::kShareSheetCustomActionsPolishDescription, kOsAndroid, - FEATURE_VALUE_TYPE(chrome::android::kShareSheetCustomActionsPolish)}, #endif // BUILDFLAG(IS_ANDROID) {"disallow-doc-written-script-loads", @@ -7388,14 +7363,6 @@ chrome::android::kCCTRealTimeEngagementSignals, kCCTRealTimeEngagementSignalsVariations, "CCTRealTimeEngagementSignals")}, - {"cct-real-time-engagement-signals-alternative-impl", - flag_descriptions::kCCTRealTimeEngagementSignalsAlternativeImplName, - flag_descriptions::kCCTRealTimeEngagementSignalsAlternativeImplDescription, - kOsAndroid, - FEATURE_WITH_PARAMS_VALUE_TYPE( - chrome::android::kCCTRealTimeEngagementSignalsAlternativeImpl, - kCCTRealTimeEngagementSignalsAlternativeImplVariations, - "CCTRealTimeEngagementSignalsAlternativeImpl")}, #endif #if BUILDFLAG(IS_ANDROID) @@ -7912,16 +7879,19 @@ flag_descriptions::kEnableFencedFramesDescription, kOsAll, FEATURE_VALUE_TYPE(blink::features::kFencedFrames)}, + {"enable-fenced-frames-cross-origin-automatic-beacons", + flag_descriptions::kEnableFencedFramesCrossOriginAutomaticBeaconsName, + flag_descriptions:: + kEnableFencedFramesCrossOriginAutomaticBeaconsDescription, + kOsAll, + FEATURE_VALUE_TYPE( + blink::features::kFencedFramesCrossOriginAutomaticBeacons)}, + {"enable-fenced-frames-developer-mode", flag_descriptions::kEnableFencedFramesDeveloperModeName, flag_descriptions::kEnableFencedFramesDeveloperModeDescription, kOsAll, FEATURE_VALUE_TYPE(blink::features::kFencedFramesDefaultMode)}, - {"enable-fenced-frames-M120-features", - flag_descriptions::kEnableFencedFramesM120FeaturesName, - flag_descriptions::kEnableFencedFramesM120FeaturesDescription, kOsAll, - FEATURE_VALUE_TYPE(blink::features::kFencedFramesM120FeaturesPart2)}, - {"enable-fenced-frames-reporting-attestations-changes", flag_descriptions::kEnableFencedFramesReportingAttestationsChangeName, flag_descriptions:: @@ -10223,14 +10193,6 @@ FEATURE_VALUE_TYPE(ash::features::kEnablePerDeskZOrder)}, #endif // BUILDFLAG(IS_CHROMEOS_ASH) -#if !BUILDFLAG(IS_ANDROID) - {"simplified-bookmark-save-flow", - power_bookmarks::flag_descriptions::kSimplifiedBookmarkSaveFlowName, - power_bookmarks::flag_descriptions::kSimplifiedBookmarkSaveFlowName, - kOsDesktop, - FEATURE_VALUE_TYPE(power_bookmarks::kSimplifiedBookmarkSaveFlow)}, -#endif - #if BUILDFLAG(IS_CHROMEOS_ASH) {"gallery-app-pdf-edit-notification", flag_descriptions::kGalleryAppPdfEditNotificationName,
diff --git a/chrome/browser/accessibility/DEPS b/chrome/browser/accessibility/DEPS index 8ae5b94..81b2219 100644 --- a/chrome/browser/accessibility/DEPS +++ b/chrome/browser/accessibility/DEPS
@@ -10,5 +10,6 @@ specific_include_rules = { 'accessibility_extension_api_ash.cc': [ "+services/accessibility/public/mojom/assistive_technology_type.mojom.h", + "+ash/accessibility/accessibility_controller_impl.h", ] } \ No newline at end of file
diff --git a/chrome/browser/accessibility/accessibility_extension_api_ash.cc b/chrome/browser/accessibility/accessibility_extension_api_ash.cc index 43d928d15..a4354378 100644 --- a/chrome/browser/accessibility/accessibility_extension_api_ash.cc +++ b/chrome/browser/accessibility/accessibility_extension_api_ash.cc
@@ -9,7 +9,7 @@ #include <set> #include <vector> -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/public/cpp/accessibility_controller_enums.h" #include "ash/public/cpp/accessibility_focus_ring_info.h" #include "ash/public/cpp/event_rewriter_controller.h"
diff --git a/chrome/browser/ash/accessibility/accessibility_manager.cc b/chrome/browser/ash/accessibility/accessibility_manager.cc index fb838aac..bf5bc271 100644 --- a/chrome/browser/ash/accessibility/accessibility_manager.cc +++ b/chrome/browser/ash/accessibility/accessibility_manager.cc
@@ -9,6 +9,7 @@ #include <utility> +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/accessibility/autoclick/autoclick_controller.h" #include "ash/accessibility/sticky_keys/sticky_keys_controller.h" #include "ash/color_enhancement/color_enhancement_controller.h" @@ -16,7 +17,6 @@ #include "ash/constants/ash_pref_names.h" #include "ash/constants/ash_switches.h" #include "ash/public/cpp/accelerators.h" -#include "ash/public/cpp/accessibility_controller.h" #include "ash/public/cpp/accessibility_controller_enums.h" #include "ash/public/cpp/accessibility_focus_ring_controller.h" #include "ash/public/cpp/accessibility_focus_ring_info.h"
diff --git a/chrome/browser/ash/accessibility/chromevox_panel.cc b/chrome/browser/ash/accessibility/chromevox_panel.cc index 544a67f..2ecb342 100644 --- a/chrome/browser/ash/accessibility/chromevox_panel.cc +++ b/chrome/browser/ash/accessibility/chromevox_panel.cc
@@ -6,7 +6,7 @@ #include <memory> -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/public/cpp/accessibility_controller_enums.h" #include "base/memory/raw_ptr.h" #include "chrome/browser/ash/accessibility/accessibility_manager.h"
diff --git a/chrome/browser/ash/accessibility/select_to_speak_event_handler_delegate_impl.cc b/chrome/browser/ash/accessibility/select_to_speak_event_handler_delegate_impl.cc index 41442e1..00745d5 100644 --- a/chrome/browser/ash/accessibility/select_to_speak_event_handler_delegate_impl.cc +++ b/chrome/browser/ash/accessibility/select_to_speak_event_handler_delegate_impl.cc
@@ -6,7 +6,7 @@ #include <memory> -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "chrome/browser/ash/accessibility/accessibility_manager.h" #include "chrome/browser/ash/accessibility/event_handler_common.h" #include "chrome/common/extensions/extension_constants.h"
diff --git a/chrome/browser/ash/accessibility/service/autoclick_client_impl.cc b/chrome/browser/ash/accessibility/service/autoclick_client_impl.cc index e17e617..73462c5 100644 --- a/chrome/browser/ash/accessibility/service/autoclick_client_impl.cc +++ b/chrome/browser/ash/accessibility/service/autoclick_client_impl.cc
@@ -4,7 +4,7 @@ #include "chrome/browser/ash/accessibility/service/autoclick_client_impl.h" -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "base/debug/stack_trace.h" #include "chrome/browser/ash/accessibility/accessibility_manager.h" #include "mojo/public/cpp/bindings/pending_receiver.h"
diff --git a/chrome/browser/ash/accessibility/service/user_interface_impl.cc b/chrome/browser/ash/accessibility/service/user_interface_impl.cc index 5d73bb65..1c5f403 100644 --- a/chrome/browser/ash/accessibility/service/user_interface_impl.cc +++ b/chrome/browser/ash/accessibility/service/user_interface_impl.cc
@@ -4,7 +4,7 @@ #include "chrome/browser/ash/accessibility/service/user_interface_impl.h" -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/public/cpp/accessibility_focus_ring_info.h" #include "chrome/browser/ash/accessibility/accessibility_manager.h" #include "content/public/common/color_parser.h"
diff --git a/chrome/browser/ash/accessibility/spoken_feedback_browsertest.cc b/chrome/browser/ash/accessibility/spoken_feedback_browsertest.cc index dec55888..4229de2 100644 --- a/chrome/browser/ash/accessibility/spoken_feedback_browsertest.cc +++ b/chrome/browser/ash/accessibility/spoken_feedback_browsertest.cc
@@ -12,7 +12,6 @@ #include "ash/constants/ash_switches.h" #include "ash/display/display_configuration_controller.h" #include "ash/public/cpp/accelerators.h" -#include "ash/public/cpp/accessibility_controller.h" #include "ash/public/cpp/event_rewriter_controller.h" #include "ash/public/cpp/screen_backlight.h" #include "ash/public/cpp/shelf_model.h"
diff --git a/chrome/browser/ash/app_mode/kiosk_system_session.cc b/chrome/browser/ash/app_mode/kiosk_system_session.cc index 75960ea..2e8b9bb 100644 --- a/chrome/browser/ash/app_mode/kiosk_system_session.cc +++ b/chrome/browser/ash/app_mode/kiosk_system_session.cc
@@ -6,7 +6,7 @@ #include <memory> #include <optional> -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "base/memory/weak_ptr.h" #include "base/notreached.h" #include "base/scoped_observation.h"
diff --git a/chrome/browser/ash/crosapi/embedded_accessibility_helper_client_ash.cc b/chrome/browser/ash/crosapi/embedded_accessibility_helper_client_ash.cc index b54ca7ba..6763e13 100644 --- a/chrome/browser/ash/crosapi/embedded_accessibility_helper_client_ash.cc +++ b/chrome/browser/ash/crosapi/embedded_accessibility_helper_client_ash.cc
@@ -6,7 +6,7 @@ #include <string> -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "chrome/browser/ash/accessibility/accessibility_manager.h" #include "chromeos/crosapi/mojom/embedded_accessibility_helper.mojom.h"
diff --git a/chrome/browser/ash/crosapi/test_controller_ash.cc b/chrome/browser/ash/crosapi/test_controller_ash.cc index 5789db1..8504dd6 100644 --- a/chrome/browser/ash/crosapi/test_controller_ash.cc +++ b/chrome/browser/ash/crosapi/test_controller_ash.cc
@@ -11,7 +11,6 @@ #include "ash/accessibility/accessibility_controller_impl.h" #include "ash/app_list/app_list_controller_impl.h" #include "ash/constants/ash_pref_names.h" -#include "ash/public/cpp/accessibility_controller.h" #include "ash/public/cpp/shelf_item_delegate.h" #include "ash/public/cpp/shelf_model.h" #include "ash/public/cpp/tablet_mode.h"
diff --git a/chrome/browser/ash/extensions/autotest_private/autotest_private_api.cc b/chrome/browser/ash/extensions/autotest_private/autotest_private_api.cc index cac4413..9e553b08 100644 --- a/chrome/browser/ash/extensions/autotest_private/autotest_private_api.cc +++ b/chrome/browser/ash/extensions/autotest_private/autotest_private_api.cc
@@ -12,6 +12,7 @@ #include <sstream> #include <utility> +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/app_list/app_list_public_test_util.h" #include "ash/components/arc/arc_prefs.h" #include "ash/components/arc/metrics/arc_metrics_constants.h" @@ -25,7 +26,6 @@ #include "ash/constants/ash_pref_names.h" #include "ash/constants/ash_switches.h" #include "ash/public/cpp/accelerators.h" -#include "ash/public/cpp/accessibility_controller.h" #include "ash/public/cpp/ambient/ambient_prefs.h" #include "ash/public/cpp/ambient/ambient_ui_model.h" #include "ash/public/cpp/app_list/app_list_types.h"
diff --git a/chrome/browser/ash/login/lock/screen_locker_unittest.cc b/chrome/browser/ash/login/lock/screen_locker_unittest.cc index 3fcb2ba..69250893 100644 --- a/chrome/browser/ash/login/lock/screen_locker_unittest.cc +++ b/chrome/browser/ash/login/lock/screen_locker_unittest.cc
@@ -21,7 +21,6 @@ #include "chrome/browser/certificate_provider/certificate_provider_service.h" #include "chrome/browser/certificate_provider/certificate_provider_service_factory.h" #include "chrome/browser/profiles/profile_manager.h" -#include "chrome/browser/ui/ash/accessibility/fake_accessibility_controller.h" #include "chrome/browser/ui/ash/assistant/assistant_browser_delegate_impl.h" #include "chrome/browser/ui/ash/login_screen_client_impl.h" #include "chrome/browser/ui/ash/session_controller_client_impl.h" @@ -183,8 +182,6 @@ ScopedStubInstallAttributes test_install_attributes_; // ScreenLocker dependencies: - // * AccessibilityManager dependencies: - FakeAccessibilityController fake_accessibility_controller_; // * LoginScreenClientImpl dependencies: session_manager::SessionManager session_manager_; TestLoginScreen test_login_screen_;
diff --git a/chrome/browser/ash/ownership/owner_key_loader.cc b/chrome/browser/ash/ownership/owner_key_loader.cc index 5b95033..7a32321 100644 --- a/chrome/browser/ash/ownership/owner_key_loader.cc +++ b/chrome/browser/ash/ownership/owner_key_loader.cc
@@ -7,8 +7,8 @@ #include <string> #include <utility> -#include "ash/constants/ash_features.h" #include "base/check_is_test.h" +#include "base/feature_list.h" #include "base/task/thread_pool.h" #include "chrome/browser/ash/ownership/ownership_histograms.h" #include "chrome/browser/ash/profiles/profile_helper.h" @@ -17,15 +17,52 @@ #include "chrome/browser/net/nss_service.h" #include "chrome/browser/net/nss_service_factory.h" #include "chrome/browser/profiles/profile.h" +#include "chrome/common/channel_info.h" #include "components/ownership/owner_key_util.h" #include "components/policy/proto/device_management_backend.pb.h" #include "components/user_manager/user_manager.h" +#include "components/version_info/channel.h" #include "content/public/browser/browser_task_traits.h" #include "content/public/browser/browser_thread.h" #include "net/cert/nss_cert_database.h" namespace ash { +// Enable storing a newly created owner key in the private slot. +BASE_FEATURE(kStoreOwnerKeyInPrivateSlot, + "StoreOwnerKeyInPrivateSlot", + base::FEATURE_ENABLED_BY_DEFAULT); + +// Enable migration of the owner key from the public to the private slot. This +// experiment represents the second stage of `kStoreOwnerKeyInPrivateSlot` and +// is only respected if kStoreOwnerKeyInPrivateSlot is enabled. +BASE_FEATURE(kMigrateOwnerKeyToPrivateSlot, + "MigrateOwnerKeyToPrivateSlot", + base::FEATURE_DISABLED_BY_DEFAULT); + +bool IsStoreOwnerKeyInPrivateSlotEnabled() { + if (base::FeatureList::GetInstance()->IsFeatureOverridden( + kStoreOwnerKeyInPrivateSlot.name)) { + // Return the value if it was overridden by Finch, command line, etc. + return base::FeatureList::IsEnabled(kStoreOwnerKeyInPrivateSlot); + } + + version_info::Channel channel = chrome::GetChannel(); + if (channel == version_info::Channel::STABLE || + channel == version_info::Channel::BETA) { + // TODO(b/264397430): Disable on beta and stable channels for now, remove + // the condition when the new code is more reliable. + return false; + } + + return base::FeatureList::IsEnabled(kStoreOwnerKeyInPrivateSlot); +} + +bool ShouldMigrateOwnerKeyToPrivateSlot() { + return IsStoreOwnerKeyInPrivateSlotEnabled() && + base::FeatureList::IsEnabled(kMigrateOwnerKeyToPrivateSlot); +} + namespace { // Max number of attempts to generate a new owner key. @@ -85,7 +122,7 @@ crypto::ScopedPK11Slot public_slot, crypto::ScopedPK11Slot private_slot) { crypto::ScopedSECKEYPrivateKey sec_priv_key; - if (private_slot && features::IsStoreOwnerKeyInPrivateSlotEnabled()) { + if (private_slot && IsStoreOwnerKeyInPrivateSlotEnabled()) { sec_priv_key = owner_key_util->GenerateKeyPair(private_slot.get()); RecordOwnerKeyEvent(OwnerKeyEvent::kPrivateSlotKeyGeneration, bool(sec_priv_key)); @@ -299,8 +336,7 @@ RecordOwnerKeyEvent(OwnerKeyEvent::kOwnerKeyInPublicSlot, /*success=*/found_in_public_slot); - if (features::ShouldMigrateOwnerKeyToPrivateSlot() && - found_in_public_slot) { + if (ShouldMigrateOwnerKeyToPrivateSlot() && found_in_public_slot) { // If the key was found in the public slot and the migration is enabled, // then replace it by generating a new one in the private slot. The old // key will be deleted by OwnerSettingsServiceAsh when the new key is @@ -314,9 +350,8 @@ return; } - if (!features::ShouldMigrateOwnerKeyToPrivateSlot() && - !features::IsStoreOwnerKeyInPrivateSlotEnabled() && - !found_in_public_slot) { + if (!ShouldMigrateOwnerKeyToPrivateSlot() && + !IsStoreOwnerKeyInPrivateSlotEnabled() && !found_in_public_slot) { // If all experiments are disabled but the key is in the private slot, it // means they were reverted and it's probably better to migrate the owner // key back to the public slot.
diff --git a/chrome/browser/ash/ownership/owner_key_loader.h b/chrome/browser/ash/ownership/owner_key_loader.h index 4cc18c1..d60e78f 100644 --- a/chrome/browser/ash/ownership/owner_key_loader.h +++ b/chrome/browser/ash/ownership/owner_key_loader.h
@@ -5,6 +5,7 @@ #ifndef CHROME_BROWSER_ASH_OWNERSHIP_OWNER_KEY_LOADER_H_ #define CHROME_BROWSER_ASH_OWNERSHIP_OWNER_KEY_LOADER_H_ +#include "base/feature_list.h" #include "base/functional/callback.h" #include "base/memory/raw_ptr.h" #include "base/memory/ref_counted.h" @@ -21,6 +22,9 @@ class DeviceSettingsService; +BASE_DECLARE_FEATURE(kStoreOwnerKeyInPrivateSlot); +BASE_DECLARE_FEATURE(kMigrateOwnerKeyToPrivateSlot); + // A helper single-use class to load the owner key. // Determines whether the current user is the owner or not. // For the non-owner just loads the public owner key (which can be used to
diff --git a/chrome/browser/ash/ownership/owner_key_loader_unittest.cc b/chrome/browser/ash/ownership/owner_key_loader_unittest.cc index 0dd1e98..43665c1 100644 --- a/chrome/browser/ash/ownership/owner_key_loader_unittest.cc +++ b/chrome/browser/ash/ownership/owner_key_loader_unittest.cc
@@ -139,8 +139,8 @@ base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatures( /*enabled_features=*/{}, - /*disabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot, - ash::features::kMigrateOwnerKeyToPrivateSlot}); + /*disabled_features=*/{kStoreOwnerKeyInPrivateSlot, + kMigrateOwnerKeyToPrivateSlot}); // In real code DeviceSettingsService must call this for the first user. device_settings_service_.MarkWillEstablishConsumerOwnership(); @@ -168,8 +168,8 @@ TEST_F(RegularOwnerKeyLoaderTest, FirstUserGeneratesOwnerKeyInPrivateSlot) { base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatures( - /*enabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{ash::features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); // In real code DeviceSettingsService must call this for the first user. device_settings_service_.MarkWillEstablishConsumerOwnership(); @@ -244,8 +244,8 @@ TEST_F(RegularOwnerKeyLoaderTest, OwnerUserLoadsExistingKeyFromPublicSlot) { base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatures( - /*enabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{ash::features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); // Configure existing device policies and the owner key. auto signing_key = ConfigureExistingPolicies(profile_->GetProfileUserName()); @@ -273,8 +273,8 @@ TEST_F(RegularOwnerKeyLoaderTest, OwnerUserLoadsExistingKeyFromPrivateSlot) { base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatures( - /*enabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{ash::features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); // Configure existing device policies and the owner key. auto signing_key = ConfigureExistingPolicies(profile_->GetProfileUserName()); @@ -304,8 +304,8 @@ OwnerUserLoadsExistingKeyFromPublicSlotWithoutPolicies) { base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatures( - /*enabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{ash::features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); policy::DevicePolicyBuilder policy_builder; auto signing_key = policy_builder.GetSigningKey(); @@ -334,8 +334,8 @@ OwnerUserLoadsExistingKeyFromPrivateSlotWithoutPolicies) { base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatures( - /*enabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{ash::features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); policy::DevicePolicyBuilder policy_builder; auto signing_key = policy_builder.GetSigningKey(); @@ -511,8 +511,8 @@ TEST_F(RegularOwnerKeyLoaderTest, MigrateFromPublicToPrivateSlot) { base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatures( - /*enabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot, - ash::features::kMigrateOwnerKeyToPrivateSlot}, + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot, + kMigrateOwnerKeyToPrivateSlot}, /*disabled_features=*/{}); // Configure existing device policies and the owner key. @@ -550,8 +550,8 @@ // With this config Chrome should generate new keys in the private slot, but // not migrate existing keys from the public slot. feature_list.InitWithFeatures( - /*enabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{ash::features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); // Configure existing device policies and the owner key. auto signing_key = ConfigureExistingPolicies(profile_->GetProfileUserName()); @@ -585,8 +585,8 @@ // With this config Chrome should generate new keys in the private slot, but // not migrate existing keys from the public slot. feature_list.InitWithFeatures( - /*enabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot, - ash::features::kMigrateOwnerKeyToPrivateSlot}, + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot, + kMigrateOwnerKeyToPrivateSlot}, /*disabled_features=*/{}); // Configure existing device policies and the owner key. @@ -622,8 +622,8 @@ // not migrate existing keys from the public slot. feature_list.InitWithFeatures( /*enabled_features=*/{}, - /*disabled_features=*/{ash::features::kStoreOwnerKeyInPrivateSlot, - ash::features::kMigrateOwnerKeyToPrivateSlot}); + /*disabled_features=*/{kStoreOwnerKeyInPrivateSlot, + kMigrateOwnerKeyToPrivateSlot}); // Configure existing device policies and the owner key. auto signing_key = ConfigureExistingPolicies(profile_->GetProfileUserName());
diff --git a/chrome/browser/ash/ownership/owner_settings_service_ash_unittest.cc b/chrome/browser/ash/ownership/owner_settings_service_ash_unittest.cc index 92ce583..33d96ad 100644 --- a/chrome/browser/ash/ownership/owner_settings_service_ash_unittest.cc +++ b/chrome/browser/ash/ownership/owner_settings_service_ash_unittest.cc
@@ -7,7 +7,6 @@ #include <memory> #include <utility> -#include "ash/constants/ash_features.h" #include "base/containers/contains.h" #include "base/containers/queue.h" #include "base/functional/bind.h" @@ -18,6 +17,7 @@ #include "base/test/scoped_path_override.h" #include "base/test/test_future.h" #include "base/values.h" +#include "chrome/browser/ash/ownership/owner_key_loader.h" #include "chrome/browser/ash/ownership/owner_settings_service_ash_factory.h" #include "chrome/browser/ash/ownership/ownership_histograms.h" #include "chrome/browser/ash/settings/device_settings_provider.h" @@ -114,8 +114,8 @@ // By default disable the migration, so the imported key doesn't get // replaced. feature_list_.InitWithFeatures( - /*enabled_features=*/{features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); provider_ = std::make_unique<DeviceSettingsProvider>( base::BindRepeating(&OnPrefChanged), device_settings_service_.get(), @@ -344,8 +344,8 @@ // By default disable the migration, so the imported key doesn't get // replaced. feature_list_.InitWithFeatures( - /*enabled_features=*/{features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); provider_ = std::make_unique<DeviceSettingsProvider>( base::BindRepeating(&OnPrefChanged), device_settings_service_.get(), @@ -438,8 +438,8 @@ base::HistogramTester histogram_tester; base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatures( - /*enabled_features=*/{features::kStoreOwnerKeyInPrivateSlot, - features::kMigrateOwnerKeyToPrivateSlot}, + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot, + kMigrateOwnerKeyToPrivateSlot}, /*disabled_features=*/{}); FakeNssService* nss_service = FakeNssService::InitializeForBrowserContext(
diff --git a/chrome/browser/ash/policy/login/login_screen_accessibility_policy_browsertest.cc b/chrome/browser/ash/policy/login/login_screen_accessibility_policy_browsertest.cc index a3480b33..b91c3c3 100644 --- a/chrome/browser/ash/policy/login/login_screen_accessibility_policy_browsertest.cc +++ b/chrome/browser/ash/policy/login/login_screen_accessibility_policy_browsertest.cc
@@ -4,9 +4,9 @@ #include <string> +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/constants/ash_pref_names.h" #include "ash/constants/ash_switches.h" -#include "ash/public/cpp/accessibility_controller.h" #include "base/command_line.h" #include "base/compiler_specific.h" #include "base/functional/bind.h"
diff --git a/chrome/browser/ash/power/ml/smart_dim/smart_dim_integration_test.cc b/chrome/browser/ash/power/ml/smart_dim/smart_dim_integration_test.cc index 58b3d75f..6e52760 100644 --- a/chrome/browser/ash/power/ml/smart_dim/smart_dim_integration_test.cc +++ b/chrome/browser/ash/power/ml/smart_dim/smart_dim_integration_test.cc
@@ -2,6 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. +#include "base/cpu.h" #include "base/run_loop.h" #include "base/test/bind.h" #include "base/test/metrics/histogram_tester.h" @@ -17,6 +18,7 @@ #include "chromeos/ash/components/standalone_browser/standalone_browser_features.h" #include "components/component_updater/component_updater_service.h" #include "net/dns/mock_host_resolver.h" +#include "testing/gtest/include/gtest/gtest.h" #include "ui/aura/env.h" #include "ui/aura/env_observer.h" #include "ui/aura/window_observer.h" @@ -189,9 +191,13 @@ base::test::ScopedFeatureList feature_list_; }; -// Disabled due to failure on chromeos-betty-pi-arc-chrome. -// TODO(http://b/308674133): Enable after fix. -IN_PROC_BROWSER_TEST_F(SmartDimLacrosIntegrationTest, DISABLED_SmartDim) { +IN_PROC_BROWSER_TEST_F(SmartDimLacrosIntegrationTest, SmartDim) { + // Lacros fails to start up correctly on VM tryservers like + // chromeos-amd64-generic (Lacros restarts in a loop). b/303359438 + if (base::CPU().is_running_in_vm()) { + GTEST_SKIP(); + } + ASSERT_TRUE(crosapi::browser_util::IsLacrosEnabled()); // The test opens a Lacros window, so ensure the Wayland server is running and
diff --git a/chrome/browser/ash/settings/cros_settings_unittest.cc b/chrome/browser/ash/settings/cros_settings_unittest.cc index 320c18de..08e8d08c 100644 --- a/chrome/browser/ash/settings/cros_settings_unittest.cc +++ b/chrome/browser/ash/settings/cros_settings_unittest.cc
@@ -16,6 +16,7 @@ #include "base/test/scoped_feature_list.h" #include "base/values.h" #include "chrome/browser/ash/login/users/fake_chrome_user_manager.h" +#include "chrome/browser/ash/ownership/owner_key_loader.h" #include "chrome/browser/ash/ownership/owner_settings_service_ash.h" #include "chrome/browser/ash/ownership/owner_settings_service_ash_factory.h" #include "chrome/browser/ash/policy/core/device_policy_builder.h" @@ -67,8 +68,8 @@ void SetUp() override { // Disable owner key migration. feature_list_.InitWithFeatures( - /*enabled_features=*/{features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); device_policy_.Build();
diff --git a/chrome/browser/ash/settings/device_settings_provider_unittest.cc b/chrome/browser/ash/settings/device_settings_provider_unittest.cc index 255b798..3dd9571 100644 --- a/chrome/browser/ash/settings/device_settings_provider_unittest.cc +++ b/chrome/browser/ash/settings/device_settings_provider_unittest.cc
@@ -14,6 +14,7 @@ #include "base/test/scoped_feature_list.h" #include "base/test/scoped_path_override.h" #include "base/values.h" +#include "chrome/browser/ash/ownership/owner_key_loader.h" #include "chrome/browser/ash/policy/core/device_local_account.h" #include "chrome/browser/ash/settings/device_settings_test_helper.h" #include "chrome/common/chrome_paths.h" @@ -64,8 +65,8 @@ // Disable owner key migration. feature_list_.InitWithFeatures( - /*enabled_features=*/{features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); EXPECT_CALL(*this, SettingChanged(_)).Times(AnyNumber()); provider_ = std::make_unique<DeviceSettingsProvider>(
diff --git a/chrome/browser/ash/settings/device_settings_service_unittest.cc b/chrome/browser/ash/settings/device_settings_service_unittest.cc index 83978060..0f63ec1 100644 --- a/chrome/browser/ash/settings/device_settings_service_unittest.cc +++ b/chrome/browser/ash/settings/device_settings_service_unittest.cc
@@ -6,13 +6,13 @@ #include <stdint.h> -#include "ash/constants/ash_features.h" #include "base/compiler_specific.h" #include "base/functional/bind.h" #include "base/functional/callback.h" #include "base/functional/callback_helpers.h" #include "base/run_loop.h" #include "base/time/time.h" +#include "chrome/browser/ash/ownership/owner_key_loader.h" #include "chrome/browser/ash/ownership/owner_settings_service_ash.h" #include "chrome/browser/ash/ownership/owner_settings_service_ash_factory.h" #include "chrome/browser/ash/settings/device_settings_test_helper.h" @@ -75,8 +75,8 @@ // Disable owner key migration. feature_list_.InitWithFeatures( - /*enabled_features=*/{features::kStoreOwnerKeyInPrivateSlot}, - /*disabled_features=*/{features::kMigrateOwnerKeyToPrivateSlot}); + /*enabled_features=*/{kStoreOwnerKeyInPrivateSlot}, + /*disabled_features=*/{kMigrateOwnerKeyToPrivateSlot}); device_policy_->payload() .mutable_device_policy_refresh_rate()
diff --git a/chrome/browser/browser_controls/android/java/src/org/chromium/chrome/browser/browser_controls/BrowserStateBrowserControlsVisibilityDelegate.java b/chrome/browser/browser_controls/android/java/src/org/chromium/chrome/browser/browser_controls/BrowserStateBrowserControlsVisibilityDelegate.java index 1e63263..4862b71 100644 --- a/chrome/browser/browser_controls/android/java/src/org/chromium/chrome/browser/browser_controls/BrowserStateBrowserControlsVisibilityDelegate.java +++ b/chrome/browser/browser_controls/android/java/src/org/chromium/chrome/browser/browser_controls/BrowserStateBrowserControlsVisibilityDelegate.java
@@ -131,9 +131,6 @@ return BrowserControlsState.HIDDEN; } else if (mTokenHolder.hasTokens() && !sDisableOverridesForTesting) { return BrowserControlsState.SHOWN; - } else if (FeatureList.isNativeInitialized() - && ChromeFeatureList.isEnabled(ChromeFeatureList.TOOLBAR_SCROLL_ABLATION_ANDROID)) { - return BrowserControlsState.SHOWN; } return BrowserControlsState.BOTH; }
diff --git a/chrome/browser/chromeos/BUILD.gn b/chrome/browser/chromeos/BUILD.gn index bccd339..dfd870e 100644 --- a/chrome/browser/chromeos/BUILD.gn +++ b/chrome/browser/chromeos/BUILD.gn
@@ -330,6 +330,7 @@ "//ui/base/ime", "//ui/chromeos/strings", "//ui/chromeos/styles:cros_styles_views", + "//ui/chromeos/styles:cros_tokens_color_mappings", "//ui/color:color_headers", "//ui/compositor", "//ui/events:event_constants",
diff --git a/chrome/browser/chromeos/policy/dlp/clipboard_bubble.cc b/chrome/browser/chromeos/policy/dlp/clipboard_bubble.cc index 2f2ce6f..ff4c867 100644 --- a/chrome/browser/chromeos/policy/dlp/clipboard_bubble.cc +++ b/chrome/browser/chromeos/policy/dlp/clipboard_bubble.cc
@@ -21,9 +21,9 @@ #include "ui/views/controls/styled_label.h" #if BUILDFLAG(IS_CHROMEOS_ASH) -#include "ash/constants/ash_features.h" #include "ash/public/cpp/new_window_delegate.h" #include "ash/public/cpp/style/color_provider.h" +#include "ui/chromeos/styles/cros_tokens_color_mappings.h" #endif // BUILDFLAG(IS_CHROMEOS_ASH) #if BUILDFLAG(IS_CHROMEOS_LACROS) @@ -158,22 +158,18 @@ ClipboardBubbleView::ClipboardBubbleView(const std::u16string& text) { SetPaintToLayer(ui::LAYER_SOLID_COLOR); -#if BUILDFLAG(IS_CHROMEOS_ASH) - ash::ColorProvider* color_provider = ash::ColorProvider::Get(); - SkColor background_color = color_provider->GetBaseLayerColor( - ash::ColorProvider::BaseLayerType::kTransparent80); - layer()->SetColor(background_color); -#elif BUILDFLAG(IS_CHROMEOS_LACROS) +#if BUILDFLAG(IS_CHROMEOS_LACROS) // TODO(crbug.com/1311180) Replace color retrieval with more long term // solution. layer()->SetColor(RetrieveColor(cros_styles::ColorName::kBgColor)); layer()->SetBackgroundBlur(kBubbleBlurRadius); -#endif // BUILDFLAG(IS_CHROMEOS_ASH) +#endif // BUILDFLAG(IS_CHROMEOS_LACROS) layer()->SetBackgroundBlur(kBubbleBlurRadius); layer()->SetRoundedCornerRadius(kCornerRadii); // Add the managed icon. #if BUILDFLAG(IS_CHROMEOS_ASH) + ash::ColorProvider* color_provider = ash::ColorProvider::Get(); const SkColor icon_color = color_provider->GetContentLayerColor( ash::ColorProvider::ContentLayerType::kIconColorPrimary); #elif BUILDFLAG(IS_CHROMEOS_LACROS) @@ -211,7 +207,6 @@ #if BUILDFLAG(IS_CHROMEOS_ASH) message_style.override_color = color_provider->GetContentLayerColor( ash::ColorProvider::ContentLayerType::kTextColorPrimary); - label_->SetDisplayedOnBackgroundColor(background_color); #elif BUILDFLAG(IS_CHROMEOS_LACROS) // TODO(crbug.com/1311180) Replace color retrieval with more long term // solution. @@ -261,6 +256,16 @@ ClipboardBubbleView::~ClipboardBubbleView() = default; +void ClipboardBubbleView::OnThemeChanged() { + views::View::OnThemeChanged(); +#if BUILDFLAG(IS_CHROMEOS_ASH) + const SkColor background_color = + GetColorProvider()->GetColor(cros_tokens::kCrosSysSystemBaseElevated); + layer()->SetColor(background_color); + label_->SetDisplayedOnBackgroundColor(background_color); +#endif // BUILDFLAG(IS_CHROMEOS_ASH) +} + void ClipboardBubbleView::UpdateBorderSize(const gfx::Size& size) { border_->SetSize(size); }
diff --git a/chrome/browser/chromeos/policy/dlp/clipboard_bubble.h b/chrome/browser/chromeos/policy/dlp/clipboard_bubble.h index a1918b3..ecf1cf7 100644 --- a/chrome/browser/chromeos/policy/dlp/clipboard_bubble.h +++ b/chrome/browser/chromeos/policy/dlp/clipboard_bubble.h
@@ -33,6 +33,9 @@ virtual gfx::Size GetBubbleSize() const = 0; protected: + // views::View: + void OnThemeChanged() override; + // This function should get called if the view got updated e.g. AddChildView. void UpdateBorderSize(const gfx::Size& size);
diff --git a/chrome/browser/component_updater/optimization_guide_on_device_model_installer.cc b/chrome/browser/component_updater/optimization_guide_on_device_model_installer.cc new file mode 100644 index 0000000..8a2eaaa --- /dev/null +++ b/chrome/browser/component_updater/optimization_guide_on_device_model_installer.cc
@@ -0,0 +1,134 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/component_updater/optimization_guide_on_device_model_installer.h" + +#include <cstdint> +#include <iterator> +#include <memory> +#include <string> +#include <vector> + +#include "base/feature_list.h" +#include "base/files/file_path.h" +#include "base/files/file_util.h" +#include "base/memory/scoped_refptr.h" +#include "base/values.h" +#include "base/version.h" +#include "chrome/browser/browser_process.h" +#include "components/optimization_guide/core/model_execution/on_device_model_component.h" +#include "components/update_client/update_client.h" +#include "components/update_client/update_client_errors.h" +#include "content/public/browser/browser_thread.h" +#include "crypto/sha2.h" + +using ::optimization_guide::OnDeviceModelComponentStateManager; + +namespace component_updater { + +namespace { + +// Extension id is fklghjjljmnfjoepjmlobpekiapffcja. +constexpr char kManifestName[] = "Optimization Guide On Device Model"; +constexpr base::FilePath::CharType kInstallationRelativePath[] = + FILE_PATH_LITERAL("OptGuideOnDeviceModel"); +constexpr uint8_t kPublicKeySHA256[32] = { + 0x90, 0x1a, 0xaa, 0x21, 0xb7, 0xa5, 0x9c, 0xce, 0x48, 0x4a, 0x5e, + 0x32, 0xff, 0x00, 0xa6, 0x2b, 0x4c, 0xb9, 0x89, 0xfc, 0x0b, 0xce, + 0x6a, 0xf9, 0x93, 0x49, 0xb6, 0x51, 0x32, 0x82, 0x2c, 0xad, +}; +static_assert(std::size(kPublicKeySHA256) == crypto::kSHA256Length); + +} // namespace + +OptimizationGuideOnDeviceModelInstallerPolicy:: + OptimizationGuideOnDeviceModelInstallerPolicy( + scoped_refptr<optimization_guide::OnDeviceModelComponentStateManager> + state_manager) + : state_manager_(state_manager) {} + +OptimizationGuideOnDeviceModelInstallerPolicy:: + ~OptimizationGuideOnDeviceModelInstallerPolicy() = default; + +bool OptimizationGuideOnDeviceModelInstallerPolicy::VerifyInstallation( + const base::Value::Dict& manifest, + const base::FilePath& install_dir) const { + return state_manager_->VerifyInstallation(install_dir, manifest); +} + +bool OptimizationGuideOnDeviceModelInstallerPolicy:: + SupportsGroupPolicyEnabledComponentUpdates() const { + return true; +} + +bool OptimizationGuideOnDeviceModelInstallerPolicy::RequiresNetworkEncryption() + const { + // This installer is only registered for users who use certain features, and + // we do not want to expose that they are users of those features. + return true; +} + +update_client::CrxInstaller::Result +OptimizationGuideOnDeviceModelInstallerPolicy::OnCustomInstall( + const base::Value::Dict& manifest, + const base::FilePath& install_dir) { + return update_client::CrxInstaller::Result(update_client::InstallError::NONE); +} + +void OptimizationGuideOnDeviceModelInstallerPolicy::OnCustomUninstall() { + state_manager_->UninstallComplete(); +} + +void OptimizationGuideOnDeviceModelInstallerPolicy::ComponentReady( + const base::Version& version, + const base::FilePath& install_dir, + base::Value::Dict manifest) { + state_manager_->SetReady(version, install_dir, manifest); +} + +base::FilePath +OptimizationGuideOnDeviceModelInstallerPolicy::GetRelativeInstallDir() const { + return base::FilePath(kInstallationRelativePath); +} + +void OptimizationGuideOnDeviceModelInstallerPolicy::GetHash( + std::vector<uint8_t>* hash) const { + hash->assign(std::begin(kPublicKeySHA256), std::end(kPublicKeySHA256)); +} + +std::string OptimizationGuideOnDeviceModelInstallerPolicy::GetName() const { + return kManifestName; +} + +update_client::InstallerAttributes +OptimizationGuideOnDeviceModelInstallerPolicy::GetInstallerAttributes() const { + return { + // TODO(b/310740288): Decide on attributes for model variant. + }; +} + +bool OptimizationGuideOnDeviceModelInstallerPolicy::AllowCachedCopies() const { + return false; +} + +void RegisterOptimizationGuideOnDeviceModelComponent( + ComponentUpdateService* cus, + scoped_refptr<OnDeviceModelComponentStateManager> state_manager) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + base::MakeRefCounted<ComponentInstaller>( + std::make_unique<OptimizationGuideOnDeviceModelInstallerPolicy>( + state_manager)) + ->Register(cus, base::DoNothing()); +} + +void UninstallOptimizationGuideOnDeviceModelComponent( + scoped_refptr<OnDeviceModelComponentStateManager> state_manager) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + base::MakeRefCounted<ComponentInstaller>( + std::make_unique<OptimizationGuideOnDeviceModelInstallerPolicy>( + state_manager)) + ->Uninstall(); +} + +} // namespace component_updater
diff --git a/chrome/browser/component_updater/optimization_guide_on_device_model_installer.h b/chrome/browser/component_updater/optimization_guide_on_device_model_installer.h new file mode 100644 index 0000000..39cddfd3 --- /dev/null +++ b/chrome/browser/component_updater/optimization_guide_on_device_model_installer.h
@@ -0,0 +1,59 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CHROME_BROWSER_COMPONENT_UPDATER_OPTIMIZATION_GUIDE_ON_DEVICE_MODEL_INSTALLER_H_ +#define CHROME_BROWSER_COMPONENT_UPDATER_OPTIMIZATION_GUIDE_ON_DEVICE_MODEL_INSTALLER_H_ + +#include "base/memory/scoped_refptr.h" +#include "components/component_updater/component_installer.h" + +namespace optimization_guide { +class OnDeviceModelComponentStateManager; +} // namespace optimization_guide + +namespace component_updater { + +class OptimizationGuideOnDeviceModelInstallerPolicy + : public ComponentInstallerPolicy { + public: + explicit OptimizationGuideOnDeviceModelInstallerPolicy( + scoped_refptr<optimization_guide::OnDeviceModelComponentStateManager> + state_manager); + ~OptimizationGuideOnDeviceModelInstallerPolicy() override; + + // Overrides for ComponentInstallerPolicy. + bool VerifyInstallation(const base::Value::Dict& manifest, + const base::FilePath& install_dir) const override; + bool SupportsGroupPolicyEnabledComponentUpdates() const override; + bool RequiresNetworkEncryption() const override; + update_client::CrxInstaller::Result OnCustomInstall( + const base::Value::Dict& manifest, + const base::FilePath& install_dir) override; + void OnCustomUninstall() override; + void ComponentReady(const base::Version& version, + const base::FilePath& install_dir, + base::Value::Dict manifest) override; + base::FilePath GetRelativeInstallDir() const override; + void GetHash(std::vector<uint8_t>* hash) const override; + std::string GetName() const override; + update_client::InstallerAttributes GetInstallerAttributes() const override; + bool AllowCachedCopies() const override; + + private: + scoped_refptr<optimization_guide::OnDeviceModelComponentStateManager> + state_manager_; +}; + +void RegisterOptimizationGuideOnDeviceModelComponent( + ComponentUpdateService* cus, + scoped_refptr<optimization_guide::OnDeviceModelComponentStateManager> + state_manager); + +void UninstallOptimizationGuideOnDeviceModelComponent( + scoped_refptr<optimization_guide::OnDeviceModelComponentStateManager> + state_manager); + +} // namespace component_updater + +#endif // CHROME_BROWSER_COMPONENT_UPDATER_OPTIMIZATION_GUIDE_ON_DEVICE_MODEL_INSTALLER_H_
diff --git a/chrome/browser/compose/compose_enabling_unittest.cc b/chrome/browser/compose/compose_enabling_unittest.cc index 0e5ae97..2414cdd4 100644 --- a/chrome/browser/compose/compose_enabling_unittest.cc +++ b/chrome/browser/compose/compose_enabling_unittest.cc
@@ -60,10 +60,7 @@ class CustomMockOptimizationGuideKeyedService : public MockOptimizationGuideKeyedService { public: - explicit CustomMockOptimizationGuideKeyedService( - content::BrowserContext* browser_context) - : MockOptimizationGuideKeyedService(browser_context) {} - + CustomMockOptimizationGuideKeyedService() = default; ~CustomMockOptimizationGuideKeyedService() override = default; MOCK_METHOD(void, @@ -100,8 +97,7 @@ context, base::BindRepeating([](content::BrowserContext* context) -> std::unique_ptr<KeyedService> { return std::make_unique< - testing::NiceMock<CustomMockOptimizationGuideKeyedService>>( - context); + testing::NiceMock<CustomMockOptimizationGuideKeyedService>>(); })); }
diff --git a/chrome/browser/compose/compose_text_usage_logger_unittest.cc b/chrome/browser/compose/compose_text_usage_logger_unittest.cc index 9eb8b94..bb21bfe 100644 --- a/chrome/browser/compose/compose_text_usage_logger_unittest.cc +++ b/chrome/browser/compose/compose_text_usage_logger_unittest.cc
@@ -389,5 +389,105 @@ }))); } +TEST_F(ComposeTextUsageLoggerTest, ContentEditableEntry) { + FormData form_data = CreateForm(FormControlType::kContentEditable); + autofill_manager()->AddSeenFormStructure( + std::make_unique<autofill::FormStructure>(form_data)); + SimulateTyping(form_data.global_id(), form_data.fields[0].global_id(), + u"Some text"); + + DeleteContents(); + + EXPECT_THAT(LoggedTextUsage(), + testing::ElementsAre(ukm::TestUkmRecorder::HumanReadableUkmEntry( + ukm_source_id_, + { + {"AutofillFormControlType", + static_cast<int64_t>(FormControlType::kContentEditable)}, + {"IsAutofillFieldType", 0}, + {"TypedCharacterCount", 8}, + {"TypedWordCount", 2}, + }))); +} + +TEST_F(ComposeTextUsageLoggerTest, ContentEditableFormNotFound) { + // Not calling AddSeenFormStructure(), so the form won't be found. + FormData form_data = CreateForm(FormControlType::kContentEditable); + SimulateTyping(form_data.global_id(), form_data.fields[0].global_id(), + u"Some text"); + + DeleteContents(); + + EXPECT_THAT(LoggedTextUsage(), + testing::ElementsAre(ukm::TestUkmRecorder::HumanReadableUkmEntry( + ukm_source_id_, { + {"AutofillFormControlType", -1}, + {"IsAutofillFieldType", 0}, + {"TypedCharacterCount", 8}, + {"TypedWordCount", 2}, + }))); +} + +TEST_F(ComposeTextUsageLoggerTest, TwoTypesOfFormsModified) { + FormData form_data = CreateForm(FormControlType::kTextArea); + autofill_manager()->AddSeenFormStructure( + std::make_unique<autofill::FormStructure>(form_data)); + SimulateTyping(form_data.global_id(), form_data.fields[0].global_id(), + u"Some text"); + SimulateTyping(form_data.global_id(), form_data.fields[1].global_id(), + u"One two three four"); + FormData content_editable_form_data = + CreateForm(FormControlType::kContentEditable); + autofill_manager()->AddSeenFormStructure( + std::make_unique<autofill::FormStructure>(content_editable_form_data)); + SimulateTyping(content_editable_form_data.global_id(), + content_editable_form_data.fields[0].global_id(), + u"Some text"); + SimulateTyping(content_editable_form_data.global_id(), + content_editable_form_data.fields[1].global_id(), + u"One two three four"); + DeleteContents(); + + EXPECT_THAT( + LoggedTextUsage(), + testing::UnorderedElementsAre( + ukm::TestUkmRecorder::HumanReadableUkmEntry( + ukm_source_id_, + { + {"AutofillFormControlType", + static_cast<int64_t>(FormControlType::kTextArea)}, + {"IsAutofillFieldType", 0}, + {"TypedCharacterCount", 8 /*9 rounded down*/}, + {"TypedWordCount", 2}, + }), + ukm::TestUkmRecorder::HumanReadableUkmEntry( + ukm_source_id_, + { + {"AutofillFormControlType", + static_cast<int64_t>(FormControlType::kTextArea)}, + {"IsAutofillFieldType", 0}, + {"TypedCharacterCount", 16 /*18 rounded down*/}, + {"TypedWordCount", 4}, + }), + + ukm::TestUkmRecorder::HumanReadableUkmEntry( + ukm_source_id_, + { + {"AutofillFormControlType", + static_cast<int64_t>(FormControlType::kContentEditable)}, + {"IsAutofillFieldType", 0}, + {"TypedCharacterCount", 8 /*9 rounded down*/}, + {"TypedWordCount", 2}, + }), + ukm::TestUkmRecorder::HumanReadableUkmEntry( + ukm_source_id_, + { + {"AutofillFormControlType", + static_cast<int64_t>(FormControlType::kContentEditable)}, + {"IsAutofillFieldType", 0}, + {"TypedCharacterCount", 16 /*18 rounded down*/}, + {"TypedWordCount", 4}, + }))); +} } // namespace } // namespace compose
diff --git a/chrome/browser/flag-metadata.json b/chrome/browser/flag-metadata.json index 0f58a70..5583ae9 100644 --- a/chrome/browser/flag-metadata.json +++ b/chrome/browser/flag-metadata.json
@@ -2283,8 +2283,8 @@ }, { "name": "enable-core-location-backend", - "owners": [ "jameshollyer@google.com" ], - "expiry_milestone": 100 + "owners": [ "deviceapi-team@google.com" ], + "expiry_milestone": 135 }, { "name": "enable-critical-persisted-tab-data", @@ -2733,6 +2733,11 @@ "expiry_milestone": 130 }, { + "name": "enable-fenced-frames-cross-origin-automatic-beacons", + "owners": [ "lbrady@google.com", "shivanisha@chromium.org", "chrome-fenced-frames-core@google.com" ], + "expiry_milestone": 130 + }, + { "name": "enable-fenced-frames-developer-mode", "owners": [ "dom@chromium.org", "shivanisha@chromium.org", "chrome-fenced-frames@google.com" ], "expiry_milestone": 130
diff --git a/chrome/browser/flag_descriptions.cc b/chrome/browser/flag_descriptions.cc index 850d297..4f640db 100644 --- a/chrome/browser/flag_descriptions.cc +++ b/chrome/browser/flag_descriptions.cc
@@ -1164,6 +1164,14 @@ "#privacy-sandbox-ads-apis to also be enabled. See " "https://github.com/shivanigithub/fenced-frame"; +const char kEnableFencedFramesCrossOriginAutomaticBeaconsName[] = + "Enable automatic beacons from cross-origin subframes."; +const char kEnableFencedFramesCrossOriginAutomaticBeaconsDescription[] = + "Allows documents that are cross-origin to an ad frame root to send " + "automatic beacons, if the document and the data are both opted in to " + "being used in cross-origin beacons. The data must still be set in a " + "document that is same-origin to the ad frame root."; + const char kEnableFencedFramesDeveloperModeName[] = "Enable the `FencedFrameConfig` constructor."; const char kEnableFencedFramesDeveloperModeDescription[] = @@ -3971,11 +3979,6 @@ const char kCCTRealTimeEngagementSignalsDescription[] = "Enables sending real-time engagement signals (e.g. scroll) through " "CustomTabsCallback."; -const char kCCTRealTimeEngagementSignalsAlternativeImplName[] = - "Enable alternative implementation for CCT real-time engagement signals."; -const char kCCTRealTimeEngagementSignalsAlternativeImplDescription[] = - "Enables an alternative implementation for sending real-time engagement " - "signals (e.g. scroll) through CustomTabsCallback."; const char kCCTTextFragmentLookupApiEnabledName[] = "Enable CCT API to lookup text fragments"; @@ -4457,12 +4460,6 @@ "When enabled, sets the market URL for use in testing the update menu " "item."; -const char kShareSheetCustomActionsPolishName[] = - "Share sheet custom actions polish"; -const char kShareSheetCustomActionsPolishDescription[] = - "Polish Chrome provided custom actions for share sheet including dropping " - "low engagement actions, and shuffle the ordering. Android only."; - const char kShareSheetMigrationAndroidName[] = "Share sheet refactor Android"; const char kShareSheetMigrationAndroidDescription[] = "When enabled, use the Android OS share sheet.";
diff --git a/chrome/browser/flag_descriptions.h b/chrome/browser/flag_descriptions.h index 6789f8c..ec795d5 100644 --- a/chrome/browser/flag_descriptions.h +++ b/chrome/browser/flag_descriptions.h
@@ -774,6 +774,9 @@ extern const char kEnableFencedFramesName[]; extern const char kEnableFencedFramesDescription[]; +extern const char kEnableFencedFramesCrossOriginAutomaticBeaconsName[]; +extern const char kEnableFencedFramesCrossOriginAutomaticBeaconsDescription[]; + extern const char kEnableFencedFramesDeveloperModeName[]; extern const char kEnableFencedFramesDeveloperModeDescription[]; @@ -2299,8 +2302,6 @@ extern const char kCCTRealTimeEngagementSignalsName[]; extern const char kCCTRealTimeEngagementSignalsDescription[]; -extern const char kCCTRealTimeEngagementSignalsAlternativeImplName[]; -extern const char kCCTRealTimeEngagementSignalsAlternativeImplDescription[]; extern const char kCCTTextFragmentLookupApiEnabledName[]; extern const char kCCTTextFragmentLookupApiEnabledDescription[]; @@ -2606,9 +2607,6 @@ extern const char kSetMarketUrlForTestingName[]; extern const char kSetMarketUrlForTestingDescription[]; -extern const char kShareSheetCustomActionsPolishName[]; -extern const char kShareSheetCustomActionsPolishDescription[]; - extern const char kShareSheetMigrationAndroidName[]; extern const char kShareSheetMigrationAndroidDescription[];
diff --git a/chrome/browser/flags/android/chrome_feature_list.cc b/chrome/browser/flags/android/chrome_feature_list.cc index cca4c06..b9482ec6 100644 --- a/chrome/browser/flags/android/chrome_feature_list.cc +++ b/chrome/browser/flags/android/chrome_feature_list.cc
@@ -204,7 +204,6 @@ &kCCTPostMessageAPI, &kCCTPrefetchDelayShowOnStart, &kCCTRealTimeEngagementSignals, - &kCCTRealTimeEngagementSignalsAlternativeImpl, &kCCTRedirectPreconnect, &kCCTRemoveRemoteViewIds, &kCCTReportParallelRequestStatus, @@ -212,6 +211,7 @@ &kCCTResizableSideSheet, &kCCTResizableSideSheetForThirdParties, &kCCTResourcePrefetch, + &kCCTTabModalDialog, &kCCTTextFragmentLookupApiEnabled, &kCCTToolbarCustomizations, &kDontAutoHideBrowserControls, @@ -302,7 +302,6 @@ &kFeedPositionAndroid, &kSearchResumptionModuleAndroid, &kShareSheetMigrationAndroid, - &kShareSheetCustomActionsPolish, &kSpecialLocaleWrapper, &kSpecialUserDecision, &kSuppressToolbarCaptures, @@ -318,7 +317,6 @@ &kTestDefaultEnabled, &kThumbnailPlaceholder, &kToolbarMicIphAndroid, - &kToolbarScrollAblationAndroid, &kTrustedWebActivityPostMessage, &kSpareTab, &kStartSurfaceAndroid, @@ -598,10 +596,6 @@ "CCTRealTimeEngagementSignals", base::FEATURE_ENABLED_BY_DEFAULT); -BASE_FEATURE(kCCTRealTimeEngagementSignalsAlternativeImpl, - "CCTRealTimeEngagementSignalsAlternativeImpl", - base::FEATURE_ENABLED_BY_DEFAULT); - BASE_FEATURE(kCCTRedirectPreconnect, "CCTRedirectPreconnect", base::FEATURE_ENABLED_BY_DEFAULT); @@ -630,6 +624,10 @@ "CCTResourcePrefetch", base::FEATURE_ENABLED_BY_DEFAULT); +BASE_FEATURE(kCCTTabModalDialog, + "CCTTabModalDialog", + base::FEATURE_ENABLED_BY_DEFAULT); + BASE_FEATURE(kCCTTextFragmentLookupApiEnabled, "CCTTextFragmentLookupApiEnabled", base::FEATURE_ENABLED_BY_DEFAULT); @@ -986,10 +984,6 @@ "ShowScrollableMVTOnNtpPhoneAndroid", base::FEATURE_DISABLED_BY_DEFAULT); -BASE_FEATURE(kShareSheetCustomActionsPolish, - "ShareSheetCustomActionsPolish", - base::FEATURE_ENABLED_BY_DEFAULT); - BASE_FEATURE(kShareSheetMigrationAndroid, "ShareSheetMigrationAndroid", base::FEATURE_ENABLED_BY_DEFAULT); @@ -1056,10 +1050,6 @@ "ToolbarMicIphAndroid", base::FEATURE_DISABLED_BY_DEFAULT); -BASE_FEATURE(kToolbarScrollAblationAndroid, - "ToolbarScrollAblationAndroid", - base::FEATURE_DISABLED_BY_DEFAULT); - BASE_FEATURE(kTrustedWebActivityPostMessage, "TrustedWebActivityPostMessage", base::FEATURE_ENABLED_BY_DEFAULT);
diff --git a/chrome/browser/flags/android/chrome_feature_list.h b/chrome/browser/flags/android/chrome_feature_list.h index 059e8d4f..b1b1510 100644 --- a/chrome/browser/flags/android/chrome_feature_list.h +++ b/chrome/browser/flags/android/chrome_feature_list.h
@@ -60,7 +60,6 @@ BASE_DECLARE_FEATURE(kCCTPostMessageAPI); BASE_DECLARE_FEATURE(kCCTPrefetchDelayShowOnStart); BASE_DECLARE_FEATURE(kCCTRealTimeEngagementSignals); -BASE_DECLARE_FEATURE(kCCTRealTimeEngagementSignalsAlternativeImpl); BASE_DECLARE_FEATURE(kCCTRedirectPreconnect); BASE_DECLARE_FEATURE(kCCTRemoveRemoteViewIds); BASE_DECLARE_FEATURE(kCCTReportParallelRequestStatus); @@ -69,6 +68,7 @@ BASE_DECLARE_FEATURE(kCCTResizableSideSheetForThirdParties); BASE_DECLARE_FEATURE(kCCTResourcePrefetch); BASE_DECLARE_FEATURE(kCCTRetainingStateInMemory); +BASE_DECLARE_FEATURE(kCCTTabModalDialog); BASE_DECLARE_FEATURE(kCCTTextFragmentLookupApiEnabled); BASE_DECLARE_FEATURE(kCCTToolbarCustomizations); BASE_DECLARE_FEATURE(kDontAutoHideBrowserControls); @@ -172,7 +172,6 @@ BASE_DECLARE_FEATURE(kFeedPositionAndroid); BASE_DECLARE_FEATURE(kScrollToTLDOptimization); BASE_DECLARE_FEATURE(kSearchResumptionModuleAndroid); -BASE_DECLARE_FEATURE(kShareSheetCustomActionsPolish); BASE_DECLARE_FEATURE(kShareSheetMigrationAndroid); BASE_DECLARE_FEATURE(kSpecialLocaleWrapper); BASE_DECLARE_FEATURE(kSpecialUserDecision); @@ -189,7 +188,6 @@ BASE_DECLARE_FEATURE(kTestDefaultEnabled); BASE_DECLARE_FEATURE(kThumbnailPlaceholder); BASE_DECLARE_FEATURE(kToolbarMicIphAndroid); -BASE_DECLARE_FEATURE(kToolbarScrollAblationAndroid); BASE_DECLARE_FEATURE(kToolbarUseHardwareBitmapDraw); BASE_DECLARE_FEATURE(kTrustedWebActivityPostMessage); BASE_DECLARE_FEATURE(kSpareTab);
diff --git a/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/ChromeFeatureList.java b/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/ChromeFeatureList.java index c0a47b7..69a0b92 100644 --- a/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/ChromeFeatureList.java +++ b/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/ChromeFeatureList.java
@@ -192,8 +192,6 @@ public static final String CCT_POST_MESSAGE_API = "CCTPostMessageAPI"; public static final String CCT_PREFETCH_DELAY_SHOW_ON_START = "CCTPrefetchDelayShowOnStart"; public static final String CCT_REAL_TIME_ENGAGEMENT_SIGNALS = "CCTRealTimeEngagementSignals"; - public static final String CCT_REAL_TIME_ENGAGEMENT_SIGNALS_ALTERNATIVE_IMPL = - "CCTRealTimeEngagementSignalsAlternativeImpl"; public static final String CCT_REDIRECT_PRECONNECT = "CCTRedirectPreconnect"; public static final String CCT_REMOVE_REMOTE_VIEW_IDS = "CCTRemoveRemoteViewIds"; public static final String CCT_REPORT_PARALLEL_REQUEST_STATUS = @@ -203,6 +201,7 @@ public static final String CCT_RESIZABLE_SIDE_SHEET_FOR_THIRD_PARTIES = "CCTResizableSideSheetForThirdParties"; public static final String CCT_RESOURCE_PREFETCH = "CCTResourcePrefetch"; + public static final String CCT_TAB_MODAL_DIALOG = "CCTTabModalDialog"; public static final String CCT_TEXT_FRAGMENT_LOOKUP_API_ENABLED = "CCTTextFragmentLookupApiEnabled"; public static final String CCT_TOOLBAR_CUSTOMIZATIONS = "CCTToolbarCustomizations"; @@ -422,7 +421,6 @@ "SearchReadyOmniboxAllowQueryEdit"; public static final String SEARCH_RESUMPTION_MODULE_ANDROID = "SearchResumptionModuleAndroid"; public static final String SEED_ACCOUNTS_REVAMP = "SeedAccountsRevamp"; - public static final String SHARE_SHEET_CUSTOM_ACTIONS_POLISH = "ShareSheetCustomActionsPolish"; public static final String SHARE_SHEET_MIGRATION_ANDROID = "ShareSheetMigrationAndroid"; public static final String SEND_TAB_TO_SELF_V2 = "SendTabToSelfV2"; public static final String SHOPPING_LIST = "ShoppingList"; @@ -466,7 +464,6 @@ public static final String TEST_DEFAULT_DISABLED = "TestDefaultDisabled"; public static final String TEST_DEFAULT_ENABLED = "TestDefaultEnabled"; public static final String THUMBNAIL_PLACEHOLDER = "ThumbnailPlaceholder"; - public static final String TOOLBAR_SCROLL_ABLATION_ANDROID = "ToolbarScrollAblationAndroid"; public static final String TOOLBAR_USE_HARDWARE_BITMAP_DRAW = "ToolbarUseHardwareBitmapDraw"; public static final String TRACKING_PROTECTION_SETTINGS_PAGE_ROLLBACK_NOTICE = "TrackingProtectionSettingsPageRollbackNotice"; @@ -541,6 +538,7 @@ new CachedFlag(CCT_RESIZABLE_SIDE_SHEET, true); public static final CachedFlag sCctResizableSideSheetForThirdParties = new CachedFlag(CCT_RESIZABLE_SIDE_SHEET_FOR_THIRD_PARTIES, true); + public static final CachedFlag sCctTabModalDialog = new CachedFlag(CCT_TAB_MODAL_DIALOG, true); public static final CachedFlag sCctToolbarCustomizations = new CachedFlag(CCT_TOOLBAR_CUSTOMIZATIONS, true); public static final CachedFlag sCloseTabSaveTabList = @@ -668,6 +666,7 @@ sCctResizableForThirdParties, sCctResizableSideSheet, sCctResizableSideSheetForThirdParties, + sCctTabModalDialog, sCctToolbarCustomizations, sCloseTabSaveTabList, sCollectAndroidFrameTimelineMetrics, @@ -786,8 +785,6 @@ newMutableFlagWithSafeDefault(SUPPRESS_TOOLBAR_CAPTURES, false); public static final MutableFlagWithSafeDefault sThumbnailPlaceholder = newMutableFlagWithSafeDefault(THUMBNAIL_PLACEHOLDER, true); - public static final MutableFlagWithSafeDefault sToolbarScrollAblation = - newMutableFlagWithSafeDefault(TOOLBAR_SCROLL_ABLATION_ANDROID, false); public static final MutableFlagWithSafeDefault sTouchDownTriggerForPrefetch = newMutableFlagWithSafeDefault(OMNIBOX_TOUCH_DOWN_TRIGGER_FOR_PREFETCH, false); public static final MutableFlagWithSafeDefault sVisibleUrlTruncation =
diff --git a/chrome/browser/lacros/clipboard_lacros_browsertest.cc b/chrome/browser/lacros/clipboard_lacros_browsertest.cc index 606c49d2..e2debc4f 100644 --- a/chrome/browser/lacros/clipboard_lacros_browsertest.cc +++ b/chrome/browser/lacros/clipboard_lacros_browsertest.cc
@@ -67,6 +67,9 @@ aura::Window* window = BrowserView::GetBrowserViewForBrowser(browser()) ->frame() ->GetNativeWindow(); + std::string id = + lacros_window_utility::GetRootWindowUniqueId(window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(id)); ASSERT_TRUE( browser_test_util::SendAndWaitForMouseClick(window->GetRootWindow()));
diff --git a/chrome/browser/lacros/download_status_updater_lacros_browsertest.cc b/chrome/browser/lacros/download_status_updater_lacros_browsertest.cc index 212234a..7a2a8ae2 100644 --- a/chrome/browser/lacros/download_status_updater_lacros_browsertest.cc +++ b/chrome/browser/lacros/download_status_updater_lacros_browsertest.cc
@@ -284,6 +284,19 @@ item_ = nullptr; } + Browser* CreateAndWaitForBrowser(Profile* profile, bool otr = false) { + Browser* browser = + otr ? CreateIncognitoBrowser(profile) : CreateBrowser(profile); + std::string browser_window_id = + lacros_window_utility::GetRootWindowUniqueId( + BrowserView::GetBrowserViewForBrowser(browser) + ->frame() + ->GetNativeWindow() + ->GetRootWindow()); + EXPECT_TRUE(browser_test_util::WaitForWindowCreation(browser_window_id)); + return browser; + } + void SetUpBrowserForTest(Browser* browser) { download_button(browser)->DisableAutoCloseTimerForTesting(); download_button(browser)->DisableDownloadStartedAnimationForTesting(); @@ -536,7 +549,7 @@ DownloadStatusUpdaterBrowserTest, ShowInBrowser_NormalDownload_PickMostRecentActiveBrowser) { // Open a different browser window and activate it. - Browser* browser2 = CreateBrowser(browser()->profile()); + Browser* browser2 = CreateAndWaitForBrowser(browser()->profile()); ActivateBrowser(browser2); DownloadStatusUpdaterClientAsyncWaiter client( @@ -563,7 +576,7 @@ DownloadStatusUpdaterBrowserTest, ShowInBrowser_DangerousDownload_PickMostRecentActiveBrowser) { // Open a different browser window and activate it. - Browser* browser2 = CreateBrowser(browser()->profile()); + Browser* browser2 = CreateAndWaitForBrowser(browser()->profile()); ActivateBrowser(browser2); DownloadStatusUpdaterClientAsyncWaiter client( @@ -693,7 +706,8 @@ DownloadStatusUpdaterBrowserTest, ShowInBrowser_NormalDownload_MatchBrowserForExactProfile) { // Open an incognito browser window. - Browser* otr_browser = CreateIncognitoBrowser(browser()->profile()); + Browser* otr_browser = + CreateAndWaitForBrowser(browser()->profile(), /*otr=*/true); // Make the incognito window the last active browser. It should not be picked // even though it is the most recent active browser, because the profile is @@ -724,7 +738,8 @@ DownloadStatusUpdaterBrowserTest, ShowInBrowser_DangerousDownload_MatchBrowserForExactProfile) { // Open an incognito browser window. - Browser* otr_browser = CreateIncognitoBrowser(browser()->profile()); + Browser* otr_browser = + CreateAndWaitForBrowser(browser()->profile(), /*otr=*/true); // Make the incognito window the last active browser. It should not be picked // even though it is the most recent active browser, because the profile is @@ -754,7 +769,8 @@ IN_PROC_BROWSER_TEST_F(DownloadStatusUpdaterBrowserTest, ShowInBrowser_NormalDownload_IncognitoBrowser) { // Open an incognito browser window. - Browser* otr_browser = CreateIncognitoBrowser(browser()->profile()); + Browser* otr_browser = + CreateAndWaitForBrowser(browser()->profile(), /*otr=*/true); // Make `browser()` the last active browser. It should not be picked even // though it is the most recent active browser, because the profile is @@ -785,7 +801,8 @@ IN_PROC_BROWSER_TEST_F(DownloadStatusUpdaterBrowserTest, ShowInBrowser_DangerousDownload_IncognitoBrowser) { // Open an incognito browser window. - Browser* otr_browser = CreateIncognitoBrowser(browser()->profile()); + Browser* otr_browser = + CreateAndWaitForBrowser(browser()->profile(), /*otr=*/true); // Make `browser()` the last active browser. It should not be picked even // though it is the most recent active browser, because the profile is
diff --git a/chrome/browser/lacros/input_method_lacros_browsertest.cc b/chrome/browser/lacros/input_method_lacros_browsertest.cc index fe41a922..df04496 100644 --- a/chrome/browser/lacros/input_method_lacros_browsertest.cc +++ b/chrome/browser/lacros/input_method_lacros_browsertest.cc
@@ -586,13 +586,7 @@ if (!input_method.is_bound()) { GTEST_SKIP() << "Unsupported ash version"; } - - // Create a browser without omnibox since we don't want to deal with the - // automatic omnibox focus. - // TODO(b/315079554): Find a cleaner way. - auto* browser2 = CreateBrowserForApp("browser2", browser()->profile()); - - const std::string id = RenderAutofocusedInputFieldInLacros(browser2); + const std::string id = RenderAutofocusedInputFieldInLacros(browser()); InputMethodTestInterfaceAsyncWaiter input_method_async_waiter( input_method.get()); input_method_async_waiter.WaitForFocus(); @@ -888,13 +882,7 @@ if (!input_method.is_bound()) { GTEST_SKIP() << "Unsupported ash version"; } - - // Create a browser without omnibox since we don't want to deal with the - // automatic omnibox focus. - // TODO(b/315079554): Find a cleaner way. - auto* browser2 = CreateBrowserForApp("browser2", browser()->profile()); - - const std::string id = RenderAutofocusedInputFieldInLacros(browser2); + const std::string id = RenderAutofocusedInputFieldInLacros(browser()); InputMethodTestInterfaceAsyncWaiter input_method_async_waiter( input_method.get()); input_method_async_waiter.WaitForFocus();
diff --git a/chrome/browser/lacros/overview_lacros_browsertest.cc b/chrome/browser/lacros/overview_lacros_browsertest.cc index f0913c7..8551369 100644 --- a/chrome/browser/lacros/overview_lacros_browsertest.cc +++ b/chrome/browser/lacros/overview_lacros_browsertest.cc
@@ -42,6 +42,12 @@ if (!IsServiceAvailable()) return; + // Wait for the window to be visible. + aura::Window* window = browser()->window()->GetNativeWindow(); + std::string id = + lacros_window_utility::GetRootWindowUniqueId(window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(id)); + // Enter overview mode. auto& test_controller = chromeos::LacrosService::Get() ->GetRemote<crosapi::mojom::TestController>(); @@ -51,8 +57,6 @@ // Close the window by closing all tabs and wait for it to stop existing in // ash. - std::string id = lacros_window_utility::GetRootWindowUniqueId( - browser()->window()->GetNativeWindow()->GetRootWindow()); browser()->tab_strip_model()->CloseAllTabs(); ASSERT_TRUE(browser_test_util::WaitForWindowDestruction(id)); } @@ -65,11 +69,22 @@ if (!IsServiceAvailable()) return; + // Wait for the window to be visible. + aura::Window* main_window = browser()->window()->GetNativeWindow(); + std::string main_id = lacros_window_utility::GetRootWindowUniqueId( + main_window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(main_id)); + // Create an incognito window and make it visible. Browser* incognito_browser = Browser::Create(Browser::CreateParams( browser()->profile()->GetPrimaryOTRProfile(/*create_if_needed=*/true), true)); AddBlankTabAndShow(incognito_browser); + aura::Window* incognito_window = + incognito_browser->window()->GetNativeWindow(); + std::string incognito_id = lacros_window_utility::GetRootWindowUniqueId( + incognito_window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(incognito_id)); // Enter overview mode. auto& test_controller = chromeos::LacrosService::Get() @@ -81,8 +96,6 @@ // Close the incognito window by closing all tabs and wait for it to stop // existing in ash. - std::string incognito_id = lacros_window_utility::GetRootWindowUniqueId( - incognito_browser->window()->GetNativeWindow()->GetRootWindow()); incognito_browser->tab_strip_model()->CloseAllTabs(); ASSERT_TRUE(browser_test_util::WaitForWindowDestruction(incognito_id));
diff --git a/chrome/browser/lacros/popup_lacros_browsertest.cc b/chrome/browser/lacros/popup_lacros_browsertest.cc index 5b9e456..6d338bb 100644 --- a/chrome/browser/lacros/popup_lacros_browsertest.cc +++ b/chrome/browser/lacros/popup_lacros_browsertest.cc
@@ -87,12 +87,16 @@ // near the top of the screen. browser()->window()->Maximize(); + // Wait for the window to be created. + aura::Window* window = browser()->window()->GetNativeWindow(); + std::string window_id = + lacros_window_utility::GetRootWindowUniqueId(window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(window_id)); + // Wait for the window to be globally positioned at 0,0. It will eventually // have this position because it is maximized. We cannot assert the position // lacros-side because Wayland clients do not know the position of their // windows on the display. - std::string window_id = lacros_window_utility::GetRootWindowUniqueId( - browser()->window()->GetNativeWindow()->GetRootWindow()); WaitForWindowPositionInScreen(window_id, gfx::Point(0, 0)); // Precondition: The browser is the only open widget.
diff --git a/chrome/browser/lacros/tab_scrubber_lacros_browsertest.cc b/chrome/browser/lacros/tab_scrubber_lacros_browsertest.cc index 0edd225e..fc2c6ca 100644 --- a/chrome/browser/lacros/tab_scrubber_lacros_browsertest.cc +++ b/chrome/browser/lacros/tab_scrubber_lacros_browsertest.cc
@@ -55,7 +55,14 @@ kTriggerTabScrubbingMinVersion)) { return; } - // Add further 5 blank tabs to the initial browser. + + // Wait for the window to be created. + aura::Window* window = browser()->window()->GetNativeWindow(); + std::string window_id = + lacros_window_utility::GetRootWindowUniqueId(window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(window_id)); + + // Add further 5 blank tabs. for (int i = 0; i < 5; ++i) AddBlankTab(browser());
diff --git a/chrome/browser/lacros/tablet_mode_lacros_browsertest.cc b/chrome/browser/lacros/tablet_mode_lacros_browsertest.cc index be320d63..f2e4d749 100644 --- a/chrome/browser/lacros/tablet_mode_lacros_browsertest.cc +++ b/chrome/browser/lacros/tablet_mode_lacros_browsertest.cc
@@ -34,11 +34,22 @@ return; } + // Wait for the window to be visible. + aura::Window* main_window = browser()->window()->GetNativeWindow(); + std::string main_id = lacros_window_utility::GetRootWindowUniqueId( + main_window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(main_id)); + // Create an incognito window and make it visible. Browser* incognito_browser = Browser::Create(Browser::CreateParams( browser()->profile()->GetPrimaryOTRProfile(/*create_if_needed=*/true), true)); AddBlankTabAndShow(incognito_browser); + aura::Window* incognito_window = + incognito_browser->window()->GetNativeWindow(); + std::string incognito_id = lacros_window_utility::GetRootWindowUniqueId( + incognito_window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(incognito_id)); auto& test_controller = lacros_service->GetRemote<crosapi::mojom::TestController>(); @@ -51,8 +62,6 @@ // Close the incognito window by closing all tabs and wait for it to stop // existing in ash. - std::string incognito_id = lacros_window_utility::GetRootWindowUniqueId( - incognito_browser->window()->GetNativeWindow()->GetRootWindow()); incognito_browser->tab_strip_model()->CloseAllTabs(); ASSERT_TRUE(browser_test_util::WaitForWindowDestruction(incognito_id));
diff --git a/chrome/browser/lacros/web_contents_can_go_back_observer_browsertest.cc b/chrome/browser/lacros/web_contents_can_go_back_observer_browsertest.cc index 73eb7cbd..e1860a0 100644 --- a/chrome/browser/lacros/web_contents_can_go_back_observer_browsertest.cc +++ b/chrome/browser/lacros/web_contents_can_go_back_observer_browsertest.cc
@@ -74,6 +74,13 @@ ASSERT_TRUE(lacros_service); ASSERT_TRUE(lacros_service->IsAvailable<crosapi::mojom::TestController>()); + aura::Window* window = BrowserView::GetBrowserViewForBrowser(browser()) + ->frame() + ->GetNativeWindow(); + std::string id = + lacros_window_utility::GetRootWindowUniqueId(window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(id)); + EXPECT_FALSE(chrome::CanGoBack(browser())); EXPECT_FALSE(chrome::CanGoForward(browser())); @@ -82,12 +89,9 @@ WindowOpenDisposition::CURRENT_TAB, ui_test_utils::BROWSER_TEST_WAIT_FOR_LOAD_STOP); - std::string window_id = lacros_window_utility::GetRootWindowUniqueId( - browser()->window()->GetNativeWindow()->GetRootWindow()); - EXPECT_TRUE(chrome::CanGoBack(browser())); EXPECT_FALSE(chrome::CanGoForward(browser())); - CheckCanGoBackOnServer(window_id, true /* expected_value */); + CheckCanGoBackOnServer(id, true /* expected_value */); // Tweak the back/forward list. chrome::GoBack(browser(), WindowOpenDisposition::CURRENT_TAB); @@ -96,7 +100,7 @@ EXPECT_FALSE(chrome::CanGoBack(browser())); EXPECT_TRUE(chrome::CanGoForward(browser())); - CheckCanGoBackOnServer(window_id, false /* expected_value */); + CheckCanGoBackOnServer(id, false /* expected_value */); } IN_PROC_BROWSER_TEST_F(WebContentsCanGoBackObserverTest, @@ -105,6 +109,13 @@ ASSERT_TRUE(lacros_service); ASSERT_TRUE(lacros_service->IsAvailable<crosapi::mojom::TestController>()); + aura::Window* window = BrowserView::GetBrowserViewForBrowser(browser()) + ->frame() + ->GetNativeWindow(); + std::string id = + lacros_window_utility::GetRootWindowUniqueId(window->GetRootWindow()); + ASSERT_TRUE(browser_test_util::WaitForWindowCreation(id)); + EXPECT_FALSE(chrome::CanGoBack(browser())); EXPECT_FALSE(chrome::CanGoForward(browser())); @@ -113,12 +124,9 @@ WindowOpenDisposition::CURRENT_TAB, ui_test_utils::BROWSER_TEST_WAIT_FOR_LOAD_STOP); - std::string window_id = lacros_window_utility::GetRootWindowUniqueId( - browser()->window()->GetNativeWindow()->GetRootWindow()); - EXPECT_TRUE(chrome::CanGoBack(browser())); EXPECT_FALSE(chrome::CanGoForward(browser())); - CheckCanGoBackOnServer(window_id, true /* expected_value */); + CheckCanGoBackOnServer(id, true /* expected_value */); NavigateToURLWithDisposition(browser(), GURL(chrome::kChromeUIVersionURL), WindowOpenDisposition::NEW_FOREGROUND_TAB, @@ -127,7 +135,7 @@ EXPECT_EQ(1, browser()->tab_strip_model()->active_index()); EXPECT_FALSE(chrome::CanGoBack(browser())); EXPECT_FALSE(chrome::CanGoForward(browser())); - CheckCanGoBackOnServer(window_id, false /* expected_value */); + CheckCanGoBackOnServer(id, false /* expected_value */); // Navigate the current (second) tab to a different URL, so we can test // back/forward later. @@ -136,7 +144,7 @@ ui_test_utils::BROWSER_TEST_WAIT_FOR_LOAD_STOP); EXPECT_TRUE(chrome::CanGoBack(browser())); EXPECT_FALSE(chrome::CanGoForward(browser())); - CheckCanGoBackOnServer(window_id, true /* expected_value */); + CheckCanGoBackOnServer(id, true /* expected_value */); // Tweak the back/forward list of the 2nd tab, and verify. chrome::GoBack(browser(), WindowOpenDisposition::CURRENT_TAB); @@ -145,7 +153,7 @@ EXPECT_FALSE(chrome::CanGoBack(browser())); EXPECT_TRUE(chrome::CanGoForward(browser())); - CheckCanGoBackOnServer(window_id, false /* expected_value */); + CheckCanGoBackOnServer(id, false /* expected_value */); // Switch to a different tab, and verify whether the `can go back` property // updates accordingly. @@ -156,5 +164,5 @@ EXPECT_TRUE(chrome::CanGoBack(browser())); EXPECT_FALSE(chrome::CanGoForward(browser())); - CheckCanGoBackOnServer(window_id, true /* expected_value */); + CheckCanGoBackOnServer(id, true /* expected_value */); }
diff --git a/chrome/browser/media/webrtc/webrtc_video_display_perf_browsertest.cc b/chrome/browser/media/webrtc/webrtc_video_display_perf_browsertest.cc index 2d1ca32..32ee550 100644 --- a/chrome/browser/media/webrtc/webrtc_video_display_perf_browsertest.cc +++ b/chrome/browser/media/webrtc/webrtc_video_display_perf_browsertest.cc
@@ -118,6 +118,59 @@ } } +content::WebContents* OpenWebrtcInternalsTab(Browser* browser) { + chrome::AddTabAt(browser, GURL(url::kAboutBlankURL), -1, true); + EXPECT_TRUE( + ui_test_utils::NavigateToURL(browser, GURL("chrome://webrtc-internals"))); + return browser->tab_strip_model()->GetActiveWebContents(); +} + +std::vector<double> ParseGoogMaxDecodeFromWebrtcInternalsTab( + const std::string& webrtc_internals_stats_json) { + std::vector<double> goog_decode_ms; + + absl::optional<base::Value> parsed_json = + base::JSONReader::Read(webrtc_internals_stats_json); + if (!parsed_json || !parsed_json->is_dict()) + return goog_decode_ms; + const base::Value::Dict& dictionary = parsed_json->GetDict(); + + // |dictionary| should have exactly two entries, one per ssrc. + if (dictionary.size() != 2u) + return goog_decode_ms; + + // Only a given |dictionary| entry will have a "stats" entry that has a key + // that ends with "recv-googMaxDecodeMs" inside (it will start with the ssrc + // id, but we don't care about that). Then collect the string of "values" out + // of that key and convert those into the |goog_decode_ms| vector of doubles. + for (auto dictionary_entry : dictionary) { + for (auto ssrc_entry : dictionary_entry.second.GetDict()) { + if (ssrc_entry.first != "stats") + continue; + + for (auto stat_entry : ssrc_entry.second.GetDict()) { + if (!base::EndsWith(stat_entry.first, "recv-googMaxDecodeMs", + base::CompareCase::SENSITIVE)) { + continue; + } + const std::string* values_entry = + stat_entry.second.GetDict().FindString("values"); + if (!values_entry) { + continue; + } + base::StringTokenizer values_tokenizer(*values_entry, "[,]"); + while (values_tokenizer.GetNext()) { + if (values_tokenizer.token_is_delim()) + continue; + goog_decode_ms.push_back(atof(values_tokenizer.token().c_str()) * + base::Time::kMicrosecondsPerMillisecond); + } + } + } + } + return goog_decode_ms; +} + } // anonymous namespace // Tests the performance of Chrome displaying remote video. @@ -162,6 +215,13 @@ void TestVideoDisplayPerf(const std::string& video_codec) { ASSERT_TRUE(embedded_test_server()->Start()); + // chrome:webrtc-internals doesn't start tracing anything until the + // connection(s) are up. + content::WebContents* webrtc_internals_tab = + OpenWebrtcInternalsTab(browser()); + EXPECT_TRUE( + content::ExecJs(webrtc_internals_tab, + "currentGetStatsMethod = OPTION_GETSTATS_LEGACY")); content::WebContents* left_tab = OpenPageAndGetUserMediaInNewTabWithConstraints( @@ -204,6 +264,12 @@ // Run the connection for 5 seconds to collect metrics. test::SleepInJavascript(left_tab, 5000); + const std::string webrtc_internals_stats_json = ExecuteJavascript( + "JSON.stringify(peerConnectionDataStore);", webrtc_internals_tab); + webrtc_decode_latencies_ = + ParseGoogMaxDecodeFromWebrtcInternalsTab(webrtc_internals_stats_json); + chrome::CloseWebContents(browser(), webrtc_internals_tab, false); + std::string json_events; ASSERT_TRUE(tracing::EndTracing(&json_events)); std::unique_ptr<trace_analyzer::TraceAnalyzer> analyzer( @@ -373,6 +439,8 @@ PrintMeanAndMax("Post-decode-to-raster latency", name_modifier, video_frame_submmitter_latencies_); + PrintMeanAndMax("WebRTC decode latency", name_modifier, + webrtc_decode_latencies_); } VideoDisplayPerfTestConfig test_config_; @@ -389,6 +457,7 @@ // These two put together represent the whole delay from encoded video frames // to OS swap buffers call (or callback, depending on the platform). std::vector<double> video_frame_submmitter_latencies_; + std::vector<double> webrtc_decode_latencies_; }; INSTANTIATE_TEST_SUITE_P(WebRtcVideoDisplayPerfBrowserTests, @@ -399,14 +468,15 @@ testing::Values(30, 60), testing::Bool())); +// TODO(crbug.com/1509755): Rewrite these tests to not use legacy GetStats API. IN_PROC_BROWSER_TEST_P(WebRtcVideoDisplayPerfBrowserTest, - TestVideoDisplayPerfVP9) { + DISABLED_TestVideoDisplayPerfVP9) { TestVideoDisplayPerf("VP9"); } #if BUILDFLAG(RTC_USE_H264) IN_PROC_BROWSER_TEST_P(WebRtcVideoDisplayPerfBrowserTest, - TestVideoDisplayPerfH264) { + DISABLED_TestVideoDisplayPerfH264) { if (!base::FeatureList::IsEnabled( blink::features::kWebRtcH264WithOpenH264FFmpeg)) { LOG(WARNING) << "Run-time feature WebRTC-H264WithOpenH264FFmpeg disabled. "
diff --git a/chrome/browser/optimization_guide/android/optimization_guide_bridge_unittest.cc b/chrome/browser/optimization_guide/android/optimization_guide_bridge_unittest.cc index 5ad8170..67aee69 100644 --- a/chrome/browser/optimization_guide/android/optimization_guide_bridge_unittest.cc +++ b/chrome/browser/optimization_guide/android/optimization_guide_bridge_unittest.cc
@@ -53,16 +53,15 @@ pref_service_ = std::make_unique<TestingPrefServiceSimple>(); optimization_guide::prefs::RegisterProfilePrefs(pref_service_->registry()); - optimization_guide_keyed_service_ = - static_cast<MockOptimizationGuideKeyedService*>( - OptimizationGuideKeyedServiceFactory::GetInstance() - ->SetTestingFactoryAndUse( - profile_, - base::BindRepeating([](content::BrowserContext* context) - -> std::unique_ptr<KeyedService> { - return std::make_unique< - MockOptimizationGuideKeyedService>(context); - }))); + optimization_guide_keyed_service_ = static_cast< + MockOptimizationGuideKeyedService*>( + OptimizationGuideKeyedServiceFactory::GetInstance() + ->SetTestingFactoryAndUse( + profile_, + base::BindRepeating([](content::BrowserContext* context) + -> std::unique_ptr<KeyedService> { + return std::make_unique<MockOptimizationGuideKeyedService>(); + }))); } void RegisterOptimizationTypes() {
diff --git a/chrome/browser/optimization_guide/mock_optimization_guide_keyed_service.cc b/chrome/browser/optimization_guide/mock_optimization_guide_keyed_service.cc index 4b235e8..f9ae2b7 100644 --- a/chrome/browser/optimization_guide/mock_optimization_guide_keyed_service.cc +++ b/chrome/browser/optimization_guide/mock_optimization_guide_keyed_service.cc
@@ -49,9 +49,10 @@ } } -MockOptimizationGuideKeyedService::MockOptimizationGuideKeyedService( - content::BrowserContext* browser_context) - : OptimizationGuideKeyedService(browser_context) {} +MockOptimizationGuideKeyedService::MockOptimizationGuideKeyedService() + : OptimizationGuideKeyedService(nullptr) {} MockOptimizationGuideKeyedService::~MockOptimizationGuideKeyedService() = default; + +void MockOptimizationGuideKeyedService::Shutdown() {}
diff --git a/chrome/browser/optimization_guide/mock_optimization_guide_keyed_service.h b/chrome/browser/optimization_guide/mock_optimization_guide_keyed_service.h index f86356fd..0c384f3 100644 --- a/chrome/browser/optimization_guide/mock_optimization_guide_keyed_service.h +++ b/chrome/browser/optimization_guide/mock_optimization_guide_keyed_service.h
@@ -25,10 +25,11 @@ static void TearDown(); static void ResetForTesting(); - explicit MockOptimizationGuideKeyedService( - content::BrowserContext* browser_context); + MockOptimizationGuideKeyedService(); ~MockOptimizationGuideKeyedService() override; + void Shutdown() override; + MOCK_METHOD(void, RegisterOptimizationTypes, (const std::vector<optimization_guide::proto::OptimizationType>&), @@ -62,6 +63,24 @@ MOCK_METHOD(void, UploadModelQualityLogs, (std::unique_ptr<optimization_guide::ModelQualityLogEntry>)); + MOCK_METHOD(void, + AddObserverForOptimizationTargetModel, + (optimization_guide::proto::OptimizationTarget, + const absl::optional<optimization_guide::proto::Any>&, + optimization_guide::OptimizationTargetModelObserver*), + (override)); + MOCK_METHOD(void, + RemoveObserverForOptimizationTargetModel, + (optimization_guide::proto::OptimizationTarget, + optimization_guide::OptimizationTargetModelObserver*), + (override)); + + MOCK_METHOD(void, + OnNavigationStartOrRedirect, + (OptimizationGuideNavigationData*), + (override)); + + MOCK_METHOD(void, OnNavigationFinish, (const std::vector<GURL>&), (override)); }; #endif // CHROME_BROWSER_OPTIMIZATION_GUIDE_MOCK_OPTIMIZATION_GUIDE_KEYED_SERVICE_H_
diff --git a/chrome/browser/optimization_guide/model_execution/chrome_on_device_model_service_controller.cc b/chrome/browser/optimization_guide/model_execution/chrome_on_device_model_service_controller.cc index 1e7d5aad..2faa10b 100644 --- a/chrome/browser/optimization_guide/model_execution/chrome_on_device_model_service_controller.cc +++ b/chrome/browser/optimization_guide/model_execution/chrome_on_device_model_service_controller.cc
@@ -17,10 +17,13 @@ } // namespace -ChromeOnDeviceModelServiceController::ChromeOnDeviceModelServiceController() +ChromeOnDeviceModelServiceController::ChromeOnDeviceModelServiceController( + base::WeakPtr<OnDeviceModelComponentStateManager> + on_device_component_state_manager) : OnDeviceModelServiceController( std::make_unique<OnDeviceModelAccessController>( - *g_browser_process->local_state())) { + *g_browser_process->local_state()), + std::move(on_device_component_state_manager)) { CHECK_EQ(nullptr, g_instance); g_instance = this; }
diff --git a/chrome/browser/optimization_guide/model_execution/chrome_on_device_model_service_controller.h b/chrome/browser/optimization_guide/model_execution/chrome_on_device_model_service_controller.h index f3cbc0f..e0b23cb 100644 --- a/chrome/browser/optimization_guide/model_execution/chrome_on_device_model_service_controller.h +++ b/chrome/browser/optimization_guide/model_execution/chrome_on_device_model_service_controller.h
@@ -7,7 +7,10 @@ #include "components/optimization_guide/core/model_execution/on_device_model_service_controller.h" +#include "base/memory/scoped_refptr.h" + namespace optimization_guide { +class OnDeviceModelComponentStateManager; // Chrome uses a single instance of OnDeviceModelServiceController. This is done // for two reasons: @@ -19,7 +22,9 @@ class ChromeOnDeviceModelServiceController : public OnDeviceModelServiceController { public: - ChromeOnDeviceModelServiceController(); + explicit ChromeOnDeviceModelServiceController( + base::WeakPtr<OnDeviceModelComponentStateManager> + on_device_component_state_manager); // Returns the OnDeviceModelServiceController, null if it one hasn't been // created yet.
diff --git a/chrome/browser/optimization_guide/optimization_guide_keyed_service.cc b/chrome/browser/optimization_guide/optimization_guide_keyed_service.cc index ba91646..76a0202 100644 --- a/chrome/browser/optimization_guide/optimization_guide_keyed_service.cc +++ b/chrome/browser/optimization_guide/optimization_guide_keyed_service.cc
@@ -16,6 +16,7 @@ #include "build/build_config.h" #include "build/chromeos_buildflags.h" #include "chrome/browser/browser_process.h" +#include "chrome/browser/component_updater/optimization_guide_on_device_model_installer.h" #include "chrome/browser/download/background_download_service_factory.h" #include "chrome/browser/metrics/chrome_metrics_service_accessor.h" #include "chrome/browser/optimization_guide/chrome_hints_manager.h" @@ -33,6 +34,7 @@ #include "components/optimization_guide/core/hints_processing_util.h" #include "components/optimization_guide/core/model_execution/model_execution_features_controller.h" #include "components/optimization_guide/core/model_execution/model_execution_manager.h" +#include "components/optimization_guide/core/model_execution/on_device_model_component.h" #include "components/optimization_guide/core/model_execution/on_device_model_service_controller.h" #include "components/optimization_guide/core/model_quality/model_quality_log_entry.h" #include "components/optimization_guide/core/model_quality/model_quality_logs_uploader_service.h" @@ -41,6 +43,7 @@ #include "components/optimization_guide/core/optimization_guide_features.h" #include "components/optimization_guide/core/optimization_guide_logger.h" #include "components/optimization_guide/core/optimization_guide_navigation_data.h" +#include "components/optimization_guide/core/optimization_guide_prefs.h" #include "components/optimization_guide/core/optimization_guide_store.h" #include "components/optimization_guide/core/optimization_guide_util.h" #include "components/optimization_guide/core/prediction_manager.h" @@ -67,6 +70,7 @@ namespace { +using ::optimization_guide::OnDeviceModelComponentStateManager; using ::optimization_guide::OnDeviceModelPerformanceClass; // Deletes old store paths that were written in incorrect locations. @@ -159,18 +163,41 @@ } scoped_refptr<optimization_guide::OnDeviceModelServiceController> -GetOnDeviceModelServiceController() { +GetOnDeviceModelServiceController( + base::WeakPtr<optimization_guide::OnDeviceModelComponentStateManager> + on_device_component_manager) { scoped_refptr<optimization_guide::OnDeviceModelServiceController> service_controller = optimization_guide:: ChromeOnDeviceModelServiceController::GetSingleInstanceMayBeNull(); if (!service_controller) { service_controller = base::MakeRefCounted< - optimization_guide::ChromeOnDeviceModelServiceController>(); + optimization_guide::ChromeOnDeviceModelServiceController>( + std::move(on_device_component_manager)); service_controller->Init(); } return service_controller; } +class OnDeviceModelComponentStateManagerDelegate + : public OnDeviceModelComponentStateManager::Delegate { + public: + ~OnDeviceModelComponentStateManagerDelegate() override = default; + void RegisterInstaller(scoped_refptr<OnDeviceModelComponentStateManager> + state_manager) override { + if (!g_browser_process) { + return; + } + component_updater::RegisterOptimizationGuideOnDeviceModelComponent( + g_browser_process->component_updater(), state_manager); + } + + void Uninstall(scoped_refptr<OnDeviceModelComponentStateManager> + state_manager) override { + component_updater::UninstallOptimizationGuideOnDeviceModelComponent( + state_manager); + } +}; + } // namespace // static @@ -200,11 +227,18 @@ } // static -void OptimizationGuideKeyedService::LogOnDeviceMetrics() { - auto controller = GetOnDeviceModelServiceController(); +// We're using a weakptr here for testing purposes. We need to allow +// OnDeviceModelComponentStateManager to be destroyed along with a test harness. +void OptimizationGuideKeyedService::DeterminePerformanceClass( + base::WeakPtr<optimization_guide::OnDeviceModelComponentStateManager> + on_device_component_state_manager) { + auto controller = + GetOnDeviceModelServiceController(on_device_component_state_manager); controller->GetEstimatedPerformanceClass(base::BindOnce( [](scoped_refptr<optimization_guide::OnDeviceModelServiceController> controller, + base::WeakPtr<optimization_guide::OnDeviceModelComponentStateManager> + on_device_component_state_manager, std::optional<on_device_model::mojom::PerformanceClass> performance_class) { auto optimization_guide_performance_class = @@ -212,7 +246,10 @@ base::UmaHistogramEnumeration( "OptimizationGuide.ModelExecution.OnDeviceModelPerformanceClass", optimization_guide_performance_class); - + if (on_device_component_state_manager) { + on_device_component_state_manager->DevicePerformanceClassChanged( + optimization_guide_performance_class); + } ChromeMetricsServiceAccessor::RegisterSyntheticFieldTrial( "SyntheticOnDeviceModelPerformanceClass", OnDeviceModelPerformanceClassToString( @@ -220,14 +257,16 @@ variations::SyntheticTrialAnnotationMode::kCurrentLog); controller->ShutdownServiceIfNoModelLoaded(); }, - controller)); + controller, on_device_component_state_manager)); } OptimizationGuideKeyedService::OptimizationGuideKeyedService( content::BrowserContext* browser_context) : browser_context_(browser_context) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); - Initialize(); + if (browser_context_) { // Null in MockOptimizationGuideKeyedService. + Initialize(); + } } OptimizationGuideKeyedService::~OptimizationGuideKeyedService() { @@ -361,28 +400,37 @@ // |this| owns |prediction_manager_|. base::Unretained(this))); - if (!profile->IsOffTheRecord() && - base::FeatureList::IsEnabled( - optimization_guide::features::kLogOnDeviceMetricsOnStartup)) { - base::SequencedTaskRunner::GetCurrentDefault()->PostDelayedTask( - FROM_HERE, - base::BindOnce(&OptimizationGuideKeyedService::LogOnDeviceMetrics), - optimization_guide::features::GetOnDeviceStartupMetricDelay()); - } - - if (!profile->IsOffTheRecord() && - base::FeatureList::IsEnabled( - optimization_guide::features::kOptimizationGuideModelExecution)) { - scoped_refptr<optimization_guide::OnDeviceModelServiceController> - service_controller; + if (!profile->IsOffTheRecord()) { + on_device_component_manager_ = + optimization_guide::OnDeviceModelComponentStateManager::CreateOrGet( + g_browser_process->local_state(), + std::make_unique<OnDeviceModelComponentStateManagerDelegate>()); + on_device_component_manager_->OnStartup(); if (base::FeatureList::IsEnabled( - optimization_guide::features::kOptimizationGuideOnDeviceModel)) { - service_controller = GetOnDeviceModelServiceController(); + optimization_guide::features::kLogOnDeviceMetricsOnStartup)) { + base::SequencedTaskRunner::GetCurrentDefault()->PostDelayedTask( + FROM_HERE, + base::BindOnce( + &OptimizationGuideKeyedService::DeterminePerformanceClass, + on_device_component_manager_->GetWeakPtr()), + optimization_guide::features::GetOnDeviceStartupMetricDelay()); } - model_execution_manager_ = - std::make_unique<optimization_guide::ModelExecutionManager>( - url_loader_factory, IdentityManagerFactory::GetForProfile(profile), - std::move(service_controller), optimization_guide_logger_.get()); + + if (base::FeatureList::IsEnabled( + optimization_guide::features::kOptimizationGuideModelExecution)) { + scoped_refptr<optimization_guide::OnDeviceModelServiceController> + service_controller; + if (base::FeatureList::IsEnabled( + optimization_guide::features::kOptimizationGuideOnDeviceModel)) { + service_controller = GetOnDeviceModelServiceController( + on_device_component_manager_->GetWeakPtr()); + } + model_execution_manager_ = + std::make_unique<optimization_guide::ModelExecutionManager>( + url_loader_factory, + IdentityManagerFactory::GetForProfile(profile), + std::move(service_controller), optimization_guide_logger_.get()); + } } if (!profile->IsOffTheRecord() &&
diff --git a/chrome/browser/optimization_guide/optimization_guide_keyed_service.h b/chrome/browser/optimization_guide/optimization_guide_keyed_service.h index d9a23b33..b1ff92b 100644 --- a/chrome/browser/optimization_guide/optimization_guide_keyed_service.h +++ b/chrome/browser/optimization_guide/optimization_guide_keyed_service.h
@@ -44,6 +44,7 @@ class ModelInfo; class ModelQualityLogEntry; class ModelQualityLogsUploaderService; +class OnDeviceModelComponentStateManager; class OptimizationGuideStore; class PredictionManager; class PredictionManagerBrowserTestBase; @@ -192,8 +193,10 @@ friend class PersonalizedHintsFetcherBrowserTest; friend class settings::SettingsUI; - // Logs metrics from the OnDeviceModelService. - static void LogOnDeviceMetrics(); + // Evaluates and logs the device performance class. + static void DeterminePerformanceClass( + base::WeakPtr<optimization_guide::OnDeviceModelComponentStateManager> + on_device_component_state_manager); // Initializes |this|. void Initialize(); @@ -210,13 +213,14 @@ } // Notifies |hints_manager_| that the navigation associated with - // |navigation_data| has started or redirected. - void OnNavigationStartOrRedirect( + // |navigation_data| has started or redirected. Virtual for testing. + virtual void OnNavigationStartOrRedirect( OptimizationGuideNavigationData* navigation_data); // Notifies |hints_manager_| that the navigation associated with - // |navigation_redirect_chain| has finished. - void OnNavigationFinish(const std::vector<GURL>& navigation_redirect_chain); + // |navigation_redirect_chain| has finished. Virtual for testing. + virtual void OnNavigationFinish( + const std::vector<GURL>& navigation_redirect_chain); // Clears data specific to the user. void ClearData(); @@ -254,6 +258,10 @@ // internals page. Must outlive `prediction_manager_` and `hints_manager_`. std::unique_ptr<OptimizationGuideLogger> optimization_guide_logger_; + // Keep a reference to this so it stays alive. + scoped_refptr<optimization_guide::OnDeviceModelComponentStateManager> + on_device_component_manager_; + // Manages the storing, loading, and fetching of hints. std::unique_ptr<optimization_guide::ChromeHintsManager> hints_manager_;
diff --git a/chrome/browser/optimization_guide/optimization_guide_keyed_service_browsertest.cc b/chrome/browser/optimization_guide/optimization_guide_keyed_service_browsertest.cc index cee813c..e2dc1fa 100644 --- a/chrome/browser/optimization_guide/optimization_guide_keyed_service_browsertest.cc +++ b/chrome/browser/optimization_guide/optimization_guide_keyed_service_browsertest.cc
@@ -9,8 +9,11 @@ #include "base/logging.h" #include "base/run_loop.h" #include "base/strings/escape.h" +#include "base/test/bind.h" #include "base/test/metrics/histogram_tester.h" +#include "base/test/run_until.h" #include "base/test/scoped_feature_list.h" +#include "base/time/time.h" #include "build/build_config.h" #include "build/chromeos_buildflags.h" #include "chrome/browser/browser_process.h" @@ -26,6 +29,7 @@ #include "components/optimization_guide/core/command_line_top_host_provider.h" #include "components/optimization_guide/core/model_execution/model_execution_features.h" #include "components/optimization_guide/core/model_execution/model_execution_features_controller.h" +#include "components/optimization_guide/core/model_execution/on_device_model_component.h" #include "components/optimization_guide/core/optimization_guide_enums.h" #include "components/optimization_guide/core/optimization_guide_features.h" #include "components/optimization_guide/core/optimization_guide_prefs.h" @@ -51,6 +55,7 @@ namespace { +using optimization_guide::OnDeviceModelComponentStateManager; using optimization_guide::proto::OptimizationType; // A WebContentsObserver that asks whether an optimization type can be applied. @@ -163,6 +168,10 @@ {optimization_guide::features::kOptimizationGuideModelExecution, {}}, {optimization_guide::features::internal::kComposeSettingsVisibility, {}}, + {optimization_guide::features::kLogOnDeviceMetricsOnStartup, + { + {"on_device_startup_metric_delay", "0"}, + }}, {optimization_guide::features::internal:: kTabOrganizationSettingsVisibility, {{"allow_unsigned_user", "true"}}}}, @@ -1155,6 +1164,25 @@ MODEL_EXECUTION_FEATURE_WALLPAPER_SEARCH)); } +IN_PROC_BROWSER_TEST_F(OptimizationGuideKeyedServiceBrowserTest, + LogOnDeviceMetricsAfterStart) { + OptimizationGuideKeyedServiceFactory::GetForProfile(browser()->profile()); + OnDeviceModelComponentStateManager* on_device_component_state_manager = + OnDeviceModelComponentStateManager::GetInstanceForTesting(); + ASSERT_TRUE(on_device_component_state_manager); + + EXPECT_TRUE(base::test::RunUntil([&]() { + return histogram_tester() + ->GetAllSamples( + "OptimizationGuide.ModelExecution." + "OnDeviceModelPerformanceClass") + .size() > 0; + })); + + histogram_tester()->ExpectTotalCount( + "OptimizationGuide.ModelExecution.OnDeviceModelPerformanceClass", 1); +} + #if !BUILDFLAG(IS_ANDROID) && !BUILDFLAG(IS_CHROMEOS_ASH) // CreateGuestBrowser() is not supported for Android or ChromeOS out of the box. IN_PROC_BROWSER_TEST_F(OptimizationGuideKeyedServiceBrowserTest,
diff --git a/chrome/browser/paint_preview/android/javatests/src/org/chromium/chrome/browser/paint_preview/TabbedPaintPreviewTest.java b/chrome/browser/paint_preview/android/javatests/src/org/chromium/chrome/browser/paint_preview/TabbedPaintPreviewTest.java index d8a2822..1e187f7 100644 --- a/chrome/browser/paint_preview/android/javatests/src/org/chromium/chrome/browser/paint_preview/TabbedPaintPreviewTest.java +++ b/chrome/browser/paint_preview/android/javatests/src/org/chromium/chrome/browser/paint_preview/TabbedPaintPreviewTest.java
@@ -24,7 +24,7 @@ import org.chromium.base.Callback; import org.chromium.base.UnguessableToken; -import org.chromium.base.supplier.ObservableSupplier; +import org.chromium.base.supplier.ObservableSupplierImpl; import org.chromium.base.test.util.CallbackHelper; import org.chromium.base.test.util.CommandLineFlags; import org.chromium.base.test.util.CriteriaHelper; @@ -311,21 +311,7 @@ private int mLastToken = TokenHolder.INVALID_TOKEN; public TestControlsVisibilityDelegate() { - super( - new ObservableSupplier<Boolean>() { - @Override - public Boolean addObserver(Callback<Boolean> obs) { - return false; - } - - @Override - public void removeObserver(Callback<Boolean> obs) {} - - @Override - public Boolean get() { - return false; - } - }); + super(new ObservableSupplierImpl<>(false)); } public boolean isPersistent() {
diff --git a/chrome/browser/permissions/permission_manager_browsertest.cc b/chrome/browser/permissions/permission_manager_browsertest.cc index 0515a244..95c1338 100644 --- a/chrome/browser/permissions/permission_manager_browsertest.cc +++ b/chrome/browser/permissions/permission_manager_browsertest.cc
@@ -52,7 +52,7 @@ callback_ = std::move(callback); } - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, @@ -60,7 +60,7 @@ base::RepeatingCallback<void(blink::mojom::PermissionStatus)> callback) override { SubscriptionId result = - permissions::PermissionManager::SubscribePermissionStatusChange( + permissions::PermissionManager::SubscribeToPermissionStatusChange( permission, render_process_host, render_frame_host, requesting_origin, callback); std::move(callback_).Run();
diff --git a/chrome/browser/policy/profile_policy_connector.cc b/chrome/browser/policy/profile_policy_connector.cc index a01f6c89..d4d10fa8 100644 --- a/chrome/browser/policy/profile_policy_connector.cc +++ b/chrome/browser/policy/profile_policy_connector.cc
@@ -255,6 +255,7 @@ void AddInfobarForActiveLocalTestPolicies( content::WebContents* web_contents) { + infobars::ContentInfoBarManager::CreateForWebContents(web_contents); CreateSimpleAlertInfoBar( infobars::ContentInfoBarManager::FromWebContents(web_contents), infobars::InfoBarDelegate::LOCAL_TEST_POLICIES_APPLIED_INFOBAR, nullptr, @@ -293,6 +294,7 @@ void DismissInfobarForActiveLocalTestPolicies( content::WebContents* web_contents) { + infobars::ContentInfoBarManager::CreateForWebContents(web_contents); auto* infobar_manager = infobars::ContentInfoBarManager::FromWebContents(web_contents); const auto it = base::ranges::find(
diff --git a/chrome/browser/predictors/loading_predictor_tab_helper_unittest.cc b/chrome/browser/predictors/loading_predictor_tab_helper_unittest.cc index 3ec25f6..9dcdd45 100644 --- a/chrome/browser/predictors/loading_predictor_tab_helper_unittest.cc +++ b/chrome/browser/predictors/loading_predictor_tab_helper_unittest.cc
@@ -94,7 +94,7 @@ base::BindRepeating([](content::BrowserContext* context) -> std::unique_ptr<KeyedService> { return std::make_unique< - NiceMock<MockOptimizationGuideKeyedService>>(context); + NiceMock<MockOptimizationGuideKeyedService>>(); }))); LoadingPredictorTabHelper::CreateForWebContents(web_contents()); tab_helper_ = LoadingPredictorTabHelper::FromWebContents(web_contents());
diff --git a/chrome/browser/prefs/browser_prefs.cc b/chrome/browser/prefs/browser_prefs.cc index da3656d..78cf778 100644 --- a/chrome/browser/prefs/browser_prefs.cc +++ b/chrome/browser/prefs/browser_prefs.cc
@@ -994,6 +994,11 @@ constexpr char kWebAndAppActivityEnabledForShopping[] = "web_and_app_activity_enabled_for_shopping"; +// Deprecated 12/2023. +#if BUILDFLAG(IS_ANDROID) +const char kTemplatesRandomOrder[] = "content_creation.notes.random_order"; +#endif + // Register local state used only for migration (clearing or moving to a new // key). void RegisterLocalStatePrefsForMigration(PrefRegistrySimple* registry) { @@ -1413,6 +1418,11 @@ // Deprecated 11/2023. registry->RegisterBooleanPref(kWebAndAppActivityEnabledForShopping, true); + + // Deprecated 12/2023. +#if BUILDFLAG(IS_ANDROID) + registry->RegisterListPref(kTemplatesRandomOrder); +#endif } void ClearSyncRequestedPrefAndMaybeMigrate(PrefService* profile_prefs) { @@ -1850,7 +1860,6 @@ #if BUILDFLAG(IS_ANDROID) cdm::MediaDrmStorageImpl::RegisterProfilePrefs(registry); - content_creation::prefs::RegisterProfilePrefs(registry); KnownInterceptionDisclosureInfoBarDelegate::RegisterProfilePrefs(registry); MediaDrmOriginIdManager::RegisterProfilePrefs(registry); NotificationChannelsProviderAndroid::RegisterProfilePrefs(registry); @@ -2667,6 +2676,11 @@ profile_prefs); #endif // !BUILDFLAG(IS_ANDROID) +#if BUILDFLAG(IS_ANDROID) + // Added 12/2023. + profile_prefs->ClearPref(kTemplatesRandomOrder); +#endif + // Please don't delete the following line. It is used by PRESUBMIT.py. // END_MIGRATE_OBSOLETE_PROFILE_PREFS
diff --git a/chrome/browser/readaloud/android/BUILD.gn b/chrome/browser/readaloud/android/BUILD.gn index 3c186f7..86e618d9 100644 --- a/chrome/browser/readaloud/android/BUILD.gn +++ b/chrome/browser/readaloud/android/BUILD.gn
@@ -8,6 +8,7 @@ android_library("java") { sources = [ "java/src/org/chromium/chrome/browser/readaloud/ReadAloudController.java", + "java/src/org/chromium/chrome/browser/readaloud/ReadAloudMetrics.java", "java/src/org/chromium/chrome/browser/readaloud/ReadAloudMiniPlayerSceneLayer.java", "java/src/org/chromium/chrome/browser/readaloud/ReadAloudPrefs.java", "java/src/org/chromium/chrome/browser/readaloud/ReadAloudToolbarButtonController.java", @@ -156,6 +157,7 @@ testonly = true sources = [ "java/src/org/chromium/chrome/browser/readaloud/ReadAloudControllerUnitTest.java", + "java/src/org/chromium/chrome/browser/readaloud/ReadAloudMetricsUnitTest.java", "java/src/org/chromium/chrome/browser/readaloud/ReadAloudMiniPlayerSceneLayerUnitTest.java", "java/src/org/chromium/chrome/browser/readaloud/ReadAloudPrefsUnitTest.java", "java/src/org/chromium/chrome/browser/readaloud/ReadAloudToolbarButtonControllerUnitTest.java", @@ -196,6 +198,7 @@ "//third_party/androidx:androidx_appcompat_appcompat_java", "//third_party/androidx:androidx_test_core_java", "//third_party/androidx:androidx_test_ext_junit_java", + "//third_party/androidx:androidx_test_runner_java", "//third_party/jni_zero:jni_zero_java", "//third_party/junit", "//third_party/mockito:mockito_java",
diff --git a/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudController.java b/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudController.java index c8dd760d..c10bc8f9 100644 --- a/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudController.java +++ b/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudController.java
@@ -196,6 +196,7 @@ @Override public void onSuccess(String url, boolean isReadable, boolean timepointsSupported) { Log.d(TAG, "onSuccess called for %s", url); + ReadAloudMetrics.recordIsPageReadable(isReadable); mReadabilityMap.put(url, isReadable); mTimepointsSupportedMap.put(url, timepointsSupported); mPendingRequests.remove(url); @@ -205,6 +206,7 @@ @Override public void onFailure(String url, Throwable t) { Log.d(TAG, "onFailure called for %s because %s", url, t); + ReadAloudMetrics.recordIsPageReadable(false); mPendingRequests.remove(url); } }; @@ -280,6 +282,7 @@ @VisibleForTesting(otherwise = VisibleForTesting.PACKAGE_PRIVATE) public void maybeCheckReadability(GURL url) { if (!isURLReadAloudSupported(url)) { + ReadAloudMetrics.recordIsPageReadable(false); return; }
diff --git a/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudControllerUnitTest.java b/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudControllerUnitTest.java index b4c5d2da..09909dd4d 100644 --- a/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudControllerUnitTest.java +++ b/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudControllerUnitTest.java
@@ -39,6 +39,7 @@ import org.chromium.base.supplier.ObservableSupplierImpl; import org.chromium.base.test.BaseRobolectricTestRunner; +import org.chromium.base.test.util.HistogramWatcher; import org.chromium.base.test.util.JniMocker; import org.chromium.chrome.browser.browser_controls.BrowserControlsSizer; import org.chromium.chrome.browser.flags.ChromeFeatureList; @@ -1080,6 +1081,28 @@ assertEquals(mController.getReadabilitySupplier().get(), testUrl); } + @Test + public void testMetricRecorded_readability() { + final String histogramName = ReadAloudMetrics.READABILITY_SUCCESS; + + var histogram = HistogramWatcher.newSingleRecordWatcher(histogramName, true); + mController.maybeCheckReadability(sTestGURL); + verify(mHooksImpl, times(1)) + .isPageReadable(eq(sTestGURL.getSpec()), mCallbackCaptor.capture()); + mCallbackCaptor.getValue().onSuccess(sTestGURL.getSpec(), true, false); + histogram.assertExpected(); + + histogram = HistogramWatcher.newSingleRecordWatcher(histogramName, false); + mCallbackCaptor.getValue().onSuccess(sTestGURL.getSpec(), false, false); + histogram.assertExpected(); + + histogram = HistogramWatcher.newSingleRecordWatcher(histogramName, false); + mCallbackCaptor + .getValue() + .onFailure(sTestGURL.getSpec(), new Throwable("Something went wrong")); + histogram.assertExpected(); + } + private void onPlaybackSuccess(Playback playback) { mPlaybackCallbackCaptor.getValue().onSuccess(playback); resolvePromises();
diff --git a/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudMetrics.java b/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudMetrics.java new file mode 100644 index 0000000..55e96ec --- /dev/null +++ b/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudMetrics.java
@@ -0,0 +1,17 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +package org.chromium.chrome.browser.readaloud; + +import androidx.annotation.VisibleForTesting; + +import org.chromium.base.metrics.RecordHistogram; + +public class ReadAloudMetrics { + @VisibleForTesting public static String READABILITY_SUCCESS = "ReadAloud.IsPageReadable"; + + public static void recordIsPageReadable(boolean successful) { + RecordHistogram.recordBooleanHistogram(READABILITY_SUCCESS, successful); + } +}
diff --git a/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudMetricsUnitTest.java b/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudMetricsUnitTest.java new file mode 100644 index 0000000..39fe82c4 --- /dev/null +++ b/chrome/browser/readaloud/android/java/src/org/chromium/chrome/browser/readaloud/ReadAloudMetricsUnitTest.java
@@ -0,0 +1,33 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +package org.chromium.chrome.browser.readaloud; + +import androidx.test.filters.SmallTest; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.robolectric.annotation.Config; + +import org.chromium.base.test.BaseRobolectricTestRunner; +import org.chromium.base.test.util.HistogramWatcher; + +/** Unit tests for {@link ReadAloudMetrics}. */ +@RunWith(BaseRobolectricTestRunner.class) +@Config(manifest = Config.NONE) +public class ReadAloudMetricsUnitTest { + @Test + @SmallTest + public void testRecordIsPageReadable() { + final String histogramName = ReadAloudMetrics.READABILITY_SUCCESS; + + var histogram = HistogramWatcher.newSingleRecordWatcher(histogramName, true); + ReadAloudMetrics.recordIsPageReadable(true); + histogram.assertExpected(); + + histogram = HistogramWatcher.newSingleRecordWatcher(histogramName, false); + ReadAloudMetrics.recordIsPageReadable(false); + histogram.assertExpected(); + } +}
diff --git a/chrome/browser/resources/ash/settings/device_page/input_device_settings_shared.css b/chrome/browser/resources/ash/settings/device_page/input_device_settings_shared.css index 7bbde9b..e7893c3 100644 --- a/chrome/browser/resources/ash/settings/device_page/input_device_settings_shared.css +++ b/chrome/browser/resources/ash/settings/device_page/input_device_settings_shared.css
@@ -44,9 +44,9 @@ } cr-dialog [slot='button-container'] { - padding: 0 32px 28px 32px; display: flex; - gap: 8px; + justify-content: space-between; + padding: 0 32px 28px 32px; } cr-dialog [slot='body'] { @@ -57,7 +57,8 @@ padding: 32px 32px 0 32px; } -cr-dialog #cancelButton { +cr-dialog #cancelButton, +cr-dialog #editButton { background-color: var(--cros-bg-color); border: solid 1px var(--cros-button-stroke-color-secondary); }
diff --git a/chrome/browser/resources/ash/settings/device_page/key_combination_input_dialog.html b/chrome/browser/resources/ash/settings/device_page/key_combination_input_dialog.html index cf2e3ebf..778e1bb4 100644 --- a/chrome/browser/resources/ash/settings/device_page/key_combination_input_dialog.html +++ b/chrome/browser/resources/ash/settings/device_page/key_combination_input_dialog.html
@@ -20,6 +20,11 @@ text-align: center; padding-bottom: 24px; } + + .right-button-group { + display: flex; + gap: 8px; + } </style> <cr-dialog id="keyCombinationInputDialog"> <div slot="title">$i18n{keyCombinationDialogTitle}</div> @@ -32,24 +37,23 @@ shortcut-input-provider="[[getShortcutProvider()]]" show-separator="true"> </shortcut-input> - <template is="dom-if" if="[[shouldShowEditButton_(isCapturing)]]"> - <div class="edit-icon-container"> - <cr-icon-button class="edit-button" - iron-icon="os-settings:edit" - on-click="onEditButtonClicked_"> - </cr-icon-button> - </div> - </template> </div> </div> <div slot="button-container"> - <div> + <div class="left-button-group"> + <template is="dom-if" if="[[shouldShowEditButton_(isCapturing)]]"> + <cr-button class="edit-button" + id="editButton" + on-click="onEditButtonClicked_"> + $i18n{buttonRemappingDialogChangeLabel} + </cr-button> + </template> + </div> + <div class="right-button-group"> <cr-button id="cancelButton" on-click="cancelDialogClicked_"> $i18n{buttonRemappingDialogCancelLabel} </cr-button> - </div> - <div> <cr-button id="saveButton" class="action-button" on-click="saveDialogClicked_" disabled$="[[shouldDisableSaveButton_(inputKeyEvent)]]">
diff --git a/chrome/browser/resources/ash/settings/os_people_page/account_manager_settings_card.html b/chrome/browser/resources/ash/settings/os_people_page/account_manager_settings_card.html index 9ed0255..df70dc5 100644 --- a/chrome/browser/resources/ash/settings/os_people_page/account_manager_settings_card.html +++ b/chrome/browser/resources/ash/settings/os_people_page/account_manager_settings_card.html
@@ -101,7 +101,7 @@ </template> <localized-link localized-string= - "[[getManagementDescription_(isChildUser_, deviceAccount_)]]" + "[[getManagementDescription_(isChildUser_, deviceAccount)]]" link-url="$i18nRaw{accountManagerChromeUIManagementURL}"> </localized-link> </div> @@ -113,7 +113,7 @@ aria-describedby="deviceAccountEmail"> <div class="profile-icon device-account-icon" aria-hidden="true" - style="background-image: [[getIconImageSet_(deviceAccount_.pic)]]"> + style="background-image: [[getIconImageSet_(deviceAccount)]]"> <template is="dom-if" if="[[shouldShowManagedBadge_(isDeviceAccountManaged_, isChildUser_)]]"> @@ -123,10 +123,10 @@ </template> </div> <span id="deviceAccountFullName" class="primary" aria-hidden="true"> - [[deviceAccount_.fullName]] + [[deviceAccount.fullName]] </span> <span id="deviceAccountEmail" class="secondary" aria-hidden="true"> - [[deviceAccount_.email]] + [[deviceAccount.email]] </span> </div> </settings-card>
diff --git a/chrome/browser/resources/ash/settings/os_people_page/account_manager_settings_card.ts b/chrome/browser/resources/ash/settings/os_people_page/account_manager_settings_card.ts index e828bd4..8c9bac4 100644 --- a/chrome/browser/resources/ash/settings/os_people_page/account_manager_settings_card.ts +++ b/chrome/browser/resources/ash/settings/os_people_page/account_manager_settings_card.ts
@@ -24,7 +24,7 @@ import {isChild} from '../common/load_time_booleans.js'; import {ParentalControlsBrowserProxyImpl} from '../parental_controls_page/parental_controls_browser_proxy.js'; -import {Account, AccountManagerBrowserProxy, AccountManagerBrowserProxyImpl} from './account_manager_browser_proxy.js'; +import {Account} from './account_manager_browser_proxy.js'; import {getTemplate} from './account_manager_settings_card.html.js'; const AccountManagerSettingsCardElementBase = @@ -45,7 +45,7 @@ /** * Primary / Device account. */ - deviceAccount_: Object, + deviceAccount: Object, isChildUser_: { type: Boolean, @@ -87,40 +87,11 @@ }; } - private browserProxy_: AccountManagerBrowserProxy; - private deviceAccount_: Account|null; + deviceAccount: Account|null; private isChildUser_: boolean; private isDeviceAccountManaged_: boolean; private isSecondaryGoogleAccountSigninAllowed_: boolean; - constructor() { - super(); - - this.browserProxy_ = AccountManagerBrowserProxyImpl.getInstance(); - } - - override connectedCallback(): void { - super.connectedCallback(); - - this.addWebUiListener('accounts-changed', this.refreshAccounts_.bind(this)); - } - - override ready(): void { - super.ready(); - this.refreshAccounts_(); - } - - private async refreshAccounts_(): Promise<void> { - const accounts = await this.browserProxy_.getAccounts(); - this.set('accounts_', accounts); - const deviceAccount = accounts.find(account => account.isDeviceAccount); - if (!deviceAccount) { - console.error('Cannot find device account.'); - return; - } - this.deviceAccount_ = deviceAccount; - } - private onManagedIconClick_(): void { if (this.isChildUser_) { ParentalControlsBrowserProxyImpl.getInstance().launchFamilyLinkSettings(); @@ -138,11 +109,11 @@ if (this.isChildUser_) { return this.i18nAdvanced('accountManagerManagementDescription'); } - if (!this.deviceAccount_) { + if (!this.deviceAccount) { return ''; } - assertExists(this.deviceAccount_.organization); - if (!this.deviceAccount_.organization) { + assertExists(this.deviceAccount.organization); + if (!this.deviceAccount.organization) { if (this.isDeviceAccountManaged_) { console.error( 'The device account is managed, but the organization is not set.'); @@ -154,7 +125,7 @@ // Where href will be set by <localized-link>. return this.i18nAdvanced('accountManagerManagementDescription', { substitutions: [ - this.deviceAccount_.organization, + this.deviceAccount.organization, ], }); } @@ -170,8 +141,11 @@ /** * @return a CSS image-set for multiple scale factors. */ - private getIconImageSet_(iconUrl: string): string { - return getImage(iconUrl); + private getIconImageSet_(): string { + if (!this.deviceAccount) { + return ''; + } + return getImage(this.deviceAccount.pic); } }
diff --git a/chrome/browser/resources/ash/settings/os_people_page/additional_accounts_settings_card.html b/chrome/browser/resources/ash/settings/os_people_page/additional_accounts_settings_card.html index 5c20e68..a45c2b5 100644 --- a/chrome/browser/resources/ash/settings/os_people_page/additional_accounts_settings_card.html +++ b/chrome/browser/resources/ash/settings/os_people_page/additional_accounts_settings_card.html
@@ -137,7 +137,7 @@ <!-- Secondary Accounts list --> <template is="dom-repeat" id="accountList" - items="[[getSecondaryAccounts_(accounts_)]]"> + items="[[getSecondaryAccounts_(accounts)]]"> <div class="settings-box" role="listitem"> <div class="profile-icon" style="background-image: [[getIconImageSet_(item.pic)]]">
diff --git a/chrome/browser/resources/ash/settings/os_people_page/additional_accounts_settings_card.ts b/chrome/browser/resources/ash/settings/os_people_page/additional_accounts_settings_card.ts index e9b841f..ea9003f 100644 --- a/chrome/browser/resources/ash/settings/os_people_page/additional_accounts_settings_card.ts +++ b/chrome/browser/resources/ash/settings/os_people_page/additional_accounts_settings_card.ts
@@ -59,7 +59,7 @@ static get properties() { return { - accounts_: { + accounts: { type: Array, value() { return []; @@ -67,11 +67,6 @@ }, /** - * Primary / Device account. - */ - deviceAccount_: Object, - - /** * The targeted account for menu operations. */ actionMenuAccount_: Object, @@ -129,10 +124,9 @@ }; } - private accounts_: Account[]; + accounts: Account[]; private actionMenuAccount_: Account|null; private browserProxy_: AccountManagerBrowserProxy; - private deviceAccount_: Account|null; private isArcAccountRestrictionsEnabled_: boolean; private isChildUser_: boolean; private isDeviceAccountManaged_: boolean; @@ -144,17 +138,6 @@ this.browserProxy_ = AccountManagerBrowserProxyImpl.getInstance(); } - override connectedCallback(): void { - super.connectedCallback(); - - this.addWebUiListener('accounts-changed', this.refreshAccounts_.bind(this)); - } - - override ready(): void { - super.ready(); - this.refreshAccounts_(); - } - override currentRouteChanged(newRoute: Route): void { if (newRoute !== routes.OS_PEOPLE) { return; @@ -163,18 +146,6 @@ this.attemptDeepLink(); } - private async refreshAccounts_(): Promise<void> { - const accounts = await this.browserProxy_.getAccounts(); - this.set('accounts_', accounts); - const deviceAccount = accounts.find(account => account.isDeviceAccount); - - if (!deviceAccount) { - console.error('Cannot find device account.'); - return; - } - this.deviceAccount_ = deviceAccount; - } - /** * @return accounts list header (e.g. 'Secondary accounts' for * regular users or 'School accounts' for child users). @@ -204,7 +175,7 @@ private addAccount_(): void { recordSettingChange( - Setting.kAddAccount, {intValue: this.accounts_.length + 1}); + Setting.kAddAccount, {intValue: this.accounts.length + 1}); this.browserProxy_.addAccount(); } @@ -249,12 +220,11 @@ } private shouldShowSecondaryAccountsList_(): boolean { - return this.accounts_.filter(account => !account.isDeviceAccount).length === - 0; + return this.getSecondaryAccounts_().length === 0; } private getSecondaryAccounts_(): Account[] { - return this.accounts_.filter(account => !account.isDeviceAccount); + return this.accounts.filter(account => !account.isDeviceAccount); } private getAddAccountLabel_(): string {
diff --git a/chrome/browser/resources/ash/settings/os_people_page/os_people_page.html b/chrome/browser/resources/ash/settings/os_people_page/os_people_page.html index 134cd01..9c5de7f 100644 --- a/chrome/browser/resources/ash/settings/os_people_page/os_people_page.html +++ b/chrome/browser/resources/ash/settings/os_people_page/os_people_page.html
@@ -46,14 +46,15 @@ </style> <os-settings-animated-pages id="pages" section="[[section_]]"> - <!-- Show settings card is RavampWayfinding is enabled. --> <template is="dom-if" if="[[isRevampWayfindingEnabled_]]"> <div route-path="default"> <account-manager-settings-card - prefs="{{prefs}}"> + prefs="{{prefs}}" + device-account="[[deviceAccount_]]"> </account-manager-settings-card> <additional-accounts-settings-card - prefs="{{prefs}}"> + prefs="{{prefs}}" + accounts="[[accounts_]]"> </additional-accounts-settings-card> <template is="dom-if" if="[[showParentalControls_]]"> <parental-controls-settings-card
diff --git a/chrome/browser/resources/ash/settings/os_people_page/os_people_page.ts b/chrome/browser/resources/ash/settings/os_people_page/os_people_page.ts index 5df1b32..a0c8a52 100644 --- a/chrome/browser/resources/ash/settings/os_people_page/os_people_page.ts +++ b/chrome/browser/resources/ash/settings/os_people_page/os_people_page.ts
@@ -25,6 +25,7 @@ import {ProfileInfo, ProfileInfoBrowserProxyImpl} from '/shared/settings/people_page/profile_info_browser_proxy.js'; import {SyncBrowserProxy, SyncBrowserProxyImpl, SyncStatus} from '/shared/settings/people_page/sync_browser_proxy.js'; import {convertImageSequenceToPng} from 'chrome://resources/ash/common/cr_picture/png.js'; +import {assert} from 'chrome://resources/js/assert.js'; import {sendWithPromise} from 'chrome://resources/js/cr.js'; import {getImage} from 'chrome://resources/js/icon.js'; import {loadTimeData} from 'chrome://resources/js/load_time_data.js'; @@ -72,6 +73,20 @@ */ syncStatus: Object, + accounts_: { + type: Array, + value() { + return []; + }, + }, + + deviceAccount_: { + type: Object, + value() { + return null; + }, + }, + authTokenInfo_: { type: Object, observer: 'onAuthTokenChanged_', @@ -81,6 +96,7 @@ * The current profile icon URL. Usually a data:image/png URL. */ profileIconUrl_: String, + profileName_: String, profileEmail_: String, @@ -155,6 +171,8 @@ } syncStatus: SyncStatus; + private accounts_: Account[]; + private deviceAccount_: Account|null; private authTokenInfo_: chrome.quickUnlockPrivate.TokenInfo|undefined; private profileIconUrl_: string; private profileName_: string; @@ -162,7 +180,7 @@ private profileLabel_: string; private fingerprintUnlockEnabled_: boolean; private isAccountManagerEnabled_: boolean; - private isRevampWayfindingEnabled_: boolean; + private readonly isRevampWayfindingEnabled_: boolean; private showParentalControls_: boolean; private section_: Section; private showPasswordPromptDialog_: boolean; @@ -353,27 +371,30 @@ private async updateAccounts_(): Promise<void> { const accounts = await AccountManagerBrowserProxyImpl.getInstance().getAccounts(); + this.accounts_ = accounts; + // The user might not have any GAIA accounts (e.g. guest mode or Active // Directory). In these cases the profile row is hidden, so there's nothing // to do. if (accounts.length === 0) { return; } - this.profileName_ = accounts[0].fullName; - this.profileEmail_ = accounts[0].email; - this.profileIconUrl_ = accounts[0].pic; - await this.setProfileLabel(accounts); - } + // First account is always the device account. + assert( + accounts[0].isDeviceAccount, + 'The device account should always be first.'); + this.deviceAccount_ = accounts[0]; + this.profileName_ = this.deviceAccount_.fullName; + this.profileEmail_ = this.deviceAccount_.email; + this.profileIconUrl_ = this.deviceAccount_.pic; - private async setProfileLabel(accounts: Account[]): Promise<void> { // Template: "$1 Google accounts" with correct plural of "account". const labelTemplate = await sendWithPromise( - 'getPluralString', 'profileLabel', accounts.length); - + 'getPluralString', 'profileLabel', this.accounts_.length); // Final output: "X Google accounts" this.profileLabel_ = loadTimeData.substituteString( - labelTemplate, accounts[0].email, accounts.length); + labelTemplate, this.profileEmail_, this.accounts_.length); } /**
diff --git a/chrome/browser/resources/chromeos/accessibility/definitions/tabs.d.ts b/chrome/browser/resources/chromeos/accessibility/definitions/tabs.d.ts index 3e1e12e3..4c59fe7 100644 --- a/chrome/browser/resources/chromeos/accessibility/definitions/tabs.d.ts +++ b/chrome/browser/resources/chromeos/accessibility/definitions/tabs.d.ts
@@ -129,24 +129,26 @@ export function duplicate(tabId: number, callback: (tab: Tab) => void): void; - export function query(queryInfo: { - active?: boolean, - pinned?: boolean, - audible?: boolean, - muted?: boolean, - highlighted?: boolean, - discarded?: boolean, - autoDiscardable?: boolean, - currentWindow?: boolean, - lastFocusedWindow?: boolean, - status?: TabStatus, - title?: string, - url?: string|string[], - groupId?: number, - windowId?: number, - windowType?: WindowType, - index?: number, - }): Promise<Tab[]>; + export function query( + queryInfo: { + active?: boolean, + pinned?: boolean, + audible?: boolean, + muted?: boolean, + highlighted?: boolean, + discarded?: boolean, + autoDiscardable?: boolean, + currentWindow?: boolean, + lastFocusedWindow?: boolean, + status?: TabStatus, + title?: string, + url?: string|string[], + groupId?: number, + windowId?: number, + windowType?: WindowType, + index?: number, + }, + callback: (tabs: Tab[]) => void): void; export function highlight(highlightInfo: { windowId?: number, tabs: number[]|number,
diff --git a/chrome/browser/resources/chromeos/accessibility/select_to_speak/BUILD.gn b/chrome/browser/resources/chromeos/accessibility/select_to_speak/BUILD.gn index 646a340..840bca6 100644 --- a/chrome/browser/resources/chromeos/accessibility/select_to_speak/BUILD.gn +++ b/chrome/browser/resources/chromeos/accessibility/select_to_speak/BUILD.gn
@@ -34,6 +34,7 @@ "input_handler.ts", "ui_manager.ts", "prefs_manager.ts", + "select_to_speak.ts", ] # Add TS files needed from ../common/ here. @@ -43,9 +44,6 @@ "tree_walker.ts", ] -# JS files required for ts build. -js_deps = [ "select_to_speak.js" ] - # Root dir must be the parent directory so it can reach common. ts_library("ts_build") { root_dir = "../" @@ -54,6 +52,7 @@ definitions = [ "../definitions/tts.d.ts", "//tools/typescript/definitions/metrics_private.d.ts", + "//tools/typescript/definitions/context_menus.d.ts", "../definitions/automation.d.ts", "../definitions/extensions.d.ts", "../definitions/runtime.d.ts", @@ -68,9 +67,6 @@ ] in_files = [] - foreach(_js_file, js_deps) { - in_files += [ "select_to_speak/" + _js_file ] - } foreach(_ts_file, ts_modules) { in_files += [ "select_to_speak/" + _ts_file ] } @@ -92,7 +88,6 @@ "checked.png", "earcons/null_selection.ogg", "select_to_speak-2x.svg", - "select_to_speak.js", "sts-icon-128.png", "sts-icon-16.png", "sts-icon-48.png",
diff --git a/chrome/browser/resources/chromeos/accessibility/select_to_speak/input_handler.ts b/chrome/browser/resources/chromeos/accessibility/select_to_speak/input_handler.ts index cda202e6..917c956 100644 --- a/chrome/browser/resources/chromeos/accessibility/select_to_speak/input_handler.ts +++ b/chrome/browser/resources/chromeos/accessibility/select_to_speak/input_handler.ts
@@ -136,11 +136,11 @@ document.addEventListener('copy', evt => this.onClipboardCopy_(evt)); chrome.accessibilityPrivate.onSelectToSpeakKeysPressedChanged.addListener( (keysPressed) => { - this.onKeysPressedChanged_(new Set(keysPressed)); + this.onKeysPressedChanged(new Set(keysPressed)); }); chrome.accessibilityPrivate.onSelectToSpeakMouseChanged.addListener( (eventType, mouseX, mouseY) => { - this.onMouseEvent_(eventType, mouseX, mouseY); + this.onMouseEvent(eventType, mouseX, mouseY); }); } @@ -180,8 +180,9 @@ * coordinates. * @param mouseY The mouse y coordinate in global screen * coordinates. + * Visible for testing. */ - private onMouseEvent_( + onMouseEvent( type: chrome.accessibilityPrivate.SyntheticMouseEventType, mouseX: number, mouseY: number): void { if (type === chrome.accessibilityPrivate.SyntheticMouseEventType.PRESS) { @@ -272,7 +273,7 @@ /** * Visible for testing. */ - private onKeysPressedChanged_(keysCurrentlyPressed: Set<number>) : void { + onKeysPressedChanged(keysCurrentlyPressed: Set<number>): void { if (keysCurrentlyPressed.size > this.keysCurrentlyDown_.size) { // If a key was pressed. for (const key of keysCurrentlyPressed) {
diff --git a/chrome/browser/resources/chromeos/accessibility/select_to_speak/select_to_speak.js b/chrome/browser/resources/chromeos/accessibility/select_to_speak/select_to_speak.ts similarity index 83% rename from chrome/browser/resources/chromeos/accessibility/select_to_speak/select_to_speak.js rename to chrome/browser/resources/chromeos/accessibility/select_to_speak/select_to_speak.ts index 7ebc9db3..a6a9bd5 100644 --- a/chrome/browser/resources/chromeos/accessibility/select_to_speak/select_to_speak.js +++ b/chrome/browser/resources/chromeos/accessibility/select_to_speak/select_to_speak.ts
@@ -15,14 +15,13 @@ import {PrefsManager} from './prefs_manager.js'; import {SelectToSpeakConstants} from './select_to_speak_constants.js'; import {TtsManager} from './tts_manager.js'; -import {UiManager} from './ui_manager.js'; +import {SelectToSpeakUiListener, UiManager} from './ui_manager.js'; -const AutomationNode = chrome.automation.AutomationNode; -const AutomationEvent = chrome.automation.AutomationEvent; -const EventType = chrome.automation.EventType; -const RoleType = chrome.automation.RoleType; -const AccessibilityFeature = chrome.accessibilityPrivate.AccessibilityFeature; -const SelectToSpeakState = chrome.accessibilityPrivate.SelectToSpeakState; +import AutomationNode = chrome.automation.AutomationNode; +import AutomationEvent = chrome.automation.AutomationEvent; +import EventType = chrome.automation.EventType; +import RoleType = chrome.automation.RoleType; +import SelectToSpeakState = chrome.accessibilityPrivate.SelectToSpeakState; // Matches one of the known GSuite apps which need the clipboard to find and // read selected text. Includes sandbox and non-sandbox versions. @@ -35,11 +34,11 @@ * pages are included, because some are not known to have a problem with * selection: Forms is not included since it's relatively similar to any HTML * page, for example. - * @param {AutomationNode=} node The node to check - * @return {?AutomationNode} The root node of the GSuite app, or null if none is - * found. + * @param node The node to check + * @return The root node of the GSuite app, or null if none is found. */ -export function getGSuiteAppRoot(node) { +export function getGSuiteAppRoot(node: AutomationNode| + undefined): AutomationNode|null { while (node !== undefined && node.root !== undefined) { if (node.root.url !== undefined && GSUITE_APP_REGEXP.exec(node.root.url)) { return node.root; @@ -51,22 +50,41 @@ /** * Select-to-speak component extension controller. - * @implements {SelectToSpeakUiListener} */ -export class SelectToSpeak { +export class SelectToSpeak implements SelectToSpeakUiListener { + private currentCharIndex_: number; + private currentNodeGroupIndex_: number; + // TODO(b/314203187): In many places we've added a currentNodeGroupItem_!, + // determine if this is correct or if a check should be added. + private currentNodeGroupItem_: ParagraphUtils.NodeGroupItem|null; + private currentNodeGroupItemIndex_: number; + private currentNodeGroups_: ParagraphUtils.NodeGroup[]; + private currentNodeWord_: {start: number, end: number}|null; + private desktop_: chrome.automation.AutomationNode|undefined; + private inputHandler_: InputHandler|null; + private intervalId_: number|undefined; + private nullSelectionTone_: HTMLAudioElement; + private onStateChangeRequestedCallbackForTest_: (() => void)|null; + private prefsManager_: PrefsManager; + private scrollToSpokenNode_: boolean; + private speechRateMultiplier_: number; + private state_: SelectToSpeakState; + private supportsNavigationPanel_: boolean; + private ttsManager_: TtsManager; + private uiManager_: UiManager; + private onLoadDesktopCallbackForTest_: (() => void)|null; + /** Please keep fields in alphabetical order. */ constructor() { /** * The start char index of the word to be spoken. The index is relative * to the text content of the current node group. - * @private {number} */ this.currentCharIndex_ = -1; /** * The index for the node group currently being spoken in * |this.currentNodeGroups_|. - * @private {number} */ this.currentNodeGroupIndex_ = -1; @@ -75,7 +93,6 @@ * representation of the original input nodes, but may not be the same. For * example, an input inline text node will be represented by its static text * node in the node group item. - * @private {?ParagraphUtils.NodeGroupItem} */ this.currentNodeGroupItem_ = null; @@ -86,7 +103,6 @@ * |this.currentNodeGroupItemIndex_| can be used to get * |this.currentNodeGroupItem_| from the current node group. However, in * Gsuite, we will have node group items outside of a node group. - * @private {number} */ this.currentNodeGroupItemIndex_ = -1; @@ -95,82 +111,61 @@ * pass one node group at a time to the TTS engine. Note that we do not use * node groups for user-selected text in Gsuite. See more details in * readNodesBetweenPositions_. - * @private {!Array<!ParagraphUtils.NodeGroup>} */ this.currentNodeGroups_ = []; /** * The indexes within the current node group item representing the word * currently being spoken. Only updated if word highlighting is enabled. - * @private {?{start: number, end: number}} */ this.currentNodeWord_ = null; - /** @private {chrome.automation.AutomationNode} */ this.desktop_; - /** - * Feature flag controlling STS language detection integration. - * @private {boolean} - */ - this.enableLanguageDetectionIntegration_ = false; - - /** @private {InputHandler} */ this.inputHandler_ = null; /** * The interval ID from a call to setInterval, which is set whenever * speech is in progress. - * @private {number|undefined} */ this.intervalId_; - /** @private {Audio} */ - this.null_selection_tone_ = new Audio('earcons/null_selection.ogg'); + this.nullSelectionTone_ = new Audio('earcons/null_selection.ogg'); /** * Function to be called when a state change request is received from the * accessibilityPrivate API. - * @protected {?function()} */ this.onStateChangeRequestedCallbackForTest_ = null; - /** @private {PrefsManager} */ this.prefsManager_ = new PrefsManager(); - /** @private {boolean} */ this.scrollToSpokenNode_ = false; - /** @private {number} Speech rate multiplier. */ + /** Speech rate multiplier. */ this.speechRateMultiplier_ = 1.0; /** * The current state of the SelectToSpeak extension, from * SelectToSpeakState. - * @private {!chrome.accessibilityPrivate.SelectToSpeakState} */ this.state_ = SelectToSpeakState.INACTIVE; /** * Whether the current nodes support use of the navigation panel. - * @private {boolean} */ this.supportsNavigationPanel_ = true; - /** @private {!TtsManager} */ this.ttsManager_ = new TtsManager(); - /** @private {!UiManager} */ - this.uiManager_ = new UiManager(this.prefsManager_, this /* listener */); + this.uiManager_ = new UiManager(this.prefsManager_, /*listener=*/ this); - /** @private {?function()} */ this.onLoadDesktopCallbackForTest_ = null; this.init_(); } - /** @private */ - init_() { + private init_(): void { chrome.automation.getDesktop(desktop => { this.desktop_ = desktop; @@ -195,7 +190,7 @@ chrome.contextMenus.create({ title: chrome.i18n.getMessage( 'select_to_speak_listen_context_menu_option_text'), - contexts: ['selection'], + contexts: [chrome.contextMenus.ContextType.SELECTION], onclick: () => { this.getFocusedNodeAndSpeakSelectedText_(); }, @@ -208,9 +203,8 @@ /** * Gets the node group currently being spoken. - * @return {!ParagraphUtils.NodeGroup|undefined} */ - getCurrentNodeGroup_() { + private getCurrentNodeGroup_(): ParagraphUtils.NodeGroup|undefined { if (this.currentNodeGroups_.length === 0) { return undefined; } @@ -218,23 +212,11 @@ } /** - * Gets the last node group from current selection. - * @return {!ParagraphUtils.NodeGroup|undefined} - */ - getLastNodeGroup_() { - if (this.currentNodeGroups_.length === 0) { - return undefined; - } - return this.currentNodeGroups_[this.currentNodeGroups_.length - 1]; - } - - /** * Determines if navigation controls should be shown (and other related * functionality, such as auto-dismiss and click-to-navigate to sentence, * should be activated) based on feature flag and user setting. - * @private */ - shouldShowNavigationControls_() { + private shouldShowNavigationControls_(): boolean { return this.prefsManager_.navigationControlsEnabled() && this.supportsNavigationPanel_; } @@ -243,10 +225,9 @@ * Called in response to our hit test after the mouse is released, * when the user is in a mode where Select-to-speak is capturing * mouse events (for example holding down Search). - * @param {!AutomationEvent} evt The automation event. - * @private + * @param evt The automation event from the hit test. */ - onAutomationHitTest_(evt) { + private onAutomationHitTest_(evt: AutomationEvent): void { // Walk up to the nearest window, web area, toolbar, or dialog that the // hit node is contained inside. Only speak objects within that // container. In the future we might include other container-like @@ -261,8 +242,8 @@ root = root.parent; } - var rect = this.inputHandler_.getMouseRect(); - var nodes = []; + var rect = this.inputHandler_!.getMouseRect(); + var nodes: chrome.automation.AutomationNode[] = []; chrome.automation.getFocus(focusedNode => { // In some cases, e.g. ARC++, the window received in the hit test request, // which is computed based on which window is the event handler for the @@ -272,7 +253,7 @@ // so, look for classname exoshell on the root or root parent to confirm // that a node is in ARC++. if (!NodeUtils.findAllMatching(root, rect, nodes) && focusedNode && - focusedNode.root.role !== RoleType.DESKTOP) { + focusedNode.root!.role !== RoleType.DESKTOP) { NodeUtils.findAllMatching(focusedNode.root, rect, nodes); } if (nodes.length === 1 && UiManager.isTrayButton(nodes[0])) { @@ -288,14 +269,15 @@ // expand to entire paragraph. nodes = NodeUtils.getAllNodesInParagraph(nodes[0]); } - this.startSpeechQueue_(nodes, {clearFocusRing: true}); + this.startSpeechQueue_(nodes, { + clearFocusRing: true, + }); MetricsUtils.recordStartEvent( MetricsUtils.StartSpeechMethod.MOUSE, this.prefsManager_); }); } - /** @private */ - getFocusedNodeAndSpeakSelectedText_() { + private getFocusedNodeAndSpeakSelectedText_(): void { chrome.automation.getFocus( focusedNode => this.requestSpeakSelectedText_( MetricsUtils.StartSpeechMethod.CONTEXT_MENU, focusedNode)); @@ -304,11 +286,12 @@ /** * Queues up selected text for reading by finding the Position objects * representing the selection. - * @private - * @param {MetricsUtils.StartSpeechMethod} method the method that + * @param method the method that * caused the text to speak. */ - requestSpeakSelectedText_(method, focusedNode) { + private requestSpeakSelectedText_( + method: MetricsUtils.StartSpeechMethod, + focusedNode: chrome.automation.AutomationNode): void { // If nothing is selected, return early. Check if the focused node has // textSelStart and textSelEnd. For native UI like the omnibox, the root // might not have a selectionStartObject and selectionEndObject. Therefore @@ -327,9 +310,9 @@ } let startObject; - let startOffset; + let startOffset = 0; let endObject; - let endOffset; + let endOffset = 0; // Use selectionStartObject/selectionEndObject if available. Otherwise, // use textSelStart/textSelEnd to get the selection offset. if (hasSelectionObjects) { @@ -398,22 +381,22 @@ /** * Reads nodes between positions. - * @param {NodeUtils.Position} firstPosition The first position at which to - * start reading. - * @param {NodeUtils.Position} lastPosition The last position at which to - * stop reading. - * @param {MetricsUtils.StartSpeechMethod | null} method the method used to + * @param firstPosition The first position at which to start reading. + * @param lastPosition The last position at which to stop reading. + * @param method the method used to * activate the speech, null if not actived by user. - * @param {AutomationNode=} focusedNode The node with user focus. - * @private + * @param focusedNode The node with user focus. */ - readNodesBetweenPositions_(firstPosition, lastPosition, method, focusedNode) { + private readNodesBetweenPositions_( + firstPosition: NodeUtils.Position, lastPosition: NodeUtils.Position, + method: MetricsUtils.StartSpeechMethod|null, + focusedNode: AutomationNode|undefined): void { const nodes = []; let selectedNode = firstPosition.node; // If the method is set, a user requested the speech. const userRequested = method !== null; /**@type {number} */ - const methodNumber = method !== null ? method : -1; + const methodNumber: number = method !== null ? method : -1; // Certain nodes such as omnibox store text value in the value property, // instead of the name property. The getNodeName method in ParagraphUtils // does handle this case properly, so use this static method to get text @@ -495,7 +478,7 @@ if (!gsuiteAppRootNode || gsuiteAppRootNode.url === undefined) { return; } - this.inputHandler_.onRequestReadClipboardData(); + this.inputHandler_!.onRequestReadClipboardData(); this.currentNodeGroupItem_ = new ParagraphUtils.NodeGroupItem(gsuiteAppRootNode, 0, false); if (tabs.length > 0 && tabs[0].url === gsuiteAppRootNode.url) { @@ -521,15 +504,15 @@ /** * Gets ready to cancel future scrolling to offscreen nodes as soon as * a user-initiated scroll is done. - * @param {AutomationNode=} root The root node to listen for events on. - * @private + * @param root The root node to listen for events on. */ - initializeScrollingToOffscreenNodes_(root) { + private initializeScrollingToOffscreenNodes_(root: AutomationNode| + undefined): void { if (!root) { return; } this.scrollToSpokenNode_ = true; - const listener = event => { + const listener = (event: chrome.automation.AutomationEvent): void => { if (event.eventFrom !== 'action') { // User initiated event. Cancel all future scrolling to spoken nodes. // If the user wants a certain scroll position we will respect that. @@ -556,11 +539,10 @@ /** * Plays a tone to let the user know they did the correct * keystroke but nothing was selected. - * @private */ - onNullSelection_() { + private onNullSelection_(): void { if (!this.shouldShowNavigationControls_()) { - this.null_selection_tone_.play(); + this.nullSelectionTone_.play(); return; } @@ -572,27 +554,23 @@ * false and |this.state_| is SPEAKING. * TODO(leileilei): use two SelectToSpeak states to differentiate speaking and * pausing with panel. - * @private */ - isPaused_() { + private isPaused_(): boolean { return !this.ttsManager_.isSpeaking() && this.state_ === SelectToSpeakState.SPEAKING; } /** * Pause the TTS. - * @return {!Promise} - * @private */ - pause_() { + private pause_(): Promise<any> { return this.ttsManager_.pause(); } /** * Resume the TTS. - * @private */ - resume_() { + private resume_(): void { // If TTS is not paused, return early. if (!this.isPaused_()) { return; @@ -610,9 +588,8 @@ /** * If resume is successful, a resume event will be sent. We use this event to * update node state. - * @param {!chrome.tts.TtsEvent} event */ - onTtsResumeSucceedEvent_(event) { + private onTtsResumeSucceedEvent_(event: chrome.tts.TtsEvent): void { // If the node group is invalid, ignore the resume event. This is not // expected. const currentNodeGroup = this.getCurrentNodeGroup_(); @@ -628,9 +605,8 @@ * is no remaining user-selected content, STS will read from the current * position to the end of the current paragraph. If there is no content left * in this paragraph, we navigate to the next paragraph. - * @param {!chrome.tts.TtsEvent} event */ - onTtsResumeErrorEvent_(event) { + private onTtsResumeErrorEvent_(_event: chrome.tts.TtsEvent): void { // If the node group is invalid, ignore the error event. This is not // expected. const currentNodeGroup = this.getCurrentNodeGroup_(); @@ -660,8 +636,10 @@ return; } - this.startSpeechQueue_( - remainingNodes, {clearFocusRing: false, startCharIndex: offset}); + this.startSpeechQueue_(remainingNodes, { + clearFocusRing: false, + startCharIndex: offset, + }); } /** @@ -671,9 +649,8 @@ * If speech was not in progress, i.e. if the user was drawing * a focus ring on the screen, this still clears the visual * focus ring. - * @private */ - stopAll_() { + private stopAll_(): void { this.ttsManager_.stop(); this.uiManager_.clear(); this.onStateChanged_(SelectToSpeakState.INACTIVE); @@ -682,9 +659,8 @@ /** * Clears the current focus ring and node, but does * not stop the speech. - * @private */ - clearFocusRingAndNode_() { + private clearFocusRingAndNode_(): void { this.uiManager_.clear(); // Clear the node and also stop the interval testing. this.resetNodes_(); @@ -698,9 +674,8 @@ /** * Resets the instance variables for nodes and node groups. - * @private */ - resetNodes_() { + private resetNodes_(): void { this.currentNodeGroups_ = []; this.currentNodeGroupIndex_ = -1; this.currentNodeGroupItem_ = null; @@ -716,9 +691,8 @@ * tabs already opened will be checked. * This should be kept in sync with the "content_scripts" section in * the Select-to-Speak manifest. - * @private */ - runContentScripts_() { + private runContentScripts_(): void { const scripts = chrome.runtime.getManifest()['content_scripts'][0]['js']; // We only ever expect one content script. @@ -745,9 +719,8 @@ /** * Set up event listeners user input. - * @private */ - setUpEventListeners_() { + private setUpEventListeners_(): void { this.inputHandler_ = new InputHandler({ // canStartSelecting: Whether mouse selection can begin. canStartSelecting: () => { @@ -760,7 +733,7 @@ // Fire a hit test event on click to warm up the cache, and cancel // if speaking. this.cancelIfSpeaking_(false /* don't clear the focus ring */); - this.desktop_.hitTest(x, y, EventType.MOUSE_PRESSED); + this.desktop_!.hitTest(x, y, EventType.MOUSE_PRESSED); } else { this.onStateChanged_(SelectToSpeakState.INACTIVE); // Do a hit test at the center of the area the user dragged over. @@ -768,7 +741,7 @@ // tree. The hit test will result in a EventType.MOUSE_RELEASED // event being fired on the result of that hit test, which will // trigger onAutomationHitTest_. - this.desktop_.hitTest(x, y, EventType.MOUSE_RELEASED); + this.desktop_!.hitTest(x, y, EventType.MOUSE_RELEASED); } }, // onSelectionChanged: Mouse selection rect changed. @@ -799,7 +772,7 @@ /** * Called when Chrome OS is requesting Select-to-Speak to switch states. */ - onStateChangeRequested() { + onStateChangeRequested(): void { // Switch Select-to-Speak states on request. // We will need to track the current state and toggle from one state to // the next when this function is called, and then call @@ -807,7 +780,7 @@ switch (this.state_) { case SelectToSpeakState.INACTIVE: // Start selection. - this.inputHandler_.setTrackingMouse(true); + this.inputHandler_!.setTrackingMouse(true); this.onStateChanged_(SelectToSpeakState.SELECTING); MetricsUtils.recordSelectToSpeakStateChangeEvent( MetricsUtils.StateChangeEvent.START_SELECTION); @@ -821,7 +794,7 @@ break; case SelectToSpeakState.SELECTING: // Cancelled selection. - this.inputHandler_.setTrackingMouse(false); + this.inputHandler_!.setTrackingMouse(false); this.onStateChanged_(SelectToSpeakState.INACTIVE); MetricsUtils.recordSelectToSpeakStateChangeEvent( MetricsUtils.StateChangeEvent.CANCEL_SELECTION); @@ -831,40 +804,40 @@ } /** Handles user request to navigate to next paragraph. */ - onNextParagraphRequested() { + onNextParagraphRequested(): void { this.navigateToNextParagraph_(constants.Dir.FORWARD); } /** Handles user request to navigate to previous paragraph. */ - onPreviousParagraphRequested() { + onPreviousParagraphRequested(): void { this.navigateToNextParagraph_(constants.Dir.BACKWARD); } /** Handles user request to navigate to next sentence. */ - onNextSentenceRequested() { + onNextSentenceRequested(): void { this.navigateToNextSentence_(constants.Dir.FORWARD); } /** Handles user request to navigate to previous sentence. */ - onPreviousSentenceRequested() { + onPreviousSentenceRequested(): void { this.navigateToNextSentence_(constants.Dir.BACKWARD); } /** Handles user request to navigate to exit STS. */ - onExitRequested() { + onExitRequested(): void { // User manually requested, so log cancel metric. MetricsUtils.recordCancelIfSpeaking(); this.stopAll_(); } /** Handles user request to pause TTS. */ - onPauseRequested() { + onPauseRequested(): void { MetricsUtils.recordPauseEvent(); this.pause_(); } /** Handles user request to resume TTS. */ - onResumeRequested() { + onResumeRequested(): void { if (this.isPaused_()) { MetricsUtils.recordResumeEvent(); this.resume_(); @@ -873,10 +846,8 @@ /** * Handles user request to adjust reading speed. - * @param {number} rateMultiplier - * @private */ - onChangeSpeedRequested(rateMultiplier) { + onChangeSpeedRequested(rateMultiplier: number): void { this.speechRateMultiplier_ = rateMultiplier; // If currently playing, stop TTS, then resume from current spot. if (!this.isPaused_()) { @@ -888,13 +859,13 @@ /** * Navigates to the next sentence. - * @param {constants.Dir} direction Direction to search for the next sentence. + * @param direction Direction to search for the next sentence. * If set to forward, we look for the sentence start after the current * position. Otherwise, we look for the sentence start before the current * position. - * @private */ - async navigateToNextSentence_(direction) { + private async navigateToNextSentence_(direction: constants.Dir): + Promise<void> { if (!this.isPaused_()) { await this.pause_(); } @@ -907,15 +878,16 @@ // Ensure the first node in the paragraph is visible. nodes[0].makeVisible(); - this.startSpeechQueue_(nodes, {startCharIndex: offset}); + this.startSpeechQueue_(nodes, { + startCharIndex: offset, + }); } /** * Navigates to the next text block in the given direction. - * @param {constants.Dir} direction - * @private */ - async navigateToNextParagraph_(direction) { + private async navigateToNextParagraph_(direction: constants.Dir): + Promise<void> { if (!this.isPaused_()) { // Stop TTS if it is currently playing. await this.pause_(); @@ -938,11 +910,9 @@ /** * A predicate for paragraph selection and navigation. The current * implementation filters out paragraph that belongs to the panel. - * @param {Array<!AutomationNode>} nodes - * @return {boolean} Whether the paragraph made of the |nodes| is valid - * @private + * @return Whether the paragraph made of the |nodes| is valid */ - skipPanel_(nodes) { + private skipPanel_(nodes: AutomationNode[]): boolean { return !AutomationUtil.getAncestors(nodes[0]).find( n => UiManager.isPanel(n)); } @@ -951,10 +921,9 @@ * Enqueue speech for the single given string. The string is not associated * with any particular nodes, so this does not do any work around drawing * focus rings, unlike startSpeechQueue_ below. - * @param {string} text The text to speak. - * @private + * @param text The text to speak. */ - startSpeech_(text) { + private startSpeech_(text: string): void { this.prepareForSpeech_(true /* clearFocusRing */); this.maybeShowEnhancedVoicesDialog_(() => { const options = this.prefsManager_.getSpeechOptions(null); @@ -985,10 +954,8 @@ * Enqueue nodes to TTS queue and start TTS. This function can be used for * adding nodes, either from user selection (e.g., mouse selection) or * navigation control (e.g., next paragraph). - * @param {!Array<AutomationNode>} nodes The nodes to speak. - * @param {!{clearFocusRing: (boolean|undefined), - * startCharIndex: (number|undefined), - * endCharIndex: (number|undefined)}=} opt_params + * @param nodes The nodes to speak. + * @param optParams: * clearFocusRing: Whether to clear the focus ring or not. For example, we * need to clear the focus ring when starting from scratch but we do not need * to clear the focus ring when resuming from a previous pause. If this is not @@ -997,11 +964,14 @@ * speaking. If this is not passed, will start at 0. * endCharIndex: The index into the last node's text at which to end * speech. If this is not passed, will stop at the end. - * @private */ - startSpeechQueue_(nodes, opt_params) { + private startSpeechQueue_(nodes: AutomationNode[], optParams?: { + clearFocusRing?: boolean, + startCharIndex?: number, + endCharIndex?: number, + }): void { this.maybeShowEnhancedVoicesDialog_(() => { - const params = opt_params || {}; + const params = optParams || {}; const clearFocusRing = params.clearFocusRing || false; let startCharIndex = params.startCharIndex; let endCharIndex = params.endCharIndex; @@ -1039,14 +1009,15 @@ * Updates the node groups to be spoken. Converts |nodes|, |startCharIndex|, * and |endCharIndex| into node groups, and updates |this.currentNodeGroups_| * and |this.currentNodeGroupIndex_|. - * @param {!Array<AutomationNode>} nodes The nodes to speak. - * @param {number=} startCharIndex The index into the first node's text at + * @param nodes The nodes to speak. + * @param startCharIndex The index into the first node's text at * which to start speaking. If this is not passed, will start at 0. - * @param {number=} endCharIndex The index into the last node's text at which + * @param endCharIndex The index into the last node's text at which * to end speech. If this is not passed, will stop at the end. - * @private */ - updateNodeGroups_(nodes, startCharIndex, endCharIndex) { + private updateNodeGroups_( + nodes: AutomationNode[], startCharIndex?: number, + endCharIndex?: number): void { this.resetNodes_(); for (let i = 0; i < nodes.length; i++) { @@ -1128,9 +1099,8 @@ /** * Starts reading the current node group. - * @private */ - startCurrentNodeGroup_() { + private startCurrentNodeGroup_(): void { const nodeGroup = this.getCurrentNodeGroup_(); if (!nodeGroup) { return; @@ -1142,21 +1112,22 @@ } const options = this.getTtsOptionsForCurrentNodeGroup_(); - const voiceName = options['voiceName'] || ''; + const voiceName = (options && options['voiceName']) || ''; const fallbackVoiceName = this.prefsManager_.getLocalVoice(); MetricsUtils.recordTtsEngineUsed(voiceName, this.prefsManager_); this.ttsManager_.speak( - nodeGroup.text, options, this.prefsManager_.isNetworkVoice(voiceName), + // TODO(b/314203187): Options may be undefined. + nodeGroup.text, options!, this.prefsManager_.isNetworkVoice(voiceName), fallbackVoiceName); } - getTtsOptionsForCurrentNodeGroup_() { + private getTtsOptionsForCurrentNodeGroup_(): chrome.tts.TtsOptions|undefined { const nodeGroup = this.getCurrentNodeGroup_(); if (!nodeGroup) { return; } - const options = /** @type {!chrome.tts.TtsOptions} */ ({}); + const options: chrome.tts.TtsOptions = {}; let language; let useVoiceSwitching = false; if (this.shouldUseVoiceSwitching_() && nodeGroup.detectedLanguage) { @@ -1177,7 +1148,7 @@ const nodeGroupText = nodeGroup.text || ''; - options.onEvent = event => { + options.onEvent = (event: chrome.tts.TtsEvent) => { switch (event.type) { case chrome.tts.EventType.START: if (nodeGroup.nodes.length <= 0) { @@ -1197,7 +1168,7 @@ this.currentNodeWord_ = null; // If |this.currentCharIndex_| is not 0, that means we have applied // a start offset. Thus, we need to pass startIndexInNodeGroup to - // opt_startIndex and overwrite the word boundaries in the original + // optStartIndex and overwrite the word boundaries in the original // node. this.updateNodeHighlight_( nodeGroupText, this.currentCharIndex_, @@ -1216,6 +1187,7 @@ this.onTtsResumeErrorEvent_(event); } break; + // @ts-expect-error: Fallthrough on purpose. case chrome.tts.EventType.PAUSE: // Updates the select to speak state to speaking to keep navigation // panel visible, so that the user can click resume from the panel. @@ -1258,9 +1230,8 @@ * indicated by the end index. If we have reached the last node group, this * function will update STS status depending whether the navigation feature is * enabled. - * @private */ - onNodeGroupSpeakingCompleted_() { + private onNodeGroupSpeakingCompleted_(): void { const currentNodeGroup = this.getCurrentNodeGroup_(); // Update the current char index to the end of the node group. If the @@ -1294,18 +1265,19 @@ /** * Update |this.currentNodeGroupItem_|, the current speaking or the node to be * spoken in the node group. - * @param {ParagraphUtils.NodeGroup} nodeGroup the current nodeGroup. - * @param {number} charIndex the start char index of the word to be spoken. + * @param nodeGroup the current nodeGroup. + * @param charIndex the start char index of the word to be spoken. * The index is relative to the entire NodeGroup. - * @param {number=} opt_startFromNodeGroupIndex the NodeGroupIndex to start + * @param optStartFromNodeGroupIndex the NodeGroupIndex to start * with. If undefined, search from 0. - * @return {boolean} if the found NodeGroupIndex is different from the - * |opt_startFromNodeGroupIndex|. + * @return If the found NodeGroupIndex is different from the + * |optStartFromNodeGroupIndex|. */ - syncCurrentNodeWithCharIndex_( - nodeGroup, charIndex, opt_startFromNodeGroupIndex) { - if (opt_startFromNodeGroupIndex === undefined) { - opt_startFromNodeGroupIndex = 0; + private syncCurrentNodeWithCharIndex_( + nodeGroup: ParagraphUtils.NodeGroup, charIndex: number, + optStartFromNodeGroupIndex?: number): boolean { + if (optStartFromNodeGroupIndex === undefined) { + optStartFromNodeGroupIndex = 0; } // There is no speaking word, set the NodeGroupItemIndex to 0. @@ -1313,17 +1285,18 @@ this.currentNodeGroupItemIndex_ = 0; this.currentNodeGroupItem_ = nodeGroup.nodes[this.currentNodeGroupItemIndex_]; - return this.currentNodeGroupItemIndex_ === opt_startFromNodeGroupIndex; + return this.currentNodeGroupItemIndex_ === optStartFromNodeGroupIndex; } // Sets the |this.currentNodeGroupItemIndex_| to - // |opt_startFromNodeGroupIndex| - this.currentNodeGroupItemIndex_ = opt_startFromNodeGroupIndex; + // |optStartFromNodeGroupIndex| + this.currentNodeGroupItemIndex_ = optStartFromNodeGroupIndex; this.currentNodeGroupItem_ = nodeGroup.nodes[this.currentNodeGroupItemIndex_]; if (this.currentNodeGroupItemIndex_ + 1 < nodeGroup.nodes.length) { - let next = nodeGroup.nodes[this.currentNodeGroupItemIndex_ + 1]; + let next: ParagraphUtils.NodeGroupItem|null = + nodeGroup.nodes[this.currentNodeGroupItemIndex_ + 1]; let nodeUpdated = false; // TODO(katie): For something like a date, the start and end // node group nodes can actually be different. Example: @@ -1345,12 +1318,14 @@ /** * Apply start or end offset to the text of the |nodeGroup|. - * @param {ParagraphUtils.NodeGroup} nodeGroup the input nodeGroup. - * @param {number} offset the size of offset. - * @param {boolean} isStartOffset whether to apply a startOffset or an + * @param nodeGroup the input nodeGroup. + * @param offset the size of offset. + * @param isStartOffset whether to apply a startOffset or an * endOffset. */ - applyOffset(nodeGroup, offset, isStartOffset) { + applyOffset( + nodeGroup: ParagraphUtils.NodeGroup, offset: number, + isStartOffset: boolean): void { if (isStartOffset) { // Applying start offset. Remove all text before the start index so that // it is not spoken. Backfill with spaces so that index counting @@ -1365,10 +1340,9 @@ /** * Prepares for speech. Call once before this.ttsManager_.speak is called. - * @param {boolean} clearFocusRing Whether to clear the focus ring. - * @private + * @param clearFocusRing Whether to clear the focus ring. */ - prepareForSpeech_(clearFocusRing) { + private prepareForSpeech_(clearFocusRing: boolean): void { this.cancelIfSpeaking_(clearFocusRing /* clear the focus ring */); // Update the UI on an interval, to adapt to automation tree changes. @@ -1383,12 +1357,12 @@ /** * Uses the 'word' speech event to determine which node is currently beings * spoken, and prepares for highlight if enabled. - * @param {!chrome.tts.TtsEvent} event The event to use for updates. - * @param {ParagraphUtils.NodeGroup} nodeGroup The node group for this + * @param event The event to use for updates. + * @param nodeGroup The node group for this * utterance. - * @private */ - onTtsWordEvent_(event, nodeGroup) { + private onTtsWordEvent_( + event: chrome.tts.TtsEvent, nodeGroup: ParagraphUtils.NodeGroup): void { if (event.charIndex === undefined) { return; } @@ -1422,9 +1396,9 @@ if (this.prefsManager_.wordHighlightingEnabled()) { if (hasLength) { this.currentNodeWord_ = { - 'start': event.charIndex - this.currentNodeGroupItem_.startChar, + 'start': event.charIndex - this.currentNodeGroupItem_!.startChar, 'end': - event.charIndex + length - this.currentNodeGroupItem_.startChar, + event.charIndex + length - this.currentNodeGroupItem_!.startChar, }; this.updateUi_(); } else { @@ -1438,11 +1412,9 @@ /** * Updates the current node and relevant points to be the next node in the * group, then returns the next node in the group after that. - * @param {!ParagraphUtils.NodeGroup} nodeGroup - * @return {ParagraphUtils.NodeGroupItem} - * @private */ - incrementCurrentNodeAndGetNext_(nodeGroup) { + private incrementCurrentNodeAndGetNext_(nodeGroup: ParagraphUtils.NodeGroup): + ParagraphUtils.NodeGroupItem|null { // Move to the next node. this.currentNodeGroupItemIndex_ += 1; this.currentNodeGroupItem_ = @@ -1458,10 +1430,9 @@ /** * Updates the state. - * @param {!chrome.accessibilityPrivate.SelectToSpeakState} state - * @private */ - onStateChanged_(state) { + private onStateChanged_( + state: chrome.accessibilityPrivate.SelectToSpeakState): void { if (this.state_ !== state) { if (state === SelectToSpeakState.INACTIVE) { this.clearFocusRingAndNode_(); @@ -1474,11 +1445,9 @@ /** * Cancels the current speech queue. - * @param {boolean} clearFocusRing Whether to clear the focus ring - * as well. - * @private + * @param clearFocusRing Whether to clear the focus ring as well. */ - cancelIfSpeaking_(clearFocusRing) { + private cancelIfSpeaking_(clearFocusRing: boolean): void { if (clearFocusRing) { this.stopAll_(); } else { @@ -1488,14 +1457,12 @@ } /** - * @param {!AutomationNode} node - * @return {!Promise<boolean>} Promise that resolves to whether the given node + * @return Promise that resolves to whether the given node * should be considered in the foreground or not. - * @private */ - isNodeInForeground_(node) { + private isNodeInForeground_(node: AutomationNode): Promise<boolean> { return new Promise(resolve => { - this.desktop_.hitTestWithReply( + this.desktop_!.hitTestWithReply( node.location.left, node.location.top, nodeAtLocation => { chrome.automation.getFocus(focusedNode => { const window = @@ -1535,10 +1502,9 @@ } /** - * @return {?AutomationNode} Current node that is being spoken. - * @private + * @return Current node that is being spoken. */ - getCurrentSpokenNode_() { + private getCurrentSpokenNode_(): AutomationNode|null { if (!this.currentNodeGroupItem_) { return null; } @@ -1561,10 +1527,9 @@ /** * Updates the UI based on the current STS and node state. - * @return {!Promise<void>} Promise that resolves when operation is complete. - * @private + * @return Promise that resolves when operation is complete. */ - async updateUi_() { + private async updateUi_(): Promise<void> { if (this.currentNodeGroupItem_ === null) { // Nothing to do. return; @@ -1600,7 +1565,7 @@ return; } - if (this.scrollToSpokenNode_ && spokenNode.state.offscreen) { + if (this.scrollToSpokenNode_ && spokenNode.state!['offscreen']) { spokenNode.makeVisible(); } const currentWord = this.prefsManager_.wordHighlightingEnabled() ? @@ -1618,10 +1583,10 @@ * showing privacy disclaimer and asking if the user wants to turn on enhanced * network voices. * - * @param {function()} callback Called back after user has confirmed or + * @param callback Called back after user has confirmed or * canceled in the dialog. */ - maybeShowEnhancedVoicesDialog_(callback) { + private maybeShowEnhancedVoicesDialog_(callback: () => any): void { if (!this.prefsManager_.enhancedVoicesDialogShown() && this.prefsManager_.enhancedNetworkVoicesAllowed()) { // TODO(crbug.com/1230227): Style this dialog to match UX mocks. @@ -1650,33 +1615,33 @@ /** * Updates the currently highlighted node word based on the current text * and the character index of an event. - * @param {string} text The current text - * @param {number} charIndex The index of a current event in the text. - * @param {number=} opt_startIndex The index at which to start the + * @param text The current text + * @param charIndex The index of a current event in the text. + * @param optStartIndex The index at which to start the * highlight. This takes precedence over the charIndex. - * @private */ - updateNodeHighlight_(text, charIndex, opt_startIndex) { + private updateNodeHighlight_( + text: string, charIndex: number, optStartIndex?: number): void { if (charIndex >= text.length) { // No need to do work if we are at the end of the paragraph. return; } // Get the next word based on the event's charIndex. - const nextWordStart = - WordUtils.getNextWordStart(text, charIndex, this.currentNodeGroupItem_); + const nextWordStart = WordUtils.getNextWordStart( + text, charIndex, this.currentNodeGroupItem_!); // The |WordUtils.getNextWordEnd| will find the correct end based on the // trimmed text, so there is no need to provide additional input like - // opt_startIndex. + // optStartIndex. const nextWordEnd = WordUtils.getNextWordEnd( - text, opt_startIndex === undefined ? nextWordStart : opt_startIndex, - this.currentNodeGroupItem_); + text, optStartIndex === undefined ? nextWordStart : optStartIndex, + this.currentNodeGroupItem_!); // Map the next word into the node's index from the text. - const nodeStart = opt_startIndex === undefined ? - nextWordStart - this.currentNodeGroupItem_.startChar : - opt_startIndex - this.currentNodeGroupItem_.startChar; + const nodeStart = optStartIndex === undefined ? + nextWordStart - this.currentNodeGroupItem_!.startChar : + optStartIndex - this.currentNodeGroupItem_!.startChar; const nodeEnd = Math.min( - nextWordEnd - this.currentNodeGroupItem_.startChar, - NodeUtils.nameLength(this.currentNodeGroupItem_.node)); + nextWordEnd - this.currentNodeGroupItem_!.startChar, + NodeUtils.nameLength(this.currentNodeGroupItem_!.node)); if ((this.currentNodeWord_ == null || nodeStart >= this.currentNodeWord_.end) && nodeStart <= nodeEnd) { @@ -1691,10 +1656,9 @@ } /** - * @return {number} Current speech rate. - * @private + * @return Current speech rate. */ - getSpeechRate_() { + private getSpeechRate_(): number { // Multiply default speech rate with user-selected multiplier. const rate = this.prefsManager_.speechRate() * this.speechRateMultiplier_; // Then round to the nearest tenth (ex. 1.799999 becomes 1.8). @@ -1702,11 +1666,9 @@ } /** - * @param {!Array<!AutomationNode>} nodes - * @return {boolean} Whether all given nodes support the navigation panel. - * @private + * @return Whether all given nodes support the navigation panel. */ - isNavigationPanelSupported_(nodes) { + private isNavigationPanelSupported_(nodes: AutomationNode[]): boolean { if (nodes.length === 0) { return true; } @@ -1728,44 +1690,39 @@ } /** - * @param {!Array<number>} keysPressed Which keys to pretend are currently - * pressed. - * @protected + * @param keysPressed Which keys to pretend are currently pressed. */ - sendMockSelectToSpeakKeysPressedChanged(keysPressed) { - this.inputHandler_.onKeysPressedChanged_(new Set(keysPressed)); + protected sendMockSelectToSpeakKeysPressedChanged(keysPressed: number[]): + void { + this.inputHandler_!.onKeysPressedChanged(new Set(keysPressed)); } /** * Fires a mock mouse down event for testing. - * @param {!chrome.accessibilityPrivate.SyntheticMouseEventType} type The - * event type. - * @param {number} mouse_x The mouse x coordinate in global screen - * coordinates. - * @param {number} mouse_y The mouse y coordinate in global screen - * coordinates. - * @protected + * @param type The event type. + * @param mouseX The mouse x coordinate in global screen coordinates. + * @param mouseY The mouse y coordinate in global screen coordinates. */ - fireMockMouseEvent(type, mouse_x, mouse_y) { - this.inputHandler_.onMouseEvent_(type, mouse_x, mouse_y); + protected fireMockMouseEvent( + type: chrome.accessibilityPrivate.SyntheticMouseEventType, mouseX: number, + mouseY: number): void { + this.inputHandler_!.onMouseEvent(type, mouseX, mouseY); } /** * TODO(crbug.com/950391): Consider adding a metric for when voice switching * gets used. - * @return {boolean} - * @private */ - shouldUseVoiceSwitching_() { + private shouldUseVoiceSwitching_(): boolean { return this.prefsManager_.voiceSwitchingEnabled(); } /** * Used by C++ tests to ensure STS load is completed. - * @param {!function()} callback Callback for when desktop is loaded from + * @param callback Callback for when desktop is loaded from * automation. */ - setOnLoadDesktopCallbackForTest(callback) { + setOnLoadDesktopCallbackForTest(callback: () => any): void { if (!this.desktop_) { this.onLoadDesktopCallbackForTest_ = callback; return;
diff --git a/chrome/browser/resources/chromeos/accessibility/select_to_speak/tsconfig.json b/chrome/browser/resources/chromeos/accessibility/select_to_speak/tsconfig.json index c699141..dca398a 100644 --- a/chrome/browser/resources/chromeos/accessibility/select_to_speak/tsconfig.json +++ b/chrome/browser/resources/chromeos/accessibility/select_to_speak/tsconfig.json
@@ -11,6 +11,7 @@ "../../../../../../tools/typescript/definitions" ], "exclude": [ + "../../../../../../tools/typescript/definitions/runtime.d.ts", "../../../../../../tools/typescript/definitions/i18n.d.ts", "../../../../../../tools/typescript/definitions/storage.d.ts" ]
diff --git a/chrome/browser/resources/chromeos/accessibility/select_to_speak/ui_manager.ts b/chrome/browser/resources/chromeos/accessibility/select_to_speak/ui_manager.ts index 2917f34..c8508dc 100644 --- a/chrome/browser/resources/chromeos/accessibility/select_to_speak/ui_manager.ts +++ b/chrome/browser/resources/chromeos/accessibility/select_to_speak/ui_manager.ts
@@ -63,7 +63,7 @@ * User requests reading speed adjustment. * @param speed rate multiplier. */ - onChangeSpeedRequested: (speed: number) => {}; + onChangeSpeedRequested: (speed: number) => void; /** User requests exiting STS. */ onExitRequested: () => void;
diff --git a/chrome/browser/resources/chromeos/accessibility/switch_access/switch_access_e2e_test_base.js b/chrome/browser/resources/chromeos/accessibility/switch_access/switch_access_e2e_test_base.js index 1d0f1cf0..cb2fc67 100644 --- a/chrome/browser/resources/chromeos/accessibility/switch_access/switch_access_e2e_test_base.js +++ b/chrome/browser/resources/chromeos/accessibility/switch_access/switch_access_e2e_test_base.js
@@ -16,7 +16,6 @@ #include "ash/keyboard/ui/keyboard_util.h" #include "ash/accessibility/accessibility_controller_impl.h" #include "ash/constants/ash_pref_names.h" -#include "ash/public/cpp/accessibility_controller.h" #include "chrome/browser/ash/accessibility/accessibility_manager.h" `); }
diff --git a/chrome/browser/resources/settings/metrics_browser_proxy.ts b/chrome/browser/resources/settings/metrics_browser_proxy.ts index bee4262..51e9e752 100644 --- a/chrome/browser/resources/settings/metrics_browser_proxy.ts +++ b/chrome/browser/resources/settings/metrics_browser_proxy.ts
@@ -120,7 +120,7 @@ * numeric values should never be reused. * * Must be kept in sync with the - * SafetyChecUnusedSitePermissionsModuleInteractions enum in + * SafetyCheckUnusedSitePermissionsModuleInteractions enum in * histograms/enums.xml */ export enum SafetyCheckUnusedSitePermissionsModuleInteractions { @@ -135,6 +135,45 @@ } /** + * Contains all entry points for Safety Hub page. + * + * These values are persisted to logs. Entries should not be renumbered and + * numeric values should never be reused. + * + * Must be kept in sync with the SafetyHubEntryPoint enum in + * histograms/enums.xml and safety_hub/safety_hub_constants.h. + */ +export enum SafetyHubEntryPoint { + PRIVACY_SAFE = 0, + PRIVACY_WARNING = 1, + SITE_SETTINGS = 2, + THREE_DOT_MENU = 3, + NOTIFICATIONS = 4, + // Max value should be updated whenever new entries are added. + MAX_VALUE = 5, +} + +/** + * Contains all Safety Hub modules. + * + * These values are persisted to logs. Entries should not be renumbered and + * numeric values should never be reused. + * + * Must be kept in sync with the SafetyHubModuleType enum in + * histograms/enums.xml and safety_hub/safety_hub_constants.h. + */ +export enum SafetyHubModuleType { + PERMISSIONS = 0, + NOTIFICATIONS = 1, + SAFE_BROWSING = 2, + EXTENSIONS = 3, + PASSWORDS = 4, + VERSION = 5, + // Max value should be updated whenever new entries are added. + MAX_VALUE = 6, +} + +/** * Contains all safe browsing interactions. * * These values are persisted to logs. Entries should not be renumbered and @@ -342,6 +381,30 @@ /** * Helper function that calls recordHistogram for the + * Settings.SafetyHub.EntryPointShown histogram + */ + recordSafetyHubEntryPointShown(page: SafetyHubEntryPoint): void; + + /** + * Helper function that calls recordHistogram for the + *Settings.SafetyHub.EntryPointClicked histogram + */ + recordSafetyHubEntryPointClicked(page: SafetyHubEntryPoint): void; + + /** + * Helper function that calls recordHistogram for the + * Settings.SafetyHub.DashboardWarning histogram + */ + recordSafetyHubModuleWarningImpression(module: SafetyHubModuleType): void; + + /** + * Helper function that calls recordHistogram for the + * Settings.SafetyHub.HasDashboardShowAnyWarning histogram + */ + recordSafetyHubDashboardAnyWarning(visible: boolean): void; + + /** + * Helper function that calls recordHistogram for the * Settings.SafetyHub.[card_name].StatusOnClick histogram */ recordSafetyHubCardStateClicked( @@ -484,6 +547,37 @@ [histogramName, state, SafetyHubCardState.MAX_VALUE]); } + recordSafetyHubEntryPointShown(page: SafetyHubEntryPoint) { + chrome.send('metricsHandler:recordInHistogram', [ + 'Settings.SafetyHub.EntryPointShown', + page, + SafetyHubEntryPoint.MAX_VALUE, + ]); + } + + recordSafetyHubEntryPointClicked(page: SafetyHubEntryPoint) { + chrome.send('metricsHandler:recordInHistogram', [ + 'Settings.SafetyHub.EntryPointClicked', + page, + SafetyHubEntryPoint.MAX_VALUE, + ]); + } + + recordSafetyHubModuleWarningImpression(module: SafetyHubModuleType) { + chrome.send('metricsHandler:recordInHistogram', [ + 'Settings.SafetyHub.DashboardWarning', + module, + SafetyHubModuleType.MAX_VALUE, + ]); + } + + recordSafetyHubDashboardAnyWarning(visible: boolean) { + chrome.send('metricsHandler:recordBooleanHistogram', [ + 'Settings.SafetyHub.HasDashboardShowAnyWarning', + visible, + ]); + } + recordSettingsPageHistogram(interaction: PrivacyElementInteractions) { chrome.send('metricsHandler:recordInHistogram', [ 'Settings.PrivacyElementInteractions',
diff --git a/chrome/browser/resources/settings/privacy_page/privacy_page.html b/chrome/browser/resources/settings/privacy_page/privacy_page.html index e3113cd..3abd2dbc 100644 --- a/chrome/browser/resources/settings/privacy_page/privacy_page.html +++ b/chrome/browser/resources/settings/privacy_page/privacy_page.html
@@ -155,7 +155,9 @@ </settings-subpage> </template> - <template is="dom-if" route-path="/adPrivacy"> + <template is="dom-if" route-path="/adPrivacy" + no-search="[[!shouldShowAdPrivacy_(isPrivacySandboxRestricted_, + isPrivacySandboxRestrictedNoticeEnabled_)]]"> <settings-subpage id="privacy-sandbox" page-title="$i18n{adPrivacyPageTitle}" associated-control="[[$$('#privacySandboxLinkRow')]]" @@ -166,7 +168,8 @@ </settings-subpage> </template> - <template is="dom-if" route-path="/adPrivacy/interests"> + <template is="dom-if" route-path="/adPrivacy/interests" + no-search="[[isPrivacySandboxRestricted_]]"> <settings-subpage id="privacy-sandbox-topics" page-title="$i18n{topicsPageTitle}" associated-control="[[$$('#privacySandboxLinkRow')]]" @@ -176,7 +179,8 @@ </settings-subpage> </template> - <template is="dom-if" route-path="/adPrivacy/sites"> + <template is="dom-if" route-path="/adPrivacy/sites" + no-search="[[isPrivacySandboxRestricted_]]"> <settings-subpage id="privacy-sandbox-fledge" page-title="$i18n{fledgePageTitle}" associated-control="[[$$('#privacySandboxLinkRow')]]" @@ -186,7 +190,9 @@ </settings-subpage> </template> - <template is="dom-if" route-path="/adPrivacy/measurement"> + <template is="dom-if" route-path="/adPrivacy/measurement" + no-search="[[!shouldShowAdPrivacy_(isPrivacySandboxRestricted_, + isPrivacySandboxRestrictedNoticeEnabled_)]]"> <settings-subpage id="privacy-sandbox-ad-measurement" page-title="$i18n{adMeasurementPageTitle}" associated-control="[[$$('#privacySandboxLinkRow')]]"
diff --git a/chrome/browser/resources/settings/privacy_page/privacy_page.ts b/chrome/browser/resources/settings/privacy_page/privacy_page.ts index 5b69da0..6b201f1 100644 --- a/chrome/browser/resources/settings/privacy_page/privacy_page.ts +++ b/chrome/browser/resources/settings/privacy_page/privacy_page.ts
@@ -38,7 +38,7 @@ import {FocusConfig} from '../focus_config.js'; import {HatsBrowserProxyImpl, TrustSafetyInteraction} from '../hats_browser_proxy.js'; import {loadTimeData} from '../i18n_setup.js'; -import {MetricsBrowserProxy, MetricsBrowserProxyImpl, PrivacyGuideInteractions} from '../metrics_browser_proxy.js'; +import {MetricsBrowserProxy, MetricsBrowserProxyImpl, PrivacyGuideInteractions, SafetyHubEntryPoint} from '../metrics_browser_proxy.js'; import {routes} from '../route.js'; import {RouteObserverMixin, Router} from '../router.js'; import {NotificationPermission, SafetyHubBrowserProxy, SafetyHubBrowserProxyImpl, SafetyHubEvent} from '../safety_hub/safety_hub_browser_proxy.js'; @@ -391,6 +391,15 @@ this.showPrivacyGuideDialog_ = Router.getInstance().getCurrentRoute() === routes.PRIVACY_GUIDE && this.isPrivacyGuideAvailable; + + // Only record the metrics when the user navigates to the notification + // settings page that shows the entry point. + if (Router.getInstance().getCurrentRoute() === + routes.SITE_SETTINGS_NOTIFICATIONS && + this.showNotificationPermissionsReview_) { + this.metricsBrowserProxy_.recordSafetyHubEntryPointShown( + SafetyHubEntryPoint.NOTIFICATIONS); + } } /** @@ -587,6 +596,8 @@ } private onSafetyHubButtonClick_() { + this.metricsBrowserProxy_.recordSafetyHubEntryPointClicked( + SafetyHubEntryPoint.NOTIFICATIONS); Router.getInstance().navigateTo(routes.SAFETY_HUB); } }
diff --git a/chrome/browser/resources/settings/safety_hub/safety_hub_card.ts b/chrome/browser/resources/settings/safety_hub/safety_hub_card.ts index 8a44b9c..45fa280 100644 --- a/chrome/browser/resources/settings/safety_hub/safety_hub_card.ts +++ b/chrome/browser/resources/settings/safety_hub/safety_hub_card.ts
@@ -46,8 +46,9 @@ switch (state) { case CardState.WARNING: case CardState.WEAK: - case CardState.INFO: return 'cr:error'; + case CardState.INFO: + return 'cr:info'; case CardState.SAFE: return 'cr:check-circle'; default:
diff --git a/chrome/browser/resources/settings/safety_hub/safety_hub_entry_point.ts b/chrome/browser/resources/settings/safety_hub/safety_hub_entry_point.ts index 4afef3d9..e4d004a 100644 --- a/chrome/browser/resources/settings/safety_hub/safety_hub_entry_point.ts +++ b/chrome/browser/resources/settings/safety_hub/safety_hub_entry_point.ts
@@ -12,7 +12,8 @@ import {PolymerElement} from 'chrome://resources/polymer/v3_0/polymer/polymer_bundled.min.js'; import {routes} from '../route.js'; -import {Router} from '../router.js'; +import {Router, RouteObserverMixin} from '../router.js'; +import {MetricsBrowserProxy, MetricsBrowserProxyImpl, SafetyHubEntryPoint} from '../metrics_browser_proxy.js'; import {SafetyHubBrowserProxy, SafetyHubBrowserProxyImpl} from './safety_hub_browser_proxy.js'; import {getTemplate} from './safety_hub_entry_point.html.js'; @@ -26,7 +27,8 @@ }; } -const SettingsSafetyHubEntryPointElementBase = I18nMixin(PolymerElement); +const SettingsSafetyHubEntryPointElementBase = + RouteObserverMixin(I18nMixin(PolymerElement)); export class SettingsSafetyHubEntryPointElement extends SettingsSafetyHubEntryPointElementBase { @@ -65,17 +67,17 @@ }; } - private safetyHubBrowserProxy_: SafetyHubBrowserProxy = - SafetyHubBrowserProxyImpl.getInstance(); - private buttonClass_: string; private hasRecommendations_: boolean; private headerString_: string; private subheaderString_: string; private headerIconColor_: string; + private safetyHubBrowserProxy_: SafetyHubBrowserProxy = + SafetyHubBrowserProxyImpl.getInstance(); + private metricsBrowserProxy_: MetricsBrowserProxy = + MetricsBrowserProxyImpl.getInstance(); override connectedCallback() { - super.connectedCallback(); this.safetyHubBrowserProxy_.getSafetyHubHasRecommendations().then( (hasRecommendations: boolean) => { this.hasRecommendations_ = hasRecommendations; @@ -85,6 +87,24 @@ (subheader: string) => { this.subheaderString_ = subheader; }); + // This should be called after the data for modules are retrieved so that + // currentRouteChanged is called afterwards. + super.connectedCallback(); + } + + override currentRouteChanged() { + if (Router.getInstance().getCurrentRoute() !== routes.PRIVACY) { + return; + } + // Only record the metrics when the user navigates to the privacy page + // that shows the entry point. + if (this.hasRecommendations_) { + this.metricsBrowserProxy_.recordSafetyHubEntryPointShown( + SafetyHubEntryPoint.PRIVACY_WARNING); + } else { + this.metricsBrowserProxy_.recordSafetyHubEntryPointShown( + SafetyHubEntryPoint.PRIVACY_SAFE); + } } private computeButtonClass_() { @@ -101,6 +121,13 @@ } private onClick_() { + if (this.hasRecommendations_) { + this.metricsBrowserProxy_.recordSafetyHubEntryPointClicked( + SafetyHubEntryPoint.PRIVACY_WARNING); + } else { + this.metricsBrowserProxy_.recordSafetyHubEntryPointClicked( + SafetyHubEntryPoint.PRIVACY_SAFE); + } Router.getInstance().navigateTo(routes.SAFETY_HUB); } }
diff --git a/chrome/browser/resources/settings/safety_hub/safety_hub_module.html b/chrome/browser/resources/settings/safety_hub/safety_hub_module.html index 9f78869..9a48d25 100644 --- a/chrome/browser/resources/settings/safety_hub/safety_hub_module.html +++ b/chrome/browser/resources/settings/safety_hub/safety_hub_module.html
@@ -78,7 +78,7 @@ #line { box-sizing: border-box; height: var(--separator-line-height); - border-bottom: 1px solid var(--google-grey-300); + border-bottom: 1px solid var(--cr-separator-color); flex: 1; }
diff --git a/chrome/browser/resources/settings/safety_hub/safety_hub_page.html b/chrome/browser/resources/settings/safety_hub/safety_hub_page.html index 86e09a8..920fc849 100644 --- a/chrome/browser/resources/settings/safety_hub/safety_hub_page.html +++ b/chrome/browser/resources/settings/safety_hub/safety_hub_page.html
@@ -30,9 +30,12 @@ } .section-header { + color: var(--cr-primary-text-color); flex: 1; /* Should be 13px when html font-size is 16px */ - font-size: 0.8125rem; + font-size: 108%; + font-weight: 400; + letter-spacing: .25px; margin-bottom: 16px; margin-top: 30px; width: 100%; @@ -44,9 +47,9 @@ } </style> -<h5 class="section-header cr-secondary-text first"> +<h2 class="section-header cr-secondary-text first"> $i18n{safetyHubPageCardSectionHeader} -</h5> +</h2> <div class="card-container"> <settings-safety-hub-card id="passwords" class="card box" data="[[passwordCardData_]]" on-click="onPasswordsClick_" @@ -61,9 +64,9 @@ tabindex="0" on-keydown="onSafeBrowsingKeyPress_"> </settings-safety-hub-card> </div> -<h5 class="section-header cr-secondary-text"> +<h2 class="section-header cr-secondary-text"> $i18n{safetyHubPageModuleSectionHeader} -</h5> +</h2> <template is="dom-if" if="[[showNotificationPermissions_]]"> <settings-safety-hub-notification-permissions-module class="module box"> </settings-safety-hub-notification-permissions-module>
diff --git a/chrome/browser/resources/settings/safety_hub/safety_hub_page.ts b/chrome/browser/resources/settings/safety_hub/safety_hub_page.ts index 04e7e2e..3df543c 100644 --- a/chrome/browser/resources/settings/safety_hub/safety_hub_page.ts +++ b/chrome/browser/resources/settings/safety_hub/safety_hub_page.ts
@@ -17,7 +17,7 @@ import {PolymerElement} from 'chrome://resources/polymer/v3_0/polymer/polymer_bundled.min.js'; import {PasswordManagerImpl, PasswordManagerPage} from '../autofill_page/password_manager_proxy.js'; -import {MetricsBrowserProxy, MetricsBrowserProxyImpl, SafetyHubCardState, SafetyHubSurfaces} from '../metrics_browser_proxy.js'; +import {MetricsBrowserProxy, MetricsBrowserProxyImpl, SafetyHubCardState, SafetyHubModuleType, SafetyHubSurfaces} from '../metrics_browser_proxy.js'; import {RelaunchMixin, RestartType} from '../relaunch_mixin.js'; import {routes} from '../route.js'; import {RouteObserverMixin, Router} from '../router.js'; @@ -83,16 +83,35 @@ }, userEducationItemList_: Array, + + // Whether the data for notification permissions is ready. + hasDataForNotificationPermissions_: Boolean, + + // Whether the data for unused site permissions is ready. + hasDataForUnusedPermissions_: Boolean, + + // Whether the data for extensions is ready. + hasDataForExtensions_: Boolean, }; } + static get observers() { + return [ + 'onAllModulesLoaded_(passwordCardData_, versionCardData_, safeBrowsingCardData_, hasDataForUnusedPermissions_, hasDataForNotificationPermissions_, hasDataForExtensions_)', + ]; + } + private passwordCardData_: CardInfo; private versionCardData_: CardInfo; private safeBrowsingCardData_: CardInfo; private showNotificationPermissions_: boolean; + private hasDataForNotificationPermissions_: boolean; private showUnusedSitePermissions_: boolean; + private hasDataForUnusedPermissions_: boolean; private showNoRecommendationsState_: boolean; private showExtensions_: boolean; + private hasDataForExtensions_: boolean; + private shouldRecordMetric_: boolean = false; private userEducationItemList_: SiteInfo[]; private browserProxy_: SafetyHubBrowserProxy = SafetyHubBrowserProxyImpl.getInstance(); @@ -100,11 +119,11 @@ MetricsBrowserProxyImpl.getInstance(); override connectedCallback() { - super.connectedCallback(); - this.initializeCards_(); this.initializeModules_(); this.initializeUserEducation_(); + + super.connectedCallback(); } override currentRouteChanged() { @@ -119,10 +138,14 @@ SafetyHubSurfaces.SAFETY_HUB_PAGE); this.metricsBrowserProxy_.recordSafetyHubInteraction( SafetyHubSurfaces.SAFETY_HUB_PAGE); + + // Only record the metrics when the user navigates to the Safety Hub page. + this.shouldRecordMetric_ = true; + this.onAllModulesLoaded_(); } private initializeCards_() { - // TODO(1443466): Add listeners for cards. + // TODO(crbug.com/1443466): Add listeners for cards. this.browserProxy_.getPasswordCardData().then((data: CardInfo) => { this.passwordCardData_ = data; }); @@ -243,6 +266,7 @@ // there is no item on the list but the list was shown before. this.showNotificationPermissions_ = permissions.length > 0 || this.showNotificationPermissions_; + this.hasDataForNotificationPermissions_ = true; } private onUnusedSitePermissionListChanged_(permissions: @@ -251,6 +275,7 @@ // there is no item on the list but the list was shown before. this.showUnusedSitePermissions_ = permissions.length > 0 || this.showUnusedSitePermissions_; + this.hasDataForUnusedPermissions_ = true; } private computeShowNoRecommendationsState_(): boolean { @@ -261,11 +286,73 @@ private onExtensionsChanged_(numberOfExtensions: number) { this.showExtensions_ = !!numberOfExtensions; + this.hasDataForExtensions_ = true; } private isEnterOrSpaceClicked_(e: KeyboardEvent): boolean { return e.key === 'Enter' || e.key === ' '; } + + private onAllModulesLoaded_() { + // If the metrics are recorded already, don't record again. + if (!this.shouldRecordMetric_) { + return; + } + + // Wait till the data of the cards be ready. + if (!this.passwordCardData_ || !this.safeBrowsingCardData_ || + !this.versionCardData_) { + return; + } + + // Wait till the data of the modules be ready. + if (!this.hasDataForUnusedPermissions_ || + !this.hasDataForNotificationPermissions_ || + !this.hasDataForExtensions_) { + return; + } + + this.shouldRecordMetric_ = false; + let hasAnyWarning: boolean = false; + // TODO(crbug.com/1443466): Iterate over the cards/modules with for loop. + if (this.passwordCardData_.state !== CardState.SAFE) { + this.metricsBrowserProxy_.recordSafetyHubModuleWarningImpression( + SafetyHubModuleType.PASSWORDS); + hasAnyWarning = true; + } + + if (this.safeBrowsingCardData_.state !== CardState.SAFE) { + this.metricsBrowserProxy_.recordSafetyHubModuleWarningImpression( + SafetyHubModuleType.SAFE_BROWSING); + hasAnyWarning = true; + } + + if (this.versionCardData_.state !== CardState.SAFE) { + this.metricsBrowserProxy_.recordSafetyHubModuleWarningImpression( + SafetyHubModuleType.VERSION); + hasAnyWarning = true; + } + + if (this.showNotificationPermissions_) { + this.metricsBrowserProxy_.recordSafetyHubModuleWarningImpression( + SafetyHubModuleType.NOTIFICATIONS); + hasAnyWarning = true; + } + + if (this.showUnusedSitePermissions_) { + this.metricsBrowserProxy_.recordSafetyHubModuleWarningImpression( + SafetyHubModuleType.PERMISSIONS); + hasAnyWarning = true; + } + + if (this.showExtensions_) { + this.metricsBrowserProxy_.recordSafetyHubModuleWarningImpression( + SafetyHubModuleType.EXTENSIONS); + hasAnyWarning = true; + } + + this.metricsBrowserProxy_.recordSafetyHubDashboardAnyWarning(hasAnyWarning); + } } declare global {
diff --git a/chrome/browser/resources/settings/settings.ts b/chrome/browser/resources/settings/settings.ts index 7d0dc48..8bca5f32 100644 --- a/chrome/browser/resources/settings/settings.ts +++ b/chrome/browser/resources/settings/settings.ts
@@ -60,7 +60,7 @@ // </if> export {HatsBrowserProxy, HatsBrowserProxyImpl, SafeBrowsingSetting, SecurityPageInteraction, TrustSafetyInteraction} from './hats_browser_proxy.js'; export {loadTimeData} from './i18n_setup.js'; -export {CvcDeletionUserAction, DeleteBrowsingDataAction, MetricsBrowserProxy, MetricsBrowserProxyImpl, PrivacyElementInteractions, PrivacyGuideInteractions, PrivacyGuideSettingsStates, PrivacyGuideStepsEligibleAndReached, SafeBrowsingInteractions, SafetyCheckInteractions, SafetyCheckNotificationsModuleInteractions, SafetyCheckUnusedSitePermissionsModuleInteractions, SafetyHubCardState, SafetyHubSurfaces} from './metrics_browser_proxy.js'; +export {CvcDeletionUserAction, DeleteBrowsingDataAction, MetricsBrowserProxy, MetricsBrowserProxyImpl, PrivacyElementInteractions, PrivacyGuideInteractions, PrivacyGuideSettingsStates, PrivacyGuideStepsEligibleAndReached, SafeBrowsingInteractions, SafetyCheckInteractions, SafetyCheckNotificationsModuleInteractions, SafetyCheckUnusedSitePermissionsModuleInteractions, SafetyHubCardState, SafetyHubEntryPoint, SafetyHubModuleType, SafetyHubSurfaces} from './metrics_browser_proxy.js'; export {NtpExtension, OnStartupBrowserProxy, OnStartupBrowserProxyImpl} from './on_startup_page/on_startup_browser_proxy.js'; export {SettingsOnStartupPageElement} from './on_startup_page/on_startup_page.js'; export {SettingsStartupUrlDialogElement} from './on_startup_page/startup_url_dialog.js';
diff --git a/chrome/browser/resources/settings/site_settings_page/site_settings_page.ts b/chrome/browser/resources/settings/site_settings_page/site_settings_page.ts index d200fe0..5c2ae188 100644 --- a/chrome/browser/resources/settings/site_settings_page/site_settings_page.ts +++ b/chrome/browser/resources/settings/site_settings_page/site_settings_page.ts
@@ -26,8 +26,9 @@ import {FocusConfig} from '../focus_config.js'; import {loadTimeData} from '../i18n_setup.js'; +import {MetricsBrowserProxy, MetricsBrowserProxyImpl, SafetyHubEntryPoint} from '../metrics_browser_proxy.js'; import {routes} from '../route.js'; -import {Router} from '../router.js'; +import {RouteObserverMixin, Router} from '../router.js'; import {SafetyHubBrowserProxy, SafetyHubBrowserProxyImpl, SafetyHubEvent, UnusedSitePermissions} from '../safety_hub/safety_hub_browser_proxy.js'; import {ContentSettingsTypes} from '../site_settings/constants.js'; @@ -385,7 +386,8 @@ }; } -const SettingsSiteSettingsPageElementBase = WebUiListenerMixin(PolymerElement); +const SettingsSiteSettingsPageElementBase = + RouteObserverMixin(WebUiListenerMixin(PolymerElement)); export class SettingsSiteSettingsPageElement extends SettingsSiteSettingsPageElementBase { @@ -528,6 +530,8 @@ private unusedSitePermissionsSubheader_: string; private safetyHubBrowserProxy_: SafetyHubBrowserProxy = SafetyHubBrowserProxyImpl.getInstance(); + private metricsBrowserProxy_: MetricsBrowserProxy = + MetricsBrowserProxyImpl.getInstance(); private lists_: { all: CategoryListItem[], @@ -537,6 +541,18 @@ contentAdvanced: CategoryListItem[], }; + override currentRouteChanged() { + if (Router.getInstance().getCurrentRoute() !== routes.SITE_SETTINGS) { + return; + } + // Only record the metrics when the user navigates to the privacy page + // that shows the entry point. + if (this.showUnusedSitePermissions_) { + this.metricsBrowserProxy_.recordSafetyHubEntryPointShown( + SafetyHubEntryPoint.SITE_SETTINGS); + } + } + private focusConfigChanged_(_newConfig: FocusConfig, oldConfig: FocusConfig) { // focusConfig is set only once on the parent, so this observer should // only fire once. @@ -578,6 +594,8 @@ } private onSafetyHubButtonClick_() { + this.metricsBrowserProxy_.recordSafetyHubEntryPointClicked( + SafetyHubEntryPoint.SITE_SETTINGS); Router.getInstance().navigateTo(routes.SAFETY_HUB); } }
diff --git a/chrome/browser/resources/side_panel/customize_chrome/wallpaper_search/wallpaper_search.html b/chrome/browser/resources/side_panel/customize_chrome/wallpaper_search/wallpaper_search.html index 4294cf8..f633aab 100644 --- a/chrome/browser/resources/side_panel/customize_chrome/wallpaper_search/wallpaper_search.html +++ b/chrome/browser/resources/side_panel/customize_chrome/wallpaper_search/wallpaper_search.html
@@ -152,13 +152,38 @@ width: 100%; } - #descriptorMenuD cr-button { + #descriptorMenuD button { + appearance: none; + display: flex; + align-items: center; + justify-content: center; background-color: var(--color-menu-button-background); border-radius: 8px; - border-color: var(--color-menu-button-background); - height: 40px; - min-width: 40px; - padding: 0px; + border: 0; + padding: 0; + width: 100%; + aspect-ratio: 1 / 1; + position: relative; + overflow: hidden; + cursor: pointer; + } + + #descriptorMenuD button:hover::before { + display: block; + content: ''; + inset: 0; + position: absolute; + background-color: var(--cr-hover-background-color); + } + + #descriptorMenuD button paper-ripple { + --paper-ripple-opacity: 1; + color: var(--cr-active-background-color); + } + + :host-context(.focus-outline-visible) #descriptorMenuD button:focus { + outline: 2px solid var(--cr-focus-outline-color); + outline-offset: 2px; } .color-check-mark { @@ -347,20 +372,22 @@ </customize-chrome-combobox> <cr-grid columns="6" id="descriptorMenuD"> <template is="dom-repeat" items="[[descriptorD_]]"> - <cr-button class="default-color" on-click="onDefaultColorClick_" + <button class="default-color" on-click="onDefaultColorClick_" aria-current$="[[getColorCheckedStatus_(item, selectedDefaultColor_)]]" title$="[[getColorLabel_(item)]]"> + <paper-ripple></paper-ripple> <customize-chrome-check-mark-wrapper class="color-check-mark" checked="[[isColorSelected_(item, selectedDefaultColor_)]]" checkmark-border-hidden> <span class="descriptor-d" style$="background-color: [[item]];"> </span> </customize-chrome-check-mark-wrapper> - </cr-button> + </button> </template> - <cr-button id="customColorContainer" on-click="onCustomColorClick_" + <button id="customColorContainer" on-click="onCustomColorClick_" aria-current$="[[getCustomColorCheckedStatus_(selectedHue_)]]" title="$i18n{colorPickerLabel}"> + <paper-ripple></paper-ripple> <customize-chrome-check-mark-wrapper class="color-check-mark" checked="[[selectedHue_]]" checkmark-border-hidden> <div class="descriptor-d" @@ -368,7 +395,7 @@ <div id="colorPickerIcon"></div> </div> </customize-chrome-check-mark-wrapper> - </cr-button> + </button> </div> </cr-grid> <cr-theme-hue-slider-dialog id="hueSlider"
diff --git a/chrome/browser/resources/side_panel/customize_chrome/wallpaper_search/wallpaper_search.ts b/chrome/browser/resources/side_panel/customize_chrome/wallpaper_search/wallpaper_search.ts index ac9e098..585822f8 100644 --- a/chrome/browser/resources/side_panel/customize_chrome/wallpaper_search/wallpaper_search.ts +++ b/chrome/browser/resources/side_panel/customize_chrome/wallpaper_search/wallpaper_search.ts
@@ -14,8 +14,10 @@ import 'chrome://resources/cr_elements/cr_icons.css.js'; import 'chrome://resources/cr_elements/cr_input/cr_input.js'; import 'chrome://resources/cr_elements/cr_loading_gradient/cr_loading_gradient.js'; +import 'chrome://resources/cr_elements/cr_shared_vars.css.js'; import 'chrome://resources/cr_elements/icons.html.js'; import 'chrome://resources/cr_components/theme_color_picker/theme_hue_slider_dialog.js'; +import 'chrome://resources/polymer/v3_0/paper-ripple/paper-ripple.js'; import {SpHeading} from 'chrome://customize-chrome-side-panel.top-chrome/shared/sp_heading.js'; import {ThemeHueSliderDialogElement} from 'chrome://resources/cr_components/theme_color_picker/theme_hue_slider_dialog.js';
diff --git a/chrome/browser/resources/tab_search/tab_organization_shared_style.css b/chrome/browser/resources/tab_search/tab_organization_shared_style.css index b5ff5d1..cd2a942 100644 --- a/chrome/browser/resources/tab_search/tab_organization_shared_style.css +++ b/chrome/browser/resources/tab_search/tab_organization_shared_style.css
@@ -7,9 +7,10 @@ * #css_wrapper_metadata_end */ .tab-organization-body { - color: var(--cr-secondary-text-color); + color: var(--color-secondary-foreground); font-size: 13px; font-weight: 400; + line-height: 20px; } .tab-organization-container {
diff --git a/chrome/browser/share/android/BUILD.gn b/chrome/browser/share/android/BUILD.gn index 4f4db71..41333e7 100644 --- a/chrome/browser/share/android/BUILD.gn +++ b/chrome/browser/share/android/BUILD.gn
@@ -16,10 +16,8 @@ "java/res/drawable/preview_icon_border_background.xml", "java/res/drawable/qrcode_background.xml", "java/res/drawable/save_icon.xml", - "java/res/drawable/save_to_device.xml", "java/res/drawable/share_icon.xml", "java/res/drawable/text_icon.xml", - "java/res/drawable/webnote.xml", "java/res/layout/qrcode_dialog.xml", "java/res/layout/qrcode_share_layout.xml", "java/res/layout/screenshot_share_sheet.xml",
diff --git a/chrome/browser/share/android/java/res/drawable/save_to_device.xml b/chrome/browser/share/android/java/res/drawable/save_to_device.xml deleted file mode 100644 index 67251bf..0000000 --- a/chrome/browser/share/android/java/res/drawable/save_to_device.xml +++ /dev/null
@@ -1,18 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -Copyright 2017 The Chromium Authors -Use of this source code is governed by a BSD-style license that can be -found in the LICENSE file. ---> - -<vector xmlns:android="http://schemas.android.com/apk/res/android" - android:width="24dp" - android:height="24dp" - android:viewportWidth="24.0" - android:viewportHeight="24.0" - android:tint="@macro/default_icon_color"> - - <path - android:pathData="M19,9h-4V3H9v6H5l7,7 7,-7zM5,18v2h14v-2H5z" - android:fillColor="@android:color/white"/> -</vector> \ No newline at end of file
diff --git a/chrome/browser/share/android/java/res/drawable/webnote.xml b/chrome/browser/share/android/java/res/drawable/webnote.xml deleted file mode 100644 index 9537abf..0000000 --- a/chrome/browser/share/android/java/res/drawable/webnote.xml +++ /dev/null
@@ -1,11 +0,0 @@ -<vector xmlns:android="http://schemas.android.com/apk/res/android" - android:width="24dp" - android:height="24dp" - android:viewportWidth="24" - android:viewportHeight="24" - android:autoMirrored="true" - android:tint="@macro/default_icon_color"> - <path - android:fillColor="@android:color/white" - android:pathData="M4,20h16c1.1,0 2,-0.9 2,-2L22,6c0,-1.1 -0.9,-2 -2,-2L4,4c-1.1,0 -2,0.9 -2,2v12c0,1.1 0.9,2 2,2zM5,13v-2h14v2L5,13zM15,7v2L5,9L5,7h10zM19,15v2L5,17v-2h14z"/> -</vector>
diff --git a/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/ChromeProvidedSharingOptionsProviderBase.java b/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/ChromeProvidedSharingOptionsProviderBase.java index 89922a1a..a81bdac 100644 --- a/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/ChromeProvidedSharingOptionsProviderBase.java +++ b/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/ChromeProvidedSharingOptionsProviderBase.java
@@ -6,8 +6,6 @@ import android.app.Activity; import android.net.Uri; -import android.os.Build; -import android.os.Build.VERSION; import android.text.TextUtils; import android.view.View; @@ -17,9 +15,6 @@ import org.chromium.base.Callback; import org.chromium.base.supplier.Supplier; import org.chromium.chrome.R; -import org.chromium.chrome.browser.content_creation.notes.NoteCreationCoordinator; -import org.chromium.chrome.browser.content_creation.notes.NoteCreationCoordinatorFactory; -import org.chromium.chrome.browser.flags.ChromeFeatureList; import org.chromium.chrome.browser.preferences.Pref; import org.chromium.chrome.browser.profiles.Profile; import org.chromium.chrome.browser.share.ChromeShareExtras.DetailedContentType; @@ -31,14 +26,11 @@ import org.chromium.chrome.browser.tab.Tab; import org.chromium.components.browser_ui.bottomsheet.BottomSheetController; import org.chromium.components.browser_ui.device_lock.DeviceLockActivityLauncher; -import org.chromium.components.browser_ui.share.ShareImageFileUtils; import org.chromium.components.browser_ui.share.ShareParams; -import org.chromium.components.feature_engagement.EventConstants; import org.chromium.components.feature_engagement.Tracker; import org.chromium.components.user_prefs.UserPrefs; import org.chromium.ui.base.Clipboard; import org.chromium.ui.base.WindowAndroid; -import org.chromium.ui.widget.Toast; import java.util.ArrayList; import java.util.Arrays; @@ -51,7 +43,6 @@ /** Provides a list of Chrome-provided sharing options. */ public abstract class ChromeProvidedSharingOptionsProviderBase { private static final String USER_ACTION_COPY_URL_SELECTED = "SharingHubAndroid.CopyURLSelected"; - private static final String USER_ACTION_COPY_GIF_SELECTED = "SharingHubAndroid.CopyGifSelected"; private static final String USER_ACTION_COPY_IMAGE_SELECTED = "SharingHubAndroid.CopyImageSelected"; private static final String USER_ACTION_COPY_SELECTED = "SharingHubAndroid.CopySelected"; @@ -61,11 +52,6 @@ "SharingHubAndroid.SendTabToSelfSelected"; private static final String USER_ACTION_QR_CODE_SELECTED = "SharingHubAndroid.QRCodeSelected"; private static final String USER_ACTION_PRINT_SELECTED = "SharingHubAndroid.PrintSelected"; - private static final String USER_ACTION_SAVE_IMAGE_SELECTED = - "SharingHubAndroid.SaveImageSelected"; - - protected static final String USER_ACTION_WEB_STYLE_NOTES_SELECTED = - "SharingHubAndroid.WebnotesStylize"; protected final Activity mActivity; protected final WindowAndroid mWindowAndroid; @@ -257,41 +243,20 @@ return availableOptions; } - protected boolean usePolishedActionOrderedList() { - return ChromeFeatureList.isEnabled(ChromeFeatureList.SHARE_SHEET_CUSTOM_ACTIONS_POLISH); - } - /** * Creates all enabled {@link FirstPartyOption}s and adds them to {@code * mOrderedFirstPartyOptions} in the order they should appear. This has to be called by child * classes before the provider can function */ protected void initializeFirstPartyOptionsInOrder() { - // Only show a limited first party share selection for automotive - if (BuildInfo.getInstance().isAutomotive) { - maybeAddCopyFirstPartyOption(); - maybeAddSendTabToSelfFirstPartyOption(); - maybeAddQrCodeFirstPartyOption(); - return; - } - if (usePolishedActionOrderedList()) { - maybeAddCopyFirstPartyOption(); + maybeAddCopyFirstPartyOption(); + // Only show a limited first party share selection for automotive. + if (!BuildInfo.getInstance().isAutomotive) { maybeAddLongScreenshotFirstPartyOption(); maybeAddPrintFirstPartyOption(); - maybeAddSendTabToSelfFirstPartyOption(); - maybeAddQrCodeFirstPartyOption(); - } else { - maybeAddWebStyleNotesFirstPartyOption(); - maybeAddScreenshotFirstPartyOption(); - maybeAddLongScreenshotFirstPartyOption(); - // Always show the copy link option as some entries does not offer the change for copy - // (e.g. feed card) - maybeAddCopyFirstPartyOption(); - maybeAddSendTabToSelfFirstPartyOption(); - maybeAddQrCodeFirstPartyOption(); - maybeAddPrintFirstPartyOption(); - maybeAddDownloadImageFirstPartyOption(); } + maybeAddSendTabToSelfFirstPartyOption(); + maybeAddQrCodeFirstPartyOption(); } private void maybeAddSendTabToSelfFirstPartyOption() { @@ -308,13 +273,6 @@ } } - private void maybeAddScreenshotFirstPartyOption() { - FirstPartyOption option = createScreenshotFirstPartyOption(); - if (option != null) { - mOrderedFirstPartyOptions.add(option); - } - } - private void maybeAddLongScreenshotFirstPartyOption() { if (!mTabProvider.hasValue()) { return; @@ -331,40 +289,18 @@ } } - protected void maybeAddWebStyleNotesFirstPartyOption() { - if (ChromeFeatureList.isEnabled(ChromeFeatureList.WEBNOTES_STYLIZE)) { - mOrderedFirstPartyOptions.add(createWebNotesStylizeFirstPartyOption()); - } - } - protected void maybeAddCopyFirstPartyOption() { mOrderedFirstPartyOptions.add(createCopyLinkFirstPartyOption()); - if (usePolishedActionOrderedList()) { - mOrderedFirstPartyOptions.add(createCopyImageFirstPartyOption(false)); - } else { - mOrderedFirstPartyOptions.add(createCopyGifFirstPartyOption()); - mOrderedFirstPartyOptions.add(createCopyImageFirstPartyOption(true)); - } + mOrderedFirstPartyOptions.add(createCopyImageFirstPartyOption()); mOrderedFirstPartyOptions.add(createCopyFirstPartyOption()); mOrderedFirstPartyOptions.add(createCopyTextFirstPartyOption()); } - protected void maybeAddDownloadImageFirstPartyOption() { - mOrderedFirstPartyOptions.add(createSaveImageFirstPartyOption()); - } - private FirstPartyOption createCopyLinkFirstPartyOption() { - FirstPartyOptionBuilder builder = - new FirstPartyOptionBuilder( - ContentType.LINK_PAGE_VISIBLE, ContentType.LINK_PAGE_NOT_VISIBLE); - if (usePolishedActionOrderedList()) { - builder.setContentTypesToDisableFor( - ContentType.LINK_AND_TEXT, ContentType.IMAGE_AND_LINK); - } else { - builder.setContentTypesToDisableFor(ContentType.LINK_AND_TEXT); - } - - return builder.setIcon(R.drawable.ic_content_copy_black, R.string.sharing_copy_url) + return new FirstPartyOptionBuilder( + ContentType.LINK_PAGE_VISIBLE, ContentType.LINK_PAGE_NOT_VISIBLE) + .setContentTypesToDisableFor(ContentType.LINK_AND_TEXT, ContentType.IMAGE_AND_LINK) + .setIcon(R.drawable.ic_content_copy_black, R.string.sharing_copy_url) .setFeatureNameForMetrics(USER_ACTION_COPY_URL_SELECTED) .setOnClickCallback( (view) -> { @@ -377,59 +313,24 @@ .build(); } - private FirstPartyOption createCopyGifFirstPartyOption() { + /** + * @return The copy first party option. + */ + protected FirstPartyOption createCopyImageFirstPartyOption() { return new FirstPartyOptionBuilder(ContentType.IMAGE, ContentType.IMAGE_AND_LINK) - .setIcon(R.drawable.ic_content_copy_black, R.string.sharing_copy_gif) - // Enables only for GIF. - .setDetailedContentTypesToDisableFor( - DetailedContentType.IMAGE, - DetailedContentType.WEB_NOTES, - DetailedContentType.NOT_SPECIFIED) - .setFeatureNameForMetrics(USER_ACTION_COPY_GIF_SELECTED) + .setIcon(R.drawable.ic_content_copy_black, R.string.sharing_copy_image) + .setFeatureNameForMetrics(USER_ACTION_COPY_IMAGE_SELECTED) .setOnClickCallback( (view) -> { Uri imageUri = mShareParams.getImageUriToShare(); if (imageUri != null) { - Clipboard.getInstance().setImageUri(imageUri); - // TODO(crbug/1448589): Remove copy GIF action. - // This is separate from regular image copy due to the string used - // on the toast. To avoid growing complexity to customize text on - // toast in Clipboard, this is logic guarded by version code. - if (VERSION.SDK_INT < Build.VERSION_CODES.TIRAMISU) { - Toast.makeText( - mActivity, - R.string.gif_copied, - Toast.LENGTH_SHORT) - .show(); - } + Clipboard.getInstance() + .setImageUri(imageUri, /* notifyOnSuccess= */ true); } }) .build(); } - /** - * @param excludeGif Whether exclude the GIF copy from copy image action. - * @return The copy first party option. - */ - protected FirstPartyOption createCopyImageFirstPartyOption(boolean excludeGif) { - FirstPartyOptionBuilder builder = - new FirstPartyOptionBuilder(ContentType.IMAGE, ContentType.IMAGE_AND_LINK) - .setIcon(R.drawable.ic_content_copy_black, R.string.sharing_copy_image) - .setFeatureNameForMetrics(USER_ACTION_COPY_IMAGE_SELECTED) - .setOnClickCallback( - (view) -> { - Uri imageUri = mShareParams.getImageUriToShare(); - if (imageUri != null) { - Clipboard.getInstance() - .setImageUri(imageUri, /* notifyOnSuccess= */ true); - } - }); - if (excludeGif) { - builder.setDetailedContentTypesToDisableFor(DetailedContentType.GIF); - } - return builder.build(); - } - private FirstPartyOption createCopyFirstPartyOption() { return new FirstPartyOptionBuilder(ContentType.LINK_AND_TEXT) .setIcon(R.drawable.ic_content_copy_black, R.string.sharing_copy) @@ -516,58 +417,6 @@ .build(); } - private FirstPartyOption createSaveImageFirstPartyOption() { - return new FirstPartyOptionBuilder(ContentType.IMAGE, ContentType.IMAGE_AND_LINK) - .setIcon(R.drawable.save_to_device, R.string.sharing_save_image) - .setFeatureNameForMetrics(USER_ACTION_SAVE_IMAGE_SELECTED) - .setOnClickCallback( - (view) -> { - Uri imageUri = mShareParams.getImageUriToShare(); - if (imageUri == null) return; - ShareImageFileUtils.getBitmapFromUriAsync( - mActivity, - imageUri, - (bitmap) -> { - SaveBitmapDelegate saveBitmapDelegate = - new SaveBitmapDelegate( - mActivity, - bitmap, - R.string.save_image_filename_prefix, - null, - mShareParams.getWindow()); - saveBitmapDelegate.save(); - }); - }) - .build(); - } - - private FirstPartyOption createWebNotesStylizeFirstPartyOption() { - String title = mShareParams.getTitle(); - return new FirstPartyOptionBuilder(ContentType.HIGHLIGHTED_TEXT) - .setIcon(R.drawable.webnote, R.string.sharing_webnotes_create_card) - .setIconContentDescription( - mActivity.getString(R.string.sharing_webnotes_accessibility_description)) - .setFeatureNameForMetrics(USER_ACTION_WEB_STYLE_NOTES_SELECTED) - .setOnClickCallback( - (view) -> { - mFeatureEngagementTracker.notifyEvent( - EventConstants.SHARING_HUB_WEBNOTES_STYLIZE_USED); - NoteCreationCoordinator coordinator = - NoteCreationCoordinatorFactory.create( - mActivity, - mShareParams.getWindow(), - mUrl, - title, - mShareParams.getRawText().trim(), - mChromeOptionShareCallback); - coordinator.showDialog(); - }) - .build(); - } - - /** Create a {@link FirstPartyOption} used to do screenshot. Return null if not supported. */ - protected abstract @Nullable FirstPartyOption createScreenshotFirstPartyOption(); - /** * Create a {@link FirstPartyOption} used to do long screenshot. Return null if not supported. */
diff --git a/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/android_share_sheet/AndroidCustomActionProvider.java b/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/android_share_sheet/AndroidCustomActionProvider.java index 5b8a3b4e..45dab858 100644 --- a/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/android_share_sheet/AndroidCustomActionProvider.java +++ b/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/android_share_sheet/AndroidCustomActionProvider.java
@@ -11,10 +11,9 @@ import android.content.Context; import android.graphics.drawable.Icon; import android.net.Uri; +import android.os.Build; import androidx.annotation.Nullable; -import androidx.annotation.OptIn; -import androidx.core.os.BuildCompat; import org.chromium.base.Callback; import org.chromium.base.supplier.Supplier; @@ -121,12 +120,10 @@ * @param params The {@link ShareParams} for the current share. * @param chromeShareExtras The {@link ChromeShareExtras} for the current share, if exists. * @param isMultiWindow Whether the current activity is in multi-window mode. - * @return List of custom action used for Android share sheet. */ - @OptIn(markerClass = androidx.core.os.BuildCompat.PrereleaseSdkCheck.class) private void initCustomActions( ShareParams params, ChromeShareExtras chromeShareExtras, boolean isMultiWindow) { - if (!BuildCompat.isAtLeastU()) { + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.UPSIDE_DOWN_CAKE) { return; } @@ -148,18 +145,6 @@ // extends ChromeProvidedSharingOptionsProviderBase: - @Override - protected boolean usePolishedActionOrderedList() { - // Always use the polished list of actions for Android share sheet. - return true; - } - - @Nullable - @Override - protected FirstPartyOption createScreenshotFirstPartyOption() { - return null; - } - @Nullable @Override protected FirstPartyOption createLongScreenshotsFirstPartyOption() { @@ -186,12 +171,6 @@ } @Override - protected void maybeAddWebStyleNotesFirstPartyOption() {} - - @Override - protected void maybeAddDownloadImageFirstPartyOption() {} - - @Override protected void maybeAddCopyFirstPartyOption() { // getLinkToTextSuccessful is only populated when an link is generated for share. if (mShareParams.getLinkToTextSuccessful() != null @@ -208,7 +187,7 @@ && (mChromeShareExtras.getDetailedContentType() == DetailedContentType.WEB_SHARE || mChromeShareExtras.getDetailedContentType() == DetailedContentType.SCREENSHOT)) { - mOrderedFirstPartyOptions.add(createCopyImageFirstPartyOption(false)); + mOrderedFirstPartyOptions.add(createCopyImageFirstPartyOption()); } mOrderedFirstPartyOptions.add(createCopyImageWithLinkFirstPartyOption()); }
diff --git a/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/share_sheet/ChromeProvidedSharingOptionsProvider.java b/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/share_sheet/ChromeProvidedSharingOptionsProvider.java index 59e4e957..5ef20fa 100644 --- a/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/share_sheet/ChromeProvidedSharingOptionsProvider.java +++ b/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/share_sheet/ChromeProvidedSharingOptionsProvider.java
@@ -18,7 +18,6 @@ import org.chromium.chrome.browser.share.ShareContentTypeHelper.ContentType; import org.chromium.chrome.browser.share.link_to_text.LinkToTextCoordinator.LinkGeneration; import org.chromium.chrome.browser.share.long_screenshots.LongScreenshotsCoordinator; -import org.chromium.chrome.browser.share.screenshot.ScreenshotCoordinator; import org.chromium.chrome.browser.share.share_sheet.ShareSheetLinkToggleMetricsHelper.LinkToggleMetricsDetails; import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.modules.image_editor.ImageEditorModuleProvider; @@ -26,7 +25,6 @@ import org.chromium.components.browser_ui.device_lock.DeviceLockActivityLauncher; import org.chromium.components.browser_ui.share.ShareParams; import org.chromium.components.feature_engagement.EventConstants; -import org.chromium.components.feature_engagement.FeatureConstants; import org.chromium.components.feature_engagement.Tracker; import org.chromium.ui.base.WindowAndroid; import org.chromium.ui.modelutil.PropertyModel; @@ -40,14 +38,12 @@ // ComponentName used for Chrome share options in ShareParams.TargetChosenCallback public static final ComponentName CHROME_PROVIDED_FEATURE_COMPONENT_NAME = new ComponentName("CHROME", "CHROME_FEATURE"); - - private static final String USER_ACTION_SCREENSHOT_SELECTED = - "SharingHubAndroid.ScreenshotSelected"; private static final String USER_ACTION_LONG_SCREENSHOT_SELECTED = "SharingHubAndroid.LongScreenshotSelected"; private final ShareSheetBottomSheetContent mBottomSheetContent; private final long mShareStartTime; + // TODO(crbug.com/1448589): Remove the image editor. private final ImageEditorModuleProvider mImageEditorModuleProvider; private final @LinkGeneration int mLinkGenerationStatusForMetrics; private final LinkToggleMetricsDetails mLinkToggleMetricsDetails; @@ -139,7 +135,6 @@ } private PropertyModel getShareSheetModel(FirstPartyOption option) { - boolean setShowNewBadge = showNewBadge(option); boolean hideBottomSheetContentOnTap = hideBottomSheetContentOnTap(option); return ShareSheetPropertyModelBuilder.createPropertyModel( @@ -159,61 +154,11 @@ option.onClickCallback.onResult(view); callTargetChosenCallback(); }, - setShowNewBadge); - } - - private boolean showNewBadge(FirstPartyOption firstPartyOption) { - if (!mFeatureEngagementTracker.isInitialized()) return false; - - if (USER_ACTION_SCREENSHOT_SELECTED.equals(firstPartyOption.featureNameForMetrics)) { - return mFeatureEngagementTracker.shouldTriggerHelpUI( - FeatureConstants.IPH_SHARE_SCREENSHOT_FEATURE); - } - if (USER_ACTION_WEB_STYLE_NOTES_SELECTED.equals(firstPartyOption.featureNameForMetrics)) { - return mFeatureEngagementTracker.shouldTriggerHelpUI( - FeatureConstants.SHARING_HUB_WEBNOTES_STYLIZE_FEATURE); - } - return false; + /* showNewBadge= */ false); } private boolean hideBottomSheetContentOnTap(FirstPartyOption firstPartyOption) { - if (USER_ACTION_SCREENSHOT_SELECTED.equals(firstPartyOption.featureNameForMetrics) - || USER_ACTION_LONG_SCREENSHOT_SELECTED.equals( - firstPartyOption.featureNameForMetrics)) { - return false; - } - return true; - } - - @Override - protected FirstPartyOption createScreenshotFirstPartyOption() { - return new FirstPartyOptionBuilder( - ContentType.LINK_PAGE_VISIBLE, - ContentType.TEXT, - ContentType.HIGHLIGHTED_TEXT, - ContentType.IMAGE) - .setDetailedContentTypesToDisableFor(DetailedContentType.WEB_NOTES) - .setIcon(R.drawable.screenshot, R.string.sharing_screenshot) - .setFeatureNameForMetrics(USER_ACTION_SCREENSHOT_SELECTED) - .setDisableForMultiWindow(true) - .setOnClickCallback( - (view) -> { - mFeatureEngagementTracker.notifyEvent( - EventConstants.SHARE_SCREENSHOT_SELECTED); - ScreenshotCoordinator coordinator = - new ScreenshotCoordinator( - mActivity, - mShareParams.getWindow(), - mUrl, - mChromeOptionShareCallback, - mBottomSheetController, - usePolishedActionOrderedList() - ? null - : mImageEditorModuleProvider); - mBottomSheetController.addObserver(coordinator); - mBottomSheetController.hideContent(mBottomSheetContent, true); - }) - .build(); + return !USER_ACTION_LONG_SCREENSHOT_SELECTED.equals(firstPartyOption.featureNameForMetrics); } @Override @@ -238,9 +183,7 @@ mUrl, mChromeOptionShareCallback, mBottomSheetController, - usePolishedActionOrderedList() - ? null - : mImageEditorModuleProvider); + null); mBottomSheetController.addObserver(coordinator); mBottomSheetController.hideContent(mBottomSheetContent, true); })
diff --git a/chrome/browser/share/android/javatests/src/org/chromium/chrome/browser/share/android_share_sheet/AndroidShareSheetControllerUnitTest.java b/chrome/browser/share/android/javatests/src/org/chromium/chrome/browser/share/android_share_sheet/AndroidShareSheetControllerUnitTest.java index c65f865..f7c23977 100644 --- a/chrome/browser/share/android/javatests/src/org/chromium/chrome/browser/share/android_share_sheet/AndroidShareSheetControllerUnitTest.java +++ b/chrome/browser/share/android/javatests/src/org/chromium/chrome/browser/share/android_share_sheet/AndroidShareSheetControllerUnitTest.java
@@ -599,37 +599,6 @@ } @Test - @DisableFeatures(ChromeFeatureList.SHARE_SHEET_CUSTOM_ACTIONS_POLISH) - @Config( - sdk = 34, - shadows = {ShadowChooserActionHelper.class}) - public void ensureNonPolishActionInOrder() { - Uri testImageUri = Uri.parse("content://test.image.uri"); - ShareParams params = - new ShareParams.Builder(mWindow, "", "") - .setFileContentType("image/png") - .setSingleImageUri(testImageUri) - .setBypassFixingDomDistillerUrl(true) - .build(); - ChromeShareExtras chromeShareExtras = - new ChromeShareExtras.Builder() - .setDetailedContentType(DetailedContentType.IMAGE) - .setContentUrl(JUnitTestGURLs.GOOGLE_URL) - .setImageSrcUrl(JUnitTestGURLs.GOOGLE_URL_DOGS) - .build(); - - mController.showShareSheet(params, chromeShareExtras, 1L); - - // No download option here. - Intent intent = Shadows.shadowOf((Activity) mActivity).peekNextStartedActivity(); - assertCustomActions( - intent, - R.string.sharing_copy_image_with_link, - R.string.sharing_send_tab_to_self, - R.string.qr_code_share_icon_label); - } - - @Test @Config( sdk = 34, shadows = {ShadowChooserActionHelper.class})
diff --git a/chrome/browser/share/android/javatests/src/org/chromium/chrome/browser/share/share_sheet/ChromeProvidedSharingOptionsProviderTest.java b/chrome/browser/share/android/javatests/src/org/chromium/chrome/browser/share/share_sheet/ChromeProvidedSharingOptionsProviderTest.java index 654f11a2a..5a64ebe 100644 --- a/chrome/browser/share/android/javatests/src/org/chromium/chrome/browser/share/share_sheet/ChromeProvidedSharingOptionsProviderTest.java +++ b/chrome/browser/share/android/javatests/src/org/chromium/chrome/browser/share/share_sheet/ChromeProvidedSharingOptionsProviderTest.java
@@ -36,7 +36,6 @@ import org.chromium.base.test.util.UserActionTester; import org.chromium.chrome.R; import org.chromium.chrome.browser.feature_engagement.TrackerFactory; -import org.chromium.chrome.browser.flags.ChromeFeatureList; import org.chromium.chrome.browser.profiles.Profile; import org.chromium.chrome.browser.share.ChromeShareExtras.DetailedContentType; import org.chromium.chrome.browser.share.ShareContentTypeHelper; @@ -50,8 +49,6 @@ import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.test.AutomotiveContextWrapperTestRule; import org.chromium.chrome.test.util.browser.Features; -import org.chromium.chrome.test.util.browser.Features.DisableFeatures; -import org.chromium.chrome.test.util.browser.Features.EnableFeatures; import org.chromium.components.browser_ui.bottomsheet.BottomSheetController; import org.chromium.components.browser_ui.device_lock.DeviceLockActivityLauncher; import org.chromium.components.browser_ui.share.ShareParams; @@ -66,13 +63,10 @@ import org.chromium.url.GURL; import org.chromium.url.JUnitTestGURLs; -import java.util.ArrayList; import java.util.List; /** Instrumentation Unit tests {@link ChromeProvidedSharingOptionsProvider}. */ @RunWith(BaseRobolectricTestRunner.class) -@EnableFeatures(ChromeFeatureList.WEBNOTES_STYLIZE) -@DisableFeatures({ChromeFeatureList.SHARE_SHEET_CUSTOM_ACTIONS_POLISH}) public class ChromeProvidedSharingOptionsProviderTest { @Rule public ActivityScenarioRule<TestActivity> mActivityScenarioRule = @@ -179,22 +173,6 @@ } @Test - public void getPropertyModels_multiWindow_doesNotIncludeScreenshot() { - setUpChromeProvidedSharingOptionsProviderTest( - /* isIncognito= */ false, /* printingEnabled= */ false, LinkGeneration.MAX); - - List<PropertyModel> propertyModels = - mChromeProvidedSharingOptionsProvider.getPropertyModels( - ShareContentTypeHelper.ALL_CONTENT_TYPES_FOR_TEST, - DetailedContentType.NOT_SPECIFIED, - /* isMultiWindow= */ true); - - assertFalse( - "Property models should not contain Screenshot.", - propertyModelsContain(propertyModels, R.string.sharing_screenshot)); - } - - @Test public void getPropertyModels_isIncognito_doesNotIncludeQrCode() { setUpChromeProvidedSharingOptionsProviderTest( /* isIncognito= */ true, /* printingEnabled= */ false, LinkGeneration.MAX); @@ -238,15 +216,12 @@ /* isMultiWindow= */ false); // Long Screenshots is supported >= Android N (7.0). - List<String> expectedModels = new ArrayList<String>(); - expectedModels.add(mActivity.getResources().getString(R.string.sharing_screenshot)); - expectedModels.add(mActivity.getResources().getString(R.string.sharing_long_screenshot)); - expectedModels.addAll( + List<String> expectedModels = ImmutableList.of( mActivity.getResources().getString(R.string.sharing_copy_url), mActivity.getResources().getString(R.string.sharing_copy_image), - mActivity.getResources().getString(R.string.qr_code_share_icon_label), - mActivity.getResources().getString(R.string.sharing_save_image))); + mActivity.getResources().getString(R.string.sharing_long_screenshot), + mActivity.getResources().getString(R.string.qr_code_share_icon_label)); assertCorrectModelsAreInTheRightOrder(propertyModels, expectedModels); } @@ -261,14 +236,11 @@ DetailedContentType.IMAGE, /* isMultiWindow= */ false); - List<String> expectedModels = new ArrayList<String>(); - expectedModels.add(mActivity.getResources().getString(R.string.sharing_screenshot)); - expectedModels.add(mActivity.getResources().getString(R.string.sharing_long_screenshot)); - expectedModels.addAll( + List<String> expectedModels = ImmutableList.of( mActivity.getResources().getString(R.string.sharing_copy_image), - mActivity.getResources().getString(R.string.qr_code_share_icon_label), - mActivity.getResources().getString(R.string.sharing_save_image))); + mActivity.getResources().getString(R.string.sharing_long_screenshot), + mActivity.getResources().getString(R.string.qr_code_share_icon_label)); assertCorrectModelsAreInTheRightOrder(propertyModels, expectedModels); } @@ -286,7 +258,6 @@ List<String> expectedModels = ImmutableList.<String>builder() .add(mActivity.getResources().getString(R.string.sharing_copy_image)) - .add(mActivity.getResources().getString(R.string.sharing_save_image)) .build(); assertCorrectModelsAreInTheRightOrder(propertyModels, expectedModels); @@ -332,7 +303,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.SHARE_SHEET_CUSTOM_ACTIONS_POLISH}) public void getPropertyModels_sharingImageForAutomotiveIncognito() { mAutoTestRule.setIsAutomotive(true); setUpChromeProvidedSharingOptionsProviderTest( @@ -350,7 +320,6 @@ } @Test - @EnableFeatures({ChromeFeatureList.SHARE_SHEET_CUSTOM_ACTIONS_POLISH}) public void getPropertyModels_textAndLinksIncognito() { mAutoTestRule.setIsAutomotive(true); setUpChromeProvidedSharingOptionsProviderTest( @@ -543,9 +512,7 @@ String label = propertyModel.get(ShareSheetItemViewProperties.LABEL); Resources res = mActivity.getResources(); // There is no link generation for Stylize Cards / Screenshots / Long Screenshots. - if (label.equals(res.getString(R.string.sharing_webnotes_create_card)) - || label.equals(res.getString(R.string.sharing_screenshot)) - || label.equals(res.getString(R.string.sharing_long_screenshot))) { + if (label.equals(res.getString(R.string.sharing_long_screenshot))) { continue; }
diff --git a/chrome/browser/sync/test/integration/web_apps_sync_test_base.cc b/chrome/browser/sync/test/integration/web_apps_sync_test_base.cc index bdbc42c..4dd8791 100644 --- a/chrome/browser/sync/test/integration/web_apps_sync_test_base.cc +++ b/chrome/browser/sync/test/integration/web_apps_sync_test_base.cc
@@ -5,6 +5,7 @@ #include "chrome/browser/sync/test/integration/web_apps_sync_test_base.h" #include "base/containers/extend.h" +#include "chrome/common/chrome_features.h" #if BUILDFLAG(IS_CHROMEOS) #include "chrome/browser/apps/link_capturing/link_capturing_features.h" @@ -12,7 +13,6 @@ #if BUILDFLAG(IS_CHROMEOS_ASH) #include "ash/constants/ash_features.h" -#include "chrome/common/chrome_features.h" #include "chromeos/ash/components/standalone_browser/feature_refs.h" #endif @@ -30,6 +30,9 @@ #if BUILDFLAG(IS_CHROMEOS) // TODO(crbug.com/1357905): Update test driver to work with new UI. disabled_features.push_back(apps::features::kLinkCapturingUiUpdate); +#else + // TOOD(b/313492499): Update test driver to work with new intent picker UI. + disabled_features.push_back(features::kDesktopPWAsLinkCapturing); #endif #if BUILDFLAG(IS_CHROMEOS_ASH)
diff --git a/chrome/browser/ui/BUILD.gn b/chrome/browser/ui/BUILD.gn index b336cff3..b1cfe4a 100644 --- a/chrome/browser/ui/BUILD.gn +++ b/chrome/browser/ui/BUILD.gn
@@ -5764,6 +5764,8 @@ "views/side_panel/read_anything/read_anything_model.h", "views/side_panel/read_anything/read_anything_side_panel_controller.cc", "views/side_panel/read_anything/read_anything_side_panel_controller.h", + "views/side_panel/read_anything/read_anything_side_panel_web_view.cc", + "views/side_panel/read_anything/read_anything_side_panel_web_view.h", "views/side_panel/read_anything/read_anything_toolbar_view.cc", "views/side_panel/read_anything/read_anything_toolbar_view.h", "views/side_panel/read_later_side_panel_web_view.cc",
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings.grd b/chrome/browser/ui/android/strings/android_chrome_strings.grd index 4ace597..8730c70 100644 --- a/chrome/browser/ui/android/strings/android_chrome_strings.grd +++ b/chrome/browser/ui/android/strings/android_chrome_strings.grd
@@ -5261,18 +5261,10 @@ Copy image with link </message> - <message name="IDS_SHARING_COPY_GIF" desc="Label for the Copy GIF button in the sharing hub."> - Copy GIF - </message> - <message name="IDS_SHARING_COPY_HIGHLIGHT_WITHOUT_LINK" desc="Label for the Copy highlighted text without link button in the sharing hub. This is used when sharing highlighted text with a generated link."> Copy without link </message> - <message name="IDS_SHARING_SCREENSHOT" desc="Label for Screenshot button in the sharing hub."> - Screenshot - </message> - <message name="IDS_SHARING_LONG_SCREENSHOT" desc="Label for Long Screenshot button in the sharing hub."> Long Screenshot </message> @@ -5301,18 +5293,6 @@ Something went wrong. Try again. </message> - <message name="IDS_SHARING_WEBNOTES_CREATE_CARD" desc="Label for the button in sharing hub for creating card for the highlight text."> - Create card - </message> - - <message name="IDS_SHARING_WEBNOTES_ACCESSIBILITY_DESCRIPTION" desc="Accessibility description for the button in sharing hub for creating card for the highlight text."> - Create stylized card with highlight - </message> - - <message name="IDS_SHARING_SAVE_IMAGE" desc="Label for the button in sharing hub for saving an image to device."> - Save to device - </message> - <message name="IDS_SHARING_SEND_TAB_TO_SELF" desc="Label for the button in sharing hub for sending the current tab to other devices if user signed in (Send Tab to Self feature)."> Send to devices </message> @@ -5321,10 +5301,6 @@ Including link: <ph name="ORIGIN">%1$s<ex>https://www.example.com</ex></ph> </message> - <message name="IDS_GIF_COPIED" desc="Text shown in the toast notification when Copy GIF is selected in the sharing hub."> - GIF Copied - </message> - <message name="IDS_QR_CODE_OPEN_SETTINGS_LABEL" desc="Text on button on QR Code sharing tab triggering Android settings."> Open Settings </message> @@ -5406,10 +5382,6 @@ chrome_screenshot_<ph name="CURRENT_TIMESTAMP_MS">%1$s<ex>1582667748515</ex></ph> </message> - <message name="IDS_SAVE_IMAGE_FILENAME_PREFIX" desc="File name prefix for downloaded image that is followed by timestamp."> - chrome_image_<ph name="CURRENT_TIMESTAMP_MS">%1$s<ex>1582667748515</ex></ph> - </message> - <!-- Chime DFM module strings --> <message name="IDS_CHIME_MODULE_TITLE" desc="Text shown when the chime module is referenced in install start, success, failure UI (e.g. in IDS_MODULE_INSTALL_START_TEXT, which will expand to 'Installing Google Notifications Platform for Chrome…')."> Google Notifications Platform
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_GIF_COPIED.png.sha1 b/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_GIF_COPIED.png.sha1 deleted file mode 100644 index a4dcdff..0000000 --- a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_GIF_COPIED.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -eab081ae058a655fecef7798e0c2ed7a7e6e0f84 \ No newline at end of file
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SAVE_IMAGE_FILENAME_PREFIX.png.sha1 b/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SAVE_IMAGE_FILENAME_PREFIX.png.sha1 deleted file mode 100644 index 01b62f85..0000000 --- a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SAVE_IMAGE_FILENAME_PREFIX.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -65b8d241d6ec39843d255bb0f76ef550724fb288 \ No newline at end of file
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_COPY_GIF.png.sha1 b/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_COPY_GIF.png.sha1 deleted file mode 100644 index 0cf2eeb0..0000000 --- a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_COPY_GIF.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -5eb907dfe34856fdb381cc2caba78a4959746a60 \ No newline at end of file
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_SAVE_IMAGE.png.sha1 b/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_SAVE_IMAGE.png.sha1 deleted file mode 100644 index bcfe9a7..0000000 --- a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_SAVE_IMAGE.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -1f462a9327fef956d2cfc0896eb64fd2a0881a7a \ No newline at end of file
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_SCREENSHOT.png.sha1 b/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_SCREENSHOT.png.sha1 deleted file mode 100644 index d0d45acb..0000000 --- a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_SCREENSHOT.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -ebb50a402703a36fb9900bb2f6368a623e561df7 \ No newline at end of file
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_WEBNOTES_ACCESSIBILITY_DESCRIPTION.png.sha1 b/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_WEBNOTES_ACCESSIBILITY_DESCRIPTION.png.sha1 deleted file mode 100644 index ab9eb375..0000000 --- a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_WEBNOTES_ACCESSIBILITY_DESCRIPTION.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -692a7c7abf41a758643dd308fd2c600200fe477d \ No newline at end of file
diff --git a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_WEBNOTES_CREATE_CARD.png.sha1 b/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_WEBNOTES_CREATE_CARD.png.sha1 deleted file mode 100644 index 19e905e..0000000 --- a/chrome/browser/ui/android/strings/android_chrome_strings_grd/IDS_SHARING_WEBNOTES_CREATE_CARD.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -973eaf1223954ff6e8f45883885aa9a1364bec2c \ No newline at end of file
diff --git a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/ToolbarFeatures.java b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/ToolbarFeatures.java index 384e347..c0fed164 100644 --- a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/ToolbarFeatures.java +++ b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/ToolbarFeatures.java
@@ -18,24 +18,6 @@ /** Private constructor to avoid instantiation. */ private ToolbarFeatures() {} - /** Returns whether captures should be blocked as part of the ablation experiment. */ - public static boolean shouldBlockCapturesForAblation() { - // The ablation experiment turns off toolbar scrolling off the screen. Initially this also - // turned off captures, which are unnecessary when the toolbar cannot scroll off. But this - // param - // allows half of this work to still be done, allowing measurement of both halves when - // compared - // to the original ablation and controls. - if (!ChromeFeatureList.sToolbarScrollAblation.isEnabled()) { - // Not in ablation or pre-native, allow captures like normal. - return false; - } - - // Ablation is enabled, follow the param. - return !ChromeFeatureList.getFieldTrialParamByFeatureAsBoolean( - ChromeFeatureList.TOOLBAR_SCROLL_ABLATION_ANDROID, ALLOW_CAPTURES, false); - } - public static boolean shouldSuppressCaptures() { return ChromeFeatureList.sSuppressionToolbarCaptures.isEnabled(); }
diff --git a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/bottom/ScrollingBottomViewResourceFrameLayout.java b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/bottom/ScrollingBottomViewResourceFrameLayout.java index 3fed416..ca01e19b 100644 --- a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/bottom/ScrollingBottomViewResourceFrameLayout.java +++ b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/bottom/ScrollingBottomViewResourceFrameLayout.java
@@ -51,10 +51,6 @@ return new ViewResourceAdapter(this) { @Override public boolean isDirty() { - if (ToolbarFeatures.shouldBlockCapturesForAblation()) { - return false; - } - if (ToolbarFeatures.shouldSuppressCaptures()) { // Dirty rect tracking will claim changes more often than token differences due // to model changes. It is also cheaper to simply check a boolean, so do it
diff --git a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhone.java b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhone.java index f448ee3..d3ac515f 100644 --- a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhone.java +++ b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhone.java
@@ -1815,9 +1815,7 @@ @Override public CaptureReadinessResult isReadyForTextureCapture() { - if (ToolbarFeatures.shouldBlockCapturesForAblation()) { - return CaptureReadinessResult.notReady(TopToolbarBlockCaptureReason.SCROLL_ABLATION); - } else if (mForceTextureCapture) { + if (mForceTextureCapture) { return CaptureReadinessResult.readyForced(); } else if (ToolbarFeatures.shouldSuppressCaptures()) { return getReadinessStateWithSuppression();
diff --git a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarTablet.java b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarTablet.java index 57cf2db..96868ce 100644 --- a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarTablet.java +++ b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarTablet.java
@@ -439,9 +439,7 @@ @Override public CaptureReadinessResult isReadyForTextureCapture() { - if (ToolbarFeatures.shouldBlockCapturesForAblation()) { - return CaptureReadinessResult.notReady(TopToolbarBlockCaptureReason.SCROLL_ABLATION); - } else if (ToolbarFeatures.shouldSuppressCaptures()) { + if (ToolbarFeatures.shouldSuppressCaptures()) { if (urlHasFocus()) { return CaptureReadinessResult.notReady( TopToolbarBlockCaptureReason.URL_BAR_HAS_FOCUS);
diff --git a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarTabletUnitTest.java b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarTabletUnitTest.java index f927afe..4028118 100644 --- a/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarTabletUnitTest.java +++ b/chrome/browser/ui/android/toolbar/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarTabletUnitTest.java
@@ -326,14 +326,6 @@ } @Test - @EnableFeatures(ChromeFeatureList.TOOLBAR_SCROLL_ABLATION_ANDROID) - public void testIsReadyForTextureCapture_Ablation() { - CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture(); - Assert.assertFalse(result.isReady); - Assert.assertEquals(TopToolbarBlockCaptureReason.SCROLL_ABLATION, result.blockReason); - } - - @Test @DisableFeatures(ChromeFeatureList.SUPPRESS_TOOLBAR_CAPTURES) public void testIsReadyForTextureCapture_NoSuppression() { CaptureReadinessResult result = mToolbarTablet.isReadyForTextureCapture();
diff --git a/chrome/browser/ui/ash/accessibility/accessibility_controller_client.cc b/chrome/browser/ui/ash/accessibility/accessibility_controller_client.cc index 065b96a..a6c5d25 100644 --- a/chrome/browser/ui/ash/accessibility/accessibility_controller_client.cc +++ b/chrome/browser/ui/ash/accessibility/accessibility_controller_client.cc
@@ -4,7 +4,7 @@ #include "chrome/browser/ui/ash/accessibility/accessibility_controller_client.h" -#include "ash/public/cpp/accessibility_controller.h" +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/public/cpp/accessibility_controller_enums.h" #include "ash/wm/desks/templates/saved_desk_util.h" #include "chrome/browser/ash/accessibility/accessibility_manager.h"
diff --git a/chrome/browser/ui/ash/accessibility/accessibility_controller_client_unittest.cc b/chrome/browser/ui/ash/accessibility/accessibility_controller_client_unittest.cc index 5d91ca00..f021f97 100644 --- a/chrome/browser/ui/ash/accessibility/accessibility_controller_client_unittest.cc +++ b/chrome/browser/ui/ash/accessibility/accessibility_controller_client_unittest.cc
@@ -6,11 +6,11 @@ #include <optional> +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/public/cpp/accessibility_controller_enums.h" +#include "ash/test/ash_test_base.h" #include "base/time/time.h" -#include "chrome/browser/ui/ash/accessibility/fake_accessibility_controller.h" #include "chromeos/ash/components/audio/sounds.h" -#include "content/public/test/browser_task_environment.h" #include "testing/gtest/include/gtest/gtest.h" #include "ui/accessibility/ax_enums.mojom.h" #include "ui/gfx/geometry/point_f.h" @@ -86,7 +86,7 @@ } // namespace -class AccessibilityControllerClientTest : public testing::Test { +class AccessibilityControllerClientTest : public ash::AshTestBase { public: AccessibilityControllerClientTest() = default; @@ -96,17 +96,14 @@ const AccessibilityControllerClientTest&) = delete; ~AccessibilityControllerClientTest() override = default; - - private: - content::BrowserTaskEnvironment task_environment_; }; TEST_F(AccessibilityControllerClientTest, MethodCalls) { - FakeAccessibilityController controller; FakeAccessibilityControllerClient client; - // Tests client is set. - EXPECT_TRUE(controller.was_client_set()); + ash::AccessibilityController* controller = + ash::AccessibilityController::Get(); + controller->SetClient(&client); // Tests TriggerAccessibilityAlert method call. const ash::AccessibilityAlert alert = ash::AccessibilityAlert::SCREEN_ON;
diff --git a/chrome/browser/ui/ash/accessibility/fake_accessibility_controller.cc b/chrome/browser/ui/ash/accessibility/fake_accessibility_controller.cc deleted file mode 100644 index bc544209..0000000 --- a/chrome/browser/ui/ash/accessibility/fake_accessibility_controller.cc +++ /dev/null
@@ -1,121 +0,0 @@ -// Copyright 2019 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "chrome/browser/ui/ash/accessibility/fake_accessibility_controller.h" - -FakeAccessibilityController::FakeAccessibilityController() = default; - -FakeAccessibilityController::~FakeAccessibilityController() = default; - -void FakeAccessibilityController::SetClient( - ash::AccessibilityControllerClient* client) { - was_client_set_ = true; -} - -void FakeAccessibilityController::SetDarkenScreen(bool darken) {} - -void FakeAccessibilityController::BrailleDisplayStateChanged(bool connected) {} - -void FakeAccessibilityController::SetFocusHighlightRect( - const gfx::Rect& bounds_in_screen) {} - -void FakeAccessibilityController::SetCaretBounds( - const gfx::Rect& bounds_in_screen) {} - -void FakeAccessibilityController::SetAccessibilityPanelAlwaysVisible( - bool always_visible) {} - -void FakeAccessibilityController::SetAccessibilityPanelBounds( - const gfx::Rect& bounds, - ash::AccessibilityPanelState state) {} - -void FakeAccessibilityController::SetSelectToSpeakState( - ash::SelectToSpeakState state) {} - -void FakeAccessibilityController::SetSelectToSpeakEventHandlerDelegate( - ash::SelectToSpeakEventHandlerDelegate* delegate) {} - -void FakeAccessibilityController::ShowSelectToSpeakPanel( - const gfx::Rect& anchor, - bool is_paused, - double speed) {} - -void FakeAccessibilityController::HideSelectToSpeakPanel() {} - -void FakeAccessibilityController::OnSelectToSpeakPanelAction( - ash::SelectToSpeakPanelAction action, - double value) {} - -void FakeAccessibilityController::HideSwitchAccessBackButton() {} - -void FakeAccessibilityController::HideSwitchAccessMenu() {} - -void FakeAccessibilityController::ShowSwitchAccessBackButton( - const gfx::Rect& anchor) {} - -void FakeAccessibilityController::ShowSwitchAccessMenu( - const gfx::Rect& anchor, - std::vector<std::string> actions) {} - -void FakeAccessibilityController::StartPointScan() {} - -void FakeAccessibilityController::StopPointScan() {} - -void FakeAccessibilityController::SetPointScanSpeedDipsPerSecond( - int point_scan_speed_dips_per_second) {} - -void FakeAccessibilityController::SetDictationActive(bool is_active) {} - -void FakeAccessibilityController::ToggleDictationFromSource( - ash::DictationToggleSource source) {} - -void FakeAccessibilityController::EnableOrToggleDictationFromSource( - ash::DictationToggleSource source) {} - -void FakeAccessibilityController::ShowDictationLanguageUpgradedNudge( - const std::string& dictation_locale, - const std::string& application_locale) {} - -void FakeAccessibilityController::HandleAutoclickScrollableBoundsFound( - const gfx::Rect& bounds_in_screen) {} - -std::u16string FakeAccessibilityController::GetBatteryDescription() const { - return std::u16string(); -} - -void FakeAccessibilityController::SetVirtualKeyboardVisible(bool is_visible) {} - -void FakeAccessibilityController::PerformAcceleratorAction( - ash::AcceleratorAction accelerator_action) {} - -void FakeAccessibilityController::NotifyAccessibilityStatusChanged() {} - -bool FakeAccessibilityController::IsAccessibilityFeatureVisibleInTrayMenu( - const std::string& path) { - return true; -} - -void FakeAccessibilityController:: - DisableSwitchAccessDisableConfirmationDialogTesting() {} - -void FakeAccessibilityController:: - DisableSwitchAccessEnableNotificationTesting() {} - -void FakeAccessibilityController:: - UpdateDictationButtonOnSpeechRecognitionDownloadChanged( - int download_progress) {} - -void FakeAccessibilityController::ShowNotificationForDictation( - ash::DictationNotificationType type, - const std::u16string& display_language) {} - -void FakeAccessibilityController::UpdateDictationBubble( - bool visible, - ash::DictationBubbleIconType icon, - const std::optional<std::u16string>& text, - const std::optional<std::vector<ash::DictationBubbleHintType>>& hints) {} - -void FakeAccessibilityController::SilenceSpokenFeedback() {} - -void FakeAccessibilityController::ShowToast(ash::AccessibilityToastType type) {}
diff --git a/chrome/browser/ui/ash/accessibility/fake_accessibility_controller.h b/chrome/browser/ui/ash/accessibility/fake_accessibility_controller.h deleted file mode 100644 index 4e518351..0000000 --- a/chrome/browser/ui/ash/accessibility/fake_accessibility_controller.h +++ /dev/null
@@ -1,86 +0,0 @@ -// Copyright 2019 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CHROME_BROWSER_UI_ASH_ACCESSIBILITY_FAKE_ACCESSIBILITY_CONTROLLER_H_ -#define CHROME_BROWSER_UI_ASH_ACCESSIBILITY_FAKE_ACCESSIBILITY_CONTROLLER_H_ - -#include "ash/public/cpp/accessibility_controller.h" - -// Fake implementation of ash's mojo AccessibilityController interface. -class FakeAccessibilityController : ash::AccessibilityController { - public: - FakeAccessibilityController(); - - FakeAccessibilityController(const FakeAccessibilityController&) = delete; - FakeAccessibilityController& operator=(const FakeAccessibilityController&) = - delete; - - ~FakeAccessibilityController() override; - - bool was_client_set() const { return was_client_set_; } - - // ash::AccessibilityController: - void SetClient(ash::AccessibilityControllerClient* client) override; - void SetDarkenScreen(bool darken) override; - void BrailleDisplayStateChanged(bool connected) override; - void SetFocusHighlightRect(const gfx::Rect& bounds_in_screen) override; - void SetCaretBounds(const gfx::Rect& bounds_in_screen) override; - void SetAccessibilityPanelAlwaysVisible(bool always_visible) override; - void SetAccessibilityPanelBounds(const gfx::Rect& bounds, - ash::AccessibilityPanelState state) override; - void SetSelectToSpeakState(ash::SelectToSpeakState state) override; - void SetSelectToSpeakEventHandlerDelegate( - ash::SelectToSpeakEventHandlerDelegate* delegate) override; - void ShowSelectToSpeakPanel(const gfx::Rect& anchor, - bool is_paused, - double speed) override; - void HideSelectToSpeakPanel() override; - void OnSelectToSpeakPanelAction(ash::SelectToSpeakPanelAction action, - double value) override; - void HideSwitchAccessBackButton() override; - void HideSwitchAccessMenu() override; - void ShowSwitchAccessBackButton(const gfx::Rect& anchor) override; - void ShowSwitchAccessMenu(const gfx::Rect& anchor, - std::vector<std::string> actions) override; - void StartPointScan() override; - void StopPointScan() override; - void SetDictationActive(bool is_active) override; - void SetPointScanSpeedDipsPerSecond( - int point_scan_speed_dips_per_second) override; - void ToggleDictationFromSource(ash::DictationToggleSource source) override; - void EnableOrToggleDictationFromSource( - ash::DictationToggleSource source) override; - void ShowDictationLanguageUpgradedNudge( - const std::string& dictation_locale, - const std::string& application_locale) override; - void HandleAutoclickScrollableBoundsFound( - const gfx::Rect& bounds_in_screen) override; - std::u16string GetBatteryDescription() const override; - void SetVirtualKeyboardVisible(bool is_visible) override; - void PerformAcceleratorAction( - ash::AcceleratorAction accelerator_action) override; - void NotifyAccessibilityStatusChanged() override; - bool IsAccessibilityFeatureVisibleInTrayMenu( - const std::string& path) override; - void DisableSwitchAccessDisableConfirmationDialogTesting() override; - void DisableSwitchAccessEnableNotificationTesting() override; - void UpdateDictationButtonOnSpeechRecognitionDownloadChanged( - int download_progress) override; - void ShowNotificationForDictation( - ash::DictationNotificationType type, - const std::u16string& display_language) override; - void UpdateDictationBubble( - bool visible, - ash::DictationBubbleIconType icon, - const std::optional<std::u16string>& text, - const std::optional<std::vector<ash::DictationBubbleHintType>>& hints) - override; - void SilenceSpokenFeedback() override; - void ShowToast(ash::AccessibilityToastType type) override; - - private: - bool was_client_set_ = false; -}; - -#endif // CHROME_BROWSER_UI_ASH_ACCESSIBILITY_FAKE_ACCESSIBILITY_CONTROLLER_H_
diff --git a/chrome/browser/ui/ash/quick_settings_integration_test.cc b/chrome/browser/ui/ash/quick_settings_integration_test.cc index 3f9a163..3ad8c4a 100644 --- a/chrome/browser/ui/ash/quick_settings_integration_test.cc +++ b/chrome/browser/ui/ash/quick_settings_integration_test.cc
@@ -7,6 +7,7 @@ #include "ash/shell.h" #include "ash/system/model/enterprise_domain_model.h" #include "ash/system/model/system_tray_model.h" +#include "base/cpu.h" #include "base/test/gtest_tags.h" #include "base/test/scoped_feature_list.h" #include "chrome/browser/ash/crosapi/browser_util.h" @@ -16,6 +17,7 @@ #include "chrome/test/base/chromeos/crosier/interactive_ash_test.h" #include "chromeos/ash/components/standalone_browser/standalone_browser_features.h" #include "components/strings/grit/components_strings.h" +#include "testing/gtest/include/gtest/gtest.h" #include "ui/aura/env.h" #include "ui/aura/env_observer.h" #include "ui/aura/window.h" @@ -165,10 +167,13 @@ base::test::ScopedFeatureList feature_list_; }; -// Flaky because Lacros can be older than Ash in chromeos_integration_tests, -// causing NOTREACHED failures at the crosapi level. b/303359438 -IN_PROC_BROWSER_TEST_F(QuickSettingsLacrosIntegrationTest, - DISABLED_ManagedDeviceInfo) { +IN_PROC_BROWSER_TEST_F(QuickSettingsLacrosIntegrationTest, ManagedDeviceInfo) { + // On VM tryservers like chromeos-amd64-generic Lacros fails to start up + // correctly (it restarts in a loop). b/303359438 + if (base::CPU().is_running_in_vm()) { + GTEST_SKIP(); + } + ASSERT_TRUE(crosapi::browser_util::IsLacrosEnabled()); base::AddFeatureIdTagToTestResult(
diff --git a/chrome/browser/ui/commerce/commerce_ui_tab_helper.cc b/chrome/browser/ui/commerce/commerce_ui_tab_helper.cc index 2cf6779..36c1d6ac 100644 --- a/chrome/browser/ui/commerce/commerce_ui_tab_helper.cc +++ b/chrome/browser/ui/commerce/commerce_ui_tab_helper.cc
@@ -497,8 +497,8 @@ if (!cluster_id_for_page_.has_value()) return; - shopping_service_->IsClusterIdTrackedByUser( - cluster_id_for_page_.value(), + shopping_service_->IsSubscribed( + BuildUserSubscriptionForClusterId(cluster_id_for_page_.value()), base::BindOnce( [](base::WeakPtr<CommerceUiTabHelper> helper, bool is_tracked) { if (!helper) {
diff --git a/chrome/browser/ui/commerce/commerce_ui_tab_helper_unittest.cc b/chrome/browser/ui/commerce/commerce_ui_tab_helper_unittest.cc index 00ec31a..bdb5703 100644 --- a/chrome/browser/ui/commerce/commerce_ui_tab_helper_unittest.cc +++ b/chrome/browser/ui/commerce/commerce_ui_tab_helper_unittest.cc
@@ -17,6 +17,7 @@ #include "components/bookmarks/test/test_bookmark_client.h" #include "components/commerce/core/commerce_feature_list.h" #include "components/commerce/core/mock_shopping_service.h" +#include "components/commerce/core/price_tracking_utils.h" #include "components/commerce/core/shopping_service.h" #include "components/commerce/core/subscriptions/commerce_subscription.h" #include "components/commerce/core/test_utils.h" @@ -160,20 +161,19 @@ shopping_service_->SetResponseForGetProductInfoForUrl(info); shopping_service_->SetIsSubscribedCallbackValue(true); - shopping_service_->SetIsClusterIdTrackedByUserResponse(true); SimulateNavigationCommitted(GURL(kProductUrl)); // First ensure that subscribe is successful. - tab_helper_->OnSubscribe(CreateUserTrackedSubscription(kClusterId), true); + tab_helper_->OnSubscribe(BuildUserSubscriptionForClusterId(kClusterId), true); base::RunLoop().RunUntilIdle(); ASSERT_TRUE(tab_helper_->IsPriceTracking()); // Now assume the user has unsubscribed again. shopping_service_->SetIsSubscribedCallbackValue(false); - shopping_service_->SetIsClusterIdTrackedByUserResponse(false); - tab_helper_->OnUnsubscribe(CreateUserTrackedSubscription(kClusterId), true); + tab_helper_->OnUnsubscribe(BuildUserSubscriptionForClusterId(kClusterId), + true); base::RunLoop().RunUntilIdle(); ASSERT_FALSE(tab_helper_->IsPriceTracking()); @@ -241,7 +241,6 @@ shopping_service_->SetResponseForGetProductInfoForUrl(info); shopping_service_->SetIsSubscribedCallbackValue(false); - shopping_service_->SetIsClusterIdTrackedByUserResponse(false); shopping_service_->SetSubscribeCallbackValue(true); SimulateNavigationCommitted(GURL(kProductUrl)); @@ -255,7 +254,7 @@ testing::_)) .Times(1); - shopping_service_->SetIsClusterIdTrackedByUserResponse(true); + shopping_service_->SetIsSubscribedCallbackValue(true); tab_helper_->SetPriceTrackingState(true, true, base::DoNothing()); ASSERT_TRUE(GetPendingTrackingStateForTesting().has_value()); ASSERT_TRUE(GetPendingTrackingStateForTesting().value());
diff --git a/chrome/browser/ui/views/bookmarks/bookmark_bubble_view.cc b/chrome/browser/ui/views/bookmarks/bookmark_bubble_view.cc index a4abb29..fab397a 100644 --- a/chrome/browser/ui/views/bookmarks/bookmark_bubble_view.cc +++ b/chrome/browser/ui/views/bookmarks/bookmark_bubble_view.cc
@@ -43,7 +43,6 @@ #include "components/image_fetcher/core/image_fetcher.h" #include "components/image_fetcher/core/image_fetcher_service.h" #include "components/page_image_service/image_service.h" -#include "components/power_bookmarks/core/power_bookmark_features.h" #include "components/signin/public/base/signin_buildflags.h" #include "components/signin/public/base/signin_metrics.h" #include "components/strings/grit/components_strings.h" @@ -380,9 +379,7 @@ CreatePriceTrackingEmailCallback(profile, anchor_view, web_contents, bookmark_node); - bool show_simplified_flow = - !already_bookmarked && base::FeatureList::IsEnabled( - power_bookmarks::kSimplifiedBookmarkSaveFlow); + bool show_simplified_flow = !already_bookmarked; auto bubble_delegate_unique = std::make_unique<BookmarkBubbleDelegate>( std::move(delegate), browser, url, show_simplified_flow);
diff --git a/chrome/browser/ui/views/bookmarks/bookmark_bubble_view_interactive_uitest.cc b/chrome/browser/ui/views/bookmarks/bookmark_bubble_view_interactive_uitest.cc index 56f6498..b0eaca2e 100644 --- a/chrome/browser/ui/views/bookmarks/bookmark_bubble_view_interactive_uitest.cc +++ b/chrome/browser/ui/views/bookmarks/bookmark_bubble_view_interactive_uitest.cc
@@ -42,10 +42,7 @@ class BookmarkBubbleViewInteractiveTest : public InteractiveBrowserTest { public: void SetUp() override { - test_features_.InitWithFeatures( - {commerce::kShoppingCollection, - power_bookmarks::kSimplifiedBookmarkSaveFlow}, - {}); + test_features_.InitWithFeatures({commerce::kShoppingCollection}, {}); set_open_about_blank_on_browser_launch(true); ASSERT_TRUE(embedded_test_server()->InitializeAndListen());
diff --git a/chrome/browser/ui/views/commerce/price_tracking_email_dialog_view_interactive_uitest.cc b/chrome/browser/ui/views/commerce/price_tracking_email_dialog_view_interactive_uitest.cc index f85f755..45353380 100644 --- a/chrome/browser/ui/views/commerce/price_tracking_email_dialog_view_interactive_uitest.cc +++ b/chrome/browser/ui/views/commerce/price_tracking_email_dialog_view_interactive_uitest.cc
@@ -130,7 +130,6 @@ info.product_cluster_id.emplace(kClusterId); mock_shopping_service->SetResponseForGetProductInfoForUrl(info); mock_shopping_service->SetIsSubscribedCallbackValue(true); - mock_shopping_service->SetIsClusterIdTrackedByUserResponse(true); } base::WeakPtrFactory<PriceTrackingEmailDialogConsentViewInteractiveTest>
diff --git a/chrome/browser/ui/views/commerce/price_tracking_icon_view_integration_test.cc b/chrome/browser/ui/views/commerce/price_tracking_icon_view_integration_test.cc index 4b368de..d6f338b4 100644 --- a/chrome/browser/ui/views/commerce/price_tracking_icon_view_integration_test.cc +++ b/chrome/browser/ui/views/commerce/price_tracking_icon_view_integration_test.cc
@@ -22,6 +22,7 @@ #include "components/bookmarks/test/bookmark_test_helpers.h" #include "components/commerce/core/commerce_feature_list.h" #include "components/commerce/core/mock_shopping_service.h" +#include "components/commerce/core/price_tracking_utils.h" #include "components/commerce/core/test_utils.h" #include "components/omnibox/browser/vector_icons.h" #include "components/strings/grit/components_strings.h" @@ -111,11 +112,11 @@ void SimulateSubscriptionChangeEvent(bool is_subscribed) { if (is_subscribed) { - GetTabHelper()->OnSubscribe(commerce::CreateUserTrackedSubscription(0L), - true); + GetTabHelper()->OnSubscribe( + commerce::BuildUserSubscriptionForClusterId(0L), true); } else { - GetTabHelper()->OnUnsubscribe(commerce::CreateUserTrackedSubscription(0L), - true); + GetTabHelper()->OnUnsubscribe( + commerce::BuildUserSubscriptionForClusterId(0L), true); } }
diff --git a/chrome/browser/ui/views/commerce/price_tracking_icon_view_interactive_uitest.cc b/chrome/browser/ui/views/commerce/price_tracking_icon_view_interactive_uitest.cc index 51c60ee..d210fbb6 100644 --- a/chrome/browser/ui/views/commerce/price_tracking_icon_view_interactive_uitest.cc +++ b/chrome/browser/ui/views/commerce/price_tracking_icon_view_interactive_uitest.cc
@@ -115,7 +115,7 @@ bookmarks::BookmarkModel* bookmark_model = BookmarkModelFactory::GetForBrowserContext(browser()->profile()); - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(true); + mock_shopping_service_->SetIsSubscribedCallbackValue(true); commerce::AddProductBookmark(bookmark_model, u"title", url, 0, is_price_tracked); @@ -182,7 +182,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingIconViewInteractiveTest, FUEBubbleShownOnPress) { - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); RunTestSequence( InstrumentTab(kShoppingTab), NavigateWebContents(kShoppingTab, @@ -209,7 +209,7 @@ commerce::AddProductBookmark(bookmark_model, u"title", embedded_test_server()->GetURL(kShoppingURL), 0, true); - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(true); + mock_shopping_service_->SetIsSubscribedCallbackValue(true); RunTestSequence( InstrumentTab(kShoppingTab), @@ -242,7 +242,7 @@ PriceTrackingBubbleShownOnPress_AfterFUE) { browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); RunTestSequence( InstrumentTab(kShoppingTab), @@ -262,7 +262,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingIconViewInteractiveTest, BubbleCanBeReshowOnPress) { - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); RunTestSequence( InstrumentTab(kShoppingTab), @@ -292,7 +292,7 @@ EnablePriceTrackOnPress) { browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); const GURL shopping_url = embedded_test_server()->GetURL(kShoppingURL); @@ -320,7 +320,7 @@ WaitForShow(kPriceTrackingBubbleDialogId)); SimulateServerPriceTrackStateUpdated(true, shopping_url); - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(true); + mock_shopping_service_->SetIsSubscribedCallbackValue(true); RunTestSequence( CheckView(kPriceTrackingChipElementId, @@ -349,7 +349,7 @@ CreateBookmarkOnPressIfNotExist) { browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); const GURL shopping_url = embedded_test_server()->GetURL(kShoppingURL); RunTestSequence(InstrumentTab(kShoppingTab), @@ -367,7 +367,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingIconViewInteractiveTest, RecordOmniboxChipClicked) { base::UserActionTester user_action_tester; - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); EXPECT_EQ(user_action_tester.GetActionCount( "Commerce.PriceTracking.OmniboxChipClicked"), 0); @@ -385,7 +385,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingIconViewInteractiveTest, RecordOmniboxChipTracked) { base::UserActionTester user_action_tester; - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); @@ -406,7 +406,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingIconViewInteractiveTest, NoRecordOmniboxChipTracked_ForTrackedProduct) { base::UserActionTester user_action_tester; - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(true); + mock_shopping_service_->SetIsSubscribedCallbackValue(true); browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); @@ -428,7 +428,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingIconViewInteractiveTest, NoRecordOmniboxChipTracked_ForFUEFlow) { base::UserActionTester user_action_tester; - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); EXPECT_EQ(user_action_tester.GetActionCount( "Commerce.PriceTracking.OmniboxChip.Tracked"), 0); @@ -445,7 +445,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingIconViewInteractiveTest, IconViewAccessibleName) { - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(true); + mock_shopping_service_->SetIsSubscribedCallbackValue(true); RunTestSequence( InstrumentTab(kShoppingTab), NavigateWebContents(kShoppingTab, @@ -478,7 +478,7 @@ IconRevertedOnFailure) { browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); // Simulate subscription failure. mock_shopping_service_->SetSubscribeCallbackValue(false); @@ -545,7 +545,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingBubbleInteractiveTest, RecordFirstRunBubbleShown) { - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); EXPECT_EQ(user_action_tester_.GetActionCount( "Commerce.PriceTracking.FirstRunBubbleShown"), 0); @@ -565,7 +565,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingBubbleInteractiveTest, RecordConfirmationShown) { - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); EXPECT_EQ(user_action_tester_.GetActionCount( @@ -586,7 +586,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingBubbleInteractiveTest, RecordConfirmationUntracked) { - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); EXPECT_EQ(user_action_tester_.GetActionCount( @@ -614,7 +614,7 @@ IN_PROC_BROWSER_TEST_F(PriceTrackingBubbleInteractiveTest, RecordEditedBookmarkFolderFromOmniboxBubble) { - mock_shopping_service_->SetIsClusterIdTrackedByUserResponse(false); + mock_shopping_service_->SetIsSubscribedCallbackValue(false); browser()->profile()->GetPrefs()->SetBoolean( prefs::kShouldShowPriceTrackFUEBubble, false); EXPECT_EQ(user_action_tester_.GetActionCount(
diff --git a/chrome/browser/ui/views/controls/subpage_view.cc b/chrome/browser/ui/views/controls/subpage_view.cc index 8ed6b2d..8fa4a7b 100644 --- a/chrome/browser/ui/views/controls/subpage_view.cc +++ b/chrome/browser/ui/views/controls/subpage_view.cc
@@ -18,14 +18,13 @@ #include "ui/views/controls/button/image_button_factory.h" #include "ui/views/controls/highlight_path_generator.h" #include "ui/views/controls/separator.h" -#include "ui/views/layout/box_layout.h" +#include "ui/views/layout/box_layout_view.h" #include "ui/views/layout/flex_layout_view.h" namespace { constexpr int kSeparatorBottomMargin = 16; constexpr int kBackIconSize = 16; constexpr int kBackIconSizeRefreshStyle = 20; -constexpr int kSpaceBetweenBackArrowAndTitle = 8; } // namespace DEFINE_ELEMENT_IDENTIFIER_VALUE(kSubpageViewId); @@ -46,9 +45,13 @@ } void SubpageView::SetUpSubpageTitle(views::Button::PressedCallback callback) { - auto title_view = std::make_unique<views::View>(); - title_view->SetLayoutManager(std::make_unique<views::FlexLayout>()) - ->SetCrossAxisAlignment(views::LayoutAlignment::kCenter); + const auto* layout_provider = ChromeLayoutProvider::Get(); + auto title_view = std::make_unique<views::BoxLayoutView>(); + title_view->SetBetweenChildSpacing( + layout_provider->GetDistanceMetric( + views::DISTANCE_RELATED_CONTROL_HORIZONTAL) - + layout_provider->GetInsetsMetric(views::INSETS_VECTOR_IMAGE_BUTTON) + .right()); auto back_button = views::CreateVectorImageButtonWithNativeTheme( std::move(callback), @@ -72,9 +75,22 @@ .SetTextContext(views::style::CONTEXT_DIALOG_TITLE) .SetHorizontalAlignment(gfx::ALIGN_LEFT) .Build()); - title_->SetProperty( - views::kMarginsKey, - gfx::Insets::TLBR(0, kSpaceBetweenBackArrowAndTitle, 0, 0)); + title_->SetMultiLine(true); + // This limits the SubpageView only works for standard the preferred width + // bubble. + int title_width = + layout_provider->GetDistanceMetric( + views::DISTANCE_BUBBLE_PREFERRED_WIDTH) - + layout_provider->GetInsetsMetric(views::INSETS_DIALOG).width() - + layout_provider->GetInsetsMetric(views::INSETS_DIALOG_TITLE).width(); + views::Button* close_button = bubble_frame_view_->close_button(); + if (close_button && close_button->GetVisible()) { + int close_button_width = + bubble_frame_view_->close_button()->width() + + layout_provider->GetDistanceMetric(views::DISTANCE_CLOSE_BUTTON_MARGIN); + title_width -= close_button_width; + } + title_->SetMaximumWidth(title_width); bubble_frame_view_->SetTitleView(std::move(title_view)); }
diff --git a/chrome/browser/ui/views/controls/subpage_view.h b/chrome/browser/ui/views/controls/subpage_view.h index 7e22ee5..c045338f 100644 --- a/chrome/browser/ui/views/controls/subpage_view.h +++ b/chrome/browser/ui/views/controls/subpage_view.h
@@ -19,7 +19,8 @@ DECLARE_ELEMENT_IDENTIFIER_VALUE(kSubpageViewId); -// A sub-page View for the PageSwitcherView. This view contains: +// A sub-page View for the PageSwitcherView in a standard preferred width +// bubble. This view contains: // * a header that has a page navigation back button, a title label, a close // button // * a content view
diff --git a/chrome/browser/ui/views/frame/browser_view.cc b/chrome/browser/ui/views/frame/browser_view.cc index 34b8cc5..16e2a27 100644 --- a/chrome/browser/ui/views/frame/browser_view.cc +++ b/chrome/browser/ui/views/frame/browser_view.cc
@@ -1756,7 +1756,7 @@ contents->GetPrimaryMainFrame() ->GetBrowserContext() ->GetPermissionController() - ->UnsubscribePermissionStatusChange( + ->UnsubscribeFromPermissionStatusChange( window_management_subscription_id_.value()); window_management_subscription_id_.reset(); } @@ -2336,7 +2336,7 @@ // It is safe to bind base::Unretained(this) because WebContents is // owned by BrowserView. window_management_subscription_id_ = - controller->SubscribePermissionStatusChange( + controller->SubscribeToPermissionStatusChange( blink::PermissionType::WINDOW_MANAGEMENT, rfh->GetProcess(), origin, base::BindRepeating(&BrowserView::UpdateWindowManagementPermission, base::Unretained(this)));
diff --git a/chrome/browser/ui/views/intent_picker_bubble_view_browsertest.cc b/chrome/browser/ui/views/intent_picker_bubble_view_browsertest.cc index 1931607..dab94d1 100644 --- a/chrome/browser/ui/views/intent_picker_bubble_view_browsertest.cc +++ b/chrome/browser/ui/views/intent_picker_bubble_view_browsertest.cc
@@ -38,12 +38,7 @@ class IntentPickerBrowserTest : public web_app::WebAppNavigationBrowserTest { public: - IntentPickerBrowserTest() { - std::vector<base::test::FeatureRef> disabled_features = { - // TODO(crbug.com/1001189): Stop disabling Paint Holding. - blink::features::kPaintHolding}; - scoped_feature_list_.InitWithFeatures({}, disabled_features); - } + IntentPickerBrowserTest() = default; template <typename Action> testing::AssertionResult DoAndWaitForIntentPickerIconUpdate(Action action) { @@ -116,9 +111,6 @@ EXPECT_EQ(test_web_app_id(), app_info[0].launch_name); EXPECT_EQ(GetAppName(), app_info[0].display_name); } - - private: - base::test::ScopedFeatureList scoped_feature_list_; }; // Tests to do with the behavior of the intent picker icon in the omnibox. Does @@ -127,7 +119,31 @@ // separately in intent_chip_button_browsertest.cc. class IntentPickerIconBrowserTest : public IntentPickerBrowserTest, - public ::testing::WithParamInterface<std::string> {}; + public ::testing::WithParamInterface<std::tuple<std::string, bool>> { + public: + // TODO(crbug.com/1001189): Stop disabling Paint Holding. + IntentPickerIconBrowserTest() { + feature_list_.InitWithFeaturesAndParameters( + apps::test::GetFeaturesToEnableLinkCapturingUX( + /*override_captures_by_default=*/IsLinkCapturingEnabled()), + {blink::features::kPaintHolding}); + } + + bool IsLinkCapturingEnabled() { return std::get<bool>(GetParam()); } + + std::string rel() { return std::get<std::string>(GetParam()); } + + bool IsDefaultOnEnabled() { +#if BUILDFLAG(IS_CHROMEOS) + return false; +#else + return IsLinkCapturingEnabled(); +#endif // BUILDFLAG(IS_CHROMEOS) + } + + private: + base::test::ScopedFeatureList feature_list_; +}; // Tests that clicking a link from a tabbed browser to outside the scope of an // installed app does not show the intent picker. @@ -139,7 +155,7 @@ https_server().GetURL(GetAppUrlHost(), GetOutOfScopeUrlPath()); NavigateToLaunchingPage(browser()); ASSERT_TRUE(ExpectLinkClickNotCapturedIntoAppBrowser( - browser(), out_of_scope_url, GetParam())); + browser(), out_of_scope_url, rel())); views::Button* intent_picker_view = GetIntentPickerIcon(); EXPECT_FALSE(intent_picker_view->GetVisible()); @@ -159,6 +175,9 @@ #endif IN_PROC_BROWSER_TEST_P(IntentPickerIconBrowserTest, MAYBE_NavigationToInScopeLinkShowsIntentPicker) { + if (IsDefaultOnEnabled()) { + GTEST_SKIP() << "Default On will launch app by default"; + } InstallTestWebApp(); const GURL in_scope_url = @@ -168,8 +187,8 @@ base::RunLoop run_loop; tab_helper->SetIconUpdateCallbackForTesting(run_loop.QuitClosure()); - ASSERT_TRUE(ExpectLinkClickNotCapturedIntoAppBrowser(browser(), in_scope_url, - GetParam())); + ASSERT_TRUE( + ExpectLinkClickNotCapturedIntoAppBrowser(browser(), in_scope_url, rel())); run_loop.Run(); views::Button* intent_picker_icon = GetIntentPickerIcon(); @@ -197,9 +216,9 @@ views::Button* intent_picker_icon = GetIntentPickerIcon(); // OpenNewTab opens a new tab and focus on the new tab. - OpenNewTab(in_scope_url, /*rel=*/GetParam()); + OpenNewTab(in_scope_url, /*rel=*/rel()); EXPECT_TRUE(intent_picker_icon->GetVisible()); - OpenNewTab(out_of_scope_url, /*rel=*/GetParam()); + OpenNewTab(out_of_scope_url, /*rel=*/rel()); EXPECT_FALSE(intent_picker_icon->GetVisible()); chrome::SelectPreviousTab(browser()); @@ -209,7 +228,7 @@ } // Tests that the navigation in iframe doesn't affect intent picker icon -IN_PROC_BROWSER_TEST_F(IntentPickerIconBrowserTest, +IN_PROC_BROWSER_TEST_P(IntentPickerIconBrowserTest, IframeNavigationDoesNotAffectIntentPicker) { InstallTestWebApp(); @@ -259,11 +278,11 @@ OpenNewTab(in_scope_url); EXPECT_TRUE(intent_picker_icon->GetVisible()); - ASSERT_TRUE(DoAndWaitForIntentPickerIconUpdate([this, redirect_url, - out_of_scope_url] { - ClickLinkAndWaitForURL(GetWebContents(), redirect_url, out_of_scope_url, - LinkTarget::SELF, GetParam()); - })); + ASSERT_TRUE(DoAndWaitForIntentPickerIconUpdate( + [this, redirect_url, out_of_scope_url] { + ClickLinkAndWaitForURL(GetWebContents(), redirect_url, out_of_scope_url, + LinkTarget::SELF, rel()); + })); EXPECT_FALSE(intent_picker_icon->GetVisible()); } @@ -277,7 +296,7 @@ #define MAYBE_DoNotShowIconAndBubbleOnServicePages \ DoNotShowIconAndBubbleOnServicePages #endif -IN_PROC_BROWSER_TEST_F(IntentPickerIconBrowserTest, +IN_PROC_BROWSER_TEST_P(IntentPickerIconBrowserTest, MAYBE_DoNotShowIconAndBubbleOnServicePages) { InstallTestWebApp(); @@ -311,7 +330,7 @@ #else #define MAYBE_DoNotShowIconOnErrorPages DoNotShowIconOnErrorPages #endif // BUILDFLAG(IS_MAC) -IN_PROC_BROWSER_TEST_F(IntentPickerIconBrowserTest, +IN_PROC_BROWSER_TEST_P(IntentPickerIconBrowserTest, MAYBE_DoNotShowIconOnErrorPages) { InstallTestWebApp(); InstallTestWebApp("www.google.com", "/"); @@ -348,7 +367,7 @@ #else #define MAYBE_PushStateURLChangeTest PushStateURLChangeTest #endif -IN_PROC_BROWSER_TEST_F(IntentPickerIconBrowserTest, +IN_PROC_BROWSER_TEST_P(IntentPickerIconBrowserTest, MAYBE_PushStateURLChangeTest) { // Note: The test page is served from embedded_test_server() as https_server() // always returns empty responses. @@ -378,17 +397,29 @@ INSTANTIATE_TEST_SUITE_P( All, IntentPickerIconBrowserTest, - testing::Values("", "noopener", "noreferrer", "nofollow")); + testing::Combine(testing::Values("", "noopener", "noreferrer", "nofollow"), +#if BUILDFLAG(IS_CHROMEOS) + testing::Values(false)), +#else + testing::Values(true, false)), +#endif // BUILDFLAG(IS_CHROMEOS) + [](const testing::TestParamInfo<std::tuple<std::string, bool>>& info) { + std::string test_name; + test_name = std::get<std::string>(info.param); + test_name.append(std::get<bool>(info.param) ? "DefaultOn" : "DefaultOff"); + return test_name; + }); class IntentPickerIconBrowserBubbleTest : public IntentPickerBrowserTest, public testing::WithParamInterface<bool> { public: + // TODO(crbug.com/1001189): Stop disabling Paint Holding. IntentPickerIconBrowserBubbleTest() { feature_list_.InitWithFeaturesAndParameters( apps::test::GetFeaturesToEnableLinkCapturingUX( /*override_captures_by_default=*/GetParam()), - {}); + {blink::features::kPaintHolding}); } bool LinkCapturingEnabledByDefault() const { return GetParam(); } @@ -454,6 +485,11 @@ return info.param ? "DefaultOn" : "DefaultOff"; }); +// This test only works when link capturing is set to default off for desktop +// platforms, as prerendering navigations are aborted during link captured app +// launches. See LinkCapturingNavigationThrottle::MaybeCreate for more +// information. +// TODO(b/297256243): Investigate prerendering integration with link capturing. class IntentPickerIconPrerenderingBrowserTest : public IntentPickerIconBrowserTest { public: @@ -522,7 +558,14 @@ INSTANTIATE_TEST_SUITE_P( All, IntentPickerIconPrerenderingBrowserTest, - testing::Values("", "noopener", "noreferrer", "nofollow")); + testing::Combine(testing::Values("", "noopener", "noreferrer", "nofollow"), + testing::Values(false)), + [](const testing::TestParamInfo<std::tuple<std::string, bool>>& info) { + std::string test_name; + test_name = std::get<std::string>(info.param); + test_name.append("DefaultOff"); + return test_name; + }); class IntentPickerIconFencedFrameBrowserTest : public IntentPickerIconBrowserTest { @@ -566,4 +609,15 @@ INSTANTIATE_TEST_SUITE_P( All, IntentPickerIconFencedFrameBrowserTest, - testing::Values("", "noopener", "noreferrer", "nofollow")); + testing::Combine(testing::Values("", "noopener", "noreferrer", "nofollow"), +#if BUILDFLAG(IS_CHROMEOS) + testing::Values(false)), +#else + testing::Values(true, false)), +#endif + [](const testing::TestParamInfo<std::tuple<std::string, bool>>& info) { + std::string test_name; + test_name = std::get<std::string>(info.param); + test_name.append(std::get<bool>(info.param) ? "DefaultOn" : "DefaultOff"); + return test_name; + });
diff --git a/chrome/browser/ui/views/permissions/chip_controller.cc b/chrome/browser/ui/views/permissions/chip_controller.cc index 261896e0..b813608 100644 --- a/chrome/browser/ui/views/permissions/chip_controller.cc +++ b/chrome/browser/ui/views/permissions/chip_controller.cc
@@ -473,6 +473,13 @@ } } +void ChipController::OnOcclusionStateChanged(bool occluded) { + if (GetBubbleWidget()) { + // Disable the prompt if it's occluded by a picture-in-picture window. + GetBubbleWidget()->GetContentsView()->SetEnabled(!occluded); + } +} + void ChipController::HideChip() { if (!chip_->GetVisible()) return; @@ -554,6 +561,7 @@ parent_was_visible_when_activation_changed_ = prompt_bubble_widget->GetPrimaryWindowWidget()->IsVisible(); prompt_bubble_widget->AddObserver(this); + occlusion_observation_.Observe(prompt_bubble_widget); } }
diff --git a/chrome/browser/ui/views/permissions/chip_controller.h b/chrome/browser/ui/views/permissions/chip_controller.h index 76c1b020b..908302366 100644 --- a/chrome/browser/ui/views/permissions/chip_controller.h +++ b/chrome/browser/ui/views/permissions/chip_controller.h
@@ -11,6 +11,8 @@ #include "base/check_is_test.h" #include "base/functional/callback_helpers.h" #include "base/timer/timer.h" +#include "chrome/browser/picture_in_picture/picture_in_picture_occlusion_observer.h" +#include "chrome/browser/picture_in_picture/scoped_picture_in_picture_occlusion_observation.h" #include "chrome/browser/ui/views/location_bar/omnibox_chip_button.h" #include "components/permissions/permission_prompt.h" #include "components/permissions/permission_request_manager.h" @@ -38,7 +40,8 @@ class ChipController : public permissions::PermissionRequestManager::Observer, public views::WidgetObserver, public BubbleOwnerDelegate, - public OmniboxChipButton::Observer { + public OmniboxChipButton::Observer, + public PictureInPictureOcclusionObserver { public: ChipController(Browser* browser_, OmniboxChipButton* chip_view); @@ -79,6 +82,9 @@ void OnExpandAnimationEnded() override; void OnCollapseAnimationEnded() override; + // PictureInPictureOcclusionObserver: + void OnOcclusionStateChanged(bool occluded) override; + // Initializes the permission prompt model as well as the permission request // manager and observes the prompt bubble. void InitializePermissionPrompt( @@ -237,6 +243,8 @@ base::ScopedObservation<OmniboxChipButton, OmniboxChipButton::Observer> observation_{this}; + ScopedPictureInPictureOcclusionObservation occlusion_observation_{this}; + base::WeakPtrFactory<ChipController> weak_factory_{this}; };
diff --git a/chrome/browser/ui/views/permissions/permission_chip_interactive_test.cc b/chrome/browser/ui/views/permissions/permission_chip_interactive_test.cc index 5246a536..8b1c8a66 100644 --- a/chrome/browser/ui/views/permissions/permission_chip_interactive_test.cc +++ b/chrome/browser/ui/views/permissions/permission_chip_interactive_test.cc
@@ -8,6 +8,8 @@ #include "base/time/time.h" #include "chrome/browser/permissions/quiet_notification_permission_ui_config.h" #include "chrome/browser/permissions/quiet_notification_permission_ui_state.h" +#include "chrome/browser/picture_in_picture/picture_in_picture_occlusion_tracker.h" +#include "chrome/browser/picture_in_picture/picture_in_picture_window_manager.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_window.h" @@ -43,6 +45,7 @@ #include "content/public/test/browser_test.h" #include "content/public/test/permissions_test_utils.h" #include "content/public/test/test_navigation_observer.h" +#include "media/base/media_switches.h" #include "net/dns/mock_host_resolver.h" #include "permission_prompt_chip.h" #include "ui/accessibility/ax_action_data.h" @@ -1645,3 +1648,71 @@ EXPECT_TRUE(content::EvalJs(main_rfh, kCheckNotifications).value.GetBool()); } + +class PictureInPictureOcclusionTrackingEnabledPermissionChipInteractiveTest + : public PermissionChipInteractiveTest { + public: + PictureInPictureOcclusionTrackingEnabledPermissionChipInteractiveTest() { + scoped_feature_list_.InitWithFeatures( + {media::kPictureInPictureOcclusionTracking}, {}); + } + + private: + base::test::ScopedFeatureList scoped_feature_list_; +}; + +IN_PROC_BROWSER_TEST_F( + PictureInPictureOcclusionTrackingEnabledPermissionChipInteractiveTest, + ShouldHideChipWhenOccludedByAPictureInPictureWindow) { + RequestPermission(permissions::RequestType::kGeolocation); + base::RunLoop().RunUntilIdle(); + + // Chip should be visible. Click it to open the prompt. + EXPECT_TRUE(GetChip()->GetVisible()); + ClickOnChip(GetChip()); + + views::View* prompt_view = + GetChipController()->GetBubbleWidget()->GetContentsView(); + ASSERT_NE(prompt_view, nullptr); + + // Create a picture-in-picture widget that does not occlude the prompt. + gfx::Rect prompt_widget_bounds = + prompt_view->GetWidget()->GetWindowBoundsInScreen(); + gfx::Rect non_occluding_bounds = + gfx::Rect(prompt_widget_bounds.right() + 1, 0, 100, 100); + views::Widget::InitParams init_params(views::Widget::InitParams::TYPE_WINDOW); + init_params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; + init_params.bounds = non_occluding_bounds; + auto pip_widget = std::make_unique<views::Widget>(std::move(init_params)); + pip_widget->Show(); + PictureInPictureWindowManager::GetInstance() + ->GetOcclusionTracker() + ->OnPictureInPictureWidgetOpened(pip_widget.get()); + + // The prompt should be enabled, as it's not occluded. + EXPECT_TRUE(prompt_view->GetEnabled()); + + // Move the picture-in-picture window to occlude the prompt. + pip_widget->SetBounds(prompt_widget_bounds); + + // The prompt should be disabled. We may need to wait for that to happen. + if (prompt_view->GetEnabled()) { + base::RunLoop wait_loop; + auto subscription = + prompt_view->AddEnabledChangedCallback(wait_loop.QuitClosure()); + wait_loop.Run(); + } + EXPECT_FALSE(prompt_view->GetEnabled()); + + // Move the picture-in-picture window to no longer occlude the prompt. + pip_widget->SetBounds(non_occluding_bounds); + + // The prompt should be enabled again. We may need to wait for that to happen. + if (!prompt_view->GetEnabled()) { + base::RunLoop wait_loop; + auto subscription = + prompt_view->AddEnabledChangedCallback(wait_loop.QuitClosure()); + wait_loop.Run(); + } + EXPECT_TRUE(prompt_view->GetEnabled()); +}
diff --git a/chrome/browser/ui/views/permissions/permission_prompt_bubble.cc b/chrome/browser/ui/views/permissions/permission_prompt_bubble.cc index 8addff3..886aa57 100644 --- a/chrome/browser/ui/views/permissions/permission_prompt_bubble.cc +++ b/chrome/browser/ui/views/permissions/permission_prompt_bubble.cc
@@ -48,6 +48,7 @@ disallowed_custom_cursors_scope_ = delegate()->GetAssociatedWebContents()->CreateDisallowCustomCursorScope(); + occlusion_observation_.Observe(prompt_bubble->GetWidget()); } void PermissionPromptBubble::CleanUpPromptBubble() { @@ -141,3 +142,10 @@ return static_cast<const PermissionPromptBubbleBaseView*>( prompt_bubble_tracker_.view()); } + +void PermissionPromptBubble::OnOcclusionStateChanged(bool occluded) { + // Disable the prompt if it's occluded by a picture-in-picture window. + if (GetPromptBubble()) { + GetPromptBubble()->GetWidget()->GetContentsView()->SetEnabled(!occluded); + } +}
diff --git a/chrome/browser/ui/views/permissions/permission_prompt_bubble.h b/chrome/browser/ui/views/permissions/permission_prompt_bubble.h index a1bd0b6..278ebaf 100644 --- a/chrome/browser/ui/views/permissions/permission_prompt_bubble.h +++ b/chrome/browser/ui/views/permissions/permission_prompt_bubble.h
@@ -6,6 +6,8 @@ #define CHROME_BROWSER_UI_VIEWS_PERMISSIONS_PERMISSION_PROMPT_BUBBLE_H_ #include "chip_controller.h" +#include "chrome/browser/picture_in_picture/picture_in_picture_occlusion_observer.h" +#include "chrome/browser/picture_in_picture/scoped_picture_in_picture_occlusion_observation.h" #include "chrome/browser/ui/views/permissions/permission_prompt_bubble_base_view.h" #include "chrome/browser/ui/views/permissions/permission_prompt_desktop.h" #include "content/public/browser/web_contents_observer.h" @@ -17,7 +19,8 @@ } class PermissionPromptBubble : public PermissionPromptDesktop, - public views::WidgetObserver { + public views::WidgetObserver, + public PictureInPictureOcclusionObserver { public: PermissionPromptBubble(Browser* browser, content::WebContents* web_contents, @@ -41,6 +44,9 @@ views::Widget* GetPromptBubbleWidgetForTesting() override; + // PictureInPictureOcclusionObserver: + void OnOcclusionStateChanged(bool occluded) override; + private: PermissionPromptBubbleBaseView* GetPromptBubble(); const PermissionPromptBubbleBaseView* GetPromptBubble() const; @@ -55,6 +61,8 @@ base::ScopedClosureRunner disallowed_custom_cursors_scope_; + ScopedPictureInPictureOcclusionObservation occlusion_observation_{this}; + base::WeakPtrFactory<PermissionPromptBubble> weak_factory_{this}; };
diff --git a/chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.cc b/chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.cc index e751df8..3181edc 100644 --- a/chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.cc +++ b/chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.cc
@@ -7,30 +7,17 @@ #include <memory> #include <utility> -#include "base/metrics/histogram_functions.h" -#include "chrome/browser/ui/views/frame/browser_view.h" +#include "chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.h" #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_toolbar_view.h" -#include "chrome/browser/ui/views/side_panel/side_panel_web_ui_view.h" -#include "chrome/browser/ui/webui/side_panel/read_anything/read_anything_untrusted_ui.h" -#include "chrome/common/accessibility/read_anything_constants.h" -#include "chrome/common/webui_url_constants.h" -#include "chrome/grit/generated_resources.h" #include "ui/base/metadata/metadata_impl_macros.h" -#include "ui/gfx/geometry/geometry_export.h" #include "ui/views/background.h" #include "ui/views/controls/separator.h" #include "ui/views/layout/flex_layout.h" -using SidePanelWebUIViewT_ReadAnythingUntrustedUI = - SidePanelWebUIViewT<ReadAnythingUntrustedUI>; -BEGIN_TEMPLATE_METADATA(SidePanelWebUIViewT_ReadAnythingUntrustedUI, - SidePanelWebUIViewT) -END_METADATA - ReadAnythingContainerView::ReadAnythingContainerView( ReadAnythingCoordinator* coordinator, std::unique_ptr<ReadAnythingToolbarView> toolbar, - std::unique_ptr<SidePanelWebUIViewT<ReadAnythingUntrustedUI>> content) + std::unique_ptr<ReadAnythingSidePanelWebView> content) : coordinator_(std::move(coordinator)) { // Create and set a FlexLayout LayoutManager for this view, set background. auto layout = std::make_unique<views::FlexLayout>();
diff --git a/chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.h b/chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.h index 9841c18..89e5c78 100644 --- a/chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.h +++ b/chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.h
@@ -9,13 +9,12 @@ #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_coordinator.h" #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_model.h" -#include "chrome/browser/ui/views/side_panel/side_panel_web_ui_view.h" #include "ui/base/metadata/metadata_header_macros.h" #include "ui/views/controls/separator.h" #include "ui/views/view.h" class ReadAnythingToolbarView; -class ReadAnythingUntrustedUI; +class ReadAnythingSidePanelWebView; /////////////////////////////////////////////////////////////////////////////// // ReadAnythingContainerView @@ -33,7 +32,7 @@ ReadAnythingContainerView( ReadAnythingCoordinator* coordinator, std::unique_ptr<ReadAnythingToolbarView> toolbar, - std::unique_ptr<SidePanelWebUIViewT<ReadAnythingUntrustedUI>> content); + std::unique_ptr<ReadAnythingSidePanelWebView> content); ReadAnythingContainerView(const ReadAnythingContainerView&) = delete; ReadAnythingContainerView& operator=(const ReadAnythingContainerView&) = delete;
diff --git a/chrome/browser/ui/views/side_panel/read_anything/read_anything_coordinator.cc b/chrome/browser/ui/views/side_panel/read_anything/read_anything_coordinator.cc index 8aa8246..e11edc7 100644 --- a/chrome/browser/ui/views/side_panel/read_anything/read_anything_coordinator.cc +++ b/chrome/browser/ui/views/side_panel/read_anything/read_anything_coordinator.cc
@@ -6,7 +6,6 @@ #include <memory> #include <string> -#include <utility> #include <vector> #include "base/functional/bind.h" @@ -22,13 +21,14 @@ #include "chrome/browser/ui/views/frame/browser_view.h" #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.h" #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_controller.h" +#include "chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_controller.h" +#include "chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.h" #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_toolbar_view.h" #include "chrome/browser/ui/views/side_panel/side_panel_coordinator.h" -#include "chrome/browser/ui/views/side_panel/side_panel_entry.h" #include "chrome/browser/ui/views/side_panel/side_panel_registry.h" +#include "chrome/browser/ui/views/side_panel/side_panel_web_ui_view.h" #include "chrome/browser/ui/webui/side_panel/read_anything/read_anything_prefs.h" #include "chrome/browser/ui/webui/side_panel/read_anything/read_anything_untrusted_ui.h" -#include "chrome/common/webui_url_constants.h" #include "chrome/grit/generated_resources.h" #include "components/feature_engagement/public/feature_constants.h" #include "components/language/core/browser/language_model.h" @@ -36,8 +36,6 @@ #include "components/language/core/common/locale_util.h" #include "ui/accessibility/accessibility_features.h" #include "ui/base/l10n/l10n_util.h" -#include "ui/base/metadata/metadata_header_macros.h" -#include "ui/base/models/combobox_model.h" namespace { @@ -55,10 +53,6 @@ } // namespace -using SidePanelWebUIViewT_ReadAnythingUntrustedUI = - SidePanelWebUIViewT<ReadAnythingUntrustedUI>; -DECLARE_TEMPLATE_METADATA(SidePanelWebUIViewT_ReadAnythingUntrustedUI, - SidePanelWebUIViewT); ReadAnythingCoordinator::ReadAnythingCoordinator(Browser* browser) : BrowserUserData<ReadAnythingCoordinator>(*browser), @@ -249,17 +243,7 @@ std::unique_ptr<views::View> ReadAnythingCoordinator::CreateContainerView() { Browser* browser = &GetBrowser(); auto web_view = - std::make_unique<SidePanelWebUIViewT<ReadAnythingUntrustedUI>>( - /* on_show_cb= */ base::RepeatingClosure(), - /* close_cb= */ base::RepeatingClosure(), - /* contents_wrapper= */ - std::make_unique<BubbleContentsWrapperT<ReadAnythingUntrustedUI>>( - /* webui_url= */ GURL( - chrome::kChromeUIUntrustedReadAnythingSidePanelURL), - /* browser_context= */ browser->profile(), - /* task_manager_string_id= */ IDS_READING_MODE_TITLE, - /* webui_resizes_host= */ false, - /* esc_closes_ui= */ false)); + std::make_unique<ReadAnythingSidePanelWebView>(browser->profile()); if (features::IsReadAnythingWebUIToolbarEnabled()) { return std::move(web_view);
diff --git a/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_controller.cc b/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_controller.cc index 51aed5f1..8e0f6ed 100644 --- a/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_controller.cc +++ b/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_controller.cc
@@ -12,6 +12,7 @@ #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_container_view.h" #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_controller.h" #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_coordinator.h" +#include "chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.h" #include "chrome/browser/ui/views/side_panel/read_anything/read_anything_toolbar_view.h" #include "chrome/browser/ui/views/side_panel/side_panel_registry.h" #include "chrome/browser/ui/views/side_panel/side_panel_web_ui_view.h" @@ -84,15 +85,8 @@ std::unique_ptr<views::View> ReadAnythingSidePanelController::CreateContainerView() { - auto web_view = - std::make_unique<SidePanelWebUIViewT<ReadAnythingUntrustedUI>>( - base::RepeatingClosure(), base::RepeatingClosure(), - std::make_unique<BubbleContentsWrapperT<ReadAnythingUntrustedUI>>( - GURL(chrome::kChromeUIUntrustedReadAnythingSidePanelURL), - Profile::FromBrowserContext(web_contents_->GetBrowserContext()), - IDS_READING_MODE_TITLE, - /*webui_resizes_host=*/false, - /*esc_closes_ui=*/false)); + auto web_view = std::make_unique<ReadAnythingSidePanelWebView>( + Profile::FromBrowserContext(web_contents_->GetBrowserContext())); if (features::IsReadAnythingWebUIToolbarEnabled()) { return std::move(web_view);
diff --git a/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_navigation_throttle.cc b/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_navigation_throttle.cc index a480c4c..390c1e86 100644 --- a/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_navigation_throttle.cc +++ b/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_navigation_throttle.cc
@@ -40,7 +40,8 @@ const auto& url = navigation_handle()->GetURL(); // Only cancel the request if a user initiated it. Otherwise when reading mode // opens, it will hit this block and cause a stack overflow. - if (url != chrome::kChromeUIUntrustedReadAnythingSidePanelURL || + if (url.GetWithEmptyPath() != + chrome::kChromeUIUntrustedReadAnythingSidePanelURL || !ui::PageTransitionCoreTypeIs(navigation_handle()->GetPageTransition(), ui::PAGE_TRANSITION_TYPED)) { return content::NavigationThrottle::PROCEED;
diff --git a/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.cc b/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.cc new file mode 100644 index 0000000..9142a956 --- /dev/null +++ b/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.cc
@@ -0,0 +1,40 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.h" +#include "chrome/browser/profiles/profile.h" +#include "chrome/browser/ui/views/side_panel/side_panel_web_ui_view.h" +#include "chrome/common/webui_url_constants.h" +#include "chrome/grit/generated_resources.h" +#include "content/public/browser/context_menu_params.h" +#include "ui/base/metadata/metadata_impl_macros.h" + +using SidePanelWebUIViewT_ReadAnythingUntrustedUI = + SidePanelWebUIViewT<ReadAnythingUntrustedUI>; +BEGIN_TEMPLATE_METADATA(SidePanelWebUIViewT_ReadAnythingUntrustedUI, + SidePanelWebUIViewT); + +END_METADATA + +ReadAnythingSidePanelWebView::ReadAnythingSidePanelWebView(Profile* profile) + : SidePanelWebUIViewT( + base::RepeatingClosure(), + base::RepeatingClosure(), + std::make_unique<BubbleContentsWrapperT<ReadAnythingUntrustedUI>>( + GURL(chrome::kChromeUIUntrustedReadAnythingSidePanelURL), + profile, + IDS_READING_MODE_TITLE, + /*webui_resizes_host=*/false, + /*esc_closes_ui=*/false)) {} + +bool ReadAnythingSidePanelWebView::HandleContextMenu( + content::RenderFrameHost& render_frame_host, + const content::ContextMenuParams& params) { + return false; +} + +ReadAnythingSidePanelWebView::~ReadAnythingSidePanelWebView() = default; + +BEGIN_METADATA(ReadAnythingSidePanelWebView) +END_METADATA
diff --git a/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.h b/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.h new file mode 100644 index 0000000..43b0b4a5 --- /dev/null +++ b/chrome/browser/ui/views/side_panel/read_anything/read_anything_side_panel_web_view.h
@@ -0,0 +1,31 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CHROME_BROWSER_UI_VIEWS_SIDE_PANEL_READ_ANYTHING_READ_ANYTHING_SIDE_PANEL_WEB_VIEW_H_ +#define CHROME_BROWSER_UI_VIEWS_SIDE_PANEL_READ_ANYTHING_READ_ANYTHING_SIDE_PANEL_WEB_VIEW_H_ + +#include "chrome/browser/ui/views/side_panel/side_panel_web_ui_view.h" +#include "chrome/browser/ui/webui/side_panel/read_anything/read_anything_untrusted_ui.h" + +class ReadAnythingSidePanelWebView + : public SidePanelWebUIViewT<ReadAnythingUntrustedUI> { + using SidePanelWebUIViewT_ReadAnythingUntrustedUI = + SidePanelWebUIViewT<ReadAnythingUntrustedUI>; + METADATA_HEADER(ReadAnythingSidePanelWebView, + SidePanelWebUIViewT_ReadAnythingUntrustedUI) + public: + explicit ReadAnythingSidePanelWebView(Profile* profile); + ReadAnythingSidePanelWebView(const ReadAnythingSidePanelWebView&) = delete; + ReadAnythingSidePanelWebView& operator=(const ReadAnythingSidePanelWebView&) = + delete; + ~ReadAnythingSidePanelWebView() override; + + bool HandleContextMenu(content::RenderFrameHost& render_frame_host, + const content::ContextMenuParams& params) override; + + private: + base::WeakPtrFactory<ReadAnythingSidePanelWebView> weak_factory_{this}; +}; + +#endif // CHROME_BROWSER_UI_VIEWS_SIDE_PANEL_READ_ANYTHING_READ_ANYTHING_SIDE_PANEL_WEB_VIEW_H_
diff --git a/chrome/browser/ui/views/side_panel/side_panel_interactive_uitest.cc b/chrome/browser/ui/views/side_panel/side_panel_interactive_uitest.cc index f4068ecf..fa00fba 100644 --- a/chrome/browser/ui/views/side_panel/side_panel_interactive_uitest.cc +++ b/chrome/browser/ui/views/side_panel/side_panel_interactive_uitest.cc
@@ -10,6 +10,7 @@ #include "chrome/browser/ui/browser_commands.h" #include "chrome/browser/ui/browser_element_identifiers.h" #include "chrome/browser/ui/side_panel/side_panel_entry_id.h" +#include "chrome/browser/ui/side_panel/side_panel_entry_key.h" #include "chrome/browser/ui/side_search/side_search_config.h" #include "chrome/browser/ui/toolbar/app_menu_model.h" #include "chrome/browser/ui/toolbar/bookmark_sub_menu_model.h" @@ -29,6 +30,7 @@ #include "chrome/test/interaction/interactive_browser_test.h" #include "chrome/test/interaction/tracked_element_webcontents.h" #include "chrome/test/interaction/webcontents_interaction_test_util.h" +#include "components/reading_list/core/reading_list_entry.h" #include "content/public/test/browser_test.h" #include "testing/gtest/include/gtest/gtest.h" #include "ui/accessibility/accessibility_features.h" @@ -63,6 +65,8 @@ IN_PROC_BROWSER_TEST_F(SidePanelInteractiveTest, SidePanelNotShownOnPwa) { DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kSecondTabElementId); GURL second_tab_url("https://test.com"); + auto* coordinator = + SidePanelUtil::GetSidePanelCoordinatorForBrowser(browser()); RunTestSequence( // Add a second tab to the tab strip @@ -79,22 +83,23 @@ ->GetActiveWebContents() ->GetLastCommittedURL(); }), - second_tab_url)); - - // Register side search entry to second_tab. - content::WebContents* active_contents = - browser()->tab_strip_model()->GetActiveWebContents(); - auto* registry = SidePanelRegistry::Get(active_contents); - registry->Register(std::make_unique<SidePanelEntry>( - SidePanelEntry::Id::kSideSearch, u"testing1", ui::ImageModel(), - base::BindRepeating([]() { return std::make_unique<views::View>(); }))); - - // Toggle side search entry to show on second_tab. - auto* coordinator = - SidePanelUtil::GetSidePanelCoordinatorForBrowser(browser()); - coordinator->Show(SidePanelEntry::Id::kSideSearch); - EXPECT_EQ(coordinator->GetComboboxDisplayedEntryIdForTesting(), - SidePanelEntry::Id::kSideSearch); + second_tab_url), + Do(base::BindLambdaForTesting([=]() { + content::WebContents* active_contents = + browser()->tab_strip_model()->GetActiveWebContents(); + auto* registry = SidePanelRegistry::Get(active_contents); + registry->Register(std::make_unique<SidePanelEntry>( + SidePanelEntry::Id::kCustomizeChrome, u"testing1", ui::ImageModel(), + base::BindRepeating( + []() { return std::make_unique<views::View>(); }))); + coordinator->Show(SidePanelEntry::Id::kCustomizeChrome); + })), + WaitForShow(kSidePanelElementId), FlushEvents(), + CheckResult(base::BindLambdaForTesting([coordinator]() { + return coordinator->IsSidePanelEntryShowing( + SidePanelEntryKey(SidePanelEntryId::kCustomizeChrome)); + }), + true)); // Install an app using second_tab_url. auto app_id = web_app::test::InstallDummyWebApp(browser()->profile(), @@ -113,6 +118,11 @@ } IN_PROC_BROWSER_TEST_F(SidePanelInteractiveTest, ToggleSidePanelVisibility) { + if (base::FeatureList::IsEnabled(features::kSidePanelPinning)) { + GTEST_SKIP() + << "Default sidepanel button is not present with pinning feature."; + } + RunTestSequence( // Ensure the side panel isn't open EnsureNotPresent(kSidePanelElementId), @@ -132,6 +142,11 @@ IN_PROC_BROWSER_TEST_F(SidePanelInteractiveTest, SwitchBetweenDifferentEntries) { + if (base::FeatureList::IsEnabled(features::kSidePanelPinning)) { + GTEST_SKIP() + << "Default sidepanel button is not present with pinning feature."; + } + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kBookmarksWebContentsId); DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kReadLaterWebContentsId); @@ -160,6 +175,11 @@ IN_PROC_BROWSER_TEST_F(SidePanelInteractiveTest, StaysOpenOnTabSwitchWithActiveGlobalEntry) { + if (base::FeatureList::IsEnabled(features::kSidePanelPinning)) { + GTEST_SKIP() + << "Default sidepanel button is not present with pinning feature."; + } + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kSecondTabElementId); RunTestSequence( @@ -185,6 +205,14 @@ IN_PROC_BROWSER_TEST_F(SidePanelInteractiveTest, ReopensToLastActiveGlobalEntry) { + // This test does not make sense with pinned feature the default toolbar + // sidepanel button is not present to show the last active global entry. + // A particular sidepanel has to be opened. + if (base::FeatureList::IsEnabled(features::kSidePanelPinning)) { + GTEST_SKIP() + << "Default sidepanel button is not present with pinning feature."; + } + RunTestSequence( // Ensure the side panel isn't open EnsureNotPresent(kSidePanelElementId), @@ -281,6 +309,12 @@ is_active)); } + auto ShowSidePanelForKey(SidePanelEntryKey key) { + return Do(base::BindLambdaForTesting([=]() { + SidePanelUtil::GetSidePanelCoordinatorForBrowser(browser())->Show(key); + })); + } + private: base::test::ScopedFeatureList scoped_feature_list_; }; @@ -401,3 +435,84 @@ // Verify the bookmarks pinned toolbar button is not highlighted. CheckPinnedToolbarActionsContainerChildInkDropState(0, false)); } + +IN_PROC_BROWSER_TEST_F(PinnedSidePanelInteractiveTest, + ToggleSidePanelVisibility) { + constexpr char kBookmarksButton[] = "bookmarks_button"; + RunTestSequence( + // Ensure the side panel isn't open + EnsureNotPresent(kSidePanelElementId), + // Open bookmarks sidepanel + OpenBookmarksSidePanel(), WaitForShow(kSidePanelElementId), FlushEvents(), + WaitForShow(kPinnedToolbarActionsContainerElementId), FlushEvents(), + // Pin the button + CheckPinButtonToggleState(false), + PressButton(kSidePanelPinButtonElementId), + CheckActionPinnedToToolbar(kActionSidePanelShowBookmarks, true), + EnsurePresent(kPinnedToolbarActionsContainerElementId), + NameChildViewByType< + PinnedToolbarActionsContainer::PinnedActionToolbarButton>( + kPinnedToolbarActionsContainerElementId, kBookmarksButton), + WaitForShow(kBookmarksButton), FlushEvents(), + // Toggle side panel + PressButton(kBookmarksButton), WaitForHide(kSidePanelElementId)); +} + +IN_PROC_BROWSER_TEST_F(PinnedSidePanelInteractiveTest, + SwitchBetweenDifferentEntries) { + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kBookmarksWebContentsId); + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kReadLaterWebContentsId); + auto* coordinator = + SidePanelUtil::GetSidePanelCoordinatorForBrowser(browser()); + + RunTestSequence( + // Ensure the side panel isn't open + EnsureNotPresent(kSidePanelElementId), + // Click the toolbar button to open the side panel + OpenBookmarksSidePanel(), WaitForShow(kSidePanelElementId), FlushEvents(), + InstrumentNonTabWebView(kBookmarksWebContentsId, + kBookmarkSidePanelWebViewElementId), + FlushEvents(), + CheckResult(base::BindLambdaForTesting([coordinator]() { + return coordinator->IsSidePanelEntryShowing( + SidePanelEntryKey(SidePanelEntryId::kBookmarks)); + }), + true), + // Switch to the reading list entry. + ShowSidePanelForKey(SidePanelEntryKey(SidePanelEntry::Id::kReadingList)), + InstrumentNonTabWebView(kReadLaterWebContentsId, + kReadLaterSidePanelWebViewElementId), + FlushEvents(), + CheckResult(base::BindLambdaForTesting([coordinator]() { + return coordinator->IsSidePanelEntryShowing( + SidePanelEntryKey(SidePanelEntryId::kReadingList)); + }), + true), + // Click on the close button to dismiss the side panel + PressButton(kSidePanelCloseButtonElementId), + WaitForHide(kSidePanelElementId)); +} + +IN_PROC_BROWSER_TEST_F(PinnedSidePanelInteractiveTest, + StaysOpenOnTabSwitchWithActiveGlobalEntry) { + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kSecondTabElementId); + + RunTestSequence( + // Add a second tab to the tab strip + AddInstrumentedTab(kSecondTabElementId, GURL(url::kAboutBlankURL)), + CheckResult(base::BindLambdaForTesting([this]() { + return browser()->tab_strip_model()->active_index(); + }), + testing::Eq(1)), + // Ensure the side panel isn't open + EnsureNotPresent(kSidePanelElementId), + // Click the toolbar button to open the side panel + OpenBookmarksSidePanel(), WaitForShow(kSidePanelElementId), FlushEvents(), + // Switch to the first tab again with the side panel open + SelectTab(kTabStripElementId, 0), + // Ensure the side panel is still visible + CheckViewProperty(kSidePanelElementId, &views::View::GetVisible, true), + // Click on the close button to dismiss the side panel + PressButton(kSidePanelCloseButtonElementId), + WaitForHide(kSidePanelElementId)); +}
diff --git a/chrome/browser/ui/views/web_apps/web_app_integration_test_driver.cc b/chrome/browser/ui/views/web_apps/web_app_integration_test_driver.cc index 9b110ff..f618f50 100644 --- a/chrome/browser/ui/views/web_apps/web_app_integration_test_driver.cc +++ b/chrome/browser/ui/views/web_apps/web_app_integration_test_driver.cc
@@ -4575,6 +4575,9 @@ #if BUILDFLAG(IS_CHROMEOS) // TODO(crbug.com/1357905): Update test driver to work with new UI. disabled_features.push_back(apps::features::kLinkCapturingUiUpdate); +#else + // TOOD(b/313492499): Update test driver to work with new intent picker UI. + disabled_features.push_back(features::kDesktopPWAsLinkCapturing); #endif // BUILDFLAG(IS_CHROMEOS) scoped_feature_list_.InitWithFeatures(enabled_features, disabled_features); }
diff --git a/chrome/browser/ui/web_applications/pwa_mixed_content_browsertest.cc b/chrome/browser/ui/web_applications/pwa_mixed_content_browsertest.cc index 29762fd..8d51f837 100644 --- a/chrome/browser/ui/web_applications/pwa_mixed_content_browsertest.cc +++ b/chrome/browser/ui/web_applications/pwa_mixed_content_browsertest.cc
@@ -170,7 +170,7 @@ const GURL app_url = GetMixedContentAppURL(); const webapps::AppId app_id = InstallPWA(app_url); - NavigateToURLAndWait(browser(), GetMixedContentAppURL()); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), GetMixedContentAppURL())); content::WebContents* tab_contents = browser()->tab_strip_model()->GetActiveWebContents(); ASSERT_EQ(tab_contents->GetLastCommittedURL(), GetMixedContentAppURL()); @@ -220,7 +220,7 @@ const GURL app_url = GetSecureIFrameAppURL(); const webapps::AppId app_id = InstallPWA(app_url); - NavigateToURLAndWait(browser(), app_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), app_url)); CheckMixedContentFailedToLoad(browser()); Browser* const app_browser = ReparentWebContentsIntoAppBrowser(
diff --git a/chrome/browser/ui/web_applications/test/web_app_browsertest_util.cc b/chrome/browser/ui/web_applications/test/web_app_browsertest_util.cc index f3651fb9..3f249c2 100644 --- a/chrome/browser/ui/web_applications/test/web_app_browsertest_util.cc +++ b/chrome/browser/ui/web_applications/test/web_app_browsertest_util.cc
@@ -94,7 +94,7 @@ } // namespace webapps::AppId InstallWebAppFromPage(Browser* browser, const GURL& app_url) { - NavigateToURLAndWait(browser, app_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser, app_url)); webapps::AppId app_id; base::RunLoop run_loop;
diff --git a/chrome/browser/ui/web_applications/web_app_browsertest.cc b/chrome/browser/ui/web_applications/web_app_browsertest.cc index 4dcd1cef..96a661e1 100644 --- a/chrome/browser/ui/web_applications/web_app_browsertest.cc +++ b/chrome/browser/ui/web_applications/web_app_browsertest.cc
@@ -1373,7 +1373,7 @@ const GURL app_url = GetSecureAppURL(); const webapps::AppId app_id = InstallPWA(app_url); - NavigateToURLAndWait(browser(), app_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), app_url)); content::WebContents* tab_contents = browser()->tab_strip_model()->GetActiveWebContents(); ASSERT_EQ(tab_contents->GetLastCommittedURL(), app_url); @@ -1390,10 +1390,10 @@ std::unique_ptr<OsIntegrationTestOverrideImpl::BlockingRegistration> registration = OsIntegrationTestOverrideImpl::OverrideForTesting(); - NavigateToURLAndWait( + EXPECT_TRUE(ui_test_utils::NavigateToURL( browser(), https_server()->GetURL( - "/banners/manifest_test_page.html?manifest=manifest_one_icon.json")); + "/banners/manifest_test_page.html?manifest=manifest_one_icon.json"))); // Wait for OS hooks and installation to complete and the app to launch. base::RunLoop run_loop_install; @@ -1699,7 +1699,7 @@ IN_PROC_BROWSER_TEST_F(WebAppBrowserTest, ReparentLastBrowserTab) { const GURL app_url = GetSecureAppURL(); const webapps::AppId app_id = InstallPWA(app_url); - NavigateToURLAndWait(browser(), app_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), app_url)); Browser* const app_browser = ReparentWebAppForActiveTab(browser()); ASSERT_EQ(app_browser->app_controller()->app_id(), app_id); @@ -1824,7 +1824,7 @@ const webapps::AppId app_id = InstallWebApp(std::move(web_app_info)); base::HistogramTester tester; - NavigateToURLAndWait(browser(), app_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), app_url)); content::WebContents* tab_contents = browser()->tab_strip_model()->GetActiveWebContents(); ASSERT_EQ(tab_contents->GetLastCommittedURL(), app_url); @@ -2533,7 +2533,7 @@ const GURL app_url = GetSecureAppURL(); InstallPWA(app_url); - NavigateToURLAndWait(browser(), app_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), app_url)); content::WebContents* tab_contents = browser()->tab_strip_model()->GetActiveWebContents(); ASSERT_EQ(tab_contents->GetLastCommittedURL(), app_url);
diff --git a/chrome/browser/ui/web_applications/web_app_controller_browsertest.cc b/chrome/browser/ui/web_applications/web_app_controller_browsertest.cc index ddaca20..9825e215 100644 --- a/chrome/browser/ui/web_applications/web_app_controller_browsertest.cc +++ b/chrome/browser/ui/web_applications/web_app_controller_browsertest.cc
@@ -141,7 +141,7 @@ EXPECT_TRUE(new_contents); WaitForLoadStop(new_contents); - EXPECT_EQ(url, new_contents->GetLastCommittedURL()); + EXPECT_EQ(url, contents->GetController().GetLastCommittedEntry()->GetURL()); EXPECT_EQ( content::PAGE_TYPE_NORMAL, new_contents->GetController().GetLastCommittedEntry()->GetPageType()); @@ -167,7 +167,7 @@ const GURL& url) { auto* manager = webapps::TestAppBannerManagerDesktop::FromWebContents( browser->tab_strip_model()->GetActiveWebContents()); - NavigateToURLAndWait(browser, url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser, url)); return manager->WaitForInstallableCheck(); }
diff --git a/chrome/browser/ui/web_applications/web_app_dark_mode_browsertest.cc b/chrome/browser/ui/web_applications/web_app_dark_mode_browsertest.cc index c477002e..89fd9e1 100644 --- a/chrome/browser/ui/web_applications/web_app_dark_mode_browsertest.cc +++ b/chrome/browser/ui/web_applications/web_app_dark_mode_browsertest.cc
@@ -12,6 +12,7 @@ #include "chrome/browser/web_applications/test/web_app_install_test_utils.h" #include "chrome/browser/web_applications/web_app.h" #include "chrome/browser/web_applications/web_app_provider.h" +#include "chrome/test/base/ui_test_utils.h" #include "components/embedder_support/switches.h" #include "components/page_load_metrics/browser/page_load_metrics_test_waiter.h" #include "content/public/test/browser_test.h" @@ -240,7 +241,7 @@ UpdateAwaiter update_awaiter(provider.install_manager()); serve_token = false; - NavigateToURLAndWait(browser(), GURL(kTestWebAppUrl)); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), GURL(kTestWebAppUrl))); update_awaiter.AwaitUpdate(); }
diff --git a/chrome/browser/ui/web_applications/web_app_launch_handler_browsertest.cc b/chrome/browser/ui/web_applications/web_app_launch_handler_browsertest.cc index 416dde0..b4533eb9 100644 --- a/chrome/browser/ui/web_applications/web_app_launch_handler_browsertest.cc +++ b/chrome/browser/ui/web_applications/web_app_launch_handler_browsertest.cc
@@ -205,7 +205,7 @@ // start_url again. { GURL alt_url = embedded_test_server()->GetURL("/web_apps/basic.html"); - NavigateToURLAndWait(app_browser, alt_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(app_browser, alt_url)); EXPECT_EQ(app_web_contents->GetLastCommittedURL(), alt_url); Browser* app_browser_2 = LaunchWebAppBrowserAndWait(app_id); @@ -222,7 +222,7 @@ chrome::NewTab(browser()); EXPECT_EQ(browser()->tab_strip_model()->count(), 2); - NavigateToURLAndWait(browser(), start_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), start_url)); ReparentWebAppForActiveTab(browser()); EXPECT_EQ(browser()->tab_strip_model()->count(), 1); @@ -642,7 +642,7 @@ UpdateAwaiter update_awaiter(provider.install_manager()); serve_token = false; - NavigateToURLAndWait(browser(), GURL(kTestWebAppUrl)); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), GURL(kTestWebAppUrl))); update_awaiter.AwaitUpdate(); }
diff --git a/chrome/browser/ui/webui/ash/settings/pages/a11y/DEPS b/chrome/browser/ui/webui/ash/settings/pages/a11y/DEPS new file mode 100644 index 0000000..02f2c7f --- /dev/null +++ b/chrome/browser/ui/webui/ash/settings/pages/a11y/DEPS
@@ -0,0 +1,5 @@ +specific_include_rules = { + 'switch_access_handler.cc': [ + "+ash/accessibility/accessibility_controller_impl.h", + ] +} \ No newline at end of file
diff --git a/chrome/browser/ui/webui/ash/settings/pages/a11y/switch_access_handler.cc b/chrome/browser/ui/webui/ash/settings/pages/a11y/switch_access_handler.cc index bdcdfc29..4c58b10 100644 --- a/chrome/browser/ui/webui/ash/settings/pages/a11y/switch_access_handler.cc +++ b/chrome/browser/ui/webui/ash/settings/pages/a11y/switch_access_handler.cc
@@ -6,9 +6,9 @@ #include <memory> +#include "ash/accessibility/accessibility_controller_impl.h" #include "ash/constants/ash_constants.h" #include "ash/constants/ash_pref_names.h" -#include "ash/public/cpp/accessibility_controller.h" #include "base/functional/bind.h" #include "base/no_destructor.h" #include "base/values.h"
diff --git a/chrome/browser/ui/webui/ash/settings/pages/device/device_section.cc b/chrome/browser/ui/webui/ash/settings/pages/device/device_section.cc index fc2c009..3b0e4279 100644 --- a/chrome/browser/ui/webui/ash/settings/pages/device/device_section.cc +++ b/chrome/browser/ui/webui/ash/settings/pages/device/device_section.cc
@@ -1756,6 +1756,8 @@ IDS_SETTINGS_CUSTOMIZE_BUTTONS_RENAMING_DIALOG_INPUT_LABEL}, {"buttonRemappingDialogCancelLabel", IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_CANCEL}, + {"buttonRemappingDialogChangeLabel", + IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_CHANGE}, {"buttonRemappingDialogDescription", IDS_SETTINGS_CUSTOMIZE_BUTTONS_DIALOG_DESCRIPTION}, {"buttonRemappingDialogSaveLabel",
diff --git a/chrome/browser/ui/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_handler_unittest.cc b/chrome/browser/ui/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_handler_unittest.cc index 6ea53ad..2df39e6 100644 --- a/chrome/browser/ui/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_handler_unittest.cc +++ b/chrome/browser/ui/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_handler_unittest.cc
@@ -110,7 +110,7 @@ base::BindRepeating([](content::BrowserContext* context) -> std::unique_ptr<KeyedService> { return std::make_unique< - testing::NiceMock<MockOptimizationGuideKeyedService>>(context); + testing::NiceMock<MockOptimizationGuideKeyedService>>(); })); profile_builder.SetSharedURLLoaderFactory(url_loader_factory); auto profile = profile_builder.Build();
diff --git a/chrome/browser/ui/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_interactive_uitest.cc b/chrome/browser/ui/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_interactive_uitest.cc index 493a093..38d4f37 100644 --- a/chrome/browser/ui/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_interactive_uitest.cc +++ b/chrome/browser/ui/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_interactive_uitest.cc
@@ -194,7 +194,7 @@ context, base::BindRepeating([](content::BrowserContext* context) -> std::unique_ptr<KeyedService> { return std::make_unique< - testing::NiceMock<MockOptimizationGuideKeyedService>>(context); + testing::NiceMock<MockOptimizationGuideKeyedService>>(); })); }
diff --git a/chrome/browser/v8_compile_hints/v8_compile_hints_tab_helper_unittest.cc b/chrome/browser/v8_compile_hints/v8_compile_hints_tab_helper_unittest.cc index 3b84635..f10b316 100644 --- a/chrome/browser/v8_compile_hints/v8_compile_hints_tab_helper_unittest.cc +++ b/chrome/browser/v8_compile_hints/v8_compile_hints_tab_helper_unittest.cc
@@ -58,7 +58,7 @@ base::BindRepeating([](content::BrowserContext* context) -> std::unique_ptr<KeyedService> { return std::make_unique< - NiceMock<MockOptimizationGuideKeyedService>>(context); + NiceMock<MockOptimizationGuideKeyedService>>(); }))); V8CompileHintsTabHelper::MaybeCreateForWebContents(web_contents()); tab_helper_ = V8CompileHintsTabHelper::FromWebContents(web_contents());
diff --git a/chrome/browser/web_applications/commands/compute_app_size_command_browsertest.cc b/chrome/browser/web_applications/commands/compute_app_size_command_browsertest.cc index 8acf952..3f5463da 100644 --- a/chrome/browser/web_applications/commands/compute_app_size_command_browsertest.cc +++ b/chrome/browser/web_applications/commands/compute_app_size_command_browsertest.cc
@@ -2,6 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. +#include "base/test/run_until.h" #include "base/test/test_future.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/web_applications/test/web_app_browsertest_util.h" @@ -9,6 +10,7 @@ #include "chrome/browser/web_applications/commands/compute_app_size_command.h" #include "chrome/browser/web_applications/web_app_command_scheduler.h" #include "chrome/browser/web_applications/web_app_provider.h" +#include "chrome/test/base/ui_test_utils.h" #include "content/public/test/browser_test.h" #include "testing/gtest/include/gtest/gtest.h" #include "url/gurl.h" @@ -22,7 +24,7 @@ GURL app_url = embedded_test_server()->GetURL("/web_apps/basic.html"); webapps::AppId app_id = InstallWebAppFromPage(browser(), app_url); - NavigateToURLAndWait(browser(), app_url); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), app_url)); const char* script = R"( localStorage.setItem('data', 'data'.repeat(5000)); @@ -38,16 +40,13 @@ // renderer process. As updates to quota manager usage occurs on a different // sequence to this procress, it requires multiple events. Due to all of this, // we are resorting to polling for non-zero values. - - while (true) { - base::test::TestFuture<absl::optional<ComputeAppSizeCommand::Size>> - app_size; - provider().scheduler().ComputeAppSize(app_id, app_size.GetCallback()); - if (app_size.Get().value().app_size_in_bytes != 0u && - app_size.Get().value().data_size_in_bytes != 0u) { - break; - } - } + base::test::TestFuture<absl::optional<ComputeAppSizeCommand::Size>> + app_size_future; + provider().scheduler().ComputeAppSize(app_id, app_size_future.GetCallback()); + EXPECT_TRUE(base::test::RunUntil([&]() { + return app_size_future.Get().value().app_size_in_bytes != 0u && + app_size_future.Get().value().data_size_in_bytes != 0u; + })); } } // namespace web_app
diff --git a/chrome/browser/web_applications/web_app_scope_extensions_browsertest.cc b/chrome/browser/web_applications/web_app_scope_extensions_browsertest.cc index a8f4c089..3a626a5 100644 --- a/chrome/browser/web_applications/web_app_scope_extensions_browsertest.cc +++ b/chrome/browser/web_applications/web_app_scope_extensions_browsertest.cc
@@ -472,7 +472,7 @@ { UpdateAwaiter update_awaiter(provider.install_manager()); serve_token = false; - NavigateToURLAndWait(browser(), GURL(kTestWebAppUrl)); + EXPECT_TRUE(ui_test_utils::NavigateToURL(browser(), GURL(kTestWebAppUrl))); update_awaiter.AwaitUpdate(); }
diff --git a/chrome/build/android-arm32.pgo.txt b/chrome/build/android-arm32.pgo.txt index ecf7627..4c212fc 100644 --- a/chrome/build/android-arm32.pgo.txt +++ b/chrome/build/android-arm32.pgo.txt
@@ -1 +1 @@ -chrome-android32-main-1702382390-aedc3b176118e492520a9cfe7aad8b29e4f1be22.profdata +chrome-android32-main-1702403939-f8050953af8eace9d59c81c55793f0e2edf1337d.profdata
diff --git a/chrome/build/android-arm64.pgo.txt b/chrome/build/android-arm64.pgo.txt index ee5fedac..9992beb5 100644 --- a/chrome/build/android-arm64.pgo.txt +++ b/chrome/build/android-arm64.pgo.txt
@@ -1 +1 @@ -chrome-android64-main-1702382390-8adedea8df7860f03fb7285696c7f874428ba41d.profdata +chrome-android64-main-1702403939-b69e446c9cbd1b1c857bd308ec679d1fbd9283b3.profdata
diff --git a/chrome/common/pref_names.h b/chrome/common/pref_names.h index 47c6c15..4bddbc9 100644 --- a/chrome/common/pref_names.h +++ b/chrome/common/pref_names.h
@@ -1528,11 +1528,9 @@ inline constexpr char kImportDialogSearchEngine[] = "import_dialog_search_engine"; -#if BUILDFLAG(IS_CHROMEOS) // Boolean controlling whether native client is force allowed by policy. inline constexpr char kNativeClientForceAllowed[] = "native_client_force_allowed"; -#endif // BUILDFLAG(IS_CHROMEOS) // Profile avatar and name inline constexpr char kProfileAvatarIndex[] = "profile.avatar_index";
diff --git a/chrome/renderer/accessibility/read_anything_app_controller_browsertest.cc b/chrome/renderer/accessibility/read_anything_app_controller_browsertest.cc index d89426f..f0243d2 100644 --- a/chrome/renderer/accessibility/read_anything_app_controller_browsertest.cc +++ b/chrome/renderer/accessibility/read_anything_app_controller_browsertest.cc
@@ -118,13 +118,21 @@ // Create simple AXTreeUpdate with a root node and 3 children. ui::AXTreeUpdate snapshot; - snapshot.root_id = 1; - snapshot.nodes.resize(4); - snapshot.nodes[0].id = 1; - snapshot.nodes[0].child_ids = {2, 3, 4}; - snapshot.nodes[1].id = 2; - snapshot.nodes[2].id = 3; - snapshot.nodes[3].id = 4; + ui::AXNodeData root; + root.id = 1; + + ui::AXNodeData child1; + child1.id = 2; + + ui::AXNodeData child2; + child2.id = 3; + + ui::AXNodeData child3; + child3.id = 4; + + root.child_ids = {child1.id, child2.id, child3.id}; + snapshot.root_id = root.id; + snapshot.nodes = {root, child1, child2, child3}; SetUpdateTreeID(&snapshot); // Send the snapshot to the controller and set its tree ID to be the active @@ -149,17 +157,19 @@ // Send update for main web content with child tree (pdf web contents). ui::AXTreeUpdate main_web_contents_update; SetUpdateTreeID(&main_web_contents_update); - main_web_contents_update.nodes.resize(1); - main_web_contents_update.nodes[0].id = 1; - main_web_contents_update.nodes[0].AddChildTreeId(pdf_web_contents_tree_id); + ui::AXNodeData node; + node.id = 1; + node.AddChildTreeId(pdf_web_contents_tree_id); + main_web_contents_update.nodes = {node}; AccessibilityEventReceived({main_web_contents_update}); // Send update for pdf web contents with child tree (iframe). ui::AXTreeUpdate pdf_web_contents_update; - pdf_web_contents_update.nodes.resize(1); - pdf_web_contents_update.root_id = 1; - pdf_web_contents_update.nodes[0].id = 1; - pdf_web_contents_update.nodes[0].AddChildTreeId(pdf_iframe_tree_id); + ui::AXNodeData pdfNode; + pdfNode.id = 1; + pdfNode.AddChildTreeId(pdf_iframe_tree_id); + pdf_web_contents_update.nodes = {pdfNode}; + pdf_web_contents_update.root_id = pdfNode.id; SetUpdateTreeID(&pdf_web_contents_update, pdf_web_contents_tree_id); AccessibilityEventReceived({pdf_web_contents_update}); @@ -399,9 +409,10 @@ TEST_F(ReadAnythingAppControllerTest, GetChildren_NoSelectionOrContentNodes) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(1); - update.nodes[0].id = 3; - update.nodes[0].role = ax::mojom::Role::kNone; + ui::AXNodeData node; + node.id = 3; + node.role = ax::mojom::Role::kNone; + update.nodes = {node}; AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(0u, GetChildren(1).size()); @@ -413,9 +424,10 @@ TEST_F(ReadAnythingAppControllerTest, GetChildren_WithContentNodes) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(1); - update.nodes[0].id = 3; - update.nodes[0].role = ax::mojom::Role::kNone; + ui::AXNodeData node; + node.id = 3; + node.role = ax::mojom::Role::kNone; + update.nodes = {node}; AccessibilityEventReceived({update}); OnAXTreeDistilled({1, 2, 3, 4}); EXPECT_EQ(2u, GetChildren(1).size()); @@ -479,14 +491,19 @@ std::string ul = "ul"; ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, - span); - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, h1); - update.nodes[2].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, ul); + ui::AXNodeData spanNode; + spanNode.id = 2; + spanNode.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, span); + + ui::AXNodeData h1Node; + h1Node.id = 3; + h1Node.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, h1); + + ui::AXNodeData ulNode; + ulNode.id = 4; + ulNode.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, ul); + update.nodes = {spanNode, h1Node, ulNode}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(span, GetHtmlTag(2)); @@ -501,16 +518,21 @@ std::string div = "div"; ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, - span); - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, h1); - update.nodes[1].role = ax::mojom::Role::kTextField; - update.nodes[2].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, ul); - update.nodes[2].role = ax::mojom::Role::kTextFieldWithComboBox; + ui::AXNodeData spanNode; + spanNode.id = 2; + spanNode.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, span); + + ui::AXNodeData h1Node; + h1Node.id = 3; + h1Node.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, h1); + h1Node.role = ax::mojom::Role::kTextField; + + ui::AXNodeData ulNode; + ulNode.id = 4; + ulNode.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, ul); + ulNode.role = ax::mojom::Role::kTextFieldWithComboBox; + update.nodes = {spanNode, h1Node, ulNode}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(span, GetHtmlTag(2)); @@ -524,12 +546,16 @@ ui::AXTreeUpdate update; ui::AXTreeID id_1 = ui::AXTreeID::CreateNewAXTreeID(); SetUpdateTreeID(&update, id_1); - update.root_id = 1; - update.nodes.resize(2); - update.nodes[0].id = 1; - update.nodes[0].child_ids = {2}; - update.nodes[1].id = 2; - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, svg); + ui::AXNodeData node; + node.id = 2; + node.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, svg); + + ui::AXNodeData root; + root.id = 1; + root.child_ids = {node.id}; + update.nodes = {root, node}; + update.root_id = root.id; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); OnActiveAXTreeIDChanged( @@ -547,16 +573,21 @@ ui::AXTreeUpdate update; ui::AXTreeID id_1 = ui::AXTreeID::CreateNewAXTreeID(); SetUpdateTreeID(&update, id_1); - update.root_id = 1; - update.nodes.resize(3); - update.nodes[0].id = 1; - update.nodes[0].child_ids = {2, 3}; - update.nodes[1].id = 2; - update.nodes[2].id = 3; - update.nodes[0].role = ax::mojom::Role::kParagraph; - update.nodes[1].role = ax::mojom::Role::kParagraph; - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, g); - update.nodes[2].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, g); + ui::AXNodeData paragraphNode; + paragraphNode.id = 2; + paragraphNode.role = ax::mojom::Role::kParagraph; + paragraphNode.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, g); + + ui::AXNodeData svgNode; + svgNode.id = 3; + svgNode.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, g); + + ui::AXNodeData root; + root.role = ax::mojom::Role::kParagraph; + root.id = 1; + root.child_ids = {paragraphNode.id, svgNode.id}; + update.root_id = root.id; + update.nodes = {root, paragraphNode, svgNode}; AccessibilityEventReceived({update}); OnAXTreeDistilled({}); OnActiveAXTreeIDChanged( @@ -575,12 +606,17 @@ std::string div = "div"; ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[1].role = ax::mojom::Role::kHeading; - update.nodes[1].html_attributes.emplace_back("aria-level", "3"); + ui::AXNodeData node1; + node1.id = 2; + + ui::AXNodeData node2; + node2.id = 3; + node2.role = ax::mojom::Role::kHeading; + node2.html_attributes.emplace_back("aria-level", "3"); + + ui::AXNodeData node3; + node3.id = 4; + update.nodes = {node1, node2, node3}; AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(h3, GetHtmlTag(3)); @@ -592,17 +628,20 @@ // Send pdf iframe update with html tags to test. ui::AXTreeUpdate update; SetUpdateTreeID(&update, pdf_iframe_tree_id); - update.nodes.resize(3); - update.root_id = 1; - update.nodes[0].id = 1; - update.nodes[0].child_ids = {2, 3}; - update.nodes[1].id = 2; - update.nodes[2].id = 3; - update.nodes[0].role = ax::mojom::Role::kPdfRoot; - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, - "h1"); - update.nodes[2].role = ax::mojom::Role::kHeading; - update.nodes[2].html_attributes.emplace_back("aria-level", "2"); + ui::AXNodeData node1; + node1.id = 2; + node1.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, "h1"); + ui::AXNodeData node2; + node2.id = 3; + node2.role = ax::mojom::Role::kHeading; + node2.html_attributes.emplace_back("aria-level", "2"); + + ui::AXNodeData root; + root.id = 1; + root.child_ids = {node1.id, node2.id}; + root.role = ax::mojom::Role::kPdfRoot; + update.root_id = root.id; + update.nodes = {root, node1, node2}; AccessibilityEventReceived({update}); OnAXTreeDistilled({}); @@ -620,28 +659,34 @@ // paragraph. ui::AXTreeUpdate update; SetUpdateTreeID(&update, pdf_iframe_tree_id); - update.nodes.resize(5); - update.root_id = 1; - update.nodes[0].id = 1; - update.nodes[0].child_ids = {2, 3, 4, 5}; - update.nodes[1].id = 2; - update.nodes[2].id = 3; - update.nodes[3].id = 4; - update.nodes[4].id = 5; - update.nodes[0].role = ax::mojom::Role::kPdfRoot; - update.nodes[1].role = ax::mojom::Role::kHeading; - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, - "h1"); - update.nodes[2].role = ax::mojom::Role::kHeading; - update.nodes[2].AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, - "h1"); - update.nodes[3].role = ax::mojom::Role::kLink; - update.nodes[4].role = ax::mojom::Role::kHeading; - update.nodes[4].html_attributes.emplace_back("aria-level", "1"); - update.nodes[4].SetNameChecked( + ui::AXNodeData headingNode1; + headingNode1.id = 2; + headingNode1.role = ax::mojom::Role::kHeading; + headingNode1.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, "h1"); + ui::AXNodeData headingNode2; + headingNode2.id = 3; + headingNode2.role = ax::mojom::Role::kHeading; + headingNode2.AddStringAttribute(ax::mojom::StringAttribute::kHtmlTag, "h1"); + + ui::AXNodeData linkNode; + linkNode.id = 4; + linkNode.role = ax::mojom::Role::kLink; + + ui::AXNodeData ariaNode; + ariaNode.id = 5; + ariaNode.role = ax::mojom::Role::kHeading; + ariaNode.html_attributes.emplace_back("aria-level", "1"); + ariaNode.SetNameChecked( "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod " "tempor incididunt ut labore et dolore magna aliqua."); - update.nodes[4].SetNameFrom(ax::mojom::NameFrom::kContents); + ariaNode.SetNameFrom(ax::mojom::NameFrom::kContents); + + ui::AXNodeData root; + root.id = 1; + root.child_ids = {headingNode1.id, headingNode2.id, linkNode.id, ariaNode.id}; + root.role = ax::mojom::Role::kPdfRoot; + update.root_id = root.id; + update.nodes = {root, headingNode1, headingNode2, linkNode, ariaNode}; AccessibilityEventReceived({update}); @@ -659,15 +704,18 @@ // Send pdf iframe update with html tags to test. ui::AXTreeUpdate update; SetUpdateTreeID(&update, pdf_iframe_tree_id); - update.nodes.resize(2); + ui::AXNodeData node; + node.id = 2; + node.role = ax::mojom::Role::kContentInfo; + node.SetNameChecked(string_constants::kPDFPageEnd); + node.SetNameFrom(ax::mojom::NameFrom::kContents); + + ui::AXNodeData root; + root.id = 1; + root.child_ids = {node.id}; + root.role = ax::mojom::Role::kPdfRoot; update.root_id = 1; - update.nodes[0].id = 1; - update.nodes[0].child_ids = {2}; - update.nodes[1].id = 2; - update.nodes[0].role = ax::mojom::Role::kPdfRoot; - update.nodes[1].role = ax::mojom::Role::kContentInfo; - update.nodes[1].SetNameChecked(string_constants::kPDFPageEnd); - update.nodes[1].SetNameFrom(ax::mojom::NameFrom::kContents); + update.nodes = {root, node}; AccessibilityEventReceived({update}); OnAXTreeDistilled({}); @@ -680,16 +728,21 @@ std::string more_text_content = " world"; ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[0].SetNameChecked(text_content); - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[1].SetNameExplicitlyEmpty(); - update.nodes[2].role = ax::mojom::Role::kStaticText; - update.nodes[2].SetNameChecked(more_text_content); + ui::AXNodeData node1; + node1.id = 2; + node1.role = ax::mojom::Role::kStaticText; + node1.SetNameChecked(text_content); + + ui::AXNodeData node2; + node2.id = 3; + node2.role = ax::mojom::Role::kStaticText; + node2.SetNameExplicitlyEmpty(); + + ui::AXNodeData node3; + node3.id = 4; + node3.role = ax::mojom::Role::kStaticText; + node3.SetNameChecked(more_text_content); + update.nodes = {node1, node2, node3}; AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ("Hello world", GetTextContent(1)); @@ -704,16 +757,22 @@ std::string text_content_3 = " friend"; ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[0].SetNameChecked(text_content_1); - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[1].SetNameChecked(text_content_2); - update.nodes[2].role = ax::mojom::Role::kStaticText; - update.nodes[2].SetNameChecked(text_content_3); + ui::AXNodeData node1; + node1.id = 2; + node1.role = ax::mojom::Role::kStaticText; + node1.SetNameChecked(text_content_1); + + ui::AXNodeData node2; + node2.id = 3; + node2.role = ax::mojom::Role::kStaticText; + node2.SetNameChecked(text_content_2); + + ui::AXNodeData node3; + node3.id = 4; + node3.role = ax::mojom::Role::kStaticText; + node3.SetNameChecked(text_content_3); + update.nodes = {node1, node2, node3}; + // Create selection from node 2-3. update.tree_data.sel_anchor_object_id = 2; update.tree_data.sel_focus_object_id = 3; @@ -735,17 +794,21 @@ ui::AXTreeUpdate update; ui::AXTreeID id_1 = ui::AXTreeID::CreateNewAXTreeID(); SetUpdateTreeID(&update, id_1); - update.root_id = 1; - update.nodes.resize(3); - update.nodes[0].id = 1; - update.nodes[0].child_ids = {2, 3}; - update.nodes[0].role = ax::mojom::Role::kParagraph; - update.nodes[1].id = 2; - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kName, - text_content); - update.nodes[2].id = 3; - update.nodes[2].AddStringAttribute(ax::mojom::StringAttribute::kName, - more_text_content); + ui::AXNodeData node1; + node1.id = 2; + node1.AddStringAttribute(ax::mojom::StringAttribute::kName, text_content); + + ui::AXNodeData node2; + node2.id = 3; + node2.AddStringAttribute(ax::mojom::StringAttribute::kName, + more_text_content); + ui::AXNodeData root; + root.id = 1; + root.child_ids = {node1.id, node2.id}; + root.role = ax::mojom::Role::kParagraph; + update.root_id = root.id; + update.nodes = {root, node1, node2}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); OnActiveAXTreeIDChanged( @@ -765,17 +828,22 @@ ui::AXTreeUpdate update; ui::AXTreeID id_1 = ui::AXTreeID::CreateNewAXTreeID(); SetUpdateTreeID(&update, id_1); - update.root_id = 1; - update.nodes.resize(3); - update.nodes[0].id = 1; - update.nodes[0].child_ids = {2, 3}; - update.nodes[0].role = ax::mojom::Role::kParagraph; - update.nodes[1].id = 2; - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kName, - text_content); - update.nodes[2].id = 3; - update.nodes[2].AddStringAttribute(ax::mojom::StringAttribute::kName, - more_text_content); + ui::AXNodeData node1; + node1.id = 2; + node1.AddStringAttribute(ax::mojom::StringAttribute::kName, text_content); + + ui::AXNodeData node2; + node2.id = 3; + node2.AddStringAttribute(ax::mojom::StringAttribute::kName, + more_text_content); + + ui::AXNodeData root; + root.id = 1; + root.child_ids = {node1.id, node2.id}; + root.role = ax::mojom::Role::kParagraph; + update.root_id = root.id; + update.nodes = {root, node1, node2}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); OnActiveAXTreeIDChanged(id_1, GURL("https://www.google.com/")); @@ -793,23 +861,32 @@ std::string js = "javascript:alert(origin)"; ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(6); - update.nodes[0].id = 1; - update.nodes[1].id = 2; - update.nodes[2].id = 3; - update.nodes[3].id = 4; - update.nodes[4].id = 5; - update.nodes[5].id = 6; - update.nodes[0].child_ids = {2, 3, 4, 5, 6}; - update.nodes[1].AddStringAttribute(ax::mojom::StringAttribute::kUrl, - http_url); - update.nodes[2].AddStringAttribute(ax::mojom::StringAttribute::kUrl, - https_url); - update.nodes[3].AddStringAttribute(ax::mojom::StringAttribute::kUrl, - invalid_url); - update.nodes[4].AddStringAttribute(ax::mojom::StringAttribute::kUrl, - missing_url); - update.nodes[5].AddStringAttribute(ax::mojom::StringAttribute::kUrl, js); + + ui::AXNodeData node1; + node1.id = 2; + node1.AddStringAttribute(ax::mojom::StringAttribute::kUrl, http_url); + + ui::AXNodeData node2; + node2.id = 3; + node2.AddStringAttribute(ax::mojom::StringAttribute::kUrl, https_url); + + ui::AXNodeData node3; + node3.id = 4; + node3.AddStringAttribute(ax::mojom::StringAttribute::kUrl, invalid_url); + + ui::AXNodeData node4; + node4.id = 5; + node4.AddStringAttribute(ax::mojom::StringAttribute::kUrl, missing_url); + + ui::AXNodeData node5; + node5.id = 6; + node5.AddStringAttribute(ax::mojom::StringAttribute::kUrl, js); + + ui::AXNodeData root; + root.id = 1; + root.child_ids = {node1.id, node2.id, node3.id, node4.id, node5.id}; + update.nodes = {root, node1, node2, node3, node4, node5}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(http_url, GetUrl(2)); @@ -822,13 +899,19 @@ TEST_F(ReadAnythingAppControllerTest, ShouldBold) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].AddTextStyle(ax::mojom::TextStyle::kOverline); - update.nodes[1].AddTextStyle(ax::mojom::TextStyle::kUnderline); - update.nodes[2].AddTextStyle(ax::mojom::TextStyle::kItalic); + ui::AXNodeData overlineNode; + overlineNode.id = 2; + overlineNode.AddTextStyle(ax::mojom::TextStyle::kOverline); + + ui::AXNodeData underlineNode; + underlineNode.id = 3; + underlineNode.AddTextStyle(ax::mojom::TextStyle::kUnderline); + + ui::AXNodeData italicNode; + italicNode.id = 4; + italicNode.AddTextStyle(ax::mojom::TextStyle::kItalic); + update.nodes = {overlineNode, underlineNode, italicNode}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(false, ShouldBold(2)); @@ -840,9 +923,10 @@ std::string dataFontCss = "italic 400 14.6667px 'Courier New'"; ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(1); - update.nodes[0].id = 2; - update.nodes[0].html_attributes.emplace_back("data-font-css", dataFontCss); + ui::AXNodeData node; + node.id = 2; + node.html_attributes.emplace_back("data-font-css", dataFontCss); + update.nodes = {node}; AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(dataFontCss, GetDataFontCss(2)); @@ -851,11 +935,15 @@ TEST_F(ReadAnythingAppControllerTest, IsOverline) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(2); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[0].AddTextStyle(ax::mojom::TextStyle::kOverline); - update.nodes[1].AddTextStyle(ax::mojom::TextStyle::kUnderline); + ui::AXNodeData overlineNode; + overlineNode.id = 2; + overlineNode.AddTextStyle(ax::mojom::TextStyle::kOverline); + + ui::AXNodeData underlineNode; + underlineNode.id = 3; + underlineNode.AddTextStyle(ax::mojom::TextStyle::kUnderline); + update.nodes = {overlineNode, underlineNode}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(true, IsOverline(2)); @@ -865,12 +953,20 @@ TEST_F(ReadAnythingAppControllerTest, IsLeafNode) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(4); - update.nodes[0].id = 1; - update.nodes[0].child_ids = {2, 3, 4}; - update.nodes[1].id = 2; - update.nodes[2].id = 3; - update.nodes[3].id = 4; + ui::AXNodeData node1; + node1.id = 2; + + ui::AXNodeData node2; + node2.id = 3; + + ui::AXNodeData node3; + node3.id = 4; + + ui::AXNodeData parent; + parent.id = 1; + parent.child_ids = {node1.id, node2.id, node3.id}; + update.nodes = {parent, node1, node2, node3}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(false, IsLeafNode(1)); @@ -894,13 +990,19 @@ TEST_F(ReadAnythingAppControllerTest, IsNodeIgnoredForReadAnything) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[1].role = ax::mojom::Role::kComboBoxGrouping; - update.nodes[2].role = ax::mojom::Role::kButton; + ui::AXNodeData staticTextNode; + staticTextNode.id = 2; + staticTextNode.role = ax::mojom::Role::kStaticText; + + ui::AXNodeData comboboxNode; + comboboxNode.id = 3; + comboboxNode.role = ax::mojom::Role::kComboBoxGrouping; + + ui::AXNodeData buttonNode; + buttonNode.id = 4; + buttonNode.role = ax::mojom::Role::kButton; + update.nodes = {staticTextNode, comboboxNode, buttonNode}; + AccessibilityEventReceived({update}); OnAXTreeDistilled({}); EXPECT_EQ(false, IsNodeIgnoredForReadAnything(2)); @@ -948,8 +1050,9 @@ TEST_F(ReadAnythingAppControllerTest, DisplayNodeIdsContains_ContentNodes) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(1); - update.nodes[0].id = 3; + ui::AXNodeData node; + node.id = 3; + update.nodes = {node}; // This update says the page loaded. When the controller receives it in // AccessibilityEventReceived, it will re-distill the tree. This is an // example of a non-generated event. @@ -986,10 +1089,11 @@ // Send a new update which settings the text content of node 2. ui::AXTreeUpdate update_1; SetUpdateTreeID(&update_1); - update_1.nodes.resize(1); - update_1.nodes[0].id = 2; - update_1.nodes[0].role = ax::mojom::Role::kStaticText; - update_1.nodes[0].SetNameChecked("Hello world"); + ui::AXNodeData node; + node.id = 2; + node.role = ax::mojom::Role::kStaticText; + node.SetNameChecked("Hello world"); + update_1.nodes = {node}; AccessibilityEventReceived({update_1}); EXPECT_EQ("Hello world", GetTextContent(1)); EXPECT_EQ("Hello world", GetTextContent(2)); @@ -1001,10 +1105,11 @@ for (int i = 2; i < 5; i++) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(1); - update.nodes[0].id = i; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[0].SetNameChecked("Node " + base::NumberToString(i)); + ui::AXNodeData staticTextNode; + staticTextNode.id = i; + staticTextNode.role = ax::mojom::Role::kStaticText; + staticTextNode.SetNameChecked("Node " + base::NumberToString(i)); + update.nodes = {staticTextNode}; batch_updates.push_back(update); } AccessibilityEventReceived(batch_updates); @@ -1018,8 +1123,9 @@ SetUpdateTreeID(&clear_update); clear_update.root_id = 1; clear_update.node_id_to_clear = 1; - clear_update.nodes.resize(1); - clear_update.nodes[0].id = 1; + ui::AXNodeData clearNode; + clearNode.id = 1; + clear_update.nodes = {clearNode}; AccessibilityEventReceived({clear_update}); EXPECT_EQ("", GetTextContent(1)); } @@ -1035,10 +1141,11 @@ // Send a new update which settings the text content of node 2. ui::AXTreeUpdate update_1; SetUpdateTreeID(&update_1); - update_1.nodes.resize(1); - update_1.nodes[0].id = 2; - update_1.nodes[0].role = ax::mojom::Role::kStaticText; - update_1.nodes[0].SetNameChecked("Hello world"); + ui::AXNodeData startNode; + startNode.id = 2; + startNode.role = ax::mojom::Role::kStaticText; + startNode.SetNameChecked("Hello world"); + update_1.nodes = {startNode}; AccessibilityEventReceived({update_1}); EXPECT_EQ("Hello world", GetTextContent(1)); EXPECT_EQ("Hello world", GetTextContent(2)); @@ -1051,10 +1158,11 @@ for (int i = 2; i < 5; i++) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(1); - update.nodes[0].id = i; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[0].SetNameChecked("Node " + base::NumberToString(i)); + ui::AXNodeData node; + node.id = i; + node.role = ax::mojom::Role::kStaticText; + node.SetNameChecked("Node " + base::NumberToString(i)); + update.nodes = {node}; batch_updates.push_back(update); } AccessibilityEventReceived(batch_updates); @@ -1069,10 +1177,11 @@ SetDistillationInProgress(false); ui::AXTreeUpdate update_2; SetUpdateTreeID(&update_2); - update_2.nodes.resize(1); - update_2.nodes[0].id = 2; - update_2.nodes[0].role = ax::mojom::Role::kStaticText; - update_2.nodes[0].SetNameChecked("Final update"); + ui::AXNodeData finalNode; + finalNode.id = 2; + finalNode.role = ax::mojom::Role::kStaticText; + finalNode.SetNameChecked("Final update"); + update_2.nodes = {finalNode}; AccessibilityEventReceived({update_2}); EXPECT_EQ("Final updateNode 3Node 4", GetTextContent(1)); @@ -1090,11 +1199,12 @@ for (int i = 0; i < 3; i++) { ui::AXTreeUpdate update; SetUpdateTreeID(&update, tree_ids[i]); - update.root_id = 1; - update.nodes.resize(1); - update.nodes[0].id = 1; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[0].SetNameChecked("Tree " + base::NumberToString(i)); + ui::AXNodeData node; + node.id = 1; + node.role = ax::mojom::Role::kStaticText; + node.SetNameChecked("Tree " + base::NumberToString(i)); + update.root_id = node.id; + update.nodes = {node}; updates.push_back(update); } // Add the three updates separately since they have different tree IDs. @@ -1121,8 +1231,9 @@ ui::AXTreeID id_1 = ui::AXTreeID::CreateNewAXTreeID(); SetUpdateTreeID(&update, id_1); update.root_id = 1; - update.nodes.resize(1); - update.nodes[0].id = 1; + ui::AXNodeData node; + node.id = 1; + update.nodes = {node}; AccessibilityEventReceived({update}); OnAXTreeDistilled({1}); @@ -1133,9 +1244,10 @@ ui::AXTreeUpdate update_1; SetUpdateTreeID(&update_1, tree_id_); - update_1.root_id = 1; - update_1.nodes.resize(1); - update_1.nodes[0].id = 1; + ui::AXNodeData root; + root.id = 1; + update_1.root_id = root.id; + update_1.nodes = {root}; AccessibilityEventReceived({update_1}); OnAXTreeDistilled({1}); @@ -1171,9 +1283,10 @@ for (int i = 0; i < 2; i++) { ui::AXTreeUpdate update; SetUpdateTreeID(&update, tree_ids[i]); - update.root_id = 1; - update.nodes.resize(1); - update.nodes[0].id = 1; + ui::AXNodeData node; + node.id = 1; + update.root_id = node.id; + update.nodes = {node}; updates.push_back(update); } @@ -1230,13 +1343,16 @@ ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.root_id = 1; - update.nodes.resize(2); - update.nodes[0].id = 1; - update.nodes[0].child_ids = child_ids; - update.nodes[1].id = id; - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[1].SetNameChecked(base::NumberToString(id)); + ui::AXNodeData root; + root.id = 1; + root.child_ids = child_ids; + + ui::AXNodeData node; + node.id = id; + node.role = ax::mojom::Role::kStaticText; + node.SetNameChecked(base::NumberToString(id)); + update.root_id = root.id; + update.nodes = {root, node}; updates.push_back(update); } @@ -1286,13 +1402,16 @@ ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.root_id = 1; - update.nodes.resize(2); - update.nodes[0].id = 1; - update.nodes[0].child_ids = child_ids; - update.nodes[1].id = id; - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[1].SetNameChecked(base::NumberToString(id)); + ui::AXNodeData root; + root.id = 1; + root.child_ids = child_ids; + + ui::AXNodeData node; + node.id = id; + node.role = ax::mojom::Role::kStaticText; + node.SetNameChecked(base::NumberToString(id)); + update.root_id = root.id; + update.nodes = {root, node}; updates.push_back(update); } @@ -1358,13 +1477,16 @@ ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.root_id = 1; - update.nodes.resize(2); - update.nodes[0].id = 1; - update.nodes[0].child_ids = child_ids; - update.nodes[1].id = id; - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[1].SetNameChecked(base::NumberToString(id)); + ui::AXNodeData root; + root.id = 1; + root.child_ids = child_ids; + + ui::AXNodeData node; + node.id = id; + node.role = ax::mojom::Role::kStaticText; + node.SetNameChecked(base::NumberToString(id)); + update.root_id = root.id; + update.nodes = {root, node}; updates.push_back(update); } @@ -1401,13 +1523,16 @@ ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.root_id = 1; - update.nodes.resize(2); - update.nodes[0].id = 1; - update.nodes[0].child_ids = child_ids; - update.nodes[1].id = id; - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[1].SetNameChecked(base::NumberToString(id)); + ui::AXNodeData root; + root.id = 1; + root.child_ids = child_ids; + + ui::AXNodeData node; + node.id = id; + node.role = ax::mojom::Role::kStaticText; + node.SetNameChecked(base::NumberToString(id)); + update.root_id = root.id; + update.nodes = {root, node}; updates.push_back(update); } @@ -1472,21 +1597,25 @@ ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.root_id = 1; - update.nodes.resize(2); - update.nodes[0].id = 1; - update.nodes[0].child_ids = child_ids; - update.nodes[1].id = id; - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[1].SetNameChecked(base::NumberToString(id)); + ui::AXNodeData root; + root.id = 1; + root.child_ids = child_ids; + + ui::AXNodeData node; + node.id = id; + node.role = ax::mojom::Role::kStaticText; + node.SetNameChecked(base::NumberToString(id)); + update.root_id = root.id; + update.nodes = {root, node}; updates.push_back(update); } // Create an update which has no tree id. ui::AXTreeUpdate update; - update.nodes.resize(1); - update.nodes[0].id = 1; - update.nodes[0].role = ax::mojom::Role::kGenericContainer; + ui::AXNodeData genericContainerNode; + genericContainerNode.id = 1; + genericContainerNode.role = ax::mojom::Role::kGenericContainer; + update.nodes = {genericContainerNode}; updates.push_back(update); // Add the three updates. @@ -1513,9 +1642,10 @@ ui::AXTreeID new_tree_id = ui::AXTreeID::CreateNewAXTreeID(); ui::AXTreeUpdate update; SetUpdateTreeID(&update, new_tree_id); - update.root_id = 1; - update.nodes.resize(1); - update.nodes[0].id = 1; + ui::AXNodeData node; + node.id = 1; + update.root_id = node.id; + update.nodes = {node}; AccessibilityEventReceived({update}); EXPECT_CALL(*distiller_, Distill).Times(1); @@ -1532,13 +1662,18 @@ TEST_F(ReadAnythingAppControllerTest, OnSelectionChange) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[2].role = ax::mojom::Role::kStaticText; + ui::AXNodeData node1; + node1.id = 2; + node1.role = ax::mojom::Role::kStaticText; + + ui::AXNodeData node2; + node2.id = 3; + node2.role = ax::mojom::Role::kStaticText; + + ui::AXNodeData node3; + node3.id = 4; + node3.role = ax::mojom::Role::kStaticText; + update.nodes = {node1, node2, node3}; AccessibilityEventReceived({update}); ui::AXNodeID anchor_node_id = 2; int anchor_offset = 0; @@ -1555,13 +1690,18 @@ TEST_F(ReadAnythingAppControllerTest, OnCollapseSelection) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[1].role = ax::mojom::Role::kStaticText; - update.nodes[2].role = ax::mojom::Role::kStaticText; + ui::AXNodeData node1; + node1.id = 2; + node1.role = ax::mojom::Role::kStaticText; + + ui::AXNodeData node2; + node2.id = 3; + node2.role = ax::mojom::Role::kStaticText; + + ui::AXNodeData node3; + node3.id = 4; + node3.role = ax::mojom::Role::kStaticText; + update.nodes = {node1, node2, node3}; AccessibilityEventReceived({update}); EXPECT_CALL(page_handler_, OnCollapseSelection()).Times(1); OnCollapseSelection(); @@ -1572,11 +1712,14 @@ OnSelectionChange_ClickAfterClickDoesNotUpdateSelection) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(2); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[1].role = ax::mojom::Role::kStaticText; + ui::AXNodeData node1; + node1.id = 2; + node1.role = ax::mojom::Role::kStaticText; + + ui::AXNodeData node2; + node2.id = 3; + node2.role = ax::mojom::Role::kStaticText; + update.nodes = {node1, node2}; AccessibilityEventReceived({update}); ui::AXTreeUpdate selection; @@ -1598,11 +1741,14 @@ OnSelectionChange_ClickAfterSelectionClearsSelection) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(2); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[1].role = ax::mojom::Role::kStaticText; + ui::AXNodeData node1; + node1.id = 2; + node1.role = ax::mojom::Role::kStaticText; + + ui::AXNodeData node2; + node2.id = 3; + node2.role = ax::mojom::Role::kStaticText; + update.nodes = {node1, node2}; AccessibilityEventReceived({update}); ui::AXTreeUpdate selection; @@ -1630,10 +1776,11 @@ ui::AXTreeID new_tree_id = ui::AXTreeID::CreateNewAXTreeID(); ui::AXTreeUpdate update; SetUpdateTreeID(&update, new_tree_id); - update.root_id = 1; - update.nodes.resize(1); - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[0].id = 1; + ui::AXNodeData root; + root.id = 1; + root.role = ax::mojom::Role::kStaticText; + update.root_id = root.id; + update.nodes = {root}; AccessibilityEventReceived({update}); EXPECT_CALL(*distiller_, Distill).Times(1); OnActiveAXTreeIDChanged(new_tree_id); @@ -1650,13 +1797,19 @@ OnSelectionChange_NonTextFieldDoesNotUpdateSelection) { ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(3); - update.nodes[0].id = 2; - update.nodes[1].id = 3; - update.nodes[2].id = 4; - update.nodes[0].role = ax::mojom::Role::kTextField; - update.nodes[1].role = ax::mojom::Role::kGenericContainer; - update.nodes[2].role = ax::mojom::Role::kTextField; + ui::AXNodeData textFieldNode1; + textFieldNode1.id = 2; + textFieldNode1.role = ax::mojom::Role::kTextField; + + ui::AXNodeData containerNode; + containerNode.id = 3; + containerNode.role = ax::mojom::Role::kGenericContainer; + + ui::AXNodeData textFieldNode2; + textFieldNode2.id = 4; + textFieldNode2.role = ax::mojom::Role::kTextField; + update.nodes = {textFieldNode1, containerNode, textFieldNode2}; + AccessibilityEventReceived({update}); ui::AXNodeID anchor_node_id = 2; int anchor_offset = 0; @@ -1712,12 +1865,15 @@ ui::AXTreeUpdate update; SetUpdateTreeID(&update); update.root_id = 1; - update.nodes.resize(2); - update.nodes[0].id = 3; - update.nodes[1].id = 4; - update.nodes[0].role = ax::mojom::Role::kStaticText; - update.nodes[0].SetNameChecked("Hello"); - update.nodes[1].role = ax::mojom::Role::kNone; // This node is ignored. + ui::AXNodeData textNode; + textNode.id = 3; + textNode.role = ax::mojom::Role::kStaticText; + textNode.SetNameChecked("Hello"); + + ui::AXNodeData ignoredNode; + ignoredNode.id = 4; + ignoredNode.role = ax::mojom::Role::kNone; // This node is ignored. + update.nodes = {textNode, ignoredNode}; AccessibilityEventReceived({update}); OnAXTreeDistilled({}); @@ -1853,16 +2009,18 @@ ui::AXTreeID pdf_web_contents_tree_id = ui::AXTreeID::CreateNewAXTreeID(); ui::AXTreeUpdate update; SetUpdateTreeID(&update); - update.nodes.resize(1); - update.nodes[0].id = 1; - update.nodes[0].AddChildTreeId(pdf_web_contents_tree_id); + ui::AXNodeData node; + node.id = 1; + node.AddChildTreeId(pdf_web_contents_tree_id); + update.nodes = {node}; AccessibilityEventReceived({update}); // Send update for pdf web contents. ui::AXTreeUpdate pdf_web_contents_update; - pdf_web_contents_update.nodes.resize(1); - pdf_web_contents_update.root_id = 1; - pdf_web_contents_update.nodes[0].id = 1; + ui::AXNodeData pdfNode; + pdfNode.id = 1; + pdf_web_contents_update.root_id = pdfNode.id; + pdf_web_contents_update.nodes = {pdfNode}; SetUpdateTreeID(&pdf_web_contents_update, pdf_web_contents_tree_id); AccessibilityEventReceived({pdf_web_contents_update}); @@ -1878,9 +2036,6 @@ std::u16string sentence3 = u"And this is yet another sentence."; ui::AXTreeUpdate update; SetUpdateTreeID(&update); - // TODO(crbug.com/1474951): Update the rest of the tests to use this - // formatting - // instead of update.nodes.resize where possible to improve readability. ui::AXNodeData staticText1; staticText1.id = 2; staticText1.role = ax::mojom::Role::kStaticText;
diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn index ab34069..662baa26 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn
@@ -810,8 +810,6 @@ "../browser/enterprise/connectors/analysis/source_destination_test_util.h", "../browser/nearby_sharing/fake_nearby_connection.cc", "../browser/nearby_sharing/fake_nearby_connection.h", - "../browser/ui/ash/accessibility/fake_accessibility_controller.cc", - "../browser/ui/ash/accessibility/fake_accessibility_controller.h", "../browser/ui/ash/clipboard_history_test_util.cc", "../browser/ui/ash/clipboard_history_test_util.h", "../browser/ui/webui/ash/login/fake_app_launch_splash_screen_handler.cc", @@ -10537,7 +10535,6 @@ if (is_chromeos_lacros) { deps += [ - ":lacros_test_support_ui", "//chromeos/lacros", "//chromeos/lacros:test_support", "//components/account_manager_core",
diff --git a/chrome/test/base/chromeos/crosier/chromeos_integration_login_mixin.h b/chrome/test/base/chromeos/crosier/chromeos_integration_login_mixin.h index 76d3496..00b903c 100644 --- a/chrome/test/base/chromeos/crosier/chromeos_integration_login_mixin.h +++ b/chrome/test/base/chromeos/crosier/chromeos_integration_login_mixin.h
@@ -57,6 +57,8 @@ void SetUp() override; void SetUpCommandLine(base::CommandLine* command_line) override; + Mode mode() const { return mode_; } + private: bool ShouldStartLoginScreen() const; void PrepareForNewUserLogin();
diff --git a/chrome/test/base/chromeos/crosier/interactive_ash_test.cc b/chrome/test/base/chromeos/crosier/interactive_ash_test.cc index c4b0b33..2887af7 100644 --- a/chrome/test/base/chromeos/crosier/interactive_ash_test.cc +++ b/chrome/test/base/chromeos/crosier/interactive_ash_test.cc
@@ -27,13 +27,30 @@ #include "chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.h" #include "chrome/browser/ui/browser_list.h" #include "chrome/browser/ui/browser_navigator.h" +#include "chrome/common/chrome_switches.h" #include "chrome/test/base/chromeos/crosier/aura_window_title_observer.h" +#include "chrome/test/base/chromeos/crosier/chromeos_integration_login_mixin.h" +#include "google_apis/gaia/gaia_switches.h" +#include "net/test/embedded_test_server/embedded_test_server.h" +#include "net/test/embedded_test_server/http_response.h" #include "ui/aura/test/find_window.h" #include "url/gurl.h" +namespace { + using InteractiveMixinBasedBrowserTest = InteractiveBrowserTestT<MixinBasedInProcessBrowserTest>; +#if BUILDFLAG(IS_CHROMEOS_DEVICE) +// Simulates a failure for a Gaia URL request. +std::unique_ptr<net::test_server::HttpResponse> HandleGaiaURL( + const net::test_server::HttpRequest& request) { + return std::make_unique<net::test_server::HungResponse>(); +} +#endif // BUILDFLAG(IS_CHROMEOS_DEVICE) + +} // namespace + InteractiveAshTest::InteractiveAshTest() { // See header file class comment. set_launch_browser_for_testing(nullptr); @@ -85,6 +102,10 @@ base::CommandLine* command_line) { CHECK(command_line); +#if BUILDFLAG(IS_CHROMEOS_DEVICE) + OverrideGaiaUrlForLacros(command_line); +#endif + // Enable the Wayland server. command_line->AppendSwitch(ash::switches::kAshEnableWaylandServer); @@ -127,6 +148,15 @@ CHECK(extra_parts->did_post_browser_start()); } +void InteractiveAshTest::SetUpOnMainThread() { + InteractiveBrowserTestT<MixinBasedInProcessBrowserTest>::SetUpOnMainThread(); + + // The embedded test server starts accepting connections after fork. + if (https_server_) { + https_server_->StartAcceptingConnections(); + } +} + void InteractiveAshTest::TearDownOnMainThread() { // Passing --test-launcher-interactive leaves the browser running after the // end of the test. @@ -189,3 +219,31 @@ state_change.event = kTextFound; return WaitForStateChange(element_id, state_change); } + +#if BUILDFLAG(IS_CHROMEOS_DEVICE) +void InteractiveAshTest::OverrideGaiaUrlForLacros( + base::CommandLine* command_line) { + // When using real Gaia login, don't override the Gaia URL. + if (login_mixin_.mode() == ChromeOSIntegrationLoginMixin::Mode::kGaiaLogin) { + return; + } + + // Set up an embedded test server. + https_server_ = std::make_unique<net::test_server::EmbeddedTestServer>( + net::test_server::EmbeddedTestServer::TYPE_HTTPS); + https_server_->RegisterRequestHandler(base::BindRepeating(&HandleGaiaURL)); + CHECK(https_server_->InitializeAndListen()); + + std::vector<std::string> lacros_args; + lacros_args.emplace_back(base::StringPrintf("--%s", switches::kNoFirstRun)); + // Override Gaia url in Lacros so that the gaia requests will NOT be handled + // with the real internet connection, but with the embedded test server. The + // embedded test server will simulate failure of the Gaia url requests which + // is expected in testing environment for Gaia authentication flow. See + // crbug.com/1371655. + lacros_args.emplace_back(base::StringPrintf( + "--%s=%s", switches::kGaiaUrl, https_server_->base_url().spec().c_str())); + command_line->AppendSwitchASCII(ash::switches::kLacrosChromeAdditionalArgs, + base::JoinString(lacros_args, "####")); +} +#endif // BUILDFLAG(IS_CHROMEOS_DEVICE)
diff --git a/chrome/test/base/chromeos/crosier/interactive_ash_test.h b/chrome/test/base/chromeos/crosier/interactive_ash_test.h index 14ea6e1..89d1b57 100644 --- a/chrome/test/base/chromeos/crosier/interactive_ash_test.h +++ b/chrome/test/base/chromeos/crosier/interactive_ash_test.h
@@ -31,6 +31,10 @@ class NavigationHandle; } +namespace net::test_server { +class EmbeddedTestServer; +} + // Base class for tests of ash-chrome integration with the ChromeOS platform, // like hardware daemons, graphics, kernel, etc. // @@ -91,6 +95,7 @@ void WaitForAshFullyStarted(); // MixinBasedInProcessBrowserTest: + void SetUpOnMainThread() override; void TearDownOnMainThread() override; // Blocks until a window exists with the given title. If a matching window @@ -134,6 +139,10 @@ private: #if BUILDFLAG(IS_CHROMEOS_DEVICE) + // Overrides the Gaia URL to point to a local test server that produces an + // error, which is expected behavior in test environments. + void OverrideGaiaUrlForLacros(base::CommandLine* command_line); + // This test runs on linux-chromeos in interactive_ui_tests and on a DUT in // chromeos_integration_tests. ChromeOSIntegrationTestMixin chromeos_integration_test_mixin_{&mixin_host_}; @@ -144,5 +153,7 @@ // Directory used by Wayland/Lacros in environment variable XDG_RUNTIME_DIR. base::ScopedTempDir scoped_temp_dir_xdg_; + + std::unique_ptr<net::test_server::EmbeddedTestServer> https_server_; }; #endif // CHROME_TEST_BASE_CHROMEOS_CROSIER_INTERACTIVE_ASH_TEST_H_
diff --git a/chrome/test/base/in_process_browser_test.cc b/chrome/test/base/in_process_browser_test.cc index 852c4ff1..f01709c 100644 --- a/chrome/test/base/in_process_browser_test.cc +++ b/chrome/test/base/in_process_browser_test.cc
@@ -155,9 +155,7 @@ #include "base/threading/thread_restrictions.h" #include "base/uuid.h" #include "base/version.h" -#include "chrome/browser/lacros/browser_test_util.h" #include "chrome/browser/lacros/cert/cert_db_initializer_factory.h" -#include "chrome/browser/ui/lacros/window_utility.h" #include "chromeos/crosapi/mojom/crosapi.mojom.h" #include "chromeos/crosapi/mojom/test_controller.mojom-test-utils.h" #include "chromeos/lacros/lacros_service.h" @@ -292,28 +290,6 @@ NotificationDisplayServiceTester::EnsureFactoryBuilt(); } -// TODO(neis): The name WaitForWindowCreation is a bit confusing. Technically, -// we are waiting for the window to become visible (or minimized) in Ash. -// Try to find a better name. -bool WaitForWindowCreation(Browser* browser) { -#if BUILDFLAG(IS_CHROMEOS_LACROS) - // TODO(crbug.com/1508245): Get rid of the IsTestControllerAvailable condition - // by making it always true (when crosapi is enabled). Moreover, propagate the - // WaitForWindowCreation return value. This requires fixing some tests that - // improperly override init params. - if (IsCrosapiEnabled() && IsTestControllerAvailable()) { - // Wait for window creation to complete in Ash in order to avoid - // wayland-crosapi race conditions in subsequent test steps. - aura::Window* window = browser->window()->GetNativeWindow(); - std::string id = - lacros_window_utility::GetRootWindowUniqueId(window->GetRootWindow()); - std::ignore = browser_test_util::WaitForWindowCreation(id); - return true; - } -#endif - return true; -} - InProcessBrowserTest* g_current_test; } // namespace @@ -899,7 +875,6 @@ observer.Wait(); browser->window()->Show(); - ASSERT_TRUE(WaitForWindowCreation(browser)); } #if !BUILDFLAG(IS_MAC) && !BUILDFLAG(IS_CHROMEOS_LACROS) @@ -980,13 +955,8 @@ // browser. content::RunAllPendingInMessageLoop(); - if (browser_) { - ASSERT_TRUE(WaitForWindowCreation(browser_)); - - if (global_browser_set_up_function_) { - ASSERT_TRUE(global_browser_set_up_function_(browser_)); - } - } + if (browser_ && global_browser_set_up_function_) + ASSERT_TRUE(global_browser_set_up_function_(browser_)); #if BUILDFLAG(IS_MAC) autorelease_pool_->Recycle();
diff --git a/chrome/test/data/webui/settings/chromeos/os_people_page/account_manager_settings_card_test.ts b/chrome/test/data/webui/settings/chromeos/os_people_page/account_manager_settings_card_test.ts index 377f183..b060fae 100644 --- a/chrome/test/data/webui/settings/chromeos/os_people_page/account_manager_settings_card_test.ts +++ b/chrome/test/data/webui/settings/chromeos/os_people_page/account_manager_settings_card_test.ts
@@ -4,7 +4,7 @@ import 'chrome://os-settings/os_settings.js'; -import {Account, AccountManagerBrowserProxyImpl} from 'chrome://os-settings/lazy_load.js'; +import {Account} from 'chrome://os-settings/lazy_load.js'; import {AccountManagerSettingsCardElement, CrIconButtonElement, ParentalControlsBrowserProxyImpl, Router, routes} from 'chrome://os-settings/os_settings.js'; import {assert} from 'chrome://resources/js/assert.js'; import {loadTimeData} from 'chrome://resources/js/load_time_data.js'; @@ -12,27 +12,32 @@ import {assertEquals, assertNull, assertTrue} from 'chrome://webui-test/chai_assert.js'; import {isVisible} from 'chrome://webui-test/test_util.js'; -import {TestAccountManagerBrowserProxy, TestAccountManagerBrowserProxyForUnmanagedAccounts} from './test_account_manager_browser_proxy.js'; import {TestParentalControlsBrowserProxy} from './test_parental_controls_browser_proxy.js'; suite('<account-manager-settings-card>', () => { - let browserProxy: TestAccountManagerBrowserProxy; let accountManagerSettingsCard: AccountManagerSettingsCardElement; - let primaryDeviceAccount: Account|undefined; + const managedAccount: Account = { + id: '123', + accountType: 1, + isDeviceAccount: true, + isSignedIn: true, + unmigrated: false, + isManaged: true, + fullName: 'Primary Account', + pic: 'data:image/png;base64,primaryAccountPicData', + email: 'primary@gmail.com', + isAvailableInArc: true, + organization: 'Family Link', + }; suiteSetup(async () => { loadTimeData.overrideValues({isDeviceAccountManaged: true}); - - browserProxy = new TestAccountManagerBrowserProxy(); - AccountManagerBrowserProxyImpl.setInstanceForTesting(browserProxy); - - primaryDeviceAccount = (await browserProxy.getAccounts()) - .find(account => account.isDeviceAccount); }); setup(() => { accountManagerSettingsCard = document.createElement('account-manager-settings-card'); + accountManagerSettingsCard.deviceAccount = managedAccount; document.body.appendChild(accountManagerSettingsCard); Router.getInstance().navigateTo(routes.OS_PEOPLE); @@ -41,64 +46,62 @@ teardown(() => { accountManagerSettingsCard.remove(); - browserProxy.reset(); Router.getInstance().resetRouteForTesting(); }); - test('managed badge is visible if device account is managed', async () => { - await browserProxy.whenCalled('getAccounts'); - flush(); - + test('managed badge is visible if device account is managed', () => { const managedBadge = accountManagerSettingsCard.shadowRoot!.querySelector( '.device-account-icon .managed-badge'); assertTrue(isVisible(managedBadge)); }); - test('account full name is correct and visible', async () => { - await browserProxy.whenCalled('getAccounts'); - flush(); - + test('account full name is correct and visible', () => { const accountFullNameEl = accountManagerSettingsCard.shadowRoot!.querySelector( '#deviceAccountFullName'); assert(accountFullNameEl); - assert(primaryDeviceAccount); + assert(managedAccount); assertTrue(isVisible(accountFullNameEl)); assertEquals( - primaryDeviceAccount.fullName, accountFullNameEl.textContent!.trim()); + managedAccount.fullName, accountFullNameEl.textContent!.trim()); }); - test('account email is correct and visible', async () => { - await browserProxy.whenCalled('getAccounts'); - flush(); - + test('account email is correct and visible', () => { const accountEmailEl = accountManagerSettingsCard.shadowRoot!.querySelector( '#deviceAccountEmail'); assert(accountEmailEl); - assert(primaryDeviceAccount); + assert(managedAccount); assertTrue(isVisible(accountEmailEl)); - assertEquals( - primaryDeviceAccount.email, accountEmailEl.textContent!.trim()); + assertEquals(managedAccount.email, accountEmailEl.textContent!.trim()); }); }); suite('AccountManagerUnmanagedAccountTests', () => { - let browserProxy: TestAccountManagerBrowserProxyForUnmanagedAccounts; let accountManagerSettingsCard: AccountManagerSettingsCardElement; + const unmanagedAccount = { + id: '123', + accountType: 1, + isDeviceAccount: true, + isSignedIn: true, + unmigrated: false, + isManaged: false, + fullName: 'Device Account', + email: 'admin@domain.com', + pic: 'data:image/png;base64,abc123', + isAvailableInArc: false, + }; suiteSetup(() => { loadTimeData.overrideValues({isDeviceAccountManaged: false}); - - browserProxy = new TestAccountManagerBrowserProxyForUnmanagedAccounts(); - AccountManagerBrowserProxyImpl.setInstanceForTesting(browserProxy); }); setup(() => { accountManagerSettingsCard = document.createElement('account-manager-settings-card'); + accountManagerSettingsCard.deviceAccount = unmanagedAccount; document.body.appendChild(accountManagerSettingsCard); Router.getInstance().navigateTo(routes.OS_PEOPLE); @@ -106,14 +109,10 @@ teardown(() => { accountManagerSettingsCard.remove(); - browserProxy.reset(); Router.getInstance().resetRouteForTesting(); }); - test('ManagementStatusForUnmanagedAccounts', async () => { - await browserProxy.whenCalled('getAccounts'); - flush(); - + test('ManagementStatusForUnmanagedAccounts', () => { const managedBadge = accountManagerSettingsCard.shadowRoot!.querySelector( '.device-account-icon .managed-badge'); // Managed badge should not be shown for unmanaged accounts. @@ -148,11 +147,12 @@ Router.getInstance().resetRouteForTesting(); }); - test('FamilyLinkIcon', () => { + test('Family link icon is visible and launches family link settings', () => { const icon = accountManagerSettingsCard.shadowRoot! .querySelector<CrIconButtonElement>( '.managed-message cr-icon-button'); assertTrue(!!icon, 'Could not find the managed icon'); + assertTrue(isVisible(icon)); assertEquals('cr20:kite', icon.ironIcon);
diff --git a/chrome/test/data/webui/settings/chromeos/os_people_page/additional_accounts_settings_card_test.ts b/chrome/test/data/webui/settings/chromeos/os_people_page/additional_accounts_settings_card_test.ts index 0c78417..8c899d00 100644 --- a/chrome/test/data/webui/settings/chromeos/os_people_page/additional_accounts_settings_card_test.ts +++ b/chrome/test/data/webui/settings/chromeos/os_people_page/additional_accounts_settings_card_test.ts
@@ -7,7 +7,6 @@ import {AccountManagerBrowserProxyImpl} from 'chrome://os-settings/lazy_load.js'; import {AdditionalAccountsSettingsCardElement, CrTooltipIconElement, Router, routes, settingMojom, setUserActionRecorderForTesting} from 'chrome://os-settings/os_settings.js'; import {assert} from 'chrome://resources/js/assert.js'; -import {webUIListenerCallback} from 'chrome://resources/js/cr.js'; import {loadTimeData} from 'chrome://resources/js/load_time_data.js'; import {getDeepActiveElement} from 'chrome://resources/js/util.js'; import {DomRepeat, flush} from 'chrome://resources/polymer/v3_0/polymer/polymer_bundled.min.js'; @@ -27,16 +26,18 @@ suiteSetup(() => { loadTimeData.overrideValues({isDeviceAccountManaged: true}); - browserProxy = new TestAccountManagerBrowserProxy(); - AccountManagerBrowserProxyImpl.setInstanceForTesting(browserProxy); + userActionRecorder = new FakeUserActionRecorder(); + setUserActionRecorderForTesting(userActionRecorder); }); setup(async () => { - userActionRecorder = new FakeUserActionRecorder(); - setUserActionRecorderForTesting(userActionRecorder); + browserProxy = new TestAccountManagerBrowserProxy(); + AccountManagerBrowserProxyImpl.setInstanceForTesting(browserProxy); + const accounts = await browserProxy.getAccounts(); additionalAccountSettingsCard = document.createElement('additional-accounts-settings-card'); + additionalAccountSettingsCard.accounts = accounts; document.body.appendChild(additionalAccountSettingsCard); const list = additionalAccountSettingsCard.shadowRoot!.querySelector<DomRepeat>( @@ -46,9 +47,6 @@ Router.getInstance().navigateTo(routes.OS_PEOPLE); flush(); - - await browserProxy.whenCalled('getAccounts'); - flush(); }); teardown(() => { @@ -155,12 +153,6 @@ `Kebab menu should be focused for settingId${removeAccountSettingId}.`); }); - test('accountList is updated when account manager updates', () => { - assertEquals(1, browserProxy.getCallCount('getAccounts')); - webUIListenerCallback('accounts-changed'); - assertEquals(2, browserProxy.getCallCount('getAccounts')); - }); - if (loadTimeData.getBoolean('arcAccountRestrictionsEnabled')) { test('arc availability is shown for secondary accounts', () => { accountList.items!.forEach((item, i) => {
diff --git a/chrome/test/data/webui/settings/chromeos/os_settings_browsertest.js b/chrome/test/data/webui/settings/chromeos/os_settings_browsertest.js index 033b55f..572f08c 100644 --- a/chrome/test/data/webui/settings/chromeos/os_settings_browsertest.js +++ b/chrome/test/data/webui/settings/chromeos/os_settings_browsertest.js
@@ -1130,7 +1130,13 @@ ['OsSettingsUiToolbar', 'os_settings_ui/os_settings_ui_toolbar_test.js'], [ 'OsSettingsUiUserActionRecorder', - 'os_settings_ui/user_action_recorder_test.js' + 'os_settings_ui/user_action_recorder_test.js', + {disabled: ['ash::features::kOsSettingsRevampWayfinding']}, + ], + [ + 'OsSettingsUiUserActionRecorderRevamp', + 'os_settings_ui/user_action_recorder_test.js', + {enabled: ['ash::features::kOsSettingsRevampWayfinding']}, ], [ 'ParentalControlsPage',
diff --git a/chrome/test/data/webui/settings/chromeos/os_settings_ui/user_action_recorder_test.ts b/chrome/test/data/webui/settings/chromeos/os_settings_ui/user_action_recorder_test.ts index 38ed7502..d177bae 100644 --- a/chrome/test/data/webui/settings/chromeos/os_settings_ui/user_action_recorder_test.ts +++ b/chrome/test/data/webui/settings/chromeos/os_settings_ui/user_action_recorder_test.ts
@@ -4,17 +4,20 @@ import 'chrome://os-settings/os_settings.js'; +import {AccountManagerBrowserProxyImpl} from 'chrome://os-settings/lazy_load.js'; import {CrSettingsPrefs, OsSettingsUiElement, Router, routes, setNearbyShareSettingsForTesting, setUserActionRecorderForTesting} from 'chrome://os-settings/os_settings.js'; import {flush} from 'chrome://resources/polymer/v3_0/polymer/polymer_bundled.min.js'; import {assertEquals, assertTrue} from 'chrome://webui-test/chai_assert.js'; import {FakeNearbyShareSettings} from 'chrome://webui-test/nearby_share/shared/fake_nearby_share_settings.js'; import {FakeUserActionRecorder} from '../fake_user_action_recorder.js'; +import {TestAccountManagerBrowserProxy} from '../os_people_page/test_account_manager_browser_proxy.js'; suite('User action recorder', () => { let ui: OsSettingsUiElement; let fakeUserActionRecorder: FakeUserActionRecorder; let fakeNearbySettings: FakeNearbyShareSettings; + let testAccountManagerBrowserProxy: TestAccountManagerBrowserProxy; async function createElement(): Promise<OsSettingsUiElement> { const element = document.createElement('os-settings-ui'); @@ -27,6 +30,11 @@ suiteSetup(() => { fakeNearbySettings = new FakeNearbyShareSettings(); setNearbyShareSettingsForTesting(fakeNearbySettings); + + // Setup fake accounts. + testAccountManagerBrowserProxy = new TestAccountManagerBrowserProxy(); + AccountManagerBrowserProxyImpl.setInstanceForTesting( + testAccountManagerBrowserProxy); }); setup(async () => { @@ -38,6 +46,7 @@ teardown(() => { ui.remove(); Router.getInstance().resetRouteForTesting(); + testAccountManagerBrowserProxy.reset(); }); test('Records navigation changes', () => {
diff --git a/chrome/test/data/webui/settings/safety_hub_card_test.ts b/chrome/test/data/webui/settings/safety_hub_card_test.ts index 90faa14..414aad9 100644 --- a/chrome/test/data/webui/settings/safety_hub_card_test.ts +++ b/chrome/test/data/webui/settings/safety_hub_card_test.ts
@@ -53,7 +53,7 @@ // Check icon for INFO state. testElement.data = getMockDataForState(CardState.INFO); flushTasks(); - assertEquals('cr:error', testElement.$.icon.icon); + assertEquals('cr:info', testElement.$.icon.icon); assertTrue(testElement.$.icon.classList.contains('grey')); // Check icon for WEAK state.
diff --git a/chrome/test/data/webui/settings/safety_hub_page_test.ts b/chrome/test/data/webui/settings/safety_hub_page_test.ts index bc8c0bf..b6f6717 100644 --- a/chrome/test/data/webui/settings/safety_hub_page_test.ts +++ b/chrome/test/data/webui/settings/safety_hub_page_test.ts
@@ -6,8 +6,8 @@ import 'chrome://settings/lazy_load.js'; import {webUIListenerCallback} from 'chrome://resources/js/cr.js'; -import {CardInfo, CardState, ContentSettingsTypes, SafetyHubBrowserProxyImpl, SafetyHubEvent,SettingsSafetyHubPageElement} from 'chrome://settings/lazy_load.js'; -import {LifetimeBrowserProxyImpl, MetricsBrowserProxyImpl, PasswordManagerImpl, PasswordManagerPage, Router, routes} from 'chrome://settings/settings.js'; +import {CardInfo, CardState, ContentSettingsTypes, SafetyHubBrowserProxyImpl, SafetyHubEvent, SettingsSafetyHubPageElement} from 'chrome://settings/lazy_load.js'; +import {LifetimeBrowserProxyImpl, MetricsBrowserProxyImpl, PasswordManagerImpl, PasswordManagerPage, Router, routes, SafetyHubModuleType, SafetyHubSurfaces} from 'chrome://settings/settings.js'; import {assertEquals, assertFalse, assertTrue} from 'chrome://webui-test/chai_assert.js'; import {isChildVisible} from 'chrome://webui-test/test_util.js'; import {flushTasks} from 'chrome://webui-test/polymer_test_util.js'; @@ -364,4 +364,110 @@ Router.getInstance().navigateTo(routes.SAFETY_HUB); await safetyHubBrowserProxy.whenCalled('dismissActiveMenuNotification'); }); + + test('Metric Recording', async function() { + const safeCardData: CardInfo = { + header: 'Dummy header', + subheader: 'Dummy subheader', + state: CardState.SAFE, + }; + + const unsafeCardData: CardInfo = { + header: 'Dummy header', + subheader: 'Dummy subheader', + state: CardState.WARNING, + }; + + function reset() { + // Reset all cards and modules on safety hub page. + safetyHubBrowserProxy.setPasswordCardData(safeCardData); + safetyHubBrowserProxy.setVersionCardData(safeCardData); + safetyHubBrowserProxy.setSafeBrowsingCardData(safeCardData); + safetyHubBrowserProxy.setUnusedSitePermissions([]); + safetyHubBrowserProxy.setNotificationPermissionReview([]); + safetyHubBrowserProxy.setNumberOfExtensionsThatNeedReview(0); + metricsBrowserProxy.reset(); + } + + async function refresh(): Promise<void> { + // Refresh the page to consume recent mock data. + document.body.removeChild(testElement); + testElement = document.createElement('settings-safety-hub-page'); + document.body.appendChild(testElement); + await flushTasks(); + } + + reset(); + await refresh(); + // Expect recordSafetyHubDashboardAnyWarning is called as false since + // there is no warning. + let result = await metricsBrowserProxy.whenCalled( + 'recordSafetyHubDashboardAnyWarning'); + assertEquals(false, result); + + // Check general interaction and impression metrics. + result = await metricsBrowserProxy.whenCalled('recordSafetyHubImpression'); + assertEquals(SafetyHubSurfaces.SAFETY_HUB_PAGE, result); + result = await metricsBrowserProxy.whenCalled('recordSafetyHubInteraction'); + assertEquals(SafetyHubSurfaces.SAFETY_HUB_PAGE, result); + + // Expect recordSafetyHubModuleWarningImpression is called for password + // card. + reset(); + safetyHubBrowserProxy.setPasswordCardData(unsafeCardData); + await refresh(); + result = await metricsBrowserProxy.whenCalled( + 'recordSafetyHubModuleWarningImpression'); + assertEquals(SafetyHubModuleType.PASSWORDS, result); + + // Expect recordSafetyHubModuleWarningImpression is called for version card. + reset(); + safetyHubBrowserProxy.setVersionCardData(unsafeCardData); + await refresh(); + result = await metricsBrowserProxy.whenCalled( + 'recordSafetyHubModuleWarningImpression'); + assertEquals(SafetyHubModuleType.VERSION, result); + + // Expect recordSafetyHubModuleWarningImpression is called for safe browsing + // card. + reset(); + safetyHubBrowserProxy.setSafeBrowsingCardData(unsafeCardData); + await refresh(); + result = await metricsBrowserProxy.whenCalled( + 'recordSafetyHubModuleWarningImpression'); + assertEquals(SafetyHubModuleType.SAFE_BROWSING, result); + + // Expect recordSafetyHubModuleWarningImpression is called for unused site + // permissions. + reset(); + safetyHubBrowserProxy.setUnusedSitePermissions( + unusedSitePermissionMockData); + await refresh(); + result = await metricsBrowserProxy.whenCalled( + 'recordSafetyHubModuleWarningImpression'); + assertEquals(SafetyHubModuleType.PERMISSIONS, result); + + // Expect recordSafetyHubModuleWarningImpression is called for notification + // permissions. + reset(); + safetyHubBrowserProxy.setNotificationPermissionReview( + notificationPermissionMockData); + await refresh(); + result = await metricsBrowserProxy.whenCalled( + 'recordSafetyHubModuleWarningImpression'); + assertEquals(SafetyHubModuleType.NOTIFICATIONS, result); + + // Expect recordSafetyHubModuleWarningImpression is called for extensions. + reset(); + safetyHubBrowserProxy.setNumberOfExtensionsThatNeedReview(1); + await refresh(); + result = await metricsBrowserProxy.whenCalled( + 'recordSafetyHubModuleWarningImpression'); + assertEquals(SafetyHubModuleType.EXTENSIONS, result); + + // Expect recordSafetyHubDashboardAnyWarning is called as true. + result = await metricsBrowserProxy.whenCalled( + 'recordSafetyHubDashboardAnyWarning'); + assertEquals(true, result); + }); });
diff --git a/chrome/test/data/webui/settings/test_metrics_browser_proxy.ts b/chrome/test/data/webui/settings/test_metrics_browser_proxy.ts index 1fe51204..08a3542 100644 --- a/chrome/test/data/webui/settings/test_metrics_browser_proxy.ts +++ b/chrome/test/data/webui/settings/test_metrics_browser_proxy.ts
@@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -import {DeleteBrowsingDataAction, MetricsBrowserProxy, PrivacyElementInteractions, PrivacyGuideInteractions, PrivacyGuideSettingsStates, PrivacyGuideStepsEligibleAndReached, SafeBrowsingInteractions, SafetyCheckInteractions, SafetyCheckNotificationsModuleInteractions, SafetyCheckUnusedSitePermissionsModuleInteractions, SafetyHubCardState, SafetyHubSurfaces} from 'chrome://settings/settings.js'; +import {DeleteBrowsingDataAction, MetricsBrowserProxy, PrivacyElementInteractions, PrivacyGuideInteractions, PrivacyGuideSettingsStates, PrivacyGuideStepsEligibleAndReached, SafeBrowsingInteractions, SafetyCheckInteractions, SafetyCheckNotificationsModuleInteractions, SafetyCheckUnusedSitePermissionsModuleInteractions, SafetyHubCardState, SafetyHubEntryPoint, SafetyHubModuleType, SafetyHubSurfaces} from 'chrome://settings/settings.js'; import {TestBrowserProxy} from 'chrome://webui-test/test_browser_proxy.js'; export class TestMetricsBrowserProxy extends TestBrowserProxy implements @@ -28,6 +28,10 @@ 'recordDeleteBrowsingDataAction', 'recordSafetyHubImpression', 'recordSafetyHubInteraction', + 'recordSafetyHubEntryPointShown', + 'recordSafetyHubEntryPointClicked', + 'recordSafetyHubModuleWarningImpression', + 'recordSafetyHubDashboardAnyWarning', ]); } @@ -125,4 +129,20 @@ recordSafetyHubInteraction(surface: SafetyHubSurfaces) { this.methodCalled('recordSafetyHubInteraction', surface); } + + recordSafetyHubEntryPointShown(page: SafetyHubEntryPoint) { + this.methodCalled('recordSafetyHubModuleWarningImpression', page); + } + + recordSafetyHubEntryPointClicked(page: SafetyHubEntryPoint) { + this.methodCalled('recordSafetyHubEntryPointClicked', page); + } + + recordSafetyHubModuleWarningImpression(module: SafetyHubModuleType) { + this.methodCalled('recordSafetyHubModuleWarningImpression', module); + } + + recordSafetyHubDashboardAnyWarning(visible: boolean) { + this.methodCalled('recordSafetyHubDashboardAnyWarning', visible); + } }
diff --git a/chrome/test/data/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_test.ts b/chrome/test/data/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_test.ts index 9ee02276..a617b9fe 100644 --- a/chrome/test/data/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_test.ts +++ b/chrome/test/data/webui/side_panel/customize_chrome/wallpaper_search/wallpaper_search_test.ts
@@ -130,7 +130,7 @@ assertEquals( 6, wallpaperSearchElement.shadowRoot! - .querySelectorAll('#descriptorMenuD cr-button') + .querySelectorAll('#descriptorMenuD button') .length); }); @@ -209,13 +209,13 @@ await flushTasks(); assertFalse( - !!$$(wallpaperSearchElement, '#descriptorMenuD cr-button [checked]')); + !!$$(wallpaperSearchElement, '#descriptorMenuD button [checked]')); $$<HTMLElement>(wallpaperSearchElement, '.default-color')!.click(); let checkedMarkedColors = wallpaperSearchElement.shadowRoot!.querySelectorAll( - '#descriptorMenuD cr-button [checked]'); + '#descriptorMenuD button [checked]'); assertEquals(1, checkedMarkedColors.length); assertEquals( checkedMarkedColors[0], @@ -229,7 +229,7 @@ new Event('selected-hue-changed')); checkedMarkedColors = wallpaperSearchElement.shadowRoot!.querySelectorAll( - '#descriptorMenuD cr-button [checked]'); + '#descriptorMenuD button [checked]'); assertEquals(1, checkedMarkedColors.length); assertEquals( checkedMarkedColors[0], @@ -277,7 +277,7 @@ wallpaperSearchElement, '#descriptorComboboxC .dropdown-item')!.click(); $$<HTMLElement>( - wallpaperSearchElement, '#descriptorMenuD cr-button')!.click(); + wallpaperSearchElement, '#descriptorMenuD button')!.click(); wallpaperSearchElement.$.submitButton.click(); assertEquals(1, handler.getCallCount('getWallpaperSearchResults')); @@ -298,7 +298,7 @@ await flushTasks(); $$<HTMLElement>( - wallpaperSearchElement, '#descriptorMenuD cr-button')!.click(); + wallpaperSearchElement, '#descriptorMenuD button')!.click(); wallpaperSearchElement.$.hueSlider.selectedHue = 10; wallpaperSearchElement.$.hueSlider.dispatchEvent(
diff --git a/chrome/test/data/webui/side_panel/read_anything/checkmark_visible_on_selected.ts b/chrome/test/data/webui/side_panel/read_anything/checkmark_visible_on_selected.ts index b49f751..6888c0c 100644 --- a/chrome/test/data/webui/side_panel/read_anything/checkmark_visible_on_selected.ts +++ b/chrome/test/data/webui/side_panel/read_anything/checkmark_visible_on_selected.ts
@@ -13,6 +13,7 @@ let toolbar: ReadAnythingToolbarElement; setup(function() { + document.body.innerHTML = window.trustedTypes!.emptyHTML; const readingMode = new FakeReadingMode(); chrome.readingMode = readingMode as unknown as typeof chrome.readingMode;
diff --git a/chrome/test/data/webui/side_panel/read_anything/read_anything_browsertest.cc b/chrome/test/data/webui/side_panel/read_anything/read_anything_browsertest.cc index 16ffa49..81073fcde 100644 --- a/chrome/test/data/webui/side_panel/read_anything/read_anything_browsertest.cc +++ b/chrome/test/data/webui/side_panel/read_anything/read_anything_browsertest.cc
@@ -2,7 +2,10 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. +#include "base/run_loop.h" #include "base/test/scoped_feature_list.h" +#include "chrome/browser/ui/side_panel/side_panel_entry_id.h" +#include "chrome/browser/ui/side_panel/side_panel_ui.h" #include "chrome/common/webui_url_constants.h" #include "chrome/test/base/web_ui_mocha_browser_test.h" #include "content/public/common/url_constants.h" @@ -22,12 +25,26 @@ set_test_loader_scheme(content::kChromeUIUntrustedScheme); } + void RunSidePanelTest(const std::string& file, + const std::string& trigger, + const SidePanelEntryId id) { + auto* side_panel_ui = SidePanelUI::GetSidePanelUIForBrowser(browser()); + side_panel_ui->Show(id); + auto* web_contents = side_panel_ui->GetWebContentsForTest(id); + ASSERT_TRUE(web_contents); + + content::WaitForLoadStop(web_contents); + + ASSERT_TRUE(RunTestOnWebContents(web_contents, file, trigger, true)); + side_panel_ui->Close(); + } + base::test::ScopedFeatureList scoped_feature_list_{features::kReadAnything}; }; using ReadAnythingMochaTest = ReadAnythingMochaBrowserTest; IN_PROC_BROWSER_TEST_F(ReadAnythingMochaTest, CheckmarkVisibleOnSelected) { - RunTest("side_panel/read_anything/checkmark_visible_on_selected.js", - "mocha.run()"); + RunSidePanelTest("side_panel/read_anything/checkmark_visible_on_selected.js", + "mocha.run()", SidePanelEntryId::kReadAnything); }
diff --git a/chrome/test/variations/pytest.ini b/chrome/test/variations/pytest.ini index 2873107..34a1b31 100644 --- a/chrome/test/variations/pytest.ini +++ b/chrome/test/variations/pytest.ini
@@ -1,2 +1,6 @@ [pytest] -pythonpath=../../../ \ No newline at end of file +pythonpath=../../../ + +filterwarnings = + # ignore warnings about re-imported modules. + ignore::pytest.PytestAssertRewriteWarning
diff --git a/chromecast/browser/cast_permission_manager.cc b/chromecast/browser/cast_permission_manager.cc index c2d1060..5df307b 100644 --- a/chromecast/browser/cast_permission_manager.cc +++ b/chromecast/browser/cast_permission_manager.cc
@@ -210,7 +210,7 @@ } CastPermissionManager::SubscriptionId -CastPermissionManager::SubscribePermissionStatusChange( +CastPermissionManager::SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, @@ -219,7 +219,7 @@ return SubscriptionId(); } -void CastPermissionManager::UnsubscribePermissionStatusChange( +void CastPermissionManager::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) {} } // namespace shell
diff --git a/chromecast/browser/cast_permission_manager.h b/chromecast/browser/cast_permission_manager.h index 16582c2..3093f67b5 100644 --- a/chromecast/browser/cast_permission_manager.h +++ b/chromecast/browser/cast_permission_manager.h
@@ -62,14 +62,14 @@ blink::PermissionType permission, content::RenderFrameHost* render_frame_host, const url::Origin& requesting_origin) override; - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, const GURL& requesting_origin, base::RepeatingCallback<void(blink::mojom::PermissionStatus)> callback) override; - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; };
diff --git a/chromeos/ash/services/recording/gif_encoder.cc b/chromeos/ash/services/recording/gif_encoder.cc index 5153049b3..71b16cd 100644 --- a/chromeos/ash/services/recording/gif_encoder.cc +++ b/chromeos/ash/services/recording/gif_encoder.cc
@@ -29,8 +29,17 @@ constexpr uint8_t kExtensionIntroducer = 0x21; // The minimum number of frames that needs to be received since the last time we -// built the color palette, before we build a new one. -constexpr uint8_t kMinNumberOfFramesBetweenPaletteRebuilds = 20; +// built the color palette, before we build a new one. Since we are dithering +// the image, we can work with an old color palette for a larger number of +// frames before we have to rebuild it. +constexpr uint8_t kMinNumberOfFramesBetweenPaletteRebuilds = 60; + +// If the screen doesn't have any damage, video frames may never be generated. +// As a result, there can be a large time interval between one frame and the +// next, in which case the existing color palette might be very stale, and needs +// to be rebuilt. +constexpr base::TimeDelta kMaxDurationBetweenSuccessiveFrames = + base::Seconds(2); // Calculates and returns the color bit depth based on the size of the given // `color_palette`. The color bit depth is the least number of bits needed to be @@ -207,12 +216,31 @@ return bitmap; } -OctreeColorQuantizer CreateQuantizer(const RgbVideoFrame& rgb_video_frame) { - return OctreeColorQuantizer(rgb_video_frame); +QuantizerPalettePair CreateQuantizer(const RgbVideoFrame& rgb_video_frame) { + return QuantizerPalettePair(OctreeColorQuantizer(rgb_video_frame)); } } // namespace +// ----------------------------------------------------------------------------- +// QuantizerPalettePair: + +QuantizerPalettePair::QuantizerPalettePair(OctreeColorQuantizer&& new_quantizer) + : quantizer(std::move(new_quantizer)) { + color_palette.reserve(kMaxNumberOfColorsInPalette); + quantizer.ExtractColorPalette(color_palette); +} + +QuantizerPalettePair::QuantizerPalettePair(QuantizerPalettePair&&) = default; + +QuantizerPalettePair& QuantizerPalettePair::operator=(QuantizerPalettePair&&) = + default; + +QuantizerPalettePair::~QuantizerPalettePair() = default; + +// ----------------------------------------------------------------------------- +// GifEncoder: + // static base::SequenceBound<GifEncoder> GifEncoder::Create( scoped_refptr<base::SequencedTaskRunner> blocking_task_runner, @@ -302,12 +330,18 @@ // sequence. We don't want the in-flight frame pool in // `FrameSinkVideoCapturerImpl` to fill up because we're not returning the // frames quick enough. + // Note that we don't allow the duration between any two successive frames to + // exceed `kMaxDurationBetweenSuccessiveFrames` without rebuilding the color + // palette as it may be very stale. if (color_palette_.empty()) { - SetQuantizer(OctreeColorQuantizer(rgb_video_frame)); - color_quantizer_.ExtractPixelColorIndices(rgb_video_frame, + SetQuantizer(CreateQuantizer(rgb_video_frame)); + color_quantizer_.ExtractPixelColorIndices(rgb_video_frame, color_palette_, pixel_color_indices_); } else { - if (frame_count_ % kMinNumberOfFramesBetweenPaletteRebuilds == 0) { + if (frame_count_ % kMinNumberOfFramesBetweenPaletteRebuilds == 0 || + (!last_frame_time_.is_null() && + frame_time - last_frame_time_ >= + kMaxDurationBetweenSuccessiveFrames)) { // Note that we have to clone the `rgb_video_frame` as the one we have // here will be disposed once this function returns. color_palette_task_runner_->PostTaskAndReplyWithResult( @@ -317,7 +351,7 @@ } // Rebuild the pixel color indices using the existing palette. - color_quantizer_.ExtractPixelColorIndices(rgb_video_frame, + color_quantizer_.ExtractPixelColorIndices(rgb_video_frame, color_palette_, pixel_color_indices_); } @@ -483,9 +517,9 @@ } } -void GifEncoder::SetQuantizer(OctreeColorQuantizer&& new_color_quantizer) { - color_quantizer_ = std::move(new_color_quantizer); - color_quantizer_.ExtractColorPalette(color_palette_); +void GifEncoder::SetQuantizer(QuantizerPalettePair&& quantizer_pair) { + color_quantizer_ = std::move(quantizer_pair.quantizer); + color_palette_ = std::move(quantizer_pair.color_palette); } } // namespace recording
diff --git a/chromeos/ash/services/recording/gif_encoder.h b/chromeos/ash/services/recording/gif_encoder.h index e6aee6b..b37727e 100644 --- a/chromeos/ash/services/recording/gif_encoder.h +++ b/chromeos/ash/services/recording/gif_encoder.h
@@ -21,6 +21,18 @@ class RgbVideoFrame; +// Defines a pair of an `OctreeColorQuantizer` and the extracted +// `color_palette` from it. +struct QuantizerPalettePair { + explicit QuantizerPalettePair(OctreeColorQuantizer&& new_quantizer); + QuantizerPalettePair(QuantizerPalettePair&&); + QuantizerPalettePair& operator=(QuantizerPalettePair&&); + ~QuantizerPalettePair(); + + OctreeColorQuantizer quantizer; + ColorTable color_palette; +}; + // Encapsulates encoding video frames into an animated GIF and writes the // encoded output to a file that it creates at the given `gif_file_path`. An // instance of this object can only be interacted with via a @@ -112,9 +124,9 @@ // implementation. void WriteColorPalette(uint8_t color_bit_depth); - // Moves the given `new_color_quantizer` into `color_quantizer_` and extracts - // a new color palette from it into `color_palette_`. - void SetQuantizer(OctreeColorQuantizer&& new_color_quantizer); + // Moves the quantizer and its extracted color palette from the given + // `quantizer_pair` into `color_quantizer_` and `color_palette_` respectively. + void SetQuantizer(QuantizerPalettePair&& quantizer_pair); // The thread pool task runner on which the color palettes are built every // `kMinNumberOfFramesBetweenPaletteRebuilds` frames except for the very first
diff --git a/chromeos/ash/services/recording/octree_color_quantizer.cc b/chromeos/ash/services/recording/octree_color_quantizer.cc index 90778525..1bb7334 100644 --- a/chromeos/ash/services/recording/octree_color_quantizer.cc +++ b/chromeos/ash/services/recording/octree_color_quantizer.cc
@@ -64,6 +64,44 @@ ForEachPixelColor(const_cast<RgbVideoFrame&>(rgb_video_frame), f); } +// Defines a color error per each color channel (R, G, and B), which is the +// difference between the original color of a pixel, and the quantized +// (predicted) color that we get from the Octree. +// +// We use this type instead of `RgbColor` (whose components are `uint8_t`s), as +// we need the components to be represented as `int`s, since the difference can +// be negative, and when scaled by the Floyd-Steinberg factors, the values can +// exceed the maximum of 255. +struct ErrorVector { + inline bool IsZero() const { return r == 0 && g == 0 && b == 0; } + + int r; + int g; + int b; +}; + +// Given the `original_color` of a pixel, and its `quantized_color`, returns the +// color error vector, which is the difference between the two. +ErrorVector GetErrorVector(const RgbColor& original_color, + const RgbColor& quantized_color) { + return ErrorVector(original_color.r - quantized_color.r, + original_color.g - quantized_color.g, + original_color.b - quantized_color.b); +} + +// Diffuses the given color `error_vector` over the given `color` by a factor +// equal to `factor / 16`. This means that each color component of +// `error_vector` will be multiplied by a `factor / 16` and added to the +// corresponding color component of `color`. The resulting `RgbColor` is +// returned. +RgbColor DiffuseErrorOnColor(const ErrorVector& error_vector, + const RgbColor& color, + int factor) { + return RgbColor(std::clamp(error_vector.r * factor / 16 + color.r, 0, 255), + std::clamp(error_vector.g * factor / 16 + color.g, 0, 255), + std::clamp(error_vector.b * factor / 16 + color.b, 0, 255)); +} + } // namespace // ----------------------------------------------------------------------------- @@ -101,20 +139,83 @@ Node* curr = leaf_nodes_head_; while (curr != nullptr) { out_color_palette.push_back(curr->GetColor()); - curr->palette_index_ = color_palette_index; + curr->palette_index_ = color_palette_index++; curr = curr->next_; - ++color_palette_index; } } void OctreeColorQuantizer::ExtractPixelColorIndices( - const RgbVideoFrame& rgb_video_frame, + RgbVideoFrame& rgb_video_frame, + const ColorTable& color_palette, ColorIndices& out_pixel_color_indices) const { size_t pixel_index = 0; + const int width = rgb_video_frame.width(); + const int height = rgb_video_frame.height(); ForEachPixelColor(rgb_video_frame, [&](const RgbColor& color) { const auto color_index = FindColorIndex(color); out_pixel_color_indices[pixel_index] = color_index; + + const int row = pixel_index / width; + const int column = pixel_index % width; + ++pixel_index; + + // The below implements the "Floyd-Steinberg" dithering algorithm (see + // https://en.wikipedia.org/wiki/Floyd%E2%80%93Steinberg_dithering). It + // works by diffusing (i.e. distributing) the color error of a pixel over + // neighboring pixels by the following factors: + // + // ----------------+----------+---------------+----------+------------------ + // | | current pixel | 7 / 16 | + // ----------------+----------+---------------+----------+------------------ + // | 3 / 16 | 5 / 16 | 1 / 16 | + // ----------------+----------+---------------+----------+------------------ + // + // It actually modifies the colors of the pixels that haven't been processed + // yet in the `rgb_video_frame` which will affect their quantized color when + // they get processed in the upcoming iterations. This results in the + // dithering of the quantized image. + const ErrorVector error_vector = + GetErrorVector(/*original_color=*/color, + /*quantized_color=*/color_palette[color_index]); + if (error_vector.IsZero()) { + return; + } + + const auto next_column = column + 1; + const auto next_row = row + 1; + const bool is_next_row_valid = next_row < height; + + if (next_column < width) { + // Same row, next column. Add error with a factor of `7 / 16`. + auto& next_col_color = rgb_video_frame.pixel_color(row, next_column); + next_col_color = + DiffuseErrorOnColor(error_vector, next_col_color, /*factor=*/7); + + if (is_next_row_valid) { + // Next row, next column. Add error with a factor of `1 / 16`. + auto& next_row_col_color = + rgb_video_frame.pixel_color(next_row, next_column); + next_row_col_color = + DiffuseErrorOnColor(error_vector, next_row_col_color, /*factor=*/1); + } + } + + if (is_next_row_valid) { + // Next row, same column. Add error with a factor of `5 / 16`. + auto& next_row_color = rgb_video_frame.pixel_color(next_row, column); + next_row_color = + DiffuseErrorOnColor(error_vector, next_row_color, /*factor=*/5); + + // Next row, previous column. Add error with a factor of `3 / 16`. + const auto prev_column = column - 1; + if (prev_column >= 0) { + auto& next_row_prev_col_color = + rgb_video_frame.pixel_color(next_row, prev_column); + next_row_prev_col_color = DiffuseErrorOnColor( + error_vector, next_row_prev_col_color, /*factor=*/3); + } + } }); }
diff --git a/chromeos/ash/services/recording/octree_color_quantizer.h b/chromeos/ash/services/recording/octree_color_quantizer.h index b4f47cc..395d9a9 100644 --- a/chromeos/ash/services/recording/octree_color_quantizer.h +++ b/chromeos/ash/services/recording/octree_color_quantizer.h
@@ -47,9 +47,16 @@ // closest colors for each pixel in the given `rgb_video_frame` from the // quantized color palette extracted by calling `ExtractColorPalette()` above. // This means `ExtractColorPalette()` must be called once before calling this - // for every received video frame (provided that the same color palette is + // for every received video frame (provided that the same `color_palette` is // still desired to be reused). - void ExtractPixelColorIndices(const RgbVideoFrame& rgb_video_frame, + // This also implements the Floyd-Steinberg dithering, meaning that the + // resulting color indices in `out_pixel_color_indices` will be of a + // quantized and dithered image of the given `rgb_video_frame` using the given + // `color_palette`. The given `rgb_video_frame` will be modified in the + // process of dithering to diffuse the color errors in each pixel over the + // colors of neighboring pixels (See implementation for details). + void ExtractPixelColorIndices(RgbVideoFrame& rgb_video_frame, + const ColorTable& color_palette, ColorIndices& out_pixel_color_indices) const; private:
diff --git a/chromeos/profiles/atom.afdo.newest.txt b/chromeos/profiles/atom.afdo.newest.txt index c917380..45f29b8 100644 --- a/chromeos/profiles/atom.afdo.newest.txt +++ b/chromeos/profiles/atom.afdo.newest.txt
@@ -1 +1 @@ -chromeos-chrome-amd64-atom-121-6154.0-1701689968-benchmark-122.0.6171.0-r1-redacted.afdo.xz +chromeos-chrome-amd64-atom-121-6167.9-1702295304-benchmark-122.0.6179.0-r1-redacted.afdo.xz
diff --git a/clank b/clank index 3d55fc4..b570761 160000 --- a/clank +++ b/clank
@@ -1 +1 @@ -Subproject commit 3d55fc4f1877714a5aefaf5ca58e533d53b61244 +Subproject commit b570761166a159d8217203052bdfc29ec90ebef9
diff --git a/components/autofill/content/renderer/autofill_agent.cc b/components/autofill/content/renderer/autofill_agent.cc index 34d7225..fb54f3dd 100644 --- a/components/autofill/content/renderer/autofill_agent.cc +++ b/components/autofill/content/renderer/autofill_agent.cc
@@ -540,6 +540,25 @@ form_tracker_->TextFieldDidChange(element); } +void AutofillAgent::ContentEditableDidChange(const WebElement& element) { + DCHECK(MaybeWasOwnedByFrame(element, unsafe_render_frame())); + if (!base::FeatureList::IsEnabled( + features::kAutofillContentEditableChangeEvents) || + !base::FeatureList::IsEnabled(features::kAutofillContentEditables) || + !base::FeatureList::IsEnabled(features::kAutofillTextAreaChangeEvents)) { + return; + } + // TODO(crbug.com/1494479): Add throttling to avoid sending this event for + // rapid changes. + if (std::optional<FormData> form = FindFormForContentEditable(element)) { + const FormFieldData& field = form->fields.front(); + if (auto* autofill_driver = unsafe_autofill_driver()) { + autofill_driver->TextFieldDidChange(*form, field, field.bounds, + AutofillTickClock::NowTicks()); + } + } +} + void AutofillAgent::OnTextFieldDidChange(const WebFormControlElement& element) { DCHECK(MaybeWasOwnedByFrame(element, unsafe_render_frame())); // TODO(crbug.com/1494479): Add throttling to avoid sending this event for
diff --git a/components/autofill/content/renderer/autofill_agent.h b/components/autofill/content/renderer/autofill_agent.h index 38da23e..eccb3ea 100644 --- a/components/autofill/content/renderer/autofill_agent.h +++ b/components/autofill/content/renderer/autofill_agent.h
@@ -272,6 +272,7 @@ // blink::WebAutofillClient: void TextFieldDidEndEditing(const blink::WebInputElement& element) override; void TextFieldDidChange(const blink::WebFormControlElement& element) override; + void ContentEditableDidChange(const blink::WebElement& element) override; void TextFieldDidReceiveKeyDown( const blink::WebInputElement& element, const blink::WebKeyboardEvent& event) override;
diff --git a/components/autofill/content/renderer/form_autofill_util.cc b/components/autofill/content/renderer/form_autofill_util.cc index 0625be6..3697e1b 100644 --- a/components/autofill/content/renderer/form_autofill_util.cc +++ b/components/autofill/content/renderer/form_autofill_util.cc
@@ -2333,13 +2333,14 @@ } field.aria_label = GetAriaLabel(document, content_editable); field.aria_description = GetAriaDescription(document, content_editable); - // TextContent() includes hidden elements and does not add linebreaks. If this - // is not sufficient in the future, consider calling HTMLElement::innerText(), - // which returns the text "as rendered" (i.e., it inserts whitespace at the - // right places and it ignores "display:none" subtrees), but is significantly - // more expensive because it triggers a layout. + // TextContentAbridged() includes hidden elements and does not add linebreaks. + // If this is not sufficient in the future, consider calling + // HTMLElement::innerText(), which returns the text "as rendered" (i.e., it + // inserts whitespace at the right places and it ignores "display:none" + // subtrees), but is significantly more expensive because it triggers a layout. field.value = - content_editable.TextContent().Utf16().substr(0, kMaxStringLength); + content_editable.TextContentAbridged(kMaxStringLength).Utf16(); + DCHECK_LE(field.value.length(), kMaxStringLength); field.selected_text = content_editable.SelectedText().Utf16().substr(0, kMaxSelectedTextLength); return form;
diff --git a/components/autofill/content/renderer/form_autofill_util_browsertest.cc b/components/autofill/content/renderer/form_autofill_util_browsertest.cc index 0072756..2de5273 100644 --- a/components/autofill/content/renderer/form_autofill_util_browsertest.cc +++ b/components/autofill/content/renderer/form_autofill_util_browsertest.cc
@@ -2082,6 +2082,52 @@ EXPECT_EQ(field.value, u"\n This is the textContent!\n "); } +TEST_F(FormAutofillUtilsTest, FindFormForContentEditableAbridgedSuccess) { + // HTML with 1500 characters of pi in the contenteditable div + LoadHTML( + R"(<body> + <div id=my-id + name=my-name + class=my-class + autocomplete=given-name + contenteditable>3.1415926535897932384626433832795028841971693993751058209749445923078164062862089986280348253421170679821480865132823066470938446095505822317253594081284811174502841027019385211055596446229489549303819644288109756659334461284756482337867831652712019091456485669234603486104543266482133936072602491412737245870066063155881748815209209628292540917153643678925903600113305305488204665213841469519415116094330572703657595919530921861173819326117931051185480744623799627495673518857527248912279381830119491298336733624406566430860213949463952247371907021798609437027705392171762931767523846748184676694051320005681271452635608277857713427577896091736371787214684409012249534301465495853710507922796892589235420199561121290219608640344181598136297747713099605187072113499999983729780499510597317328160963185950244594553469083026425223082533446850352619311881710100031378387528865875332083814206171776691473035982534904287554687311595628638823537875937519577818577805321712268066130019278766111959092164201989380952572010654858632788659361533818279682303019520353018529689957736225994138912497217752834791315155748572424541506959508295331168617278558890750983817546374649393192550604009277016711390098488240128583616035637076601047101819429555961989467678374494482553797747268471040475346462080466842590694912933136770289891521047521620569660240580381501935112533824300355876402474964732639141992726042699227967823547816360093417216412199245863150302861829745557067498385054945885869269956909272107975093029</div> + </body>)"); + WebElement content_editable = + GetMainFrame()->GetDocument().GetElementById("my-id"); + ASSERT_FALSE(content_editable.IsNull()); + std::optional<FormData> form = FindFormForContentEditable(content_editable); + ASSERT_EQ(form->fields.size(), 1u); + const FormFieldData& field = form->fields[0]; + EXPECT_TRUE(form->unique_renderer_id); + EXPECT_EQ(*form->unique_renderer_id, *field.unique_renderer_id); + EXPECT_EQ(form->unique_renderer_id, field.host_form_id); + EXPECT_EQ(field.parsed_autocomplete->field_type, HtmlFieldType::kGivenName); + EXPECT_EQ(field.name, u"my-id"); + EXPECT_EQ(field.id_attribute, u"my-id"); + EXPECT_EQ(field.name_attribute, u"my-name"); + EXPECT_EQ(field.css_classes, u"my-class"); + // Only extract 1024 characters from the div. + EXPECT_EQ(field.value.length(), 1024u); + EXPECT_EQ( + field.value, + u"3." + u"14159265358979323846264338327950288419716939937510582097494459230781640" + u"62862089986280348253421170679821480865132823066470938446095505822317253" + u"59408128481117450284102701938521105559644622948954930381964428810975665" + u"93344612847564823378678316527120190914564856692346034861045432664821339" + u"36072602491412737245870066063155881748815209209628292540917153643678925" + u"90360011330530548820466521384146951941511609433057270365759591953092186" + u"11738193261179310511854807446237996274956735188575272489122793818301194" + u"91298336733624406566430860213949463952247371907021798609437027705392171" + u"76293176752384674818467669405132000568127145263560827785771342757789609" + u"17363717872146844090122495343014654958537105079227968925892354201995611" + u"21290219608640344181598136297747713099605187072113499999983729780499510" + u"59731732816096318595024459455346908302642522308253344685035261931188171" + u"01000313783875288658753320838142061717766914730359825349042875546873115" + u"95628638823537875937519577818577805321712268066130019278766111959092164" + u"2019893809525720106548586327"); +} + TEST_F(FormAutofillUtilsTest, FindFormForContentEditableFailures) { LoadHTML( R"(<body>
diff --git a/components/autofill/core/common/autofill_features.cc b/components/autofill/core/common/autofill_features.cc index 6f07078..8e27f23 100644 --- a/components/autofill/core/common/autofill_features.cc +++ b/components/autofill/core/common/autofill_features.cc
@@ -618,11 +618,17 @@ base::FEATURE_DISABLED_BY_DEFAULT); // Sends text change events for textarea elements. When this is off, only input -// elements send text change events. +// elements and maybe contenteditable elements send text change events. BASE_FEATURE(kAutofillTextAreaChangeEvents, "AutofillTextAreaChangeEvents", base::FEATURE_DISABLED_BY_DEFAULT); +// Sends text change events for contenteditable elements. When this is off, +// only input elements and maybe textarea elements send text change events. +BASE_FEATURE(kAutofillContentEditableChangeEvents, + "AutofillContentEditableChangeEvents", + base::FEATURE_DISABLED_BY_DEFAULT); + // When enabled, on form submit, observations for every used profile are // collected into the profile's `token_quality()`. // TODO(crbug.com/1453650): Remove when launched.
diff --git a/components/autofill/core/common/autofill_features.h b/components/autofill/core/common/autofill_features.h index 20f791fa..08f4910 100644 --- a/components/autofill/core/common/autofill_features.h +++ b/components/autofill/core/common/autofill_features.h
@@ -206,6 +206,8 @@ COMPONENT_EXPORT(AUTOFILL) BASE_DECLARE_FEATURE(kAutofillTextAreaChangeEvents); COMPONENT_EXPORT(AUTOFILL) +BASE_DECLARE_FEATURE(kAutofillContentEditableChangeEvents); +COMPONENT_EXPORT(AUTOFILL) BASE_DECLARE_FEATURE(kAutofillTrackProfileTokenQuality); COMPONENT_EXPORT(AUTOFILL) BASE_DECLARE_FEATURE(kAutofillUseImprovedLabelDisambiguation);
diff --git a/components/certificate_transparency/chrome_ct_policy_enforcer.cc b/components/certificate_transparency/chrome_ct_policy_enforcer.cc index 0216883..bd75165d 100644 --- a/components/certificate_transparency/chrome_ct_policy_enforcer.cc +++ b/components/certificate_transparency/chrome_ct_policy_enforcer.cc
@@ -83,9 +83,19 @@ base::Time log_list_date, std::vector<std::pair<std::string, base::Time>> disqualified_logs, std::map<std::string, OperatorHistoryEntry> log_operator_history) + : ChromeCTPolicyEnforcer(log_list_date, + std::move(disqualified_logs), + std::move(log_operator_history), + base::DefaultClock::GetInstance()) {} + +ChromeCTPolicyEnforcer::ChromeCTPolicyEnforcer( + base::Time log_list_date, + std::vector<std::pair<std::string, base::Time>> disqualified_logs, + std::map<std::string, OperatorHistoryEntry> log_operator_history, + const base::Clock* clock) : disqualified_logs_(std::move(disqualified_logs)), log_operator_history_(std::move(log_operator_history)), - clock_(base::DefaultClock::GetInstance()), + clock_(clock), log_list_date_(log_list_date) {} ChromeCTPolicyEnforcer::~ChromeCTPolicyEnforcer() {} @@ -93,7 +103,7 @@ CTPolicyCompliance ChromeCTPolicyEnforcer::CheckCompliance( net::X509Certificate* cert, const net::ct::SCTList& verified_scts, - const net::NetLogWithSource& net_log) { + const net::NetLogWithSource& net_log) const { // If the build is not timely, no certificate is considered compliant // with CT policy. The reasoning is that, for example, a log might // have been pulled and is no longer considered valid; thus, a client @@ -122,10 +132,6 @@ log_list_date_ = update_time; disqualified_logs_ = std::move(disqualified_logs); log_operator_history_ = std::move(log_operator_history); - - if (disqualified_log_for_testing_.has_value()) { - disqualified_log_for_testing_ = std::nullopt; - } } bool ChromeCTPolicyEnforcer::IsLogDisqualified( @@ -133,12 +139,6 @@ base::Time* disqualification_date) const { CHECK_EQ(log_id.size(), crypto::kSHA256Length); - if (disqualified_log_for_testing_.has_value() && - log_id == disqualified_log_for_testing_.value().first) { - *disqualification_date = disqualified_log_for_testing_.value().second; - return *disqualification_date < base::Time::Now(); - } - auto p = std::lower_bound( std::begin(disqualified_logs_), std::end(disqualified_logs_), log_id, [](const auto& a, std::string_view b) { return a.first < b; });
diff --git a/components/certificate_transparency/chrome_ct_policy_enforcer.h b/components/certificate_transparency/chrome_ct_policy_enforcer.h index 992caeb..44ba99d 100644 --- a/components/certificate_transparency/chrome_ct_policy_enforcer.h +++ b/components/certificate_transparency/chrome_ct_policy_enforcer.h
@@ -54,13 +54,18 @@ base::Time log_list_date, std::vector<std::pair<std::string, base::Time>> disqualified_logs, std::map<std::string, OperatorHistoryEntry> log_operator_history); + ChromeCTPolicyEnforcer( + base::Time log_list_date, + std::vector<std::pair<std::string, base::Time>> disqualified_logs, + std::map<std::string, OperatorHistoryEntry> log_operator_history, + const base::Clock* clock); ~ChromeCTPolicyEnforcer() override; net::ct::CTPolicyCompliance CheckCompliance( net::X509Certificate* cert, const net::ct::SCTList& verified_scts, - const net::NetLogWithSource& net_log) override; + const net::NetLogWithSource& net_log) const override; // Updates the list of logs used for compliance checks. |disqualified_logs| // is a map of log ID to disqualification date. @@ -69,8 +74,6 @@ std::vector<std::pair<std::string, base::Time>> disqualified_logs, std::map<std::string, OperatorHistoryEntry> log_operator_history); - void SetClockForTesting(const base::Clock* clock) { clock_ = clock; } - // TODO(https://crbug.com/999240): These are exposed to allow end-to-end // testing by higher layers (i.e. that the ChromeCTPolicyEnforcer is // correctly constructed). When either this issue or https://crbug.com/848277 @@ -90,16 +93,6 @@ ct_log_list_always_timely_for_testing_ = always_timely; } - void SetOperatorHistoryForTesting( - std::map<std::string, OperatorHistoryEntry> log_operator_history) { - log_operator_history_ = std::move(log_operator_history); - } - - void SetDisqualifiedLogForTesting( - const std::pair<std::string, base::Time>& disqualified_log) { - disqualified_log_for_testing_ = disqualified_log; - } - private: FRIEND_TEST_ALL_PREFIXES(ChromeCTPolicyEnforcerTest, IsLogDisqualifiedTimestamp); @@ -128,7 +121,7 @@ std::map<std::string, OperatorHistoryEntry> log_operator_history_; - raw_ptr<const base::Clock> clock_; + const raw_ptr<const base::Clock> clock_; // The time at which |disqualified_logs_| and |log_operator_history_| were // generated. @@ -137,12 +130,6 @@ // If set, the CT log list will be considered timely regardless of its last // update time. bool ct_log_list_always_timely_for_testing_ = false; - - // If set, this log ID will be considered a disqualified log, effective at the - // specified time. - // Calling UpdateCTLogList clears this value if set. - std::optional<std::pair<std::string, base::Time>> - disqualified_log_for_testing_; }; } // namespace certificate_transparency
diff --git a/components/certificate_transparency/chrome_ct_policy_enforcer_unittest.cc b/components/certificate_transparency/chrome_ct_policy_enforcer_unittest.cc index c5434418e..19d70933 100644 --- a/components/certificate_transparency/chrome_ct_policy_enforcer_unittest.cc +++ b/components/certificate_transparency/chrome_ct_policy_enforcer_unittest.cc
@@ -49,11 +49,7 @@ class ChromeCTPolicyEnforcerTest : public ::testing::Test { public: void SetUp() override { - auto enforcer = std::make_unique<ChromeCTPolicyEnforcer>( - base::Time::Now(), GetDisqualifiedLogs(), - std::map<std::string, OperatorHistoryEntry>()); - enforcer->SetClockForTesting(&clock_); - policy_enforcer_ = std::move(enforcer); + test_now_ = base::Time::Now(); std::string der_test_cert(net::ct::GetDerEncodedX509Cert()); chain_ = X509Certificate::CreateFromBytes( @@ -61,7 +57,15 @@ ASSERT_TRUE(chain_.get()); test_log_id_ = std::string(kTestLogID, crypto::kSHA256Length); another_log_id_.assign(crypto::kSHA256Length, 1); - clock_.SetNow(base::Time::Now()); + clock_.SetNow(test_now_); + } + + std::unique_ptr<ChromeCTPolicyEnforcer> MakeChromeCTPolicyEnforcer( + std::vector<std::pair<std::string, base::Time>> disqualified_logs, + std::map<std::string, OperatorHistoryEntry> log_operator_history) { + return std::make_unique<ChromeCTPolicyEnforcer>( + test_now_, std::move(disqualified_logs), + std::move(log_operator_history), &clock_); } void FillListWithSCTsOfOrigin( @@ -85,9 +89,11 @@ } } - void AddDisqualifiedLogSCT(SignedCertificateTimestamp::Origin desired_origin, - bool timestamp_after_disqualification_date, - SCTList* verified_scts) { + void AddDisqualifiedLogSCT( + SignedCertificateTimestamp::Origin desired_origin, + bool timestamp_after_disqualification_date, + std::pair<std::string, base::Time>* disqualified_log, + SCTList* verified_scts) { static const char kTestRetiredLogID[] = "\xcd\xb5\x17\x9b\x7f\xc1\xc0\x46\xfe\xea\x31\x13\x6a\x3f\x8f\x00\x2e" "\x61\x82\xfa\xf8\x89\x6f\xec\xc8\xb2\xf5\xb5\xab\x60\x49\x00"; @@ -97,8 +103,8 @@ ASSERT_TRUE(base::Time::FromUTCExploded({2022, 4, 0, 16, 0, 0, 0, 0}, &retirement_time)); - policy_enforcer_->SetDisqualifiedLogForTesting( - std::make_pair(std::string(kTestRetiredLogID, 32), retirement_time)); + *disqualified_log = + std::make_pair(std::string(kTestRetiredLogID, 32), retirement_time); scoped_refptr<SignedCertificateTimestamp> sct( new SignedCertificateTimestamp()); @@ -142,8 +148,8 @@ } protected: + base::Time test_now_; base::SimpleTestClock clock_; - std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer_; scoped_refptr<X509Certificate> chain_; std::string test_log_id_; std::string another_log_id_; @@ -152,6 +158,7 @@ TEST_F(ChromeCTPolicyEnforcerTest, DoesNotConformToCTPolicyNotEnoughFreshSCTs) { SCTList scts; + std::pair<std::string, base::Time> disqualified_log; std::map<std::string, OperatorHistoryEntry> operator_history; // The results should be the same before and after disqualification, @@ -164,12 +171,13 @@ FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION, 1, &scts); AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION, - false, &scts); + false, &disqualified_log, &scts); FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); // Two SCTs from TLS, one of them from a disqualified log after the // disqualification time. @@ -178,41 +186,47 @@ FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION, 1, &scts); AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION, - true, &scts); + true, &disqualified_log, &scts); FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); // Two embedded SCTs, one of them from a disqualified log before the // disqualification time. scts.clear(); operator_history.clear(); FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_EMBEDDED, 1, &scts); - AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, false, &scts); + AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, false, + &disqualified_log, &scts); FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); // Two embedded SCTs, one of them from a disqualified log after the // disqualification time. scts.clear(); operator_history.clear(); FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_EMBEDDED, 1, &scts); - AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, true, &scts); + AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, true, + &disqualified_log, &scts); FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, ConformsToCTPolicyWithMixOfEmbeddedAndNonEmbedded) { SCTList scts; + std::pair<std::string, base::Time> disqualified_log; std::map<std::string, OperatorHistoryEntry> operator_history; // One SCT from TLS, one Embedded SCT from before disqualification time. @@ -220,12 +234,14 @@ operator_history.clear(); FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION, 1, &scts); - AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, false, &scts); + AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, false, + &disqualified_log, &scts); FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); // One SCT from TLS, one Embedded SCT from after disqualification time. // The embedded SCT is still counted towards the diversity requirement even @@ -234,12 +250,14 @@ operator_history.clear(); FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION, 1, &scts); - AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, true, &scts); + AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, true, + &disqualified_log, &scts); FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, ConformsToCTPolicyWithNonEmbeddedSCTs) { @@ -249,11 +267,13 @@ std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, EnforcementDisabledByBinaryAge) { @@ -263,17 +283,19 @@ std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); clock_.Advance(base::Days(71)); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, ConformsToCTPolicyWithEmbeddedSCTs) { @@ -283,11 +305,13 @@ std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, @@ -309,11 +333,13 @@ std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, ConformsToCTPolicyWithPooledEmbeddedSCTs) { @@ -334,11 +360,13 @@ std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, DoesNotConformToCTPolicyNotEnoughSCTs) { @@ -348,11 +376,13 @@ std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, @@ -364,16 +394,21 @@ desired_log_ids, &scts); FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_EMBEDDED, 1, std::vector<std::string>(), &scts); - AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, false, &scts); + std::pair<std::string, base::Time> disqualified_log; + AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, + /*timestamp_after_disqualification_date=*/false, + &disqualified_log, &scts); std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); + + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); // |chain_| is valid for 10 years - over 180 days - so requires 3 SCTs. - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, @@ -381,22 +416,30 @@ SCTList scts; // Add required - 1 valid SCTs. FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_EMBEDDED, 2, &scts); - AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, true, &scts); + std::pair<std::string, base::Time> disqualified_log; + AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, + /*timestamp_after_disqualification_date=*/true, + &disqualified_log, &scts); std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); + + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); // |chain_| is valid for 10 years - over 180 days - so requires 3 SCTs. - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, DoesNotConformWithIssuanceDateAfterDisqualificationDate) { SCTList scts; - AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, true, &scts); + std::pair<std::string, base::Time> disqualified_log; + AddDisqualifiedLogSCT(SignedCertificateTimestamp::SCT_EMBEDDED, + /*timestamp_after_disqualification_date=*/true, + &disqualified_log, &scts); // Add required - 1 valid SCTs. FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_EMBEDDED, 2, &scts); // Make sure all SCTs are after the disqualification date. @@ -405,15 +448,21 @@ std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); + + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer({disqualified_log}, operator_history); // |chain_| is valid for 10 years - over 180 days - so requires 3 SCTs. - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, UpdateCTLogList) { + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), + std::map<std::string, OperatorHistoryEntry>()); + SCTList scts; FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION, 2, &scts); @@ -426,26 +475,30 @@ operator_history[sct->log_id] = entry; } - policy_enforcer_->UpdateCTLogList(base::Time::Now(), disqualified_logs, - operator_history); + policy_enforcer->UpdateCTLogList(base::Time::Now(), disqualified_logs, + operator_history); // The check should fail since the logs all have the same operator. - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); // Update the list again, this time including diverse operators. FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->UpdateCTLogList(base::Time::Now(), disqualified_logs, - operator_history); + policy_enforcer->UpdateCTLogList(base::Time::Now(), disqualified_logs, + operator_history); // The check should now succeed. - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, TimestampUpdates) { + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), + std::map<std::string, OperatorHistoryEntry>()); + SCTList scts; FillListWithSCTsOfOrigin(SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION, 1, &scts); @@ -455,23 +508,23 @@ std::map<std::string, OperatorHistoryEntry> log_operator_history; FillOperatorHistoryWithDiverseOperators(scts, &log_operator_history); - policy_enforcer_->UpdateCTLogList(base::Time::Now() - base::Days(71), - disqualified_logs, log_operator_history); + policy_enforcer->UpdateCTLogList(base::Time::Now() - base::Days(71), + disqualified_logs, log_operator_history); // The check should return build not timely even though there are not enough // SCTs. - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); // Update the last update time value again, this time with a recent time. - policy_enforcer_->UpdateCTLogList(base::Time::Now(), disqualified_logs, - log_operator_history); + policy_enforcer->UpdateCTLogList(base::Time::Now(), disqualified_logs, + log_operator_history); // The check should now fail - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, IsLogDisqualifiedTimestamp) { @@ -486,15 +539,16 @@ base::Time future_disqualification = base::Time::Now() + base::Hours(1); disqualified_logs.emplace_back(kModifiedTestLogID, future_disqualification); disqualified_logs.emplace_back(kTestLogID, past_disqualification); - policy_enforcer_->UpdateCTLogList(base::Time::Now(), disqualified_logs, - log_operator_history); + + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(disqualified_logs, log_operator_history); base::Time disqualification_time; EXPECT_TRUE( - policy_enforcer_->IsLogDisqualified(kTestLogID, &disqualification_time)); + policy_enforcer->IsLogDisqualified(kTestLogID, &disqualification_time)); EXPECT_EQ(disqualification_time, past_disqualification); - EXPECT_FALSE(policy_enforcer_->IsLogDisqualified(kModifiedTestLogID, - &disqualification_time)); + EXPECT_FALSE(policy_enforcer->IsLogDisqualified(kModifiedTestLogID, + &disqualification_time)); EXPECT_EQ(disqualification_time, future_disqualification); } @@ -508,13 +562,14 @@ std::map<std::string, OperatorHistoryEntry> log_operator_history; disqualified_logs.emplace_back(kModifiedTestLogID, base::Time::Now() - base::Days(1)); - policy_enforcer_->UpdateCTLogList(base::Time::Now(), disqualified_logs, - log_operator_history); + + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(disqualified_logs, log_operator_history); base::Time unused; // IsLogDisqualified should return false for a log that is not in the // disqualified list. - EXPECT_FALSE(policy_enforcer_->IsLogDisqualified(kTestLogID, &unused)); + EXPECT_FALSE(policy_enforcer->IsLogDisqualified(kTestLogID, &unused)); } TEST_F(ChromeCTPolicyEnforcerTest, @@ -538,13 +593,13 @@ } std::sort(std::begin(disqualified_logs), std::end(disqualified_logs)); - policy_enforcer_->UpdateCTLogList(base::Time::Now(), disqualified_logs, - log_operator_history); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(disqualified_logs, log_operator_history); // SCTs should comply since retirement date is in the future. - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, @@ -569,13 +624,13 @@ FillOperatorHistoryWithDiverseOperators(scts, &log_operator_history); - policy_enforcer_->UpdateCTLogList(base::Time::Now(), disqualified_logs, - log_operator_history); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(disqualified_logs, log_operator_history); // SCTs should not comply since retirement date is in the past. - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, UpdatedSCTRequirements) { @@ -637,7 +692,10 @@ // Add different operators to the logs so the SCTs comply with operator // diversity. FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); + + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + CTPolicyCompliance expected; if (j == scts_required) { // If the scts provided are as many as are required, the cert should be @@ -650,8 +708,8 @@ // In any other case, the 'not enough' check should trip. expected = CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS; } - EXPECT_EQ(expected, policy_enforcer_->CheckCompliance(cert.get(), scts, - NetLogWithSource())) + EXPECT_EQ(expected, policy_enforcer->CheckCompliance(cert.get(), scts, + NetLogWithSource())) << " for: " << (validity_end - validity_start).InDays() << " and " << scts_required << " scts=" << scts.size() << " j=" << j; } @@ -669,11 +727,13 @@ entry.current_operator_ = "Operator"; operator_history[sct->log_id] = entry; } - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, ConformsToCTPolicyDifferentOperators) { @@ -682,11 +742,13 @@ 2, std::vector<std::string>(), &scts); std::map<std::string, OperatorHistoryEntry> operator_history; FillOperatorHistoryWithDiverseOperators(scts, &operator_history); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, ConformsToPolicyDueToOperatorSwitch) { @@ -704,11 +766,13 @@ // end time after the SCT timestamp. operator_history[scts[1]->log_id].previous_operators_.emplace_back( "Different Operator", scts[1]->timestamp + base::Seconds(1)); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, DoesNotConformToPolicyDueToOperatorSwitch) { @@ -723,11 +787,13 @@ // with an end time after the SCT timestamp. operator_history[scts[1]->log_id].previous_operators_.emplace_back( "Operator 0", scts[1]->timestamp + base::Seconds(1)); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, MultipleOperatorSwitches) { @@ -743,11 +809,13 @@ "Different Operator", scts[1]->timestamp - base::Seconds(1)); operator_history[scts[1]->log_id].previous_operators_.emplace_back( "Operator 0", scts[1]->timestamp + base::Seconds(1)); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } TEST_F(ChromeCTPolicyEnforcerTest, MultipleOperatorSwitchesBeforeSCTTimestamp) { @@ -767,11 +835,13 @@ "Different Operator", scts[1]->timestamp - base::Seconds(2)); operator_history[scts[1]->log_id].previous_operators_.emplace_back( "Yet Another Different Operator", scts[1]->timestamp - base::Seconds(1)); - policy_enforcer_->SetOperatorHistoryForTesting(operator_history); - EXPECT_EQ(CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, - policy_enforcer_->CheckCompliance(chain_.get(), scts, - NetLogWithSource())); + std::unique_ptr<ChromeCTPolicyEnforcer> policy_enforcer = + MakeChromeCTPolicyEnforcer(GetDisqualifiedLogs(), operator_history); + + EXPECT_EQ( + CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS, + policy_enforcer->CheckCompliance(chain_.get(), scts, NetLogWithSource())); } } // namespace certificate_transparency
diff --git a/components/commerce/core/metrics/scheduled_metrics_manager_unittest.cc b/components/commerce/core/metrics/scheduled_metrics_manager_unittest.cc index 4ac9c589..da692b59 100644 --- a/components/commerce/core/metrics/scheduled_metrics_manager_unittest.cc +++ b/components/commerce/core/metrics/scheduled_metrics_manager_unittest.cc
@@ -12,6 +12,7 @@ #include "components/commerce/core/metrics/scheduled_metrics_manager.h" #include "components/commerce/core/mock_shopping_service.h" #include "components/commerce/core/pref_names.h" +#include "components/commerce/core/price_tracking_utils.h" #include "components/commerce/core/test_utils.h" #include "components/power_bookmarks/core/power_bookmark_utils.h" #include "components/power_bookmarks/core/proto/power_bookmark_meta.pb.h" @@ -56,8 +57,8 @@ // Add two tracked products. shopping_service_->SetGetAllSubscriptionsCallbackValue( - {CreateUserTrackedSubscription(123L), - CreateUserTrackedSubscription(456L)}); + {BuildUserSubscriptionForClusterId(123L), + BuildUserSubscriptionForClusterId(456L)}); CreateUpdateManagerAndWait(); @@ -71,7 +72,7 @@ base::HistogramTester histogram_tester; shopping_service_->SetGetAllSubscriptionsCallbackValue( - {CreateUserTrackedSubscription(123L)}); + {BuildUserSubscriptionForClusterId(123L)}); CreateUpdateManagerAndWait(); @@ -106,7 +107,7 @@ // Have at least one tracked product. shopping_service_->SetGetAllSubscriptionsCallbackValue( - {CreateUserTrackedSubscription(123L)}); + {BuildUserSubscriptionForClusterId(123L)}); CreateUpdateManagerAndWait(); @@ -127,7 +128,7 @@ // Have at least one tracked product. shopping_service_->SetGetAllSubscriptionsCallbackValue( - {CreateUserTrackedSubscription(123L)}); + {BuildUserSubscriptionForClusterId(123L)}); CreateUpdateManagerAndWait();
diff --git a/components/commerce/core/mock_shopping_service.cc b/components/commerce/core/mock_shopping_service.cc index 32e1cebb..f0e2f05b 100644 --- a/components/commerce/core/mock_shopping_service.cc +++ b/components/commerce/core/mock_shopping_service.cc
@@ -45,7 +45,6 @@ SetIsSubscribedCallbackValue(true); SetGetAllSubscriptionsCallbackValue(std::vector<CommerceSubscription>()); SetIsShoppingListEligible(true); - SetIsClusterIdTrackedByUserResponse(true); SetIsMerchantViewerEnabled(true); SetGetAllPriceTrackedBookmarksCallbackValue( std::vector<const bookmarks::BookmarkNode*>()); @@ -190,15 +189,6 @@ }); } -void MockShoppingService::SetIsClusterIdTrackedByUserResponse(bool is_tracked) { - ON_CALL(*this, IsClusterIdTrackedByUser) - .WillByDefault([is_tracked](uint64_t cluster_id, - base::OnceCallback<void(bool)> callback) { - base::SequencedTaskRunner::GetCurrentDefault()->PostTask( - FROM_HERE, base::BindOnce(std::move(callback), is_tracked)); - }); -} - void MockShoppingService::SetIsMerchantViewerEnabled(bool is_enabled) { ON_CALL(*this, IsMerchantViewerEnabled) .WillByDefault(testing::Return(is_enabled));
diff --git a/components/commerce/core/mock_shopping_service.h b/components/commerce/core/mock_shopping_service.h index d26c085e..52b649a0 100644 --- a/components/commerce/core/mock_shopping_service.h +++ b/components/commerce/core/mock_shopping_service.h
@@ -96,10 +96,6 @@ WaitForReady, (base::OnceCallback<void(ShoppingService*)>), (override)); - MOCK_METHOD(void, - IsClusterIdTrackedByUser, - (uint64_t cluster_id, base::OnceCallback<void(bool)> callback), - (override)); MOCK_METHOD(bool, IsMerchantViewerEnabled, (), (override)); MOCK_METHOD(bool, IsPriceInsightsEligible, (), (override)); MOCK_METHOD(bool, IsDiscountEligibleToShowOnNavigation, (), (override)); @@ -138,7 +134,6 @@ std::vector<CommerceSubscription> subscriptions); void SetIsShoppingListEligible(bool enabled); void SetIsReady(bool ready); - void SetIsClusterIdTrackedByUserResponse(bool is_tracked); void SetIsMerchantViewerEnabled(bool is_enabled); void SetGetAllPriceTrackedBookmarksCallbackValue( std::vector<const bookmarks::BookmarkNode*> bookmarks);
diff --git a/components/commerce/core/price_tracking_utils.h b/components/commerce/core/price_tracking_utils.h index 18f974c7..1dfeb78 100644 --- a/components/commerce/core/price_tracking_utils.h +++ b/components/commerce/core/price_tracking_utils.h
@@ -120,8 +120,9 @@ // set by the user or is still in the default state. bool IsEmailNotificationPrefSetByUser(PrefService* pref_service); -// Build a user-tracked price tracking subscription object for the provided -// cluster ID. +// Builds a user-managed price tracking subscription object for the provided +// cluster ID. This does not change the state of the subscription, it only +// creates the object representing the subscription. CommerceSubscription BuildUserSubscriptionForClusterId(uint64_t cluster_id); // Returns whether price tracking can be initiated given either a ProductInfo
diff --git a/components/commerce/core/price_tracking_utils_unittest.cc b/components/commerce/core/price_tracking_utils_unittest.cc index ecf552b..c547806 100644 --- a/components/commerce/core/price_tracking_utils_unittest.cc +++ b/components/commerce/core/price_tracking_utils_unittest.cc
@@ -373,7 +373,7 @@ ASSERT_EQ(2U, bookmark_model_->other_node()->children().size()); shopping_service_->SetGetAllSubscriptionsCallbackValue( - {CreateUserTrackedSubscription(12345L)}); + {BuildUserSubscriptionForClusterId(12345L)}); base::RunLoop run_loop; GetAllPriceTrackedBookmarks(
diff --git a/components/commerce/core/shopping_service.cc b/components/commerce/core/shopping_service.cc index 3e21b77..33859737 100644 --- a/components/commerce/core/shopping_service.cc +++ b/components/commerce/core/shopping_service.cc
@@ -1527,21 +1527,6 @@ return true; } -void ShoppingService::IsClusterIdTrackedByUser( - uint64_t cluster_id, - base::OnceCallback<void(bool)> callback) { - if (!subscriptions_manager_) { - base::SequencedTaskRunner::GetCurrentDefault()->PostTask( - FROM_HERE, base::BindOnce(std::move(callback), false)); - return; - } - - CommerceSubscription sub( - SubscriptionType::kPriceTrack, IdentifierType::kProductClusterId, - base::NumberToString(cluster_id), ManagementType::kUserManaged); - subscriptions_manager_->IsSubscribed(std::move(sub), std::move(callback)); -} - void ShoppingService::StartTrackingParcels( const std::vector<std::pair<ParcelIdentifier::Carrier, std::string>>& parcel_identifiers,
diff --git a/components/commerce/core/shopping_service.h b/components/commerce/core/shopping_service.h index 214f60c..20a8e572 100644 --- a/components/commerce/core/shopping_service.h +++ b/components/commerce/core/shopping_service.h
@@ -377,12 +377,6 @@ virtual void WaitForReady( base::OnceCallback<void(ShoppingService*)> callback); - // Check whether a product (based on cluster ID) is explicitly price tracked - // by the user. - virtual void IsClusterIdTrackedByUser( - uint64_t cluster_id, - base::OnceCallback<void(bool)> callback); - // This is a feature check for the "merchant viewer", which will return true // if the user has the feature flag enabled or (if applicable) is in an // enabled country and locale.
diff --git a/components/commerce/core/test_utils.cc b/components/commerce/core/test_utils.cc index 06dd18c..0ff7ddb6a 100644 --- a/components/commerce/core/test_utils.cc +++ b/components/commerce/core/test_utils.cc
@@ -72,12 +72,6 @@ std::move(meta)); } -CommerceSubscription CreateUserTrackedSubscription(uint64_t cluster_id) { - return CommerceSubscription( - SubscriptionType::kPriceTrack, IdentifierType::kProductClusterId, - base::NumberToString(cluster_id), ManagementType::kUserManaged); -} - void SetShoppingListEnterprisePolicyPref(PrefService* prefs, bool enabled) { prefs->SetBoolean(kShoppingListEnabledPrefName, enabled); }
diff --git a/components/commerce/core/test_utils.h b/components/commerce/core/test_utils.h index a28c2b6..a1864ff 100644 --- a/components/commerce/core/test_utils.h +++ b/components/commerce/core/test_utils.h
@@ -72,8 +72,6 @@ const absl::optional<int64_t>& last_subscription_change_time = absl::nullopt); -CommerceSubscription CreateUserTrackedSubscription(uint64_t cluster_id); - // Sets the state of the enterprise policy for the shopping list feature for // testing. void SetShoppingListEnterprisePolicyPref(PrefService* prefs, bool enabled);
diff --git a/components/commerce/core/webui/shopping_list_handler_unittest.cc b/components/commerce/core/webui/shopping_list_handler_unittest.cc index e1d922e..a0a210eb 100644 --- a/components/commerce/core/webui/shopping_list_handler_unittest.cc +++ b/components/commerce/core/webui/shopping_list_handler_unittest.cc
@@ -230,7 +230,7 @@ handler_->TrackPriceForBookmark(product->id()); // Assume the subscription callback fires with a success. - handler_->OnSubscribe(CreateUserTrackedSubscription(cluster_id), true); + handler_->OnSubscribe(BuildUserSubscriptionForClusterId(cluster_id), true); task_environment_.RunUntilIdle(); } @@ -253,7 +253,7 @@ handler_->UntrackPriceForBookmark(product->id()); // Assume the subscription callback fires with a success. - handler_->OnUnsubscribe(CreateUserTrackedSubscription(cluster_id), true); + handler_->OnUnsubscribe(BuildUserSubscriptionForClusterId(cluster_id), true); task_environment_.RunUntilIdle(); } @@ -280,7 +280,7 @@ handler_->TrackPriceForBookmark(product->id()); // Assume the subscription callback fires with a failure. - handler_->OnUnsubscribe(CreateUserTrackedSubscription(cluster_id), false); + handler_->OnUnsubscribe(BuildUserSubscriptionForClusterId(cluster_id), false); task_environment_.RunUntilIdle(); } @@ -307,7 +307,7 @@ handler_->UntrackPriceForBookmark(product->id()); // Assume the subscription callback fires with a failure. - handler_->OnUnsubscribe(CreateUserTrackedSubscription(cluster_id), false); + handler_->OnUnsubscribe(BuildUserSubscriptionForClusterId(cluster_id), false); task_environment_.RunUntilIdle(); } @@ -321,7 +321,7 @@ PriceUntrackedForBookmark(MojoBookmarkInfoWithId(product->id()))); // Assume the plumbing for subscriptions works and fake an unsubscribe event. - handler_->OnUnsubscribe(CreateUserTrackedSubscription(123L), true); + handler_->OnUnsubscribe(BuildUserSubscriptionForClusterId(123L), true); task_environment_.RunUntilIdle(); } @@ -332,7 +332,7 @@ MojoBookmarkInfoWithClusterId(cluster_id))) .Times(1); - handler_->OnUnsubscribe(CreateUserTrackedSubscription(cluster_id), true); + handler_->OnUnsubscribe(BuildUserSubscriptionForClusterId(cluster_id), true); task_environment_.RunUntilIdle(); } @@ -346,7 +346,7 @@ AddProductBookmark(bookmark_model_.get(), u"product 2", GURL("http://example.com/2"), 456L, false, 4560000, "usd"); shopping_service_->SetGetAllSubscriptionsCallbackValue( - {CreateUserTrackedSubscription(123L)}); + {BuildUserSubscriptionForClusterId(123L)}); std::vector<const bookmarks::BookmarkNode*> bookmark_list; bookmark_list.push_back(product);
diff --git a/components/component_updater/installer_policies/BUILD.gn b/components/component_updater/installer_policies/BUILD.gn index 39fb776..0948f0f 100644 --- a/components/component_updater/installer_policies/BUILD.gn +++ b/components/component_updater/installer_policies/BUILD.gn
@@ -16,8 +16,6 @@ sources = [ "autofill_states_component_installer.cc", "autofill_states_component_installer.h", - "client_side_phishing_component_installer_policy.cc", - "client_side_phishing_component_installer_policy.h", "masked_domain_list_component_installer_policy.cc", "masked_domain_list_component_installer_policy.h", "origin_trials_component_installer.cc",
diff --git a/components/component_updater/installer_policies/client_side_phishing_component_installer_policy.cc b/components/component_updater/installer_policies/client_side_phishing_component_installer_policy.cc deleted file mode 100644 index c7a7b190..0000000 --- a/components/component_updater/installer_policies/client_side_phishing_component_installer_policy.cc +++ /dev/null
@@ -1,113 +0,0 @@ -// Copyright 2021 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "components/component_updater/installer_policies/client_side_phishing_component_installer_policy.h" - -#include <stdint.h> -#include <memory> -#include <string> -#include <vector> - -#include "base/files/file_path.h" -#include "base/files/file_util.h" -#include "base/functional/bind.h" -#include "base/functional/callback.h" -#include "base/values.h" -#include "base/version.h" -#include "components/component_updater/component_installer.h" - -namespace component_updater { - -namespace { -const char kClientSidePhishingManifestName[] = "Client Side Phishing Detection"; - -// The SHA256 of the SubjectPublicKeyInfo used to sign the extension. -// The extension id is: imefjhfbkmcmebodilednhmaccmincoa -const uint8_t kClientSidePhishingPublicKeySHA256[32] = { - 0x8c, 0x45, 0x97, 0x51, 0xac, 0x2c, 0x41, 0xe3, 0x8b, 0x43, 0xd7, - 0xc0, 0x22, 0xc8, 0xd2, 0xe0, 0xe3, 0xe2, 0x33, 0x88, 0x1f, 0x09, - 0x6d, 0xde, 0x65, 0x6a, 0x83, 0x32, 0x71, 0x52, 0x6e, 0x77}; - -} // namespace - -const base::FilePath::CharType kClientModelBinaryPbFileName[] = - FILE_PATH_LITERAL("client_model.pb"); -const base::FilePath::CharType kVisualTfLiteModelFileName[] = - FILE_PATH_LITERAL("visual_model.tflite"); - -ClientSidePhishingComponentInstallerPolicy:: - ClientSidePhishingComponentInstallerPolicy( - const ReadFilesCallback& read_files_callback, - const InstallerAttributesCallback& installer_attributes_callback) - : read_files_callback_(std::move(read_files_callback)), - installer_attributes_callback_(std::move(installer_attributes_callback)) { -} - -ClientSidePhishingComponentInstallerPolicy:: - ~ClientSidePhishingComponentInstallerPolicy() = default; - -// static -void ClientSidePhishingComponentInstallerPolicy::GetPublicHash( - std::vector<uint8_t>* hash) { - hash->assign(kClientSidePhishingPublicKeySHA256, - kClientSidePhishingPublicKeySHA256 + - std::size(kClientSidePhishingPublicKeySHA256)); -} - -bool ClientSidePhishingComponentInstallerPolicy:: - SupportsGroupPolicyEnabledComponentUpdates() const { - return true; -} - -bool ClientSidePhishingComponentInstallerPolicy::RequiresNetworkEncryption() - const { - return false; -} - -update_client::CrxInstaller::Result -ClientSidePhishingComponentInstallerPolicy::OnCustomInstall( - const base::Value::Dict& manifest, - const base::FilePath& install_dir) { - return update_client::CrxInstaller::Result(0); // Nothing custom here. -} - -void ClientSidePhishingComponentInstallerPolicy::OnCustomUninstall() {} - -void ClientSidePhishingComponentInstallerPolicy::ComponentReady( - const base::Version& version, - const base::FilePath& install_dir, - base::Value::Dict manifest) { - read_files_callback_.Run(install_dir); -} - -// Called during startup and installation before ComponentReady(). -bool ClientSidePhishingComponentInstallerPolicy::VerifyInstallation( - const base::Value::Dict& manifest, - const base::FilePath& install_dir) const { - // No need to actually validate the proto here, since we'll do the checking - // in PopulateFromDynamicUpdate(). - return base::PathExists(install_dir.Append(kClientModelBinaryPbFileName)) || - base::PathExists(install_dir.Append(kVisualTfLiteModelFileName)); -} - -base::FilePath -ClientSidePhishingComponentInstallerPolicy::GetRelativeInstallDir() const { - return base::FilePath(FILE_PATH_LITERAL("ClientSidePhishing")); -} - -void ClientSidePhishingComponentInstallerPolicy::GetHash( - std::vector<uint8_t>* hash) const { - GetPublicHash(hash); -} - -std::string ClientSidePhishingComponentInstallerPolicy::GetName() const { - return kClientSidePhishingManifestName; -} - -update_client::InstallerAttributes -ClientSidePhishingComponentInstallerPolicy::GetInstallerAttributes() const { - return installer_attributes_callback_.Run(); -} - -} // namespace component_updater
diff --git a/components/component_updater/installer_policies/client_side_phishing_component_installer_policy.h b/components/component_updater/installer_policies/client_side_phishing_component_installer_policy.h deleted file mode 100644 index 8b71e2d..0000000 --- a/components/component_updater/installer_policies/client_side_phishing_component_installer_policy.h +++ /dev/null
@@ -1,76 +0,0 @@ -// Copyright 2021 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef COMPONENTS_COMPONENT_UPDATER_INSTALLER_POLICIES_CLIENT_SIDE_PHISHING_COMPONENT_INSTALLER_POLICY_H_ -#define COMPONENTS_COMPONENT_UPDATER_INSTALLER_POLICIES_CLIENT_SIDE_PHISHING_COMPONENT_INSTALLER_POLICY_H_ - -#include <stdint.h> -#include <memory> -#include <string> -#include <vector> - -#include "base/functional/callback.h" -#include "base/values.h" -#include "components/component_updater/component_installer.h" - -namespace base { -class FilePath; -class Version; -} // namespace base - -namespace component_updater { - -extern const base::FilePath::CharType kClientModelBinaryPbFileName[]; -extern const base::FilePath::CharType kVisualTfLiteModelFileName[]; - -class ClientSidePhishingComponentInstallerPolicy - : public ComponentInstallerPolicy { - public: - // A callback to read model files from the given install path and populate the - // model appropriately, used to customize the behaviour of `ComponentReady`. - using ReadFilesCallback = - base::RepeatingCallback<void(const base::FilePath&)>; - // A callback that returns the appoperiate installer attributes, used to - // customize the behaviour of `GetInstallerAttributes`. - using InstallerAttributesCallback = - base::RepeatingCallback<update_client::InstallerAttributes()>; - - ClientSidePhishingComponentInstallerPolicy( - const ReadFilesCallback& read_files_callback, - const InstallerAttributesCallback& installer_attributes_callback); - ClientSidePhishingComponentInstallerPolicy( - const ClientSidePhishingComponentInstallerPolicy&) = delete; - ClientSidePhishingComponentInstallerPolicy& operator=( - const ClientSidePhishingComponentInstallerPolicy&) = delete; - ~ClientSidePhishingComponentInstallerPolicy() override; - - static void GetPublicHash(std::vector<uint8_t>* hash); - - private: - // The following methods override ComponentInstallerPolicy. - bool SupportsGroupPolicyEnabledComponentUpdates() const override; - bool RequiresNetworkEncryption() const override; - update_client::CrxInstaller::Result OnCustomInstall( - const base::Value::Dict& manifest, - const base::FilePath& install_dir) override; - void OnCustomUninstall() override; - bool VerifyInstallation(const base::Value::Dict& manifest, - const base::FilePath& install_dir) const override; - void ComponentReady(const base::Version& version, - const base::FilePath& install_dir, - base::Value::Dict manifest) override; - base::FilePath GetRelativeInstallDir() const override; - void GetHash(std::vector<uint8_t>* hash) const override; - std::string GetName() const override; - update_client::InstallerAttributes GetInstallerAttributes() const override; - - static base::FilePath GetInstalledPath(const base::FilePath& base); - - ReadFilesCallback read_files_callback_; - InstallerAttributesCallback installer_attributes_callback_; -}; - -} // namespace component_updater - -#endif // COMPONENTS_COMPONENT_UPDATER_INSTALLER_POLICIES_CLIENT_SIDE_PHISHING_COMPONENT_INSTALLER_POLICY_H_
diff --git a/components/exo/keyboard_unittest.cc b/components/exo/keyboard_unittest.cc index be5e6210..a6bade9 100644 --- a/components/exo/keyboard_unittest.cc +++ b/components/exo/keyboard_unittest.cc
@@ -883,7 +883,7 @@ EXPECT_TRUE(keyboard.HasDeviceConfigurationDelegate()); testing::Mock::VerifyAndClearExpectations(&configuration_delegate); - ash::AccessibilityControllerImpl* accessibility_controller = + ash::AccessibilityController* accessibility_controller = ash::Shell::Get()->accessibility_controller(); // Enable a11y keyboard calls OnKeyboardTypeChanged() with false.
diff --git a/components/feature_engagement/public/android/java/src/org/chromium/components/feature_engagement/EventConstants.java b/components/feature_engagement/public/android/java/src/org/chromium/components/feature_engagement/EventConstants.java index bbe4b8c..87def57 100644 --- a/components/feature_engagement/public/android/java/src/org/chromium/components/feature_engagement/EventConstants.java +++ b/components/feature_engagement/public/android/java/src/org/chromium/components/feature_engagement/EventConstants.java
@@ -150,10 +150,6 @@ /** Shared Highlighting button event */ public static final String IPH_SHARED_HIGHLIGHTING_USED = "iph_shared_highlighting_used"; - /** Webnotes Stylize feature used from Sharing Hub */ - public static final String SHARING_HUB_WEBNOTES_STYLIZE_USED = - "sharing_hub_webnotes_stylize_used"; - /** AutoDark disabled from app menu events. */ public static final String AUTO_DARK_DISABLED_IN_APP_MENU = "auto_dark_disabled_in_app_menu";
diff --git a/components/history/core/browser/history_database.cc b/components/history/core/browser/history_database.cc index 9a3d586..11b81c3 100644 --- a/components/history/core/browser/history_database.cc +++ b/components/history/core/browser/history_database.cc
@@ -293,7 +293,6 @@ } int HistoryDatabase::CountUniqueHostsVisitedLastMonth() { - base::TimeTicks start_time = base::TimeTicks::Now(); // Collect all URLs visited within the last month. base::Time one_month_ago = base::Time::Now() - base::Days(30); @@ -310,8 +309,6 @@ hosts.insert(url.host()); } - UMA_HISTOGRAM_TIMES("History.DatabaseMonthlyHostCountTime", - base::TimeTicks::Now() - start_time); return hosts.size(); }
diff --git a/components/history/core/browser/history_service_unittest.cc b/components/history/core/browser/history_service_unittest.cc index ed229500..a0a1677 100644 --- a/components/history/core/browser/history_service_unittest.cc +++ b/components/history/core/browser/history_service_unittest.cc
@@ -876,7 +876,6 @@ // Counts hosts visited in the last month. TEST_F(HistoryServiceTest, CountMonthlyVisitedHosts) { - base::HistogramTester histogram_tester; HistoryService* history = history_service_.get(); ASSERT_TRUE(history); @@ -896,8 +895,6 @@ AddPageInThePast(history, "https://www.yahoo.com/foo", 29); EXPECT_EQ(3, GetMonthlyHostCountHelper(history, &tracker_)); - // The time required to compute host count is reported on each computation. - histogram_tester.ExpectTotalCount("History.DatabaseMonthlyHostCountTime", 4); } TEST_F(HistoryServiceTest, GetDomainDiversityShortBasetimeRange) {
diff --git a/components/history/core/browser/top_sites_backend.cc b/components/history/core/browser/top_sites_backend.cc index 30618b6b..6e6b06f 100644 --- a/components/history/core/browser/top_sites_backend.cc +++ b/components/history/core/browser/top_sites_backend.cc
@@ -55,11 +55,10 @@ std::move(callback)); } -void TopSitesBackend::UpdateTopSites(const TopSitesDelta& delta, - const RecordHistogram record_or_not) { +void TopSitesBackend::UpdateTopSites(const TopSitesDelta& delta) { db_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&TopSitesBackend::UpdateTopSitesOnDBThread, - this, delta, record_or_not)); + FROM_HERE, + base::BindOnce(&TopSitesBackend::UpdateTopSitesOnDBThread, this, delta)); } void TopSitesBackend::ResetDatabase() { @@ -91,21 +90,13 @@ return db_ ? db_->GetSites() : MostVisitedURLList(); } -void TopSitesBackend::UpdateTopSitesOnDBThread( - const TopSitesDelta& delta, const RecordHistogram record_or_not) { +void TopSitesBackend::UpdateTopSitesOnDBThread(const TopSitesDelta& delta) { TRACE_EVENT0("startup", "history::TopSitesBackend::UpdateTopSitesOnDBThread"); if (!db_) return; - base::TimeTicks begin_time = base::TimeTicks::Now(); - db_->ApplyDelta(delta); - - if (record_or_not == RECORD_HISTOGRAM_YES) { - UMA_HISTOGRAM_TIMES("History.FirstUpdateTime", - base::TimeTicks::Now() - begin_time); - } } void TopSitesBackend::ResetDatabaseOnDBThread(const base::FilePath& file_path) {
diff --git a/components/history/core/browser/top_sites_backend.h b/components/history/core/browser/top_sites_backend.h index db4ca4a..8fae8a01 100644 --- a/components/history/core/browser/top_sites_backend.h +++ b/components/history/core/browser/top_sites_backend.h
@@ -27,15 +27,6 @@ // thread. class TopSitesBackend : public base::RefCountedThreadSafe<TopSitesBackend> { public: - // TODO(yiyaoliu): Remove the enums and related code when crbug/223430 is - // fixed. - // An enum representing whether the UpdateTopSites execution time related - // histogram should be recorded. - enum RecordHistogram { - RECORD_HISTOGRAM_YES, - RECORD_HISTOGRAM_NO - }; - using GetMostVisitedSitesCallback = base::OnceCallback<void(MostVisitedURLList)>; @@ -54,8 +45,7 @@ base::CancelableTaskTracker* tracker); // Updates top sites database from the specified delta. - void UpdateTopSites(const TopSitesDelta& delta, - const RecordHistogram record_or_not); + void UpdateTopSites(const TopSitesDelta& delta); // Deletes the database and recreates it. void ResetDatabase(); @@ -75,8 +65,7 @@ MostVisitedURLList GetMostVisitedSitesOnDBThread(); // Updates top sites. - void UpdateTopSitesOnDBThread(const TopSitesDelta& delta, - const RecordHistogram record_or_not); + void UpdateTopSitesOnDBThread(const TopSitesDelta& delta); // Resets the database. void ResetDatabaseOnDBThread(const base::FilePath& file_path);
diff --git a/components/history/core/browser/top_sites_impl.cc b/components/history/core/browser/top_sites_impl.cc index d3d6085..0e53f261 100644 --- a/components/history/core/browser/top_sites_impl.cc +++ b/components/history/core/browser/top_sites_impl.cc
@@ -18,7 +18,6 @@ #include "base/location.h" #include "base/memory/ref_counted.h" #include "base/metrics/histogram_functions.h" -#include "base/metrics/histogram_macros.h" #include "base/ranges/algorithm.h" #include "base/strings/string_util.h" #include "base/strings/utf_string_conversions.h" @@ -125,8 +124,6 @@ }; // Initially, histogram is not recorded. -bool TopSitesImpl::histogram_recorded_ = false; - TopSitesImpl::TopSitesImpl(PrefService* pref_service, HistoryService* history_service, TemplateURLService* template_url_service, @@ -376,21 +373,10 @@ TopSitesDelta delta; DiffMostVisited(top_sites_, top_sites, &delta); - TopSitesBackend::RecordHistogram record_or_not = - TopSitesBackend::RECORD_HISTOGRAM_NO; - - if (location == CALL_LOCATION_FROM_ON_GOT_MOST_VISITED_URLS && - !histogram_recorded_) { - // Will be passed to TopSitesBackend to let it record the histogram. - record_or_not = TopSitesBackend::RECORD_HISTOGRAM_YES; - // Change it to true so that the histogram will not be recorded any more. - histogram_recorded_ = true; - } - bool should_notify_observers = false; // If there is a change in urls, update the db and notify observers. if (!delta.deleted.empty() || !delta.added.empty() || !delta.moved.empty()) { - backend_->UpdateTopSites(delta, record_or_not); + backend_->UpdateTopSites(delta); should_notify_observers = true; } // If there is no url change in top sites, check if the titles have changes.
diff --git a/components/history/core/browser/top_sites_impl.h b/components/history/core/browser/top_sites_impl.h index 5bc47e7..257afcc 100644 --- a/components/history/core/browser/top_sites_impl.h +++ b/components/history/core/browser/top_sites_impl.h
@@ -234,10 +234,6 @@ // Are we loaded? bool loaded_; - // Have the SetTopSites execution time related histograms been recorded? - // The histogram should only be recorded once for each Chrome execution. - static bool histogram_recorded_; - base::ScopedObservation<HistoryService, HistoryServiceObserver> history_service_observation_{this}; };
diff --git a/components/metrics/generate_expired_histograms_array.gni b/components/metrics/generate_expired_histograms_array.gni index 2b121757..72a5de8 100644 --- a/components/metrics/generate_expired_histograms_array.gni +++ b/components/metrics/generate_expired_histograms_array.gni
@@ -199,6 +199,7 @@ "//tools/metrics/histograms/metadata/quickstart/enums.xml", "//tools/metrics/histograms/metadata/quickstart/histograms.xml", "//tools/metrics/histograms/metadata/quota/histograms.xml", + "//tools/metrics/histograms/metadata/readaloud/histograms.xml", "//tools/metrics/histograms/metadata/renderer/histograms.xml", "//tools/metrics/histograms/metadata/renderer4/histograms.xml", "//tools/metrics/histograms/metadata/safe_browsing/enums.xml",
diff --git a/components/optimization_guide/core/BUILD.gn b/components/optimization_guide/core/BUILD.gn index 4b731bc..f26cc320 100644 --- a/components/optimization_guide/core/BUILD.gn +++ b/components/optimization_guide/core/BUILD.gn
@@ -141,6 +141,7 @@ "insertion_ordered_set.h", "optimization_guide_constants.cc", "optimization_guide_constants.h", + "optimization_guide_enums.h", "optimization_guide_features.cc", "optimization_guide_features.h", "optimization_guide_prefs.cc", @@ -203,7 +204,6 @@ "optimization_filter.h", "optimization_guide_decider.h", "optimization_guide_decision.h", - "optimization_guide_enums.h", "optimization_guide_logger.cc", "optimization_guide_logger.h", "optimization_guide_model_executor.h", @@ -254,6 +254,8 @@ "model_execution/model_execution_util.h", "model_execution/on_device_model_access_controller.cc", "model_execution/on_device_model_access_controller.h", + "model_execution/on_device_model_component.cc", + "model_execution/on_device_model_component.h", "model_execution/on_device_model_execution_config_interpreter.cc", "model_execution/on_device_model_execution_config_interpreter.h", "model_execution/on_device_model_execution_proto_descriptors.h", @@ -496,10 +498,13 @@ "model_execution/model_execution_features_unittest.cc", "model_execution/model_execution_fetcher_unittest.cc", "model_execution/model_execution_manager_unittest.cc", + "model_execution/on_device_model_component_unittest.cc", "model_execution/on_device_model_execution_config_interpreter_unittest.cc", "model_execution/on_device_model_execution_proto_value_utils_unittest.cc", "model_execution/on_device_model_service_controller_unittest.cc", "model_execution/optimization_guide_model_execution_error_unittest.cc", + "model_execution/test_on_device_model_component.cc", + "model_execution/test_on_device_model_component.h", ] } if (build_with_tflite_lib) {
diff --git a/components/optimization_guide/core/model_execution/on_device_model_component.cc b/components/optimization_guide/core/model_execution/on_device_model_component.cc new file mode 100644 index 0000000..a3134c70 --- /dev/null +++ b/components/optimization_guide/core/model_execution/on_device_model_component.cc
@@ -0,0 +1,208 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/optimization_guide/core/model_execution/on_device_model_component.h" + +#include "base/files/file_path.h" +#include "base/files/file_util.h" +#include "base/memory/ptr_util.h" +#include "base/memory/scoped_refptr.h" +#include "base/no_destructor.h" +#include "base/time/time.h" +#include "base/types/cxx23_to_underlying.h" +#include "components/optimization_guide/core/optimization_guide_enums.h" +#include "components/optimization_guide/core/optimization_guide_features.h" +#include "components/optimization_guide/core/optimization_guide_prefs.h" +#include "components/prefs/pref_service.h" + +namespace optimization_guide { +namespace { + +base::WeakPtr<OnDeviceModelComponentStateManager>& GetInstance() { + static base::NoDestructor<base::WeakPtr<OnDeviceModelComponentStateManager>> + state_manager_instance; + return *state_manager_instance.get(); +} + +bool WasAnOnDeviceFeatureRecentlyUsed(const PrefService& local_state) { + base::Time last_use = local_state.GetTime( + prefs::localstate::kLastTimeOnDeviceEligibleFeatureWasUsed); + constexpr base::TimeDelta grace_period = base::Days(7); + auto time_since_use = base::Time::Now() - last_use; + // Note: Since we're storing a base::Time, we need to consider the possibility + // of clock changes. + return time_since_use < grace_period && time_since_use > -grace_period; +} + +bool IsDeviceCapable(const PrefService& local_state) { + int value = + local_state.GetInteger(prefs::localstate::kOnDevicePerformanceClass); + if (value < 0 || + value > static_cast<int>(OnDeviceModelPerformanceClass::kMaxValue)) { + return false; + } + return features::IsPerformanceClassCompatibleWithOnDeviceModel( + static_cast<OnDeviceModelPerformanceClass>(value)); +} + +bool IsModelNeeded(const PrefService& local_state) { + return WasAnOnDeviceFeatureRecentlyUsed(local_state) && + features::IsOnDeviceExecutionEnabled() && IsDeviceCapable(local_state); +} + +} // namespace + +void OnDeviceModelComponentStateManager::UninstallComplete() { + local_state_->ClearPref( + prefs::localstate::kLastTimeEligibleForOnDeviceModelDownload); + + component_installer_registered_ = false; +} + +void OnDeviceModelComponentStateManager::OnDeviceEligibleFeatureUsed() { + local_state_->SetTime( + prefs::localstate::kLastTimeOnDeviceEligibleFeatureWasUsed, + base::Time::Now()); + + UpdateRegistration(); +} + +void OnDeviceModelComponentStateManager::DevicePerformanceClassChanged( + OnDeviceModelPerformanceClass performance_class) { + local_state_->SetInteger(prefs::localstate::kOnDevicePerformanceClass, + base::to_underlying(performance_class)); + + UpdateRegistration(); +} + +void OnDeviceModelComponentStateManager::OnStartup() { + // TODO(b/302327114): Add UMA. + UpdateRegistration(); +} + +void OnDeviceModelComponentStateManager::UpdateRegistration() { + // After the installer is registered, don't do anything until after a chrome + // restart. + if (component_installer_registered_) { + return; + } + + switch (GetRegistrationDecision()) { + case OnDeviceRegistrationDecision::kDoNotInstall: + break; + case OnDeviceRegistrationDecision::kInstall: + component_installer_registered_ = true; + delegate_->RegisterInstaller(this); + break; + case OnDeviceRegistrationDecision::kUninstall: + // Don't allow UpdateRegistration to do anything until after + // UninstallComplete. + component_installer_registered_ = true; + delegate_->Uninstall(this); + break; + } +} + +OnDeviceModelComponentStateManager::OnDeviceRegistrationDecision +OnDeviceModelComponentStateManager::GetRegistrationDecision() { + if (IsModelNeeded(*local_state_)) { + local_state_->SetTime( + prefs::localstate::kLastTimeEligibleForOnDeviceModelDownload, + base::Time::Now()); + return OnDeviceRegistrationDecision::kInstall; + } + + auto last_time_eligible = local_state_->GetTime( + prefs::localstate::kLastTimeEligibleForOnDeviceModelDownload); + if (last_time_eligible == base::Time::Min()) { + return OnDeviceRegistrationDecision::kDoNotInstall; + } + + const base::TimeDelta retention_time = + features::GetOnDeviceModelRetentionTime(); + auto time_since_eligible = base::Time::Now() - last_time_eligible; + if (time_since_eligible < retention_time && + time_since_eligible > -retention_time) { + return OnDeviceRegistrationDecision::kInstall; + } + return OnDeviceRegistrationDecision::kUninstall; +} + +OnDeviceModelComponentStateManager::OnDeviceModelComponentStateManager( + PrefService* local_state, + std::unique_ptr<Delegate> delegate) + : local_state_(local_state), delegate_(std::move(delegate)) { + CHECK(local_state); // Useful to catch poor test setup. +} + +OnDeviceModelComponentStateManager::~OnDeviceModelComponentStateManager() = + default; + +const OnDeviceModelComponentState* +OnDeviceModelComponentStateManager::GetState() { + return state_.get(); +} + +scoped_refptr<OnDeviceModelComponentStateManager> +OnDeviceModelComponentStateManager::CreateOrGet( + PrefService* local_state, + std::unique_ptr<Delegate> delegate) { + base::WeakPtr<OnDeviceModelComponentStateManager>& instance = GetInstance(); + if (!instance) { + auto state_manager = + base::WrapRefCounted(new OnDeviceModelComponentStateManager( + local_state, std::move(delegate))); + instance = state_manager->GetWeakPtr(); + return state_manager; + } + return scoped_refptr<OnDeviceModelComponentStateManager>(instance.get()); +} + +void OnDeviceModelComponentStateManager::AddObserver(Observer* observer) { + observers_.AddObserver(observer); +} + +void OnDeviceModelComponentStateManager::RemoveObserver(Observer* observer) { + observers_.RemoveObserver(observer); +} + +// static +OnDeviceModelComponentStateManager* +OnDeviceModelComponentStateManager::GetInstanceForTesting() { + return GetInstance().get(); +} + +bool OnDeviceModelComponentStateManager::VerifyInstallation( + const base::FilePath& install_dir, + const base::Value::Dict& manifest) { + // TODO(b/302327114): Avoid having these file names duplicated. Either + // have OnDeviceModelComponentState provide the full path to each file, + // or add these names as constants in a shared place. + for (const base::FilePath::CharType* file_name : + {FILE_PATH_LITERAL("spm.model"), FILE_PATH_LITERAL("weights.bin"), + FILE_PATH_LITERAL("model.pb"), + FILE_PATH_LITERAL("on_device_model_execution_config.pb")}) { + if (!base::PathExists(install_dir.Append(file_name))) { + return false; + } + } + return true; +} + +void OnDeviceModelComponentStateManager::SetReady( + const base::Version& version, + const base::FilePath& install_dir, + const base::Value::Dict& manifest) { + state_ = base::WrapUnique(new OnDeviceModelComponentState); + state_->install_dir_ = install_dir; + state_->version_ = version; + for (auto& o : observers_) { + o.StateChanged(state_.get()); + } +} + +OnDeviceModelComponentState::OnDeviceModelComponentState() = default; +OnDeviceModelComponentState::~OnDeviceModelComponentState() = default; + +} // namespace optimization_guide
diff --git a/components/optimization_guide/core/model_execution/on_device_model_component.h b/components/optimization_guide/core/model_execution/on_device_model_component.h new file mode 100644 index 0000000..b83cd78 --- /dev/null +++ b/components/optimization_guide/core/model_execution/on_device_model_component.h
@@ -0,0 +1,157 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef COMPONENTS_OPTIMIZATION_GUIDE_CORE_MODEL_EXECUTION_ON_DEVICE_MODEL_COMPONENT_H_ +#define COMPONENTS_OPTIMIZATION_GUIDE_CORE_MODEL_EXECUTION_ON_DEVICE_MODEL_COMPONENT_H_ + +#include <memory> + +#include "base/files/file_path.h" +#include "base/functional/callback.h" +#include "base/memory/ref_counted.h" +#include "base/observer_list.h" +#include "base/observer_list_types.h" +#include "base/values.h" +#include "base/version.h" +#include "components/optimization_guide/core/optimization_guide_enums.h" + +class PrefService; + +namespace optimization_guide { + +inline constexpr std::string_view kOnDeviceModelCrxId = + "fklghjjljmnfjoepjmlobpekiapffcja"; + +class OnDeviceModelComponentState; + +// Manages the state of the on-device component. +// This object needs to have lifetime equal to the browser process. This is +// achieved by holding a scoped_refptr on KeyedServices which need it, and on +// the installer (which is owned by ComponentUpdaterService). +class OnDeviceModelComponentStateManager + : public base::RefCounted<OnDeviceModelComponentStateManager> { + public: + class Delegate { + public: + virtual ~Delegate() = default; + + // Registers the component installer. Calls + // `OnDeviceModelComponentStateManager::SetReady` when the component is + // ready to use. + virtual void RegisterInstaller( + scoped_refptr<OnDeviceModelComponentStateManager> state_manager) = 0; + + // Uninstall the component. Calls + // `OnDeviceModelComponentStateManager::UninstallComplete()` when uninstall + // completes. + virtual void Uninstall( + scoped_refptr<OnDeviceModelComponentStateManager> state_manager) = 0; + }; + + class Observer : public base::CheckedObserver { + public: + // Called whenever the on-device component state changes. `state` is null if + // the component is not available. + virtual void StateChanged(const OnDeviceModelComponentState* state) = 0; + }; + + // Creates the instance if one does not already exist. Returns an existing + // instance otherwise. + static scoped_refptr<OnDeviceModelComponentStateManager> CreateOrGet( + PrefService* local_state, + std::unique_ptr<Delegate> delegate); + + // Called at startup. Triggers install or uninstall of the component if + // necessary. + void OnStartup(); + + // Should be called whenever an on-device eligible feature was used. + void OnDeviceEligibleFeatureUsed(); + + // Should be called whenever the device performance class changes. + void DevicePerformanceClassChanged( + OnDeviceModelPerformanceClass performance_class); + + // Returns the current state. Null if the component is not available. + const OnDeviceModelComponentState* GetState(); + + void AddObserver(Observer* observer); + void RemoveObserver(Observer* observer); + + // Functions called by the component installer: + + // Called when the on-device component has been uninstalled. + void UninstallComplete(); + + // Returns whether the component installation is valid. + bool VerifyInstallation(const base::FilePath& install_dir, + const base::Value::Dict& manifest); + + // Creates the on-device component state, only called after VerifyInstallation + // returns true. + void SetReady(const base::Version& version, + const base::FilePath& install_dir, + const base::Value::Dict& manifest); + + base::WeakPtr<OnDeviceModelComponentStateManager> GetWeakPtr() { + return weak_ptr_factory_.GetWeakPtr(); + } + + // Testing functionality: + static OnDeviceModelComponentStateManager* GetInstanceForTesting(); + + private: + friend class base::RefCounted<OnDeviceModelComponentStateManager>; + + enum class OnDeviceRegistrationDecision { + // The component should be installed. + kInstall, + // The component should not be installed, and should be removed. + kUninstall, + // The component should not be installed, and does not need removed. + kDoNotInstall, + }; + + OnDeviceModelComponentStateManager(PrefService* local_state, + std::unique_ptr<Delegate> delegate); + ~OnDeviceModelComponentStateManager(); + + // Called at startup to determine whether to install or uninstall the on + // device component. + OnDeviceRegistrationDecision GetRegistrationDecision(); + + // Installs the component installer if it needs installed. + void UpdateRegistration(); + + raw_ptr<PrefService> local_state_; + std::unique_ptr<Delegate> delegate_; + base::ObserverList<Observer> observers_; + bool component_installer_registered_ = false; + std::unique_ptr<OnDeviceModelComponentState> state_; + + base::WeakPtrFactory<OnDeviceModelComponentStateManager> weak_ptr_factory_{ + this}; +}; + +// State of the on-device model component. +class OnDeviceModelComponentState { + public: + ~OnDeviceModelComponentState(); + + const base::FilePath& GetInstallDirectory() const { return install_dir_; } + const base::Version& GetVersion() const { return version_; } + + private: + OnDeviceModelComponentState(); + friend class OnDeviceModelComponentStateManager; + + base::FilePath install_dir_; + base::Version version_; + // Note that we'll need to read the manifest and expose additional + // information for b/310740288. +}; + +} // namespace optimization_guide + +#endif // COMPONENTS_OPTIMIZATION_GUIDE_CORE_MODEL_EXECUTION_ON_DEVICE_MODEL_COMPONENT_H_
diff --git a/components/optimization_guide/core/model_execution/on_device_model_component_unittest.cc b/components/optimization_guide/core/model_execution/on_device_model_component_unittest.cc new file mode 100644 index 0000000..efcb8cea --- /dev/null +++ b/components/optimization_guide/core/model_execution/on_device_model_component_unittest.cc
@@ -0,0 +1,210 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/optimization_guide/core/model_execution/on_device_model_component.h" + +#include <memory> + +#include "base/scoped_add_feature_flags.h" +#include "base/test/scoped_feature_list.h" +#include "base/test/task_environment.h" +#include "base/thread_annotations.h" +#include "base/types/cxx23_to_underlying.h" +#include "components/optimization_guide/core/model_execution/test_on_device_model_component.h" +#include "components/optimization_guide/core/optimization_guide_enums.h" +#include "components/optimization_guide/core/optimization_guide_features.h" +#include "components/optimization_guide/core/optimization_guide_prefs.h" +#include "components/prefs/testing_pref_service.h" +#include "testing/gmock/include/gmock/gmock.h" +#include "testing/gtest/include/gtest/gtest.h" + +namespace optimization_guide { +namespace { + +class StubObserver : public OnDeviceModelComponentStateManager::Observer { + public: + void StateChanged(const OnDeviceModelComponentState* state) override { + state_ = state; + } + + const OnDeviceModelComponentState* GetState() { return state_; } + + private: + raw_ptr<const OnDeviceModelComponentState> state_; +}; + +class OnDeviceModelComponentTest : public testing::Test { + public: + void SetUp() override { + prefs::RegisterLocalStatePrefs(local_state_.registry()); + + local_state_.SetInteger( + prefs::localstate::kOnDevicePerformanceClass, + base::to_underlying(OnDeviceModelPerformanceClass::kLow)); + local_state_.SetTime( + prefs::localstate::kLastTimeOnDeviceEligibleFeatureWasUsed, + base::Time::Now()); + + feature_list_.InitWithFeatures({features::kOptimizationGuideModelExecution, + features::kOptimizationGuideOnDeviceModel, + features::kLogOnDeviceMetricsOnStartup}, + {}); + } + + scoped_refptr<OnDeviceModelComponentStateManager> manager() { + return on_device_component_state_manager_.get(); + } + + protected: + base::test::TaskEnvironment task_environment_{ + base::test::TaskEnvironment::TimeSource::MOCK_TIME}; + TestingPrefServiceSimple local_state_; + base::test::ScopedFeatureList feature_list_; + TestOnDeviceModelComponentStateManager on_device_component_state_manager_{ + &local_state_}; +}; + +TEST_F(OnDeviceModelComponentTest, InstallsWhenEligible) { + manager()->OnStartup(); + + EXPECT_TRUE(on_device_component_state_manager_.IsInstallerRegistered()); + EXPECT_EQ(local_state_.GetTime( + prefs::localstate::kLastTimeEligibleForOnDeviceModelDownload), + base::Time::Now()); +} + +TEST_F(OnDeviceModelComponentTest, DoesNotInstallWhenFeatureNotEnabled) { + // It should not install if any of these features are disabled. + for (const base::Feature* feature : + {&features::kOptimizationGuideModelExecution, + &features::kOptimizationGuideOnDeviceModel, + &features::kLogOnDeviceMetricsOnStartup}) { + SCOPED_TRACE(feature->name); + on_device_component_state_manager_.Reset(); + base::test::ScopedFeatureList features; + features.InitAndDisableFeature(*feature); + + manager()->OnStartup(); + EXPECT_FALSE(on_device_component_state_manager_.IsInstallerRegistered()); + } +} + +TEST_F(OnDeviceModelComponentTest, NoEligibleFeatureUse) { + local_state_.ClearPref( + prefs::localstate::kLastTimeOnDeviceEligibleFeatureWasUsed); + + manager()->OnStartup(); + EXPECT_FALSE(on_device_component_state_manager_.IsInstallerRegistered()); +} + +TEST_F(OnDeviceModelComponentTest, EligibleFeatureUseTooOld) { + local_state_.SetTime( + prefs::localstate::kLastTimeOnDeviceEligibleFeatureWasUsed, + base::Time::Now() - base::Days(31)); + + manager()->OnStartup(); + EXPECT_FALSE(on_device_component_state_manager_.IsInstallerRegistered()); +} + +TEST_F(OnDeviceModelComponentTest, NoPerformanceClass) { + local_state_.ClearPref(prefs::localstate::kOnDevicePerformanceClass); + + manager()->OnStartup(); + EXPECT_FALSE(on_device_component_state_manager_.IsInstallerRegistered()); +} + +TEST_F(OnDeviceModelComponentTest, PerformanceClassTooLow) { + local_state_.SetInteger( + prefs::localstate::kOnDevicePerformanceClass, + base::to_underlying(OnDeviceModelPerformanceClass::kVeryLow)); + + manager()->OnStartup(); + EXPECT_FALSE(on_device_component_state_manager_.IsInstallerRegistered()); +} + +TEST_F(OnDeviceModelComponentTest, UninstallNeeded) { + // This pref records that the model was eligible for download previously, + // and hasn't been cleaned up yet. + local_state_.SetTime( + prefs::localstate::kLastTimeEligibleForOnDeviceModelDownload, + base::Time::Now() - base::Minutes(1) - + features::GetOnDeviceModelRetentionTime()); + local_state_.ClearPref( + prefs::localstate::kLastTimeOnDeviceEligibleFeatureWasUsed); + + // Should uninstall the first time, and skip uninstallation the next time. + manager()->OnStartup(); + EXPECT_TRUE(on_device_component_state_manager_.WasComponentUninstalled()); + + manager()->UninstallComplete(); + + manager()->OnStartup(); + EXPECT_FALSE(on_device_component_state_manager_.IsInstallerRegistered()); +} + +TEST_F(OnDeviceModelComponentTest, InstallWhileNotEligible) { + // If the model is already installed, we don't uninstall right away. + local_state_.SetTime( + prefs::localstate::kLastTimeEligibleForOnDeviceModelDownload, + base::Time::Now() - base::Days(1)); + local_state_.ClearPref( + prefs::localstate::kLastTimeOnDeviceEligibleFeatureWasUsed); + + manager()->OnStartup(); + EXPECT_TRUE(on_device_component_state_manager_.IsInstallerRegistered()); +} + +TEST_F(OnDeviceModelComponentTest, GetStateInitiallyNull) { + EXPECT_EQ(manager()->GetState(), nullptr); +} + +TEST_F(OnDeviceModelComponentTest, SetReady) { + StubObserver observer; + manager()->AddObserver(&observer); + manager()->SetReady(base::Version("0.1.1"), + base::FilePath(FILE_PATH_LITERAL("/some/path")), + base::Value::Dict()); + + const OnDeviceModelComponentState* state = manager()->GetState(); + ASSERT_TRUE(state); + + EXPECT_EQ(state->GetInstallDirectory(), + base::FilePath(FILE_PATH_LITERAL("/some/path"))); + EXPECT_EQ(state->GetVersion(), base::Version("0.1.1")); + ASSERT_EQ(observer.GetState(), state); +} + +TEST_F(OnDeviceModelComponentTest, InstallAfterPerformanceClassChanges) { + // This sequence would happen on first run. + local_state_.ClearPref(prefs::localstate::kOnDevicePerformanceClass); + manager()->OnStartup(); + ASSERT_FALSE(on_device_component_state_manager_.IsInstallerRegistered()); + + manager()->DevicePerformanceClassChanged(OnDeviceModelPerformanceClass::kLow); + + EXPECT_TRUE(on_device_component_state_manager_.IsInstallerRegistered()); +} + +TEST_F(OnDeviceModelComponentTest, DontUninstallAfterPerformanceClassChanges) { + manager()->OnStartup(); + ASSERT_TRUE(on_device_component_state_manager_.IsInstallerRegistered()); + + manager()->DevicePerformanceClassChanged(OnDeviceModelPerformanceClass::kLow); + + EXPECT_TRUE(on_device_component_state_manager_.IsInstallerRegistered()); + EXPECT_FALSE(on_device_component_state_manager_.WasComponentUninstalled()); +} + +TEST_F(OnDeviceModelComponentTest, InstallAfterEligibleFeatureWasUsed) { + local_state_.ClearPref( + prefs::localstate::kLastTimeOnDeviceEligibleFeatureWasUsed); + manager()->OnStartup(); + ASSERT_FALSE(on_device_component_state_manager_.IsInstallerRegistered()); + + manager()->OnDeviceEligibleFeatureUsed(); + EXPECT_TRUE(on_device_component_state_manager_.IsInstallerRegistered()); +} + +} // namespace +} // namespace optimization_guide
diff --git a/components/optimization_guide/core/model_execution/on_device_model_service_controller.cc b/components/optimization_guide/core/model_execution/on_device_model_service_controller.cc index 3e1388b..ed96c55 100644 --- a/components/optimization_guide/core/model_execution/on_device_model_service_controller.cc +++ b/components/optimization_guide/core/model_execution/on_device_model_service_controller.cc
@@ -8,6 +8,7 @@ #include "base/strings/strcat.h" #include "base/task/thread_pool.h" #include "components/optimization_guide/core/model_execution/on_device_model_access_controller.h" +#include "components/optimization_guide/core/model_execution/on_device_model_component.h" #include "components/optimization_guide/core/model_execution/on_device_model_execution_config_interpreter.h" #include "components/optimization_guide/core/model_execution/session_impl.h" #include "components/optimization_guide/core/model_util.h" @@ -61,10 +62,22 @@ } // namespace OnDeviceModelServiceController::OnDeviceModelServiceController( - std::unique_ptr<OnDeviceModelAccessController> access_controller) - : access_controller_(std::move(access_controller)) {} + std::unique_ptr<OnDeviceModelAccessController> access_controller, + base::WeakPtr<optimization_guide::OnDeviceModelComponentStateManager> + on_device_component_state_manager) + : access_controller_(std::move(access_controller)), + on_device_component_state_manager_( + std::move(on_device_component_state_manager)) { + if (on_device_component_state_manager_) { + on_device_component_state_manager_->AddObserver(this); + } +} -OnDeviceModelServiceController::~OnDeviceModelServiceController() = default; +OnDeviceModelServiceController::~OnDeviceModelServiceController() { + if (on_device_component_state_manager_) { + on_device_component_state_manager_->RemoveObserver(this); + } +} void OnDeviceModelServiceController::Init( const base::FilePath& model_path, @@ -79,13 +92,21 @@ void OnDeviceModelServiceController::Init() { auto model_path_override_switch = switches::GetOnDeviceModelExecutionOverride(); + std::optional<base::FilePath> model_path; if (model_path_override_switch) { - auto file_path = StringToFilePath(*model_path_override_switch); - if (file_path) { - Init(*file_path, - std::make_unique<OnDeviceModelExecutionConfigInterpreter>()); + model_path = StringToFilePath(*model_path_override_switch); + } else if (on_device_component_state_manager_) { + const OnDeviceModelComponentState* state = + on_device_component_state_manager_->GetState(); + if (state) { + model_path = state->GetInstallDirectory(); } } + + if (model_path) { + Init(*model_path, + std::make_unique<OnDeviceModelExecutionConfigInterpreter>()); + } } std::unique_ptr<OptimizationGuideModelExecutor::Session> @@ -93,6 +114,7 @@ proto::ModelExecutionFeature feature, ExecuteRemoteFn execute_remote_fn, OptimizationGuideLogger* optimization_guide_logger) { + on_device_component_state_manager_->OnDeviceEligibleFeatureUsed(); ScopedEligibilityReasonLogger logger(feature); if (!base::FeatureList::IsEnabled( features::kOptimizationGuideOnDeviceModel)) { @@ -179,6 +201,19 @@ weak_ptr_factory_.GetWeakPtr())); } +void OnDeviceModelServiceController::StateChanged( + const OnDeviceModelComponentState* state) { + if (state && model_path_.empty()) { + Init(); + } else { + // TODO(b/302327114): Support other cases. Decide how to handle: + // * If state is null and Init() has already been called. We should prevent + // future requests from being handled, and maybe kill in-flight tasks. + // * If state is non-null and Init() has already been called. We should + // probably re-load any files as they may have changed. + } +} + void OnDeviceModelServiceController::OnLoadModelResult( on_device_model::mojom::LoadModelResult result) { base::UmaHistogramEnumeration(
diff --git a/components/optimization_guide/core/model_execution/on_device_model_service_controller.h b/components/optimization_guide/core/model_execution/on_device_model_service_controller.h index 6bf191bc..60a3d95 100644 --- a/components/optimization_guide/core/model_execution/on_device_model_service_controller.h +++ b/components/optimization_guide/core/model_execution/on_device_model_service_controller.h
@@ -10,9 +10,11 @@ #include "base/memory/raw_ptr.h" #include "base/memory/raw_ref.h" #include "base/memory/ref_counted.h" +#include "base/memory/scoped_refptr.h" #include "base/memory/weak_ptr.h" #include "base/sequence_checker.h" #include "base/types/pass_key.h" +#include "components/optimization_guide/core/model_execution/on_device_model_component.h" #include "components/optimization_guide/core/model_execution/session_impl.h" #include "components/optimization_guide/core/optimization_guide_model_executor.h" #include "components/optimization_guide/proto/model_execution.pb.h" @@ -29,6 +31,7 @@ namespace optimization_guide { class OnDeviceModelAccessController; +class OnDeviceModelComponentStateManager; class OnDeviceModelExecutionConfigInterpreter; // Controls the lifetime of the on-device model service, loading and unloading @@ -43,10 +46,13 @@ // this. Also handle multiple requests gracefully and fail the subsequent // requests, while handling the first one. class OnDeviceModelServiceController - : public base::RefCounted<OnDeviceModelServiceController> { + : public base::RefCounted<OnDeviceModelServiceController>, + public OnDeviceModelComponentStateManager::Observer { public: explicit OnDeviceModelServiceController( - std::unique_ptr<OnDeviceModelAccessController> access_controller); + std::unique_ptr<OnDeviceModelAccessController> access_controller, + base::WeakPtr<OnDeviceModelComponentStateManager> + on_device_component_state_manager); // Initializes the on-device model controller with the parameters, to be ready // to load models and execute. @@ -88,13 +94,16 @@ return model_remote_.is_bound() || service_remote_.is_bound(); } + // OnDeviceModelComponentStateManager::Observer. + void StateChanged(const OnDeviceModelComponentState* state) override; + private: friend class base::RefCounted<OnDeviceModelServiceController>; friend class ChromeOnDeviceModelServiceController; friend class OnDeviceModelServiceControllerTest; friend class FakeOnDeviceModelServiceController; - virtual ~OnDeviceModelServiceController(); + ~OnDeviceModelServiceController() override; // Makes sure the service is running and starts a mojo session. void StartMojoSession( @@ -118,6 +127,8 @@ // This may be null in the destructor, otherwise non-null. std::unique_ptr<OnDeviceModelAccessController> access_controller_; + base::WeakPtr<OnDeviceModelComponentStateManager> + on_device_component_state_manager_; base::FilePath model_path_; std::unique_ptr<OnDeviceModelExecutionConfigInterpreter> config_interpreter_; mojo::Remote<on_device_model::mojom::OnDeviceModelService> service_remote_;
diff --git a/components/optimization_guide/core/model_execution/on_device_model_service_controller_unittest.cc b/components/optimization_guide/core/model_execution/on_device_model_service_controller_unittest.cc index 1fe87ea..33811f4 100644 --- a/components/optimization_guide/core/model_execution/on_device_model_service_controller_unittest.cc +++ b/components/optimization_guide/core/model_execution/on_device_model_service_controller_unittest.cc
@@ -14,6 +14,7 @@ #include "base/test/task_environment.h" #include "components/optimization_guide/core/model_execution/on_device_model_access_controller.h" #include "components/optimization_guide/core/model_execution/on_device_model_execution_config_interpreter.h" +#include "components/optimization_guide/core/model_execution/test_on_device_model_component.h" #include "components/optimization_guide/core/optimization_guide_features.h" #include "components/optimization_guide/core/optimization_guide_logger.h" #include "components/optimization_guide/core/optimization_guide_prefs.h" @@ -180,8 +181,12 @@ : public OnDeviceModelServiceController { public: explicit FakeOnDeviceModelServiceController( - std::unique_ptr<OnDeviceModelAccessController> access_controller) - : OnDeviceModelServiceController(std::move(access_controller)) {} + std::unique_ptr<OnDeviceModelAccessController> access_controller, + base::WeakPtr<OnDeviceModelComponentStateManager> + on_device_component_state_manager) + : OnDeviceModelServiceController( + std::move(access_controller), + std::move(on_device_component_state_manager)) {} void LaunchService() override { did_launch_service_ = true; @@ -225,6 +230,11 @@ RecreateServiceController(); } + void TearDown() override { + access_controller_ = nullptr; + test_controller_ = nullptr; + } + ExecuteRemoteFn CreateExecuteRemoteFn() { return base::BindLambdaForTesting( [=](proto::ModelExecutionFeature feature, @@ -239,14 +249,16 @@ } void RecreateServiceController() { - test_controller_ = nullptr; access_controller_ = nullptr; + test_controller_ = nullptr; auto access_controller = std::make_unique<OnDeviceModelAccessController>(pref_service_); access_controller_ = access_controller.get(); test_controller_ = base::MakeRefCounted<FakeOnDeviceModelServiceController>( - std::move(access_controller)); + std::move(access_controller), + on_device_component_state_manager_.get()->GetWeakPtr()); + proto::OnDeviceModelExecutionFeatureConfig config; config.set_feature(kFeature); auto& input_config = *config.mutable_input_config(); @@ -327,6 +339,8 @@ base::test::TaskEnvironment task_environment_{ base::test::TaskEnvironment::TimeSource::MOCK_TIME}; TestingPrefServiceSimple pref_service_; + TestOnDeviceModelComponentStateManager on_device_component_state_manager_{ + &pref_service_}; scoped_refptr<FakeOnDeviceModelServiceController> test_controller_; // Owned by FakeOnDeviceModelServiceController. raw_ptr<OnDeviceModelAccessController> access_controller_ = nullptr; @@ -801,7 +815,8 @@ std::make_unique<OnDeviceModelAccessController>(pref_service_); access_controller_ = access_controller.get(); test_controller_ = base::MakeRefCounted<FakeOnDeviceModelServiceController>( - std::move(access_controller)); + std::move(access_controller), + on_device_component_state_manager_.get()->GetWeakPtr()); proto::OnDeviceModelExecutionFeatureConfig config; config.set_feature(kFeature); @@ -844,7 +859,8 @@ std::make_unique<OnDeviceModelAccessController>(pref_service_); access_controller_ = access_controller.get(); test_controller_ = base::MakeRefCounted<FakeOnDeviceModelServiceController>( - std::move(access_controller)); + std::move(access_controller), + on_device_component_state_manager_.get()->GetWeakPtr()); proto::OnDeviceModelExecutionFeatureConfig config; config.set_feature(kFeature);
diff --git a/components/optimization_guide/core/model_execution/test_on_device_model_component.cc b/components/optimization_guide/core/model_execution/test_on_device_model_component.cc new file mode 100644 index 0000000..1dba212 --- /dev/null +++ b/components/optimization_guide/core/model_execution/test_on_device_model_component.cc
@@ -0,0 +1,71 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/optimization_guide/core/model_execution/test_on_device_model_component.h" + +#include "base/check.h" + +namespace optimization_guide { + +class FakeOnDeviceModelComponentStateManagerDelegate + : public OnDeviceModelComponentStateManager::Delegate { + public: + ~FakeOnDeviceModelComponentStateManagerDelegate() override = default; + void RegisterInstaller(scoped_refptr<OnDeviceModelComponentStateManager> + state_manager) override { + installer_registered_ = true; + } + void Uninstall(scoped_refptr<OnDeviceModelComponentStateManager> + state_manager) override { + uninstall_called_ = true; + } + + private: + friend class TestOnDeviceModelComponentStateManager; + bool installer_registered_ = false; + bool uninstall_called_ = false; +}; + +TestOnDeviceModelComponentStateManager::TestOnDeviceModelComponentStateManager( + PrefService* local_state) + : local_state_(local_state) {} + +TestOnDeviceModelComponentStateManager:: + ~TestOnDeviceModelComponentStateManager() { + Reset(); +} + +scoped_refptr<OnDeviceModelComponentStateManager> +TestOnDeviceModelComponentStateManager::get() { + // Note that we create the instance lazily to allow tests time to register + // prefs. + if (!manager_) { + CHECK(!OnDeviceModelComponentStateManager::GetInstanceForTesting()) + << "Instance already exists"; + auto delegate = + std::make_unique<FakeOnDeviceModelComponentStateManagerDelegate>(); + delegate_ = delegate.get(); + manager_ = OnDeviceModelComponentStateManager::CreateOrGet( + local_state_, std::move(delegate)); + CHECK(manager_); + } + return manager_; +} + +void TestOnDeviceModelComponentStateManager::Reset() { + if (manager_) { + delegate_ = nullptr; + manager_ = nullptr; + } +} + +bool TestOnDeviceModelComponentStateManager::IsInstallerRegistered() const { + return delegate_ && delegate_->installer_registered_; +} + +bool TestOnDeviceModelComponentStateManager::WasComponentUninstalled() const { + return delegate_ && delegate_->uninstall_called_; +} + +} // namespace optimization_guide
diff --git a/components/optimization_guide/core/model_execution/test_on_device_model_component.h b/components/optimization_guide/core/model_execution/test_on_device_model_component.h new file mode 100644 index 0000000..abf7f4e0 --- /dev/null +++ b/components/optimization_guide/core/model_execution/test_on_device_model_component.h
@@ -0,0 +1,38 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef COMPONENTS_OPTIMIZATION_GUIDE_CORE_MODEL_EXECUTION_TEST_ON_DEVICE_MODEL_COMPONENT_H_ +#define COMPONENTS_OPTIMIZATION_GUIDE_CORE_MODEL_EXECUTION_TEST_ON_DEVICE_MODEL_COMPONENT_H_ +#include "components/optimization_guide/core/model_execution/on_device_model_component.h" + +class PrefService; + +namespace optimization_guide { + +class FakeOnDeviceModelComponentStateManagerDelegate; + +// Provides scoped creation and destruction of +// OnDeviceModelComponentStateManager. Checks to make sure only one instance is +// used at a time. +class TestOnDeviceModelComponentStateManager { + public: + explicit TestOnDeviceModelComponentStateManager(PrefService* local_state); + ~TestOnDeviceModelComponentStateManager(); + + scoped_refptr<OnDeviceModelComponentStateManager> get(); + + void Reset(); + + bool IsInstallerRegistered() const; + bool WasComponentUninstalled() const; + + private: + raw_ptr<PrefService> local_state_; + raw_ptr<FakeOnDeviceModelComponentStateManagerDelegate> delegate_; + scoped_refptr<OnDeviceModelComponentStateManager> manager_; +}; + +} // namespace optimization_guide + +#endif // COMPONENTS_OPTIMIZATION_GUIDE_CORE_MODEL_EXECUTION_TEST_ON_DEVICE_MODEL_COMPONENT_H_
diff --git a/components/optimization_guide/core/optimization_guide_enums.h b/components/optimization_guide/core/optimization_guide_enums.h index fbeefc3..2ad52cc 100644 --- a/components/optimization_guide/core/optimization_guide_enums.h +++ b/components/optimization_guide/core/optimization_guide_enums.h
@@ -268,9 +268,9 @@ // Performance class of this device. // -// These values are persisted to logs. Entries should not be renumbered and -// numeric values should never be reused. -enum class OnDeviceModelPerformanceClass { +// These values are persisted to logs and prefs. Entries should not be +// renumbered and numeric values should never be reused. +enum class OnDeviceModelPerformanceClass : int { kUnknown = 0, // See on_device_model::mojom::PerformanceClass for explanation of these. @@ -281,6 +281,9 @@ kHigh = 5, kVeryHigh = 6, + // WARNING!: If you add a new performance class, please be aware of + // `IsPerformanceClassCompatibleWithOnDeviceModel`. + // The service crashed, so a valid value was not returned. kServiceCrash = 7,
diff --git a/components/optimization_guide/core/optimization_guide_features.cc b/components/optimization_guide/core/optimization_guide_features.cc index ad91e7f8..8b652006 100644 --- a/components/optimization_guide/core/optimization_guide_features.cc +++ b/components/optimization_guide/core/optimization_guide_features.cc
@@ -15,10 +15,12 @@ #include "base/metrics/field_trial_params.h" #include "base/strings/string_split.h" #include "base/strings/string_util.h" +#include "base/strings/to_string.h" #include "base/system/sys_info.h" #include "build/build_config.h" #include "components/optimization_guide/core/insertion_ordered_set.h" #include "components/optimization_guide/core/optimization_guide_constants.h" +#include "components/optimization_guide/core/optimization_guide_enums.h" #include "components/optimization_guide/core/optimization_guide_switches.h" #include "components/optimization_guide/machine_learning_tflite_buildflags.h" #include "components/optimization_guide/proto/common_types.pb.h" @@ -990,10 +992,38 @@ return kOnDeviceModelFallbackToServerOnDisconnect.Get(); } +bool IsPerformanceClassCompatibleWithOnDeviceModel( + OnDeviceModelPerformanceClass performance_class) { + std::string perf_classes_string = base::GetFieldTrialParamValueByFeature( + kOptimizationGuideOnDeviceModel, + "compatible_on_device_performance_classes"); + if (perf_classes_string.empty()) { + perf_classes_string = "3,4,5,6"; + } + std::vector<std::string_view> perf_classes_list = base::SplitStringPiece( + perf_classes_string, ",", base::WhitespaceHandling::TRIM_WHITESPACE, + base::SplitResult::SPLIT_WANT_NONEMPTY); + return base::Contains(perf_classes_list, + base::ToString(static_cast<int>(performance_class))); +} + bool CanLaunchOnDeviceModelService() { return base::FeatureList::IsEnabled(kOptimizationGuideOnDeviceModel) || base::FeatureList::IsEnabled(kLogOnDeviceMetricsOnStartup); } +bool IsOnDeviceExecutionEnabled() { + return base::FeatureList::IsEnabled( + features::kOptimizationGuideModelExecution) && + base::FeatureList::IsEnabled(kOptimizationGuideOnDeviceModel) && + base::FeatureList::IsEnabled(kLogOnDeviceMetricsOnStartup); +} + +base::TimeDelta GetOnDeviceModelRetentionTime() { + return base::GetFieldTrialParamByFeatureAsTimeDelta( + kOptimizationGuideOnDeviceModel, "on_device_model_retention_time", + base::Days(30)); +} + } // namespace features } // namespace optimization_guide
diff --git a/components/optimization_guide/core/optimization_guide_features.h b/components/optimization_guide/core/optimization_guide_features.h index 679b210..ccfc377 100644 --- a/components/optimization_guide/core/optimization_guide_features.h +++ b/components/optimization_guide/core/optimization_guide_features.h
@@ -13,6 +13,7 @@ #include "base/feature_list.h" #include "base/metrics/field_trial_params.h" #include "base/time/time.h" +#include "components/optimization_guide/core/optimization_guide_enums.h" #include "components/optimization_guide/core/page_content_annotation_type.h" #include "components/optimization_guide/proto/hints.pb.h" #include "components/optimization_guide/proto/model_execution.pb.h" @@ -530,10 +531,31 @@ COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) bool GetOnDeviceFallbackToServerOnDisconnect(); -// Whether any features are enabled that allow launching the on-device service. +// Returns whether the performance class is compatible with executing the +// on-device model. Used to determine whether or not to fetch the on-device +// model. +COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) +bool IsPerformanceClassCompatibleWithOnDeviceModel( + OnDeviceModelPerformanceClass performance_class); + +// Whether any features are enabled that allow launching the on-device +// service. COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) bool CanLaunchOnDeviceModelService(); +// Whether on-device execution is enabled. +COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) +bool IsOnDeviceExecutionEnabled(); + +// The on-device model is fetched when the device is considered eligible for +// on-device execution. When the device stops being eligible, the model is +// retained for this amount of time. This protects the user from repeatedly +// downloading the model in the event eligibility fluctuates. for on-device +// evaluation +// See on_device_model_component.cc for how eligibility is computed. +COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) +base::TimeDelta GetOnDeviceModelRetentionTime(); + } // namespace features } // namespace optimization_guide
diff --git a/components/optimization_guide/core/optimization_guide_features_unittest.cc b/components/optimization_guide/core/optimization_guide_features_unittest.cc index 05fdba91..3717453 100644 --- a/components/optimization_guide/core/optimization_guide_features_unittest.cc +++ b/components/optimization_guide/core/optimization_guide_features_unittest.cc
@@ -402,6 +402,23 @@ } } +TEST(OptimizationGuideFeaturesTest, + IsPerformanceClassCompatibleWithOnDeviceModel) { + base::test::ScopedFeatureList scoped_feature_list; + scoped_feature_list.InitAndEnableFeatureWithParameters( + features::kOptimizationGuideOnDeviceModel, + {{"compatible_on_device_performance_classes", "4,6"}}); + + EXPECT_FALSE(features::IsPerformanceClassCompatibleWithOnDeviceModel( + OnDeviceModelPerformanceClass::kError)); + EXPECT_TRUE(features::IsPerformanceClassCompatibleWithOnDeviceModel( + OnDeviceModelPerformanceClass::kMedium)); + EXPECT_FALSE(features::IsPerformanceClassCompatibleWithOnDeviceModel( + OnDeviceModelPerformanceClass::kHigh)); + EXPECT_TRUE(features::IsPerformanceClassCompatibleWithOnDeviceModel( + OnDeviceModelPerformanceClass::kVeryHigh)); +} + } // namespace } // namespace optimization_guide
diff --git a/components/optimization_guide/core/optimization_guide_prefs.cc b/components/optimization_guide/core/optimization_guide_prefs.cc index 5d0acf3..93dcd09 100644 --- a/components/optimization_guide/core/optimization_guide_prefs.cc +++ b/components/optimization_guide/core/optimization_guide_prefs.cc
@@ -125,11 +125,25 @@ const char kOnDeviceModelTimeoutCount[] = "optimization_guide.on_device.timeout_count"; +// Stores the last computed `OnDeviceModelPerformanceClass` of the device. +const char kOnDevicePerformanceClass[] = + "optimization_guide.on_device.performance_class"; + // A dictionary pref that stores the file paths that need to be deleted as keys. // The value will not be used. const char kStoreFilePathsToDelete[] = "optimization_guide.store_file_paths_to_delete"; +// A timestamp for the last time a feature was used which could have benefited +// from the on-device model. We will use this to help decide whether to acquire +// the on device model. +const char kLastTimeOnDeviceEligibleFeatureWasUsed[] = + "optimization_guide.last_time_on_device_eligible_feature_used"; + +// A timestamp for the last time the on-device model was eligible for download. +const char kLastTimeEligibleForOnDeviceModelDownload[] = + "optimization_guide.on_device.last_time_eligible_for_download"; + } // namespace localstate void RegisterProfilePrefs(PrefRegistrySimple* registry) { @@ -165,7 +179,12 @@ registry->RegisterDictionaryPref(localstate::kModelCacheKeyMapping); registry->RegisterIntegerPref(localstate::kOnDeviceModelCrashCount, 0); registry->RegisterIntegerPref(localstate::kOnDeviceModelTimeoutCount, 0); + registry->RegisterIntegerPref(localstate::kOnDevicePerformanceClass, 0); registry->RegisterDictionaryPref(localstate::kStoreFilePathsToDelete); + registry->RegisterTimePref( + localstate::kLastTimeOnDeviceEligibleFeatureWasUsed, base::Time::Min()); + registry->RegisterTimePref( + localstate::kLastTimeEligibleForOnDeviceModelDownload, base::Time::Min()); } } // namespace prefs
diff --git a/components/optimization_guide/core/optimization_guide_prefs.h b/components/optimization_guide/core/optimization_guide_prefs.h index ccb3fc7..8d2da7b1 100644 --- a/components/optimization_guide/core/optimization_guide_prefs.h +++ b/components/optimization_guide/core/optimization_guide_prefs.h
@@ -64,7 +64,13 @@ COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) extern const char kOnDeviceModelTimeoutCount[]; COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) +extern const char kOnDevicePerformanceClass[]; +COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) extern const char kStoreFilePathsToDelete[]; +COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) +extern const char kLastTimeOnDeviceEligibleFeatureWasUsed[]; +COMPONENT_EXPORT(OPTIMIZATION_GUIDE_FEATURES) +extern const char kLastTimeEligibleForOnDeviceModelDownload[]; } // namespace localstate
diff --git a/components/permissions/permission_manager.cc b/components/permissions/permission_manager.cc index 357c6ed..1a0311a7 100644 --- a/components/permissions/permission_manager.cc +++ b/components/permissions/permission_manager.cc
@@ -411,7 +411,7 @@ } PermissionManager::SubscriptionId -PermissionManager::SubscribePermissionStatusChange( +PermissionManager::SubscribeToPermissionStatusChange( PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, @@ -474,7 +474,7 @@ return id; } -void PermissionManager::UnsubscribePermissionStatusChange( +void PermissionManager::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); if (is_shutting_down_)
diff --git a/components/permissions/permission_manager.h b/components/permissions/permission_manager.h index 1dd1f82..1354e754 100644 --- a/components/permissions/permission_manager.h +++ b/components/permissions/permission_manager.h
@@ -141,13 +141,13 @@ bool IsPermissionOverridable( blink::PermissionType permission, const absl::optional<url::Origin>& origin) override; - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, const GURL& requesting_origin, base::RepeatingCallback<void(PermissionStatus)> callback) override; - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; absl::optional<gfx::Rect> GetExclusionAreaBoundsInScreen( content::WebContents* web_contents) const override;
diff --git a/components/permissions/permission_manager_unittest.cc b/components/permissions/permission_manager_unittest.cc index f04abc71..af0a3632 100644 --- a/components/permissions/permission_manager_unittest.cc +++ b/components/permissions/permission_manager_unittest.cc
@@ -194,20 +194,21 @@ } content::PermissionControllerDelegate::SubscriptionId - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, const GURL& requesting_origin, base::RepeatingCallback<void(PermissionStatus)> callback) { - return GetPermissionManager()->SubscribePermissionStatusChange( + return GetPermissionManager()->SubscribeToPermissionStatusChange( permission, render_process_host, render_frame_host, requesting_origin, std::move(callback)); } - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( content::PermissionControllerDelegate::SubscriptionId subscription_id) { - GetPermissionManager()->UnsubscribePermissionStatusChange(subscription_id); + GetPermissionManager()->UnsubscribeFromPermissionStatusChange( + subscription_id); } bool IsPermissionOverridable(PermissionType permission, @@ -406,7 +407,7 @@ TEST_F(PermissionManagerTest, SubscriptionDestroyedCleanlyWithoutUnsubscribe) { // Test that the PermissionManager shuts down cleanly with subscriptions that // haven't been removed, crbug.com/720071. - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -415,7 +416,7 @@ TEST_F(PermissionManagerTest, SubscribeUnsubscribeAfterShutdown) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -426,22 +427,22 @@ // reenterant. GetPermissionManager()->Shutdown(); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); // Check that subscribe/unsubscribe after shutdown don't crash. content::PermissionControllerDelegate::SubscriptionId subscription2_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, base::Unretained(this))); - UnsubscribePermissionStatusChange(subscription2_id); + UnsubscribeFromPermissionStatusChange(subscription2_id); } TEST_F(PermissionManagerTest, SameTypeChangeNotifies) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -452,12 +453,12 @@ EXPECT_TRUE(callback_called()); EXPECT_EQ(PermissionStatus::GRANTED, callback_result()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, DifferentTypeChangeDoesNotNotify) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -468,18 +469,18 @@ EXPECT_FALSE(callback_called()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, ChangeAfterUnsubscribeDoesNotNotify) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, base::Unretained(this))); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); SetPermission(url(), url(), PermissionType::GEOLOCATION, PermissionStatus::GRANTED); @@ -490,19 +491,19 @@ TEST_F(PermissionManagerTest, ChangeAfterUnsubscribeOnlyNotifiesActiveSubscribers) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, base::Unretained(this))); - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, base::Unretained(this))); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); SetPermission(url(), url(), PermissionType::GEOLOCATION, PermissionStatus::GRANTED); @@ -512,7 +513,7 @@ TEST_F(PermissionManagerTest, DifferentPrimaryUrlDoesNotNotify) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -523,12 +524,12 @@ EXPECT_FALSE(callback_called()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, DifferentSecondaryUrlDoesNotNotify) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::STORAGE_ACCESS_GRANT, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -539,12 +540,12 @@ EXPECT_FALSE(callback_called()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, WildCardPatternNotifies) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -556,7 +557,7 @@ EXPECT_TRUE(callback_called()); EXPECT_EQ(PermissionStatus::GRANTED, callback_result()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, ClearSettingsNotifies) { @@ -564,7 +565,7 @@ PermissionStatus::GRANTED); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -576,12 +577,12 @@ EXPECT_TRUE(callback_called()); EXPECT_EQ(PermissionStatus::ASK, callback_result()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, NewValueCorrectlyPassed) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -592,14 +593,14 @@ EXPECT_TRUE(callback_called()); EXPECT_EQ(PermissionStatus::DENIED, callback_result()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, ChangeWithoutPermissionChangeDoesNotNotify) { SetPermission(PermissionType::GEOLOCATION, PermissionStatus::GRANTED); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -610,7 +611,7 @@ EXPECT_FALSE(callback_called()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, ChangesBackAndForth) { @@ -618,7 +619,7 @@ PermissionStatus::ASK); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -637,14 +638,14 @@ EXPECT_TRUE(callback_called()); EXPECT_EQ(PermissionStatus::ASK, callback_result()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, ChangesBackAndForthWorker) { SetPermission(PermissionType::GEOLOCATION, PermissionStatus::ASK); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, process(), /*render_frame_host=*/nullptr, url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -662,12 +663,12 @@ EXPECT_TRUE(callback_called()); EXPECT_EQ(PermissionStatus::ASK, callback_result()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, SubscribeMIDIPermission) { content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::MIDI, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -679,7 +680,7 @@ EXPECT_FALSE(callback_called()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, PermissionIgnoredCleanup) { @@ -877,7 +878,7 @@ content::RenderFrameHost* child = AddChildRFH(parent, GURL(kOrigin2)); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, child, GURL(kOrigin2), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -904,7 +905,7 @@ EXPECT_EQ(PermissionStatus::GRANTED, GetPermissionStatusForCurrentDocument( PermissionType::GEOLOCATION, child)); - subscription_id = SubscribePermissionStatusChange( + subscription_id = SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, child, GURL(kOrigin2), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -921,7 +922,7 @@ EXPECT_EQ(PermissionStatus::DENIED, GetPermissionStatusForCurrentDocument( PermissionType::GEOLOCATION, child)); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, SubscribeUnsubscribeAndResubscribe) { @@ -929,7 +930,7 @@ NavigateAndCommit(GURL(kOrigin1)); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), GURL(kOrigin1), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -941,7 +942,7 @@ EXPECT_EQ(callback_count(), 1); EXPECT_EQ(PermissionStatus::GRANTED, callback_result()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); // ensure no callbacks are received when unsubscribed. SetPermission(PermissionType::GEOLOCATION, PermissionStatus::DENIED); @@ -950,7 +951,7 @@ EXPECT_EQ(callback_count(), 1); content::PermissionControllerDelegate::SubscriptionId subscription_id_2 = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), GURL(kOrigin1), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -962,7 +963,7 @@ EXPECT_EQ(callback_count(), 2); EXPECT_EQ(PermissionStatus::DENIED, callback_result()); - UnsubscribePermissionStatusChange(subscription_id_2); + UnsubscribeFromPermissionStatusChange(subscription_id_2); } TEST_F(PermissionManagerTest, GetCanonicalOrigin) { @@ -1052,7 +1053,7 @@ NavigateAndCommit(GURL(kOrigin1)); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), GURL(kOrigin1), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -1078,7 +1079,7 @@ false /* dismissed_prompt_was_quiet */); EXPECT_EQ(callback_count(), 1); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, UpdatePermissionStatusWithDeviceStatus) { @@ -1136,7 +1137,7 @@ permissions_client().SetCanRequestDevicePermission(true); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -1194,7 +1195,7 @@ EXPECT_TRUE(callback_called()); EXPECT_EQ(PermissionStatus::GRANTED, callback_result()); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } TEST_F(PermissionManagerTest, @@ -1205,7 +1206,7 @@ permissions_client().SetCanRequestDevicePermission(false); content::PermissionControllerDelegate::SubscriptionId subscription_id = - SubscribePermissionStatusChange( + SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, main_rfh(), url(), base::BindRepeating(&PermissionManagerTest::OnPermissionChange, @@ -1247,7 +1248,7 @@ EXPECT_EQ(PermissionStatus::GRANTED, callback_result()); Reset(); - UnsubscribePermissionStatusChange(subscription_id); + UnsubscribeFromPermissionStatusChange(subscription_id); } } // namespace permissions
diff --git a/components/policy/resources/templates/policy_definitions/Miscellaneous/DeviceExtendedFkeysModifier.yaml b/components/policy/resources/templates/policy_definitions/Miscellaneous/DeviceExtendedFkeysModifier.yaml index f46fc27..8b67810 100644 --- a/components/policy/resources/templates/policy_definitions/Miscellaneous/DeviceExtendedFkeysModifier.yaml +++ b/components/policy/resources/templates/policy_definitions/Miscellaneous/DeviceExtendedFkeysModifier.yaml
@@ -9,8 +9,6 @@ features: dynamic_refresh: true per_profile: false -future_on: -- chrome_os items: - caption: F11/F12 settings are disabled name: Disabled @@ -34,5 +32,7 @@ - 2 - 3 type: integer +supported_on: +- chrome_os:122- tags: [] type: int-enum
diff --git a/components/power_bookmarks/core/BUILD.gn b/components/power_bookmarks/core/BUILD.gn index 1728432e..cb55b72 100644 --- a/components/power_bookmarks/core/BUILD.gn +++ b/components/power_bookmarks/core/BUILD.gn
@@ -43,8 +43,6 @@ static_library("features") { sources = [ - "flag_descriptions.cc", - "flag_descriptions.h", "power_bookmark_features.cc", "power_bookmark_features.h", ]
diff --git a/components/power_bookmarks/core/flag_descriptions.cc b/components/power_bookmarks/core/flag_descriptions.cc deleted file mode 100644 index f35c9483..0000000 --- a/components/power_bookmarks/core/flag_descriptions.cc +++ /dev/null
@@ -1,14 +0,0 @@ -// Copyright 2023 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "components/power_bookmarks/core/flag_descriptions.h" - -namespace power_bookmarks::flag_descriptions { - -const char kSimplifiedBookmarkSaveFlowName[] = "Simplified Bookmark Save Flow"; -const char kSimplifiedBookmarkSaveFlowDescription[] = - "Show a simplified version of the bookmark save flow without rename and " - "folder options."; - -} // namespace power_bookmarks::flag_descriptions
diff --git a/components/power_bookmarks/core/flag_descriptions.h b/components/power_bookmarks/core/flag_descriptions.h deleted file mode 100644 index cee6dac8..0000000 --- a/components/power_bookmarks/core/flag_descriptions.h +++ /dev/null
@@ -1,15 +0,0 @@ -// Copyright 2023 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef COMPONENTS_POWER_BOOKMARKS_CORE_FLAG_DESCRIPTIONS_H_ -#define COMPONENTS_POWER_BOOKMARKS_CORE_FLAG_DESCRIPTIONS_H_ - -namespace power_bookmarks::flag_descriptions { - -extern const char kSimplifiedBookmarkSaveFlowName[]; -extern const char kSimplifiedBookmarkSaveFlowDescription[]; - -} // namespace power_bookmarks::flag_descriptions - -#endif // COMPONENTS_POWER_BOOKMARKS_CORE_FLAG_DESCRIPTIONS_H_
diff --git a/components/power_bookmarks/core/power_bookmark_features.cc b/components/power_bookmarks/core/power_bookmark_features.cc index 678d58e..a2cc053 100644 --- a/components/power_bookmarks/core/power_bookmark_features.cc +++ b/components/power_bookmarks/core/power_bookmark_features.cc
@@ -11,8 +11,4 @@ "PowerBookmarkBackend", base::FEATURE_DISABLED_BY_DEFAULT); -BASE_FEATURE(kSimplifiedBookmarkSaveFlow, - "SimplifiedBookmarkSaveFlow", - base::FEATURE_ENABLED_BY_DEFAULT); - } // namespace power_bookmarks
diff --git a/components/power_bookmarks/core/power_bookmark_features.h b/components/power_bookmarks/core/power_bookmark_features.h index 6f8448c..665b8a0 100644 --- a/components/power_bookmarks/core/power_bookmark_features.h +++ b/components/power_bookmarks/core/power_bookmark_features.h
@@ -11,8 +11,6 @@ // Controls the power bookmarks backend. BASE_DECLARE_FEATURE(kPowerBookmarkBackend); -BASE_DECLARE_FEATURE(kSimplifiedBookmarkSaveFlow); - } // namespace power_bookmarks #endif // COMPONENTS_POWER_BOOKMARKS_CORE_POWER_BOOKMARK_FEATURES_H_
diff --git a/components/reading_list/core/dual_reading_list_model.cc b/components/reading_list/core/dual_reading_list_model.cc index 48f7540..773bef0 100644 --- a/components/reading_list/core/dual_reading_list_model.cc +++ b/components/reading_list/core/dual_reading_list_model.cc
@@ -609,9 +609,6 @@ return; } - // Only expected for changes received via sync. - DCHECK(ToReadingListModelImpl(model)->IsTrackingSyncMetadata()); - NotifyObserversWithWillMoveEntry(url); UpdateEntryStateCountersOnEntryRemoval(*GetEntryByURL(url)); } @@ -623,9 +620,6 @@ return; } - // Only expected for changes received via sync. - DCHECK(ToReadingListModelImpl(model)->IsTrackingSyncMetadata()); - UpdateEntryStateCountersOnEntryInsertion(*GetEntryByURL(url)); NotifyObserversWithDidMoveEntry(url); } @@ -812,4 +806,13 @@ return local_or_syncable_model_->GetKeys(); } +ReadingListModel* DualReadingListModel::GetLocalOrSyncableModel() { + return local_or_syncable_model_.get(); +} + +ReadingListModel* DualReadingListModel::GetAccountModelIfSyncing() { + return account_model_->IsTrackingSyncMetadata() ? account_model_.get() + : nullptr; +} + } // namespace reading_list
diff --git a/components/reading_list/core/dual_reading_list_model.h b/components/reading_list/core/dual_reading_list_model.h index 4505eabf..47f070f2 100644 --- a/components/reading_list/core/dual_reading_list_model.h +++ b/components/reading_list/core/dual_reading_list_model.h
@@ -138,6 +138,13 @@ StorageStateForTesting GetStorageStateForURLForTesting(const GURL& url); + // Returns the model responsible for the local/syncable reading list. + ReadingListModel* GetLocalOrSyncableModel(); + // Returns the model responsible for the account-bound reading list. This can + // toggle between null and non-null at runtime depending on the sync/signin + // state. + ReadingListModel* GetAccountModelIfSyncing(); + private: void NotifyObserversWithWillRemoveEntry(const GURL& url); void NotifyObserversWithDidRemoveEntry(const GURL& url);
diff --git a/components/reading_list/core/dual_reading_list_model_unittest.cc b/components/reading_list/core/dual_reading_list_model_unittest.cc index b9f3a20..5ab8aea 100644 --- a/components/reading_list/core/dual_reading_list_model_unittest.cc +++ b/components/reading_list/core/dual_reading_list_model_unittest.cc
@@ -130,6 +130,7 @@ absl::optional<base::FilePath> distilation_path_; }; +// TODO(crbug.com/1510547): Add test coverage for GetAccountModelIfSyncing. class DualReadingListModelTest : public testing::Test { public: DualReadingListModelTest() = default;
diff --git a/components/reporting/storage/storage_unittest.cc b/components/reporting/storage/storage_unittest.cc index 6a315ea..b267e45 100644 --- a/components/reporting/storage/storage_unittest.cc +++ b/components/reporting/storage/storage_unittest.cc
@@ -762,7 +762,7 @@ const raw_ptr<base::flat_map<Priority, int64_t>> last_upload_generation_id_; const raw_ptr<LastRecordDigestMap> last_record_digest_map_; - const raw_ptr<const MockUpload, DanglingUntriaged> mock_upload_; + const raw_ptr<const MockUpload> mock_upload_; const base::SequenceBound<SequenceBoundUpload> sequence_bound_upload_; const scoped_refptr<test::Decryptor> decryptor_;
diff --git a/components/safe_browsing/core/browser/db/v4_local_database_manager.cc b/components/safe_browsing/core/browser/db/v4_local_database_manager.cc index fde6764..f13b28b 100644 --- a/components/safe_browsing/core/browser/db/v4_local_database_manager.cc +++ b/components/safe_browsing/core/browser/db/v4_local_database_manager.cc
@@ -935,19 +935,21 @@ } } + bool did_match_allowlist = *match == AsyncMatch::MATCH; if (check->client_callback_type == ClientCallbackType::CHECK_OTHER) { - bool result = *match == AsyncMatch::MATCH; if (GetPrefixMatchesIsAsync()) { // This is already asynchronous so no need for another PostTask. - std::move(callback).Run(result); + std::move(callback).Run(did_match_allowlist); } else { - sb_task_runner()->PostTask(FROM_HERE, - base::BindOnce(std::move(callback), result)); + sb_task_runner()->PostTask( + FROM_HERE, base::BindOnce(std::move(callback), did_match_allowlist)); } } else if (check->client_callback_type == ClientCallbackType::CHECK_CSD_ALLOWLIST) { if (GetPrefixMatchesIsAsync()) { - check->most_severe_threat_type = SB_THREAT_TYPE_CSD_ALLOWLIST; + check->most_severe_threat_type = did_match_allowlist + ? SB_THREAT_TYPE_CSD_ALLOWLIST + : SB_THREAT_TYPE_SAFE; RespondToClient(std::move(check)); } } else {
diff --git a/components/safe_browsing/core/browser/db/v4_local_database_manager_unittest.cc b/components/safe_browsing/core/browser/db/v4_local_database_manager_unittest.cc index 636f685..493fb0a 100644 --- a/components/safe_browsing/core/browser/db/v4_local_database_manager_unittest.cc +++ b/components/safe_browsing/core/browser/db/v4_local_database_manager_unittest.cc
@@ -740,7 +740,7 @@ ReplaceV4Database(store_and_hash_prefixes, /* stores_available= */ true); TestAllowlistClient client( - /* match_expected= */ true, + /* match_expected= */ false, /* expected_sb_threat_type= */ SB_THREAT_TYPE_CSD_ALLOWLIST); const GURL url_check("https://other.com/"); auto result =
diff --git a/content/browser/accessibility/dump_accessibility_tree_browsertest.cc b/content/browser/accessibility/dump_accessibility_tree_browsertest.cc index c165b8b7..3e5217b 100644 --- a/content/browser/accessibility/dump_accessibility_tree_browsertest.cc +++ b/content/browser/accessibility/dump_accessibility_tree_browsertest.cc
@@ -3729,9 +3729,12 @@ RunRegressionTest(FILE_PATH_LITERAL("title-in-shadow.html")); } -// TODO(https://crbug.com/1175562): Flaky -IN_PROC_BROWSER_TEST_P(DumpAccessibilityTreeTest, - DISABLED_ReusedMapChangeMapName) { +IN_PROC_BROWSER_TEST_P(DumpAccessibilityTreeTest, ReusedMapChangeMapName) { + RunRegressionTest(FILE_PATH_LITERAL("reused-map-change-map-name.html")); +} + +IN_PROC_BROWSER_TEST_P(YieldingParserDumpAccessibilityTreeTest, + ReusedMapChangeMapName) { RunRegressionTest(FILE_PATH_LITERAL("reused-map-change-map-name.html")); }
diff --git a/content/browser/android/nfc_host.cc b/content/browser/android/nfc_host.cc index 1696f3c..98ee802 100644 --- a/content/browser/android/nfc_host.cc +++ b/content/browser/android/nfc_host.cc
@@ -68,14 +68,17 @@ if (!subscription_id_) { // base::Unretained() is safe here because the subscription is canceled when // this object is destroyed. - // TODO(crbug.com/1271543) : Move `SubscribePermissionStatusChange` to + // TODO(crbug.com/1271543) : Move `SubscribeToPermissionStatusChange` to // `PermissionController`. - subscription_id_ = permission_controller_->SubscribePermissionStatusChange( - blink::PermissionType::NFC, /*render_process_host=*/nullptr, - render_frame_host, - render_frame_host->GetMainFrame()->GetLastCommittedOrigin().GetURL(), - base::BindRepeating(&NFCHost::OnPermissionStatusChange, - base::Unretained(this))); + subscription_id_ = + permission_controller_->SubscribeToPermissionStatusChange( + blink::PermissionType::NFC, /*render_process_host=*/nullptr, + render_frame_host, + render_frame_host->GetMainFrame() + ->GetLastCommittedOrigin() + .GetURL(), + base::BindRepeating(&NFCHost::OnPermissionStatusChange, + base::Unretained(this))); } if (!nfc_provider_) { @@ -125,7 +128,8 @@ void NFCHost::Close() { nfc_provider_.reset(); - permission_controller_->UnsubscribePermissionStatusChange(subscription_id_); + permission_controller_->UnsubscribeFromPermissionStatusChange( + subscription_id_); subscription_id_ = PermissionController::SubscriptionId(); }
diff --git a/content/browser/android/nfc_host_unittest.cc b/content/browser/android/nfc_host_unittest.cc index 743e9b42..261ce33 100644 --- a/content/browser/android/nfc_host_unittest.cc +++ b/content/browser/android/nfc_host_unittest.cc
@@ -60,9 +60,9 @@ .WillOnce(Return(blink::mojom::PermissionStatus::GRANTED)) .WillOnce(Return(blink::mojom::PermissionStatus::GRANTED)); EXPECT_CALL(mock_permission_manager(), - SubscribePermissionStatusChange(blink::PermissionType::NFC, - /*render_process_host=*/nullptr, - main_rfh(), GURL(kTestUrl), _)) + SubscribeToPermissionStatusChange(blink::PermissionType::NFC, + /*render_process_host=*/nullptr, + main_rfh(), GURL(kTestUrl), _)) .WillOnce(Return(kSubscriptionId)); mojo::Remote<device::mojom::NFC> nfc1, nfc2; @@ -75,7 +75,7 @@ EXPECT_TRUE(nfc2.is_bound()); EXPECT_CALL(mock_permission_manager(), - UnsubscribePermissionStatusChange(kSubscriptionId)); + UnsubscribeFromPermissionStatusChange(kSubscriptionId)); DeleteContents(); }
diff --git a/content/browser/attribution_reporting/attribution_host_unittest.cc b/content/browser/attribution_reporting/attribution_host_unittest.cc index 154d362..24e017e7 100644 --- a/content/browser/attribution_reporting/attribution_host_unittest.cc +++ b/content/browser/attribution_reporting/attribution_host_unittest.cc
@@ -122,10 +122,10 @@ // permissions policy set. FrameTreeNode* fenced_frame_node = static_cast<RenderFrameHostImpl*>(fenced_frame)->frame_tree_node(); - absl::optional<FencedFrameProperties> new_props = - fenced_frame_node->GetFencedFrameProperties(); - new_props->effective_enabled_permissions.push_back( + FencedFrameConfig new_config = FencedFrameConfig(GURL("about:blank")); + new_config.effective_enabled_permissions.push_back( blink::mojom::PermissionsPolicyFeature::kAttributionReporting); + FencedFrameProperties new_props = FencedFrameProperties(new_config); fenced_frame_node->set_fenced_frame_properties(new_props); }
diff --git a/content/browser/attribution_reporting/attribution_storage_sql.cc b/content/browser/attribution_reporting/attribution_storage_sql.cc index 58d971a..40e39f6 100644 --- a/content/browser/attribution_reporting/attribution_storage_sql.cc +++ b/content/browser/attribution_reporting/attribution_storage_sql.cc
@@ -21,6 +21,7 @@ #include "base/check_op.h" #include "base/containers/enum_set.h" #include "base/containers/flat_set.h" +#include "base/containers/span.h" #include "base/files/file_util.h" #include "base/functional/bind.h" #include "base/functional/overloaded.h" @@ -831,14 +832,10 @@ int64_t min_priority; while (min_priority_statement.Step()) { - std::string metadata; - if (!min_priority_statement.ColumnBlobAsString(0, &metadata)) { - continue; - } - uint32_t trigger_data; int64_t priority; - if (!DeserializeReportMetadata(metadata, trigger_data, priority)) { + if (base::span<const uint8_t> blob = min_priority_statement.ColumnBlob(0); + !DeserializeReportMetadata(blob, trigger_data, priority)) { continue; } @@ -1542,13 +1539,9 @@ corruption_causes.Put(ReportCorruptionStatus::kReportingOriginMismatch); } - std::string metadata; - if (!statement.ColumnBlobAsString(col++, &metadata)) { - corruption_causes.Put(ReportCorruptionStatus::kMetadataAsStringFailed); - } - absl::optional<AttributionReport::Data> data; - switch (*report_type) { + switch (base::span<const uint8_t> metadata = statement.ColumnBlob(col++); + *report_type) { case AttributionReport::Type::kEventLevel: { if (!source_data.has_value()) { corruption_causes.Put(
diff --git a/content/browser/attribution_reporting/attribution_storage_sql.h b/content/browser/attribution_reporting/attribution_storage_sql.h index 8d50665..7c1c5d8 100644 --- a/content/browser/attribution_reporting/attribution_storage_sql.h +++ b/content/browser/attribution_reporting/attribution_storage_sql.h
@@ -93,7 +93,7 @@ kInvalidReportingOrigin = 4, kInvalidReportType = 5, kReportingOriginMismatch = 6, - kMetadataAsStringFailed = 7, + // Obsolete: kMetadataAsStringFailed = 7, kSourceDataMissingEventLevel = 8, kSourceDataMissingAggregatable = 9, kSourceDataFoundNullAggregatable = 10,
diff --git a/content/browser/attribution_reporting/attribution_storage_sql_migrations_unittest.cc b/content/browser/attribution_reporting/attribution_storage_sql_migrations_unittest.cc index aca04ee..f05c74b 100644 --- a/content/browser/attribution_reporting/attribution_storage_sql_migrations_unittest.cc +++ b/content/browser/attribution_reporting/attribution_storage_sql_migrations_unittest.cc
@@ -4,6 +4,7 @@ #include "content/browser/attribution_reporting/attribution_storage_sql_migrations.h" +#include "base/containers/span.h" #include "base/files/file_path.h" #include "base/files/file_util.h" #include "base/files/scoped_temp_dir.h" @@ -362,9 +363,10 @@ db.GetUniqueStatement("SELECT read_only_source_data FROM sources")); ASSERT_TRUE(s.Step()); proto::AttributionReadOnlySourceData msg; - std::string blob; - ASSERT_TRUE(s.ColumnBlobAsString(0, &blob)); - ASSERT_TRUE(msg.ParseFromString(blob)); + { + base::span<const uint8_t> blob = s.ColumnBlob(0); + ASSERT_TRUE(msg.ParseFromArray(blob.data(), blob.size())); + } EXPECT_EQ(3, msg.max_event_level_reports()); EXPECT_FALSE(msg.has_randomized_response_rate()); EXPECT_EQ(0, msg.event_level_report_window_start_time());
diff --git a/content/browser/attribution_reporting/attribution_storage_sql_unittest.cc b/content/browser/attribution_reporting/attribution_storage_sql_unittest.cc index 61a8763..43af75e 100644 --- a/content/browser/attribution_reporting/attribution_storage_sql_unittest.cc +++ b/content/browser/attribution_reporting/attribution_storage_sql_unittest.cc
@@ -15,6 +15,7 @@ #include <vector> #include "base/check.h" +#include "base/containers/span.h" #include "base/files/file_util.h" #include "base/files/scoped_temp_dir.h" #include "base/functional/bind.h" @@ -1761,11 +1762,11 @@ while (get_statement.Step()) { int64_t id = get_statement.ColumnInt64(0); - std::string blob; - ASSERT_TRUE(get_statement.ColumnBlobAsString(1, &blob)); - proto::AttributionReadOnlySourceData msg; - ASSERT_TRUE(msg.ParseFromString(blob)); + { + base::span<const uint8_t> blob = get_statement.ColumnBlob(1); + ASSERT_TRUE(msg.ParseFromArray(blob.data(), blob.size())); + } msg.clear_randomized_response_rate(); @@ -1805,11 +1806,11 @@ while (get_statement.Step()) { int64_t id = get_statement.ColumnInt64(0); - std::string blob; - ASSERT_TRUE(get_statement.ColumnBlobAsString(1, &blob)); - proto::AttributionReadOnlySourceData msg; - ASSERT_TRUE(msg.ParseFromString(blob)); + { + base::span<const uint8_t> blob = get_statement.ColumnBlob(1); + ASSERT_TRUE(msg.ParseFromArray(blob.data(), blob.size())); + } msg.clear_event_level_epsilon();
diff --git a/content/browser/attribution_reporting/sql_utils.cc b/content/browser/attribution_reporting/sql_utils.cc index 2bd970b..6bf9fa4 100644 --- a/content/browser/attribution_reporting/sql_utils.cc +++ b/content/browser/attribution_reporting/sql_utils.cc
@@ -11,6 +11,7 @@ #include <utility> #include <vector> +#include "base/containers/span.h" #include "base/feature_list.h" #include "base/time/time.h" #include "components/aggregation_service/features.h" @@ -195,13 +196,10 @@ absl::optional<proto::AttributionReadOnlySourceData> DeserializeReadOnlySourceDataAsProto(sql::Statement& stmt, int col) { - std::string str; - if (!stmt.ColumnBlobAsString(col, &str)) { - return absl::nullopt; - } proto::AttributionReadOnlySourceData msg; - if (!msg.ParseFromString(str)) { + if (base::span<const uint8_t> blob = stmt.ColumnBlob(col); + !msg.ParseFromArray(blob.data(), blob.size())) { return absl::nullopt; } return msg; @@ -223,13 +221,9 @@ absl::optional<attribution_reporting::FilterData> DeserializeFilterData( sql::Statement& stmt, int col) { - std::string string; - if (!stmt.ColumnBlobAsString(col, &string)) { - return absl::nullopt; - } - proto::AttributionFilterData msg; - if (!msg.ParseFromString(string)) { + if (base::span<const uint8_t> blob = stmt.ColumnBlob(col); + !msg.ParseFromArray(blob.data(), blob.size())) { return absl::nullopt; } @@ -273,13 +267,9 @@ absl::optional<attribution_reporting::AggregationKeys> DeserializeAggregationKeys(sql::Statement& stmt, int col) { - std::string str; - if (!stmt.ColumnBlobAsString(col, &str)) { - return absl::nullopt; - } - proto::AttributionAggregatableSource msg; - if (!msg.ParseFromString(str)) { + if (base::span<const uint8_t> blob = stmt.ColumnBlob(col); + !msg.ParseFromArray(blob.data(), blob.size())) { return absl::nullopt; } @@ -305,12 +295,12 @@ return msg.SerializeAsString(); } -bool DeserializeReportMetadata(const std::string& str, +bool DeserializeReportMetadata(base::span<const uint8_t> blob, uint32_t& trigger_data, int64_t& priority) { proto::AttributionEventLevelMetadata msg; - if (!msg.ParseFromString(str) || !msg.has_trigger_data() || - !msg.has_priority()) { + if (!msg.ParseFromArray(blob.data(), blob.size()) || + !msg.has_trigger_data() || !msg.has_priority()) { return false; } @@ -340,11 +330,11 @@ } bool DeserializeReportMetadata( - const std::string& str, + base::span<const uint8_t> blob, AttributionReport::AggregatableAttributionData& data) { proto::AttributionAggregatableMetadata msg; - if (!msg.ParseFromString(str) || msg.contributions().empty() || - !msg.has_common_data() || + if (!msg.ParseFromArray(blob.data(), blob.size()) || + msg.contributions().empty() || !msg.has_common_data() || !DeserializeCommonAggregatableData(msg.common_data(), data.common_data)) { return false; } @@ -378,11 +368,11 @@ return msg.SerializeAsString(); } -bool DeserializeReportMetadata(const std::string& str, +bool DeserializeReportMetadata(base::span<const uint8_t> blob, AttributionReport::NullAggregatableData& data) { proto::AttributionNullAggregatableMetadata msg; - if (!msg.ParseFromString(str) || !msg.has_fake_source_time() || - !msg.has_common_data() || + if (!msg.ParseFromArray(blob.data(), blob.size()) || + !msg.has_fake_source_time() || !msg.has_common_data() || !DeserializeCommonAggregatableData(msg.common_data(), data.common_data)) { return false; }
diff --git a/content/browser/attribution_reporting/sql_utils.h b/content/browser/attribution_reporting/sql_utils.h index 04e9a00..64f767cb 100644 --- a/content/browser/attribution_reporting/sql_utils.h +++ b/content/browser/attribution_reporting/sql_utils.h
@@ -9,6 +9,7 @@ #include <string> +#include "base/containers/span.h" #include "components/attribution_reporting/source_type.mojom-forward.h" #include "components/attribution_reporting/trigger_data_matching.mojom-forward.h" #include "content/browser/attribution_reporting/attribution_report.h" @@ -80,16 +81,16 @@ std::string SerializeReportMetadata( const AttributionReport::NullAggregatableData&); -[[nodiscard]] bool DeserializeReportMetadata(const std::string&, +[[nodiscard]] bool DeserializeReportMetadata(base::span<const uint8_t>, uint32_t& trigger_data, int64_t& priority); [[nodiscard]] bool DeserializeReportMetadata( - const std::string&, + base::span<const uint8_t>, AttributionReport::AggregatableAttributionData&); [[nodiscard]] bool DeserializeReportMetadata( - const std::string&, + base::span<const uint8_t>, AttributionReport::NullAggregatableData&); } // namespace content
diff --git a/content/browser/client_hints/client_hints.cc b/content/browser/client_hints/client_hints.cc index adf593b..92a3236 100644 --- a/content/browser/client_hints/client_hints.cc +++ b/content/browser/client_hints/client_hints.cc
@@ -574,7 +574,7 @@ frame_tree_node->GetFencedFrameProperties(); base::span<const blink::mojom::PermissionsPolicyFeature> permissions; if (fenced_frame_properties) { - permissions = fenced_frame_properties->effective_enabled_permissions; + permissions = fenced_frame_properties->effective_enabled_permissions(); } permissions_policy = blink::PermissionsPolicy::CreateForFencedFrame( resource_origin, permissions);
diff --git a/content/browser/fenced_frame/fenced_frame_config.cc b/content/browser/fenced_frame/fenced_frame_config.cc index f8a5f4ac..b31b8661 100644 --- a/content/browser/fenced_frame/fenced_frame_config.cc +++ b/content/browser/fenced_frame/fenced_frame_config.cc
@@ -238,7 +238,7 @@ VisibilityToContent::kOpaque), mode_(config.mode_), is_ad_component_(config.is_ad_component_), - effective_enabled_permissions(config.effective_enabled_permissions) { + effective_enabled_permissions_(config.effective_enabled_permissions) { if (config.shared_storage_budget_metadata_) { shared_storage_budget_metadata_.emplace( &config.shared_storage_budget_metadata_->GetValueIgnoringVisibility(), @@ -322,7 +322,7 @@ redacted_properties.mode_ = mode_; redacted_properties.effective_enabled_permissions_ = - effective_enabled_permissions; + effective_enabled_permissions_; return redacted_properties; }
diff --git a/content/browser/fenced_frame/fenced_frame_config.h b/content/browser/fenced_frame/fenced_frame_config.h index 9fa9503..7bb767b 100644 --- a/content/browser/fenced_frame/fenced_frame_config.h +++ b/content/browser/fenced_frame/fenced_frame_config.h
@@ -40,9 +40,6 @@ // `FencedFrameConfig` and the `kEmbedder` entity. The constructor // automatically performs the redaction process. // -// TODO(crbug.com/1347953): Remove this disclaimer. -// (Note: the following two steps aren't implemented yet, and are currently -// accomplished with urns.) // * FLEDGE returns the redacted config to the embedder's renderer. // `RedactedFencedFrameConfig` supports mojom type mappings for // `blink::mojom::FencedFrameConfig`. @@ -200,7 +197,7 @@ private: friend class content::FencedFrameURLMapping; friend struct FencedFrameConfig; - friend struct FencedFrameProperties; + friend class FencedFrameProperties; T value_; VisibilityToEmbedder visibility_to_embedder_; @@ -333,8 +330,8 @@ // These `FencedFrameProperties` are stored in the fenced frame root // `FrameTreeNode`, and live between embedder-initiated fenced frame // navigations. -// TODO(crbug.com/1417871): Turn this into a class and make its fields private. -struct CONTENT_EXPORT FencedFrameProperties { +class CONTENT_EXPORT FencedFrameProperties { + public: // The empty constructor is used for: // * pre-navigation fenced frames // * embedder-initiated non-opaque url navigations @@ -354,8 +351,6 @@ blink::FencedFrame::RedactedFencedFrameProperties RedactFor( FencedFrameEntity entity) const; - absl::optional<FencedFrameProperty<GURL>> mapped_url_; - // Update the stored mapped URL to a new one given by `url`. // `this` must have a value for `mapped_url_` when the function is called. // We use this method when an embedder-initiated fenced frame root navigation @@ -380,6 +375,90 @@ const absl::optional<AutomaticBeaconInfo> GetAutomaticBeaconInfo( blink::mojom::AutomaticBeaconType event_type) const; + const absl::optional<FencedFrameProperty<GURL>>& mapped_url() const { + return mapped_url_; + } + + const absl::optional<FencedFrameProperty<AdAuctionData>>& ad_auction_data() + const { + return ad_auction_data_; + } + + const base::RepeatingClosure& on_navigate_callback() const { + return on_navigate_callback_; + } + + const absl::optional< + FencedFrameProperty<std::vector<std::pair<GURL, FencedFrameConfig>>>> + nested_urn_config_pairs() const { + return nested_urn_config_pairs_; + } + + const absl::optional< + FencedFrameProperty<raw_ptr<const SharedStorageBudgetMetadata>>>& + shared_storage_budget_metadata() const { + return shared_storage_budget_metadata_; + } + + const absl::optional<std::u16string>& embedder_shared_storage_context() + const { + return embedder_shared_storage_context_; + } + + // Used to store the shared storage context passed from the embedder + // (navigation initiator)'s renderer into the new FencedFrameProperties. + // TODO(crbug.com/1417871): Refactor this to be part of the + // FencedFrameProperties constructor rather than + // OnFencedFrameURLMappingComplete. + void SetEmbedderSharedStorageContext( + const absl::optional<std::u16string>& embedder_shared_storage_context) { + embedder_shared_storage_context_ = embedder_shared_storage_context; + } + + const scoped_refptr<FencedFrameReporter>& fenced_frame_reporter() const { + return fenced_frame_reporter_; + } + + const absl::optional<FencedFrameProperty<base::UnguessableToken>>& + partition_nonce() const { + return partition_nonce_; + } + + // Used for urn iframes, which should not have a separate storage/network + // partition. + // TODO(crbug.com/1417871): Refactor this to be part of the + // FencedFrameProperties constructor rather than + // OnFencedFrameURLMappingComplete. + void ClearPartitionNonce() { partition_nonce_ = absl::nullopt; } + + const DeprecatedFencedFrameMode& mode() const { return mode_; } + + bool is_ad_component() const { return is_ad_component_; } + + const std::vector<blink::mojom::PermissionsPolicyFeature>& + effective_enabled_permissions() const { + return effective_enabled_permissions_; + } + + // Set the current FencedFrameProperties to have "opaque ads mode". + // This should only be used during tests, when the proper embedder-initiated + // fenced frame root urn/config navigation flow isn't available. + // TODO(crbug.com/1347953): Refactor and expand use of test utils so there is + // a consistent way to do this properly everywhere. Consider removing + // arbitrary restrictions in "default mode" so that using opaque ads mode is + // less necessary. + void SetFencedFramePropertiesOpaqueAdsModeForTesting() { + mode_ = blink::FencedFrame::DeprecatedFencedFrameMode::kOpaqueAds; + } + + private: + FRIEND_TEST_ALL_PREFIXES(FencedFrameConfigMojomTraitsTest, + ConfigMojomTraitsTest); + FRIEND_TEST_ALL_PREFIXES(FencedFrameConfigMojomTraitsTest, + PropertiesHasFencedFrameReportingTest); + + absl::optional<FencedFrameProperty<GURL>> mapped_url_; + absl::optional<FencedFrameProperty<gfx::Size>> container_size_; // TODO(crbug.com/1420638): The representation of size in fenced frame config @@ -452,7 +531,7 @@ // See entry in spec: // https://wicg.github.io/fenced-frame/#fenced-frame-config-effective-enabled-permissions std::vector<blink::mojom::PermissionsPolicyFeature> - effective_enabled_permissions; + effective_enabled_permissions_; }; } // namespace content
diff --git a/content/browser/fenced_frame/redacted_fenced_frame_config_mojom_traits_unittest.cc b/content/browser/fenced_frame/redacted_fenced_frame_config_mojom_traits_unittest.cc index 2808737..16175e8 100644 --- a/content/browser/fenced_frame/redacted_fenced_frame_config_mojom_traits_unittest.cc +++ b/content/browser/fenced_frame/redacted_fenced_frame_config_mojom_traits_unittest.cc
@@ -301,7 +301,7 @@ RedactedFencedFrameProperties input_properties = browser_properties.RedactFor(entity); - ASSERT_TRUE(browser_properties.mode_ == input_properties.mode()); + ASSERT_TRUE(browser_properties.mode() == input_properties.mode()); RedactedFencedFrameProperties output_properties; mojo::test::SerializeAndDeserialize<blink::mojom::FencedFrameProperties>(
diff --git a/content/browser/geolocation/geolocation_service_impl.cc b/content/browser/geolocation/geolocation_service_impl.cc index c8accdc..bf104fc 100644 --- a/content/browser/geolocation/geolocation_service_impl.cc +++ b/content/browser/geolocation/geolocation_service_impl.cc
@@ -126,7 +126,7 @@ subscription_id_ = PermissionControllerImpl::FromBrowserContext( render_frame_host_->GetBrowserContext()) - ->SubscribePermissionStatusChange( + ->SubscribeToPermissionStatusChange( blink::PermissionType::GEOLOCATION, /*render_process_host=*/nullptr, render_frame_host_, requesting_url, @@ -141,7 +141,7 @@ subscription_id_.value()) { PermissionControllerImpl::FromBrowserContext( render_frame_host_->GetBrowserContext()) - ->UnsubscribePermissionStatusChange(subscription_id_); + ->UnsubscribeFromPermissionStatusChange(subscription_id_); geolocation_context_->OnPermissionRevoked(requesting_origin_); } }
diff --git a/content/browser/interest_group/ad_auction_service_impl.cc b/content/browser/interest_group/ad_auction_service_impl.cc index 832f4af..706b4199 100644 --- a/content/browser/interest_group/ad_auction_service_impl.cc +++ b/content/browser/interest_group/ad_auction_service_impl.cc
@@ -246,11 +246,11 @@ return; } - if (!fenced_frame_properties->ad_auction_data_.has_value()) { + if (!fenced_frame_properties->ad_auction_data().has_value()) { return; } - if (fenced_frame_properties->is_ad_component_ && + if (fenced_frame_properties->is_ad_component() && !base::FeatureList::IsEnabled( blink::features::kFencedFramesM120FeaturesPart2)) { // The ability to leave interest group from an ad component is not supported @@ -259,7 +259,7 @@ } const blink::FencedFrame::AdAuctionData& auction_data = - fenced_frame_properties->ad_auction_data_->GetValueIgnoringVisibility(); + fenced_frame_properties->ad_auction_data()->GetValueIgnoringVisibility(); if (auction_data.interest_group_owner != origin()) { // The ad page calling LeaveAdInterestGroup is not the owner of the group. @@ -447,11 +447,11 @@ void OnFencedFrameURLMappingComplete( const absl::optional<FencedFrameProperties>& properties) override { if (properties) { - if (properties->mapped_url_) { - *mapped_url_ = properties->mapped_url_->GetValueIgnoringVisibility(); + if (properties->mapped_url()) { + *mapped_url_ = properties->mapped_url()->GetValueIgnoringVisibility(); } - if (send_reports_ && properties->on_navigate_callback_) { - properties->on_navigate_callback_.Run(); + if (send_reports_ && properties->on_navigate_callback()) { + properties->on_navigate_callback().Run(); } } called_ = true;
diff --git a/content/browser/interest_group/ad_auction_service_impl_unittest.cc b/content/browser/interest_group/ad_auction_service_impl_unittest.cc index 9bba82d..935c233 100644 --- a/content/browser/interest_group/ad_auction_service_impl_unittest.cc +++ b/content/browser/interest_group/ad_auction_service_impl_unittest.cc
@@ -833,8 +833,8 @@ absl::optional<GURL> ConvertFencedFrameURNToURL(const GURL& urn_url) { auto properties = GetFencedFramePropertiesForURN(urn_url); - if (properties && properties->mapped_url_.has_value()) { - return properties->mapped_url_->GetValueIgnoringVisibility(); + if (properties && properties->mapped_url().has_value()) { + return properties->mapped_url()->GetValueIgnoringVisibility(); } return absl::nullopt; } @@ -846,7 +846,7 @@ void InvokeCallbackForURN(const GURL& urn_url) { auto properties = GetFencedFramePropertiesForURN(urn_url); ASSERT_TRUE(properties); - properties->on_navigate_callback_.Run(); + properties->on_navigate_callback().Run(); } // Creates a new AdAuctionServiceImpl and use it to try and join @@ -10798,7 +10798,7 @@ GetFencedFramePropertiesForURN(*result); ASSERT_TRUE(properties); EXPECT_THAT( - properties->fenced_frame_reporter_->GetAdBeaconMapForTesting(), + properties->fenced_frame_reporter()->GetAdBeaconMapForTesting(), testing::UnorderedElementsAre( testing::Pair( blink::FencedFrame::ReportingDestination::kBuyer, @@ -11082,7 +11082,7 @@ GetFencedFramePropertiesForURN(*result); ASSERT_TRUE(properties); EXPECT_THAT( - properties->fenced_frame_reporter_->GetAdBeaconMapForTesting(), + properties->fenced_frame_reporter()->GetAdBeaconMapForTesting(), testing::UnorderedElementsAre( testing::Pair( blink::FencedFrame::ReportingDestination::kBuyer, @@ -11707,7 +11707,7 @@ GetFencedFramePropertiesForURN(*result); ASSERT_TRUE(properties); EXPECT_THAT( - properties->fenced_frame_reporter_->GetAdBeaconMapForTesting(), + properties->fenced_frame_reporter()->GetAdBeaconMapForTesting(), testing::UnorderedElementsAre( testing::Pair( blink::FencedFrame::ReportingDestination::kBuyer, @@ -11913,7 +11913,7 @@ GetFencedFramePropertiesForURN(*result); ASSERT_TRUE(properties); EXPECT_THAT( - properties->fenced_frame_reporter_->GetAdBeaconMapForTesting(), + properties->fenced_frame_reporter()->GetAdBeaconMapForTesting(), testing::UnorderedElementsAre( testing::Pair( blink::FencedFrame::ReportingDestination::kBuyer, @@ -12121,7 +12121,7 @@ GetFencedFramePropertiesForURN(*result); ASSERT_TRUE(properties); EXPECT_THAT( - properties->fenced_frame_reporter_->GetAdBeaconMapForTesting(), + properties->fenced_frame_reporter()->GetAdBeaconMapForTesting(), testing::UnorderedElementsAre( testing::Pair( blink::FencedFrame::ReportingDestination::kBuyer, @@ -12291,7 +12291,7 @@ GetFencedFramePropertiesForURN(*result); ASSERT_TRUE(properties); EXPECT_THAT( - properties->fenced_frame_reporter_->GetAdBeaconMapForTesting(), + properties->fenced_frame_reporter()->GetAdBeaconMapForTesting(), testing::UnorderedElementsAre( testing::Pair( blink::FencedFrame::ReportingDestination::kBuyer, @@ -12471,7 +12471,7 @@ GetFencedFramePropertiesForURN(*result); ASSERT_TRUE(properties); EXPECT_THAT( - properties->fenced_frame_reporter_->GetAdBeaconMapForTesting(), + properties->fenced_frame_reporter()->GetAdBeaconMapForTesting(), testing::UnorderedElementsAre( testing::Pair(blink::FencedFrame::ReportingDestination::kBuyer, testing::ElementsAre()),
diff --git a/content/browser/permissions/permission_controller_impl.cc b/content/browser/permissions/permission_controller_impl.cc index 88ba1a3..b94bf6f 100644 --- a/content/browser/permissions/permission_controller_impl.cc +++ b/content/browser/permissions/permission_controller_impl.cc
@@ -651,7 +651,7 @@ } PermissionControllerImpl::SubscriptionId -PermissionControllerImpl::SubscribePermissionStatusChange( +PermissionControllerImpl::SubscribeToPermissionStatusChange( PermissionType permission, RenderProcessHost* render_process_host, RenderFrameHost* render_frame_host, @@ -682,7 +682,7 @@ browser_context_->GetPermissionControllerDelegate(); if (delegate) { subscription->delegate_subscription_id = - delegate->SubscribePermissionStatusChange( + delegate->SubscribeToPermissionStatusChange( permission, render_process_host, render_frame_host, requesting_origin, base::BindRepeating( @@ -694,17 +694,17 @@ } PermissionControllerImpl::SubscriptionId -PermissionControllerImpl::SubscribePermissionStatusChange( +PermissionControllerImpl::SubscribeToPermissionStatusChange( PermissionType permission, RenderProcessHost* render_process_host, const url::Origin& requesting_origin, const base::RepeatingCallback<void(PermissionStatus)>& callback) { - return SubscribePermissionStatusChange(permission, render_process_host, - /*render_frame_host=*/nullptr, - requesting_origin.GetURL(), callback); + return SubscribeToPermissionStatusChange( + permission, render_process_host, + /*render_frame_host=*/nullptr, requesting_origin.GetURL(), callback); } -void PermissionControllerImpl::UnsubscribePermissionStatusChange( +void PermissionControllerImpl::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) { Subscription* subscription = subscriptions_.Lookup(subscription_id); if (!subscription) @@ -712,7 +712,7 @@ PermissionControllerDelegate* delegate = browser_context_->GetPermissionControllerDelegate(); if (delegate) { - delegate->UnsubscribePermissionStatusChange( + delegate->UnsubscribeFromPermissionStatusChange( subscription->delegate_subscription_id); } subscriptions_.Remove(subscription_id);
diff --git a/content/browser/permissions/permission_controller_impl.h b/content/browser/permissions/permission_controller_impl.h index 8eb13dd..9d41d85c 100644 --- a/content/browser/permissions/permission_controller_impl.h +++ b/content/browser/permissions/permission_controller_impl.h
@@ -81,19 +81,19 @@ // Only one of |render_process_host| and |render_frame_host| should be set, // or neither. RenderProcessHost will be inferred from |render_frame_host|. - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( PermissionType permission, RenderProcessHost* render_process_host, RenderFrameHost* render_frame_host, const GURL& requesting_origin, const base::RepeatingCallback<void(PermissionStatus)>& callback); - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( PermissionType permission, RenderProcessHost* render_process_host, const url::Origin& requesting_origin, const base::RepeatingCallback<void(PermissionStatus)>& callback) override; - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; // If there's currently a permission prompt bubble for the given WebContents,
diff --git a/content/browser/permissions/permission_controller_impl_unittest.cc b/content/browser/permissions/permission_controller_impl_unittest.cc index 611c7fc8..8e4f52a 100644 --- a/content/browser/permissions/permission_controller_impl_unittest.cc +++ b/content/browser/permissions/permission_controller_impl_unittest.cc
@@ -381,11 +381,11 @@ kTestOrigin, PermissionType::GEOLOCATION, PermissionStatus::DENIED); base::MockCallback<PermissionStatusCallback> geo_callback; - permission_controller()->SubscribePermissionStatusChange( + permission_controller()->SubscribeToPermissionStatusChange( PermissionType::GEOLOCATION, nullptr, nullptr, kUrl, geo_callback.Get()); base::MockCallback<PermissionStatusCallback> sync_callback; - permission_controller()->SubscribePermissionStatusChange( + permission_controller()->SubscribeToPermissionStatusChange( PermissionType::BACKGROUND_SYNC, nullptr, nullptr, kUrl, sync_callback.Get());
diff --git a/content/browser/permissions/permission_service_context.cc b/content/browser/permissions/permission_service_context.cc index 3d4cd259..8c335a7 100644 --- a/content/browser/permissions/permission_service_context.cc +++ b/content/browser/permissions/permission_service_context.cc
@@ -63,7 +63,7 @@ BrowserContext* browser_context = context_->GetBrowserContext(); if (browser_context) { PermissionControllerImpl::FromBrowserContext(browser_context) - ->UnsubscribePermissionStatusChange(id_); + ->UnsubscribeFromPermissionStatusChange(id_); } } @@ -197,7 +197,7 @@ GURL requesting_origin(origin.Serialize()); auto subscription_id = PermissionControllerImpl::FromBrowserContext(browser_context) - ->SubscribePermissionStatusChange( + ->SubscribeToPermissionStatusChange( permission_type, render_process_host_, render_frame_host_, requesting_origin, base::BindRepeating(
diff --git a/content/browser/renderer_host/frame_tree_node.cc b/content/browser/renderer_host/frame_tree_node.cc index 39443f5b8..bda0a796 100644 --- a/content/browser/renderer_host/frame_tree_node.cc +++ b/content/browser/renderer_host/frame_tree_node.cc
@@ -958,7 +958,7 @@ // `properties` will exist for both fenced frames as well as iframes loaded // with a urn:uuid. This allows URN iframes to call this function without // getting bad-messaged. - if (!properties || !properties->fenced_frame_reporter_) { + if (!properties || !properties->fenced_frame_reporter()) { mojo::ReportBadMessage( "Automatic beacon data can only be set in fenced frames or iframes " "loaded from a config with a fenced frame reporter."); @@ -966,9 +966,9 @@ } // This metadata should only be present in the renderer in frames that are // same-origin to the mapped url. - if (!properties->mapped_url_.has_value() || + if (!properties->mapped_url().has_value() || !current_origin().IsSameOriginWith(url::Origin::Create( - properties->mapped_url_->GetValueIgnoringVisibility()))) { + properties->mapped_url()->GetValueIgnoringVisibility()))) { mojo::ReportBadMessage( "Automatic beacon data can only be set from documents that are same-" "origin to the mapped url from the fenced frame config."); @@ -992,7 +992,7 @@ // This implies the fenced frame is from shared storage. if (node->fenced_frame_properties_ && - node->fenced_frame_properties_->shared_storage_budget_metadata_) { + node->fenced_frame_properties_->shared_storage_budget_metadata()) { shared_storage_fenced_frame_root_count += 1; } } else { @@ -1015,8 +1015,8 @@ if (!root_fenced_frame_properties.has_value()) { return absl::nullopt; } - if (root_fenced_frame_properties->partition_nonce_.has_value()) { - return root_fenced_frame_properties->partition_nonce_ + if (root_fenced_frame_properties->partition_nonce().has_value()) { + return root_fenced_frame_properties->partition_nonce() ->GetValueIgnoringVisibility(); } // It is only possible for there to be `FencedFrameProperties` but no @@ -1056,7 +1056,7 @@ return blink::FencedFrame::DeprecatedFencedFrameMode::kDefault; } - return root_fenced_frame_properties->mode_; + return root_fenced_frame_properties->mode(); } bool FrameTreeNode::IsErrorPageIsolationEnabled() const { @@ -1075,9 +1075,9 @@ while (true) { if (node->fenced_frame_properties_ && - node->fenced_frame_properties_->shared_storage_budget_metadata_) { + node->fenced_frame_properties_->shared_storage_budget_metadata()) { result.emplace_back( - node->fenced_frame_properties_->shared_storage_budget_metadata_ + node->fenced_frame_properties_->shared_storage_budget_metadata() ->GetValueIgnoringVisibility()); } @@ -1097,12 +1097,12 @@ GetFencedFramePropertiesForEditing(); // We only return embedder context for frames that are same origin with the // fenced frame root or ancestor URN iframe. - if (!properties || !properties->mapped_url_.has_value() || + if (!properties || !properties->mapped_url().has_value() || !current_origin().IsSameOriginWith(url::Origin::Create( - properties->mapped_url_->GetValueIgnoringVisibility()))) { + properties->mapped_url()->GetValueIgnoringVisibility()))) { return absl::nullopt; } - return properties->embedder_shared_storage_context_; + return properties->embedder_shared_storage_context(); } const scoped_refptr<BrowsingContextState>&
diff --git a/content/browser/renderer_host/frame_tree_node.h b/content/browser/renderer_host/frame_tree_node.h index 7c8ac46a..215a374 100644 --- a/content/browser/renderer_host/frame_tree_node.h +++ b/content/browser/renderer_host/frame_tree_node.h
@@ -526,8 +526,8 @@ // less necessary. void SetFencedFramePropertiesOpaqueAdsModeForTesting() { if (fenced_frame_properties_.has_value()) { - fenced_frame_properties_->mode_ = - blink::FencedFrame::DeprecatedFencedFrameMode::kOpaqueAds; + fenced_frame_properties_ + ->SetFencedFramePropertiesOpaqueAdsModeForTesting(); } }
diff --git a/content/browser/renderer_host/media/media_stream_manager.cc b/content/browser/renderer_host/media/media_stream_manager.cc index ad844d2b..38175174 100644 --- a/content/browser/renderer_host/media/media_stream_manager.cc +++ b/content/browser/renderer_host/media/media_stream_manager.cc
@@ -4031,7 +4031,7 @@ if (is_audio_request) { // It is safe to bind base::Unretained(this) because MediaStreamManager is // owned by BrowserMainLoop. - audio_subscription_id = controller->SubscribePermissionStatusChange( + audio_subscription_id = controller->SubscribeToPermissionStatusChange( blink::PermissionType::AUDIO_CAPTURE, /*render_process_host=*/nullptr, RenderFrameHost::FromID(requesting_render_frame_host_id), origin, @@ -4044,7 +4044,7 @@ if (is_video_request) { // It is safe to bind base::Unretained(this) because MediaStreamManager is // owned by BrowserMainLoop. - video_subscription_id = controller->SubscribePermissionStatusChange( + video_subscription_id = controller->SubscribeToPermissionStatusChange( blink::PermissionType::VIDEO_CAPTURE, /*render_process_host=*/nullptr, RenderFrameHost::FromID(requesting_render_frame_host_id), origin, @@ -4104,8 +4104,8 @@ return; } - controller->UnsubscribePermissionStatusChange(audio_subscription_id); - controller->UnsubscribePermissionStatusChange(video_subscription_id); + controller->UnsubscribeFromPermissionStatusChange(audio_subscription_id); + controller->UnsubscribeFromPermissionStatusChange(video_subscription_id); } void MediaStreamManager::PermissionChangedCallback(
diff --git a/content/browser/renderer_host/navigation_request.cc b/content/browser/renderer_host/navigation_request.cc index 10177bba..1b5fd36 100644 --- a/content/browser/renderer_host/navigation_request.cc +++ b/content/browser/renderer_host/navigation_request.cc
@@ -2416,16 +2416,16 @@ return; } - if (properties->on_navigate_callback_) { - properties->on_navigate_callback_.Run(); + if (properties->on_navigate_callback()) { + properties->on_navigate_callback().Run(); } // Currently, all fenced frame use cases include mapped urls. Patch up // url-related fields to use the underlying mapped url, rather than the // original urn. - CHECK(properties->mapped_url_.has_value()); + CHECK(properties->mapped_url().has_value()); const GURL& mapped_url_value = - properties->mapped_url_->GetValueIgnoringVisibility(); + properties->mapped_url()->GetValueIgnoringVisibility(); common_params_->url = mapped_url_value; commit_params_->original_url = mapped_url_value; @@ -2436,19 +2436,19 @@ // Set the shared storage context in the fenced frame properties. DCHECK(fenced_frame_properties_); - fenced_frame_properties_->embedder_shared_storage_context_ = - embedder_shared_storage_context_; + fenced_frame_properties_->SetEmbedderSharedStorageContext( + embedder_shared_storage_context_); embedder_shared_storage_context_ = absl::nullopt; // For urns loaded into iframes for FLEDGE OT, for compatibility we don't // want to use a fenced frame nonce. if (!frame_tree_node_->IsFencedFrameRoot()) { CHECK(blink::features::IsAllowURNsInIframeEnabled()); - fenced_frame_properties_->partition_nonce_ = absl::nullopt; + fenced_frame_properties_->ClearPartitionNonce(); } // This implies the URN is created from shared storage. - if (fenced_frame_properties_->shared_storage_budget_metadata_) { + if (fenced_frame_properties_->shared_storage_budget_metadata()) { base::TimeDelta time_spent_in_fenced_frame_url_mapping = base::TimeTicks::Now() - fenced_frame_url_mapping_start_time_; @@ -7509,7 +7509,7 @@ // * Embedder-initiated FF root navigations to transparent (non-urn) urls. // In those cases, we skip this step. if (fenced_frame_properties_.has_value() && - fenced_frame_properties_->mapped_url_.has_value()) { + fenced_frame_properties_->mapped_url().has_value()) { fenced_frame_properties_->UpdateMappedURL(GetURL()); } } @@ -7529,9 +7529,9 @@ if (computed_fenced_frame_properties.has_value()) { content::FencedFrameEntity entity = content::FencedFrameEntity::kSameOriginContent; - if (computed_fenced_frame_properties->mapped_url_.has_value() && + if (computed_fenced_frame_properties->mapped_url().has_value() && !url::Origin::Create(common_params_->url) - .IsSameOriginWith(computed_fenced_frame_properties->mapped_url_ + .IsSameOriginWith(computed_fenced_frame_properties->mapped_url() ->GetValueIgnoringVisibility())) { entity = content::FencedFrameEntity::kCrossOriginContent; } @@ -8766,7 +8766,7 @@ // extra policies defined in the outer document/"allow" attribute won't have // any effect. for (const blink::mojom::PermissionsPolicyFeature feature : - computed_fenced_frame_properties->effective_enabled_permissions) { + computed_fenced_frame_properties->effective_enabled_permissions()) { if (!IsFencedFrameRequiredPolicyFeatureAllowed(origin, feature)) { const blink::PermissionsPolicyFeatureToNameMap& feature_to_name_map = blink::GetPermissionsPolicyFeatureToNameMap(); @@ -9422,14 +9422,14 @@ if (!computed_fenced_frame_properties.has_value()) { return absl::nullopt; } - if (!computed_fenced_frame_properties->partition_nonce_.has_value()) { + if (!computed_fenced_frame_properties->partition_nonce().has_value()) { // It is only possible for there to be `FencedFrameProperties` but no // partition nonce in urn iframes (which could indeed be nested inside a // fenced frame). CHECK(blink::features::IsAllowURNsInIframeEnabled()); return absl::nullopt; } - return computed_fenced_frame_properties->partition_nonce_ + return computed_fenced_frame_properties->partition_nonce() ->GetValueIgnoringVisibility(); }
diff --git a/content/browser/renderer_host/navigation_request_unittest.cc b/content/browser/renderer_host/navigation_request_unittest.cc index 33b1514a..bf4471e 100644 --- a/content/browser/renderer_host/navigation_request_unittest.cc +++ b/content/browser/renderer_host/navigation_request_unittest.cc
@@ -528,10 +528,10 @@ content::RenderFrameHostTester::For(main_rfh())->AppendFencedFrame()); FrameTreeNode* fenced_frame_node = static_cast<RenderFrameHostImpl*>(fenced_frame_root)->frame_tree_node(); - absl::optional<FencedFrameProperties> new_props = - fenced_frame_node->GetFencedFrameProperties(); - new_props->effective_enabled_permissions.push_back( + FencedFrameConfig new_config = FencedFrameConfig(GURL("about:blank")); + new_config.effective_enabled_permissions.push_back( blink::mojom::PermissionsPolicyFeature::kSharedStorage); + FencedFrameProperties new_props = FencedFrameProperties(new_config); fenced_frame_node->set_fenced_frame_properties(new_props); fenced_frame_root->ResetPermissionsPolicy();
diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc index 2f60f2b..6bad112 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc
@@ -642,7 +642,7 @@ frame->frame_tree_node()->GetFencedFrameProperties(); base::span<const blink::mojom::PermissionsPolicyFeature> permissions; if (fenced_frame_properties) { - permissions = fenced_frame_properties->effective_enabled_permissions; + permissions = fenced_frame_properties->effective_enabled_permissions(); } subframe_policy = blink::PermissionsPolicy::CreateForFencedFrame( subframe_origin, permissions); @@ -8492,7 +8492,7 @@ const absl::optional<FencedFrameProperties>& fenced_frame_properties = frame_tree_node_->GetFencedFrameProperties(); if (!fenced_frame_properties.has_value() || - !fenced_frame_properties->fenced_frame_reporter_) { + !fenced_frame_properties->fenced_frame_reporter()) { // No associated fenced frame reporter. This should have been captured // in the renderer process at `Fence::reportEvent`. // This implies there is an inconsistency between the browser and the @@ -8503,9 +8503,9 @@ "consistent between the two."); return; } - if (!fenced_frame_properties->mapped_url_.has_value() || + if (!fenced_frame_properties->mapped_url().has_value() || !GetLastCommittedOrigin().IsSameOriginWith( - url::Origin::Create(fenced_frame_properties->mapped_url_ + url::Origin::Create(fenced_frame_properties->mapped_url() ->GetValueIgnoringVisibility()))) { mojo::ReportBadMessage( "This frame is cross-origin to the mapped url of its fenced frame " @@ -8513,7 +8513,7 @@ return; } - fenced_frame_properties->fenced_frame_reporter_ + fenced_frame_properties->fenced_frame_reporter() ->SendPrivateAggregationRequestsForEvent(event_type); } @@ -8691,7 +8691,7 @@ base::UmaHistogramEnumeration(blink::kFencedFrameTopNavigationHistogram, blink::FencedFrameNavigationState::kCommit); } - if (!properties.has_value() || !properties->fenced_frame_reporter_) { + if (!properties.has_value() || !properties->fenced_frame_reporter()) { return; } FencedDocumentData* fenced_document_data = nullptr; @@ -8752,10 +8752,10 @@ // when the initiator document is cross-origin with the fenced frame config's // mapped url, but only if the document opts in through a header. bool is_same_origin = - properties->mapped_url_.has_value() && + properties->mapped_url().has_value() && initiator_rfh->GetLastCommittedOrigin().IsSameOriginWith( url::Origin::Create( - properties->mapped_url_->GetValueIgnoringVisibility())); + properties->mapped_url()->GetValueIgnoringVisibility())); if (!is_same_origin && !initiator_allows_fenced_frame_automatic_beacons) { RecordAutomaticBeaconOutcome( blink::AutomaticBeaconOutcome::kNotSameOriginNotOptedIn); @@ -8772,7 +8772,7 @@ RecordAutomaticBeaconOutcome(blink::AutomaticBeaconOutcome::kSuccess); for (const auto& destination : - properties->fenced_frame_reporter_->ReportingDestinations()) { + properties->fenced_frame_reporter()->ReportingDestinations()) { std::string data; // For data to be sent in the automatic beacon, it must be specified in // the event's "destination" for setReportEventDataForAutomaticBeacons(). @@ -8828,7 +8828,7 @@ frame_tree_node_->GetFencedFrameProperties(); if (!fenced_frame_properties.has_value() || - !fenced_frame_properties->fenced_frame_reporter_) { + !fenced_frame_properties->fenced_frame_reporter()) { // No associated fenced frame reporter. This should have been captured // in the renderer process at `Fence::reportEvent`. // This implies there is an inconsistency between the browser and the @@ -8838,7 +8838,7 @@ return false; } - if (fenced_frame_properties->is_ad_component_) { + if (fenced_frame_properties->is_ad_component()) { // Direct invocation of fence.reportEvent from an ad component is // disallowed. AddMessageToConsole( @@ -8848,9 +8848,9 @@ return false; } - if (!fenced_frame_properties->mapped_url_.has_value() || + if (!fenced_frame_properties->mapped_url().has_value() || !GetLastCommittedOrigin().IsSameOriginWith( - url::Origin::Create(fenced_frame_properties->mapped_url_ + url::Origin::Create(fenced_frame_properties->mapped_url() ->GetValueIgnoringVisibility()))) { mojo::ReportBadMessage( "This frame is cross-origin to the mapped url of its fenced frame " @@ -8896,7 +8896,8 @@ } if (!frame_tree_node_->GetFencedFrameProperties() - ->fenced_frame_reporter_->SendReport( + ->fenced_frame_reporter() + ->SendReport( event_variant, destination, /*request_initiator_frame=*/this, fenced_frame_data->features(), error_message, console_message_level, GetFrameTreeNodeId(), navigation_id)) { @@ -8945,7 +8946,7 @@ // iframes loaded with a urn:uuid. This allows URN iframes to call this // function without getting bad-messaged. if (!fenced_frame_properties || - !fenced_frame_properties->fenced_frame_reporter_) { + !fenced_frame_properties->fenced_frame_reporter()) { mojo::ReportBadMessage( "Automatic beacon data can only be set in fenced frames or iframes " "loaded from a config with a fenced frame reporter."); @@ -8953,9 +8954,9 @@ } // This metadata should only be present in the renderer in frames that are // same-origin to the mapped url. - if (!fenced_frame_properties->mapped_url_.has_value() || + if (!fenced_frame_properties->mapped_url().has_value() || !GetLastCommittedOrigin().IsSameOriginWith( - url::Origin::Create(fenced_frame_properties->mapped_url_ + url::Origin::Create(fenced_frame_properties->mapped_url() ->GetValueIgnoringVisibility()))) { mojo::ReportBadMessage( "Automatic beacon data can only be set from documents that are same-" @@ -8965,7 +8966,7 @@ // Ad components cannot set event data for automatic beacons. std::string event_data_to_use = - fenced_frame_properties->is_ad_component_ ? std::string{} : event_data; + fenced_frame_properties->is_ad_component() ? std::string{} : event_data; auto* fenced_document_data = FencedDocumentData::GetOrCreateForCurrentDocument(this); @@ -11695,7 +11696,7 @@ frame_tree_node()->GetFencedFrameProperties(); base::span<const blink::mojom::PermissionsPolicyFeature> permissions; if (fenced_frame_properties) { - permissions = fenced_frame_properties->effective_enabled_permissions; + permissions = fenced_frame_properties->effective_enabled_permissions(); } permissions_policy_ = blink::PermissionsPolicy::CreateForFencedFrame( last_committed_origin_, permissions); @@ -13229,7 +13230,7 @@ if (fenced_frame_properties && (frame_tree_node()->IsFencedFrameRoot() || !frame_tree_node()->IsInFencedFrameTree())) { - if (fenced_frame_properties->nested_urn_config_pairs_.has_value()) { + if (fenced_frame_properties->nested_urn_config_pairs().has_value()) { // Store nested ad components in the fenced frame's url map. // This may only be done after creating the DocumentAssociatedData for // the new document, if appropriate, since `fenced_frame_urls_map` hangs @@ -13237,17 +13238,17 @@ // the urn iframe root don't create a new Page (because the root of the // Page is the top-level frame). So this operation is a no-op. GetPage().fenced_frame_urls_map().ImportPendingAdComponents( - fenced_frame_properties->nested_urn_config_pairs_ + fenced_frame_properties->nested_urn_config_pairs() ->GetValueIgnoringVisibility()); } - if (fenced_frame_properties->ad_auction_data_.has_value()) { + if (fenced_frame_properties->ad_auction_data().has_value()) { AdAuctionDocumentData::CreateForCurrentDocument( this, - fenced_frame_properties->ad_auction_data_ + fenced_frame_properties->ad_auction_data() ->GetValueIgnoringVisibility() .interest_group_owner, - fenced_frame_properties->ad_auction_data_ + fenced_frame_properties->ad_auction_data() ->GetValueIgnoringVisibility() .interest_group_name); }
diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc index c66c7eb..01807b1 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc
@@ -3468,7 +3468,6 @@ switches::kV, switches::kVideoCaptureUseGpuMemoryBuffer, switches::kVideoThreads, - switches::kVideoUnderflowThresholdMs, switches::kVModule, switches::kWaitForDebuggerOnNavigation, switches::kWebAuthRemoteDesktopSupport,
diff --git a/content/browser/web_package/signed_exchange_handler_unittest.cc b/content/browser/web_package/signed_exchange_handler_unittest.cc index a1ae7284..9bb64510 100644 --- a/content/browser/web_package/signed_exchange_handler_unittest.cc +++ b/content/browser/web_package/signed_exchange_handler_unittest.cc
@@ -161,7 +161,7 @@ class MockCTPolicyEnforcer : public net::CTPolicyEnforcer { public: - MOCK_METHOD3( + MOCK_CONST_METHOD3( CheckCompliance, net::ct::CTPolicyCompliance(net::X509Certificate* cert, const net::ct::SCTList& verified_scts,
diff --git a/content/browser/webid/federated_auth_request_impl.cc b/content/browser/webid/federated_auth_request_impl.cc index d04a708..114f7860 100644 --- a/content/browser/webid/federated_auth_request_impl.cc +++ b/content/browser/webid/federated_auth_request_impl.cc
@@ -331,6 +331,17 @@ render_frame_host->GetPage()); } +FedCmMetrics::NumAccounts ComputeNumMatchingAccounts( + const IdpNetworkRequestManager::AccountList& accounts) { + if (accounts.empty()) { + return FedCmMetrics::NumAccounts::kZero; + } + if (accounts.size() == 1u) { + return FedCmMetrics::NumAccounts::kOne; + } + return FedCmMetrics::NumAccounts::kMultiple; +} + void FilterAccountsWithLoginHint( const std::string& login_hint, IdpNetworkRequestManager::AccountList& accounts) { @@ -346,12 +357,7 @@ return !base::Contains(account.login_hints, login_hint); }; base::EraseIf(accounts, filter); - FedCmMetrics::NumAccounts num_matching = FedCmMetrics::NumAccounts::kZero; - if (accounts.size() == 1u) { - num_matching = FedCmMetrics::NumAccounts::kOne; - } else if (accounts.size() > 1u) { - num_matching = FedCmMetrics::NumAccounts::kMultiple; - } + FedCmMetrics::NumAccounts num_matching = ComputeNumMatchingAccounts(accounts); base::UmaHistogramEnumeration("Blink.FedCm.LoginHint.NumMatchingAccounts", num_matching); } @@ -374,6 +380,9 @@ }; base::EraseIf(accounts, filter); } + FedCmMetrics::NumAccounts num_matching = ComputeNumMatchingAccounts(accounts); + base::UmaHistogramEnumeration("Blink.FedCm.DomainHint.NumMatchingAccounts", + num_matching); } std::unique_ptr<FedCmMetrics> CreateFedCmMetrics(
diff --git a/content/browser/webid/federated_auth_request_impl_unittest.cc b/content/browser/webid/federated_auth_request_impl_unittest.cc index e8af0cf..2369273 100644 --- a/content/browser/webid/federated_auth_request_impl_unittest.cc +++ b/content/browser/webid/federated_auth_request_impl_unittest.cc
@@ -4458,6 +4458,9 @@ RunAuthTest(parameters, kExpectationSuccess, configuration); ASSERT_EQ(displayed_accounts().size(), 1u); EXPECT_EQ(displayed_accounts()[0].id, kAccountId); + + histogram_tester_.ExpectTotalCount( + "Blink.FedCm.DomainHint.NumMatchingAccounts", 0); } TEST_F(FederatedAuthRequestImplTest, DomainHintSingleAccountMatch) { @@ -4474,6 +4477,10 @@ RunAuthTest(parameters, kExpectationSuccess, configuration); ASSERT_EQ(displayed_accounts().size(), 1u); EXPECT_EQ(displayed_accounts()[0].id, kAccountId); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kOne, 1); } TEST_F(FederatedAuthRequestImplTest, DomainHintSingleAccountStarMatch) { @@ -4491,6 +4498,10 @@ RunAuthTest(parameters, kExpectationSuccess, configuration); ASSERT_EQ(displayed_accounts().size(), 1u); EXPECT_EQ(displayed_accounts()[0].id, kAccountId); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kOne, 1); } TEST_F(FederatedAuthRequestImplTest, DomainHintSingleAccountStarNoMatch) { @@ -4512,6 +4523,10 @@ RunAuthTest(parameters, expectations, configuration); EXPECT_TRUE(DidFetch(FetchedEndpoint::ACCOUNTS)); EXPECT_FALSE(did_show_accounts_dialog()); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kZero, 1); } TEST_F(FederatedAuthRequestImplTest, DomainHintSingleAccountNoMatch) { @@ -4533,6 +4548,10 @@ RunAuthTest(parameters, expectations, configuration); EXPECT_TRUE(DidFetch(FetchedEndpoint::ACCOUNTS)); EXPECT_FALSE(did_show_accounts_dialog()); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kZero, 1); } TEST_F(FederatedAuthRequestImplTest, DomainHintNoMatch) { @@ -4550,6 +4569,10 @@ RunAuthTest(parameters, expectations, kConfigurationValid); EXPECT_TRUE(DidFetch(FetchedEndpoint::ACCOUNTS)); EXPECT_FALSE(did_show_accounts_dialog()); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kZero, 1); } TEST_F(FederatedAuthRequestImplTest, DomainHintMultipleAccountsSingleMatch) { @@ -4566,6 +4589,10 @@ RunAuthTest(parameters, kExpectationSuccess, configuration); ASSERT_EQ(displayed_accounts().size(), 1u); EXPECT_EQ(displayed_accounts()[0].id, kAccountIdZach); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kOne, 1); } TEST_F(FederatedAuthRequestImplTest, @@ -4584,6 +4611,10 @@ ASSERT_EQ(displayed_accounts().size(), 2u); EXPECT_EQ(displayed_accounts()[0].id, kAccountIdNicolas); EXPECT_EQ(displayed_accounts()[1].id, kAccountIdZach); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kMultiple, 1); } TEST_F(FederatedAuthRequestImplTest, DomainHintMultipleAccountsStar) { @@ -4602,6 +4633,10 @@ ASSERT_EQ(displayed_accounts().size(), 2u); EXPECT_EQ(displayed_accounts()[0].id, kAccountIdNicolas); EXPECT_EQ(displayed_accounts()[1].id, kAccountIdZach); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kMultiple, 1); } TEST_F(FederatedAuthRequestImplTest, DomainHintMultipleAccountsNoMatch) { @@ -4623,6 +4658,10 @@ RunAuthTest(parameters, expectations, configuration); EXPECT_TRUE(DidFetch(FetchedEndpoint::ACCOUNTS)); EXPECT_FALSE(did_show_accounts_dialog()); + + histogram_tester_.ExpectUniqueSample( + "Blink.FedCm.DomainHint.NumMatchingAccounts", + FedCmMetrics::NumAccounts::kZero, 1); } // Test that when FedCmRpContext flag is enabled and rp_context is specified,
diff --git a/content/public/browser/permission_controller.h b/content/public/browser/permission_controller.h index 4fb5df93..05afd6e 100644 --- a/content/public/browser/permission_controller.h +++ b/content/public/browser/permission_controller.h
@@ -100,13 +100,13 @@ virtual void ResetPermission(blink::PermissionType permission, const url::Origin& origin) = 0; - virtual SubscriptionId SubscribePermissionStatusChange( + virtual SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, RenderProcessHost* render_process_host, const url::Origin& requesting_origin, const base::RepeatingCallback<void(PermissionStatus)>& callback) = 0; - virtual void UnsubscribePermissionStatusChange( + virtual void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) = 0; // Returns `true` if a document subscribed to
diff --git a/content/public/browser/permission_controller_delegate.h b/content/public/browser/permission_controller_delegate.h index 68c0d50..2c23867 100644 --- a/content/public/browser/permission_controller_delegate.h +++ b/content/public/browser/permission_controller_delegate.h
@@ -121,7 +121,7 @@ // unsubscribe, which can be `is_null()` if the subscribe was not successful. // Exactly one of |render_process_host| and |render_frame_host| should be // set, RenderProcessHost will be inferred from |render_frame_host|. - virtual SubscriptionId SubscribePermissionStatusChange( + virtual SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, @@ -130,9 +130,9 @@ // Unregisters from permission status change notifications. The // |subscription_id| must match the value returned by the - // SubscribePermissionStatusChange call. Unsubscribing an already + // SubscribeToPermissionStatusChange call. Unsubscribing an already // unsubscribed |subscription_id| or an `is_null()` ID is a no-op. - virtual void UnsubscribePermissionStatusChange( + virtual void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) = 0; // If there's currently a permission UI presenting for the given WebContents,
diff --git a/content/public/test/fenced_frame_reporter_observer.cc b/content/public/test/fenced_frame_reporter_observer.cc index d7e809d..44a397d7 100644 --- a/content/public/test/fenced_frame_reporter_observer.cc +++ b/content/public/test/fenced_frame_reporter_observer.cc
@@ -58,7 +58,7 @@ CHECK(fenced_frame_properties.has_value()); scoped_refptr<content::FencedFrameReporter> fenced_frame_reporter = - fenced_frame_properties->fenced_frame_reporter_; + fenced_frame_properties->fenced_frame_reporter(); CHECK(fenced_frame_reporter); return std::make_unique<FencedFrameReporterObserverForTesting>(
diff --git a/content/public/test/mock_permission_controller.cc b/content/public/test/mock_permission_controller.cc index 5137c4e..11dbf76 100644 --- a/content/public/test/mock_permission_controller.cc +++ b/content/public/test/mock_permission_controller.cc
@@ -24,7 +24,7 @@ void MockPermissionController::ResetPermission(blink::PermissionType permission, const url::Origin& origin) {} -void MockPermissionController::UnsubscribePermissionStatusChange( +void MockPermissionController::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) {} } // namespace content
diff --git a/content/public/test/mock_permission_controller.h b/content/public/test/mock_permission_controller.h index d23a742c..dc5fb3d 100644 --- a/content/public/test/mock_permission_controller.h +++ b/content/public/test/mock_permission_controller.h
@@ -71,14 +71,14 @@ void ResetPermission(blink::PermissionType permission, const url::Origin& origin) override; - MOCK_METHOD4(SubscribePermissionStatusChange, + MOCK_METHOD4(SubscribeToPermissionStatusChange, SubscriptionId(blink::PermissionType permission, RenderProcessHost* render_process_host, const url::Origin& requesting_origin, const base::RepeatingCallback<void( blink::mojom::PermissionStatus)>& callback)); - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; };
diff --git a/content/public/test/mock_permission_manager.h b/content/public/test/mock_permission_manager.h index aeba0e7f..aedb7fa 100644 --- a/content/public/test/mock_permission_manager.h +++ b/content/public/test/mock_permission_manager.h
@@ -65,7 +65,7 @@ base::OnceCallback< void(const std::vector<blink::mojom::PermissionStatus>&)> callback) override; - MOCK_METHOD5(SubscribePermissionStatusChange, + MOCK_METHOD5(SubscribeToPermissionStatusChange, SubscriptionId( blink::PermissionType permission, RenderProcessHost* render_process_host, @@ -73,7 +73,7 @@ const GURL& requesting_origin, base::RepeatingCallback<void(blink::mojom::PermissionStatus)> callback)); - MOCK_METHOD1(UnsubscribePermissionStatusChange, + MOCK_METHOD1(UnsubscribeFromPermissionStatusChange, void(SubscriptionId subscription_id)); };
diff --git a/content/shell/browser/shell_permission_manager.cc b/content/shell/browser/shell_permission_manager.cc index f0a1197..8724e953 100644 --- a/content/shell/browser/shell_permission_manager.cc +++ b/content/shell/browser/shell_permission_manager.cc
@@ -197,7 +197,7 @@ } ShellPermissionManager::SubscriptionId -ShellPermissionManager::SubscribePermissionStatusChange( +ShellPermissionManager::SubscribeToPermissionStatusChange( PermissionType permission, RenderProcessHost* render_process_host, RenderFrameHost* render_frame_host, @@ -206,7 +206,7 @@ return SubscriptionId(); } -void ShellPermissionManager::UnsubscribePermissionStatusChange( +void ShellPermissionManager::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) {} } // namespace content
diff --git a/content/shell/browser/shell_permission_manager.h b/content/shell/browser/shell_permission_manager.h index 8ed8407..8ee39ca 100644 --- a/content/shell/browser/shell_permission_manager.h +++ b/content/shell/browser/shell_permission_manager.h
@@ -59,14 +59,14 @@ blink::PermissionType permission, content::RenderFrameHost* render_frame_host, const url::Origin& overridden_origin) override; - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, RenderProcessHost* render_process_host, RenderFrameHost* render_frame_host, const GURL& requesting_origin, base::RepeatingCallback<void(blink::mojom::PermissionStatus)> callback) override; - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; };
diff --git a/content/test/content_test_bundle_data.filelist b/content/test/content_test_bundle_data.filelist index 4afa6061..51c1b55 100644 --- a/content/test/content_test_bundle_data.filelist +++ b/content/test/content_test_bundle_data.filelist
@@ -5439,6 +5439,7 @@ data/accessibility/regression/slot-creation-crash.html data/accessibility/regression/title-in-shadow-expected-blink.txt data/accessibility/regression/title-in-shadow.html +data/accessibility/regression/workplace.jpg data/accessibility/regression/xml-in-iframe-crash.html data/accessibility/relations/ignore-duplicate-relation-ids-expected-auralinux.txt data/accessibility/relations/ignore-duplicate-relation-ids-expected-win.txt
diff --git a/content/test/data/accessibility/regression/reused-map-change-map-name-expected-blink.txt b/content/test/data/accessibility/regression/reused-map-change-map-name-expected-blink.txt index 0903328..142c849 100644 --- a/content/test/data/accessibility/regression/reused-map-change-map-name-expected-blink.txt +++ b/content/test/data/accessibility/regression/reused-map-change-map-name-expected-blink.txt
@@ -1,15 +1,17 @@ rootWebArea focusable name='done' ++genericContainer ignored ++++genericContainer ignored -++++++image name='star1' +++++++heading name='Image Maps' +++++++++staticText name='Image Maps' +++++++++++inlineTextBox name='Image Maps' +++++++paragraph +++++++++staticText name='After map1 is renamed map2, the third picture should have only the coffee mapped' +++++++++++inlineTextBox name='After map1 is renamed map2, the third picture should have only the coffee mapped' +++++++image name='Workplace pic 1' ++++++staticText name=' ' -++++++++inlineTextBox name=' ' -++++++image name='star2' +++++++image name='Workplace pic 2' ++++++staticText name=' ' -++++++image name='star3' -++++++++link focusable name='Area' -++++++++link focusable name='Area2' +++++++image name='Workplace pic 3' +++++++++link focusable name='Coffee only (origin map1)' ++++++staticText name=' ' -++++++++inlineTextBox name=' ' -++++++image name='star4' -++++++genericContainer +++++++image name='Workplace pic 4'
diff --git a/content/test/data/accessibility/regression/reused-map-change-map-name.html b/content/test/data/accessibility/regression/reused-map-change-map-name.html index b7e4fcb3..f6c118eb 100644 --- a/content/test/data/accessibility/regression/reused-map-change-map-name.html +++ b/content/test/data/accessibility/regression/reused-map-change-map-name.html
@@ -3,24 +3,26 @@ @AURALINUX-ALLOW:focus* @WAIT-FOR:done --> -<!-- Only the first image that uses a given map gets its area children. --> -<img id="img1" alt="star1" usemap="#map1" - src="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg'/%3E"> -<img id="img2" alt="star2" usemap="#map1" - src="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg'/%3E"> -<img id="img3" alt="star3" usemap="#map2" - src="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg'/%3E"> -<img id="img4" alt="star4" usemap="#map2" - src="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg'/%3E"> +<!DOCTYPE html> +<html> +<body> + +<h2>Image Maps</h2> +<p>After map1 is renamed map2, the third picture should have only the coffee mapped</p> + +<img src="workplace.jpg" alt="Workplace pic 1" usemap="#map1" width="400" height="379"> +<img src="workplace.jpg" alt="Workplace pic 2" usemap="#map1" width="400" height="379"> +<img src="workplace.jpg" alt="Workplace pic 3" usemap="#map2" width="400" height="379"> +<img src="workplace.jpg" alt="Workplace pic 4" usemap="#map2" width="400" height="379"> + <map name="map1"> - <area shape="rect" coords="0,0,5,5" href="about:blank" alt="Area"> + <area shape="circle" coords="337,300,44" alt="Coffee only (origin map1)" href="coffee.htm"> </map> <map name="map2"> - <area shape="rect" coords="0,0,5,5" href="about:blank" alt="Area"> - <area shape="rect" coords="3,3,8,8" href="about:blank" alt="Area2" autofocus> + <area shape="rect" coords="34,44,270,350" alt="Computer" href="computer.htm"> + <area shape="rect" coords="290,172,333,250" alt="Phone" href="phone.htm"> + <area shape="circle" coords="337,300,44" alt="Cup of coffee" href="coffee.htm"> </map> -<div id="container"> -</div> <script> document.addEventListener('DOMContentLoaded', () => { @@ -33,3 +35,6 @@ }, 250); }); </script> + +</body> +</html>
diff --git a/content/test/data/accessibility/regression/workplace.jpg b/content/test/data/accessibility/regression/workplace.jpg new file mode 100644 index 0000000..4e95fba --- /dev/null +++ b/content/test/data/accessibility/regression/workplace.jpg Binary files differ
diff --git a/content/test/fenced_frame_test_utils.h b/content/test/fenced_frame_test_utils.h index c092cf6e..59be56e 100644 --- a/content/test/fenced_frame_test_utils.h +++ b/content/test/fenced_frame_test_utils.h
@@ -49,41 +49,41 @@ absl::optional<GURL> mapped_url() const { if (!observed_fenced_frame_properties_ || - !observed_fenced_frame_properties_->mapped_url_) { + !observed_fenced_frame_properties_->mapped_url()) { return absl::nullopt; } - return observed_fenced_frame_properties_->mapped_url_ + return observed_fenced_frame_properties_->mapped_url() ->GetValueIgnoringVisibility(); } absl::optional<std::vector<std::pair<GURL, FencedFrameConfig>>> nested_urn_config_pairs() const { if (!observed_fenced_frame_properties_ || - !observed_fenced_frame_properties_->nested_urn_config_pairs_) { + !observed_fenced_frame_properties_->nested_urn_config_pairs()) { return absl::nullopt; } - return observed_fenced_frame_properties_->nested_urn_config_pairs_ + return observed_fenced_frame_properties_->nested_urn_config_pairs() ->GetValueIgnoringVisibility(); } absl::optional<AdAuctionData> ad_auction_data() const { if (!observed_fenced_frame_properties_ || - !observed_fenced_frame_properties_->ad_auction_data_) { + !observed_fenced_frame_properties_->ad_auction_data()) { return absl::nullopt; } - return observed_fenced_frame_properties_->ad_auction_data_ + return observed_fenced_frame_properties_->ad_auction_data() ->GetValueIgnoringVisibility(); } const base::RepeatingClosure& on_navigate_callback() const { - return observed_fenced_frame_properties_->on_navigate_callback_; + return observed_fenced_frame_properties_->on_navigate_callback(); } FencedFrameReporter* fenced_frame_reporter() { if (!observed_fenced_frame_properties_) { return nullptr; } - return observed_fenced_frame_properties_->fenced_frame_reporter_.get(); + return observed_fenced_frame_properties_->fenced_frame_reporter().get(); } private:
diff --git a/content/web_test/browser/web_test_permission_manager.cc b/content/web_test/browser/web_test_permission_manager.cc index 2e24569..70cbd184 100644 --- a/content/web_test/browser/web_test_permission_manager.cc +++ b/content/web_test/browser/web_test_permission_manager.cc
@@ -296,7 +296,7 @@ } WebTestPermissionManager::SubscriptionId -WebTestPermissionManager::SubscribePermissionStatusChange( +WebTestPermissionManager::SubscribeToPermissionStatusChange( blink::PermissionType permission, RenderProcessHost* render_process_host, RenderFrameHost* render_frame_host, @@ -324,7 +324,7 @@ return id; } -void WebTestPermissionManager::UnsubscribePermissionStatusChange( +void WebTestPermissionManager::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) { DCHECK_CURRENTLY_ON(BrowserThread::UI);
diff --git a/content/web_test/browser/web_test_permission_manager.h b/content/web_test/browser/web_test_permission_manager.h index e9cb9ab..1da5251 100644 --- a/content/web_test/browser/web_test_permission_manager.h +++ b/content/web_test/browser/web_test_permission_manager.h
@@ -73,14 +73,14 @@ blink::PermissionType permission, content::RenderFrameHost* render_frame_host, const url::Origin& overridden_origin) override; - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, RenderProcessHost* render_process_host, RenderFrameHost* render_frame_host, const GURL& requesting_origin, base::RepeatingCallback<void(blink::mojom::PermissionStatus)> callback) override; - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; void SetPermission(
diff --git a/docs/testing/android_instrumentation_tests.md b/docs/testing/android_instrumentation_tests.md index acce6469..db702f7 100644 --- a/docs/testing/android_instrumentation_tests.md +++ b/docs/testing/android_instrumentation_tests.md
@@ -1,57 +1,11 @@ # Android Instrumentation Tests -Instrumentation tests are Java tests based on -[`android.app.Instrumentation`](https://developer.android.com/reference/android/app/Instrumentation.html). -They run on a device. +Instrumentation tests are JUnit 4 tests that run on devices or emulators. They +can be either unit tests or integration test. [TOC] -## Writing an instrumentation test - -Currently, an instrumentation test is just a JUnit3-style test based on -[android.test.InstrumentationTestCase](https://developer.android.com/reference/android/test/InstrumentationTestCase.html). -(This will change starting in [Android N](https://en.wikipedia.org/wiki/Android_Nougat).) - -Writing an instrumentation test case can be simple, e.g. - -```java -package org.chromium.sample.test; - -import android.test.InstrumentationTestCase; - -public class MyInstrumentationTest extends InstrumentationTestCase { - - // Note that, because it's a JUnit3-style test, the test method *must* - // start with "test". - public void testTheFirst() { - bool writingInstrumentationTestsCanBeEasy = true; - - // InstrumentationTestCase inherits the assert* methods through - // junit.framework.TestCase. - assertTrue(writingInstrumentationTestsCanBeEasy); - } - - public void testTheSecond() { - bool writingInstrumentationTestsIsAlwaysEasy = false; - assertFalse(writingInstrumentationTestsIsAlwaysEasy); - } -} -``` - -After writing a test, you can run it by: - - - Adding the file to the relevant gn target if the entire file is new. -Typically, the "relevant gn target" is simply the target containing the -other files in the same directory. - - Rebuild. - - Run the test - -## Instrumentation test features - -In many cases, Chromium has extended the instrumentation test framework -classes to implement additional features. - -### Tracing +## Tracing Enabling tracing during a test run allows all the function calls involved to be observed in a visual display (using Chrome's built-in chrome://tracing feature). @@ -66,13 +20,7 @@ the device. For a more detailed look, add the (no-argument) `--trace-all` flag. This causes every function called on the Python side to be added to the trace. -### Annotations - -Instrumentation tests in Chromium use a wide variety of annotations to control -and manipulate test execution. Some of these are implemented in Chromium, while -others are pulled in from outside. They include: - -#### Test Batching +## Test Batching Annotations The [`@Batch("group_name")`](https://chromium.googlesource.com/chromium/src/+/main/base/test/android/javatests/src/org/chromium/base/test/util/Batch.java) annotation is used to run all tests with the same batch group name in the same @@ -84,23 +32,18 @@ seconds), and that doesn't count the cost of starting an Activity like ChromeTabbedActivity. -#### Size annotations +## Size Annotations -Size annotations are used primarily by the test runner to determine the length -of time to wait before considering a test hung (i.e., its timeout duration). +Size annotations are [used by the test runner] to determine the length of time +to wait before considering a test hung (i.e., its timeout duration). -Several of the annotations are Android APIs from -[android.test.suitebuilder.annotation](https://developer.android.com/reference/android/test/suitebuilder/annotation/package-summary.html) -(prior to [Android N](https://en.wikipedia.org/wiki/Android_Nougat)) or -[androidx.test.filters](https://developer.android.com/reference/androidx/test/filters/package-summary.html) -(starting in Android N). These are all fairly self-explanatory: +Annotations from `androidx.test.filters`: - [`@SmallTest`](https://developer.android.com/reference/androidx/test/filters/SmallTest.html) (timeout: **10 seconds**) - [`@MediumTest`](https://developer.android.com/reference/androidx/test/filters/MediumTest.html) (timeout: **30 seconds**) - [`@LargeTest`](https://developer.android.com/reference/androidx/test/filters/LargeTest.html) (timeout: **2 minutes**) -A few additional size annotations are provided in -[//base](https://chromium.googlesource.com/chromium/src/+/main/base): +Annotations from `//base`: - [`@EnormousTest`](https://chromium.googlesource.com/chromium/src/+/main/base/test/android/javatests/src/org/chromium/base/test/util/EnormousTest.java) (timeout: **5 minutes**) Typically used for tests that require WiFi. @@ -109,16 +52,14 @@ - [`@Manual`](https://chromium.googlesource.com/chromium/src/+/main/base/test/android/javatests/src/org/chromium/base/test/util/Manual.java) (timeout: **10 hours**) Used for manual tests. -Beware that the timeout durations for these annotations are subject to -change, though they rarely do. These values are defined -[here](https://chromium.googlesource.com/chromium/src/+/main/build/android/pylib/local/device/local_device_instrumentation_test_run.py#20). +[used by the test runner]: https://source.chromium.org/search?q=file:local_device_instrumentation_test_run.py%20symbol:TIMEOUT_ANNOTATIONS&sq=&ss=chromium -#### Annotations that disable tests +## Annotations that Disable Tests There are several annotations that control whether or not a test runs. Some are conditional, others are not. -##### Unconditional disabling +### Unconditional Disabling [**@DisabledTest**](https://chromium.googlesource.com/chromium/src/+/main/base/test/android/javatests/src/org/chromium/base/test/util/DisabledTest.java) unconditionally disables a test. @@ -129,7 +70,7 @@ ) ``` -##### Conditional disabling +### Conditional Disabling There are two primary annotation categories that conditionally disable tests: **@DisableIf** and **@Restriction**. The **@DisableIf** annotations are intended @@ -235,7 +176,7 @@ ) ``` -#### Annotations that affect how a test is run +## Command-Line Flags Annotations Several annotations affect how a test is run in interesting or nontrivial ways. @@ -263,7 +204,7 @@ ) ``` -#### Feature annotations +## Feature Annotations [**@Feature**](https://chromium.googlesource.com/chromium/src/+/main/base/test/android/javatests/src/org/chromium/base/test/util/Feature.java) has been used inconsistently in Chromium to group tests across
diff --git a/extensions/docs/testing_api.md b/extensions/docs/testing_api.md index 13b469e6..2156410 100644 --- a/extensions/docs/testing_api.md +++ b/extensions/docs/testing_api.md
@@ -305,7 +305,12 @@ <verify state> ``` -This, too, will be even more readable with Promise-based APIs. +For Promise-based calls in MV3 tests this can be simplified even more: + +```js +const tab = await chrome.tabs.create({url: url}); +<verify state> +``` ### listenOnce() and listenForever() `chrome.test.listenOnce()` and `chrome.test.listenForever()` are utility
diff --git a/fuchsia_web/webengine/browser/web_engine_permission_delegate.cc b/fuchsia_web/webengine/browser/web_engine_permission_delegate.cc index 4db99fd..e3a60fe 100644 --- a/fuchsia_web/webengine/browser/web_engine_permission_delegate.cc +++ b/fuchsia_web/webengine/browser/web_engine_permission_delegate.cc
@@ -109,7 +109,7 @@ } WebEnginePermissionDelegate::SubscriptionId -WebEnginePermissionDelegate::SubscribePermissionStatusChange( +WebEnginePermissionDelegate::SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, @@ -121,7 +121,7 @@ return SubscriptionId(); } -void WebEnginePermissionDelegate::UnsubscribePermissionStatusChange( +void WebEnginePermissionDelegate::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) { // TODO(crbug.com/1063094): Implement permission status subscription. It's // used in blink to emit PermissionStatus.onchange notifications.
diff --git a/fuchsia_web/webengine/browser/web_engine_permission_delegate.h b/fuchsia_web/webengine/browser/web_engine_permission_delegate.h index 1096b145a3..487ff98 100644 --- a/fuchsia_web/webengine/browser/web_engine_permission_delegate.h +++ b/fuchsia_web/webengine/browser/web_engine_permission_delegate.h
@@ -59,14 +59,14 @@ blink::PermissionType permission, content::RenderFrameHost* render_frame_host, const url::Origin& overridden_origin) override; - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, const GURL& requesting_origin, base::RepeatingCallback<void(blink::mojom::PermissionStatus)> callback) override; - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; };
diff --git a/headless/lib/browser/headless_permission_manager.cc b/headless/lib/browser/headless_permission_manager.cc index 285f5aa..8eddd09 100644 --- a/headless/lib/browser/headless_permission_manager.cc +++ b/headless/lib/browser/headless_permission_manager.cc
@@ -94,7 +94,7 @@ } HeadlessPermissionManager::SubscriptionId -HeadlessPermissionManager::SubscribePermissionStatusChange( +HeadlessPermissionManager::SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, @@ -103,7 +103,7 @@ return SubscriptionId(); } -void HeadlessPermissionManager::UnsubscribePermissionStatusChange( +void HeadlessPermissionManager::UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) {} } // namespace headless
diff --git a/headless/lib/browser/headless_permission_manager.h b/headless/lib/browser/headless_permission_manager.h index 1481295..926b8a5 100644 --- a/headless/lib/browser/headless_permission_manager.h +++ b/headless/lib/browser/headless_permission_manager.h
@@ -65,14 +65,14 @@ blink::PermissionType permission, content::RenderFrameHost* render_frame_host, const url::Origin& overridden_origin) override; - SubscriptionId SubscribePermissionStatusChange( + SubscriptionId SubscribeToPermissionStatusChange( blink::PermissionType permission, content::RenderProcessHost* render_process_host, content::RenderFrameHost* render_frame_host, const GURL& requesting_origin, base::RepeatingCallback<void(blink::mojom::PermissionStatus)> callback) override; - void UnsubscribePermissionStatusChange( + void UnsubscribeFromPermissionStatusChange( SubscriptionId subscription_id) override; private:
diff --git a/infra/config/generated/builders/ci/GPU FYI Win x64 Builder/gn-args.json b/infra/config/generated/builders/ci/GPU FYI Win x64 Builder/gn-args.json index a8bb27ba..da74d64 100644 --- a/infra/config/generated/builders/ci/GPU FYI Win x64 Builder/gn-args.json +++ b/infra/config/generated/builders/ci/GPU FYI Win x64 Builder/gn-args.json
@@ -7,6 +7,7 @@ "is_debug": false, "proprietary_codecs": true, "symbol_level": 1, + "target_os": "win", "use_remoteexec": true } } \ No newline at end of file
diff --git a/infra/config/generated/builders/try/gpu-fyi-try-win10-amd-rel-64/gn-args.json b/infra/config/generated/builders/try/gpu-fyi-try-win10-amd-rel-64/gn-args.json index a8bb27ba..da74d64 100644 --- a/infra/config/generated/builders/try/gpu-fyi-try-win10-amd-rel-64/gn-args.json +++ b/infra/config/generated/builders/try/gpu-fyi-try-win10-amd-rel-64/gn-args.json
@@ -7,6 +7,7 @@ "is_debug": false, "proprietary_codecs": true, "symbol_level": 1, + "target_os": "win", "use_remoteexec": true } } \ No newline at end of file
diff --git a/infra/config/generated/builders/try/gpu-fyi-try-win10-intel-exp-64/gn-args.json b/infra/config/generated/builders/try/gpu-fyi-try-win10-intel-exp-64/gn-args.json index a8bb27ba..da74d64 100644 --- a/infra/config/generated/builders/try/gpu-fyi-try-win10-intel-exp-64/gn-args.json +++ b/infra/config/generated/builders/try/gpu-fyi-try-win10-intel-exp-64/gn-args.json
@@ -7,6 +7,7 @@ "is_debug": false, "proprietary_codecs": true, "symbol_level": 1, + "target_os": "win", "use_remoteexec": true } } \ No newline at end of file
diff --git a/infra/config/generated/builders/try/gpu-fyi-try-win10-intel-rel-64/gn-args.json b/infra/config/generated/builders/try/gpu-fyi-try-win10-intel-rel-64/gn-args.json index a8bb27ba..da74d64 100644 --- a/infra/config/generated/builders/try/gpu-fyi-try-win10-intel-rel-64/gn-args.json +++ b/infra/config/generated/builders/try/gpu-fyi-try-win10-intel-rel-64/gn-args.json
@@ -7,6 +7,7 @@ "is_debug": false, "proprietary_codecs": true, "symbol_level": 1, + "target_os": "win", "use_remoteexec": true } } \ No newline at end of file
diff --git a/infra/config/generated/builders/try/gpu-fyi-try-win10-nvidia-exp-64/gn-args.json b/infra/config/generated/builders/try/gpu-fyi-try-win10-nvidia-exp-64/gn-args.json index a8bb27ba..da74d64 100644 --- a/infra/config/generated/builders/try/gpu-fyi-try-win10-nvidia-exp-64/gn-args.json +++ b/infra/config/generated/builders/try/gpu-fyi-try-win10-nvidia-exp-64/gn-args.json
@@ -7,6 +7,7 @@ "is_debug": false, "proprietary_codecs": true, "symbol_level": 1, + "target_os": "win", "use_remoteexec": true } } \ No newline at end of file
diff --git a/infra/config/generated/builders/try/gpu-fyi-try-win10-nvidia-rel-64/gn-args.json b/infra/config/generated/builders/try/gpu-fyi-try-win10-nvidia-rel-64/gn-args.json index a8bb27ba..da74d64 100644 --- a/infra/config/generated/builders/try/gpu-fyi-try-win10-nvidia-rel-64/gn-args.json +++ b/infra/config/generated/builders/try/gpu-fyi-try-win10-nvidia-rel-64/gn-args.json
@@ -7,6 +7,7 @@ "is_debug": false, "proprietary_codecs": true, "symbol_level": 1, + "target_os": "win", "use_remoteexec": true } } \ No newline at end of file
diff --git a/infra/config/generated/luci/cr-buildbucket.cfg b/infra/config/generated/luci/cr-buildbucket.cfg index 194fe92..774f7b4 100644 --- a/infra/config/generated/luci/cr-buildbucket.cfg +++ b/infra/config/generated/luci/cr-buildbucket.cfg
@@ -67691,12 +67691,11 @@ builders { name: "android-official" swarming_host: "chromium-swarm.appspot.com" - dimensions: "builderless:1" + dimensions: "builder:android-official" dimensions: "cores:32" dimensions: "cpu:x86-64" dimensions: "os:Ubuntu-22.04" dimensions: "pool:luci.chromium.try" - dimensions: "ssd:1" exe { cipd_package: "infra/chromium/bootstrapper/${platform}" cipd_version: "latest"
diff --git a/infra/config/generated/testing/variants.pyl b/infra/config/generated/testing/variants.pyl index 33978b9..f644df0 100644 --- a/infra/config/generated/testing/variants.pyl +++ b/infra/config/generated/testing/variants.pyl
@@ -337,16 +337,16 @@ }, 'LACROS_VERSION_SKEW_CANARY': { 'identifier': 'Lacros version skew testing ash canary', - 'description': 'Run with ash-chrome version 122.0.6180.0', + 'description': 'Run with ash-chrome version 122.0.6181.0', 'args': [ - '--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome', + '--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome', ], 'swarming': { 'cipd_packages': [ { 'cipd_package': 'chromium/testing/linux-ash-chromium/x86_64/ash.zip', - 'location': 'lacros_version_skew_tests_v122.0.6180.0', - 'revision': 'version:122.0.6180.0', + 'location': 'lacros_version_skew_tests_v122.0.6181.0', + 'revision': 'version:122.0.6181.0', }, ], },
diff --git a/infra/config/subprojects/chromium/ci/chromium.gpu.fyi.star b/infra/config/subprojects/chromium/ci/chromium.gpu.fyi.star index 1460f67..266a6ff 100644 --- a/infra/config/subprojects/chromium/ci/chromium.gpu.fyi.star +++ b/infra/config/subprojects/chromium/ci/chromium.gpu.fyi.star
@@ -1566,6 +1566,9 @@ "try_builder", "reclient", "disable_nacl", + # Remove this once the decision to use cross-compilation or not in + # crbug.com/1510985 is made. + "win_cross", ], ), console_view_entry = consoles.console_view_entry(
diff --git a/infra/config/subprojects/chromium/try/tryserver.chromium.star b/infra/config/subprojects/chromium/try/tryserver.chromium.star index 380632bf..7c850ef 100644 --- a/infra/config/subprojects/chromium/try/tryserver.chromium.star +++ b/infra/config/subprojects/chromium/try/tryserver.chromium.star
@@ -43,7 +43,7 @@ "dcheck_always_on", ], ), - ssd = True, + builderless = False, contact_team_email = "clank-engprod@google.com", )
diff --git a/infra/config/targets/lacros-version-skew-variants.json b/infra/config/targets/lacros-version-skew-variants.json index 6e30c798..b8fee8b 100644 --- a/infra/config/targets/lacros-version-skew-variants.json +++ b/infra/config/targets/lacros-version-skew-variants.json
@@ -1,16 +1,16 @@ { "LACROS_VERSION_SKEW_CANARY": { "args": [ - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "identifier": "Lacros version skew testing ash canary", "swarming": { "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ] }
diff --git a/ios/chrome/browser/push_notification/model/BUILD.gn b/ios/chrome/browser/push_notification/model/BUILD.gn index ee781e2..2db0cce 100644 --- a/ios/chrome/browser/push_notification/model/BUILD.gn +++ b/ios/chrome/browser/push_notification/model/BUILD.gn
@@ -56,6 +56,7 @@ "push_notification_util.mm", ] deps = [ + ":constants", ":push_notification_client", "//base", "//components/optimization_guide/core:features", @@ -84,6 +85,13 @@ sources = [ "notifications_alert_presenter.h" ] } +source_set("constants") { + sources = [ + "constants.h", + "constants.mm", + ] +} + source_set("unit_tests") { testonly = true sources = [
diff --git a/ios/chrome/browser/push_notification/model/constants.h b/ios/chrome/browser/push_notification/model/constants.h new file mode 100644 index 0000000..80669c9 --- /dev/null +++ b/ios/chrome/browser/push_notification/model/constants.h
@@ -0,0 +1,17 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef IOS_CHROME_BROWSER_PUSH_NOTIFICATION_MODEL_CONSTANTS_H_ +#define IOS_CHROME_BROWSER_PUSH_NOTIFICATION_MODEL_CONSTANTS_H_ + +#import <string> + +// Key of commerce notification used in pref +// kFeaturePushNotificationPermissions. +extern std::string const kCommerceNotificationKey; + +// Key of content notification used in pref kFeaturePushNotificationPermissions. +extern std::string const kContentNotificationKey; + +#endif // IOS_CHROME_BROWSER_PUSH_NOTIFICATION_MODEL_CONSTANTS_H_
diff --git a/ios/chrome/browser/push_notification/model/constants.mm b/ios/chrome/browser/push_notification/model/constants.mm new file mode 100644 index 0000000..21d5f3f --- /dev/null +++ b/ios/chrome/browser/push_notification/model/constants.mm
@@ -0,0 +1,8 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#import "ios/chrome/browser/push_notification/model/constants.h" + +std::string const kCommerceNotificationKey = "PRICE_DROP"; +std::string const kContentNotificationKey = "CONTENT";
diff --git a/ios/chrome/browser/push_notification/model/push_notification_client_manager.mm b/ios/chrome/browser/push_notification/model/push_notification_client_manager.mm index 8457890..86caabf 100644 --- a/ios/chrome/browser/push_notification/model/push_notification_client_manager.mm +++ b/ios/chrome/browser/push_notification/model/push_notification_client_manager.mm
@@ -10,6 +10,7 @@ #import "components/optimization_guide/core/optimization_guide_features.h" #import "ios/chrome/browser/commerce/model/push_notification/commerce_push_notification_client.h" #import "ios/chrome/browser/commerce/model/push_notification/push_notification_feature.h" +#import "ios/chrome/browser/push_notification/model/constants.h" #import "ios/chrome/browser/push_notification/model/push_notification_util.h" #import "ios/chrome/browser/shared/public/features/features.h" @@ -101,10 +102,10 @@ PushNotificationClientId client_id) { switch (client_id) { case PushNotificationClientId::kCommerce: { - return "PRICE_DROP"; + return kCommerceNotificationKey; } case PushNotificationClientId::kContent: { - return "CONTENT"; + return kContentNotificationKey; } } }
diff --git a/ios/chrome/browser/ui/authentication/signin/signin_coordinator.mm b/ios/chrome/browser/ui/authentication/signin/signin_coordinator.mm index afa986a..02336bc0 100644 --- a/ios/chrome/browser/ui/authentication/signin/signin_coordinator.mm +++ b/ios/chrome/browser/ui/authentication/signin/signin_coordinator.mm
@@ -265,8 +265,7 @@ - (void)dealloc { // -[SigninCoordinator runCompletionCallbackWithSigninResult:completionInfo:] // has to be called by the subclass before the coordinator is deallocated. - DUMP_WILL_BE_CHECK(!self.signinCompletion) - << base::SysNSStringToUTF8([self description]); + DCHECK(!self.signinCompletion) << base::SysNSStringToUTF8([self description]); } - (void)interruptWithAction:(SigninCoordinatorInterrupt)action
diff --git a/ios/chrome/browser/ui/content_suggestions/ntp_home_egtest.mm b/ios/chrome/browser/ui/content_suggestions/ntp_home_egtest.mm index 2f22df6..bfbec5d 100644 --- a/ios/chrome/browser/ui/content_suggestions/ntp_home_egtest.mm +++ b/ios/chrome/browser/ui/content_suggestions/ntp_home_egtest.mm
@@ -167,7 +167,7 @@ if ([self isRunningTest:@selector(testLargeFakeboxFocus)]) { config.features_enabled.push_back(kIOSLargeFakebox); } - if ([self isRunningTest:@selector(testMinimumHeight)]) { + if ([self isRunningTest:@selector(DISABLED_testMinimumHeight)]) { config.features_enabled.push_back(kMagicStack); } return config; @@ -999,7 +999,8 @@ performAction:grey_tap()]; } -- (void)testMinimumHeight { +// TODO(crbug.com/1510926): This test is flaky. +- (void)DISABLED_testMinimumHeight { [ChromeEarlGreyAppInterface setBoolValue:NO forUserPref:base::SysUTF8ToNSString(prefs::kArticlesForYouEnabled)];
diff --git a/ios/chrome/browser/ui/price_notifications/price_notifications_price_tracking_mediator.mm b/ios/chrome/browser/ui/price_notifications/price_notifications_price_tracking_mediator.mm index fb2dc585..4986138 100644 --- a/ios/chrome/browser/ui/price_notifications/price_notifications_price_tracking_mediator.mm +++ b/ios/chrome/browser/ui/price_notifications/price_notifications_price_tracking_mediator.mm
@@ -229,8 +229,9 @@ [self createPriceNotificationTableViewItem:NO fromProductInfo:productInfo atURL:URL]; - self.shoppingService->IsClusterIdTrackedByUser( - productInfo->product_cluster_id.value(), + self.shoppingService->IsSubscribed( + commerce::BuildUserSubscriptionForClusterId( + productInfo->product_cluster_id.value()), base::BindOnce(^(bool isTracked) { [weakSelf.consumer setTrackableItem:item currentlyTracking:isTracked]; }));
diff --git a/ios/chrome/browser/ui/settings/notifications/BUILD.gn b/ios/chrome/browser/ui/settings/notifications/BUILD.gn index 02e3340..6790ea5 100644 --- a/ios/chrome/browser/ui/settings/notifications/BUILD.gn +++ b/ios/chrome/browser/ui/settings/notifications/BUILD.gn
@@ -75,6 +75,7 @@ "//components/commerce/core:pref_names", "//components/prefs", "//components/prefs/ios:ios", + "//ios/chrome/browser/push_notification/model:constants", "//ios/chrome/browser/push_notification/model:push_notification_client", "//ios/chrome/browser/push_notification/model:push_notification_service", "//ios/chrome/browser/shared/model/application_context", @@ -83,6 +84,24 @@ ] } +source_set("unit_tests") { + testonly = true + sources = [ "notifications_settings_observer_unittest.mm" ] + deps = [ + ":notifications_ui", + ":utils", + "//base/test:test_support", + "//components/commerce/core:pref_names", + "//components/prefs", + "//components/prefs:test_support", + "//ios/chrome/browser/push_notification/model:constants", + "//ios/chrome/browser/push_notification/model:push_notification_client", + "//ios/chrome/browser/shared/model/prefs:pref_names", + "//third_party/ocmock", + ] + frameworks = [ "UIKit.framework" ] +} + source_set("eg2_tests") { configs += [ "//build/config/ios:xctest_config" ] testonly = true
diff --git a/ios/chrome/browser/ui/settings/notifications/notifications_coordinator.mm b/ios/chrome/browser/ui/settings/notifications/notifications_coordinator.mm index f727542..8b68d88 100644 --- a/ios/chrome/browser/ui/settings/notifications/notifications_coordinator.mm +++ b/ios/chrome/browser/ui/settings/notifications/notifications_coordinator.mm
@@ -81,6 +81,11 @@ animated:YES]; } +- (void)stop { + _notificationsObserver.delegate = nil; + _notificationsObserver = nil; +} + #pragma mark - NotificationsAlertPresenter - (void)presentPushNotificationPermissionAlert {
diff --git a/ios/chrome/browser/ui/settings/notifications/notifications_mediator.mm b/ios/chrome/browser/ui/settings/notifications/notifications_mediator.mm index 602db0a..5d0037a 100644 --- a/ios/chrome/browser/ui/settings/notifications/notifications_mediator.mm +++ b/ios/chrome/browser/ui/settings/notifications/notifications_mediator.mm
@@ -254,14 +254,14 @@ [self updateDetailTextForItem:_priceTrackingItem withClientID:clientID]; break; } - // TODO(b/307593022): Move Notification popup logic here when the pref is - // ready. case PushNotificationClientId::kContent: { break; } } } +#pragma mark - private + // Updates the current user's permission preference for the given `client_id`. - (void)setPreferenceFor:(PushNotificationClientId)clientID to:(BOOL)enabled { PushNotificationService* service =
diff --git a/ios/chrome/browser/ui/settings/notifications/notifications_settings_observer.mm b/ios/chrome/browser/ui/settings/notifications/notifications_settings_observer.mm index 19821af..9cbcb3a 100644 --- a/ios/chrome/browser/ui/settings/notifications/notifications_settings_observer.mm +++ b/ios/chrome/browser/ui/settings/notifications/notifications_settings_observer.mm
@@ -9,6 +9,7 @@ #import "components/commerce/core/pref_names.h" #import "components/prefs/pref_change_registrar.h" #import "components/prefs/pref_service.h" +#import "ios/chrome/browser/push_notification/model/constants.h" #import "ios/chrome/browser/push_notification/model/push_notification_client_id.h" #import "ios/chrome/browser/shared/model/prefs/pref_names.h" @@ -18,6 +19,15 @@ // Registrar for pref changes notifications. PrefChangeRegistrar _prefChangeRegistrar; + + // Pref Service. + raw_ptr<PrefService> _prefService; + + // YES if price tracing notification is enabled. + BOOL _priceTrackingNotificationEnabled; + + // YES if content notification is enabled. + BOOL _contentNotificationEnabled; } - (instancetype)initWithPrefService:(PrefService*)prefService { @@ -31,6 +41,16 @@ commerce::kPriceEmailNotificationsEnabled, &_prefChangeRegistrar); _prefObserverBridge->ObserveChangesForPreference( prefs::kFeaturePushNotificationPermissions, &_prefChangeRegistrar); + + _prefService = prefService; + _priceTrackingNotificationEnabled = + _prefService->GetDict(prefs::kFeaturePushNotificationPermissions) + .FindBool(kCommerceNotificationKey) + .value_or(false); + _contentNotificationEnabled = + _prefService->GetDict(prefs::kFeaturePushNotificationPermissions) + .FindBool(kContentNotificationKey) + .value_or(false); } return self; @@ -38,16 +58,38 @@ #pragma mark - PrefObserverDelegate -// TODO(b/304830588) Decouple kFeaturePushNotificationPermissions from Price -// Tracking to make it universally usable. Add two separate prefs for Content -// and Price Tracking, and keep the original one which is updated if at least -// one of the other prefs is True, and becomes false when both are False. - (void)onPreferenceChanged:(const std::string&)preferenceName { - if (preferenceName == commerce::kPriceEmailNotificationsEnabled || - preferenceName == prefs::kFeaturePushNotificationPermissions) { + if (preferenceName == commerce::kPriceEmailNotificationsEnabled) { [self.delegate notificationsSettingsDidChangeForClient: PushNotificationClientId::kCommerce]; + } else if (preferenceName == prefs::kFeaturePushNotificationPermissions) { + if (_priceTrackingNotificationEnabled != + [self isPriceTrackingNotificationEnabled]) { + _priceTrackingNotificationEnabled = + [self isPriceTrackingNotificationEnabled]; + [self.delegate notificationsSettingsDidChangeForClient: + PushNotificationClientId::kCommerce]; + } else if (_contentNotificationEnabled != + [self isContentNotificationEnabled]) { + _contentNotificationEnabled = [self isContentNotificationEnabled]; + [self.delegate notificationsSettingsDidChangeForClient: + PushNotificationClientId::kContent]; + } } } +#pragma mark - private + +- (BOOL)isPriceTrackingNotificationEnabled { + return _prefService->GetDict(prefs::kFeaturePushNotificationPermissions) + .FindBool(kCommerceNotificationKey) + .value_or(false); +} + +- (BOOL)isContentNotificationEnabled { + return _prefService->GetDict(prefs::kFeaturePushNotificationPermissions) + .FindBool(kContentNotificationKey) + .value_or(false); +} + @end
diff --git a/ios/chrome/browser/ui/settings/notifications/notifications_settings_observer_unittest.mm b/ios/chrome/browser/ui/settings/notifications/notifications_settings_observer_unittest.mm new file mode 100644 index 0000000..95467ac --- /dev/null +++ b/ios/chrome/browser/ui/settings/notifications/notifications_settings_observer_unittest.mm
@@ -0,0 +1,74 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#import "ios/chrome/browser/ui/settings/notifications/notifications_settings_observer.h" + +#import "base/test/task_environment.h" +#import "components/commerce/core/pref_names.h" +#import "components/prefs/pref_registry_simple.h" +#import "components/prefs/scoped_user_pref_update.h" +#import "components/prefs/testing_pref_service.h" +#import "ios/chrome/browser/push_notification/model/constants.h" +#import "ios/chrome/browser/push_notification/model/push_notification_client_id.h" +#import "ios/chrome/browser/shared/model/prefs/pref_names.h" +#import "ios/chrome/browser/ui/settings/notifications/notifications_settings_observer.h" +#import "testing/platform_test.h" +#import "third_party/ocmock/OCMock/OCMock.h" +#import "third_party/ocmock/gtest_support.h" + +// Tests NotificationsSettingsObserver functionality. +class NotificationsSettingsObserverTest : public PlatformTest { + protected: + void SetUp() override { + PlatformTest::SetUp(); + + pref_service_ = std::make_unique<TestingPrefServiceSimple>(); + + pref_service_->registry()->RegisterDictionaryPref( + prefs::kFeaturePushNotificationPermissions); + pref_service_->registry()->RegisterBooleanPref( + commerce::kPriceEmailNotificationsEnabled, false); + + observer_ = [[NotificationsSettingsObserver alloc] + initWithPrefService:pref_service_.get()]; + observer_.delegate = mock_delegate_; + } + + void TurnOnNotificationForKey(const std::string key) { + ScopedDictPrefUpdate update(pref_service_.get(), + prefs::kFeaturePushNotificationPermissions); + update->Set(key, true); + } + + base::test::TaskEnvironment task_environment_; + std::unique_ptr<TestingPrefServiceSimple> pref_service_; + NotificationsSettingsObserver* observer_; + id<NotificationsSettingsObserverDelegate> mock_delegate_ = + OCMProtocolMock(@protocol(NotificationsSettingsObserverDelegate)); +}; + +// Tests the observer delegate is notified with correct client id when pref +// kPriceEmailNotificationsEnabled changed. +TEST_F(NotificationsSettingsObserverTest, + PrefkPriceEmailNotificationsEnabledChanged) { + OCMExpect([mock_delegate_ notificationsSettingsDidChangeForClient: + PushNotificationClientId::kCommerce]); + pref_service_->SetBoolean(commerce::kPriceEmailNotificationsEnabled, true); + EXPECT_OCMOCK_VERIFY(mock_delegate_); +} + +// Tests the observer delegate is notified with correct client id when +// kFeaturePushNotificationPermissions pref changed. +TEST_F(NotificationsSettingsObserverTest, + PrefkFeaturePushNotificationPermissionsChanged) { + OCMExpect([mock_delegate_ notificationsSettingsDidChangeForClient: + PushNotificationClientId::kCommerce]); + TurnOnNotificationForKey(kCommerceNotificationKey); + EXPECT_OCMOCK_VERIFY(mock_delegate_); + + OCMExpect([mock_delegate_ notificationsSettingsDidChangeForClient: + PushNotificationClientId::kContent]); + TurnOnNotificationForKey(kContentNotificationKey); + EXPECT_OCMOCK_VERIFY(mock_delegate_); +}
diff --git a/ios/chrome/test/BUILD.gn b/ios/chrome/test/BUILD.gn index 3209cab..dcbe10b 100644 --- a/ios/chrome/test/BUILD.gn +++ b/ios/chrome/test/BUILD.gn
@@ -407,6 +407,7 @@ "//ios/chrome/browser/ui/settings/downloads/save_to_photos:unit_tests", "//ios/chrome/browser/ui/settings/google_services:unit_tests", "//ios/chrome/browser/ui/settings/language:unit_tests", + "//ios/chrome/browser/ui/settings/notifications:unit_tests", "//ios/chrome/browser/ui/settings/password:unit_tests", "//ios/chrome/browser/ui/settings/password/password_checkup:unit_tests", "//ios/chrome/browser/ui/settings/password/password_details:unit_tests",
diff --git a/ios/web/shell/BUILD.gn b/ios/web/shell/BUILD.gn index 0463438a..0cce78b0 100644 --- a/ios/web/shell/BUILD.gn +++ b/ios/web/shell/BUILD.gn
@@ -9,6 +9,7 @@ ios_app_bundle("ios_web_shell") { info_plist = "Info.plist" + bundle_identifier = shared_bundle_id_for_test_apps deps = [ ":shell" ]
diff --git a/media/base/media_switches.cc b/media/base/media_switches.cc index f9e9d363..514edfef 100644 --- a/media/base/media_switches.cc +++ b/media/base/media_switches.cc
@@ -145,11 +145,6 @@ // automated testing. const char kMuteAudio[] = "mute-audio"; -// Allows clients to override the threshold for when the media renderer will -// declare the underflow state for the video stream when audio is present. -// TODO(dalecurtis): Remove once experiments for http://crbug.com/470940 finish. -const char kVideoUnderflowThresholdMs[] = "video-underflow-threshold-ms"; - // Disables the new rendering algorithm for webrtc, which is designed to improve // the rendering smoothness. const char kDisableRTCSmoothnessAlgorithm[] =
diff --git a/media/base/media_switches.h b/media/base/media_switches.h index 04f5528f..cbb5753 100644 --- a/media/base/media_switches.h +++ b/media/base/media_switches.h
@@ -71,8 +71,6 @@ MEDIA_EXPORT extern const char kMuteAudio[]; -MEDIA_EXPORT extern const char kVideoUnderflowThresholdMs[]; - MEDIA_EXPORT extern const char kDisableRTCSmoothnessAlgorithm[]; MEDIA_EXPORT extern const char kForceVideoOverlays[];
diff --git a/net/cert/ct_policy_enforcer.cc b/net/cert/ct_policy_enforcer.cc index 717d022a..5f8ddf1 100644 --- a/net/cert/ct_policy_enforcer.cc +++ b/net/cert/ct_policy_enforcer.cc
@@ -11,7 +11,7 @@ ct::CTPolicyCompliance DefaultCTPolicyEnforcer::CheckCompliance( X509Certificate* cert, const ct::SCTList& verified_scts, - const NetLogWithSource& net_log) { + const NetLogWithSource& net_log) const { return ct::CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY; }
diff --git a/net/cert/ct_policy_enforcer.h b/net/cert/ct_policy_enforcer.h index 47be4b7..9721e61b 100644 --- a/net/cert/ct_policy_enforcer.h +++ b/net/cert/ct_policy_enforcer.h
@@ -38,7 +38,7 @@ virtual ct::CTPolicyCompliance CheckCompliance( X509Certificate* cert, const ct::SCTList& verified_scts, - const NetLogWithSource& net_log) = 0; + const NetLogWithSource& net_log) const = 0; }; // A default implementation of Certificate Transparency policies that is @@ -53,7 +53,7 @@ ct::CTPolicyCompliance CheckCompliance( X509Certificate* cert, const ct::SCTList& verified_scts, - const NetLogWithSource& net_log) override; + const NetLogWithSource& net_log) const override; }; } // namespace net
diff --git a/net/quic/crypto/proof_verifier_chromium_test.cc b/net/quic/crypto/proof_verifier_chromium_test.cc index 1ef3097..2f63604 100644 --- a/net/quic/crypto/proof_verifier_chromium_test.cc +++ b/net/quic/crypto/proof_verifier_chromium_test.cc
@@ -70,10 +70,10 @@ // A mock CTPolicyEnforcer that returns a custom verification result. class MockCTPolicyEnforcer : public CTPolicyEnforcer { public: - MOCK_METHOD3(CheckCompliance, - ct::CTPolicyCompliance(X509Certificate* cert, - const ct::SCTList&, - const NetLogWithSource&)); + MOCK_CONST_METHOD3(CheckCompliance, + ct::CTPolicyCompliance(X509Certificate* cert, + const ct::SCTList&, + const NetLogWithSource&)); }; class MockRequireCTDelegate : public TransportSecurityState::RequireCTDelegate {
diff --git a/net/socket/ssl_client_socket_unittest.cc b/net/socket/ssl_client_socket_unittest.cc index 6cde27e2..9f11df6 100644 --- a/net/socket/ssl_client_socket_unittest.cc +++ b/net/socket/ssl_client_socket_unittest.cc
@@ -585,10 +585,10 @@ // A mock CTPolicyEnforcer that returns a custom verification result. class MockCTPolicyEnforcer : public CTPolicyEnforcer { public: - MOCK_METHOD3(CheckCompliance, - ct::CTPolicyCompliance(X509Certificate* cert, - const ct::SCTList&, - const NetLogWithSource&)); + MOCK_CONST_METHOD3(CheckCompliance, + ct::CTPolicyCompliance(X509Certificate* cert, + const ct::SCTList&, + const NetLogWithSource&)); }; class MockRequireCTDelegate : public TransportSecurityState::RequireCTDelegate {
diff --git a/net/socket/ssl_server_socket_unittest.cc b/net/socket/ssl_server_socket_unittest.cc index 7dc2434..265e8cfe 100644 --- a/net/socket/ssl_server_socket_unittest.cc +++ b/net/socket/ssl_server_socket_unittest.cc
@@ -115,7 +115,7 @@ ct::CTPolicyCompliance CheckCompliance( X509Certificate* cert, const ct::SCTList& verified_scts, - const NetLogWithSource& net_log) override { + const NetLogWithSource& net_log) const override { return ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS; } };
diff --git a/net/url_request/url_request_quic_unittest.cc b/net/url_request/url_request_quic_unittest.cc index c823354..b6ef5e9 100644 --- a/net/url_request/url_request_quic_unittest.cc +++ b/net/url_request/url_request_quic_unittest.cc
@@ -66,7 +66,7 @@ ct::CTPolicyCompliance CheckCompliance( X509Certificate* cert, const ct::SCTList& verified_scts, - const NetLogWithSource& net_log) override { + const NetLogWithSource& net_log) const override { return ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS; } };
diff --git a/services/tracing/perfetto/privacy_filtered_fields-inl.h b/services/tracing/perfetto/privacy_filtered_fields-inl.h index 68b1c10..a2b403181 100644 --- a/services/tracing/perfetto/privacy_filtered_fields-inl.h +++ b/services/tracing/perfetto/privacy_filtered_fields-inl.h
@@ -460,6 +460,19 @@ constexpr MessageInfo kScrollPredictorMetrics = { kScrollPredictorMetricsIndices, kScrollPredictorMetricsComplexMessages}; +// Proto Message: PageLoad +constexpr int kPageLoadIndices[] = {1, -1}; +constexpr MessageInfo kPageLoad = {kPageLoadIndices, nullptr}; + +// Proto Message: StartUp +constexpr int kStartUpIndices[] = {1, 3, -1}; +constexpr MessageInfo kStartUp = {kStartUpIndices, nullptr}; + +// Proto Message: WebContentInteraction +constexpr int kWebContentInteractionIndices[] = {1, 2, -1}; +constexpr MessageInfo kWebContentInteraction = {kWebContentInteractionIndices, + nullptr}; + // Proto Message: TrackEvent constexpr int kTrackEventIndices[] = { 1, 2, 3, 5, 6, 9, 10, 11, 12, 16, 17, 22, @@ -468,7 +481,7 @@ 1003, 1004, 1005, 1006, 1007, 1008, 1009, 1010, 1011, 1012, 1013, 1014, 1015, 1016, 1017, 1018, 1019, 1020, 1021, 1022, 1023, 1024, 1025, 1028, 1031, 1032, 1033, 1034, 1036, 1038, 1039, 1040, 1041, 1042, 1046, 1047, - 1048, 1049, 1050, 1051, 1052, 1053, 1054, 1055, -1}; + 1048, 1049, 1050, 1051, 1052, 1053, 1054, 1055, 1056, 1057, 1058, -1}; constexpr MessageInfo const* kTrackEventComplexMessages[] = { nullptr, nullptr, @@ -549,7 +562,10 @@ &kChromeGraphicsPipeline, &kCrasUnified, &kLibunwindstackUnwinder, - &kScrollPredictorMetrics}; + &kScrollPredictorMetrics, + &kPageLoad, + &kStartUp, + &kWebContentInteraction}; constexpr MessageInfo kTrackEvent = {kTrackEventIndices, kTrackEventComplexMessages}; @@ -632,9 +648,9 @@ constexpr MessageInfo kNamedRule = {kNamedRuleIndices, nullptr}; // Proto Message: TriggerRule -constexpr int kTriggerRuleIndices[] = {1, 2, 3, -1}; +constexpr int kTriggerRuleIndices[] = {1, 2, 3, 4, -1}; constexpr MessageInfo const* kTriggerRuleComplexMessages[] = { - nullptr, &kHistogramRule, &kNamedRule}; + nullptr, &kHistogramRule, &kNamedRule, nullptr}; constexpr MessageInfo kTriggerRule = {kTriggerRuleIndices, kTriggerRuleComplexMessages}; @@ -724,9 +740,14 @@ constexpr MessageInfo kTrackDescriptor = {kTrackDescriptorIndices, kTrackDescriptorComplexMessages}; +// Proto Message: TraceUuid +constexpr int kTraceUuidIndices[] = {1, 2, -1}; +constexpr MessageInfo kTraceUuid = {kTraceUuidIndices, nullptr}; + // Proto Message: TracePacket -constexpr int kTracePacketIndices[] = {6, 8, 10, 11, 12, 13, 35, 36, 41, 42, - 43, 44, 51, 54, 56, 58, 59, 60, 87, -1}; +constexpr int kTracePacketIndices[] = {6, 8, 10, 11, 12, 13, 35, + 36, 41, 42, 43, 44, 51, 54, + 56, 58, 59, 60, 87, 89, -1}; constexpr MessageInfo const* kTracePacketComplexMessages[] = { &kClockSnapshot, nullptr, @@ -746,7 +767,8 @@ nullptr, &kTracePacketDefaults, &kTrackDescriptor, - nullptr}; + nullptr, + &kTraceUuid}; constexpr MessageInfo kTracePacket = {kTracePacketIndices, kTracePacketComplexMessages};
diff --git a/skia/BUILD.gn b/skia/BUILD.gn index 9839362..7d6900c 100644 --- a/skia/BUILD.gn +++ b/skia/BUILD.gn
@@ -596,18 +596,14 @@ } if (skia_support_pdf) { + # Blink includes Skia's JPEG encoder and decoder which pdf uses. + assert(use_blink) deps += [ "//third_party:freetype_harfbuzz", "//third_party/zlib", ] public += skia_pdf_public sources += skia_pdf_sources - if (use_blink) { - # Blink includes Skia's JPEG decoder - sources += skia_pdf_jpeginfo_lib - } else { - sources += skia_pdf_jpeginfo_none - } } else { sources += [ "//third_party/skia/src/pdf/SkDocument_PDF_None.cpp" ] }
diff --git a/testing/buildbot/chromium.chromiumos.json b/testing/buildbot/chromium.chromiumos.json index cd4c6f9..8e2eef0 100644 --- a/testing/buildbot/chromium.chromiumos.json +++ b/testing/buildbot/chromium.chromiumos.json
@@ -6193,9 +6193,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter;../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "isolate_profile_data": true, "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" @@ -6205,8 +6205,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": { @@ -6343,9 +6343,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.filter;../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "isolate_profile_data": true, "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" @@ -6355,8 +6355,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": {
diff --git a/testing/buildbot/chromium.coverage.json b/testing/buildbot/chromium.coverage.json index a47178cf..461ad43 100644 --- a/testing/buildbot/chromium.coverage.json +++ b/testing/buildbot/chromium.coverage.json
@@ -20593,9 +20593,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter;../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "isolate_profile_data": true, "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" @@ -20605,8 +20605,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": { @@ -20743,9 +20743,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.filter;../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "isolate_profile_data": true, "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" @@ -20755,8 +20755,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": {
diff --git a/testing/buildbot/chromium.fyi.json b/testing/buildbot/chromium.fyi.json index dadbf733..d233607 100644 --- a/testing/buildbot/chromium.fyi.json +++ b/testing/buildbot/chromium.fyi.json
@@ -43432,9 +43432,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter;../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" }, @@ -43443,8 +43443,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": { @@ -43582,9 +43582,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.filter;../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" }, @@ -43593,8 +43593,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": { @@ -44906,9 +44906,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter;../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" }, @@ -44917,8 +44917,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": { @@ -45056,9 +45056,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.filter;../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" }, @@ -45067,8 +45067,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": { @@ -45766,9 +45766,9 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter;../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" }, @@ -45777,8 +45777,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": {
diff --git a/testing/buildbot/chromium.memory.json b/testing/buildbot/chromium.memory.json index a645e4fd..4e08cee 100644 --- a/testing/buildbot/chromium.memory.json +++ b/testing/buildbot/chromium.memory.json
@@ -16313,12 +16313,12 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter;../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome", + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome", "--test-launcher-print-test-stdio=always", "--combine-ash-logs-on-bots", "--asan-symbolize-output" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "isolate_profile_data": true, "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" @@ -16328,8 +16328,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": { @@ -16483,12 +16483,12 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.filter;../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome", + "--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome", "--test-launcher-print-test-stdio=always", "--combine-ash-logs-on-bots", "--asan-symbolize-output" ], - "description": "Run with ash-chrome version 122.0.6180.0", + "description": "Run with ash-chrome version 122.0.6181.0", "isolate_profile_data": true, "merge": { "script": "//testing/merge_scripts/standard_gtest_merge.py" @@ -16498,8 +16498,8 @@ "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v122.0.6180.0", - "revision": "version:122.0.6180.0" + "location": "lacros_version_skew_tests_v122.0.6181.0", + "revision": "version:122.0.6181.0" } ], "dimensions": {
diff --git a/testing/buildbot/filters/android.emulator_11.content_shell_test_apk.filter b/testing/buildbot/filters/android.emulator_11.content_shell_test_apk.filter index f42e467..d4fe188 100644 --- a/testing/buildbot/filters/android.emulator_11.content_shell_test_apk.filter +++ b/testing/buildbot/filters/android.emulator_11.content_shell_test_apk.filter
@@ -5,9 +5,6 @@ -org.chromium.content.browser.input.ImeInputModeTest.testShowAndHideInputMode -org.chromium.content.browser.input.ImeInputModeTest.testShowAndHideInputModeWithPhysicalKeyboard -# crbug.com/1220151 --org.chromium.base.task.AsyncTaskTest.testChromeThreadPoolExecutorOsAsyncTask - # crbug.com/1220155 -org.chromium.content.browser.ContentTextSelectionTest.testSelectionClearedAfterLossOfFocus -org.chromium.content.browser.ContentTextSelectionTest.testSelectionPreservedAfterLossOfFocusIfRequested
diff --git a/testing/buildbot/filters/android.emulator_12.content_shell_test_apk.filter b/testing/buildbot/filters/android.emulator_12.content_shell_test_apk.filter index 9e73461..ab91c383 100644 --- a/testing/buildbot/filters/android.emulator_12.content_shell_test_apk.filter +++ b/testing/buildbot/filters/android.emulator_12.content_shell_test_apk.filter
@@ -6,9 +6,6 @@ -org.chromium.content.browser.input.ImeInputModeTest.testShowAndHideInputMode -org.chromium.content.browser.input.ImeInputModeTest.testShowAndHideInputModeWithPhysicalKeyboard -# https://crbug.com/1220151 --org.chromium.base.task.AsyncTaskTest.testChromeThreadPoolExecutorOsAsyncTask - # https://crbug.com/1233309 -org.chromium.content.browser.GestureDetectorResetTest.testSeparateClicksAreRegisteredOnReload
diff --git a/testing/buildbot/filters/android.emulator_12l.content_shell_test_apk.filter b/testing/buildbot/filters/android.emulator_12l.content_shell_test_apk.filter index 11b66342..21cb3c5 100644 --- a/testing/buildbot/filters/android.emulator_12l.content_shell_test_apk.filter +++ b/testing/buildbot/filters/android.emulator_12l.content_shell_test_apk.filter
@@ -6,9 +6,6 @@ -org.chromium.content.browser.input.ImeInputModeTest.testShowAndHideInputMode -org.chromium.content.browser.input.ImeInputModeTest.testShowAndHideInputModeWithPhysicalKeyboard -# https://crbug.com/1220151 --org.chromium.base.task.AsyncTaskTest.testChromeThreadPoolExecutorOsAsyncTask - # https://crbug.com/1233309 -org.chromium.content.browser.GestureDetectorResetTest.testSeparateClicksAreRegisteredOnReload
diff --git a/testing/buildbot/filters/android.emulator_13.content_shell_test_apk.filter b/testing/buildbot/filters/android.emulator_13.content_shell_test_apk.filter index 6c4983a..bb7e871 100644 --- a/testing/buildbot/filters/android.emulator_13.content_shell_test_apk.filter +++ b/testing/buildbot/filters/android.emulator_13.content_shell_test_apk.filter
@@ -6,9 +6,6 @@ -org.chromium.content.browser.input.ImeInputModeTest.testShowAndHideInputMode -org.chromium.content.browser.input.ImeInputModeTest.testShowAndHideInputModeWithPhysicalKeyboard -# https://crbug.com/1220151 --org.chromium.base.task.AsyncTaskTest.testChromeThreadPoolExecutorOsAsyncTask - # https://crbug.com/1233309 -org.chromium.content.browser.GestureDetectorResetTest.testSeparateClicksAreRegisteredOnReload
diff --git a/testing/buildbot/variants.pyl b/testing/buildbot/variants.pyl index 33978b9..f644df0 100644 --- a/testing/buildbot/variants.pyl +++ b/testing/buildbot/variants.pyl
@@ -337,16 +337,16 @@ }, 'LACROS_VERSION_SKEW_CANARY': { 'identifier': 'Lacros version skew testing ash canary', - 'description': 'Run with ash-chrome version 122.0.6180.0', + 'description': 'Run with ash-chrome version 122.0.6181.0', 'args': [ - '--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6180.0/test_ash_chrome', + '--ash-chrome-path-override=../../lacros_version_skew_tests_v122.0.6181.0/test_ash_chrome', ], 'swarming': { 'cipd_packages': [ { 'cipd_package': 'chromium/testing/linux-ash-chromium/x86_64/ash.zip', - 'location': 'lacros_version_skew_tests_v122.0.6180.0', - 'revision': 'version:122.0.6180.0', + 'location': 'lacros_version_skew_tests_v122.0.6181.0', + 'revision': 'version:122.0.6181.0', }, ], },
diff --git a/testing/variations/fieldtrial_testing_config.json b/testing/variations/fieldtrial_testing_config.json index fdbbdbe..3d52c7bf 100644 --- a/testing/variations/fieldtrial_testing_config.json +++ b/testing/variations/fieldtrial_testing_config.json
@@ -2921,21 +2921,6 @@ ] } ], - "CCTRealTimeEngagementSignalsAlternativeImpl": [ - { - "platforms": [ - "android" - ], - "experiments": [ - { - "name": "Enabled", - "enable_features": [ - "CCTRealTimeEngagementSignalsAlternativeImpl" - ] - } - ] - } - ], "CPSS": [ { "platforms": [ @@ -5601,6 +5586,37 @@ ] } ], + "DesktopLinkCapturingPWAExperiment": [ + { + "platforms": [ + "linux", + "mac", + "windows" + ], + "experiments": [ + { + "name": "Enabled_DefaultOn", + "params": { + "link_capturing_guardrail_storage_duration": "60", + "on_by_default": "true" + }, + "enable_features": [ + "DesktopPWAsLinkCapturing" + ] + }, + { + "name": "Enabled_DefaultOff", + "params": { + "link_capturing_guardrail_storage_duration": "60", + "on_by_default": "false" + }, + "enable_features": [ + "DesktopPWAsLinkCapturing" + ] + } + ] + } + ], "DesktopNtpDriveCache": [ { "platforms": [ @@ -13783,6 +13799,25 @@ ] } ], + "PriceTrackingIconColors": [ + { + "platforms": [ + "chromeos", + "chromeos_lacros", + "linux", + "mac", + "windows" + ], + "experiments": [ + { + "name": "Enabled", + "enable_features": [ + "PriceTrackingIconColors" + ] + } + ] + } + ], "PriceTrackingPageActionIconLabelFeatureIPH": [ { "platforms": [ @@ -15625,9 +15660,7 @@ "name": "Enabled", "enable_features": [ "ShoppingCollection", - "ShoppingListTrackByDefault", - "ShoppingListWAARestrictionRemoval", - "SimplifiedBookmarkSaveFlow" + "ShoppingListTrackByDefault" ] } ]
diff --git a/third_party/angle b/third_party/angle index 398cfb4..f8fae1f 160000 --- a/third_party/angle +++ b/third_party/angle
@@ -1 +1 @@ -Subproject commit 398cfb4b1421901b8c18be07faf5f54bf14c7633 +Subproject commit f8fae1ff4fae14fc6ba0aa1dc3af2e13a6e9a597
diff --git a/third_party/blink/public/common/fenced_frame/redacted_fenced_frame_config.h b/third_party/blink/public/common/fenced_frame/redacted_fenced_frame_config.h index aa26830..9cfbd705 100644 --- a/third_party/blink/public/common/fenced_frame/redacted_fenced_frame_config.h +++ b/third_party/blink/public/common/fenced_frame/redacted_fenced_frame_config.h
@@ -23,7 +23,7 @@ namespace content { struct FencedFrameConfig; -struct FencedFrameProperties; +class FencedFrameProperties; } // namespace content namespace blink::FencedFrame { @@ -208,7 +208,7 @@ } private: - friend struct content::FencedFrameProperties; + friend class content::FencedFrameProperties; friend struct mojo::StructTraits< blink::mojom::FencedFramePropertiesDataView, blink::FencedFrame::RedactedFencedFrameProperties>;
diff --git a/third_party/blink/public/web/web_autofill_client.h b/third_party/blink/public/web/web_autofill_client.h index 78d02a88..98e6356 100644 --- a/third_party/blink/public/web/web_autofill_client.h +++ b/third_party/blink/public/web/web_autofill_client.h
@@ -66,6 +66,9 @@ virtual void TextFieldDidChange(const WebFormControlElement&) {} virtual void TextFieldDidReceiveKeyDown(const WebInputElement&, const WebKeyboardEvent&) {} + // This is called once per-character when a user edits a contenteditable + // element by typing. + virtual void ContentEditableDidChange(const WebElement&) {} // This is called when a datalist indicator is clicked. virtual void OpenTextDataListChooser(const WebInputElement&) {} // This is called when the datalist for an input has changed.
diff --git a/third_party/blink/public/web/web_element.h b/third_party/blink/public/web/web_element.h index 02fa305..9cd08e8 100644 --- a/third_party/blink/public/web/web_element.h +++ b/third_party/blink/public/web/web_element.h
@@ -80,6 +80,7 @@ WebString GetAttribute(const WebString&) const; void SetAttribute(const WebString& name, const WebString& value); WebString TextContent() const; + WebString TextContentAbridged(unsigned int max_length) const; WebString InnerHTML() const; // Returns true if the element's contenteditable attribute is in the true
diff --git a/third_party/blink/renderer/core/css/css_style_declaration.cc b/third_party/blink/renderer/core/css/css_style_declaration.cc index 044b1fc..ce913fe1 100644 --- a/third_party/blink/renderer/core/css/css_style_declaration.cc +++ b/third_party/blink/renderer/core/css/css_style_declaration.cc
@@ -42,6 +42,7 @@ #include "third_party/blink/renderer/core/css/properties/css_property.h" #include "third_party/blink/renderer/core/css/property_bitsets.h" #include "third_party/blink/renderer/core/execution_context/execution_context.h" +#include "third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h" #include "third_party/blink/renderer/platform/bindings/exception_state.h" #include "third_party/blink/renderer/platform/bindings/script_state.h" #include "third_party/blink/renderer/platform/wtf/std_lib_extras.h" @@ -224,6 +225,9 @@ "CSSStyleDeclaration", CSSProperty::Get(ResolveCSSPropertyID(unresolved_property)) .GetPropertyName()); + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidSetStyle(); if (value->IsNumber()) { double double_value = NativeValueTraits<IDLUnrestrictedDouble>::NativeValue( script_state->GetIsolate(), value, exception_state);
diff --git a/third_party/blink/renderer/core/dom/element.cc b/third_party/blink/renderer/core/dom/element.cc index 67c4e53a..3610b6b 100644 --- a/third_party/blink/renderer/core/dom/element.cc +++ b/third_party/blink/renderer/core/dom/element.cc
@@ -185,6 +185,7 @@ #include "third_party/blink/renderer/core/page/page_animator.h" #include "third_party/blink/renderer/core/page/pointer_lock_controller.h" #include "third_party/blink/renderer/core/page/scrolling/root_scroller_controller.h" +#include "third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h" #include "third_party/blink/renderer/core/page/spatial_navigation.h" #include "third_party/blink/renderer/core/paint/paint_layer.h" #include "third_party/blink/renderer/core/paint/paint_layer_scrollable_area.h" @@ -1556,6 +1557,10 @@ return 0; } + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); + GetDocument().UpdateStyleAndLayoutForNode(this, DocumentUpdateReason::kJavaScript); @@ -1592,6 +1597,10 @@ return 0; } + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); + GetDocument().UpdateStyleAndLayoutForNode(this, DocumentUpdateReason::kJavaScript); @@ -2150,6 +2159,9 @@ } DOMRectList* Element::getClientRects() { + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); GetDocument().EnsurePaintLocationDataValidForNode( this, DocumentUpdateReason::kJavaScript); Vector<gfx::QuadF> quads; @@ -2199,6 +2211,9 @@ } DOMRect* Element::GetBoundingClientRectForBinding() { + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); return GetBoundingClientRect(); }
diff --git a/third_party/blink/renderer/core/dom/element.h b/third_party/blink/renderer/core/dom/element.h index 4e5cd001..b8ee4e9 100644 --- a/third_party/blink/renderer/core/dom/element.h +++ b/third_party/blink/renderer/core/dom/element.h
@@ -412,7 +412,7 @@ DOMRectList* getClientRects(); // Returns a rectangle in zoomed pixel units. gfx::RectF GetBoundingClientRectNoLifecycleUpdateNoAdjustment() const; - // Returns a rectangle in CSS pixel units. i.e. ignorign zoom. + // Returns a rectangle in CSS pixel units. i.e. ignoring zoom. gfx::RectF GetBoundingClientRectNoLifecycleUpdate() const; DOMRect* GetBoundingClientRect(); DOMRect* GetBoundingClientRectForBinding();
diff --git a/third_party/blink/renderer/core/dom/node.cc b/third_party/blink/renderer/core/dom/node.cc index c3621aa..d63585e 100644 --- a/third_party/blink/renderer/core/dom/node.cc +++ b/third_party/blink/renderer/core/dom/node.cc
@@ -1940,7 +1940,8 @@ } String Node::textContent(bool convert_brs_to_newlines, - TextVisitor* visitor) const { + TextVisitor* visitor, + unsigned int max_length) const { // This covers ProcessingInstruction and Comment that should return their // value when .textContent is accessed on them, but should be ignored when // iterated over as a descendant of a ContainerNode. @@ -1965,8 +1966,14 @@ content.Append('\n'); } else if (auto* text_node = DynamicTo<Text>(node)) { content.Append(text_node->data()); + // Only abridge text content when max_length is explicitly set. + if (max_length < UINT_MAX && content.length() > max_length) { + content.Resize(max_length); + break; + } } } + return content.ReleaseString(); }
diff --git a/third_party/blink/renderer/core/dom/node.h b/third_party/blink/renderer/core/dom/node.h index bea7a0a..8ce0445d 100644 --- a/third_party/blink/renderer/core/dom/node.h +++ b/third_party/blink/renderer/core/dom/node.h
@@ -26,6 +26,8 @@ #ifndef THIRD_PARTY_BLINK_RENDERER_CORE_DOM_NODE_H_ #define THIRD_PARTY_BLINK_RENDERER_CORE_DOM_NODE_H_ +#include <climits> + #include "base/dcheck_is_on.h" #include "base/notreached.h" #include "third_party/blink/public/mojom/input/focus_type.mojom-blink-forward.h" @@ -305,7 +307,8 @@ const AtomicString& lookupNamespaceURI(const String& prefix) const; String textContent(bool convert_brs_to_newlines = false, - TextVisitor* visitor = nullptr) const; + TextVisitor* visitor = nullptr, + unsigned int max_length = UINT_MAX) const; virtual void setTextContent(const String&); V8UnionStringOrTrustedScript* textContentForBinding() const; virtual void setTextContentForBinding(
diff --git a/third_party/blink/renderer/core/dom/range.cc b/third_party/blink/renderer/core/dom/range.cc index 7df78ca..0c86ea1 100644 --- a/third_party/blink/renderer/core/dom/range.cc +++ b/third_party/blink/renderer/core/dom/range.cc
@@ -57,6 +57,7 @@ #include "third_party/blink/renderer/core/layout/layout_object.h" #include "third_party/blink/renderer/core/layout/layout_text.h" #include "third_party/blink/renderer/core/layout/layout_text_fragment.h" +#include "third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h" #include "third_party/blink/renderer/core/svg/svg_svg_element.h" #include "third_party/blink/renderer/core/trustedtypes/trusted_types_util.h" #include "third_party/blink/renderer/platform/bindings/exception_state.h" @@ -1611,6 +1612,9 @@ } DOMRectList* Range::getClientRects() const { + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); DisplayLockUtilities::ScopedForcedUpdate force_locks( this, DisplayLockContext::ForcedPhase::kLayout); owner_document_->UpdateStyleAndLayout(DocumentUpdateReason::kJavaScript); @@ -1622,6 +1626,9 @@ } DOMRect* Range::getBoundingClientRect() const { + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); return DOMRect::FromRectF(BoundingRect()); }
diff --git a/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc b/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc index cee73ba..d2718143 100644 --- a/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc +++ b/third_party/blink/renderer/core/editing/commands/composite_edit_command.cc
@@ -72,6 +72,7 @@ #include "third_party/blink/renderer/core/editing/visible_selection.h" #include "third_party/blink/renderer/core/editing/visible_units.h" #include "third_party/blink/renderer/core/frame/local_frame.h" +#include "third_party/blink/renderer/core/html/forms/html_input_element.h" #include "third_party/blink/renderer/core/html/html_br_element.h" #include "third_party/blink/renderer/core/html/html_div_element.h" #include "third_party/blink/renderer/core/html/html_element.h" @@ -82,6 +83,8 @@ #include "third_party/blink/renderer/core/html_names.h" #include "third_party/blink/renderer/core/layout/layout_block_flow.h" #include "third_party/blink/renderer/core/layout/layout_text.h" +#include "third_party/blink/renderer/core/page/chrome_client.h" +#include "third_party/blink/renderer/core/page/page.h" #include "third_party/blink/renderer/platform/bindings/exception_state.h" #include "third_party/blink/renderer/platform/heap/collection_support/clear_collection_scope.h" #include "third_party/blink/renderer/platform/heap/garbage_collected.h" @@ -2101,6 +2104,12 @@ // Command will be equal to last edit command only in the case of typing if (last_edit_command == this) { DCHECK(IsTypingCommand()); + if (Element* element = undo_step.StartingRootEditableElement()) { + element->GetDocument() + .GetPage() + ->GetChromeClient() + .DidUserChangeContentEditableContent(*element); + } } else if (last_edit_command && last_edit_command->IsDragAndDropCommand() && (GetInputType() == InputEvent::InputType::kDeleteByDrag || GetInputType() == InputEvent::InputType::kInsertFromDrop)) {
diff --git a/third_party/blink/renderer/core/exported/web_element.cc b/third_party/blink/renderer/core/exported/web_element.cc index e8c7cb3..0639dd6 100644 --- a/third_party/blink/renderer/core/exported/web_element.cc +++ b/third_party/blink/renderer/core/exported/web_element.cc
@@ -119,6 +119,9 @@ WebString WebElement::TextContent() const { return ConstUnwrap<Element>()->textContent(); } +WebString WebElement::TextContentAbridged(const unsigned int max_length) const { + return ConstUnwrap<Element>()->textContent(false, nullptr, max_length); +} WebString WebElement::InnerHTML() const { return ConstUnwrap<Element>()->innerHTML();
diff --git a/third_party/blink/renderer/core/frame/dom_visual_viewport.cc b/third_party/blink/renderer/core/frame/dom_visual_viewport.cc index a53763d..c7de067 100644 --- a/third_party/blink/renderer/core/frame/dom_visual_viewport.cc +++ b/third_party/blink/renderer/core/frame/dom_visual_viewport.cc
@@ -35,6 +35,7 @@ #include "third_party/blink/renderer/core/geometry/dom_rect.h" #include "third_party/blink/renderer/core/layout/adjust_for_absolute_zoom.h" #include "third_party/blink/renderer/core/page/page.h" +#include "third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h" #include "third_party/blink/renderer/core/paint/paint_layer_scrollable_area.h" #include "third_party/blink/renderer/core/style/computed_style.h" #include "third_party/blink/renderer/platform/widget/frame_widget.h" @@ -94,6 +95,10 @@ if (!view || !view->LayoutViewport()) return 0; + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); + frame->GetDocument()->UpdateStyleAndLayout(DocumentUpdateReason::kJavaScript); float viewport_x = view->LayoutViewport()->GetScrollOffset().x(); @@ -117,6 +122,10 @@ if (!view || !view->LayoutViewport()) return 0; + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); + frame->GetDocument()->UpdateStyleAndLayout(DocumentUpdateReason::kJavaScript); float viewport_y = view->LayoutViewport()->GetScrollOffset().y();
diff --git a/third_party/blink/renderer/core/frame/local_dom_window.cc b/third_party/blink/renderer/core/frame/local_dom_window.cc index f9b31ca0..b2ccfc6 100644 --- a/third_party/blink/renderer/core/frame/local_dom_window.cc +++ b/third_party/blink/renderer/core/frame/local_dom_window.cc
@@ -127,6 +127,7 @@ #include "third_party/blink/renderer/core/page/create_window.h" #include "third_party/blink/renderer/core/page/page.h" #include "third_party/blink/renderer/core/page/scrolling/scrolling_coordinator.h" +#include "third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h" #include "third_party/blink/renderer/core/paint/paint_layer_scrollable_area.h" #include "third_party/blink/renderer/core/probe/core_probes.h" #include "third_party/blink/renderer/core/script/modulator.h" @@ -186,6 +187,9 @@ int RequestAnimationFrame(Document* document, V8FrameRequestCallback* callback, bool legacy) { + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidRequestAnimationFrame(); SetCurrentTaskAsCallbackParent(callback); auto* frame_callback = MakeGarbageCollected<V8FrameCallback>(callback); frame_callback->SetUseLegacyTimeBase(legacy); @@ -1646,6 +1650,10 @@ if (!view) return 0; + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); + document()->UpdateStyleAndLayout(DocumentUpdateReason::kJavaScript); // TODO(bokan): This is wrong when the document.rootScroller is non-default. @@ -1663,6 +1671,10 @@ if (!view) return 0; + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic::DidAccessScrollOffset(); + document()->UpdateStyleAndLayout(DocumentUpdateReason::kJavaScript); // TODO(bokan): This is wrong when the document.rootScroller is non-default.
diff --git a/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.cc b/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.cc index c124404..a5dde98 100644 --- a/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.cc +++ b/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.cc
@@ -615,6 +615,7 @@ RECORD_METRIC(JavascriptDocumentUpdate); RECORD_METRIC(ParseStyleSheet); RECORD_METRIC(Accessibility); + RECORD_METRIC(PossibleSynchronizedScrollCount); builder.Record(recorder); #undef RECORD_METRIC @@ -672,6 +673,7 @@ RECORD_METRIC(JavascriptDocumentUpdate); RECORD_METRIC(ParseStyleSheet); RECORD_METRIC(Accessibility); + RECORD_METRIC(PossibleSynchronizedScrollCount); builder.Record(recorder); #undef RECORD_METRIC
diff --git a/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.h b/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.h index 75030b4..fb483c8 100644 --- a/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.h +++ b/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.h
@@ -150,8 +150,9 @@ kUserDrivenDocumentUpdate, kParseStyleSheet, kAccessibility, + kPossibleSynchronizedScrollCount, kCount, - kMainFrame + kMainFrame, }; // For metrics that require it, this converts the input value to use @@ -201,7 +202,8 @@ {"Blink.ServiceDocumentUpdate.UpdateTime", true}, {"Blink.UserDrivenDocumentUpdate.UpdateTime", true}, {"Blink.ParseStyleSheet.UpdateTime", true}, - {"Blink.Accessibility.UpdateTime", true}}; + {"Blink.Accessibility.UpdateTime", true}, + {"Blink.PossibleSynchronizedScrollCount.UpdateTime", true}}; static_assert(std::size(data) == kCount, "Metrics data mismatch"); return data; }
diff --git a/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator_test.cc b/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator_test.cc index 60c4326..c096fba 100644 --- a/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator_test.cc +++ b/third_party/blink/renderer/core/frame/local_frame_ukm_aggregator_test.cc
@@ -5,6 +5,7 @@ #include "third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.h" #include "base/metrics/statistics_recorder.h" +#include "base/strings/stringprintf.h" #include "base/test/metrics/histogram_tester.h" #include "base/test/test_mock_time_task_runner.h" #include "cc/metrics/begin_main_frame_metrics.h" @@ -18,6 +19,7 @@ #include "third_party/blink/renderer/core/testing/intersection_observer_test_helper.h" #include "third_party/blink/renderer/core/testing/sim/sim_request.h" #include "third_party/blink/renderer/core/testing/sim/sim_test.h" +#include "third_party/blink/renderer/platform/testing/testing_platform_support_with_mock_scheduler.h" namespace blink { @@ -1038,4 +1040,286 @@ histogram_tester.ExpectTotalCount("Blink.MainFrame.UpdateTime.PreFCP", 1); } +enum SyncScrollMutation { + kSyncScrollMutatesPosition, + kSyncScrollMutatesTransform, + kSyncScrollMutatesPositionBeforeAccess, + kSyncScrollMutatesNothing, +}; + +enum SyncScrollPositionAccess { + kSyncScrollAccessScrollOffset, + kSyncScrollDoesNotAccessScrollOffset, +}; + +enum SyncScrollHandlerStrategy { + kSyncScrollWithEventHandler, + kSyncScrollWithEventHandlerSchedulingRAF, + kSyncScrollNoEventHandlerWithRAF, + kSyncScrollNoEventHandler, +}; + +using SyncScrollHeuristicTestConfig = + ::testing::tuple<SyncScrollMutation, + SyncScrollPositionAccess, + SyncScrollHandlerStrategy>; + +class LocalFrameUkmAggregatorSyncScrollTest + : public LocalFrameUkmAggregatorSimTest, + public ::testing::WithParamInterface<SyncScrollHeuristicTestConfig> { + public: + static std::string PrintTestName( + const ::testing::TestParamInfo<SyncScrollHeuristicTestConfig>& info) { + std::stringstream ss; + switch (GetSyncScrollMutation(info.param)) { + case SyncScrollMutation::kSyncScrollMutatesPosition: + ss << "MutatesPosition"; + break; + case SyncScrollMutation::kSyncScrollMutatesPositionBeforeAccess: + ss << "MutatesPositionBeforeAccess"; + break; + case SyncScrollMutation::kSyncScrollMutatesTransform: + ss << "MutatesTransform"; + break; + case SyncScrollMutation::kSyncScrollMutatesNothing: + ss << "MutatesNothing"; + break; + } + ss << "_"; + switch (GetSyncScrollPositionAccess(info.param)) { + case SyncScrollPositionAccess::kSyncScrollAccessScrollOffset: + ss << "AccessScrollOffset"; + break; + case SyncScrollPositionAccess::kSyncScrollDoesNotAccessScrollOffset: + ss << "DoesNotAccessScrollOffset"; + break; + } + ss << "_"; + switch (GetSyncScrollHandlerStrategy(info.param)) { + case SyncScrollHandlerStrategy::kSyncScrollWithEventHandler: + ss << "WithEventHandler"; + break; + case SyncScrollHandlerStrategy::kSyncScrollWithEventHandlerSchedulingRAF: + ss << "WithEventHandlerSchedulingRAF"; + break; + case SyncScrollHandlerStrategy::kSyncScrollNoEventHandler: + ss << "NoEventHandler"; + break; + case SyncScrollHandlerStrategy::kSyncScrollNoEventHandlerWithRAF: + ss << "NoEventHandlerWithRAF"; + break; + } + return ss.str(); + } + + protected: + static SyncScrollMutation GetSyncScrollMutation( + const SyncScrollHeuristicTestConfig& config) { + return ::testing::get<0>(config); + } + + static SyncScrollPositionAccess GetSyncScrollPositionAccess( + const SyncScrollHeuristicTestConfig& config) { + return ::testing::get<1>(config); + } + + static SyncScrollHandlerStrategy GetSyncScrollHandlerStrategy( + const SyncScrollHeuristicTestConfig& config) { + return ::testing::get<2>(config); + } + + bool ShouldTriggerSyncScrollHeuristic() const { + // We would only attempt to synchronize scrolling if we had a scroll handler + // and, provided this is the case, we look for both mutating a property and + // accessing scroll offset. Note: it's also ok to mutate via rAF, provided + // that rAF was scheduled during the scroll handler. + return GetSyncScrollMutation(GetParam()) != + SyncScrollMutation::kSyncScrollMutatesNothing && + GetSyncScrollMutation(GetParam()) != + SyncScrollMutation::kSyncScrollMutatesPositionBeforeAccess && + GetSyncScrollPositionAccess(GetParam()) == + SyncScrollPositionAccess::kSyncScrollAccessScrollOffset && + (GetSyncScrollHandlerStrategy(GetParam()) == + SyncScrollHandlerStrategy::kSyncScrollWithEventHandler || + GetSyncScrollHandlerStrategy(GetParam()) == + SyncScrollHandlerStrategy:: + kSyncScrollWithEventHandlerSchedulingRAF); + } + + std::string GenerateNewScrollPosition() { + switch (GetSyncScrollPositionAccess(GetParam())) { + case SyncScrollPositionAccess::kSyncScrollAccessScrollOffset: + return "document.scrollingElement.scrollTop"; + case SyncScrollPositionAccess::kSyncScrollDoesNotAccessScrollOffset: + return "100"; + } + NOTREACHED(); + } + + std::string GenerateMutation() { + std::string pos = GenerateNewScrollPosition(); + switch (GetSyncScrollMutation(GetParam())) { + case SyncScrollMutation::kSyncScrollMutatesPosition: + return base::StringPrintf("card.style.top = %s + 'px'", pos.c_str()); + case SyncScrollMutation::kSyncScrollMutatesTransform: + return base::StringPrintf( + "card.style.transform = 'translateY(' + %s + 'px)'", pos.c_str()); + case SyncScrollMutation::kSyncScrollMutatesPositionBeforeAccess: + return base::StringPrintf( + "card.style.top = Math.floor(Math.random() * 100) + 'px'; var " + "unused = %s", + pos.c_str()); + case SyncScrollMutation::kSyncScrollMutatesNothing: + return ""; + } + NOTREACHED(); + } + + std::string GenerateScrollHandler() { + switch (GetSyncScrollHandlerStrategy(GetParam())) { + case SyncScrollHandlerStrategy::kSyncScrollWithEventHandler: + return base::StringPrintf(R"HTML( + document.addEventListener('scroll', (e) => { + %s; + }); + )HTML", + GenerateMutation().c_str()); + case SyncScrollHandlerStrategy::kSyncScrollWithEventHandlerSchedulingRAF: + return base::StringPrintf(R"HTML( + document.addEventListener('scroll', (e) => { + window.requestAnimationFrame((t) => { %s; }); + }); + )HTML", + GenerateMutation().c_str()); + case SyncScrollHandlerStrategy::kSyncScrollNoEventHandlerWithRAF: + return base::StringPrintf(R"HTML( + function doSyncEffect(t) { + %s; + window.requestAnimationFrame(doSyncEffect); + } + window.requestAnimationFrame(doSyncEffect); + )HTML", + GenerateMutation().c_str()); + case SyncScrollHandlerStrategy::kSyncScrollNoEventHandler: + return ""; + } + NOTREACHED(); + } + + ScopedTestingPlatformSupport<TestingPlatformSupportWithMockScheduler> + platform_; +}; + +TEST_P(LocalFrameUkmAggregatorSyncScrollTest, SyncScrollHeuristicRAFSetTop) { + base::HistogramTester histogram_tester; + const bool should_trigger = ShouldTriggerSyncScrollHeuristic(); + + WebView().MainFrameViewWidget()->Resize(gfx::Size(800, 600)); + SimRequest main_resource("https://example.com/", "text/html"); + LoadURL("https://example.com/"); + std::string html = base::StringPrintf(R"HTML( + <!DOCTYPE html> + <style> + #card { + background: green; + width: 100px; + height: 100px; + position: absolute; + } + </style> + <div id='card'></div> + <div style='background:orange;width:100px;height:10000px'></div> + <script> + %s + </script> + )HTML", + GenerateScrollHandler().c_str()); + main_resource.Complete(html.c_str()); + + // Wait until the script has had time to run. + platform_->RunForPeriodSeconds(5.); + base::RunLoop().RunUntilIdle(); + + // Do a pre-FCP frame. + Compositor().BeginFrame(); + + // We haven't scrolled at this point, so we should never have a count. + histogram_tester.ExpectTotalCount( + "Blink.PossibleSynchronizedScrollCount.UpdateTime.PreFCP", 0); + + // Cause a pre-FCP scroll. + auto* scrolling_element = + LocalFrameRoot().GetFrame()->GetDocument()->scrollingElement(); + scrolling_element->setScrollTop(100.0); + + // Do another pre-FCP frame. + Compositor().BeginFrame(); + + // Now that we'ev scrolled, we should have an update if triggering conditions + // are met. + histogram_tester.ExpectTotalCount( + "Blink.PossibleSynchronizedScrollCount.UpdateTime.PreFCP", + should_trigger ? 1 : 0); + + // Cause FCP on the next frame. + Element* target = GetDocument().getElementById(AtomicString("card")); + target->setInnerHTML("hello world"); + + Compositor().BeginFrame(); + + EXPECT_FALSE(IsBeforeFCPForTesting()); + + scrolling_element = + LocalFrameRoot().GetFrame()->GetDocument()->scrollingElement(); + scrolling_element->setScrollTop(200.0); + + // Do another post-FCP frame. + Compositor().BeginFrame(); + + if (should_trigger) { + // Should only have triggered for the one pre FCP scroll. + EXPECT_THAT( + histogram_tester.GetAllSamples("Blink.PossibleSynchronizedScrollCount." + "UpdateTime.AggregatedPreFCP"), + base::BucketsAre(base::Bucket(1, 1))); + // Should only have triggered for the one post FCP scroll. + histogram_tester.ExpectTotalCount( + "Blink.PossibleSynchronizedScrollCount.UpdateTime.PostFCP", 1); + // Should only trigger for the two scroll top adjustments. + EXPECT_THAT( + histogram_tester.GetAllSamples("Renderer.PossibleSynchronizedScroll"), + base::BucketsInclude(base::Bucket(0, 2), base::Bucket(1, 2))); + } else { + // Should never trigger. + EXPECT_THAT( + histogram_tester.GetAllSamples("Blink.PossibleSynchronizedScrollCount." + "UpdateTime.AggregatedPreFCP"), + base::BucketsAre(base::Bucket(0, 1))); + histogram_tester.ExpectTotalCount( + "Blink.PossibleSynchronizedScrollCount.UpdateTime.PostFCP", 0); + EXPECT_THAT( + histogram_tester.GetAllSamples("Renderer.PossibleSynchronizedScroll"), + base::BucketsInclude(base::Bucket(0, 4))); + } +} + +INSTANTIATE_TEST_SUITE_P( + P, + LocalFrameUkmAggregatorSyncScrollTest, + ::testing::Combine( + ::testing::Values( + SyncScrollMutation::kSyncScrollMutatesPosition, + SyncScrollMutation::kSyncScrollMutatesTransform, + SyncScrollMutation::kSyncScrollMutatesPositionBeforeAccess, + SyncScrollMutation::kSyncScrollMutatesNothing), + ::testing::Values( + SyncScrollPositionAccess::kSyncScrollAccessScrollOffset, + SyncScrollPositionAccess::kSyncScrollDoesNotAccessScrollOffset), + ::testing::Values( + SyncScrollHandlerStrategy::kSyncScrollWithEventHandler, + SyncScrollHandlerStrategy::kSyncScrollWithEventHandlerSchedulingRAF, + SyncScrollHandlerStrategy::kSyncScrollNoEventHandlerWithRAF, + SyncScrollHandlerStrategy::kSyncScrollNoEventHandler)), + LocalFrameUkmAggregatorSyncScrollTest::PrintTestName); + } // namespace blink
diff --git a/third_party/blink/renderer/core/layout/absolute_utils.cc b/third_party/blink/renderer/core/layout/absolute_utils.cc index ed7bffb..b460303 100644 --- a/third_party/blink/renderer/core/layout/absolute_utils.cc +++ b/third_party/blink/renderer/core/layout/absolute_utils.cc
@@ -22,6 +22,20 @@ using InsetBias = InsetModifiedContainingBlock::InsetBias; +StyleSelfAlignmentData AlignSelf(const ComputedStyle& style) { + return RuntimeEnabledFeatures::LayoutAlignForPositionedEnabled() + ? style.ResolvedAlignSelf(ItemPosition::kNormal) + : StyleSelfAlignmentData(ItemPosition::kNormal, + OverflowAlignment::kDefault); +} + +StyleSelfAlignmentData JustifySelf(const ComputedStyle& style) { + return RuntimeEnabledFeatures::LayoutAlignForPositionedEnabled() + ? style.ResolvedJustifySelf(ItemPosition::kNormal) + : StyleSelfAlignmentData(ItemPosition::kNormal, + OverflowAlignment::kDefault); +} + inline InsetBias GetStaticPositionInsetBias( LogicalStaticPosition::InlineEdge inline_edge) { switch (inline_edge) { @@ -46,6 +60,56 @@ } } +InsetBias GetAlignmentInsetBias( + const StyleSelfAlignmentData& alignment, + WritingDirectionMode container_writing_direction, + WritingDirectionMode self_writing_direction, + bool is_justify_axis, + absl::optional<InsetBias>* out_safe_inset_bias) { + // `alignment` is in the writing-direction of the containing-block, vs. the + // inset-bias which is relative to the writing-direction of the candidate. + const LogicalToLogical bias( + self_writing_direction, container_writing_direction, InsetBias::kStart, + InsetBias::kEnd, InsetBias::kStart, InsetBias::kEnd); + + if (alignment.Overflow() == OverflowAlignment::kSafe) { + *out_safe_inset_bias = + is_justify_axis ? bias.InlineStart() : bias.BlockStart(); + } + + switch (alignment.GetPosition()) { + case ItemPosition::kStart: + case ItemPosition::kFlexStart: + case ItemPosition::kBaseline: + case ItemPosition::kStretch: + case ItemPosition::kNormal: + case ItemPosition::kAnchorCenter: + return is_justify_axis ? bias.InlineStart() : bias.BlockStart(); + case ItemPosition::kCenter: + return InsetBias::kEqual; + case ItemPosition::kEnd: + case ItemPosition::kFlexEnd: + case ItemPosition::kLastBaseline: + return is_justify_axis ? bias.InlineEnd() : bias.BlockEnd(); + case ItemPosition::kSelfStart: + return InsetBias::kStart; + case ItemPosition::kSelfEnd: + return InsetBias::kEnd; + case ItemPosition::kLeft: + DCHECK(is_justify_axis); + return container_writing_direction.IsLtr() ? bias.InlineStart() + : bias.InlineEnd(); + case ItemPosition::kRight: + DCHECK(is_justify_axis); + return container_writing_direction.IsRtl() ? bias.InlineStart() + : bias.InlineEnd(); + case ItemPosition::kLegacy: + case ItemPosition::kAuto: + NOTREACHED(); + return InsetBias::kStart; + } +} + // Computes the inset modified containing block in one axis, accounting for // insets and the static-position. void ComputeUnclampedIMCBInOneAxis( @@ -54,10 +118,12 @@ const absl::optional<LayoutUnit>& inset_end, const LayoutUnit static_position_offset, InsetBias static_position_inset_bias, - bool start_side_matches_containing_block, + InsetBias alignment_inset_bias, + const absl::optional<InsetBias>& safe_alignment_inset_bias, LayoutUnit* imcb_start_out, LayoutUnit* imcb_end_out, - InsetBias* imcb_inset_bias_out) { + InsetBias* imcb_inset_bias_out, + absl::optional<InsetBias>* imcb_safe_inset_bias_out) { DCHECK_NE(available_size, kIndefiniteSize); if (!inset_start && !inset_end) { // If both our insets are auto, the available-space is defined by the @@ -100,11 +166,10 @@ *imcb_inset_bias_out = inset_start.has_value() ? InsetBias::kStart : InsetBias::kEnd; } else { - // Otherwise the weaker inset is the inset of the end edge (where end is - // interpreted relative to the writing mode of the containing block). - *imcb_inset_bias_out = start_side_matches_containing_block - ? InsetBias::kStart - : InsetBias::kEnd; + // Both insets were set - use the alignment bias (defaults to the "start" + // edge of the containing block if we have normal alignment). + *imcb_inset_bias_out = alignment_inset_bias; + *imcb_safe_inset_bias_out = safe_alignment_inset_bias; } } } @@ -113,29 +178,43 @@ const LogicalSize& available_size, const LogicalOofInsets& insets, const LogicalStaticPosition& static_position, + const ComputedStyle& style, WritingDirectionMode container_writing_direction, WritingDirectionMode self_writing_direction) { InsetModifiedContainingBlock imcb; imcb.available_size = available_size; - // Determines if the "start" sides of margins match. - const LogicalToLogical start_sides_match( - container_writing_direction, self_writing_direction, - /* inline_start */ true, /* inline_end */ false, - /* block_start */ true, /* block_end */ false); + const bool is_parallel = + IsParallelWritingMode(container_writing_direction.GetWritingMode(), + self_writing_direction.GetWritingMode()); + const auto inline_alignment = + is_parallel ? JustifySelf(style) : AlignSelf(style); + const auto block_alignment = + is_parallel ? AlignSelf(style) : JustifySelf(style); + + absl::optional<InsetBias> safe_inline_alignment_inset_bias; + const auto inline_alignment_inset_bias = GetAlignmentInsetBias( + inline_alignment, container_writing_direction, self_writing_direction, + /* is_justify_axis */ is_parallel, &safe_inline_alignment_inset_bias); + absl::optional<InsetBias> safe_block_alignment_inset_bias; + const auto block_alignment_inset_bias = GetAlignmentInsetBias( + block_alignment, container_writing_direction, self_writing_direction, + /* is_justify_axis */ !is_parallel, &safe_block_alignment_inset_bias); ComputeUnclampedIMCBInOneAxis( available_size.inline_size, insets.inline_start, insets.inline_end, static_position.offset.inline_offset, GetStaticPositionInsetBias(static_position.inline_edge), - start_sides_match.InlineStart(), &imcb.inline_start, &imcb.inline_end, - &imcb.inline_inset_bias); + inline_alignment_inset_bias, safe_inline_alignment_inset_bias, + &imcb.inline_start, &imcb.inline_end, &imcb.inline_inset_bias, + &imcb.safe_inline_inset_bias); ComputeUnclampedIMCBInOneAxis( available_size.block_size, insets.block_start, insets.block_end, static_position.offset.block_offset, GetStaticPositionInsetBias(static_position.block_edge), - start_sides_match.BlockStart(), &imcb.block_start, &imcb.block_end, - &imcb.block_inset_bias); + block_alignment_inset_bias, safe_block_alignment_inset_bias, + &imcb.block_start, &imcb.block_end, &imcb.block_inset_bias, + &imcb.safe_block_inset_bias); return imcb; } @@ -223,24 +302,67 @@ LayoutUnit imcb_start, LayoutUnit imcb_end, const InsetBias imcb_inset_bias, + const absl::optional<InsetBias>& imcb_safe_inset_bias, const LayoutUnit margin_start, const LayoutUnit margin_end, const LayoutUnit size, LayoutUnit* inset_start_out, LayoutUnit* inset_end_out) { DCHECK_NE(available_size, kIndefiniteSize); - const LayoutUnit free_space = + LayoutUnit free_space = available_size - imcb_start - imcb_end - margin_start - margin_end - size; + InsetBias bias = imcb_inset_bias; + if (imcb_safe_inset_bias && free_space < LayoutUnit()) { + free_space = LayoutUnit(); + bias = *imcb_safe_inset_bias; + } // Move the weaker inset edge to consume all the free space, so that: // `imcb_start` + `margin_start` + `size` + `margin_end` + `imcb_end` = // `available_size` - ResizeIMCBInOneAxis(imcb_inset_bias, free_space, &imcb_start, &imcb_end); + ResizeIMCBInOneAxis(bias, free_space, &imcb_start, &imcb_end); *inset_start_out = imcb_start + margin_start; *inset_end_out = imcb_end + margin_end; } +bool CanComputeBlockSizeWithoutLayout( + const BlockNode& node, + WritingDirectionMode container_writing_direction, + ItemPosition block_alignment_position, + bool has_auto_block_inset) { + // Tables (even with an explicit size) apply a min-content constraint. + if (node.IsTable()) { + return false; + } + // Replaced elements always have their size computed ahead of time. + if (node.IsReplaced()) { + return true; + } + const auto& style = node.Style(); + if (style.LogicalHeight().IsContentOrIntrinsic() || + style.LogicalMinHeight().IsContentOrIntrinsic() || + style.LogicalMaxHeight().IsContentOrIntrinsic()) { + return false; + } + if (style.LogicalHeight().IsAuto()) { + // Any 'auto' inset will trigger shink-to-fit sizing. + if (has_auto_block_inset) { + return false; + } + if (block_alignment_position == ItemPosition::kStretch) { + return true; + } + // Non-normal alignment will trigger shrink-to-fit sizing. + if (block_alignment_position != ItemPosition::kNormal) { + return false; + } + } + return true; +} + +} // namespace + bool IsInsetAutoForAxis(const Length& side1, const Length& side2, const ComputedStyle& style, @@ -264,36 +386,6 @@ .IsNone(); } -bool CanComputeBlockSizeWithoutLayout( - const BlockNode& node, - WritingDirectionMode container_writing_direction, - const AnchorEvaluatorImpl* anchor_evaluator) { - // Tables (even with an explicit size) apply a min-content constraint. - if (node.IsTable()) { - return false; - } - // Replaced elements always have their size computed ahead of time. - if (node.IsReplaced()) { - return true; - } - const auto& style = node.Style(); - if (style.LogicalHeight().IsContentOrIntrinsic() || - style.LogicalMinHeight().IsContentOrIntrinsic() || - style.LogicalMaxHeight().IsContentOrIntrinsic()) { - return false; - } - if (style.LogicalHeight().IsAuto()) { - // Any 'auto' inset will trigger shink-to-fit sizing. - if (IsInsetAutoForAxis(style.LogicalTop(), style.LogicalBottom(), style, - container_writing_direction, anchor_evaluator)) { - return false; - } - } - return true; -} - -} // namespace - LogicalOofInsets ComputeOutOfFlowInsets( const ComputedStyle& style, const LogicalSize& available_logical_size, @@ -366,9 +458,9 @@ const LogicalStaticPosition& static_position, WritingDirectionMode container_writing_direction, WritingDirectionMode self_writing_direction) { - InsetModifiedContainingBlock imcb = - ComputeUnclampedIMCB(available_size, insets, static_position, - container_writing_direction, self_writing_direction); + InsetModifiedContainingBlock imcb = ComputeUnclampedIMCB( + available_size, insets, static_position, node.Style(), + container_writing_direction, self_writing_direction); // Clamp any negative size to 0. if (imcb.InlineSize() < LayoutUnit()) { ResizeIMCBInOneAxis(imcb.inline_inset_bias, imcb.InlineSize(), @@ -398,9 +490,10 @@ const LogicalSize& available_size, const LogicalOofInsets& insets, const LogicalStaticPosition& static_position, + const ComputedStyle& style, WritingDirectionMode container_writing_direction, WritingDirectionMode self_writing_direction) { - return ComputeUnclampedIMCB(available_size, insets, static_position, + return ComputeUnclampedIMCB(available_size, insets, static_position, style, container_writing_direction, self_writing_direction); } @@ -418,10 +511,25 @@ DCHECK(dimensions); DCHECK_GE(imcb.InlineSize(), LayoutUnit()); + const bool is_justify_axis = IsParallelWritingMode( + container_writing_direction.GetWritingMode(), style.GetWritingMode()); + const auto alignment_position = + (is_justify_axis ? JustifySelf(style) : AlignSelf(style)).GetPosition(); + const auto block_alignment_position = + (is_justify_axis ? AlignSelf(style) : JustifySelf(style)).GetPosition(); + + const bool has_auto_inline_inset = + IsInsetAutoForAxis(style.LogicalInlineStart(), style.LogicalInlineEnd(), + style, container_writing_direction, anchor_evaluator); + const bool has_auto_block_inset = + IsInsetAutoForAxis(style.LogicalTop(), style.LogicalBottom(), style, + container_writing_direction, anchor_evaluator); + bool depends_on_min_max_sizes = false; const bool can_compute_block_size_without_layout = CanComputeBlockSizeWithoutLayout(node, container_writing_direction, - anchor_evaluator); + block_alignment_position, + has_auto_block_inset); auto MinMaxSizesFunc = [&](MinMaxSizesType type) -> MinMaxSizesResult { DCHECK(!node.IsReplaced()); @@ -454,10 +562,6 @@ builder.ToConstraintSpace()); }; - const bool has_auto_inline_inset = - IsInsetAutoForAxis(style.LogicalInlineStart(), style.LogicalInlineEnd(), - style, container_writing_direction, anchor_evaluator); - LayoutUnit inline_size; if (replaced_size) { DCHECK(node.IsReplaced()); @@ -466,22 +570,34 @@ Length main_inline_length = style.LogicalWidth(); Length min_inline_length = style.LogicalMinWidth(); - const bool stretch_inline_size = !has_auto_inline_inset; + const bool is_implicit_stretch = + !has_auto_inline_inset && alignment_position == ItemPosition::kNormal; + const bool is_explicit_stretch = + !has_auto_inline_inset && alignment_position == ItemPosition::kStretch; + const bool is_stretch = is_implicit_stretch || is_explicit_stretch; + + // If our block constraint is strong/explicit. + const bool is_block_explicit = + !style.LogicalHeight().IsAuto() || + (!has_auto_block_inset && + block_alignment_position == ItemPosition::kStretch); // Determine how "auto" should resolve. if (main_inline_length.IsAuto()) { if (node.IsTable()) { - // Tables always shrink-to-fit. - main_inline_length = Length::FitContent(); + // Tables always shrink-to-fit unless explicitly asked to stretch. + main_inline_length = is_explicit_stretch ? Length::FillAvailable() + : Length::FitContent(); } else if (!style.AspectRatio().IsAuto() && can_compute_block_size_without_layout && - (!stretch_inline_size || !style.LogicalHeight().IsAuto())) { + (!is_stretch || (is_implicit_stretch && is_block_explicit))) { // We'd like to apply the aspect-ratio. // The aspect-ratio applies from the block-axis if we can compute our // block-size without invoking layout, and either: // - We aren't stretching our auto inline-size. - // - We are stretching our auto inline-size, but the block-size isn't - // auto. + // - We are stretching our auto inline-size, but the block-size has a + // stronger (explicit) constraint, e.g: + // "height:10px" or "align-self:stretch". main_inline_length = Length::FitContent(); // Apply the automatic minimum size. @@ -489,8 +605,8 @@ min_inline_length.IsAuto()) min_inline_length = Length::MinIntrinsic(); } else { - main_inline_length = stretch_inline_size ? Length::FillAvailable() - : Length::FitContent(); + main_inline_length = + is_stretch ? Length::FillAvailable() : Length::FitContent(); } } @@ -526,7 +642,7 @@ ComputeInsets(space.AvailableSize().inline_size, imcb.inline_start, imcb.inline_end, imcb.inline_inset_bias, - dimensions->margins.inline_start, + imcb.safe_inline_inset_bias, dimensions->margins.inline_start, dimensions->margins.inline_end, inline_size, &dimensions->inset.inline_start, &dimensions->inset.inline_end); @@ -546,12 +662,19 @@ DCHECK(dimensions); DCHECK_GE(imcb.BlockSize(), LayoutUnit()); - const bool is_table = node.IsTable(); + const bool is_justify_axis = !IsParallelWritingMode( + container_writing_direction.GetWritingMode(), style.GetWritingMode()); + const auto alignment_position = + (is_justify_axis ? JustifySelf(style) : AlignSelf(style)).GetPosition(); + + const bool has_auto_block_inset = + IsInsetAutoForAxis(style.LogicalTop(), style.LogicalBottom(), style, + container_writing_direction, anchor_evaluator); const LayoutResult* result = nullptr; MinMaxSizes min_max_block_sizes = ComputeMinMaxBlockSizes( - space, style, border_padding, imcb.Size().block_size, anchor_evaluator); + space, style, border_padding, imcb.BlockSize(), anchor_evaluator); auto IntrinsicBlockSizeFunc = [&]() -> LayoutUnit { DCHECK(!node.IsReplaced()); @@ -563,13 +686,21 @@ style.GetWritingDirection(), /* is_new_fc */ true); builder.SetAvailableSize( - {dimensions->size.inline_size, space.AvailableSize().block_size}); + {dimensions->size.inline_size, imcb.BlockSize()}); builder.SetIsFixedInlineSize(true); builder.SetPercentageResolutionSize(space.PercentageResolutionSize()); + // Use the computed |MinMaxSizes| because |node.Layout()| can't resolve // the `anchor-size()` function. builder.SetOverrideMinMaxBlockSizes(min_max_block_sizes); + // Tables need to know about the explicit stretch constraint to produce + // the correct result. + if (!has_auto_block_inset && + alignment_position == ItemPosition::kStretch) { + builder.SetBlockAutoBehavior(AutoSizeBehavior::kStretchExplicit); + } + if (space.IsInitialColumnBalancingPass()) { // The |fragmentainer_offset_delta| will not make a difference in the // initial column balancing pass. @@ -586,10 +717,6 @@ .BlockSize(); }; - const bool has_auto_block_inset = - IsInsetAutoForAxis(style.LogicalTop(), style.LogicalBottom(), style, - container_writing_direction, anchor_evaluator); - LayoutUnit block_size; if (replaced_size) { DCHECK(node.IsReplaced()); @@ -597,19 +724,27 @@ } else { Length main_block_length = style.LogicalHeight(); - const bool stretch_block_size = !has_auto_block_inset; + const bool is_table = node.IsTable(); + + const bool is_implicit_stretch = + !has_auto_block_inset && alignment_position == ItemPosition::kNormal; + const bool is_explicit_stretch = + !has_auto_block_inset && alignment_position == ItemPosition::kStretch; + const bool is_stretch = is_implicit_stretch || is_explicit_stretch; // Determine how "auto" should resolve. if (main_block_length.IsAuto()) { if (is_table) { - // Tables always shrink-to-fit. - main_block_length = Length::FitContent(); + // Tables always shrink-to-fit unless explicitly asked to stretch. + main_block_length = is_explicit_stretch ? Length::FillAvailable() + : Length::FitContent(); } else if (!style.AspectRatio().IsAuto() && - dimensions->size.inline_size != kIndefiniteSize) { + dimensions->size.inline_size != kIndefiniteSize && + !is_explicit_stretch) { main_block_length = Length::FitContent(); } else { main_block_length = - stretch_block_size ? Length::FillAvailable() : Length::FitContent(); + is_stretch ? Length::FillAvailable() : Length::FitContent(); } } @@ -655,9 +790,9 @@ ComputeInsets(space.AvailableSize().block_size, imcb.block_start, imcb.block_end, imcb.block_inset_bias, - dimensions->margins.block_start, dimensions->margins.block_end, - block_size, &dimensions->inset.block_start, - &dimensions->inset.block_end); + imcb.safe_block_inset_bias, dimensions->margins.block_start, + dimensions->margins.block_end, block_size, + &dimensions->inset.block_start, &dimensions->inset.block_end); return result; }
diff --git a/third_party/blink/renderer/core/layout/absolute_utils.h b/third_party/blink/renderer/core/layout/absolute_utils.h index 781d124..845a4e9 100644 --- a/third_party/blink/renderer/core/layout/absolute_utils.h +++ b/third_party/blink/renderer/core/layout/absolute_utils.h
@@ -47,6 +47,12 @@ absl::optional<LayoutUnit> block_end; }; +bool IsInsetAutoForAxis(const Length& side1, + const Length& side2, + const ComputedStyle& style, + WritingDirectionMode container_writing_direction, + const AnchorEvaluatorImpl*); + CORE_EXPORT LogicalOofInsets ComputeOutOfFlowInsets(const ComputedStyle& style, const LogicalSize& available_size, @@ -72,6 +78,12 @@ InsetBias inline_inset_bias = InsetBias::kStart; InsetBias block_inset_bias = InsetBias::kStart; + // If safe alignment is specified (e.g. "align-self: safe end") and the + // object overflows its containing block it'll become start aligned instead. + // This field indicates the "start" edge of the containing block. + absl::optional<InsetBias> safe_inline_inset_bias; + absl::optional<InsetBias> safe_block_inset_bias; + LayoutUnit InlineEndOffset() const { return available_size.inline_size - inline_end; } @@ -106,6 +118,7 @@ ComputeIMCBForPositionFallback(const LogicalSize& available_size, const LogicalOofInsets&, const LogicalStaticPosition&, + const ComputedStyle&, WritingDirectionMode container_writing_direction, WritingDirectionMode self_writing_direction);
diff --git a/third_party/blink/renderer/core/layout/inline/inline_item.cc b/third_party/blink/renderer/core/layout/inline/inline_item.cc index 4a5b7bb..2fb92a1 100644 --- a/third_party/blink/renderer/core/layout/inline/inline_item.cc +++ b/third_party/blink/renderer/core/layout/inline/inline_item.cc
@@ -178,7 +178,7 @@ case kInitialLetterBox: return "InitialLetterBox"; case kListMarker: - return "ListMerker"; + return "ListMarker"; case kBidiControl: return "BidiControl"; }
diff --git a/third_party/blink/renderer/core/layout/length_utils.cc b/third_party/blink/renderer/core/layout/length_utils.cc index ecd5387..a7477516 100644 --- a/third_party/blink/renderer/core/layout/length_utils.cc +++ b/third_party/blink/renderer/core/layout/length_utils.cc
@@ -765,9 +765,6 @@ space.AvailableSize().block_size != kIndefiniteSize)) { Length block_length_to_resolve = block_length; if (block_length_to_resolve.IsAuto()) { - // TODO(dgrogan): This code block (and its corresponding inline version - // below) didn't make any tests pass when written so it may be - // unnecessary or untested. Check again when launching ReplacedNG. DCHECK(space.IsBlockAutoBehaviorStretch()); block_length_to_resolve = Length::FillAvailable(); }
diff --git a/third_party/blink/renderer/core/layout/out_of_flow_layout_part.cc b/third_party/blink/renderer/core/layout/out_of_flow_layout_part.cc index 5133f20..9d3ffff 100644 --- a/third_party/blink/renderer/core/layout/out_of_flow_layout_part.cc +++ b/third_party/blink/renderer/core/layout/out_of_flow_layout_part.cc
@@ -1970,7 +1970,7 @@ absl::optional<LogicalSize> replaced_size; if (node_info.node.IsReplaced()) { - // Create a new space with the IMCB size. + // Create a new space with the IMCB size, and stretch constraints. ConstraintSpaceBuilder builder(candidate_style.GetWritingMode(), candidate_style.GetWritingDirection(), /* is_new_fc */ true); @@ -1980,6 +1980,37 @@ builder.SetReplacedPercentageResolutionSize( node_info.constraint_space.PercentageResolutionSize()); + if (RuntimeEnabledFeatures::LayoutAlignForPositionedEnabled()) { + const bool is_parallel = + IsParallelWritingMode(container_writing_direction.GetWritingMode(), + candidate_writing_direction.GetWritingMode()); + const ItemPosition inline_position = + (is_parallel ? candidate_style.JustifySelf() + : candidate_style.AlignSelf()) + .GetPosition(); + const bool is_inline_stretch = + !IsInsetAutoForAxis(candidate_style.LogicalInlineStart(), + candidate_style.LogicalInlineEnd(), + candidate_style, container_writing_direction, + anchor_evaluator) && + inline_position == ItemPosition::kStretch; + if (is_inline_stretch) { + builder.SetInlineAutoBehavior(AutoSizeBehavior::kStretchExplicit); + } + const ItemPosition block_position = + (is_parallel ? candidate_style.AlignSelf() + : candidate_style.JustifySelf()) + .GetPosition(); + const bool is_block_stretch = + !IsInsetAutoForAxis(candidate_style.LogicalTop(), + candidate_style.LogicalBottom(), candidate_style, + container_writing_direction, anchor_evaluator) && + block_position == ItemPosition::kStretch; + if (is_block_stretch) { + builder.SetBlockAutoBehavior(AutoSizeBehavior::kStretchExplicit); + } + } + replaced_size = ComputeReplacedSize( node_info.node, builder.ToConstraintSpace(), border_padding, ReplacedSizeMode::kNormal, anchor_evaluator); @@ -2006,7 +2037,7 @@ if (try_fit_available_space) { imcb_for_position_fallback = ComputeIMCBForPositionFallback( node_info.constraint_space.AvailableSize(), insets, - node_info.static_position, container_writing_direction, + node_info.static_position, candidate_style, container_writing_direction, candidate_writing_direction); if (!CalculateNonOverflowingRangeInOneAxis( insets.inline_start, insets.inline_end,
diff --git a/third_party/blink/renderer/core/page/build.gni b/third_party/blink/renderer/core/page/build.gni index 4ff67a5..9521de6d 100644 --- a/third_party/blink/renderer/core/page/build.gni +++ b/third_party/blink/renderer/core/page/build.gni
@@ -74,6 +74,8 @@ "scrolling/root_scroller_controller.h", "scrolling/scrolling_coordinator.cc", "scrolling/scrolling_coordinator.h", + "scrolling/sync_scroll_attempt_heuristic.cc", + "scrolling/sync_scroll_attempt_heuristic.h", "scrolling/snap_coordinator.cc", "scrolling/snap_coordinator.h", "scrolling/sticky_position_scrolling_constraints.cc",
diff --git a/third_party/blink/renderer/core/page/chrome_client.h b/third_party/blink/renderer/core/page/chrome_client.h index b6ab6cb..cb3d2d6 100644 --- a/third_party/blink/renderer/core/page/chrome_client.h +++ b/third_party/blink/renderer/core/page/chrome_client.h
@@ -498,6 +498,7 @@ HTMLElement*, WebFormRelatedChangeType) {} virtual void DidChangeValueInTextField(HTMLFormControlElement&) {} + virtual void DidUserChangeContentEditableContent(Element&) {} virtual void DidEndEditingOnTextField(HTMLInputElement&) {} virtual void HandleKeyboardEventOnTextField(HTMLInputElement&, KeyboardEvent&) {}
diff --git a/third_party/blink/renderer/core/page/chrome_client_impl.cc b/third_party/blink/renderer/core/page/chrome_client_impl.cc index 4d1c8dc..7b362ff0 100644 --- a/third_party/blink/renderer/core/page/chrome_client_impl.cc +++ b/third_party/blink/renderer/core/page/chrome_client_impl.cc
@@ -49,6 +49,7 @@ #include "third_party/blink/public/web/blink.h" #include "third_party/blink/public/web/web_autofill_client.h" #include "third_party/blink/public/web/web_console_message.h" +#include "third_party/blink/public/web/web_form_element.h" #include "third_party/blink/public/web/web_input_element.h" #include "third_party/blink/public/web/web_local_frame_client.h" #include "third_party/blink/public/web/web_node.h" @@ -59,6 +60,7 @@ #include "third_party/blink/public/web/web_window_features.h" #include "third_party/blink/renderer/bindings/core/v8/script_controller.h" #include "third_party/blink/renderer/core/dom/document.h" +#include "third_party/blink/renderer/core/dom/element.h" #include "third_party/blink/renderer/core/dom/node.h" #include "third_party/blink/renderer/core/events/web_input_event_conversion.h" #include "third_party/blink/renderer/core/exported/web_dev_tools_agent_impl.h" @@ -1245,6 +1247,23 @@ } } +void ChromeClientImpl::DidUserChangeContentEditableContent(Element& element) { + Document& doc = element.GetDocument(); + // Selecting the focused element as we are only interested in changes made by + // the user. We assume the user must focus the field to type into it. + WebElement focused_element = doc.FocusedElement(); + // If element argument is not the focused element we can assume the user + // was not typing (this covers cases like element.innerText = 'foo'). + // Value changes caused by |document.execCommand| calls should not be + // interpreted as a user action. See https://crbug.com/764760. + if (!element.IsFocusedElementInDocument() || doc.IsRunningExecCommand()) { + return; + } + if (auto* fill_client = AutofillClientFromFrame(doc.GetFrame())) { + fill_client->ContentEditableDidChange(focused_element); + } +} + void ChromeClientImpl::DidEndEditingOnTextField( HTMLInputElement& input_element) { if (auto* fill_client =
diff --git a/third_party/blink/renderer/core/page/chrome_client_impl.h b/third_party/blink/renderer/core/page/chrome_client_impl.h index d0459b32..d86a685 100644 --- a/third_party/blink/renderer/core/page/chrome_client_impl.h +++ b/third_party/blink/renderer/core/page/chrome_client_impl.h
@@ -260,6 +260,7 @@ void HandleKeyboardEventOnTextField(HTMLInputElement&, KeyboardEvent&) override; void DidChangeValueInTextField(HTMLFormControlElement&) override; + void DidUserChangeContentEditableContent(Element&) override; void DidEndEditingOnTextField(HTMLInputElement&) override; void OpenTextDataListChooser(HTMLInputElement&) override; void TextFieldDataListChanged(HTMLInputElement&) override;
diff --git a/third_party/blink/renderer/core/page/page_animator.cc b/third_party/blink/renderer/core/page/page_animator.cc index 2219e73..e156b6633 100644 --- a/third_party/blink/renderer/core/page/page_animator.cc +++ b/third_party/blink/renderer/core/page/page_animator.cc
@@ -20,6 +20,7 @@ #include "third_party/blink/renderer/core/loader/document_loader.h" #include "third_party/blink/renderer/core/page/chrome_client.h" #include "third_party/blink/renderer/core/page/page.h" +#include "third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h" #include "third_party/blink/renderer/core/page/validation_message_client.h" #include "third_party/blink/renderer/core/paint/paint_layer_scrollable_area.h" #include "third_party/blink/renderer/core/svg/svg_document_extensions.h" @@ -103,6 +104,9 @@ controllers.emplace_back(document.first->GetScriptedAnimationController(), document.second); } + // TODO(crbug.com/1499981): This should be removed once synchronized scrolling + // impact is understood. + SyncScrollAttemptHeuristic heuristic(page_->MainFrame()); ServiceScriptedAnimations(monotonic_animation_start_time, controllers); page_->GetValidationMessageClient().LayoutOverlay(); } @@ -249,6 +253,7 @@ // 8. For each fully active Document in docs, run the scroll steps // for that Document, passing in now as the timestamp. run_for_all_active_controllers_with_timing([&](wtf_size_t i) { + auto scope = SyncScrollAttemptHeuristic::GetScrollHandlerScope(); active_controllers[i]->DispatchEvents(WTF::BindRepeating([](Event* event) { return event->type() == event_type_names::kScroll || event->type() == event_type_names::kSnapchanged || @@ -283,6 +288,7 @@ // 13. For each fully active Document in docs, run the animation // frame callbacks for that Document, passing in now as the timestamp. run_for_all_active_controllers_with_timing([&](wtf_size_t i) { + auto scope = SyncScrollAttemptHeuristic::GetRequestAnimationFrameScope(); active_controllers[i]->ExecuteFrameCallbacks(); if (!active_controllers[i]->GetExecutionContext()) { return;
diff --git a/third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.cc b/third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.cc new file mode 100644 index 0000000..2418588 --- /dev/null +++ b/third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.cc
@@ -0,0 +1,119 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h" + +#include "base/check_op.h" +#include "base/metrics/histogram_functions.h" +#include "third_party/blink/renderer/core/frame/local_frame.h" +#include "third_party/blink/renderer/core/frame/local_frame_ukm_aggregator.h" +#include "third_party/blink/renderer/core/frame/local_frame_view.h" + +namespace blink { + +namespace { + +SyncScrollAttemptHeuristic* g_sync_scroll_attempt_heuristic = nullptr; + +} // namespace + +SyncScrollAttemptHeuristic::SyncScrollAttemptHeuristic(Frame* frame) + : frame_(frame), last_instance_(g_sync_scroll_attempt_heuristic) { + if (frame_ && frame_->IsOutermostMainFrame()) { + g_sync_scroll_attempt_heuristic = this; + } else { + g_sync_scroll_attempt_heuristic = nullptr; + } +} + +SyncScrollAttemptHeuristic::~SyncScrollAttemptHeuristic() { + if (frame_ && frame_->IsOutermostMainFrame()) { + CHECK_EQ(g_sync_scroll_attempt_heuristic, this); + } + g_sync_scroll_attempt_heuristic = last_instance_; + const bool saw_possible_sync_scrolling_attempt = + did_access_scroll_offset_ && did_set_style_; + if (saw_possible_sync_scrolling_attempt && frame_ && + frame_->IsOutermostMainFrame() && !frame_->IsDetached()) { + // This will not cover cases where |frame_| is remote. + if (LocalFrame* local_frame = DynamicTo<LocalFrame>(frame_)) { + if (local_frame->View()) { + if (LocalFrameUkmAggregator* ukm_aggregator = + local_frame->View()->GetUkmAggregator()) { + ukm_aggregator->RecordCountSample( + LocalFrameUkmAggregator::kPossibleSynchronizedScrollCount, 1); + } + } + } + } + base::UmaHistogramBoolean("Renderer.PossibleSynchronizedScroll", + saw_possible_sync_scrolling_attempt); +} + +SyncScrollAttemptHeuristic::Scope::Scope(bool enable_observation) + : enable_observation_(enable_observation) { + if (enable_observation_) { + SyncScrollAttemptHeuristic::EnableObservation(); + } +} + +SyncScrollAttemptHeuristic::Scope::~Scope() { + if (enable_observation_) { + SyncScrollAttemptHeuristic::DisableObservation(); + } +} + +SyncScrollAttemptHeuristic::Scope +SyncScrollAttemptHeuristic::GetScrollHandlerScope() { + return Scope(g_sync_scroll_attempt_heuristic); +} + +SyncScrollAttemptHeuristic::Scope +SyncScrollAttemptHeuristic::GetRequestAnimationFrameScope() { + // We only want to observe rAF if one was requested during a scroll + // handler. If that's the case, |did_request_animation_frame_| should be + // true. + return Scope(g_sync_scroll_attempt_heuristic && + g_sync_scroll_attempt_heuristic->did_request_animation_frame_); +} + +void SyncScrollAttemptHeuristic::DidAccessScrollOffset() { + if (UNLIKELY(g_sync_scroll_attempt_heuristic && + g_sync_scroll_attempt_heuristic->is_observing_)) { + g_sync_scroll_attempt_heuristic->did_access_scroll_offset_ = true; + } +} + +void SyncScrollAttemptHeuristic::DidSetStyle() { + // We only want to record a mutation if we've already accessed the scroll + // offset. + if (UNLIKELY(g_sync_scroll_attempt_heuristic && + g_sync_scroll_attempt_heuristic->is_observing_ && + g_sync_scroll_attempt_heuristic->did_access_scroll_offset_)) { + g_sync_scroll_attempt_heuristic->did_set_style_ = true; + } +} + +void SyncScrollAttemptHeuristic::DidRequestAnimationFrame() { + if (UNLIKELY(g_sync_scroll_attempt_heuristic && + g_sync_scroll_attempt_heuristic->is_observing_)) { + g_sync_scroll_attempt_heuristic->did_request_animation_frame_ = true; + } +} + +void SyncScrollAttemptHeuristic::EnableObservation() { + if (UNLIKELY(g_sync_scroll_attempt_heuristic)) { + CHECK(!g_sync_scroll_attempt_heuristic->is_observing_); + g_sync_scroll_attempt_heuristic->is_observing_ = true; + } +} + +void SyncScrollAttemptHeuristic::DisableObservation() { + if (UNLIKELY(g_sync_scroll_attempt_heuristic)) { + CHECK(g_sync_scroll_attempt_heuristic->is_observing_); + g_sync_scroll_attempt_heuristic->is_observing_ = false; + } +} + +} // namespace blink
diff --git a/third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h b/third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h new file mode 100644 index 0000000..dce3c67 --- /dev/null +++ b/third_party/blink/renderer/core/page/scrolling/sync_scroll_attempt_heuristic.h
@@ -0,0 +1,67 @@ +// Copyright 2023 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef THIRD_PARTY_BLINK_RENDERER_CORE_PAGE_SCROLLING_SYNC_SCROLL_ATTEMPT_HEURISTIC_H_ +#define THIRD_PARTY_BLINK_RENDERER_CORE_PAGE_SCROLLING_SYNC_SCROLL_ATTEMPT_HEURISTIC_H_ + +#include "base/memory/stack_allocated.h" +#include "third_party/blink/renderer/core/core_export.h" + +namespace blink { + +class Frame; + +// SyncScrollAttemptHeuristic handles detecting cases where a page attempts to +// synchronize an effect with scrolling. While a vended Scope instance exists, +// the heuristic observes when script accesses scroll position and then also +// modifies inline style in order to estimate when script is attempting to +// synchronize content with scrolling. This is complicated somewhat by rAF. It +// can happen that a scroll handler will use rAF to realize the update. We only +// attempt to detect sync scroll attempts if the given frame is the outermost +// main frame and UKM is not recorded when the given frame is remote. +// +// TODO(crbug.com/1499981): This should be removed once synchronized scrolling +// impact is understood. +class CORE_EXPORT SyncScrollAttemptHeuristic final { + STACK_ALLOCATED(); + + public: + explicit SyncScrollAttemptHeuristic(Frame* frame); + SyncScrollAttemptHeuristic(const SyncScrollAttemptHeuristic&) = delete; + SyncScrollAttemptHeuristic& operator=(const SyncScrollAttemptHeuristic&) = + delete; + ~SyncScrollAttemptHeuristic(); + + class Scope { + STACK_ALLOCATED(); + + public: + explicit Scope(bool enable_observation); + ~Scope(); + + private: + bool enable_observation_ = false; + }; + + [[nodiscard]] static Scope GetScrollHandlerScope(); + [[nodiscard]] static Scope GetRequestAnimationFrameScope(); + static void DidAccessScrollOffset(); + static void DidSetStyle(); + static void DidRequestAnimationFrame(); + + private: + static void EnableObservation(); + static void DisableObservation(); + + Frame* frame_ = nullptr; + SyncScrollAttemptHeuristic* last_instance_ = nullptr; + bool did_access_scroll_offset_ = false; + bool did_set_style_ = false; + bool did_request_animation_frame_ = false; + bool is_observing_ = false; +}; + +} // namespace blink + +#endif // THIRD_PARTY_BLINK_RENDERER_CORE_PAGE_SCROLLING_SYNC_SCROLL_ATTEMPT_HEURISTIC_H_
diff --git a/third_party/blink/renderer/modules/accessibility/ax_object_cache_impl.cc b/third_party/blink/renderer/modules/accessibility/ax_object_cache_impl.cc index 6826317..303f06d 100644 --- a/third_party/blink/renderer/modules/accessibility/ax_object_cache_impl.cc +++ b/third_party/blink/renderer/modules/accessibility/ax_object_cache_impl.cc
@@ -3509,9 +3509,6 @@ case TreeUpdateReason::kMarkDirtyFromRemove: EnsureMarkDirtyWithCleanLayout(node); break; - case TreeUpdateReason::kNameAttributeChanged: - HandleNameAttributeChangedWithCleanLayout(node); - break; case TreeUpdateReason::kNodeGainedFocus: HandleNodeGainedFocusWithCleanLayout(node); break; @@ -3527,6 +3524,7 @@ RemoveValidationMessageObjectWithCleanLayout(node); break; case TreeUpdateReason::kRoleChangeFromAriaHasPopup: + case TreeUpdateReason::kRoleChangeFromImageMapName: case TreeUpdateReason::kRoleChangeFromRoleOrType: HandleRoleChangeWithCleanLayout(node); break; @@ -4059,7 +4057,7 @@ } else if (attr_name == html_names::kUsemapAttr) { DeferTreeUpdate(TreeUpdateReason::kUseMapAttributeChanged, element); } else if (attr_name == html_names::kNameAttr) { - DeferTreeUpdate(TreeUpdateReason::kNameAttributeChanged, element); + HandleNameAttributeChanged(element); } else if (attr_name == html_names::kControlsAttr) { ChildrenChanged(element); } else if (attr_name == html_names::kHrefAttr) { @@ -4086,16 +4084,26 @@ HandleRoleChangeWithCleanLayout(previous_map->ImageElement()); } -void AXObjectCacheImpl::HandleNameAttributeChangedWithCleanLayout(Node* node) { +void AXObjectCacheImpl::HandleNameAttributeChanged(Node* node) { + HTMLMapElement* map = DynamicTo<HTMLMapElement>(node); + if (!map) { + return; + } + // Changing a map name can alter an image's role and children. - // The name has already changed, so we can no longer find the primary image - // via the DOM. Use an area child's parent to find the old image. - // If the old image was treated as a map, and now isn't, it will take care - // of updating any other image that is newly associated with the map, - // via AXNodeObject::AddImageMapChildren(). - if (HTMLMapElement* map = DynamicTo<HTMLMapElement>(node)) { - if (AXObject* ax_previous_image = GetAXImageForMap(*map)) - HandleRoleChangeWithCleanLayout(ax_previous_image->GetNode()); + // First update any image that may have used the old map name. + if (AXObject* ax_previous_image = GetAXImageForMap(*map)) { + DeferTreeUpdate(TreeUpdateReason::kRoleChangeFromImageMapName, + ax_previous_image->GetElement()); + } + + // Then, update any image which may use the new map name. + HTMLImageElement* new_image = map->ImageElement(); + if (new_image) { + if (AXObject* obj = Get(new_image)) { + DeferTreeUpdate(TreeUpdateReason::kRoleChangeFromImageMapName, + obj->GetElement()); + } } }
diff --git a/third_party/blink/renderer/modules/accessibility/ax_object_cache_impl.h b/third_party/blink/renderer/modules/accessibility/ax_object_cache_impl.h index bee9e2b..7b42ad95 100644 --- a/third_party/blink/renderer/modules/accessibility/ax_object_cache_impl.h +++ b/third_party/blink/renderer/modules/accessibility/ax_object_cache_impl.h
@@ -774,15 +774,15 @@ kMarkDirtyFromHandleLayout = 11, kMarkDirtyFromHandleScroll = 12, kMarkDirtyFromRemove = 13, - kNameAttributeChanged = 14, - kNodeGainedFocus = 15, - kNodeLostFocus = 16, - kPostNotificationFromHandleLoadComplete = 17, - kPostNotificationFromHandleLoadStart = 18, - kPostNotificationFromHandleScrolledToAnchor = 19, - kRemoveValidationMessageObjectFromFocusedUIElement = 20, - kRemoveValidationMessageObjectFromValidationMessageObject = 21, - kRoleChangeFromAriaHasPopup = 22, + kNodeGainedFocus = 14, + kNodeLostFocus = 15, + kPostNotificationFromHandleLoadComplete = 16, + kPostNotificationFromHandleLoadStart = 17, + kPostNotificationFromHandleScrolledToAnchor = 18, + kRemoveValidationMessageObjectFromFocusedUIElement = 19, + kRemoveValidationMessageObjectFromValidationMessageObject = 20, + kRoleChangeFromAriaHasPopup = 21, + kRoleChangeFromImageMapName = 22, kRoleChangeFromRoleOrType = 23, kRoleMaybeChangedFromEventListener = 24, kRoleMaybeChangedFromHref = 25, @@ -989,7 +989,7 @@ // call children changed. void HandleTextMarkerDataAddedWithCleanLayout(Node*); void HandleUseMapAttributeChangedWithCleanLayout(Node*); - void HandleNameAttributeChangedWithCleanLayout(Node*); + void HandleNameAttributeChanged(Node*); bool DoesEventListenerImpactIgnoredState(const AtomicString& event_type, const Node& node) const;
diff --git a/third_party/blink/renderer/modules/indexeddb/BUILD.gn b/third_party/blink/renderer/modules/indexeddb/BUILD.gn index 8406d6a..9bd9485 100644 --- a/third_party/blink/renderer/modules/indexeddb/BUILD.gn +++ b/third_party/blink/renderer/modules/indexeddb/BUILD.gn
@@ -60,8 +60,6 @@ "inspector_indexed_db_agent.h", "web_idb_cursor.cc", "web_idb_cursor.h", - "web_idb_database.cc", - "web_idb_database.h", ] public_deps = [
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_cursor.cc b/third_party/blink/renderer/modules/indexeddb/idb_cursor.cc index 2bef174..e450fffc 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_cursor.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_cursor.cc
@@ -40,7 +40,6 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_database.h" #include "third_party/blink/renderer/modules/indexeddb/idb_object_store.h" #include "third_party/blink/renderer/modules/indexeddb/idb_transaction.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/platform/bindings/exception_state.h" #include "third_party/blink/renderer/platform/bindings/script_state.h" #include "third_party/blink/renderer/platform/bindings/v8_private_property.h" @@ -356,7 +355,7 @@ IDBDatabase::kIsKeyCursorErrorMessage); return nullptr; } - if (!transaction_->BackendDB()) { + if (!transaction_->db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -364,7 +363,7 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - transaction_->BackendDB()->Delete( + transaction_->db()->Delete( transaction_->Id(), EffectiveObjectStore()->Id(), IdbPrimaryKey(), WTF::BindOnce(&IDBRequest::OnDelete, WrapPersistent(request))); return request;
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_database.cc b/third_party/blink/renderer/modules/indexeddb/idb_database.cc index 02b22b7..03dc8c65 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_database.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_database.cc
@@ -47,12 +47,16 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_event_dispatcher.h" #include "third_party/blink/renderer/modules/indexeddb/idb_index.h" #include "third_party/blink/renderer/modules/indexeddb/idb_key_path.h" +#include "third_party/blink/renderer/modules/indexeddb/idb_key_range.h" #include "third_party/blink/renderer/modules/indexeddb/idb_version_change_event.h" +#include "third_party/blink/renderer/modules/indexeddb/indexed_db_blink_mojom_traits.h" +#include "third_party/blink/renderer/modules/indexeddb/indexed_db_dispatcher.h" #include "third_party/blink/renderer/platform/bindings/exception_code.h" #include "third_party/blink/renderer/platform/bindings/exception_state.h" #include "third_party/blink/renderer/platform/heap/garbage_collected.h" #include "third_party/blink/renderer/platform/instrumentation/tracing/trace_event.h" #include "third_party/blink/renderer/platform/wtf/assertions.h" +#include "third_party/blink/renderer/platform/wtf/functional.h" #include "third_party/blink/renderer/platform/wtf/std_lib_extras.h" namespace blink { @@ -94,20 +98,23 @@ IDBDatabase::IDBDatabase( ExecutionContext* context, - std::unique_ptr<WebIDBDatabase> backend, mojo::PendingAssociatedReceiver<mojom::blink::IDBDatabaseCallbacks> callbacks_receiver, - mojo::PendingRemote<mojom::blink::ObservedFeature> connection_lifetime) + mojo::PendingRemote<mojom::blink::ObservedFeature> connection_lifetime, + mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase> pending_database) : ActiveScriptWrappable<IDBDatabase>({}), ExecutionContextLifecycleObserver(context), - backend_(std::move(backend)), + database_remote_(context), connection_lifetime_(std::move(connection_lifetime)), callbacks_receiver_(this, context) { + database_remote_.Bind(std::move(pending_database), + context->GetTaskRunner(TaskType::kDatabaseAccess)); callbacks_receiver_.Bind(std::move(callbacks_receiver), context->GetTaskRunner(TaskType::kDatabaseAccess)); } void IDBDatabase::Trace(Visitor* visitor) const { + visitor->Trace(database_remote_); visitor->Trace(version_change_transaction_); visitor->Trace(transactions_); visitor->Trace(callbacks_receiver_); @@ -157,27 +164,30 @@ TransactionWillFinish(transaction); - if (close_pending_ && transactions_.empty()) + if (close_pending_ && transactions_.empty()) { CloseConnection(); + } } void IDBDatabase::ForcedClose() { - for (const auto& it : transactions_) + for (const auto& it : transactions_) { it.value->StartAborting(nullptr); + } this->close(); DispatchEvent(*Event::Create(event_type_names::kClose)); } void IDBDatabase::VersionChange(int64_t old_version, int64_t new_version) { TRACE_EVENT0("IndexedDB", "IDBDatabase::onVersionChange"); - if (!GetExecutionContext()) + if (!GetExecutionContext()) { return; + } if (close_pending_) { // If we're pending, that means there's a busy transaction. We won't // fire 'versionchange' but since we're not closing immediately the // back-end should still send out 'blocked'. - backend_->VersionChangeIgnored(); + VersionChangeIgnored(); return; } @@ -205,8 +215,9 @@ DOMStringList* IDBDatabase::objectStoreNames() const { auto* object_store_names = MakeGarbageCollected<DOMStringList>(); - for (const auto& it : metadata_.object_stores) + for (const auto& it : metadata_.object_stores) { object_store_names->Append(it.value->name); + } object_store_names->Sort(); return object_store_names; } @@ -255,7 +266,7 @@ return nullptr; } - if (!backend_) { + if (!database_remote_.is_bound()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -266,10 +277,9 @@ version_change_transaction_->CreateObjectStore(object_store_id, name, key_path, auto_increment); - scoped_refptr<IDBObjectStoreMetadata> store_metadata = - base::AdoptRef(new IDBObjectStoreMetadata( - name, object_store_id, key_path, auto_increment, - WebIDBDatabase::kMinimumIndexId)); + scoped_refptr<IDBObjectStoreMetadata> store_metadata = base::AdoptRef( + new IDBObjectStoreMetadata(name, object_store_id, key_path, + auto_increment, IDBDatabase::kMinimumIndexId)); auto* object_store = MakeGarbageCollected<IDBObjectStore>( store_metadata, version_change_transaction_.Get()); version_change_transaction_->ObjectStoreCreated(name, object_store); @@ -279,41 +289,6 @@ return object_store; } -void IDBDatabase::deleteObjectStore(const String& name, - ExceptionState& exception_state) { - TRACE_EVENT0("IndexedDB", "IDBDatabase::deleteObjectStore"); - if (!version_change_transaction_) { - exception_state.ThrowDOMException( - DOMExceptionCode::kInvalidStateError, - IDBDatabase::kNotVersionChangeTransactionErrorMessage); - return; - } - if (!version_change_transaction_->IsActive()) { - exception_state.ThrowDOMException( - DOMExceptionCode::kTransactionInactiveError, - version_change_transaction_->InactiveErrorMessage()); - return; - } - - int64_t object_store_id = FindObjectStoreId(name); - if (object_store_id == IDBObjectStoreMetadata::kInvalidId) { - exception_state.ThrowDOMException( - DOMExceptionCode::kNotFoundError, - "The specified object store was not found."); - return; - } - - if (!backend_) { - exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, - IDBDatabase::kDatabaseClosedErrorMessage); - return; - } - - version_change_transaction_->DeleteObjectStore(object_store_id); - version_change_transaction_->ObjectStoreDeleted(object_store_id, name); - metadata_.object_stores.erase(object_store_id); -} - IDBTransaction* IDBDatabase::transaction( ScriptState* script_state, const V8UnionStringOrStringSequence* store_names, @@ -329,8 +304,9 @@ scope.insert(store_names->GetAsString()); break; case V8UnionStringOrStringSequence::ContentType::kStringSequence: - for (const String& name : store_names->GetAsStringSequence()) + for (const String& name : store_names->GetAsStringSequence()) { scope.insert(name); + } break; } @@ -347,7 +323,7 @@ return nullptr; } - if (!backend_) { + if (!database_remote_.is_bound()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -396,36 +372,74 @@ mojo::PendingAssociatedReceiver<mojom::blink::IDBTransaction> receiver = transaction_remote.BindNewEndpointAndPassReceiver( execution_context->GetTaskRunner(TaskType::kDatabaseAccess)); - backend_->CreateTransaction(std::move(receiver), transaction_id, - object_store_ids, mode, durability); + CreateTransaction(std::move(receiver), transaction_id, object_store_ids, mode, + durability); return IDBTransaction::CreateNonVersionChange( script_state, std::move(transaction_remote), transaction_id, scope, mode, durability, this); } +void IDBDatabase::deleteObjectStore(const String& name, + ExceptionState& exception_state) { + TRACE_EVENT0("IndexedDB", "IDBDatabase::deleteObjectStore"); + if (!version_change_transaction_) { + exception_state.ThrowDOMException( + DOMExceptionCode::kInvalidStateError, + IDBDatabase::kNotVersionChangeTransactionErrorMessage); + return; + } + if (!version_change_transaction_->IsActive()) { + exception_state.ThrowDOMException( + DOMExceptionCode::kTransactionInactiveError, + version_change_transaction_->InactiveErrorMessage()); + return; + } + + int64_t object_store_id = FindObjectStoreId(name); + if (object_store_id == IDBObjectStoreMetadata::kInvalidId) { + exception_state.ThrowDOMException( + DOMExceptionCode::kNotFoundError, + "The specified object store was not found."); + return; + } + + if (!database_remote_.is_bound()) { + exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, + IDBDatabase::kDatabaseClosedErrorMessage); + return; + } + + version_change_transaction_->DeleteObjectStore(object_store_id); + version_change_transaction_->ObjectStoreDeleted(object_store_id, name); + metadata_.object_stores.erase(object_store_id); +} + void IDBDatabase::close() { TRACE_EVENT0("IndexedDB", "IDBDatabase::close"); - if (close_pending_) + if (close_pending_) { return; + } connection_lifetime_.reset(); close_pending_ = true; - if (transactions_.empty()) + if (transactions_.empty()) { CloseConnection(); + } } void IDBDatabase::CloseConnection() { DCHECK(close_pending_); DCHECK(transactions_.empty()); - if (backend_) { - backend_.reset(); + if (database_remote_.is_bound()) { + database_remote_.reset(); } - if (callbacks_receiver_.is_bound()) + if (callbacks_receiver_.is_bound()) { callbacks_receiver_.reset(); + } } DispatchEventResult IDBDatabase::DispatchEventInternal(Event& event) { @@ -434,19 +448,23 @@ event.SetTarget(this); // If this event originated from script, it should have no side effects. - if (!event.isTrusted()) + if (!event.isTrusted()) { return EventTarget::DispatchEventInternal(event); + } DCHECK(event.type() == event_type_names::kVersionchange || event.type() == event_type_names::kClose); - if (!GetExecutionContext()) + if (!GetExecutionContext()) { return DispatchEventResult::kCanceledBeforeDispatch; + } DispatchEventResult dispatch_result = EventTarget::DispatchEventInternal(event); + if (event.type() == event_type_names::kVersionchange && !close_pending_ && - backend_) - backend_->VersionChangeIgnored(); + database_remote_.is_bound()) { + VersionChangeIgnored(); + } return dispatch_result; } @@ -463,14 +481,14 @@ void IDBDatabase::RenameObjectStore(int64_t object_store_id, const String& new_name) { DCHECK(version_change_transaction_) - << "Object store renamed on database without a versionchange transaction"; + << "Object store renamed on database without a versionchange " + "transaction"; DCHECK(version_change_transaction_->IsActive()) << "Object store renamed when versionchange transaction is not active"; - DCHECK(backend_) << "Object store renamed after database connection closed"; DCHECK(metadata_.object_stores.Contains(object_store_id)); - backend_->RenameObjectStore(version_change_transaction_->Id(), - object_store_id, new_name); + RenameObjectStore(version_change_transaction_->Id(), object_store_id, + new_name); IDBObjectStoreMetadata* object_store_metadata = metadata_.object_stores.at(object_store_id); @@ -513,16 +531,15 @@ // Immediately close the connection to the back end. Don't attempt a // normal close() since that may wait on transactions which require a // round trip to the back-end to abort. - if (backend_) { - backend_.reset(); + if (database_remote_.is_bound()) { + database_remote_.reset(); } - connection_lifetime_.reset(); } void IDBDatabase::ContextEnteredBackForwardCache() { - if (backend_) { - backend_->DidBecomeInactive(); + if (database_remote_.is_bound()) { + DidBecomeInactive(); } } @@ -551,4 +568,159 @@ STATIC_ASSERT_ENUM(mojom::blink::IDBException::kTimeoutError, DOMExceptionCode::kTimeoutError); +void IDBDatabase::Get( + int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const IDBKeyRange* key_range, + bool key_only, + base::OnceCallback<void(mojom::blink::IDBDatabaseGetResultPtr)> + result_callback) { + IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); + + mojom::blink::IDBKeyRangePtr key_range_ptr = + mojom::blink::IDBKeyRange::From(key_range); + database_remote_->Get(transaction_id, object_store_id, index_id, + std::move(key_range_ptr), key_only, + std::move(result_callback)); +} + +void IDBDatabase::GetAll(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const IDBKeyRange* key_range, + int64_t max_count, + bool key_only, + IDBRequest* request) { + IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); + + mojom::blink::IDBKeyRangePtr key_range_ptr = + mojom::blink::IDBKeyRange::From(key_range); + database_remote_->GetAll( + transaction_id, object_store_id, index_id, std::move(key_range_ptr), + key_only, max_count, + WTF::BindOnce(&IDBRequest::OnGetAll, WrapWeakPersistent(request), + key_only)); +} + +void IDBDatabase::SetIndexKeys(int64_t transaction_id, + int64_t object_store_id, + std::unique_ptr<IDBKey> primary_key, + Vector<IDBIndexKeys> index_keys) { + database_remote_->SetIndexKeys(transaction_id, object_store_id, + std::move(primary_key), std::move(index_keys)); +} + +void IDBDatabase::SetIndexesReady(int64_t transaction_id, + int64_t object_store_id, + const Vector<int64_t>& index_ids) { + database_remote_->SetIndexesReady(transaction_id, object_store_id, + std::move(index_ids)); +} + +void IDBDatabase::OpenCursor(int64_t object_store_id, + int64_t index_id, + const IDBKeyRange* key_range, + mojom::blink::IDBCursorDirection direction, + bool key_only, + mojom::blink::IDBTaskType task_type, + IDBRequest* request) { + IndexedDBDispatcher::ResetCursorPrefetchCaches(request->transaction()->Id(), + nullptr); + + mojom::blink::IDBKeyRangePtr key_range_ptr = + mojom::blink::IDBKeyRange::From(key_range); + database_remote_->OpenCursor( + request->transaction()->Id(), object_store_id, index_id, + std::move(key_range_ptr), direction, key_only, task_type, + WTF::BindOnce(&IDBRequest::OnOpenCursor, WrapWeakPersistent(request))); +} + +void IDBDatabase::Count(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const IDBKeyRange* key_range, + mojom::blink::IDBDatabase::CountCallback callback) { + IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); + + database_remote_->Count(transaction_id, object_store_id, index_id, + mojom::blink::IDBKeyRange::From(key_range), + std::move(callback)); +} + +void IDBDatabase::Delete(int64_t transaction_id, + int64_t object_store_id, + const IDBKey* primary_key, + base::OnceCallback<void(bool)> success_callback) { + IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); + + mojom::blink::IDBKeyRangePtr key_range_ptr = + mojom::blink::IDBKeyRange::From(IDBKeyRange::Create(primary_key)); + database_remote_->DeleteRange(transaction_id, object_store_id, + std::move(key_range_ptr), + std::move(success_callback)); +} + +void IDBDatabase::DeleteRange(int64_t transaction_id, + int64_t object_store_id, + const IDBKeyRange* key_range, + base::OnceCallback<void(bool)> success_callback) { + IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); + + mojom::blink::IDBKeyRangePtr key_range_ptr = + mojom::blink::IDBKeyRange::From(key_range); + database_remote_->DeleteRange(transaction_id, object_store_id, + std::move(key_range_ptr), + std::move(success_callback)); +} + +void IDBDatabase::GetKeyGeneratorCurrentNumber( + int64_t transaction_id, + int64_t object_store_id, + mojom::blink::IDBDatabase::GetKeyGeneratorCurrentNumberCallback callback) { + database_remote_->GetKeyGeneratorCurrentNumber( + transaction_id, object_store_id, std::move(callback)); +} + +void IDBDatabase::Clear( + int64_t transaction_id, + int64_t object_store_id, + mojom::blink::IDBDatabase::ClearCallback success_callback) { + IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); + database_remote_->Clear(transaction_id, object_store_id, + std::move(success_callback)); +} + +void IDBDatabase::CreateIndex(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const String& name, + const IDBKeyPath& key_path, + bool unique, + bool multi_entry) { + database_remote_->CreateIndex(transaction_id, object_store_id, index_id, name, + key_path, unique, multi_entry); +} + +void IDBDatabase::DeleteIndex(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id) { + database_remote_->DeleteIndex(transaction_id, object_store_id, index_id); +} + +void IDBDatabase::RenameIndex(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const String& new_name) { + DCHECK(!new_name.IsNull()); + database_remote_->RenameIndex(transaction_id, object_store_id, index_id, + new_name); +} + +void IDBDatabase::Abort(int64_t transaction_id) { + if (database_remote_.is_bound()) { + database_remote_->Abort(transaction_id); + } +} + } // namespace blink
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_database.h b/third_party/blink/renderer/modules/indexeddb/idb_database.h index 5ae40a4d..852ea90 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_database.h +++ b/third_party/blink/renderer/modules/indexeddb/idb_database.h
@@ -42,7 +42,7 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_object_store.h" #include "third_party/blink/renderer/modules/indexeddb/idb_transaction.h" #include "third_party/blink/renderer/modules/indexeddb/indexed_db.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" +#include "third_party/blink/renderer/modules/indexeddb/web_idb_cursor.h" #include "third_party/blink/renderer/modules/modules_export.h" #include "third_party/blink/renderer/platform/heap/collection_support/heap_hash_map.h" #include "third_party/blink/renderer/platform/heap/garbage_collected.h" @@ -66,10 +66,11 @@ public: IDBDatabase( ExecutionContext*, - std::unique_ptr<WebIDBDatabase>, mojo::PendingAssociatedReceiver<mojom::blink::IDBDatabaseCallbacks> callbacks_receiver, - mojo::PendingRemote<mojom::blink::ObservedFeature> connection_lifetime); + mojo::PendingRemote<mojom::blink::ObservedFeature> connection_lifetime, + mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase> + pending_database); void Trace(Visitor*) const override; @@ -145,9 +146,6 @@ void RevertObjectStoreMetadata( scoped_refptr<IDBObjectStoreMetadata> old_metadata); - // Will return nullptr if this database is stopped. - WebIDBDatabase* Backend() const { return backend_.get(); } - static int64_t NextTransactionId(); static const char kIndexDeletedErrorMessage[]; @@ -168,6 +166,90 @@ static const char kTransactionReadOnlyErrorMessage[]; static const char kDatabaseClosedErrorMessage[]; + static const int64_t kMinimumIndexId = 30; + + void RenameObjectStore(int64_t transaction_id, + int64_t object_store_id, + const String& new_name) { + database_remote_->RenameObjectStore(transaction_id, object_store_id, + new_name); + } + void CreateTransaction(mojo::PendingAssociatedReceiver< + mojom::blink::IDBTransaction> transaction_receiver, + int64_t transaction_id, + const Vector<int64_t>& object_store_ids, + mojom::blink::IDBTransactionMode mode, + mojom::blink::IDBTransactionDurability durability) { + database_remote_->CreateTransaction(std::move(transaction_receiver), + transaction_id, object_store_ids, mode, + durability); + } + void VersionChangeIgnored() { database_remote_->VersionChangeIgnored(); } + void Get( + int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const IDBKeyRange*, + bool key_only, + base::OnceCallback<void(mojom::blink::IDBDatabaseGetResultPtr)> result); + void GetAll(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const IDBKeyRange*, + int64_t max_count, + bool key_only, + IDBRequest*); + void SetIndexKeys(int64_t transaction_id, + int64_t object_store_id, + std::unique_ptr<IDBKey> primary_key, + Vector<IDBIndexKeys>); + void SetIndexesReady(int64_t transaction_id, + int64_t object_store_id, + const Vector<int64_t>& index_ids); + void OpenCursor(int64_t object_store_id, + int64_t index_id, + const IDBKeyRange*, + mojom::blink::IDBCursorDirection direction, + bool key_only, + mojom::blink::IDBTaskType, + IDBRequest*); + void Count(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const IDBKeyRange*, + mojom::blink::IDBDatabase::CountCallback callback); + void Delete(int64_t transaction_id, + int64_t object_store_id, + const IDBKey* primary_key, + mojom::blink::IDBDatabase::DeleteRangeCallback callback); + void DeleteRange(int64_t transaction_id, + int64_t object_store_id, + const IDBKeyRange*, + mojom::blink::IDBDatabase::DeleteRangeCallback callback); + void GetKeyGeneratorCurrentNumber( + int64_t transaction_id, + int64_t object_store_id, + mojom::blink::IDBDatabase::GetKeyGeneratorCurrentNumberCallback callback); + void Clear(int64_t transaction_id, + int64_t object_store_id, + mojom::blink::IDBDatabase::ClearCallback callback); + void CreateIndex(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const String& name, + const IDBKeyPath&, + bool unique, + bool multi_entry); + void DeleteIndex(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id); + void RenameIndex(int64_t transaction_id, + int64_t object_store_id, + int64_t index_id, + const String& new_name); + void Abort(int64_t transaction_id); + void DidBecomeInactive() { database_remote_->DidBecomeInactive(); } + protected: // EventTarget DispatchEventResult DispatchEventInternal(Event&) override; @@ -180,7 +262,7 @@ void CloseConnection(); IDBDatabaseMetadata metadata_; - std::unique_ptr<WebIDBDatabase> backend_; + HeapMojoAssociatedRemote<mojom::blink::IDBDatabase> database_remote_; Member<IDBTransaction> version_change_transaction_; HeapHashMap<int64_t, Member<IDBTransaction>> transactions_; // No interface here, so no need to bind it. This is only for
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_factory_client.cc b/third_party/blink/renderer/modules/indexeddb/idb_factory_client.cc index 9df68e9..7576a81 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_factory_client.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_factory_client.cc
@@ -40,7 +40,6 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_open_db_request.h" #include "third_party/blink/renderer/modules/indexeddb/idb_value.h" #include "third_party/blink/renderer/modules/indexeddb/web_idb_cursor.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/platform/heap/garbage_collected.h" #include "third_party/blink/renderer/platform/wtf/shared_buffer.h" #include "third_party/blink/renderer/platform/wtf/std_lib_extras.h" @@ -96,20 +95,18 @@ void IDBFactoryClient::OpenSuccess( mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase> pending_database, const IDBDatabaseMetadata& metadata) { - std::unique_ptr<WebIDBDatabase> db; - if (pending_database.is_valid()) { - db = std::make_unique<WebIDBDatabase>(std::move(pending_database), - task_runner_); + if (!request_) { + return; } - if (request_) { + #if DCHECK_IS_ON() DCHECK(!request_->TransactionHasQueuedResults()); #endif // DCHECK_IS_ON() IDBOpenDBRequest* request = request_.Get(); Detach(); - request->OnOpenDBSuccess(std::move(db), IDBDatabaseMetadata(metadata)); + request->OnOpenDBSuccess(std::move(pending_database), task_runner_, + IDBDatabaseMetadata(metadata)); // `this` may be deleted because event dispatch can run a nested loop. - } } void IDBFactoryClient::DeleteSuccess(int64_t old_version) { @@ -144,23 +141,20 @@ mojom::blink::IDBDataLoss data_loss, const String& data_loss_message, const IDBDatabaseMetadata& metadata) { - std::unique_ptr<WebIDBDatabase> db; - if (pending_database.is_valid()) { - db = std::make_unique<WebIDBDatabase>(std::move(pending_database), - task_runner_); + if (!request_) { + return; } - if (request_) { + #if DCHECK_IS_ON() DCHECK(!request_->TransactionHasQueuedResults()); #endif // DCHECK_IS_ON() - request_->OnUpgradeNeeded(old_version, std::move(db), - IDBDatabaseMetadata(metadata), data_loss, - data_loss_message); + request_->OnUpgradeNeeded(old_version, std::move(pending_database), + task_runner_, IDBDatabaseMetadata(metadata), + data_loss, data_loss_message); // `this` may be deleted because event dispatch can run a nested loop. // Not resetting |request_|. In this instance we will have to forward at // least one other call in the set UpgradeNeeded() / OpenSuccess() / // Error(). - } } } // namespace blink
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_index.cc b/third_party/blink/renderer/modules/indexeddb/idb_index.cc index 9d601ea..1b5e2f1 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_index.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_index.cc
@@ -92,7 +92,7 @@ IDBDatabase::kIndexNameTakenErrorMessage); return; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return; @@ -139,7 +139,7 @@ if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -155,8 +155,8 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); request->SetCursorDetails(indexed_db::kCursorKeyAndValue, direction); - BackendDB()->OpenCursor(object_store_->Id(), Id(), key_range, direction, - false, mojom::IDBTaskType::Normal, request); + db()->OpenCursor(object_store_->Id(), Id(), key_range, direction, false, + mojom::IDBTaskType::Normal, request); return request; } @@ -183,7 +183,7 @@ if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -191,9 +191,8 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->Count( - transaction_->Id(), object_store_->Id(), Id(), key_range, - WTF::BindOnce(&IDBRequest::OnCount, WrapWeakPersistent(request))); + db()->Count(transaction_->Id(), object_store_->Id(), Id(), key_range, + WTF::BindOnce(&IDBRequest::OnCount, WrapWeakPersistent(request))); return request; } @@ -222,7 +221,7 @@ ExecutionContext::From(script_state), range, exception_state); if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -231,8 +230,8 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); request->SetCursorDetails(indexed_db::kCursorKeyOnly, direction); - BackendDB()->OpenCursor(object_store_->Id(), Id(), key_range, direction, true, - mojom::IDBTaskType::Normal, request); + db()->OpenCursor(object_store_->Id(), Id(), key_range, direction, true, + mojom::IDBTaskType::Normal, request); return request; } @@ -320,16 +319,15 @@ IDBDatabase::kNoKeyOrKeyRangeErrorMessage); return nullptr; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; } IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->Get(transaction_->Id(), object_store_->Id(), Id(), key_range, - key_only, - WTF::BindOnce(&IDBRequest::OnGet, WrapPersistent(request))); + db()->Get(transaction_->Id(), object_store_->Id(), Id(), key_range, key_only, + WTF::BindOnce(&IDBRequest::OnGet, WrapPersistent(request))); return request; } @@ -358,7 +356,7 @@ ExecutionContext::From(script_state), range, exception_state); if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -366,13 +364,13 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->GetAll(transaction_->Id(), object_store_->Id(), Id(), key_range, - max_count, key_only, request); + db()->GetAll(transaction_->Id(), object_store_->Id(), Id(), key_range, + max_count, key_only, request); return request; } -WebIDBDatabase* IDBIndex::BackendDB() const { - return transaction_->BackendDB(); +IDBDatabase* IDBIndex::db() const { + return transaction_->db(); } } // namespace blink
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_index.h b/third_party/blink/renderer/modules/indexeddb/idb_index.h index 2b30a54..a3d56f9 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_index.h +++ b/third_party/blink/renderer/modules/indexeddb/idb_index.h
@@ -33,7 +33,6 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_metadata.h" #include "third_party/blink/renderer/modules/indexeddb/idb_request.h" #include "third_party/blink/renderer/modules/indexeddb/web_idb_cursor.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/platform/bindings/script_wrappable.h" #include "third_party/blink/renderer/platform/wtf/forward.h" #include "third_party/blink/renderer/platform/wtf/text/wtf_string.h" @@ -120,7 +119,7 @@ mojom::IDBCursorDirection, IDBRequest::AsyncTraceState = IDBRequest::AsyncTraceState()); - WebIDBDatabase* BackendDB() const; + IDBDatabase* db() const; private: const IDBIndexMetadata& Metadata() const { return *metadata_; }
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_object_store.cc b/third_party/blink/renderer/modules/indexeddb/idb_object_store.cc index a4a6df0..0b7a56c7 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_object_store.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_object_store.cc
@@ -51,7 +51,6 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_key_path.h" #include "third_party/blink/renderer/modules/indexeddb/idb_value_wrapping.h" #include "third_party/blink/renderer/modules/indexeddb/indexed_db_blink_mojom_traits.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/platform/bindings/exception_state.h" #include "third_party/blink/renderer/platform/bindings/script_state.h" #include "third_party/blink/renderer/platform/instrumentation/tracing/trace_event.h" @@ -104,7 +103,7 @@ IDBDatabase::kObjectStoreNameTakenErrorMessage); return; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return; @@ -156,7 +155,7 @@ IDBDatabase::kNoKeyOrKeyRangeErrorMessage); return nullptr; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -164,10 +163,9 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->Get( - transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, key_range, - /*key_only=*/false, - WTF::BindOnce(&IDBRequest::OnGet, WrapWeakPersistent(request))); + db()->Get(transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, key_range, + /*key_only=*/false, + WTF::BindOnce(&IDBRequest::OnGet, WrapWeakPersistent(request))); return request; } @@ -200,7 +198,7 @@ IDBDatabase::kNoKeyOrKeyRangeErrorMessage); return nullptr; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -208,9 +206,9 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->Get(transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, - key_range, /*key_only=*/true, - WTF::BindOnce(&IDBRequest::OnGet, WrapPersistent(request))); + db()->Get(transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, key_range, + /*key_only=*/true, + WTF::BindOnce(&IDBRequest::OnGet, WrapPersistent(request))); return request; } @@ -248,7 +246,7 @@ ExecutionContext::From(script_state), key_range, exception_state); if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -256,8 +254,8 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->GetAll(transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, - range, max_count, false, request); + db()->GetAll(transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, range, + max_count, false, request); return request; } @@ -295,7 +293,7 @@ ExecutionContext::From(script_state), key_range, exception_state); if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -303,8 +301,8 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->GetAll(transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, - range, max_count, true, request); + db()->GetAll(transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, range, + max_count, true, request); return request; } @@ -567,7 +565,7 @@ return nullptr; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -643,7 +641,7 @@ IDBDatabase::kNoKeyOrKeyRangeErrorMessage); return nullptr; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -658,7 +656,7 @@ IDBRequest::AsyncTraceState metrics) { IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->DeleteRange( + db()->DeleteRange( transaction_->Id(), Id(), key_range, WTF::BindOnce(&IDBRequest::OnDelete, WrapPersistent(request))); return request; @@ -670,7 +668,7 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->GetKeyGeneratorCurrentNumber( + db()->GetKeyGeneratorCurrentNumber( transaction_->Id(), Id(), WTF::BindOnce(&IDBRequest::OnGotKeyGeneratorCurrentNumber, WrapWeakPersistent(request))); @@ -700,7 +698,7 @@ IDBDatabase::kTransactionReadOnlyErrorMessage); return nullptr; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -708,9 +706,8 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->Clear( - transaction_->Id(), Id(), - WTF::BindOnce(&IDBRequest::OnClear, WrapPersistent(request))); + db()->Clear(transaction_->Id(), Id(), + WTF::BindOnce(&IDBRequest::OnClear, WrapPersistent(request))); return request; } @@ -759,8 +756,9 @@ EventTarget* target = event->target(); IDBRequest* request = static_cast<IDBRequest*>(target); - if (!database_->Backend()) // If database is stopped? + if (!database_) { // If database is stopped? return; + } ScriptState::Scope scope(script_state_); @@ -784,16 +782,15 @@ ObjectStoreMetadata(), IndexMetadata(), value)}); - database_->Backend()->SetIndexKeys(transaction_id_, object_store_id_, - IDBKey::Clone(primary_key), - std::move(index_keys)); + database_->SetIndexKeys(transaction_id_, object_store_id_, + IDBKey::Clone(primary_key), + std::move(index_keys)); } else { // Now that we are done indexing, tell the backend to go // back to processing tasks of type NormalTask. Vector<int64_t> index_ids; index_ids.push_back(IndexMetadata().id); - database_->Backend()->SetIndexesReady(transaction_id_, object_store_id_, - index_ids); + database_->SetIndexesReady(transaction_id_, object_store_id_, index_ids); database_.Clear(); } } @@ -852,7 +849,7 @@ "The keyPath argument was an array and the multiEntry option is true."); return nullptr; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -860,8 +857,8 @@ int64_t index_id = metadata_->max_index_id + 1; DCHECK_NE(index_id, IDBIndexMetadata::kInvalidId); - BackendDB()->CreateIndex(transaction_->Id(), Id(), index_id, name, key_path, - options->unique(), options->multiEntry()); + db()->CreateIndex(transaction_->Id(), Id(), index_id, name, key_path, + options->unique(), options->multiEntry()); ++metadata_->max_index_id; @@ -957,13 +954,13 @@ IDBDatabase::kNoSuchIndexErrorMessage); return; } - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return; } - BackendDB()->DeleteIndex(transaction_->Id(), Id(), index_id); + db()->DeleteIndex(transaction_->Id(), Id(), index_id); metadata_->indexes.erase(index_id); IDBIndexMap::iterator it = index_map_.find(name); @@ -1002,7 +999,7 @@ if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -1021,8 +1018,8 @@ script_state, this, transaction_.Get(), std::move(metrics)); request->SetCursorDetails(indexed_db::kCursorKeyAndValue, direction); - BackendDB()->OpenCursor(Id(), IDBIndexMetadata::kInvalidId, range, direction, - false, task_type, request); + db()->OpenCursor(Id(), IDBIndexMetadata::kInvalidId, range, direction, false, + task_type, request); return request; } @@ -1054,7 +1051,7 @@ if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -1064,8 +1061,8 @@ script_state, this, transaction_.Get(), std::move(metrics)); request->SetCursorDetails(indexed_db::kCursorKeyOnly, direction); - BackendDB()->OpenCursor(Id(), IDBIndexMetadata::kInvalidId, key_range, - direction, true, mojom::IDBTaskType::Normal, request); + db()->OpenCursor(Id(), IDBIndexMetadata::kInvalidId, key_range, direction, + true, mojom::IDBTaskType::Normal, request); return request; } @@ -1094,7 +1091,7 @@ if (exception_state.HadException()) return nullptr; - if (!BackendDB()) { + if (!db()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, IDBDatabase::kDatabaseClosedErrorMessage); return nullptr; @@ -1102,9 +1099,8 @@ IDBRequest* request = IDBRequest::Create( script_state, this, transaction_.Get(), std::move(metrics)); - BackendDB()->Count( - transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, key_range, - WTF::BindOnce(&IDBRequest::OnCount, WrapWeakPersistent(request))); + db()->Count(transaction_->Id(), Id(), IDBIndexMetadata::kInvalidId, key_range, + WTF::BindOnce(&IDBRequest::OnCount, WrapWeakPersistent(request))); return request; } @@ -1186,7 +1182,7 @@ DCHECK(transaction_->IsVersionChange()); DCHECK(transaction_->IsActive()); - BackendDB()->RenameIndex(transaction_->Id(), Id(), index_id, new_name); + db()->RenameIndex(transaction_->Id(), Id(), index_id, new_name); auto metadata_iterator = metadata_->indexes.find(index_id); DCHECK_NE(metadata_iterator, metadata_->indexes.end()) << "Invalid index_id"; @@ -1210,8 +1206,8 @@ return IDBIndexMetadata::kInvalidId; } -WebIDBDatabase* IDBObjectStore::BackendDB() const { - return transaction_->BackendDB(); +IDBDatabase* IDBObjectStore::db() const { + return transaction_->db(); } } // namespace blink
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_object_store.h b/third_party/blink/renderer/modules/indexeddb/idb_object_store.h index d37fa20..f159205 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_object_store.h +++ b/third_party/blink/renderer/modules/indexeddb/idb_object_store.h
@@ -38,7 +38,6 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_request.h" #include "third_party/blink/renderer/modules/indexeddb/idb_transaction.h" #include "third_party/blink/renderer/modules/indexeddb/web_idb_cursor.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/platform/bindings/script_wrappable.h" #include "third_party/blink/renderer/platform/heap/collection_support/heap_hash_map.h" #include "third_party/blink/renderer/platform/wtf/text/wtf_string.h" @@ -191,7 +190,7 @@ } void RenameIndex(int64_t index_id, const String& new_name); - WebIDBDatabase* BackendDB() const; + IDBDatabase* db() const; private: using IDBIndexMap = HeapHashMap<String, Member<IDBIndex>>;
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_open_db_request.cc b/third_party/blink/renderer/modules/indexeddb/idb_open_db_request.cc index 6da5506..ab00408 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_open_db_request.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_open_db_request.cc
@@ -106,11 +106,13 @@ event_type_names::kBlocked, old_version, new_version_nullable)); } -void IDBOpenDBRequest::OnUpgradeNeeded(int64_t old_version, - std::unique_ptr<WebIDBDatabase> backend, - const IDBDatabaseMetadata& metadata, - mojom::blink::IDBDataLoss data_loss, - String data_loss_message) { +void IDBOpenDBRequest::OnUpgradeNeeded( + int64_t old_version, + mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase> pending_database, + scoped_refptr<base::SingleThreadTaskRunner> task_runner, + const IDBDatabaseMetadata& metadata, + mojom::blink::IDBDataLoss data_loss, + String data_loss_message) { TRACE_EVENT0("IndexedDB", "IDBOpenDBRequest::onUpgradeNeeded()"); probe::AsyncTask async_task(GetExecutionContext(), async_task_context(), "upgradeNeeded"); @@ -122,8 +124,8 @@ DCHECK(callbacks_receiver_); auto* idb_database = MakeGarbageCollected<IDBDatabase>( - GetExecutionContext(), std::move(backend), std::move(callbacks_receiver_), - std::move(connection_lifetime_)); + GetExecutionContext(), std::move(callbacks_receiver_), + std::move(connection_lifetime_), std::move(pending_database)); idb_database->SetMetadata(metadata); if (old_version == IDBDatabaseMetadata::kNoVersion) { @@ -146,8 +148,10 @@ data_loss_message)); } -void IDBOpenDBRequest::OnOpenDBSuccess(std::unique_ptr<WebIDBDatabase> backend, - const IDBDatabaseMetadata& metadata) { +void IDBOpenDBRequest::OnOpenDBSuccess( + mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase> pending_database, + scoped_refptr<base::SingleThreadTaskRunner> task_runner, + const IDBDatabaseMetadata& metadata) { TRACE_EVENT0("IndexedDB", "IDBOpenDBRequest::onSuccess(database)"); probe::AsyncTask async_task(GetExecutionContext(), async_task_context(), "success"); @@ -159,17 +163,17 @@ IDBDatabase* idb_database = nullptr; if (ResultAsAny()) { - // Previous OnUpgradeNeeded call delivered the backend. - DCHECK(!backend.get()); + DCHECK(!pending_database.is_valid()); idb_database = ResultAsAny()->IdbDatabase(); DCHECK(idb_database); DCHECK(!callbacks_receiver_); } else { - DCHECK(backend.get()); + DCHECK(pending_database); DCHECK(callbacks_receiver_); + idb_database = MakeGarbageCollected<IDBDatabase>( - GetExecutionContext(), std::move(backend), - std::move(callbacks_receiver_), std::move(connection_lifetime_)); + GetExecutionContext(), std::move(callbacks_receiver_), + std::move(connection_lifetime_), std::move(pending_database)); SetResult(MakeGarbageCollected<IDBAny>(idb_database)); } idb_database->SetMetadata(metadata);
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_open_db_request.h b/third_party/blink/renderer/modules/indexeddb/idb_open_db_request.h index 2877cfa..5b75daaeb 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_open_db_request.h +++ b/third_party/blink/renderer/modules/indexeddb/idb_open_db_request.h
@@ -35,7 +35,6 @@ #include "third_party/blink/public/mojom/indexeddb/indexeddb.mojom-blink.h" #include "third_party/blink/renderer/modules/indexeddb/idb_request.h" #include "third_party/blink/renderer/modules/indexeddb/idb_transaction.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/modules/modules_export.h" namespace blink { @@ -68,11 +67,13 @@ // request cannot be issued after a request that needs processing. void OnBlocked(int64_t existing_version); void OnUpgradeNeeded(int64_t old_version, - std::unique_ptr<WebIDBDatabase>, + mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase>, + scoped_refptr<base::SingleThreadTaskRunner>, const IDBDatabaseMetadata&, mojom::blink::IDBDataLoss, String data_loss_message); - void OnOpenDBSuccess(std::unique_ptr<WebIDBDatabase>, + void OnOpenDBSuccess(mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase>, + scoped_refptr<base::SingleThreadTaskRunner>, const IDBDatabaseMetadata&); void OnDeleteDBSuccess(int64_t old_version); void OnDBFactoryError(DOMException*);
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_request_test.cc b/third_party/blink/renderer/modules/indexeddb/idb_request_test.cc index eddf3aec..7ad9ad8 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_request_test.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_request_test.cc
@@ -61,7 +61,6 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_value_wrapping.h" #include "third_party/blink/renderer/modules/indexeddb/mock_idb_database.h" #include "third_party/blink/renderer/modules/indexeddb/mock_idb_transaction.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/platform/bindings/script_state.h" #include "third_party/blink/renderer/platform/heap/garbage_collected.h" #include "third_party/blink/renderer/platform/testing/task_environment.h" @@ -188,14 +187,12 @@ void BuildTransaction(V8TestingScope& scope, MockIDBDatabase& mock_database, MockIDBTransaction& mock_transaction_remote) { - auto database_backend = std::make_unique<WebIDBDatabase>( - mock_database.BindNewEndpointAndPassDedicatedRemote(), - blink::scheduler::GetSingleThreadTaskRunnerForTesting()); - db_ = MakeGarbageCollected<IDBDatabase>( - scope.GetExecutionContext(), std::move(database_backend), - mojo::NullAssociatedReceiver(), mojo::NullRemote()); - auto* execution_context = scope.GetExecutionContext(); + + db_ = MakeGarbageCollected<IDBDatabase>( + execution_context, mojo::NullAssociatedReceiver(), mojo::NullRemote(), + mock_database.BindNewEndpointAndPassDedicatedRemote()); + IDBTransaction::TransactionMojoRemote transaction_remote(execution_context); mojo::PendingAssociatedReceiver<mojom::blink::IDBTransaction> receiver = transaction_remote.BindNewEndpointAndPassReceiver(
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_transaction.cc b/third_party/blink/renderer/modules/indexeddb/idb_transaction.cc index c2a879c..822387f 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_transaction.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_transaction.cc
@@ -493,8 +493,8 @@ // due to a constraint error), we're already asynchronous. AbortOutstandingRequests(/*queue_tasks=*/from_frontend); - if (from_frontend && BackendDB()) { - BackendDB()->Abort(id_); + if (from_frontend && database_) { + database_->Abort(id_); } } @@ -585,10 +585,6 @@ return mojom::blink::IDBTransactionMode::ReadOnly; } -WebIDBDatabase* IDBTransaction::BackendDB() const { - return database_->Backend(); -} - const String& IDBTransaction::mode() const { switch (mode_) { case mojom::blink::IDBTransactionMode::ReadOnly:
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_transaction.h b/third_party/blink/renderer/modules/indexeddb/idb_transaction.h index b35a260d..5e10e466 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_transaction.h +++ b/third_party/blink/renderer/modules/indexeddb/idb_transaction.h
@@ -30,6 +30,7 @@ #include "base/dcheck_is_on.h" #include "third_party/blink/public/mojom/indexeddb/indexeddb.mojom-blink-forward.h" +#include "third_party/blink/public/mojom/indexeddb/indexeddb.mojom-blink.h" #include "third_party/blink/renderer/bindings/core/v8/active_script_wrappable.h" #include "third_party/blink/renderer/core/dom/dom_string_list.h" #include "third_party/blink/renderer/core/dom/events/event_listener.h" @@ -38,7 +39,6 @@ #include "third_party/blink/renderer/modules/event_target_modules.h" #include "third_party/blink/renderer/modules/indexeddb/idb_metadata.h" #include "third_party/blink/renderer/modules/indexeddb/indexed_db.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/modules/modules_export.h" #include "third_party/blink/renderer/platform/heap/collection_support/heap_hash_map.h" #include "third_party/blink/renderer/platform/heap/collection_support/heap_linked_hash_set.h" @@ -112,9 +112,6 @@ static mojom::blink::IDBTransactionMode StringToMode(const String&); - // When the connection is closed backend will be 0. - WebIDBDatabase* BackendDB() const; - int64_t Id() const { return id_; } bool IsActive() const { return state_ == kActive; } bool IsFinished() const { return state_ == kFinished; }
diff --git a/third_party/blink/renderer/modules/indexeddb/idb_transaction_test.cc b/third_party/blink/renderer/modules/indexeddb/idb_transaction_test.cc index 999c8c52..1ac0789d 100644 --- a/third_party/blink/renderer/modules/indexeddb/idb_transaction_test.cc +++ b/third_party/blink/renderer/modules/indexeddb/idb_transaction_test.cc
@@ -54,7 +54,6 @@ #include "third_party/blink/renderer/modules/indexeddb/idb_value_wrapping.h" #include "third_party/blink/renderer/modules/indexeddb/mock_idb_database.h" #include "third_party/blink/renderer/modules/indexeddb/mock_idb_transaction.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" #include "third_party/blink/renderer/platform/bindings/v8_per_isolate_data.h" #include "third_party/blink/renderer/platform/heap/garbage_collected.h" #include "third_party/blink/renderer/platform/testing/task_environment.h" @@ -85,14 +84,12 @@ void BuildTransaction(V8TestingScope& scope, MockIDBDatabase& mock_database, MockIDBTransaction& mock_transaction_remote) { - auto database_backend = std::make_unique<WebIDBDatabase>( - mock_database.BindNewEndpointAndPassDedicatedRemote(), - blink::scheduler::GetSingleThreadTaskRunnerForTesting()); - db_ = MakeGarbageCollected<IDBDatabase>( - scope.GetExecutionContext(), std::move(database_backend), - mojo::NullAssociatedReceiver(), mojo::NullRemote()); - auto* execution_context = scope.GetExecutionContext(); + + db_ = MakeGarbageCollected<IDBDatabase>( + execution_context, mojo::NullAssociatedReceiver(), mojo::NullRemote(), + mock_database.BindNewEndpointAndPassDedicatedRemote()); + IDBTransaction::TransactionMojoRemote transaction_remote(execution_context); mojo::PendingAssociatedReceiver<mojom::blink::IDBTransaction> receiver = transaction_remote.BindNewEndpointAndPassReceiver(
diff --git a/third_party/blink/renderer/modules/indexeddb/mock_idb_database.cc b/third_party/blink/renderer/modules/indexeddb/mock_idb_database.cc index f66311c..162f17a7 100644 --- a/third_party/blink/renderer/modules/indexeddb/mock_idb_database.cc +++ b/third_party/blink/renderer/modules/indexeddb/mock_idb_database.cc
@@ -17,10 +17,8 @@ mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase> MockIDBDatabase::BindNewEndpointAndPassDedicatedRemote() { auto remote = receiver_.BindNewEndpointAndPassDedicatedRemote(); - receiver_.set_disconnect_handler( WTF::BindOnce(&MockIDBDatabase::OnDisconnect, base::Unretained(this))); - return remote; }
diff --git a/third_party/blink/renderer/modules/indexeddb/web_idb_database.cc b/third_party/blink/renderer/modules/indexeddb/web_idb_database.cc deleted file mode 100644 index ec7a9c1..0000000 --- a/third_party/blink/renderer/modules/indexeddb/web_idb_database.cc +++ /dev/null
@@ -1,210 +0,0 @@ -// Copyright 2013 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h" - -#include <utility> - -#include "base/format_macros.h" -#include "base/memory/ptr_util.h" -#include "base/task/single_thread_task_runner.h" -#include "mojo/public/cpp/bindings/self_owned_associated_receiver.h" -#include "mojo/public/cpp/bindings/self_owned_receiver.h" -#include "third_party/blink/public/mojom/indexeddb/indexeddb.mojom-blink.h" -#include "third_party/blink/renderer/modules/indexeddb/idb_database_error.h" -#include "third_party/blink/renderer/modules/indexeddb/idb_key_range.h" -#include "third_party/blink/renderer/modules/indexeddb/idb_request.h" -#include "third_party/blink/renderer/modules/indexeddb/indexed_db_blink_mojom_traits.h" -#include "third_party/blink/renderer/modules/indexeddb/indexed_db_dispatcher.h" -#include "third_party/blink/renderer/platform/heap/persistent.h" -#include "third_party/blink/renderer/platform/wtf/functional.h" -#include "third_party/blink/renderer/platform/wtf/text/wtf_string.h" - -namespace blink { - -WebIDBDatabase::WebIDBDatabase( - mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase> pending_database, - scoped_refptr<base::SingleThreadTaskRunner> task_runner) - : task_runner_(std::move(task_runner)) { - database_.Bind(std::move(pending_database), task_runner_); -} - -WebIDBDatabase::~WebIDBDatabase() = default; - -void WebIDBDatabase::RenameObjectStore(int64_t transaction_id, - int64_t object_store_id, - const String& new_name) { - database_->RenameObjectStore(transaction_id, object_store_id, new_name); -} - -void WebIDBDatabase::CreateTransaction( - mojo::PendingAssociatedReceiver<mojom::blink::IDBTransaction> - transaction_receiver, - int64_t transaction_id, - const Vector<int64_t>& object_store_ids, - mojom::blink::IDBTransactionMode mode, - mojom::blink::IDBTransactionDurability durability) { - database_->CreateTransaction(std::move(transaction_receiver), transaction_id, - object_store_ids, mode, durability); -} - -void WebIDBDatabase::VersionChangeIgnored() { - database_->VersionChangeIgnored(); -} - -void WebIDBDatabase::Get( - int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const IDBKeyRange* key_range, - bool key_only, - base::OnceCallback<void(mojom::blink::IDBDatabaseGetResultPtr)> - result_callback) { - IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); - - mojom::blink::IDBKeyRangePtr key_range_ptr = - mojom::blink::IDBKeyRange::From(key_range); - database_->Get(transaction_id, object_store_id, index_id, - std::move(key_range_ptr), key_only, - std::move(result_callback)); -} - -void WebIDBDatabase::GetAll(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const IDBKeyRange* key_range, - int64_t max_count, - bool key_only, - IDBRequest* request) { - IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); - - mojom::blink::IDBKeyRangePtr key_range_ptr = - mojom::blink::IDBKeyRange::From(key_range); - database_->GetAll(transaction_id, object_store_id, index_id, - std::move(key_range_ptr), key_only, max_count, - WTF::BindOnce(&IDBRequest::OnGetAll, - WrapWeakPersistent(request), key_only)); -} - -void WebIDBDatabase::SetIndexKeys(int64_t transaction_id, - int64_t object_store_id, - std::unique_ptr<IDBKey> primary_key, - Vector<IDBIndexKeys> index_keys) { - database_->SetIndexKeys(transaction_id, object_store_id, - std::move(primary_key), std::move(index_keys)); -} - -void WebIDBDatabase::SetIndexesReady(int64_t transaction_id, - int64_t object_store_id, - const Vector<int64_t>& index_ids) { - database_->SetIndexesReady(transaction_id, object_store_id, - std::move(index_ids)); -} - -void WebIDBDatabase::OpenCursor(int64_t object_store_id, - int64_t index_id, - const IDBKeyRange* key_range, - mojom::blink::IDBCursorDirection direction, - bool key_only, - mojom::blink::IDBTaskType task_type, - IDBRequest* request) { - IndexedDBDispatcher::ResetCursorPrefetchCaches(request->transaction()->Id(), - nullptr); - - mojom::blink::IDBKeyRangePtr key_range_ptr = - mojom::blink::IDBKeyRange::From(key_range); - database_->OpenCursor( - request->transaction()->Id(), object_store_id, index_id, - std::move(key_range_ptr), direction, key_only, task_type, - WTF::BindOnce(&IDBRequest::OnOpenCursor, WrapWeakPersistent(request))); -} - -void WebIDBDatabase::Count(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const IDBKeyRange* key_range, - mojom::blink::IDBDatabase::CountCallback callback) { - IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); - - database_->Count(transaction_id, object_store_id, index_id, - mojom::blink::IDBKeyRange::From(key_range), - std::move(callback)); -} - -void WebIDBDatabase::Delete(int64_t transaction_id, - int64_t object_store_id, - const IDBKey* primary_key, - base::OnceCallback<void(bool)> success_callback) { - IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); - - mojom::blink::IDBKeyRangePtr key_range_ptr = - mojom::blink::IDBKeyRange::From(IDBKeyRange::Create(primary_key)); - database_->DeleteRange(transaction_id, object_store_id, - std::move(key_range_ptr), std::move(success_callback)); -} - -void WebIDBDatabase::DeleteRange( - int64_t transaction_id, - int64_t object_store_id, - const IDBKeyRange* key_range, - base::OnceCallback<void(bool)> success_callback) { - IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); - - mojom::blink::IDBKeyRangePtr key_range_ptr = - mojom::blink::IDBKeyRange::From(key_range); - database_->DeleteRange(transaction_id, object_store_id, - std::move(key_range_ptr), std::move(success_callback)); -} - -void WebIDBDatabase::GetKeyGeneratorCurrentNumber( - int64_t transaction_id, - int64_t object_store_id, - mojom::blink::IDBDatabase::GetKeyGeneratorCurrentNumberCallback callback) { - database_->GetKeyGeneratorCurrentNumber(transaction_id, object_store_id, - std::move(callback)); -} - -void WebIDBDatabase::Clear( - int64_t transaction_id, - int64_t object_store_id, - mojom::blink::IDBDatabase::ClearCallback success_callback) { - IndexedDBDispatcher::ResetCursorPrefetchCaches(transaction_id, nullptr); - database_->Clear(transaction_id, object_store_id, - std::move(success_callback)); -} - -void WebIDBDatabase::CreateIndex(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const String& name, - const IDBKeyPath& key_path, - bool unique, - bool multi_entry) { - database_->CreateIndex(transaction_id, object_store_id, index_id, name, - key_path, unique, multi_entry); -} - -void WebIDBDatabase::DeleteIndex(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id) { - database_->DeleteIndex(transaction_id, object_store_id, index_id); -} - -void WebIDBDatabase::RenameIndex(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const String& new_name) { - DCHECK(!new_name.IsNull()); - database_->RenameIndex(transaction_id, object_store_id, index_id, new_name); -} - -void WebIDBDatabase::Abort(int64_t transaction_id) { - database_->Abort(transaction_id); -} - -void WebIDBDatabase::DidBecomeInactive() { - database_->DidBecomeInactive(); -} - -} // namespace blink
diff --git a/third_party/blink/renderer/modules/indexeddb/web_idb_database.h b/third_party/blink/renderer/modules/indexeddb/web_idb_database.h deleted file mode 100644 index 7ac0ace8..0000000 --- a/third_party/blink/renderer/modules/indexeddb/web_idb_database.h +++ /dev/null
@@ -1,115 +0,0 @@ -// Copyright 2013 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef THIRD_PARTY_BLINK_RENDERER_MODULES_INDEXEDDB_WEB_IDB_DATABASE_H_ -#define THIRD_PARTY_BLINK_RENDERER_MODULES_INDEXEDDB_WEB_IDB_DATABASE_H_ - -#include <stdint.h> -#include <memory> - -#include "base/task/single_thread_task_runner.h" -#include "mojo/public/cpp/bindings/associated_remote.h" -#include "mojo/public/cpp/bindings/pending_associated_receiver.h" -#include "mojo/public/cpp/bindings/pending_associated_remote.h" -#include "third_party/blink/public/mojom/indexeddb/indexeddb.mojom-blink.h" -#include "third_party/blink/renderer/modules/indexeddb/web_idb_cursor.h" -#include "third_party/blink/renderer/modules/modules_export.h" - -namespace blink { -class IDBRequest; - -class MODULES_EXPORT WebIDBDatabase final { - public: - WebIDBDatabase( - mojo::PendingAssociatedRemote<mojom::blink::IDBDatabase> pending_database, - scoped_refptr<base::SingleThreadTaskRunner> task_runner); - ~WebIDBDatabase(); - - static const int64_t kMinimumIndexId = 30; - - void RenameObjectStore(int64_t transaction_id, - int64_t object_store_id, - const String& new_name); - void CreateTransaction(mojo::PendingAssociatedReceiver< - mojom::blink::IDBTransaction> transaction_receiver, - int64_t transaction_id, - const Vector<int64_t>& scope, - mojom::blink::IDBTransactionMode mode, - mojom::blink::IDBTransactionDurability durability); - - void VersionChangeIgnored(); - - void Get( - int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const IDBKeyRange*, - bool key_only, - base::OnceCallback<void(mojom::blink::IDBDatabaseGetResultPtr)> result); - void GetAll(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const IDBKeyRange*, - int64_t max_count, - bool key_only, - IDBRequest*); - void SetIndexKeys(int64_t transaction_id, - int64_t object_store_id, - std::unique_ptr<IDBKey> primary_key, - Vector<IDBIndexKeys>); - void SetIndexesReady(int64_t transaction_id, - int64_t object_store_id, - const Vector<int64_t>& index_ids); - void OpenCursor(int64_t object_store_id, - int64_t index_id, - const IDBKeyRange*, - mojom::blink::IDBCursorDirection direction, - bool key_only, - mojom::blink::IDBTaskType, - IDBRequest*); - void Count(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const IDBKeyRange*, - mojom::blink::IDBDatabase::CountCallback callback); - void Delete(int64_t transaction_id, - int64_t object_store_id, - const IDBKey* primary_key, - mojom::blink::IDBDatabase::DeleteRangeCallback callback); - void DeleteRange(int64_t transaction_id, - int64_t object_store_id, - const IDBKeyRange*, - mojom::blink::IDBDatabase::DeleteRangeCallback callback); - void GetKeyGeneratorCurrentNumber( - int64_t transaction_id, - int64_t object_store_id, - mojom::blink::IDBDatabase::GetKeyGeneratorCurrentNumberCallback callback); - void Clear(int64_t transaction_id, - int64_t object_store_id, - mojom::blink::IDBDatabase::ClearCallback callback); - void CreateIndex(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const String& name, - const IDBKeyPath&, - bool unique, - bool multi_entry); - void DeleteIndex(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id); - void RenameIndex(int64_t transaction_id, - int64_t object_store_id, - int64_t index_id, - const String& new_name); - void Abort(int64_t transaction_id); - void DidBecomeInactive(); - - private: - mojo::AssociatedRemote<mojom::blink::IDBDatabase> database_; - scoped_refptr<base::SingleThreadTaskRunner> task_runner_; -}; - -} // namespace blink - -#endif // THIRD_PARTY_BLINK_RENDERER_MODULES_INDEXEDDB_WEB_IDB_DATABASE_H_
diff --git a/third_party/blink/renderer/platform/runtime_enabled_features.json5 b/third_party/blink/renderer/platform/runtime_enabled_features.json5 index 1f8ce82a..492b4b9 100644 --- a/third_party/blink/renderer/platform/runtime_enabled_features.json5 +++ b/third_party/blink/renderer/platform/runtime_enabled_features.json5
@@ -667,7 +667,7 @@ }, { name: "ClipboardWellFormedHtmlSanitizationWrite", - status: "stable", + status: "experimental", }, { // https://drafts.fxtf.org/css-masking/#typedef-geometry-box @@ -2191,6 +2191,10 @@ settable_from_internals: true, }, { + name: "LayoutAlignForPositioned", + status: "stable", + }, + { name: "LayoutFlexNewRowAlgorithmV3", status: "test", },
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-htb.html new file mode 100644 index 0000000..786cec7 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-htb.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-vlr.html new file mode 100644 index 0000000..917e50d5 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-vlr.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-vrl.html new file mode 100644 index 0000000..b60d4615 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-ltr-vrl.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-htb.html new file mode 100644 index 0000000..9bf919dd4 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-htb.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-vlr.html new file mode 100644 index 0000000..5c1e8c75 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-vlr.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-vrl.html new file mode 100644 index 0000000..b7f00569 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-htb-rtl-vrl.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-htb.html new file mode 100644 index 0000000..98e3c0b --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-htb.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-vlr.html new file mode 100644 index 0000000..73585d2 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-vlr.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-vrl.html new file mode 100644 index 0000000..39ecd38 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-ltr-vrl.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-htb.html new file mode 100644 index 0000000..7a4167f --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-htb.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-vlr.html new file mode 100644 index 0000000..4ce7d46 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-vlr.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-vrl.html new file mode 100644 index 0000000..0fe16044 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vlr-rtl-vrl.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-htb.html new file mode 100644 index 0000000..98e6145a --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-htb.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-vlr.html new file mode 100644 index 0000000..d22b347 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-vlr.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-vrl.html new file mode 100644 index 0000000..602b7afb --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-ltr-vrl.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-htb.html new file mode 100644 index 0000000..1dcfd87 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-htb.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-vlr.html new file mode 100644 index 0000000..d22b347 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-vlr.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-vrl.html new file mode 100644 index 0000000..602b7afb --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/align-self-vrl-rtl-vrl.html
@@ -0,0 +1,110 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="align-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="align-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-htb.html new file mode 100644 index 0000000..cfef344 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-htb.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-vlr.html new file mode 100644 index 0000000..55680f4 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-vlr.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-vrl.html new file mode 100644 index 0000000..57ee3af --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-ltr-vrl.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-htb.html new file mode 100644 index 0000000..95e54c2b --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-htb.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-vlr.html new file mode 100644 index 0000000..e7224e7 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-vlr.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-vrl.html new file mode 100644 index 0000000..ba7e98a --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-htb-rtl-vrl.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-width="20" data-offset-x="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-width="20" data-offset-x="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-width="20" data-offset-x="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-width="40" data-offset-x="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-htb.html new file mode 100644 index 0000000..d47c50467 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-htb.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-vlr.html new file mode 100644 index 0000000..71e3687 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-vlr.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-vrl.html new file mode 100644 index 0000000..ae90d4d --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-ltr-vrl.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-htb.html new file mode 100644 index 0000000..1a192b56 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-htb.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-vlr.html new file mode 100644 index 0000000..cb9986d --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-vlr.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-vrl.html new file mode 100644 index 0000000..fb717a0 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vlr-rtl-vrl.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-htb.html new file mode 100644 index 0000000..e2cbff3 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-htb.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-vlr.html new file mode 100644 index 0000000..5aa2f48 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-vlr.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-vrl.html new file mode 100644 index 0000000..cf2db8d3 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-ltr-vrl.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-htb.html new file mode 100644 index 0000000..317e53e9 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-htb.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-vlr.html new file mode 100644 index 0000000..2d144d16 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-vlr.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-lr; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-vrl.html new file mode 100644 index 0000000..026c6e9 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/justify-self-vrl-rtl-vrl.html
@@ -0,0 +1,126 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: rtl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: vertical-rl; + direction: ltr; + position: absolute; + background: green; + inset: 0; +} + +.item::before { + width: 20px; + height: 20px; + content: ''; + display: block; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-start;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: self-end;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container"> + <div class="item rtl" style="justify-self: start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: center;" data-expected-height="20" data-offset-y="10"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: baseline;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: last baseline;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-start;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: self-end;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: left;" data-expected-height="20" data-offset-y="0"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: right;" data-expected-height="20" data-offset-y="20"></div> +</div> + +<div class="container"> + <div class="item rtl" style="justify-self: stretch;" data-expected-height="40" data-offset-y="0"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-htb.html new file mode 100644 index 0000000..9e259c1 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-htb.html
@@ -0,0 +1,149 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + position: absolute; + background: green; + inset: 5px; + margin: 10px; + width: 30px; + height: 30px; +} + +.safe { + align-self: safe end; +} +.unsafe { + align-self: unsafe end; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="15"></div> +</div> + +<!-- UNSAFE --> +<br> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="-5"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="15"></div> +</div> + +<!-- UNSAFE RTL --> +<br> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="-5"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-vlr.html new file mode 100644 index 0000000..d47b183 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-vlr.html
@@ -0,0 +1,149 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + position: absolute; + background: green; + inset: 5px; + margin: 10px; + width: 30px; + height: 30px; +} + +.safe { + align-self: safe end; +} +.unsafe { + align-self: unsafe end; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="15"></div> +</div> + +<!-- UNSAFE --> +<br> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="-5"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="15"></div> +</div> + +<!-- UNSAFE RTL --> +<br> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="-5"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-vrl.html new file mode 100644 index 0000000..34327620 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-align-self-vrl.html
@@ -0,0 +1,149 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + position: absolute; + background: green; + inset: 5px; + margin: 10px; + width: 30px; + height: 30px; +} + +.safe { + align-self: safe end; +} +.unsafe { + align-self: unsafe end; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="-5"></div> +</div> + +<!-- UNSAFE --> +<br> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="15"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="-5"></div> +</div> + +<!-- UNSAFE RTL --> +<br> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="15"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-htb.html new file mode 100644 index 0000000..0fa5cc3 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-htb.html
@@ -0,0 +1,149 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + position: absolute; + background: green; + inset: 5px; + margin: 10px; + width: 30px; + height: 30px; +} + +.safe { + justify-self: safe end; +} +.unsafe { + justify-self: unsafe end; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="15"></div> +</div> + +<!-- UNSAFE --> +<br> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="-5"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="-5"></div> +</div> + +<!-- UNSAFE RTL --> +<br> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-x="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-x="15"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-vlr.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-vlr.html new file mode 100644 index 0000000..7554975f --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-vlr.html
@@ -0,0 +1,149 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-lr; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + position: absolute; + background: green; + inset: 5px; + margin: 10px; + width: 30px; + height: 30px; +} + +.safe { + justify-self: safe end; +} +.unsafe { + justify-self: unsafe end; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="15"></div> +</div> + +<!-- UNSAFE --> +<br> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="-5"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="-5"></div> +</div> + +<!-- UNSAFE RTL --> +<br> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="15"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-vrl.html new file mode 100644 index 0000000..fe2405c --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/safe-justify-self-vrl.html
@@ -0,0 +1,149 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + direction: ltr; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + position: absolute; + background: green; + inset: 5px; + margin: 10px; + width: 30px; + height: 30px; +} + +.safe { + justify-self: safe end; +} +.unsafe { + justify-self: unsafe end; +} + +.rtl { + direction: rtl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="15"></div> +</div> + +<!-- UNSAFE --> +<br> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="-5"></div> +</div> + +<!-- RTL --> +<br> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="-5"></div> +</div> + +<div class="container rtl"> + <div class="item safe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="-5"></div> +</div> + +<!-- UNSAFE RTL --> +<br> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: horizontal-tb; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: veritcal-rl; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-rl; direction: rtl;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: ltr;" data-offset-y="15"></div> +</div> + +<div class="container rtl"> + <div class="item unsafe" style="writing-mode: vertical-lr; direction: rtl;" data-offset-y="15"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-htb-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-htb-htb.html new file mode 100644 index 0000000..dc7df332e --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-htb-htb.html
@@ -0,0 +1,100 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 60px; + height: 60px; +} + +.item { + writing-mode: horizontal-tb; + position: absolute; + background: green; + inset: 5px 10px 5px 10px; +} + +.child::before { + aspect-ratio: 1/1; + min-width: 20px; + min-height: 20px; + width: 100%; + height: 100%; + content: ''; + display: block; +} + +.ar { + aspect-ratio: 1/1; + min-width: 20px; + min-height: 20px; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<body> + +<div class="container"> + <div class="item child" style="justify-self: start; align-self: start;" data-expected-width="20" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item child" style="justify-self: stretch; align-self: start;" data-expected-width="40" data-expected-height="40"></div> +</div> + +<div class="container"> + <div class="item child" style="justify-self: start; align-self: stretch;" data-expected-width="50" data-expected-height="50"></div> +</div> + +<div class="container"> + <div class="item child" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></div> +</div> + +<br> + +<div class="container"> + <div class="item ar" style="justify-self: start; align-self: start;" data-expected-width="20" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: stretch; align-self: start;" data-expected-width="40" data-expected-height="40"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: start; align-self: stretch;" data-expected-width="50" data-expected-height="50"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></div> +</div> + +<br> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: start; align-self: start;" data-expected-width="10" data-expected-height="10"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: stretch; align-self: start;" data-expected-width="40" data-expected-height="40"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: start; align-self: stretch;" data-expected-width="50" data-expected-height="50"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></canvas> +</div>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-htb-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-htb-vrl.html new file mode 100644 index 0000000..cd2c9b9a --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-htb-vrl.html
@@ -0,0 +1,100 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 60px; + height: 60px; +} + +.item { + writing-mode: vertical-rl; + position: absolute; + background: green; + inset: 5px 10px 5px 10px; +} + +.item::before { + aspect-ratio: 1/1; + min-width: 20px; + min-height: 20px; + width: 100%; + height: 100%; + content: ''; + display: block; +} + +.ar { + aspect-ratio: 1/1; + min-width: 20px; + min-height: 20px; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<body> + +<div class="container"> + <div class="item" style="justify-self: start; align-self: start;" data-expected-width="20" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch; align-self: start;" data-expected-width="40" data-expected-height="40"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: start; align-self: stretch;" data-expected-width="50" data-expected-height="50"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></div> +</div> + +<br> + +<div class="container"> + <div class="item ar" style="justify-self: start; align-self: start;" data-expected-width="20" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: stretch; align-self: start;" data-expected-width="40" data-expected-height="40"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: start; align-self: stretch;" data-expected-width="50" data-expected-height="50"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></div> +</div> + +<br> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: start; align-self: start;" data-expected-width="10" data-expected-height="10"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: stretch; align-self: start;" data-expected-width="40" data-expected-height="40"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: start; align-self: stretch;" data-expected-width="50" data-expected-height="50"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></canvas> +</div>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-vrl-htb.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-vrl-htb.html new file mode 100644 index 0000000..7b10021 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-vrl-htb.html
@@ -0,0 +1,100 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 60px; + height: 60px; +} + +.item { + writing-mode: horizontal-tb; + position: absolute; + background: green; + inset: 5px 10px 5px 10px; +} + +.item::before { + aspect-ratio: 1/1; + min-width: 20px; + min-height: 20px; + width: 100%; + height: 100%; + content: ''; + display: block; +} + +.ar { + aspect-ratio: 1/1; + min-width: 20px; + min-height: 20px; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<body> + +<div class="container"> + <div class="item" style="justify-self: start; align-self: start;" data-expected-width="20" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch; align-self: start;" data-expected-width="50" data-expected-height="50"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: start; align-self: stretch;" data-expected-width="40" data-expected-height="40"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></div> +</div> + +<br> + +<div class="container"> + <div class="item ar" style="justify-self: start; align-self: start;" data-expected-width="20" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: stretch; align-self: start;" data-expected-width="50" data-expected-height="50"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: start; align-self: stretch;" data-expected-width="40" data-expected-height="40"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></div> +</div> + +<br> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: start; align-self: start;" data-expected-width="10" data-expected-height="10"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: stretch; align-self: start;" data-expected-width="50" data-expected-height="50"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: start; align-self: stretch;" data-expected-width="40" data-expected-height="40"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></canvas> +</div>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-vrl-vrl.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-vrl-vrl.html new file mode 100644 index 0000000..10f11a9f --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/stretch-intrinsic-size-vrl-vrl.html
@@ -0,0 +1,100 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: vertical-rl; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 60px; + height: 60px; +} + +.item { + writing-mode: vertical-rl; + position: absolute; + background: green; + inset: 5px 10px 5px 10px; +} + +.item::before { + aspect-ratio: 1/1; + min-width: 20px; + min-height: 20px; + width: 100%; + height: 100%; + content: ''; + display: block; +} + +.ar { + aspect-ratio: 1/1; + min-width: 20px; + min-height: 20px; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<body> + +<div class="container"> + <div class="item" style="justify-self: start; align-self: start;" data-expected-width="20" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch; align-self: start;" data-expected-width="50" data-expected-height="50"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: start; align-self: stretch;" data-expected-width="40" data-expected-height="40"></div> +</div> + +<div class="container"> + <div class="item" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></div> +</div> + +<br> + +<div class="container"> + <div class="item ar" style="justify-self: start; align-self: start;" data-expected-width="20" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: stretch; align-self: start;" data-expected-width="50" data-expected-height="50"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: start; align-self: stretch;" data-expected-width="40" data-expected-height="40"></div> +</div> + +<div class="container"> + <div class="item ar" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></div> +</div> + +<br> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: start; align-self: start;" data-expected-width="10" data-expected-height="10"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: stretch; align-self: start;" data-expected-width="50" data-expected-height="50"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: start; align-self: stretch;" data-expected-width="40" data-expected-height="40"></canvas> +</div> + +<div class="container"> + <canvas width="10" height="10" class="item" style="justify-self: stretch; align-self: stretch;" data-expected-width="40" data-expected-height="50"></canvas> +</div>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/table-align-self-stretch.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/table-align-self-stretch.html new file mode 100644 index 0000000..bedd0a5 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/table-align-self-stretch.html
@@ -0,0 +1,84 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#align-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + position: absolute; + background: green; + inset: 5px; + align-self: stretch; + display: table; +} + +.item::before { + content: ''; + display: block; + width: 10px; + height: 20px; +} + +.big::before { + width: 50px; + height: 60px; +} + +.vrl { + writing-mode: vertical-rl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<body> + +<div class="container"> + <div class="item" data-expected-width="10" data-expected-height="30"></div> +</div> + +<div class="container"> + <div class="item big" data-expected-width="50" data-expected-height="60"></div> +</div> + +<div class="container"> + <div class="item vrl" data-expected-width="10" data-expected-height="30"></div> +</div> + +<div class="container"> + <div class="item big vrl" data-expected-width="50" data-expected-height="60"></div> +</div> + +<br> + +<div class="container vrl"> + <div class="item" data-expected-width="30" data-expected-height="20"></div> +</div> + +<div class="container vrl"> + <div class="item big" data-expected-width="50" data-expected-height="60"></div> +</div> + +<div class="container vrl"> + <div class="item vrl" data-expected-width="30" data-expected-height="20"></div> +</div> + +<div class="container vrl"> + <div class="item big vrl" data-expected-width="50" data-expected-height="60"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/abspos/table-justify-self-stretch.html b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/table-justify-self-stretch.html new file mode 100644 index 0000000..c409b107 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/abspos/table-justify-self-stretch.html
@@ -0,0 +1,84 @@ +<!DOCTYPE html> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#justify-abspos"> +<style> +body { + margin: 0; +} + +.container { + writing-mode: horizontal-tb; + display: inline-block; + position: relative; + margin: 20px; + border: solid 4px; + width: 40px; + height: 40px; +} + +.item { + writing-mode: horizontal-tb; + position: absolute; + background: green; + inset: 5px; + justify-self: stretch; + display: table; +} + +.item::before { + content: ''; + display: block; + width: 10px; + height: 20px; +} + +.big::before { + width: 50px; + height: 60px; +} + +.vrl { + writing-mode: vertical-rl; +} +</style> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/resources/check-layout-th.js"></script> + +<body onload="checkLayout('.item')"> + +<body> + +<div class="container"> + <div class="item" data-expected-width="30" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item big" data-expected-width="50" data-expected-height="60"></div> +</div> + +<div class="container"> + <div class="item vrl" data-expected-width="30" data-expected-height="20"></div> +</div> + +<div class="container"> + <div class="item big vrl" data-expected-width="50" data-expected-height="60"></div> +</div> + +<br> + +<div class="container vrl"> + <div class="item" data-expected-width="10" data-expected-height="30"></div> +</div> + +<div class="container vrl"> + <div class="item big" data-expected-width="50" data-expected-height="60"></div> +</div> + +<div class="container vrl"> + <div class="item vrl" data-expected-width="10" data-expected-height="30"></div> +</div> + +<div class="container vrl"> + <div class="item big vrl" data-expected-width="50" data-expected-height="60"></div> +</div> +
diff --git a/third_party/blink/web_tests/external/wpt/shared-storage/resources/register-service-worker-iframe.https.html b/third_party/blink/web_tests/external/wpt/shared-storage/resources/register-service-worker-iframe.https.html new file mode 100644 index 0000000..547ab1d --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/shared-storage/resources/register-service-worker-iframe.https.html
@@ -0,0 +1,66 @@ +<!doctype html> +<body> + <script src=/resources/testharness.js></script> + <script src=/common/utils.js></script> + <script src=/fenced-frame/resources/utils.js></script> + <script src=/shared-storage/resources/util.js></script> + <script src=/shared-storage/resources/util.sub.js></script> + <script src=/service-workers/service-worker/resources/test-helpers.sub.js></script> + <script> + const INTERMEDIATE_FRAME_SUFFIX = + 'able-fetch-request-fallback-to-network-iframe.https.html' + const ORIGIN = new URL("", location.href).origin; + + window.addEventListener('message', async function handler(event) { + const data = event.data; + if (data.script && data.scope && data.port) { + var absoluteScope = (new URL(data.scope, window.location).href); + let oldReg =await navigator.serviceWorker.getRegistration(data.scope); + if (oldReg && oldReg.scope === absoluteScope) { + await oldReg.unregister(); + } + let reg = await navigator.serviceWorker.register(data.script, + { scope: data.scope }); + let worker = reg.installing; + await new Promise(function(resolve) { + worker.addEventListener('statechange', function() { + if (worker.state == 'activated') { + resolve(); + } + }); + }); + assert_not_equals(worker, null, 'worker is installing'); + + let result = await loadNestedSharedStorageFrameInNewFrame({ + key: 'c', value: 'd', + hasSharedStorageWritableAttribute: true, + // Same-origin to this frame, cross-origin to top. + isSameOrigin: true, + }); + const urls = [ + { + "url": ORIGIN + data.scope + INTERMEDIATE_FRAME_SUFFIX, + "mode": "navigate", + "SSWHeader": "null" + }, + { + "url": ORIGIN + "/resources/testharness.js", + "mode": "no-cors", + "SSWHeader": "null" + }, + { + "url": ORIGIN + result.nestedFrameUrl, + "mode": "navigate", + "SSWHeader": "null" + }, + ]; + await checkInterceptedUrls(worker, urls); + await verifyKeyValueForOrigin('c', 'd', ORIGIN); + await deleteKeyForOrigin('c', ORIGIN); + data.port.postMessage({msg: 'test completed'}); + reg.unregister() + window.removeEventListener('message', handler); + } + }); + </script> +</body>
diff --git a/third_party/blink/web_tests/external/wpt/shared-storage/resources/shared-storage-writable-fetch-request-fallback-to-network-iframe.https.html b/third_party/blink/web_tests/external/wpt/shared-storage/resources/shared-storage-writable-fetch-request-fallback-to-network-iframe.https.html index 8229ce8..3451d914 100644 --- a/third_party/blink/web_tests/external/wpt/shared-storage/resources/shared-storage-writable-fetch-request-fallback-to-network-iframe.https.html +++ b/third_party/blink/web_tests/external/wpt/shared-storage/resources/shared-storage-writable-fetch-request-fallback-to-network-iframe.https.html
@@ -18,5 +18,39 @@ img.src = url; }); } + + function loadFrame(url, hasSharedStorageWritableAttribute) { + return new Promise(function(resolve, reject) { + var frame = document.createElement('iframe'); + document.body.appendChild(frame); + frame.onload = function() { + window.parent.postMessage({msg: 'iframe loaded'}, "*"); + resolve(frame); + }; + frame.onerror = function() { + reject(new Error('Nested iframe load failed')); + }; + if (hasSharedStorageWritableAttribute) { + frame.sharedStorageWritable = true; + } + frame.src = url; + }); + } + + function fetchUrl(url, hasSharedStorageWritableAttribute) { + return new Promise(function(resolve, reject) { + fetch(url, {sharedStorageWritable: + hasSharedStorageWritableAttribute}) + .then(response => { + if (!response.ok) { + throw new Error('Failed to fetch ' + url + '; ' + + String(response.status) + ' ' + response.statusText); + } + resolve(response); + }).catch(error => { + reject(error); + }); + }); + } </script> </body>
diff --git a/third_party/blink/web_tests/external/wpt/shared-storage/resources/util.js b/third_party/blink/web_tests/external/wpt/shared-storage/resources/util.js index f827658..4a7fcc4 100644 --- a/third_party/blink/web_tests/external/wpt/shared-storage/resources/util.js +++ b/third_party/blink/web_tests/external/wpt/shared-storage/resources/util.js
@@ -196,3 +196,22 @@ const result = await nextValueFromServer(outerKey); assert_equals(result, 'delete_key_loaded'); } + +function getFetchedUrls(worker) { + return new Promise(function(resolve) { + var channel = new MessageChannel(); + channel.port1.onmessage = function(msg) { + resolve(msg); + }; + worker.postMessage({port: channel.port2}, [channel.port2]); + }); +} + +function checkInterceptedUrls(worker, expectedRequests) { + return getFetchedUrls(worker).then(function(msg) { + let actualRequests = msg.data.requests; + assert_equals(actualRequests.length, expectedRequests.length); + assert_equals( + JSON.stringify(actualRequests), JSON.stringify(expectedRequests)); + }); +}
diff --git a/third_party/blink/web_tests/external/wpt/shared-storage/resources/util.sub.js b/third_party/blink/web_tests/external/wpt/shared-storage/resources/util.sub.js index 970c33b7..f147209d 100644 --- a/third_party/blink/web_tests/external/wpt/shared-storage/resources/util.sub.js +++ b/third_party/blink/web_tests/external/wpt/shared-storage/resources/util.sub.js
@@ -69,3 +69,49 @@ document.body.appendChild(frame); return promise; } + +async function loadNestedSharedStorageFrameInNewFrame(data) { + const SCOPE = '/shared-storage/resources/shared-storage-writ'; + const INTERMEDIATE_FRAME_SUFFIX = + 'able-fetch-request-fallback-to-network-iframe.https.html' + const CROSS_ORIGIN = 'https://{{domains[www]}}:{{ports[https][0]}}'; + + let {key, value, hasSharedStorageWritableAttribute, isSameOrigin} = data; + + const windowPromise = new Promise((resolve, reject) => { + window.addEventListener('message', async function handler(evt) { + if (evt.data.msg && evt.data.msg === 'iframe loaded') { + window.removeEventListener('message', handler); + resolve(); + } + }); + window.addEventListener('error', () => { + reject(new Error('Navigation error')); + }); + }); + + const framePromise = new Promise((resolve, reject) => { + let frame = document.createElement('iframe'); + frame.src = SCOPE + INTERMEDIATE_FRAME_SUFFIX; + frame.onload = function() { + resolve(frame); + }; + frame.onerror = function() { + reject(new Error('Iframe load failed')); + }; + document.body.appendChild(frame); + }); + let frame = await framePromise; + + let rawWriteHeader = `set;key=${key};value=${value}`; + let writeHeader = encodeURIComponent(rawWriteHeader); + const sameOriginNestedSrc = `/shared-storage/resources/` + + `shared-storage-write.py?write=${writeHeader}`; + const nestedSrc = + isSameOrigin ? sameOriginNestedSrc : CROSS_ORIGIN + sameOriginNestedSrc; + + let nestedFrame = frame.contentWindow.loadFrame( + nestedSrc, hasSharedStorageWritableAttribute); + await windowPromise; + return {frame: frame, nestedFrame: nestedFrame, nestedFrameUrl: nestedSrc}; +}
diff --git a/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-fetch.tentative.https.sub.html b/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-fetch.tentative.https.sub.html new file mode 100644 index 0000000..ea7af527 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-fetch.tentative.https.sub.html
@@ -0,0 +1,109 @@ +<!doctype html> +<body> + <script src=/resources/testharness.js></script> + <script src=/resources/testharnessreport.js></script> + <script src=/common/utils.js></script> + <script src=/fenced-frame/resources/utils.js></script> + <script src=/shared-storage/resources/util.js></script> + <script src=/service-workers/service-worker/resources/test-helpers.sub.js></script> + <script> + const SCOPE = '/shared-storage/resources/' + + 'shared-storage-writable-fetch-request-fallback-to-network-iframe.https.html'; + const SCRIPT = '/shared-storage/resources/' + + 'shared-storage-writable-fetch-request-fallback-to-network-worker.js'; + const SAME_ORIGIN = new URL("", location.href).origin; + const CROSS_ORIGIN = 'https://{{domains[www]}}:{{ports[https][0]}}'; + + async function fetchSharedStorageUrlInNewFrame(data) { + let {test, key, value, hasSharedStorageWritableAttribute, isSameOrigin} + = data; + + const framePromise = new Promise((resolve, reject) => { + let frame = document.createElement('iframe'); + frame.src = SCOPE; + frame.onload = function() { + resolve(frame); + }; + frame.onerror = function() { + reject(new Error('Iframe load failed')); + }; + test.add_cleanup(function() { + frame.remove(); + }); + document.body.appendChild(frame); + }); + let frame = await framePromise; + + let rawWriteHeader = `set;key=${key};value=${value}`; + let writeHeader = encodeURIComponent(rawWriteHeader); + const sameOriginSrc = `/shared-storage/resources/` + + `shared-storage-write.py?write=${writeHeader}`; + const src = isSameOrigin ? + sameOriginSrc : + CROSS_ORIGIN + sameOriginSrc; + return { + response: frame.contentWindow.fetchUrl(src, + hasSharedStorageWritableAttribute), + url: src, + }; + } + + promise_test(async t => { + await service_worker_unregister(t, SCOPE); + let reg = await navigator.serviceWorker.register(SCRIPT, + { scope: SCOPE }); + t.add_cleanup(_ => reg.unregister()); + let worker = reg.installing; + await wait_for_state(t, worker, 'activated'); + assert_not_equals(worker, null, 'worker is installing'); + + let {response, url} = await fetchSharedStorageUrlInNewFrame({ + test: t, + key: 'a', value: 'b', + hasSharedStorageWritableAttribute: true, + isSameOrigin: true, + }); + checkInterceptedUrls(worker, [ + {"url": SAME_ORIGIN + SCOPE, "mode": "navigate", "SSWHeader": "null"}, + { + "url": SAME_ORIGIN + "/resources/testharness.js", + "mode": "no-cors", + "SSWHeader": "null" + }, + {"url": SAME_ORIGIN + url, "mode": "cors", "SSWHeader": "null"}, + ]); + await verifyKeyValueForOrigin('a', 'b', SAME_ORIGIN); + await deleteKeyForOrigin('a', SAME_ORIGIN); + }, 'test fetch(url, {sharedStorageWritable: true}) via JS from service ' + + 'worker for same origin fetch'); + + promise_test(async t => { + await service_worker_unregister(t, SCOPE); + let reg = await navigator.serviceWorker.register(SCRIPT, + { scope: SCOPE }); + t.add_cleanup(_ => reg.unregister()); + let worker = reg.installing; + await wait_for_state(t, worker, 'activated'); + assert_not_equals(worker, null, 'worker is installing'); + + let {response, url} = await fetchSharedStorageUrlInNewFrame({ + test: t, + key: 'c', value: 'd', + hasSharedStorageWritableAttribute: true, + isSameOrigin: false, + }); + checkInterceptedUrls(worker, [ + {"url": SAME_ORIGIN + SCOPE, "mode": "navigate", "SSWHeader": "null"}, + { + "url": SAME_ORIGIN + "/resources/testharness.js", + "mode": "no-cors", + "SSWHeader": "null" + }, + {"url": url, "mode": "cors", "SSWHeader": "null"}, + ]); + await verifyKeyValueForOrigin('c', 'd', CROSS_ORIGIN); + await deleteKeyForOrigin('c', CROSS_ORIGIN); + }, 'test fetch(url, {sharedStorageWritable: true}) via JS from service ' + + 'worker for cross origin fetch'); + </script> +</body>
diff --git a/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-iframe.tentative.https.sub.html b/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-iframe.tentative.https.sub.html new file mode 100644 index 0000000..9eb2820 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-iframe.tentative.https.sub.html
@@ -0,0 +1,98 @@ +<!doctype html> +<body> + <script src=/resources/testharness.js></script> + <script src=/resources/testharnessreport.js></script> + <script src=/common/utils.js></script> + <script src=/fenced-frame/resources/utils.js></script> + <script src=/shared-storage/resources/util.js></script> + <script src=/shared-storage/resources/util.sub.js></script> + <script src=/service-workers/service-worker/resources/test-helpers.sub.js></script> + <script> + const SCOPE = '/shared-storage/resources/shared-storage-writ'; + const INTERMEDIATE_FRAME_SUFFIX = + 'able-fetch-request-fallback-to-network-iframe.https.html' + const SCRIPT = '/shared-storage/resources/' + + 'shared-storage-writable-fetch-request-fallback-to-network-worker.js'; + const WORKER_FRAME = '/shared-storage/resources/' + + 'register-service-worker-iframe.https.html'; + const SAME_ORIGIN = new URL("", location.href).origin; + const CROSS_ORIGIN = 'https://{{domains[www]}}:{{ports[https][0]}}'; + + promise_test(async t => { + await service_worker_unregister(t, SCOPE); + let reg = await navigator.serviceWorker.register(SCRIPT, + { scope: SCOPE }); + t.add_cleanup(_ => reg.unregister()); + let worker = reg.installing; + await wait_for_state(t, worker, 'activated'); + assert_not_equals(worker, null, 'worker is installing'); + + let {frame, nestedFrame, nestedFrameUrl} = + await loadNestedSharedStorageFrameInNewFrame({ + key: 'a', value: 'b', + hasSharedStorageWritableAttribute: true, + isSameOrigin: true, + }); + t.add_cleanup(function() { + frame.remove(); + }); + checkInterceptedUrls(worker, [ + { + "url": SAME_ORIGIN + SCOPE + INTERMEDIATE_FRAME_SUFFIX, + "mode": "navigate", + "SSWHeader": "null" + }, + { + "url": SAME_ORIGIN + "/resources/testharness.js", + "mode": "no-cors", + "SSWHeader": "null" + }, + { + "url": SAME_ORIGIN + nestedFrameUrl, + "mode": "navigate", + "SSWHeader": "null" + }, + ]); + await verifyKeyValueForOrigin('a', 'b', SAME_ORIGIN); + await deleteKeyForOrigin('a', SAME_ORIGIN); + }, 'test <iframe sharedstoragewritable src=[url]> via JS from service ' + + 'worker for same origin iframe'); + + promise_test(async t => { + const workerFramePromise = new Promise((resolve, reject) => { + let workerFrame = document.createElement('iframe'); + workerFrame.src = CROSS_ORIGIN + WORKER_FRAME; + workerFrame.id = 'worker_frame'; + workerFrame.onload = function() { + resolve(workerFrame); + }; + workerFrame.onerror = function() { + reject(new Error('Worker frame load failed')); + }; + t.add_cleanup(function() { + workerFrame.remove(); + }); + document.body.appendChild(workerFrame); + }); + let workerFrame = await workerFramePromise; + + const messagePromise = new Promise((resolve, reject) => { + let channel = new MessageChannel(); + channel.port1.onmessage = function(e) { + resolve(e.data); + }; + let message = { + script: SCRIPT, + scope: SCOPE, + port: channel.port2, + }; + document.getElementById('worker_frame').contentWindow + .postMessage(message, "*", + [channel.port2]); + }); + let {msg} = await messagePromise; + assert_equals(msg, 'test completed'); + }, 'test <iframe sharedstoragewritable src=[url]> via JS from service ' + + 'worker for cross origin iframe'); + </script> +</body>
diff --git a/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-img.tentative.https.sub.html b/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-img.tentative.https.sub.html index 9e7326d..6d48155 100644 --- a/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-img.tentative.https.sub.html +++ b/third_party/blink/web_tests/external/wpt/shared-storage/shared-storage-writable-service-worker-img.tentative.https.sub.html
@@ -7,23 +7,6 @@ <script src=/shared-storage/resources/util.js></script> <script src=/service-workers/service-worker/resources/test-helpers.sub.js></script> <script> - function getFetchedUrls(worker) { - return new Promise(function(resolve) { - var channel = new MessageChannel(); - channel.port1.onmessage = function(msg) { resolve(msg); }; - worker.postMessage({port: channel.port2}, [channel.port2]); - }); - } - - function checkInterceptedUrls(worker, expectedRequests) { - return getFetchedUrls(worker) - .then(function(msg) { - let actualRequests = msg.data.requests; - assert_equals(actualRequests.length, expectedRequests.length); - assert_equals(JSON.stringify(actualRequests), JSON.stringify(expectedRequests)); - }); - } - const SCOPE = '/shared-storage/resources/' + 'shared-storage-writable-fetch-request-fallback-to-network-iframe.https.html'; const SCRIPT = '/shared-storage/resources/' @@ -31,10 +14,11 @@ const SAME_ORIGIN = new URL("", location.href).origin; const CROSS_ORIGIN = 'https://{{domains[www]}}:{{ports[https][0]}}'; - async function loadSharedStorageImageFromNewFrame(data) { - let {test, key, value, hasSharedStorageWritableAttribute, isSameOrigin} = data; + async function loadSharedStorageImageInNewFrame(data) { + let {test, key, value, hasSharedStorageWritableAttribute, isSameOrigin} + = data; - const frame_promise = new Promise((resolve, reject) => { + const framePromise = new Promise((resolve, reject) => { let frame = document.createElement('iframe'); frame.src = SCOPE; frame.onload = function() { @@ -48,27 +32,30 @@ }); document.body.appendChild(frame); }); - let frame = await frame_promise; + let frame = await framePromise; const sameOriginImgSrc = `/shared-storage/resources/` + `shared-storage-writable-pixel.png?key=${key}&value=${value}`; - const imgSrc = isSameOrigin ? sameOriginImgSrc : CROSS_ORIGIN + sameOriginImgSrc; + const imgSrc = isSameOrigin ? + sameOriginImgSrc : + CROSS_ORIGIN + sameOriginImgSrc; return { loadedImage: frame.contentWindow.loadImage(imgSrc, - hasSharedStorageWritableAttribute), + hasSharedStorageWritableAttribute), imageUrl: imgSrc, }; } promise_test(async t => { await service_worker_unregister(t, SCOPE); - let reg = await navigator.serviceWorker.register(SCRIPT, { scope: SCOPE }); + let reg = await navigator.serviceWorker.register(SCRIPT, + { scope: SCOPE }); t.add_cleanup(_ => reg.unregister()); let worker = reg.installing; await wait_for_state(t, worker, 'activated'); assert_not_equals(worker, null, 'worker is installing'); - let {loadedImage, imageUrl} = await loadSharedStorageImageFromNewFrame({ + let {loadedImage, imageUrl} = await loadSharedStorageImageInNewFrame({ test: t, key: 'a', value: 'b', hasSharedStorageWritableAttribute: true, @@ -76,7 +63,11 @@ }); checkInterceptedUrls(worker, [ {"url": SAME_ORIGIN + SCOPE, "mode": "navigate", "SSWHeader": "null"}, - {"url": SAME_ORIGIN + "/resources/testharness.js", "mode": "no-cors", "SSWHeader": "null"}, + { + "url": SAME_ORIGIN + "/resources/testharness.js", + "mode": "no-cors", + "SSWHeader": "null" + }, {"url": SAME_ORIGIN + imageUrl, "mode": "no-cors", "SSWHeader": "null"}, ]); await verifyKeyValueForOrigin('a', 'b', SAME_ORIGIN); @@ -86,13 +77,14 @@ promise_test(async t => { await service_worker_unregister(t, SCOPE); - let reg = await navigator.serviceWorker.register(SCRIPT, { scope: SCOPE }); + let reg = await navigator.serviceWorker.register(SCRIPT, + { scope: SCOPE }); t.add_cleanup(_ => reg.unregister()); let worker = reg.installing; await wait_for_state(t, worker, 'activated'); assert_not_equals(worker, null, 'worker is installing'); - let {loadedImage, imageUrl} = await loadSharedStorageImageFromNewFrame({ + let {loadedImage, imageUrl} = await loadSharedStorageImageInNewFrame({ test: t, key: 'c', value: 'd', hasSharedStorageWritableAttribute: true, @@ -100,7 +92,11 @@ }); checkInterceptedUrls(worker, [ {"url": SAME_ORIGIN + SCOPE, "mode": "navigate", "SSWHeader": "null"}, - {"url": SAME_ORIGIN + "/resources/testharness.js", "mode": "no-cors", "SSWHeader": "null"}, + { + "url": SAME_ORIGIN + "/resources/testharness.js", + "mode": "no-cors", + "SSWHeader": "null" + }, {"url": imageUrl, "mode": "no-cors", "SSWHeader": "null"}, ]); await verifyKeyValueForOrigin('c', 'd', CROSS_ORIGIN);
diff --git a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-fragment-nosw.https-expected.txt b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-fragment-nosw.https-expected.txt index 2265f789..88e9473 100644 --- a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-fragment-nosw.https-expected.txt +++ b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-fragment-nosw.https-expected.txt
@@ -1,3 +1,4 @@ This is a testharness.js-based test. -Harness Error. harness_status.status = 1 , harness_status.message = TypeError: test_driver.set_rph_registration_mode is not a function +Harness Error. harness_status.status = 1 , harness_status.message = error: Action set_rph_registration_mode not implemented +[NOTRUN] registerProtocolHandler() and a handler with %s in the fragment (does not use a service worker) Harness: the test ran to completion.
diff --git a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-fragment.https-expected.txt b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-fragment.https-expected.txt index 2265f789..52929258 100644 --- a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-fragment.https-expected.txt +++ b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-fragment.https-expected.txt
@@ -1,3 +1,4 @@ This is a testharness.js-based test. -Harness Error. harness_status.status = 1 , harness_status.message = TypeError: test_driver.set_rph_registration_mode is not a function +Harness Error. harness_status.status = 1 , harness_status.message = error: Action set_rph_registration_mode not implemented +[NOTRUN] registerProtocolHandler() and a handler with %s in the fragment Harness: the test ran to completion.
diff --git a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-path.https-expected.txt b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-path.https-expected.txt index 2265f789..b73c2bd 100644 --- a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-path.https-expected.txt +++ b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-path.https-expected.txt
@@ -1,3 +1,4 @@ This is a testharness.js-based test. -Harness Error. harness_status.status = 1 , harness_status.message = TypeError: test_driver.set_rph_registration_mode is not a function +Harness Error. harness_status.status = 1 , harness_status.message = error: Action set_rph_registration_mode not implemented +[NOTRUN] registerProtocolHandler() and a handler with %s in the path Harness: the test ran to completion.
diff --git a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-query-nosw.https-expected.txt b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-query-nosw.https-expected.txt index 2265f789..71ed126 100644 --- a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-query-nosw.https-expected.txt +++ b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-query-nosw.https-expected.txt
@@ -1,3 +1,4 @@ This is a testharness.js-based test. -Harness Error. harness_status.status = 1 , harness_status.message = TypeError: test_driver.set_rph_registration_mode is not a function +Harness Error. harness_status.status = 1 , harness_status.message = error: Action set_rph_registration_mode not implemented +[NOTRUN] registerProtocolHandler() and a handler with %s in the query (does not use a service worker) Harness: the test ran to completion.
diff --git a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-query.https-expected.txt b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-query.https-expected.txt index 2265f789..813f466c 100644 --- a/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-query.https-expected.txt +++ b/third_party/blink/web_tests/platform/linux-chrome/external/wpt/html/webappapis/system-state-and-capabilities/the-navigator-object/protocol-handler-query.https-expected.txt
@@ -1,3 +1,4 @@ This is a testharness.js-based test. -Harness Error. harness_status.status = 1 , harness_status.message = TypeError: test_driver.set_rph_registration_mode is not a function +Harness Error. harness_status.status = 1 , harness_status.message = error: Action set_rph_registration_mode not implemented +[NOTRUN] registerProtocolHandler() and a handler with %s in the query Harness: the test ran to completion.
diff --git a/third_party/blink/web_tests/resources/testdriver.js b/third_party/blink/web_tests/resources/testdriver.js index 93419c6..70c7991 100644 --- a/third_party/blink/web_tests/resources/testdriver.js +++ b/third_party/blink/web_tests/resources/testdriver.js
@@ -647,7 +647,7 @@ * * This function places `Secure Payment * Confirmation <https://w3c.github.io/secure-payment-confirmation>`_ into - * an automated 'autoaccept' or 'autoreject' mode, to allow testing + * an automated 'autoAccept' or 'autoReject' mode, to allow testing * without user interaction with the transaction UX prompt. * * Matches the `Set SPC Transaction Mode @@ -667,8 +667,8 @@ * @param {String} mode - The `transaction mode * <https://w3c.github.io/secure-payment-confirmation/#enumdef-transactionautomationmode>`_ * to set. Must be one of "``none``", - * "``autoaccept``", or - * "``autoreject``". + * "``autoAccept``", or + * "``autoReject``". * @param {WindowProxy} context - Browsing context in which * to run the call, or null for the current * browsing context. @@ -681,6 +681,42 @@ }, /** + * Sets the current registration automation mode for Register Protocol Handlers. + * + * This function places `Register Protocol Handlers + * <https://html.spec.whatwg.org/multipage/system-state.html#custom-handlers>`_ into + * an automated 'autoAccept' or 'autoReject' mode, to allow testing + * without user interaction with the transaction UX prompt. + * + * Matches the `Set Register Protocol Handler Mode + * <https://html.spec.whatwg.org/multipage/system-state.html#set-rph-registration-mode>`_ + * WebDriver command. + * + * @example + * await test_driver.set_rph_registration_mode("autoAccept"); + * test.add_cleanup(() => { + * return test_driver.set_rph_registration_mode("none"); + * }); + * + * navigator.registerProtocolHandler('web+soup', 'soup?url=%s'); + * + * @param {String} mode - The `registration mode + * <https://html.spec.whatwg.org/multipage/system-state.html#registerprotocolhandler()-automation-mode>`_ + * to set. Must be one of "``none``", + * "``autoAccept``", or + * "``autoReject``". + * @param {WindowProxy} context - Browsing context in which + * to run the call, or null for the current + * browsing context. + * + * @returns {Promise} Fulfilled after the transaction mode has been set, + * or rejected if setting the mode fails. + */ + set_rph_registration_mode: function(mode, context=null) { + return window.test_driver_internal.set_rph_registration_mode(mode, context); + }, + + /** * Cancels the Federated Credential Management dialog * * Matches the `Cancel dialog @@ -699,6 +735,25 @@ }, /** + * Clicks a button on the Federated Credential Management dialog + * + * Matches the `Click dialog button + * <https://fedidcg.github.io/FedCM/#webdriver-clickdialogbutton>`_ + * WebDriver command. + * + * @param {String} dialog_button - String enum representing the dialog button to click. + * @param {WindowProxy} context - Browsing context in which + * to run the call, or null for the current + * browsing context. + * + * @returns {Promise} Fulfilled after the button is clicked, + * or rejected in case the WebDriver command errors + */ + click_fedcm_dialog_button: function(dialog_button, context=null) { + return window.test_driver_internal.click_fedcm_dialog_button(dialog_button, context); + }, + + /** * Selects an account from the Federated Credential Management dialog * * Matches the `Select account @@ -806,6 +861,149 @@ */ reset_fedcm_cooldown: function(context=null) { return window.test_driver_internal.reset_fedcm_cooldown(context); + }, + + /** + * Creates a virtual sensor for use with the Generic Sensors APIs. + * + * Matches the `Create Virtual Sensor + * <https://w3c.github.io/sensors/#create-virtual-sensor-command>`_ + * WebDriver command. + * + * Once created, a virtual sensor is available to all navigables under + * the same top-level traversable (i.e. all frames in the same page, + * regardless of origin). + * + * @param {String} sensor_type - A `virtual sensor type + * <https://w3c.github.io/sensors/#virtual-sensor-metadata-virtual-sensor-type>`_ + * such as "accelerometer". + * @param {Object} [sensor_params={}] - Optional parameters described + * in `Create Virtual Sensor + * <https://w3c.github.io/sensors/#create-virtual-sensor-command>`_. + * @param {WindowProxy} [context=null] - Browsing context in which to + * run the call, or null for the + * current browsing context. + * + * @returns {Promise} Fulfilled when virtual sensor is created. + * Rejected in case the WebDriver command errors out + * (including if a virtual sensor of the same type + * already exists). + */ + create_virtual_sensor: function(sensor_type, sensor_params={}, context=null) { + return window.test_driver_internal.create_virtual_sensor(sensor_type, sensor_params, context); + }, + + /** + * Causes a virtual sensor to report a new reading to any connected + * platform sensor. + * + * Matches the `Update Virtual Sensor Reading + * <https://w3c.github.io/sensors/#update-virtual-sensor-reading-command>`_ + * WebDriver command. + * + * Note: The ``Promise`` it returns may fulfill before or after a + * "reading" event is fired. When using + * :js:func:`EventWatcher.wait_for`, it is necessary to take this into + * account: + * + * Note: New values may also be discarded due to the checks in `update + * latest reading + * <https://w3c.github.io/sensors/#update-latest-reading>`_. + * + * @example + * // Avoid races between EventWatcher and update_virtual_sensor(). + * // This assumes you are sure this reading will be processed (see + * // the example below otherwise). + * const reading = { x: 1, y: 2, z: 3 }; + * await Promise.all([ + * test_driver.update_virtual_sensor('gyroscope', reading), + * watcher.wait_for('reading') + * ]); + * + * @example + * // Do not wait forever if you are not sure the reading will be + * // processed. + * const readingPromise = watcher.wait_for('reading'); + * const timeoutPromise = new Promise(resolve => { + * t.step_timeout(() => resolve('TIMEOUT', 3000)) + * }); + * + * const reading = { x: 1, y: 2, z: 3 }; + * await test_driver.update_virtual_sensor('gyroscope', 'reading'); + * + * const value = + * await Promise.race([timeoutPromise, readingPromise]); + * if (value !== 'TIMEOUT') { + * // Do something. The "reading" event was fired. + * } + * + * @param {String} sensor_type - A `virtual sensor type + * <https://w3c.github.io/sensors/#virtual-sensor-metadata-virtual-sensor-type>`_ + * such as "accelerometer". + * @param {Object} reading - An Object describing a reading in a format + * dependent on ``sensor_type`` (e.g. ``{x: + * 1, y: 2, z: 3}`` or ``{ illuminance: 42 + * }``). + * @param {WindowProxy} [context=null] - Browsing context in which to + * run the call, or null for the + * current browsing context. + * + * @returns {Promise} Fulfilled after the reading update reaches the + * virtual sensor. Rejected in case the WebDriver + * command errors out (including if a virtual sensor + * of the given type does not exist). + */ + update_virtual_sensor: function(sensor_type, reading, context=null) { + return window.test_driver_internal.update_virtual_sensor(sensor_type, reading, context); + }, + + /** + * Triggers the removal of a virtual sensor if it exists. + * + * Matches the `Delete Virtual Sensor + * <https://w3c.github.io/sensors/#delete-virtual-sensor-command>`_ + * WebDriver command. + * + * @param {String} sensor_type - A `virtual sensor type + * <https://w3c.github.io/sensors/#virtual-sensor-metadata-virtual-sensor-type>`_ + * such as "accelerometer". + * @param {WindowProxy} [context=null] - Browsing context in which to + * run the call, or null for the + * current browsing context. + * + * @returns {Promise} Fulfilled after the virtual sensor has been + * removed or if a sensor of the given type does not + * exist. Rejected in case the WebDriver command + * errors out. + + */ + remove_virtual_sensor: function(sensor_type, context=null) { + return window.test_driver_internal.remove_virtual_sensor(sensor_type, context); + }, + + /** + * Returns information about a virtual sensor. + * + * Matches the `Get Virtual Sensor Information + * <https://w3c.github.io/sensors/#get-virtual-sensor-information-command>`_ + * WebDriver command. + * + * @param {String} sensor_type - A `virtual sensor type + * <https://w3c.github.io/sensors/#virtual-sensor-metadata-virtual-sensor-type>`_ + * such as "accelerometer". + * @param {WindowProxy} [context=null] - Browsing context in which to + * run the call, or null for the + * current browsing context. + * + * @returns {Promise} Fulfilled with an Object with the properties + * described in `Get Virtual Sensor Information + * <https://w3c.github.io/sensors/#get-virtual-sensor-information-command>`_. + * Rejected in case the WebDriver command errors out + * (including if a virtual sensor of the given type + * does not exist). + */ + get_virtual_sensor_information: function(sensor_type, context=null) { + return window.test_driver_internal.get_virtual_sensor_information(sensor_type, context); } }; @@ -932,10 +1130,18 @@ throw new Error("set_spc_transaction_mode() is not implemented by testdriver-vendor.js"); }, + set_rph_registration_mode: function(mode, context=null) { + return Promise.reject(new Error("unimplemented")); + }, + async cancel_fedcm_dialog(context=null) { throw new Error("cancel_fedcm_dialog() is not implemented by testdriver-vendor.js"); }, + async click_fedcm_dialog_button(dialog_button, context=null) { + throw new Error("click_fedcm_dialog_button() is not implemented by testdriver-vendor.js"); + }, + async select_fedcm_account(account_index, context=null) { throw new Error("select_fedcm_account() is not implemented by testdriver-vendor.js"); }, @@ -958,6 +1164,22 @@ async reset_fedcm_cooldown(context=null) { throw new Error("reset_fedcm_cooldown() is not implemented by testdriver-vendor.js"); + }, + + async create_virtual_sensor(sensor_type, sensor_params, context=null) { + throw new Error("create_virtual_sensor() is not implemented by testdriver-vendor.js"); + }, + + async update_virtual_sensor(sensor_type, reading, context=null) { + throw new Error("update_virtual_sensor() is not implemented by testdriver-vendor.js"); + }, + + async remove_virtual_sensor(sensor_type, context=null) { + throw new Error("remove_virtual_sensor() is not implemented by testdriver-vendor.js"); + }, + + async get_virtual_sensor_information(sensor_type, context=null) { + throw new Error("get_virtual_sensor_information() is not implemented by testdriver-vendor.js"); } }; })();
diff --git a/third_party/perfetto b/third_party/perfetto index ff3b631..0c15215 160000 --- a/third_party/perfetto +++ b/third_party/perfetto
@@ -1 +1 @@ -Subproject commit ff3b6318208109a97dc91f5f653edfca466d3cca +Subproject commit 0c152157409b6d7ba49a83eeeab1a358a1098d20
diff --git a/third_party/skia b/third_party/skia index 053490e..f82251f 160000 --- a/third_party/skia +++ b/third_party/skia
@@ -1 +1 @@ -Subproject commit 053490edfa703f3433d97a299ee80f2acc93de71 +Subproject commit f82251f0091c52eee7125c06786d3c7e72c15327
diff --git a/third_party/wpt_tools/README.chromium b/third_party/wpt_tools/README.chromium index 3828fac6..f6cc35a 100644 --- a/third_party/wpt_tools/README.chromium +++ b/third_party/wpt_tools/README.chromium
@@ -1,7 +1,7 @@ Name: web-platform-tests - Test Suites for Web Platform specifications Short Name: wpt URL: https://github.com/web-platform-tests/wpt/ -Version: c359284745e2a2f6c44af320d1d6c43ce51f25bc +Version: a50aec6c90d6ce28629fa4eb5cbeba0d1d65c53b License: LICENSES FOR W3C TEST SUITES (https://www.w3.org/Consortium/Legal/2008/03-bsd-license.html) Security Critical: no Shipped: no
diff --git a/third_party/wpt_tools/WPTIncludeList b/third_party/wpt_tools/WPTIncludeList index 33415ff..cd318ba 100644 --- a/third_party/wpt_tools/WPTIncludeList +++ b/third_party/wpt_tools/WPTIncludeList
@@ -283,6 +283,7 @@ ./tools/webdriver/webdriver/bidi/modules/script.py ./tools/webdriver/webdriver/bidi/modules/session.py ./tools/webdriver/webdriver/bidi/transport.py +./tools/webdriver/webdriver/bidi/undefined.py ./tools/webdriver/webdriver/client.py ./tools/webdriver/webdriver/error.py ./tools/webdriver/webdriver/protocol.py
diff --git a/third_party/wpt_tools/wpt/resources/testdriver.js b/third_party/wpt_tools/wpt/resources/testdriver.js index 0327e17..70c7991 100644 --- a/third_party/wpt_tools/wpt/resources/testdriver.js +++ b/third_party/wpt_tools/wpt/resources/testdriver.js
@@ -647,7 +647,7 @@ * * This function places `Secure Payment * Confirmation <https://w3c.github.io/secure-payment-confirmation>`_ into - * an automated 'autoaccept' or 'autoreject' mode, to allow testing + * an automated 'autoAccept' or 'autoReject' mode, to allow testing * without user interaction with the transaction UX prompt. * * Matches the `Set SPC Transaction Mode @@ -667,8 +667,8 @@ * @param {String} mode - The `transaction mode * <https://w3c.github.io/secure-payment-confirmation/#enumdef-transactionautomationmode>`_ * to set. Must be one of "``none``", - * "``autoaccept``", or - * "``autoreject``". + * "``autoAccept``", or + * "``autoReject``". * @param {WindowProxy} context - Browsing context in which * to run the call, or null for the current * browsing context. @@ -681,6 +681,42 @@ }, /** + * Sets the current registration automation mode for Register Protocol Handlers. + * + * This function places `Register Protocol Handlers + * <https://html.spec.whatwg.org/multipage/system-state.html#custom-handlers>`_ into + * an automated 'autoAccept' or 'autoReject' mode, to allow testing + * without user interaction with the transaction UX prompt. + * + * Matches the `Set Register Protocol Handler Mode + * <https://html.spec.whatwg.org/multipage/system-state.html#set-rph-registration-mode>`_ + * WebDriver command. + * + * @example + * await test_driver.set_rph_registration_mode("autoAccept"); + * test.add_cleanup(() => { + * return test_driver.set_rph_registration_mode("none"); + * }); + * + * navigator.registerProtocolHandler('web+soup', 'soup?url=%s'); + * + * @param {String} mode - The `registration mode + * <https://html.spec.whatwg.org/multipage/system-state.html#registerprotocolhandler()-automation-mode>`_ + * to set. Must be one of "``none``", + * "``autoAccept``", or + * "``autoReject``". + * @param {WindowProxy} context - Browsing context in which + * to run the call, or null for the current + * browsing context. + * + * @returns {Promise} Fulfilled after the transaction mode has been set, + * or rejected if setting the mode fails. + */ + set_rph_registration_mode: function(mode, context=null) { + return window.test_driver_internal.set_rph_registration_mode(mode, context); + }, + + /** * Cancels the Federated Credential Management dialog * * Matches the `Cancel dialog @@ -699,21 +735,22 @@ }, /** - * Accepts a FedCM "Confirm IDP login" dialog. + * Clicks a button on the Federated Credential Management dialog * - * Matches the `Confirm IDP Login - * <https://fedidcg.github.io/FedCM/#webdriver-confirmidplogin>`_ + * Matches the `Click dialog button + * <https://fedidcg.github.io/FedCM/#webdriver-clickdialogbutton>`_ * WebDriver command. * + * @param {String} dialog_button - String enum representing the dialog button to click. * @param {WindowProxy} context - Browsing context in which * to run the call, or null for the current * browsing context. * - * @returns {Promise} Fulfilled after the IDP login has started, + * @returns {Promise} Fulfilled after the button is clicked, * or rejected in case the WebDriver command errors */ - confirm_idp_login: function(context=null) { - return window.test_driver_internal.confirm_idp_login(context); + click_fedcm_dialog_button: function(dialog_button, context=null) { + return window.test_driver_internal.click_fedcm_dialog_button(dialog_button, context); }, /** @@ -1093,12 +1130,16 @@ throw new Error("set_spc_transaction_mode() is not implemented by testdriver-vendor.js"); }, + set_rph_registration_mode: function(mode, context=null) { + return Promise.reject(new Error("unimplemented")); + }, + async cancel_fedcm_dialog(context=null) { throw new Error("cancel_fedcm_dialog() is not implemented by testdriver-vendor.js"); }, - async confirm_idp_login(context=null) { - throw new Error("confirm_idp_login() is not implemented by testdriver-vendor.js"); + async click_fedcm_dialog_button(dialog_button, context=null) { + throw new Error("click_fedcm_dialog_button() is not implemented by testdriver-vendor.js"); }, async select_fedcm_account(account_index, context=null) {
diff --git a/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/error.py b/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/error.py index 7b688dd1..75505ea 100644 --- a/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/error.py +++ b/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/error.py
@@ -63,6 +63,10 @@ error_code = "no such handle" +class NoSuchHistoryEntryException(BidiException): + error_code = "no such history entry" + + class NoSuchNodeException(BidiException): error_code = "no such node"
diff --git a/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/modules/_module.py b/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/modules/_module.py index 060010b..45e2f1c 100644 --- a/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/modules/_module.py +++ b/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/modules/_module.py
@@ -9,6 +9,8 @@ TYPE_CHECKING, ) +from ..undefined import UNDEFINED + if TYPE_CHECKING: from ..client import BidiSession @@ -49,7 +51,8 @@ self.params_fn = fn self.result_fn: Optional[Callable[..., Any]] = None - def result(self, fn: Callable[[Any, MutableMapping[str, Any]], Any]) -> None: + def result(self, fn: Callable[[Any, MutableMapping[str, Any]], + Any]) -> None: self.result_fn = fn def __set_name__(self, owner: Any, name: str) -> None: @@ -61,7 +64,7 @@ @functools.wraps(params_fn) async def inner(self: Any, **kwargs: Any) -> Any: raw_result = kwargs.pop("raw_result", False) - params = params_fn(self, **kwargs) + params = remove_undefined(params_fn(self, **kwargs)) # Convert the classname and the method name to a bidi command name mod_name = owner.__name__[0].lower() + owner.__name__[1:] @@ -85,6 +88,7 @@ class BidiModule: + def __init__(self, session: "BidiSession"): self.session = session @@ -96,3 +100,7 @@ for i in range(1, len(parts)): parts[i] = parts[i].title() return "".join(parts) + + +def remove_undefined(obj: Mapping[str, Any]) -> Mapping[str, Any]: + return {key: value for key, value in obj.items() if value != UNDEFINED}
diff --git a/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/modules/browsing_context.py b/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/modules/browsing_context.py index 2938be2e..e0371a7 100644 --- a/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/modules/browsing_context.py +++ b/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/modules/browsing_context.py
@@ -1,19 +1,16 @@ import base64 +from enum import Enum from typing import Any, Dict, List, Mapping, MutableMapping, Optional, Union from ._module import BidiModule, command +from ..undefined import UNDEFINED, Undefined class ElementOptions(Dict[str, Any]): - def __init__( - self, element: Mapping[str, Any], scroll_into_view: Optional[bool] = None - ): + def __init__(self, element: Mapping[str, Any]): self["type"] = "element" self["element"] = element - if scroll_into_view is not None: - self["scrollIntoView"] = scroll_into_view - class BoxOptions(Dict[str, Any]): def __init__(self, x: float, y: float, width: float, height: float): @@ -27,6 +24,19 @@ ClipOptions = Union[ElementOptions, BoxOptions] +class OriginOptions(Enum): + DOCUMENT = "document" + VIEWPORT = "viewport" + + +class FormatOptions(Dict[str, Any]): + def __init__(self, type: str, quality: Optional[float] = None): + dict.__init__(self, type=type) + + if quality is not None: + self["quality"] = quality + + class BrowsingContext(BidiModule): @command def activate(self, context: str) -> Mapping[str, Any]: @@ -34,12 +44,20 @@ @command def capture_screenshot( - self, context: str, clip: Optional[ClipOptions] = None + self, + context: str, + clip: Optional[ClipOptions] = None, + origin: Optional[OriginOptions] = None, + format: Optional[FormatOptions] = None, ) -> Mapping[str, Any]: params: MutableMapping[str, Any] = {"context": context} + if format is not None: + params["format"] = format if clip is not None: params["clip"] = clip + if origin is not None: + params["origin"] = origin return params @@ -180,16 +198,20 @@ @command def set_viewport(self, context: str, - viewport: Optional[Mapping[str, Any]] = None, - device_pixel_ratio: Optional[float] = None) -> Mapping[str, Any]: + viewport: Union[Optional[Mapping[str, Any]], Undefined] = UNDEFINED, + device_pixel_ratio: Union[Optional[float], Undefined] = UNDEFINED) -> Mapping[str, Any]: params: MutableMapping[str, Any] = { "context": context, } - if viewport is not None: + if viewport is not UNDEFINED: params["viewport"] = viewport - if device_pixel_ratio is not None: + if device_pixel_ratio is not UNDEFINED: params["devicePixelRatio"] = device_pixel_ratio return params + + @command + def traverse_history(self, context: str, delta: int) -> Mapping[str, Any]: + return {"context": context, "delta": delta}
diff --git a/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/undefined.py b/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/undefined.py new file mode 100644 index 0000000..8dad6e1 --- /dev/null +++ b/third_party/wpt_tools/wpt/tools/webdriver/webdriver/bidi/undefined.py
@@ -0,0 +1,6 @@ +class Undefined: + def __init__(self) -> None: + raise RuntimeError('Import UNDEFINED instead.') + + +UNDEFINED = Undefined.__new__(Undefined)
diff --git a/third_party/wpt_tools/wpt/tools/wpt/android.py b/third_party/wpt_tools/wpt/tools/wpt/android.py index c99acf3..1061181 100644 --- a/third_party/wpt_tools/wpt/tools/wpt/android.py +++ b/third_party/wpt_tools/wpt/tools/wpt/android.py
@@ -15,7 +15,7 @@ wpt_root = os.path.abspath(os.path.join(here, os.pardir, os.pardir)) -NDK_VERSION = "r23c" +NDK_VERSION = "r25c" CMDLINE_TOOLS_VERSION_STRING = "11.0" CMDLINE_TOOLS_VERSION = "9644228"
diff --git a/third_party/wpt_tools/wpt/tools/wpt/run.py b/third_party/wpt_tools/wpt/tools/wpt/run.py index c5012af1..4297c392 100644 --- a/third_party/wpt_tools/wpt/tools/wpt/run.py +++ b/third_party/wpt_tools/wpt/tools/wpt/run.py
@@ -395,22 +395,23 @@ device_serial=device_serial, prompt=kwargs["prompt"]) - if "ADB_PATH" not in os.environ: - adb_path = os.path.join(android.get_paths(None)["sdk"], - "platform-tools", - "adb") - os.environ["ADB_PATH"] = adb_path - adb_path = os.environ["ADB_PATH"] + if kwargs["adb_binary"] is None: + if "ADB_PATH" not in os.environ: + adb_path = os.path.join(android.get_paths(None)["sdk"], + "platform-tools", + "adb") + os.environ["ADB_PATH"] = adb_path + kwargs["adb_binary"] = os.environ["ADB_PATH"] - self._logcat = AndroidLogcat(adb_path, base_path=kwargs["logcat_dir"]) + self._logcat = AndroidLogcat(kwargs["adb_binary"], base_path=kwargs["logcat_dir"]) for device_serial in kwargs["device_serial"]: - device = mozdevice.ADBDeviceFactory(adb=adb_path, + device = mozdevice.ADBDeviceFactory(adb=kwargs["adb_binary"], device=device_serial) self._logcat.start(device_serial) if self.browser.apk_path: device.uninstall_app(app) - device.install_app(self.browser.apk_path) + device.install_app(self.browser.apk_path, timeout=600) elif not device.is_app_installed(app): raise WptrunError("app %s not installed on device %s" % (app, device_serial))
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/edge.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/edge.py index c6936e7..5b49545 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/edge.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/edge.py
@@ -95,7 +95,7 @@ return [self.webdriver_binary, f"--port={self.port}"] + self.webdriver_args -def run_info_extras(**kwargs): +def run_info_extras(logger, **kwargs): osReleaseCommand = r"(Get-ItemProperty 'HKLM:\Software\Microsoft\Windows NT\CurrentVersion').ReleaseId" osBuildCommand = r"(Get-ItemProperty 'HKLM:\Software\Microsoft\Windows NT\CurrentVersion').BuildLabEx" try:
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/epiphany.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/epiphany.py index 912173a..562b2dc 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/epiphany.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/epiphany.py
@@ -71,5 +71,5 @@ return {} -def run_info_extras(**kwargs): +def run_info_extras(logger, **kwargs): return {"webkit_port": "gtk"}
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/firefox.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/firefox.py index 72f6c85..0cb5ff5d 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/firefox.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/firefox.py
@@ -193,7 +193,7 @@ "supports_debugger": True} -def run_info_extras(**kwargs): +def run_info_extras(logger, **kwargs): def get_bool_pref_if_exists(pref): for key, value in kwargs.get('extra_prefs', []): @@ -213,7 +213,8 @@ "fission": not kwargs.get("disable_fission"), "sessionHistoryInParent": (not kwargs.get("disable_fission") or not get_bool_pref("fission.disableSessionHistoryInParent")), - "swgl": get_bool_pref("gfx.webrender.software")} + "swgl": get_bool_pref("gfx.webrender.software"), + "privateBrowsing": (kwargs["tags"] is not None and ("privatebrowsing" in kwargs["tags"]))} rv.update(run_info_browser_version(**kwargs)) @@ -567,6 +568,7 @@ if self.lsan_handler: self.lsan_handler.process() if self.leak_report_file is not None: + processed_files = None if not clean_shutdown: # If we didn't get a clean shutdown there probably isn't a leak report file self.logger.warning("Firefox didn't exit cleanly, not processing leak logs") @@ -575,7 +577,7 @@ # content process crashed and in that case we don't want the test to fail. # Ideally we would record which content process crashed and just skip those. self.logger.info("PROCESS LEAKS %s" % self.leak_report_file) - mozleak.process_leak_log( + processed_files = mozleak.process_leak_log( self.leak_report_file, leak_thresholds=self.mozleak_thresholds, ignore_missing_leaks=["tab", "gmplugin"], @@ -583,6 +585,11 @@ stack_fixer=self.stack_fixer, scope=self.group_metadata.get("scope"), allowed=self.mozleak_allowed) + if processed_files: + for path in processed_files: + if os.path.exists(path): + os.unlink(path) + # Fallback for older versions of mozleak, or if we didn't shutdown cleanly if os.path.exists(self.leak_report_file): os.unlink(self.leak_report_file)
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/firefox_android.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/firefox_android.py index 1937d97..6ebe4a6 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/firefox_android.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/firefox_android.py
@@ -1,6 +1,8 @@ # mypy: allow-untyped-defs import os +import subprocess +import re from mozrunner import FennecEmulatorRunner, get_app_context @@ -14,6 +16,7 @@ from .base import (Browser, ExecutorBrowser) from .firefox import (get_timeout_multiplier, # noqa: F401 + run_info_browser_version, run_info_extras as fx_run_info_extras, update_properties, # noqa: F401 executor_kwargs as fx_executor_kwargs, # noqa: F401 @@ -87,14 +90,45 @@ return [] -def run_info_extras(**kwargs): - rv = fx_run_info_extras(**kwargs) +def run_info_extras(logger, **kwargs): + rv = fx_run_info_extras(logger, **kwargs) package = kwargs["package_name"] rv.update({"e10s": True if package is not None and "geckoview" in package else False, "headless": False}) + + if kwargs["browser_version"] is None: + rv.update(run_info_browser_version(**kwargs)) + + if rv.get("browser_version") is None: + # If we didn't get the browser version from the apk, try to get it from adb dumpsys + rv["browser_version"] = get_package_browser_version(logger, + kwargs["adb_binary"], + kwargs["package_name"]) + return rv +def get_package_browser_version(logger, adb_binary, package_name): + if adb_binary is None: + logger.warning("Couldn't run adb to get Firefox Android version number") + return None + try: + completed = subprocess.run([adb_binary, "shell", "dumpsys", "package", package_name], + check=True, + capture_output=True, + encoding="utf8") + except subprocess.CalledProcessError as e: + logger.warning(f"adb failed with return code {e.returncode}\nCaptured stderr:\n{e.stderr}") + return None + + version_name_re = re.compile(r"^\s+versionName=(.*)") + for line in completed.stdout.splitlines(): + m = version_name_re.match(line) + if m is not None: + return m.group(1) + logger.warning("Failed to find versionName property in dumpsys output") + + def env_options(): return {"server_host": "127.0.0.1", "supports_debugger": True}
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/safari.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/safari.py index 40f5f548..44d289c7 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/safari.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/safari.py
@@ -69,7 +69,7 @@ return {} -def run_info_extras(**kwargs): +def run_info_extras(logger, **kwargs): webdriver_binary = kwargs["webdriver_binary"] rv = {}
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/webkit.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/webkit.py index cecfbe4e..a3e8d13 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/webkit.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/webkit.py
@@ -72,7 +72,7 @@ return {} -def run_info_extras(**kwargs): +def run_info_extras(logger, **kwargs): return {"webkit_port": kwargs["webkit_port"]}
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/webkitgtk_minibrowser.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/webkitgtk_minibrowser.py index 355ffe35..29a9563 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/webkitgtk_minibrowser.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/browsers/webkitgtk_minibrowser.py
@@ -76,7 +76,7 @@ return {} -def run_info_extras(**kwargs): +def run_info_extras(logger, **kwargs): return {"webkit_port": "gtk"}
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/actions.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/actions.py index d987553..f698b92d 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/actions.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/actions.py
@@ -277,6 +277,18 @@ self.logger.debug("Setting SPC transaction mode to %s" % mode) return self.protocol.spc_transactions.set_spc_transaction_mode(mode) +class SetRPHRegistrationModeAction: + name = "set_rph_registration_mode" + + def __init__(self, logger, protocol): + self.logger = logger + self.protocol = protocol + + def __call__(self, payload): + mode = payload["mode"] + self.logger.debug("Setting RPH registration mode to %s" % mode) + return self.protocol.rph_registrations.set_rph_registration_mode(mode) + class CancelFedCMDialogAction: name = "cancel_fedcm_dialog" @@ -442,6 +454,7 @@ RemoveAllCredentialsAction, SetUserVerifiedAction, SetSPCTransactionModeAction, + SetRPHRegistrationModeAction, CancelFedCMDialogAction, ConfirmIDPLoginAction, SelectFedCMAccountAction,
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/base.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/base.py index e89b57b57..7ef9c9b 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/base.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/base.py
@@ -760,7 +760,10 @@ except AttributeError as e: # If we fail to get an attribute from the protocol presumably that's a # ProtocolPart we don't implement - if getattr(e, "obj") == self.protocol: + # AttributeError got an obj property in Python 3.10, for older versions we + # fall back to looking at the error message. + if ((hasattr(e, "obj") and getattr(e, "obj") == self.protocol) or + "'{self.protocol.__class__.__name__}' has no attribute" in str(e)): raise NotImplementedError from e except self.unimplemented_exc: self.logger.warning("Action %s not implemented" % action)
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/executormarionette.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/executormarionette.py index 1f183f1..8d60f1e 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/executormarionette.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/executormarionette.py
@@ -1037,8 +1037,14 @@ self.implementation_kwargs = {} if reftest_internal: self.implementation_kwargs["screenshot"] = reftest_screenshot - self.implementation_kwargs["chrome_scope"] = (browser_version is not None and - int(browser_version.split(".")[0]) < 82) + self.implementation_kwargs["chrome_scope"] = False + # Older versions of Gecko require switching to chrome scope to run refests + if browser_version is not None: + try: + major_version = int(browser_version.split(".")[0]) + self.implementation_kwargs["chrome_scope"] = major_version < 82 + except ValueError: + pass self.close_after_done = close_after_done self.has_window = False self.original_pref_values = {}
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/executorwebdriver.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/executorwebdriver.py index e3760b8..8b61f16c 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/executorwebdriver.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/executorwebdriver.py
@@ -32,6 +32,7 @@ WindowProtocolPart, DebugProtocolPart, SPCTransactionsProtocolPart, + RPHRegistrationsProtocolPart, FedCMProtocolPart, VirtualSensorProtocolPart, merge_dicts) @@ -363,6 +364,13 @@ body = {"mode": mode} return self.webdriver.send_session_command("POST", "secure-payment-confirmation/set-mode", body) +class WebDriverRPHRegistrationsProtocolPart(RPHRegistrationsProtocolPart): + def setup(self): + self.webdriver = self.parent.webdriver + + def set_rph_registration_mode(self, mode): + body = {"mode": mode} + return self.webdriver.send_session_command("POST", "custom-handlers/set-mode", body) class WebDriverFedCMProtocolPart(FedCMProtocolPart): def setup(self): @@ -432,6 +440,7 @@ WebDriverSetPermissionProtocolPart, WebDriverVirtualAuthenticatorProtocolPart, WebDriverSPCTransactionsProtocolPart, + WebDriverRPHRegistrationsProtocolPart, WebDriverFedCMProtocolPart, WebDriverDebugProtocolPart, WebDriverVirtualSensorPart]
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/protocol.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/protocol.py index cac25e4..2bae86c 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/protocol.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/executors/protocol.py
@@ -616,6 +616,18 @@ :param str mode: The automation mode to set""" pass +class RPHRegistrationsProtocolPart(ProtocolPart): + """Protocol part for Custom Handlers registrations""" + __metaclass__ = ABCMeta + + name = "rph_registrations" + + @abstractmethod + def set_rph_registration_mode(self, mode): + """Set the RPH registration automation mode + + :param str mode: The automation mode to set""" + pass class FedCMProtocolPart(ProtocolPart): """Protocol part for Federated Credential Management"""
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/products.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/products.py index 5b26557..c81396f 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/products.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/products.py
@@ -31,7 +31,7 @@ self.env_options = getattr(module, data["env_options"])() self.get_env_extras = getattr(module, data["env_extras"]) self.run_info_extras = (getattr(module, data["run_info_extras"]) - if "run_info_extras" in data else lambda **kwargs:{}) + if "run_info_extras" in data else lambda product, **kwargs:{}) self.get_timeout_multiplier = getattr(module, data["timeout_multiplier"]) self.executor_classes = {}
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/testdriver-extra.js b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/testdriver-extra.js index 29c6615..4cb54626 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/testdriver-extra.js +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/testdriver-extra.js
@@ -269,6 +269,10 @@ return create_action("set_spc_transaction_mode", {mode, context}); }; + window.test_driver_internal.set_rph_registration_mode = function(mode, context = null) { + return create_action("set_rph_registration_mode", {mode, context}); + }; + window.test_driver_internal.cancel_fedcm_dialog = function(context = null) { return create_action("cancel_fedcm_dialog", {context}); };
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/testrunner.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/testrunner.py index f29e902..2d81cab 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/testrunner.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/testrunner.py
@@ -640,7 +640,7 @@ self.recording.set(["testrunner", "test"] + self.state.test.id.split("/")[1:]) self.logger.test_start(self.state.test.id, subsuite=self.state.subsuite) if self.rerun > 1: - self.logger.info("Run %d/%d" % (self.run_count, self.rerun)) + self.logger.info(f"Run {self.run_count + 1}/{self.rerun}") self.send_message("reset") self.run_count += 1 if self.debug_info is None:
diff --git a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/wptrunner.py b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/wptrunner.py index b9e51901..d65369b 100644 --- a/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/wptrunner.py +++ b/third_party/wpt_tools/wpt/tools/wptrunner/wptrunner/wptrunner.py
@@ -52,7 +52,7 @@ def get_loader(test_paths: wptcommandline.TestPaths, product: products.Product, **kwargs: Any) -> Tuple[testloader.TestQueueBuilder, testloader.TestLoader]: - run_info_extras = product.run_info_extras(**kwargs) + run_info_extras = product.run_info_extras(logger, **kwargs) base_run_info = wpttest.get_run_info(kwargs["run_info"], product.name, browser_version=kwargs.get("browser_version"),
diff --git a/third_party/wpt_tools/wpt/websockets/handlers/sleep_10_v13_wsh.py b/third_party/wpt_tools/wpt/websockets/handlers/sleep_10_v13_wsh.py index b0f1dde..bdef2f2 100755 --- a/third_party/wpt_tools/wpt/websockets/handlers/sleep_10_v13_wsh.py +++ b/third_party/wpt_tools/wpt/websockets/handlers/sleep_10_v13_wsh.py
@@ -4,16 +4,7 @@ from mod_pywebsocket import msgutil def web_socket_do_extra_handshake(request): - request.connection.write(b'x') - time.sleep(2) - request.connection.write(b'x') - time.sleep(2) - request.connection.write(b'x') - time.sleep(2) - request.connection.write(b'x') - time.sleep(2) - request.connection.write(b'x') - time.sleep(2) + time.sleep(10) return def web_socket_transfer_data(request):
diff --git a/tools/metrics/histograms/enums.xml b/tools/metrics/histograms/enums.xml index 4dfd6f2..ea24b61 100644 --- a/tools/metrics/histograms/enums.xml +++ b/tools/metrics/histograms/enums.xml
@@ -9127,7 +9127,9 @@ <int value="4" label="Invalid reporting_origin field"/> <int value="5" label="Invalid report_type field"/> <int value="6" label="Mismatched reporting origin between source and report"/> - <int value="7" label="Metadata could not be read from database"/> + <int value="7" + label="(Obsolete) Metadata could not be read from database. Removed in + 2023/12."/> <int value="8" label="Source data missing - event level report"/> <int value="9" label="Source data missing - aggregatable report"/> <int value="10" label="Source data found - null aggregatable report"/> @@ -31491,6 +31493,8 @@ <int value="-783999903" label="FilesTrashDrive:disabled"/> <int value="-783890018" label="LacrosProfileMigrationForAnyUser:disabled"/> <int value="-783093620" label="WebViewHitTestInBlinkOnTouchStart:enabled"/> + <int value="-782689039" + label="FencedFramesCrossOriginAutomaticBeacons:enabled"/> <int value="-782193212" label="AutofillEnablePaymentsMandatoryReauth:enabled"/> <int value="-781625651" @@ -34574,6 +34578,8 @@ <int value="684112629" label="BluetoothCoredump:disabled"/> <int value="684806628" label="TranslateLanguageByULP:disabled"/> <int value="685406951" label="UseNotificationCompatBuilder:disabled"/> + <int value="685571935" + label="FencedFramesCrossOriginAutomaticBeacons:disabled"/> <int value="685916283" label="enable-zip-archiver-on-file-manager"/> <int value="686929809" label="BorealisWebUIInstaller:enabled"/> <int value="687838135" label="ThirdPartyDoodles:disabled"/>
diff --git a/tools/metrics/histograms/histograms_index.txt b/tools/metrics/histograms/histograms_index.txt index 1bb6d21..7d00183f 100644 --- a/tools/metrics/histograms/histograms_index.txt +++ b/tools/metrics/histograms/histograms_index.txt
@@ -166,6 +166,7 @@ tools/metrics/histograms/metadata/quickstart/enums.xml tools/metrics/histograms/metadata/quickstart/histograms.xml tools/metrics/histograms/metadata/quota/histograms.xml +tools/metrics/histograms/metadata/readaloud/histograms.xml tools/metrics/histograms/metadata/renderer/histograms.xml tools/metrics/histograms/metadata/renderer4/histograms.xml tools/metrics/histograms/metadata/safe_browsing/enums.xml
diff --git a/tools/metrics/histograms/metadata/METRIC_REVIEWER_OWNERS b/tools/metrics/histograms/metadata/METRIC_REVIEWER_OWNERS index 9b1c176..051ae25 100644 --- a/tools/metrics/histograms/metadata/METRIC_REVIEWER_OWNERS +++ b/tools/metrics/histograms/metadata/METRIC_REVIEWER_OWNERS
@@ -347,6 +347,10 @@ xiaohuic@chromium.org # quota ayui@chromium.org +# readaloud +andreaxg@google.com +basiaz@google.com +iwells@google.com # renderer4 schenney@chromium.org # renderer
diff --git a/tools/metrics/histograms/metadata/blink/histograms.xml b/tools/metrics/histograms/metadata/blink/histograms.xml index 2dd014a..96530ad 100644 --- a/tools/metrics/histograms/metadata/blink/histograms.xml +++ b/tools/metrics/histograms/metadata/blink/histograms.xml
@@ -124,11 +124,7 @@ <histogram base="true" name="Blink.Accessibility.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>ikilpatrick@chromium.org</owner> <owner>layout-dev@chromium.org</owner> @@ -149,11 +145,7 @@ <histogram base="true" name="Blink.AnchorElementMetricsIntersectionObserver.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -176,11 +168,7 @@ <histogram base="true" name="Blink.Animate.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -715,11 +703,7 @@ <histogram base="true" name="Blink.CompositingCommit.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -740,11 +724,7 @@ <histogram base="true" name="Blink.CompositingInputs.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -798,11 +778,7 @@ <histogram base="true" name="Blink.ContentDocumentUpdate.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -1096,11 +1072,7 @@ <histogram base="true" name="Blink.DisplayLockIntersectionObserver.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -1342,6 +1314,16 @@ </summary> </histogram> +<histogram name="Blink.FedCm.DomainHint.NumMatchingAccounts" + enum="FedCmNumAccounts" expires_after="2024-06-12"> + <owner>npm@chromium.org</owner> + <owner>web-identity-eng@google.com</owner> + <summary> + Records the number of accounts the match a domain hint. Records at the time + the accounts received by the FedCM API are filtered. + </summary> +</histogram> + <histogram name="Blink.FedCm.Error.ErrorDialogResult" enum="FedCmErrorDialogResult" expires_after="M130"> <owner>tanzachary@chromium.org</owner> @@ -1481,8 +1463,8 @@ </summary> </histogram> -<histogram name="Blink.FedCm.LoginHint" enum="FedCmNumAccounts" - expires_after="2024-05-18"> +<histogram name="Blink.FedCm.LoginHint.NumMatchingAccounts" + enum="FedCmNumAccounts" expires_after="2024-05-18"> <owner>npm@chromium.org</owner> <owner>web-identity-eng@google.com</owner> <summary> @@ -2010,11 +1992,7 @@ <histogram base="true" name="Blink.ForcedStyleAndLayout.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2048,11 +2026,7 @@ <histogram base="true" name="Blink.HandleInputEvents.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2072,11 +2046,7 @@ <histogram base="true" name="Blink.HitTestDocumentUpdate.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2445,11 +2415,7 @@ <histogram base="true" name="Blink.ImplCompositorCommit.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2471,11 +2437,7 @@ <histogram base="true" name="Blink.IntersectionObservation.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2497,11 +2459,7 @@ <histogram base="true" name="Blink.IntersectionObservationInternalCount.UpdateTime" units="count" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>szager@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2514,11 +2472,7 @@ <histogram base="true" name="Blink.IntersectionObservationJavascriptCount.UpdateTime" units="count" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>szager@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2530,11 +2484,7 @@ <histogram base="true" name="Blink.JavascriptDocumentUpdate.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2559,11 +2509,7 @@ <histogram base="true" name="Blink.JavascriptIntersectionObserver.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2616,11 +2562,7 @@ <histogram base="true" name="Blink.Layout.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>layout-dev@chromium.org</owner> @@ -2663,11 +2605,7 @@ <histogram base="true" name="Blink.LazyLoadIntersectionObserver.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2905,11 +2843,7 @@ <histogram base="true" name="Blink.MainFrame.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -2929,11 +2863,7 @@ <histogram base="true" name="Blink.MediaIntersectionObserver.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -3183,11 +3113,7 @@ <histogram base="true" name="Blink.Paint.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -3207,11 +3133,7 @@ <histogram base="true" name="Blink.ParseStyleSheet.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>cduvall@chromium.org</owner> <owner>jam@chromium.org</owner> @@ -3230,6 +3152,18 @@ </summary> </histogram> +<histogram base="true" name="Blink.PossibleSynchronizedScrollCount.UpdateTime" + units="count" expires_after="2024-06-01"> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> + + <owner>vollick@chromium.org</owner> + <owner>flackr@chromium.org</owner> + <summary> + The total number times a page is estimated to have attempted a sync-scroll + update (i.e., synchronizing an effect with scroll). + </summary> +</histogram> + <histogram name="Blink.PreloadRequestWaitTime" units="ms" expires_after="2023-10-22"> <owner>cduvall@chromium.org</owner> @@ -3242,11 +3176,7 @@ <histogram base="true" name="Blink.PrePaint.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -3534,11 +3464,7 @@ <histogram base="true" name="Blink.ServiceDocumentUpdate.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -3721,11 +3647,7 @@ <histogram base="true" name="Blink.Style.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>layout-dev@chromium.org</owner> @@ -3757,11 +3679,7 @@ <histogram name="Blink.UpdateViewportIntersection.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -4170,11 +4088,7 @@ <histogram base="true" name="Blink.UserDrivenDocumentUpdate.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -4262,11 +4176,7 @@ <histogram base="true" name="Blink.VisualUpdateDelay.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>szager@chromium.org</owner> <owner>paint-dev@chromium.org</owner> @@ -4281,11 +4191,7 @@ <histogram base="true" name="Blink.WaitForCommit.UpdateTime" units="microseconds" expires_after="2024-06-01"> -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" --> - -<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" --> +<!-- Name completed by histogram_suffixes name="BlinkUpdateTimeSuffixes" --> <owner>pdr@chromium.org</owner> <owner>paint-dev@chromium.org</owner>
diff --git a/tools/metrics/histograms/metadata/families/enums.xml b/tools/metrics/histograms/metadata/families/enums.xml index a910b8c..7683362 100644 --- a/tools/metrics/histograms/metadata/families/enums.xml +++ b/tools/metrics/histograms/metadata/families/enums.xml
@@ -180,22 +180,6 @@ <int value="4" label="Regular User"/> </enum> -<enum name="KidsChromeManagementClientParsingError"> - <int value="0" label="Success"/> - <int value="1" label="Response dictionary failure"/> - <int value="2" label="Display classification failure"/> - <int value="3" label="Invalid display classification"/> -</enum> - -<enum name="KidsManagementURLCheckerResponseStatus"> - <int value="0" label="Success"/> - <int value="1" label="Network Error"/> - <int value="2" label="Unexpected Classification Value"/> - <int value="3" label="Parsing Error"/> - <int value="4" label="Token Error"/> - <int value="5" label="Http Error"/> -</enum> - <enum name="LegacySupervisedUserStatus"> <int value="0" label="Displayed on login screen"/> <int value="1" label="Hidden on login screen"/>
diff --git a/tools/metrics/histograms/metadata/families/histograms.xml b/tools/metrics/histograms/metadata/families/histograms.xml index 934be12e..f112db1b 100644 --- a/tools/metrics/histograms/metadata/families/histograms.xml +++ b/tools/metrics/histograms/metadata/families/histograms.xml
@@ -697,44 +697,6 @@ </summary> </histogram> -<histogram name="ManagedUsers.KidsManagementClassifyUrlFailureDelay" units="ms" - expires_after="2024-12-12"> - <owner>escordeiro@chromium.org</owner> - <owner>unichrome-eng@google.com</owner> - <owner>cros-families-eng@google.com</owner> - <summary> - The extra page load delays introduced by network requests due to the - supervised user url filtering feature, measured once per page load, for - failed requests. This is the delay to fetch the token and call the - ClassifyUrl rpc, when there is a cache miss. - </summary> -</histogram> - -<histogram name="ManagedUsers.KidsManagementClassifyUrlSuccessDelay" units="ms" - expires_after="2024-12-12"> - <owner>escordeiro@chromium.org</owner> - <owner>unichrome-eng@google.com</owner> - <owner>cros-families-eng@google.com</owner> - <summary> - The extra page load delays introduced by network requests due to the - supervised user url filtering feature, measured once per page load. This is - the delay to fetch the token and call the ClassifyUrl rpc, when there is a - cache miss. Only recorded for successful requests. - </summary> -</histogram> - -<histogram name="ManagedUsers.KidsManagementUrlCheckerResponseStatus" - enum="KidsManagementURLCheckerResponseStatus" expires_after="2024-12-12"> - <owner>escordeiro@chromium.org</owner> - <owner>unichrome-eng@google.com</owner> - <owner>cros-families-eng@google.com</owner> - <summary> - The counts of response status from supervised user - KidsManagementURLCheckerCLient. Each entry includes the outcome of a request - (i.e. success, net error, parsing error). - </summary> -</histogram> - <histogram name="ManagedUsers.RequestPermissionSource" enum="ManagedUserURLRequestPermissionSource" expires_after="2024-04-28"> <owner>agawronska@chromium.org</owner>
diff --git a/tools/metrics/histograms/metadata/histogram_suffixes_list.xml b/tools/metrics/histograms/metadata/histogram_suffixes_list.xml index 77154afb..af15fb7 100644 --- a/tools/metrics/histograms/metadata/histogram_suffixes_list.xml +++ b/tools/metrics/histograms/metadata/histogram_suffixes_list.xml
@@ -548,80 +548,10 @@ <affected-histogram name="WebRTC.Stun.BatchSuccessPercent.UnknownNAT"/> </histogram_suffixes> -<histogram_suffixes name="BlinkUpdateTimeAggregatedSuffixes" separator="."> +<histogram_suffixes name="BlinkUpdateTimeSuffixes" separator="."> <suffix name="AggregatedPreFCP" label="All the time spent Pre First Contentful Paint in this component"/> - <affected-histogram name="Blink.Accessibility.UpdateTime"/> - <affected-histogram - name="Blink.AnchorElementMetricsIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.Animate.UpdateTime"/> - <affected-histogram name="Blink.CompositingCommit.UpdateTime"/> - <affected-histogram name="Blink.CompositingInputs.UpdateTime"/> - <affected-histogram name="Blink.ContentDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.DisplayLockIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.ForcedStyleAndLayout.UpdateTime"/> - <affected-histogram name="Blink.HandleInputEvents.UpdateTime"/> - <affected-histogram name="Blink.HitTestDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.ImplCompositorCommit.UpdateTime"/> - <affected-histogram name="Blink.IntersectionObservation.UpdateTime"/> - <affected-histogram - name="Blink.IntersectionObservationInternalCount.UpdateTime"/> - <affected-histogram - name="Blink.IntersectionObservationJavascriptCount.UpdateTime"/> - <affected-histogram name="Blink.JavascriptDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.JavascriptIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.Layout.UpdateTime"/> - <affected-histogram name="Blink.LazyLoadIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.MainFrame.UpdateTime"/> - <affected-histogram name="Blink.MediaIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.Paint.UpdateTime"/> - <affected-histogram name="Blink.ParseStyleSheet.UpdateTime"/> - <affected-histogram name="Blink.PrePaint.UpdateTime"/> - <affected-histogram name="Blink.ServiceDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.Style.UpdateTime"/> - <affected-histogram name="Blink.UpdateViewportIntersection.UpdateTime"/> - <affected-histogram name="Blink.UserDrivenDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.VisualUpdateDelay.UpdateTime"/> - <affected-histogram name="Blink.WaitForCommit.UpdateTime"/> -</histogram_suffixes> - -<histogram_suffixes name="BlinkUpdateTimePostFCPSuffixes" separator="."> <suffix name="PostFCP" label="Update occurred after First Contentful Paint."/> - <affected-histogram name="Blink.Accessibility.UpdateTime"/> - <affected-histogram - name="Blink.AnchorElementMetricsIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.Animate.UpdateTime"/> - <affected-histogram name="Blink.CompositingCommit.UpdateTime"/> - <affected-histogram name="Blink.CompositingInputs.UpdateTime"/> - <affected-histogram name="Blink.ContentDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.DisplayLockIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.ForcedStyleAndLayout.UpdateTime"/> - <affected-histogram name="Blink.HandleInputEvents.UpdateTime"/> - <affected-histogram name="Blink.HitTestDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.ImplCompositorCommit.UpdateTime"/> - <affected-histogram name="Blink.IntersectionObservation.UpdateTime"/> - <affected-histogram - name="Blink.IntersectionObservationInternalCount.UpdateTime"/> - <affected-histogram - name="Blink.IntersectionObservationJavascriptCount.UpdateTime"/> - <affected-histogram name="Blink.JavascriptDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.JavascriptIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.Layout.UpdateTime"/> - <affected-histogram name="Blink.LazyLoadIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.MainFrame.UpdateTime"/> - <affected-histogram name="Blink.MediaIntersectionObserver.UpdateTime"/> - <affected-histogram name="Blink.Paint.UpdateTime"/> - <affected-histogram name="Blink.ParseStyleSheet.UpdateTime"/> - <affected-histogram name="Blink.PrePaint.UpdateTime"/> - <affected-histogram name="Blink.ServiceDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.Style.UpdateTime"/> - <affected-histogram name="Blink.UpdateViewportIntersection.UpdateTime"/> - <affected-histogram name="Blink.UserDrivenDocumentUpdate.UpdateTime"/> - <affected-histogram name="Blink.VisualUpdateDelay.UpdateTime"/> - <affected-histogram name="Blink.WaitForCommit.UpdateTime"/> -</histogram_suffixes> - -<histogram_suffixes name="BlinkUpdateTimePreFCPSuffixes" separator="."> <suffix name="PreFCP" label="Update occurred before First Contentful Paint."/> <affected-histogram name="Blink.Accessibility.UpdateTime"/> <affected-histogram @@ -648,6 +578,7 @@ <affected-histogram name="Blink.MediaIntersectionObserver.UpdateTime"/> <affected-histogram name="Blink.Paint.UpdateTime"/> <affected-histogram name="Blink.ParseStyleSheet.UpdateTime"/> + <affected-histogram name="Blink.PossibleSynchronizedScrollCount.UpdateTime"/> <affected-histogram name="Blink.PrePaint.UpdateTime"/> <affected-histogram name="Blink.ServiceDocumentUpdate.UpdateTime"/> <affected-histogram name="Blink.Style.UpdateTime"/>
diff --git a/tools/metrics/histograms/metadata/history/histograms.xml b/tools/metrics/histograms/metadata/history/histograms.xml index 1a2aa85..6a04445a 100644 --- a/tools/metrics/histograms/metadata/history/histograms.xml +++ b/tools/metrics/histograms/metadata/history/histograms.xml
@@ -1834,18 +1834,6 @@ </summary> </histogram> -<histogram name="History.FirstUpdateTime" units="ms" expires_after="2020-02-02"> - <owner>yiyaoliu@chromium.org</owner> - <component>UI>Browser>History</component> - <summary> - The amount of time for function - history::TopSitesBackend::UpdateTopSitesOnDBThread to execute when this - function is called during startup. Excludes the case where local - TopSitesDatabase db_ is unavailable, i.e. where the update doesn't really - happen. - </summary> -</histogram> - <histogram name="History.ForeignVisitsLegacy" units="visits" expires_after="2024-04-28"> <owner>tommycli@chromium.org</owner>
diff --git a/tools/metrics/histograms/metadata/readaloud/OWNERS b/tools/metrics/histograms/metadata/readaloud/OWNERS new file mode 100644 index 0000000..70798d9 --- /dev/null +++ b/tools/metrics/histograms/metadata/readaloud/OWNERS
@@ -0,0 +1,7 @@ +per-file OWNERS=file://tools/metrics/histograms/metadata/METRIC_REVIEWER_OWNERS + +# Prefer sending CLs to the owners listed below. +# Use chromium-metrics-reviews@google.com as a backup. +andreaxg@google.com +basiaz@google.com +iwells@google.com \ No newline at end of file
diff --git a/tools/metrics/histograms/metadata/readaloud/histograms.xml b/tools/metrics/histograms/metadata/readaloud/histograms.xml new file mode 100644 index 0000000..3a9dd43 --- /dev/null +++ b/tools/metrics/histograms/metadata/readaloud/histograms.xml
@@ -0,0 +1,39 @@ +<!-- +Copyright 2023 The Chromium Authors +Use of this source code is governed by a BSD-style license that can be +found in the LICENSE file. +--> + +<!-- +This file is used to generate a comprehensive list of Compose histograms +along with a detailed description for each histogram. + +For best practices on writing histogram descriptions, see +https://chromium.googlesource.com/chromium/src.git/+/HEAD/tools/metrics/histograms/README.md + +Please follow the instructions in the OWNERS file in this directory to find a +reviewer. If no OWNERS file exists, please consider signing up at +go/reviewing-metrics (Googlers only), as all subdirectories are expected to +have an OWNERS file. As a last resort you can send the CL to +chromium-metrics-reviews@google.com. +--> + +<histogram-configuration> + +<histograms> + +<histogram name="ReadAloud.IsPageReadable" enum="BooleanSuccess" + expires_after="2024-06-02"> + <owner>andreaxg@google.com</owner> + <owner>basiaz@google.com</owner> + <owner>iwells@google.com</owner> + <summary> + Histogram for recording if a page readability check comes back successful or + not. The readability check is run on each page load for Android clients who + are eligible for ReadAloud. + </summary> +</histogram> + +</histograms> + +</histogram-configuration>
diff --git a/tools/metrics/histograms/metadata/renderer/histograms.xml b/tools/metrics/histograms/metadata/renderer/histograms.xml index 9ed385da..548669f 100644 --- a/tools/metrics/histograms/metadata/renderer/histograms.xml +++ b/tools/metrics/histograms/metadata/renderer/histograms.xml
@@ -511,6 +511,20 @@ </summary> </histogram> +<histogram name="Renderer.PossibleSynchronizedScroll" enum="BooleanSuccess" + expires_after="2024-04-28"> + <owner>vollick@chromium.org</owner> + <owner>flackr@chromium.org</owner> + <summary> + Counts the number of times we estimate that a page (whose main frame is the + outermost main frame) is attempting to synchronously make updates in + response to scroll (eg, to implement a JavaScript-based parallax effect). We + make this estimation based on a heuristic that checks that we a) have a + scroll handler, b) have accessed scroll position, and c) have made an update + (and this update can be realized by scheduling rAF). + </summary> +</histogram> + <histogram name="Renderer.Preload.UnusedResource" enum="BooleanSuccess" expires_after="2024-06-09"> <owner>yoavweiss@chromium.org</owner>
diff --git a/tools/metrics/ukm/ukm.xml b/tools/metrics/ukm/ukm.xml index 564caf7..a923733 100644 --- a/tools/metrics/ukm/ukm.xml +++ b/tools/metrics/ukm/ukm.xml
@@ -5004,6 +5004,14 @@ The time spent parsing style sheets. </summary> </metric> + <metric name="PossibleSynchronizedScrollCount"> + <summary> + The total number times a page (whose main frame is both the outermost main + frame and is local) is estimated to have attempted a sync- scroll update + (i.e., synchronizing an effect with scroll) between navigation and First + Contentful Paint. + </summary> + </metric> <metric name="PrePaint"> <summary> The time spent in pre-paint document lifecycle work, between navigation @@ -6065,6 +6073,27 @@ The total main frame time spent parsing style sheets. </summary> </metric> + <metric name="PossibleSynchronizedScrollCount"> + <summary> + The total number times a page (whose main frame is both the outermost main + frame and is local) is estimated to have attempted a sync- scroll update + (i.e., synchronizing an effect with scroll). + </summary> + <aggregation> + <history> + <statistics> + <quantiles type="std-percentiles"/> + </statistics> + </history> + </aggregation> + </metric> + <metric name="PossibleSynchronizedScrollCountBeginMainFrame"> + <summary> + The total number times a page (whose main frame is both the outermost main + frame and is local) is estimated to have attempted a sync- scroll update + (i.e., synchronizing an effect with scroll). + </summary> + </metric> <metric name="PrePaint"> <summary> The time taken for pre-paint for the main frame in microseconds during the
diff --git a/tools/perf/core/perfetto_binary_roller/binary_deps.json b/tools/perf/core/perfetto_binary_roller/binary_deps.json index cf192c1..d86b663 100644 --- a/tools/perf/core/perfetto_binary_roller/binary_deps.json +++ b/tools/perf/core/perfetto_binary_roller/binary_deps.json
@@ -14,7 +14,7 @@ }, "mac": { "hash": "5d8dbe78fcd33af1ed7c69c5e49a5b44f9159848", - "full_remote_path": "chromium-telemetry/perfetto_binaries/trace_processor_shell/mac/8c0a74dad3bea98a5284009a273f5a4b573ecfe9/trace_processor_shell" + "full_remote_path": "chromium-telemetry/perfetto_binaries/trace_processor_shell/mac/ff3b6318208109a97dc91f5f653edfca466d3cca/trace_processor_shell" }, "mac_arm64": { "hash": "28d38c5eef93cf965ad3b3c656d4419f8e55f864", @@ -22,7 +22,7 @@ }, "linux": { "hash": "a72dcf8e23bc86107f2d7929810907e2b5082e31", - "full_remote_path": "chromium-telemetry/perfetto_binaries/trace_processor_shell/linux/12b9622ad9250c5411740ffcfbd8958f47bd7cf5/trace_processor_shell" + "full_remote_path": "chromium-telemetry/perfetto_binaries/trace_processor_shell/linux/ff3b6318208109a97dc91f5f653edfca466d3cca/trace_processor_shell" } }, "power_profile.sql": {
diff --git a/tools/rust/build_rust.py b/tools/rust/build_rust.py index 682e500..cbaa4c6b 100755 --- a/tools/rust/build_rust.py +++ b/tools/rust/build_rust.py
@@ -753,6 +753,11 @@ GitCherryPick(RUST_SRC_DIR, 'https://github.com/rust-lang/rust.git', 'a0c5079889b1f86dd9e246d8863a5c8b44fbdb78') + # TODO: Remove once + # https://github.com/rust-lang/rust/pull/118866 has been merged. + GitCherryPick(RUST_SRC_DIR, 'https://github.com/rust-lang/rust.git', + '46a801559127441675f2341bd1d684809a47def1') + path = FetchBetaPackage('cargo', checkout_revision) if sys.platform == 'win32': cargo_bin = os.path.join(path, 'cargo', 'bin', 'cargo.exe')
diff --git a/ui/accessibility/BUILD.gn b/ui/accessibility/BUILD.gn index 6099edb..c3155c5 100644 --- a/ui/accessibility/BUILD.gn +++ b/ui/accessibility/BUILD.gn
@@ -526,6 +526,8 @@ sources = [ "android/javatests/src/org/chromium/ui/accessibility/AccessibilityStateTest.java" ] deps = [ ":ax_base_java", + ":ui_accessibility_features_java", + "//base:base_java_test_support", "//base:base_junit_test_support", "//third_party/androidx:androidx_test_runner_java", "//third_party/junit:junit",
diff --git a/ui/accessibility/android/java/src/org/chromium/ui/accessibility/AccessibilityState.java b/ui/accessibility/android/java/src/org/chromium/ui/accessibility/AccessibilityState.java index 3b43edf..1846f84 100644 --- a/ui/accessibility/android/java/src/org/chromium/ui/accessibility/AccessibilityState.java +++ b/ui/accessibility/android/java/src/org/chromium/ui/accessibility/AccessibilityState.java
@@ -565,7 +565,7 @@ == AccessibilityServiceInfo.FEEDBACK_GENERIC); } - static void updateAccessibilityServices() { + protected static void updateAccessibilityServices() { long now = SystemClock.elapsedRealtimeNanos() / 1000; if (!sInitialized) { sState = new State(false, false, false, false, false, false, false, false); @@ -1178,4 +1178,12 @@ sInitialized = true; sIsInTestingMode = true; } + + protected static void uninitializeForTesting() { + sState = null; + sAccessibilityManager = null; + sInitialized = false; + sIsInTestingMode = false; + sPreInitCachedValuePerformGesturesEnabled = null; + } }
diff --git a/ui/accessibility/android/javatests/src/org/chromium/ui/accessibility/AccessibilityStateTest.java b/ui/accessibility/android/javatests/src/org/chromium/ui/accessibility/AccessibilityStateTest.java index 0b68311..6a696c4 100644 --- a/ui/accessibility/android/javatests/src/org/chromium/ui/accessibility/AccessibilityStateTest.java +++ b/ui/accessibility/android/javatests/src/org/chromium/ui/accessibility/AccessibilityStateTest.java
@@ -21,13 +21,18 @@ import androidx.test.filters.SmallTest; +import org.junit.After; import org.junit.Assert; import org.junit.Before; +import org.junit.Rule; import org.junit.Test; +import org.junit.rules.TestRule; import org.junit.runner.RunWith; import org.robolectric.RuntimeEnvironment; import org.chromium.base.test.BaseRobolectricTestRunner; +import org.chromium.base.test.util.Features; +import org.chromium.base.test.util.Features.EnableFeatures; import java.lang.reflect.Constructor; import java.lang.reflect.Method; @@ -42,6 +47,24 @@ private static final String EVENT_TYPE_MASK_ERROR = "Conversion of event masks to event types not correct."; + private static final int MOCK_EVENT_TYPE_MASK = + AccessibilityEvent.TYPE_VIEW_CLICKED + | AccessibilityEvent.TYPE_VIEW_FOCUSED + | AccessibilityEvent.TYPE_VIEW_TEXT_CHANGED + | AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED; + + private static final int MOCK_FLAG_TYPE_MASK = + AccessibilityServiceInfo.DEFAULT + | AccessibilityServiceInfo.FLAG_REQUEST_TOUCH_EXPLORATION_MODE + | AccessibilityServiceInfo.FLAG_REQUEST_ENHANCED_WEB_ACCESSIBILITY + | AccessibilityServiceInfo.FLAG_REPORT_VIEW_IDS + | AccessibilityServiceInfo.FLAG_RETRIEVE_INTERACTIVE_WINDOWS; + + private static final int MOCK_CAPABILITY_TYPE_MASK = + AccessibilityServiceInfo.CAPABILITY_CAN_RETRIEVE_WINDOW_CONTENT; + + @Rule public TestRule mProcessor = new Features.JUnitProcessor(); + private Context mContext; @Before @@ -59,6 +82,11 @@ AccessibilityState.setStateMaskForTesting(CAPABILITIES_MASK_HEURISTIC, 0); } + @After + public void tearDown() { + AccessibilityState.uninitializeForTesting(); + } + @Test @SmallTest public void testSimpleString() { @@ -287,6 +315,7 @@ @Test @SmallTest + @EnableFeatures(UiAccessibilityFeatures.START_SURFACE_ACCESSIBILITY_CHECK) public void testCalculateHeuristicState_Autofill_passwordManager() { AccessibilityServiceInfo myService = new BuilderForTests(mContext) @@ -297,14 +326,19 @@ .setFlags(AccessibilityState.PASSWORD_MANAGER_FLAG_TYPE_MASK) .setCapabilities(AccessibilityState.PASSWORD_MANAGER_CAPABILITY_TYPE_MASK) .build(); + startTestWithService( + myService, + "android/com.android.server.autofill.AutofillCompatAccessibilityService"); - Assert.assertNotNull(myService); - AccessibilityState.calculateHeuristicState(myService); + AccessibilityState.updateAccessibilityServices(); + + Assert.assertTrue(AccessibilityState.isAnyAccessibilityServiceEnabled()); Assert.assertFalse(AccessibilityState.areOnlyPasswordManagerMasksRequested()); } @Test @SmallTest + @EnableFeatures(UiAccessibilityFeatures.START_SURFACE_ACCESSIBILITY_CHECK) public void testCalculateHeuristicState_notAutofill_notPasswordManager() { AccessibilityServiceInfo myService = new BuilderForTests(mContext) @@ -312,14 +346,17 @@ .setFlags(~0) .setCapabilities(~0) .build(); + startTestWithService(myService); - Assert.assertNotNull(myService); - AccessibilityState.calculateHeuristicState(myService); + AccessibilityState.updateAccessibilityServices(); + + Assert.assertTrue(AccessibilityState.isAnyAccessibilityServiceEnabled()); Assert.assertFalse(AccessibilityState.areOnlyPasswordManagerMasksRequested()); } @Test @SmallTest + @EnableFeatures(UiAccessibilityFeatures.START_SURFACE_ACCESSIBILITY_CHECK) public void testCalculateHeuristicState_notAutofill_passwordManager() { AccessibilityServiceInfo myService = new BuilderForTests(mContext) @@ -327,12 +364,67 @@ .setFlags(AccessibilityState.PASSWORD_MANAGER_FLAG_TYPE_MASK) .setCapabilities(AccessibilityState.PASSWORD_MANAGER_CAPABILITY_TYPE_MASK) .build(); + startTestWithService(myService); - Assert.assertNotNull(myService); - AccessibilityState.calculateHeuristicState(myService); + AccessibilityState.updateAccessibilityServices(); + + Assert.assertTrue(AccessibilityState.isAnyAccessibilityServiceEnabled()); Assert.assertTrue(AccessibilityState.areOnlyPasswordManagerMasksRequested()); } + @Test + @SmallTest + @EnableFeatures(UiAccessibilityFeatures.START_SURFACE_ACCESSIBILITY_CHECK) + public void testTogglingMisconfiguredAccessibilityServices() { + // This service has the same config as Microsoft Authenticator during recent P0. + AccessibilityServiceInfo errorProneService = + new BuilderForTests(mContext) + .setEventTypes(MOCK_EVENT_TYPE_MASK) + .setFlags(MOCK_FLAG_TYPE_MASK) + .setCapabilities(MOCK_CAPABILITY_TYPE_MASK) + .build(); + + // This service has the correct config for a password manager. + AccessibilityServiceInfo properConfigService = + new BuilderForTests(mContext) + .setEventTypes(MOCK_EVENT_TYPE_MASK) + .setFlags(MOCK_FLAG_TYPE_MASK) + .setCapabilities( + MOCK_CAPABILITY_TYPE_MASK + | AccessibilityServiceInfo + .CAPABILITY_CAN_REQUEST_TOUCH_EXPLORATION) + .build(); + + startTestWithService(errorProneService); + + AccessibilityState.updateAccessibilityServices(); + + Assert.assertTrue(AccessibilityState.isAnyAccessibilityServiceEnabled()); + // Before P0 fix, this call would have (incorrectly) returned true. + Assert.assertFalse(AccessibilityState.isTouchExplorationEnabled()); + + // Now enable the proper config, and ensure we do not enter an infinite loop and that + // we now show touch exploration as being enabled. + AccessibilityState.setEnabledServiceInfoListForTesting(List.of(properConfigService)); + + AccessibilityState.updateAccessibilityServices(); + + Assert.assertTrue(AccessibilityState.isAnyAccessibilityServiceEnabled()); + Assert.assertTrue(AccessibilityState.isTouchExplorationEnabled()); + } + + private void startTestWithService(AccessibilityServiceInfo newService) { + startTestWithService( + newService, "com.example.google/app.accessibility.AccessibilityService"); + } + + private void startTestWithService(AccessibilityServiceInfo newService, String serviceName) { + Assert.assertNotNull(newService); + Assert.assertFalse(AccessibilityState.isAnyAccessibilityServiceEnabled()); + AccessibilityState.setEnabledServiceInfoListForTesting(List.of(newService)); + AccessibilityState.setEnabledServiceStringForTesting(serviceName); + } + public static class BuilderForTests { private Context mContext;
diff --git a/ui/gfx/x/connection.cc b/ui/gfx/x/connection.cc index e9034ec7de..b11df74 100644 --- a/ui/gfx/x/connection.cc +++ b/ui/gfx/x/connection.cc
@@ -183,6 +183,7 @@ Connection::~Connection() { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + window_event_manager_.Reset(); platform_event_source.reset(); }
diff --git a/ui/gfx/x/window_event_manager.cc b/ui/gfx/x/window_event_manager.cc index 7aee20e..9b5b32040 100644 --- a/ui/gfx/x/window_event_manager.cc +++ b/ui/gfx/x/window_event_manager.cc
@@ -113,10 +113,18 @@ : connection_(connection) {} WindowEventManager::~WindowEventManager() { + Reset(); +} + +void WindowEventManager::Reset() { + if (!connection_) { + return; + } // Clear events still requested by not-yet-deleted ScopedEventSelectors. for (const auto& mask_pair : mask_map_) { SetEventMask(connection_, mask_pair.first, EventMask::NoEvent); } + connection_ = nullptr; } void WindowEventManager::SelectEvents(Window window, EventMask event_mask) { @@ -143,7 +151,9 @@ return; } - SetEventMask(connection_, window, new_mask); + if (connection_) { + SetEventMask(connection_, window, new_mask); + } if (new_mask == EventMask::NoEvent) { mask_map_.erase(window);
diff --git a/ui/gfx/x/window_event_manager.h b/ui/gfx/x/window_event_manager.h index 4b85f49..c0158edd 100644 --- a/ui/gfx/x/window_event_manager.h +++ b/ui/gfx/x/window_event_manager.h
@@ -53,6 +53,8 @@ ~WindowEventManager(); + void Reset(); + private: friend class ScopedEventSelector; @@ -70,7 +72,7 @@ // necessary. void AfterMaskChanged(Window window, EventMask old_mask); - const raw_ptr<Connection> connection_; + raw_ptr<Connection> connection_; std::map<Window, std::unique_ptr<MultiMask>> mask_map_; };
diff --git a/v8 b/v8 index ba99d7f..b057218 160000 --- a/v8 +++ b/v8
@@ -1 +1 @@ -Subproject commit ba99d7f61f605e0c4c5131f01ff9d4fc36ab269b +Subproject commit b057218023961f8b94b0313dd6ddbcc274c06e74