diff --git a/DEPS b/DEPS index 2230ddf..ff0bc0e 100644 --- a/DEPS +++ b/DEPS
@@ -144,11 +144,11 @@ # 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': '63fdd0191be0a96bdc642bffbdc08af9dfadef62', + 'skia_revision': '8c31f2bf7f154e00952da9bdfbe3accc7691aecf', # 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': '39c867908d66ff39b240ef7826ebfde9246d3327', + 'v8_revision': '3ec321d4ceec28228248d2b530719ac180847d3f', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling swarming_client # and whatever else without interference from each other. @@ -156,11 +156,11 @@ # 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': '1c16455ea1a50801a33ab7be0b0fd94bbd1f62aa', + 'angle_revision': 'b243a2a4f27b7ab93b34dd247088afa7c2a10038', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling SwiftShader # and whatever else without interference from each other. - 'swiftshader_revision': '763b77946e17811b1fed2617434e8886f8a41b42', + 'swiftshader_revision': '64f2cec30c96dad0ac67cdffe42feda7611fe4ae', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling PDFium # and whatever else without interference from each other. @@ -179,7 +179,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling googletest # and whatever else without interference from each other. - 'googletest_revision': '437e1008c97b6bf595fec85da42c6925babd96b2', + 'googletest_revision': '6077f444da944d96d311d358d761164261f1cdd0', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling lighttpd # and whatever else without interference from each other. @@ -279,11 +279,11 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling feed # and whatever else without interference from each other. - 'dawn_revision': '6eb681cc54c5d1f50f85ede54f4bb11a58ee86c4', + 'dawn_revision': '9dbb81f004b65faacbff0e5508bc7b7a40654f2b', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling feed # and whatever else without interference from each other. - 'quiche_revision': 'd57d3f905ac470ad0b31352907668c22ffb0c0b4', + 'quiche_revision': '58ac6508f78fd1a1685d9ad23b3fc084ee54e764', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling ios_webkit # and whatever else without interference from each other. @@ -808,7 +808,7 @@ # Build tools for Chrome OS. Note: This depends on third_party/pyelftools. 'src/third_party/chromite': { - 'url': Var('chromium_git') + '/chromiumos/chromite.git' + '@' + '73df0d84ad47e4916b8259e32b010846fd00261b', + 'url': Var('chromium_git') + '/chromiumos/chromite.git' + '@' + '66c4e85a160b6b01b49a1cafb6776f6012f31e39', 'condition': 'checkout_linux', }, @@ -1083,7 +1083,7 @@ }, 'src/third_party/libvpx/source/libvpx': - Var('chromium_git') + '/webm/libvpx.git' + '@' + 'cd9f1763c861edfd86d2814e029a34f3ce821e72', + Var('chromium_git') + '/webm/libvpx.git' + '@' + 'bb407a27b2e32f89f0e9eeee2bcd0aa9d5cfea3f', 'src/third_party/libwebm/source': Var('chromium_git') + '/webm/libwebm.git' + '@' + '51ca718c3adf0ddedacd7df25fe45f67dc5a9ce1', @@ -1194,7 +1194,7 @@ }, 'src/third_party/perfetto': - Var('android_git') + '/platform/external/perfetto.git' + '@' + 'a7fc7a353fbd5c863363e5e5a34d41dea8e43b4f', + Var('android_git') + '/platform/external/perfetto.git' + '@' + 'c182e466c1b0b2d845f5afc15cee84406158ef87', 'src/third_party/perl': { 'url': Var('chromium_git') + '/chromium/deps/perl.git' + '@' + '6f3e5028eb65d0b4c5fdd792106ac4c84eee1eb3', @@ -1362,7 +1362,7 @@ Var('chromium_git') + '/external/khronosgroup/webgl.git' + '@' + '6453c2f5604ec8bca15e9e1edc64e979da8f1083', 'src/third_party/webrtc': - Var('webrtc_git') + '/src.git' + '@' + 'ea3dddf1d0880e89d84a7e502f65c65993d4169d', + Var('webrtc_git') + '/src.git' + '@' + '0be40bf53fc4aa6707636a385e5eaaf01da7c7e4', 'src/third_party/xdg-utils': { 'url': Var('chromium_git') + '/chromium/deps/xdg-utils.git' + '@' + 'd80274d5869b17b8c9067a1022e4416ee7ed5e0d', @@ -1403,7 +1403,7 @@ Var('chromium_git') + '/v8/v8.git' + '@' + Var('v8_revision'), 'src-internal': { - 'url': 'https://chrome-internal.googlesource.com/chrome/src-internal.git@8411465ea3c949b3f13f3076aca61ca4ee996877', + 'url': 'https://chrome-internal.googlesource.com/chrome/src-internal.git@223c459965a8777dbe34a456508808b65496ad34', 'condition': 'checkout_src_internal', },
diff --git a/PRESUBMIT.py b/PRESUBMIT.py index 6249613d..14f7bc2 100644 --- a/PRESUBMIT.py +++ b/PRESUBMIT.py
@@ -17,6 +17,8 @@ r"^skia[\\/].*", r"^third_party[\\/]blink[\\/].*", r"^third_party[\\/]breakpad[\\/].*", + # sqlite is an imported third party dependency. + r"^third_party[\\/]sqlite[\\/].*", r"^v8[\\/].*", r".*MakeFile$", r".+_autogen\.h$",
diff --git a/android_webview/browser/aw_browser_context.cc b/android_webview/browser/aw_browser_context.cc index 5d93053..516b4ed 100644 --- a/android_webview/browser/aw_browser_context.cc +++ b/android_webview/browser/aw_browser_context.cc
@@ -9,6 +9,7 @@ #include <utility> #include "android_webview/browser/aw_browser_policy_connector.h" +#include "android_webview/browser/aw_browser_process.h" #include "android_webview/browser/aw_content_browser_client.h" #include "android_webview/browser/aw_download_manager_delegate.h" #include "android_webview/browser/aw_feature_list.h" @@ -49,7 +50,6 @@ #include "content/public/browser/browser_thread.h" #include "content/public/browser/cors_exempt_headers.h" #include "content/public/browser/download_request_utils.h" -#include "content/public/browser/network_service_instance.h" #include "content/public/browser/ssl_host_state_delegate.h" #include "content/public/browser/storage_partition.h" #include "content/public/browser/web_contents.h" @@ -63,36 +63,12 @@ namespace android_webview { -namespace prefs { - -// String that specifies the Android account type to use for Negotiate -// authentication. -const char kAuthAndroidNegotiateAccountType[] = - "auth.android_negotiate_account_type"; - -// Whitelist containing servers for which Integrated Authentication is enabled. -const char kAuthServerWhitelist[] = "auth.server_whitelist"; - -} // namespace prefs - namespace { const void* const kDownloadManagerDelegateKey = &kDownloadManagerDelegateKey; AwBrowserContext* g_browser_context = NULL; -std::unique_ptr<net::ProxyConfigServiceAndroid> CreateProxyConfigService() { - std::unique_ptr<net::ProxyConfigServiceAndroid> config_service_android = - std::make_unique<net::ProxyConfigServiceAndroid>( - base::CreateSingleThreadTaskRunnerWithTraits({BrowserThread::IO}), - base::ThreadTaskRunnerHandle::Get()); - - // TODO(csharrison) Architect the wrapper better so we don't need a cast for - // android ProxyConfigServices. - config_service_android->set_exclude_pac_url(true); - return config_service_android; -} - // Empty method to skip origin security check as DownloadManager will set its // own method. bool IgnoreOriginSecurityCheck(const GURL& url) { @@ -186,10 +162,6 @@ false); registry->RegisterBooleanPref(autofill::prefs::kAutofillCreditCardEnabled, false); - - registry->RegisterStringPref(prefs::kAuthServerWhitelist, std::string()); - registry->RegisterStringPref(prefs::kAuthAndroidNegotiateAccountType, - std::string()); } void AwBrowserContext::CreateUserPrefService() { @@ -212,7 +184,6 @@ policy::POLICY_LEVEL_MANDATORY)); user_pref_service_ = pref_service_factory.Create(pref_registry); - pref_change_registrar_.Init(user_pref_service_.get()); user_prefs::UserPrefs::Set(this, user_pref_service_.get()); } @@ -226,15 +197,13 @@ return supported_schemes; } -void AwBrowserContext::PreMainMessageLoopRun(net::NetLog* net_log) { - FilePath cache_path = GetCacheDir(); - +void AwBrowserContext::PreMainMessageLoopRun() { CreateUserPrefService(); if (!base::FeatureList::IsEnabled(network::features::kNetworkService)) { + // TODO(amalova): Create a new instance for non-default profiles. url_request_context_getter_ = - new AwURLRequestContextGetter(cache_path, CreateProxyConfigService(), - user_pref_service_.get(), net_log); + AwBrowserProcess::GetInstance()->GetAwURLRequestContext(); } scoped_refptr<base::SequencedTaskRunner> db_task_runner = @@ -250,23 +219,10 @@ EnsureResourceContextInitialized(this); - if (base::FeatureList::IsEnabled(network::features::kNetworkService)) { - auto auth_pref_callback = base::BindRepeating( - &AwBrowserContext::OnAuthPrefsChanged, base::Unretained(this)); - pref_change_registrar_.Add(prefs::kAuthServerWhitelist, auth_pref_callback); - pref_change_registrar_.Add(prefs::kAuthAndroidNegotiateAccountType, - auth_pref_callback); - } - content::WebUIControllerFactory::RegisterFactory( AwWebUIControllerFactory::GetInstance()); } -void AwBrowserContext::OnAuthPrefsChanged() { - content::GetNetworkService()->ConfigureHttpAuthPrefs( - CreateHttpAuthDynamicParams()); -} - void AwBrowserContext::AddVisitedURLs(const std::vector<GURL>& urls) { DCHECK(visitedlink_master_); visitedlink_master_->AddURLs(urls); @@ -283,10 +239,6 @@ return form_database_service_.get(); } -AwURLRequestContextGetter* AwBrowserContext::GetAwURLRequestContext() { - return url_request_context_getter_.get(); -} - autofill::AutocompleteHistoryManager* AwBrowserContext::GetAutocompleteHistoryManager() { if (!autocomplete_history_manager_) { @@ -383,7 +335,7 @@ // content::StoragePartitionImplMap::Create(). This is not fixable // until http://crbug.com/159193. Until then, assert that the context // has already been allocated and just handle setting the protocol_handlers. - DCHECK(url_request_context_getter_.get()); + DCHECK(url_request_context_getter_); url_request_context_getter_->SetHandlersAndInterceptors( protocol_handlers, std::move(request_interceptors)); return url_request_context_getter_.get(); @@ -391,7 +343,7 @@ net::URLRequestContextGetter* AwBrowserContext::CreateMediaRequestContext() { DCHECK(!base::FeatureList::IsEnabled(network::features::kNetworkService)); - return url_request_context_getter_.get(); + return AwBrowserProcess::GetInstance()->GetAwURLRequestContext(); } download::InProgressDownloadManager* @@ -402,19 +354,6 @@ base::BindRepeating(&content::DownloadRequestUtils::IsURLSafe), nullptr); } -network::mojom::HttpAuthDynamicParamsPtr -AwBrowserContext::CreateHttpAuthDynamicParams() { - network::mojom::HttpAuthDynamicParamsPtr auth_dynamic_params = - network::mojom::HttpAuthDynamicParams::New(); - - auth_dynamic_params->server_whitelist = - user_pref_service_->GetString(prefs::kAuthServerWhitelist); - auth_dynamic_params->android_negotiate_account_type = - user_pref_service_->GetString(prefs::kAuthAndroidNegotiateAccountType); - - return auth_dynamic_params; -} - void AwBrowserContext::RebuildTable( const scoped_refptr<URLEnumerator>& enumerator) { // Android WebView rebuilds from WebChromeClient.getVisitedHistory. The client
diff --git a/android_webview/browser/aw_browser_context.h b/android_webview/browser/aw_browser_context.h index a907818..997dd27f 100644 --- a/android_webview/browser/aw_browser_context.h +++ b/android_webview/browser/aw_browser_context.h
@@ -15,7 +15,6 @@ #include "base/macros.h" #include "base/memory/ref_counted.h" #include "components/keyed_service/core/simple_factory_key.h" -#include "components/prefs/pref_change_registrar.h" #include "components/prefs/pref_registry_simple.h" #include "components/visitedlink/browser/visitedlink_delegate.h" #include "content/public/browser/browser_context.h" @@ -38,10 +37,6 @@ class InProgressDownloadManager; } -namespace net { -class NetLog; -} - namespace policy { class BrowserPolicyConnectorBase; } @@ -56,14 +51,6 @@ class AwQuotaManagerBridge; class AwURLRequestContextGetter; -namespace prefs { - -// Used for Kerberos authentication. -extern const char kAuthAndroidNegotiateAccountType[]; -extern const char kAuthServerWhitelist[]; - -} // namespace prefs - class AwBrowserContext : public content::BrowserContext, public visitedlink::VisitedLinkDelegate { public: @@ -88,14 +75,13 @@ static std::vector<std::string> GetAuthSchemes(); // Maps to BrowserMainParts::PreMainMessageLoopRun. - void PreMainMessageLoopRun(net::NetLog* net_log); + void PreMainMessageLoopRun(); // These methods map to Add methods in visitedlink::VisitedLinkMaster. void AddVisitedURLs(const std::vector<GURL>& urls); AwQuotaManagerBridge* GetQuotaManagerBridge(); AwFormDatabaseService* GetFormDatabaseService(); - AwURLRequestContextGetter* GetAwURLRequestContext(); autofill::AutocompleteHistoryManager* GetAutocompleteHistoryManager(); // content::BrowserContext implementation. @@ -125,9 +111,6 @@ // visitedlink::VisitedLinkDelegate implementation. void RebuildTable(const scoped_refptr<URLEnumerator>& enumerator) override; - // Constructs HttpAuthDynamicParams based on |user_pref_service_|. - network::mojom::HttpAuthDynamicParamsPtr CreateHttpAuthDynamicParams(); - PrefService* GetPrefService() const { return user_pref_service_.get(); } void SetExtendedReportingAllowed(bool allowed); @@ -137,7 +120,6 @@ const base::FilePath& relative_partition_path); private: - void OnAuthPrefsChanged(); void CreateUserPrefService(); // The file path where data for this context is persisted. @@ -156,7 +138,6 @@ std::unique_ptr<policy::BrowserPolicyConnectorBase> browser_policy_connector_; std::unique_ptr<AwSSLHostStateDelegate> ssl_host_state_delegate_; std::unique_ptr<content::PermissionControllerDelegate> permission_manager_; - PrefChangeRegistrar pref_change_registrar_; SimpleFactoryKey simple_factory_key_;
diff --git a/android_webview/browser/aw_browser_main_parts.cc b/android_webview/browser/aw_browser_main_parts.cc index 724faf94..5fda767 100644 --- a/android_webview/browser/aw_browser_main_parts.cc +++ b/android_webview/browser/aw_browser_main_parts.cc
@@ -119,9 +119,9 @@ } void AwBrowserMainParts::PreMainMessageLoopRun() { + AwBrowserProcess::GetInstance()->PreMainMessageLoopRun(); AwBrowserContext* context = browser_client_->InitBrowserContext(); - context->PreMainMessageLoopRun(browser_client_->GetNonNetworkServiceNetLog()); - AwBrowserProcess::GetInstance()->InitSafeBrowsing(); + context->PreMainMessageLoopRun(); content::RenderFrameHost::AllowInjectingJavaScript(); }
diff --git a/android_webview/browser/aw_browser_policy_connector.cc b/android_webview/browser/aw_browser_policy_connector.cc index b33c337..0e2feed 100644 --- a/android_webview/browser/aw_browser_policy_connector.cc +++ b/android_webview/browser/aw_browser_policy_connector.cc
@@ -6,7 +6,7 @@ #include <memory> -#include "android_webview/browser/aw_browser_context.h" +#include "android_webview/browser/aw_browser_process.h" #include "base/bind.h" #include "components/policy/core/browser/android/android_combined_policy_provider.h" #include "components/policy/core/browser/configuration_policy_handler_list.h"
diff --git a/android_webview/browser/aw_browser_process.cc b/android_webview/browser/aw_browser_process.cc index 811cc3f..042b08c 100644 --- a/android_webview/browser/aw_browser_process.cc +++ b/android_webview/browser/aw_browser_process.cc
@@ -5,14 +5,29 @@ #include "android_webview/browser/aw_browser_process.h" #include "android_webview/browser/aw_browser_context.h" +#include "base/base_paths_posix.h" +#include "base/path_service.h" #include "base/task/post_task.h" #include "content/public/browser/browser_task_traits.h" #include "content/public/browser/browser_thread.h" +#include "services/network/public/cpp/features.h" using content::BrowserThread; namespace android_webview { +namespace prefs { + +// String that specifies the Android account type to use for Negotiate +// authentication. +const char kAuthAndroidNegotiateAccountType[] = + "auth.android_negotiate_account_type"; + +// Whitelist containing servers for which Integrated Authentication is enabled. +const char kAuthServerWhitelist[] = "auth.server_whitelist"; + +} // namespace prefs + namespace { AwBrowserProcess* g_aw_browser_process = nullptr; } // namespace @@ -32,6 +47,22 @@ g_aw_browser_process = nullptr; } +void AwBrowserProcess::PreMainMessageLoopRun() { + if (base::FeatureList::IsEnabled(network::features::kNetworkService)) { + pref_change_registrar_.Init(local_state()); + auto auth_pref_callback = base::BindRepeating( + &AwBrowserProcess::OnAuthPrefsChanged, base::Unretained(this)); + pref_change_registrar_.Add(prefs::kAuthServerWhitelist, auth_pref_callback); + pref_change_registrar_.Add(prefs::kAuthAndroidNegotiateAccountType, + auth_pref_callback); + } + + if (!base::FeatureList::IsEnabled(network::features::kNetworkService)) { + CreateURLRequestContextGetter(); + } + InitSafeBrowsing(); +} + PrefService* AwBrowserProcess::local_state() { if (!local_state_) CreateLocalState(); @@ -51,8 +82,8 @@ } void AwBrowserProcess::CreateSafeBrowsingUIManager() { - safe_browsing_ui_manager_ = new AwSafeBrowsingUIManager( - AwBrowserContext::GetDefault()->GetAwURLRequestContext()); + safe_browsing_ui_manager_ = + new AwSafeBrowsingUIManager(AwBrowserProcess::GetAwURLRequestContext()); } void AwBrowserProcess::CreateSafeBrowsingWhitelistManager() { @@ -110,4 +141,60 @@ return safe_browsing_ui_manager_.get(); } +// static +void AwBrowserProcess::RegisterNetworkContextLocalStatePrefs( + PrefRegistrySimple* pref_registry) { + pref_registry->RegisterStringPref(prefs::kAuthServerWhitelist, std::string()); + pref_registry->RegisterStringPref(prefs::kAuthAndroidNegotiateAccountType, + std::string()); +} + +network::mojom::HttpAuthDynamicParamsPtr +AwBrowserProcess::CreateHttpAuthDynamicParams() { + network::mojom::HttpAuthDynamicParamsPtr auth_dynamic_params = + network::mojom::HttpAuthDynamicParams::New(); + + auth_dynamic_params->server_whitelist = + local_state()->GetString(prefs::kAuthServerWhitelist); + auth_dynamic_params->android_negotiate_account_type = + local_state()->GetString(prefs::kAuthAndroidNegotiateAccountType); + + return auth_dynamic_params; +} + +void AwBrowserProcess::OnAuthPrefsChanged() { + content::GetNetworkService()->ConfigureHttpAuthPrefs( + CreateHttpAuthDynamicParams()); +} + +namespace { +std::unique_ptr<net::ProxyConfigServiceAndroid> CreateProxyConfigService() { + std::unique_ptr<net::ProxyConfigServiceAndroid> config_service_android = + std::make_unique<net::ProxyConfigServiceAndroid>( + base::CreateSingleThreadTaskRunnerWithTraits({BrowserThread::IO}), + base::ThreadTaskRunnerHandle::Get()); + + config_service_android->set_exclude_pac_url(true); + return config_service_android; +} +} // namespace + +// Default profile reuses global URLRequestGetter +void AwBrowserProcess::CreateURLRequestContextGetter() { + DCHECK(!base::FeatureList::IsEnabled(network::features::kNetworkService)); + base::FilePath cache_path; + if (!base::PathService::Get(base::DIR_CACHE, &cache_path)) { + NOTREACHED() << "Failed to get app cache directory for Android WebView"; + } + cache_path = + cache_path.Append(FILE_PATH_LITERAL("org.chromium.android_webview")); + + url_request_context_getter_ = new AwURLRequestContextGetter( + cache_path, CreateProxyConfigService(), local_state(), new net::NetLog()); +} + +AwURLRequestContextGetter* AwBrowserProcess::GetAwURLRequestContext() { + return url_request_context_getter_.get(); +} + } // namespace android_webview
diff --git a/android_webview/browser/aw_browser_process.h b/android_webview/browser/aw_browser_process.h index a7aab8a..89eee6a4 100644 --- a/android_webview/browser/aw_browser_process.h +++ b/android_webview/browser/aw_browser_process.h
@@ -7,15 +7,31 @@ #ifndef ANDROID_WEBVIEW_BROWSER_AW_BROWSER_PROCESS_H_ #define ANDROID_WEBVIEW_BROWSER_AW_BROWSER_PROCESS_H_ +#include "android_webview/browser/aw_browser_context.h" #include "android_webview/browser/aw_feature_list_creator.h" +#include "android_webview/browser/net/aw_url_request_context_getter.h" #include "android_webview/browser/safe_browsing/aw_safe_browsing_ui_manager.h" #include "android_webview/browser/safe_browsing/aw_safe_browsing_whitelist_manager.h" +#include "base/feature_list.h" +#include "components/prefs/pref_change_registrar.h" #include "components/prefs/pref_service.h" #include "components/safe_browsing/android/remote_database_manager.h" #include "components/safe_browsing/triggers/trigger_manager.h" +#include "content/public/browser/network_service_instance.h" +#include "net/log/net_log.h" +#include "services/network/network_service.h" +#include "services/network/public/cpp/features.h" namespace android_webview { +namespace prefs { + +// Used for Kerberos authentication. +extern const char kAuthAndroidNegotiateAccountType[]; +extern const char kAuthServerWhitelist[]; + +} // namespace prefs + class AwBrowserProcess { public: AwBrowserProcess(AwFeatureListCreator* aw_feature_list_creator); @@ -43,10 +59,23 @@ // Called on UI and IO threads. AwSafeBrowsingUIManager* GetSafeBrowsingUIManager() const; + static void RegisterNetworkContextLocalStatePrefs( + PrefRegistrySimple* pref_registry); + // Constructs HttpAuthDynamicParams based on |local_state_|. + network::mojom::HttpAuthDynamicParamsPtr CreateHttpAuthDynamicParams(); + + AwURLRequestContextGetter* GetAwURLRequestContext(); + + void PreMainMessageLoopRun(); + private: void CreateSafeBrowsingUIManager(); void CreateSafeBrowsingWhitelistManager(); + void OnAuthPrefsChanged(); + + void CreateURLRequestContextGetter(); + // If non-null, this object holds a pref store that will be taken by // AwBrowserProcess to create the |local_state_|. // The AwFeatureListCreator is owned by AwMainDelegate. @@ -65,11 +94,15 @@ safe_browsing_db_manager_; bool safe_browsing_db_manager_started_ = false; + PrefChangeRegistrar pref_change_registrar_; + // TODO(amalova): Consider to make WhitelistManager per-profile. // Accessed on UI and IO threads. std::unique_ptr<AwSafeBrowsingWhitelistManager> safe_browsing_whitelist_manager_; + scoped_refptr<AwURLRequestContextGetter> url_request_context_getter_; + DISALLOW_COPY_AND_ASSIGN(AwBrowserProcess); };
diff --git a/android_webview/browser/aw_content_browser_client.cc b/android_webview/browser/aw_content_browser_client.cc index c0271b7..8b65d01 100644 --- a/android_webview/browser/aw_content_browser_client.cc +++ b/android_webview/browser/aw_content_browser_client.cc
@@ -96,7 +96,6 @@ #include "mojo/public/cpp/bindings/pending_associated_receiver.h" #include "net/android/network_library.h" #include "net/http/http_util.h" -#include "net/log/net_log.h" #include "net/ssl/ssl_cert_request_info.h" #include "net/ssl/ssl_info.h" #include "services/network/network_service.h" @@ -331,9 +330,6 @@ frame_interfaces_.AddInterface( base::BindRepeating(&DummyBindPasswordManagerDriver)); sniff_file_urls_ = AwSettings::GetAllowSniffingFileUrls(); - - if (!base::FeatureList::IsEnabled(network::features::kNetworkService)) - non_network_service_net_log_.reset(new net::NetLog()); } AwContentBrowserClient::~AwContentBrowserClient() {} @@ -357,12 +353,10 @@ if (!base::FeatureList::IsEnabled(network::features::kNetworkService)) return nullptr; - // There is only one BrowserContext in WebView, so initialize this now as it - // depends on the PrefService which is owned by the BrowserContext. - auto* aw_context = static_cast<AwBrowserContext*>(context); content::GetNetworkService()->ConfigureHttpAuthPrefs( - aw_context->CreateHttpAuthDynamicParams()); + AwBrowserProcess::GetInstance()->CreateHttpAuthDynamicParams()); + auto* aw_context = static_cast<AwBrowserContext*>(context); network::mojom::NetworkContextPtr network_context; network::mojom::NetworkContextParamsPtr context_params = aw_context->GetNetworkContextParams(in_memory, relative_partition_path); @@ -626,10 +620,6 @@ AwResourceDispatcherHostDelegate::ResourceDispatcherHostCreated(); } -net::NetLog* AwContentBrowserClient::GetNonNetworkServiceNetLog() { - return non_network_service_net_log_.get(); -} - base::FilePath AwContentBrowserClient::GetDefaultDownloadDirectory() { // Android WebView does not currently use the Chromium downloads system. // Download requests are cancelled immedately when recognized; see
diff --git a/android_webview/browser/aw_content_browser_client.h b/android_webview/browser/aw_content_browser_client.h index 05e1ebdd..9b34344 100644 --- a/android_webview/browser/aw_content_browser_client.h +++ b/android_webview/browser/aw_content_browser_client.h
@@ -21,10 +21,6 @@ class RenderFrameHost; } -namespace net { -class NetLog; -} - namespace safe_browsing { class UrlCheckerDelegate; } @@ -271,9 +267,6 @@ scoped_refptr<safe_browsing::UrlCheckerDelegate> GetSafeBrowsingUrlCheckerDelegate(); - // TODO(eroman): Remove once WebView has switched over to NetworkService. - std::unique_ptr<net::NetLog> non_network_service_net_log_; - // Android WebView currently has a single global (non-off-the-record) browser // context. std::unique_ptr<AwBrowserContext> browser_context_;
diff --git a/android_webview/browser/aw_feature_list_creator.cc b/android_webview/browser/aw_feature_list_creator.cc index be90a46..6611973e 100644 --- a/android_webview/browser/aw_feature_list_creator.cc +++ b/android_webview/browser/aw_feature_list_creator.cc
@@ -11,6 +11,7 @@ #include <vector> #include "android_webview/browser/aw_browser_context.h" +#include "android_webview/browser/aw_browser_process.h" #include "android_webview/browser/aw_metrics_service_client.h" #include "android_webview/browser/aw_variations_seed_bridge.h" #include "android_webview/browser/net/aw_url_request_context_getter.h" @@ -79,6 +80,7 @@ #if BUILDFLAG(ENABLE_MOJO_CDM) cdm::MediaDrmStorageImpl::RegisterProfilePrefs(pref_registry.get()); #endif + AwBrowserProcess::RegisterNetworkContextLocalStatePrefs(pref_registry.get()); PrefServiceFactory pref_service_factory;
diff --git a/android_webview/browser/aw_proxy_controller.cc b/android_webview/browser/aw_proxy_controller.cc index ba648c74..02bc7ed 100644 --- a/android_webview/browser/aw_proxy_controller.cc +++ b/android_webview/browser/aw_proxy_controller.cc
@@ -3,6 +3,7 @@ // found in the LICENSE file. #include "android_webview/browser/aw_browser_context.h" +#include "android_webview/browser/aw_browser_process.h" #include "android_webview/browser/net/aw_proxy_config_monitor.h" #include "android_webview/browser/net/aw_url_request_context_getter.h" #include "android_webview/native_jni/AwProxyController_jni.h" @@ -81,7 +82,7 @@ ScopedJavaGlobalRef<jobject>(env, executor))); } else { result = - AwBrowserContext::GetDefault() + AwBrowserProcess::GetInstance() ->GetAwURLRequestContext() ->SetProxyOverride( proxy_rules, bypass_rules, @@ -104,7 +105,7 @@ ScopedJavaGlobalRef<jobject>(env, listener), ScopedJavaGlobalRef<jobject>(env, executor))); } else { - AwBrowserContext::GetDefault() + AwBrowserProcess::GetInstance() ->GetAwURLRequestContext() ->ClearProxyOverride(base::BindOnce( &ProxyOverrideChanged, ScopedJavaGlobalRef<jobject>(env, obj),
diff --git a/android_webview/browser/net/aw_url_request_context_getter.cc b/android_webview/browser/net/aw_url_request_context_getter.cc index 95c7541..d0661d5 100644 --- a/android_webview/browser/net/aw_url_request_context_getter.cc +++ b/android_webview/browser/net/aw_url_request_context_getter.cc
@@ -10,6 +10,7 @@ #include <vector> #include "android_webview/browser/aw_browser_context.h" +#include "android_webview/browser/aw_browser_process.h" #include "android_webview/browser/aw_content_browser_client.h" #include "android_webview/browser/aw_feature_list.h" #include "android_webview/browser/net/aw_cookie_store_wrapper.h"
diff --git a/android_webview/browser/net/aw_url_request_context_getter_unittest.cc b/android_webview/browser/net/aw_url_request_context_getter_unittest.cc index 488b31e..6289d94 100644 --- a/android_webview/browser/net/aw_url_request_context_getter_unittest.cc +++ b/android_webview/browser/net/aw_url_request_context_getter_unittest.cc
@@ -7,6 +7,7 @@ #include <memory> #include "android_webview/browser/aw_browser_context.h" +#include "android_webview/browser/aw_browser_process.h" #include "base/android/jni_android.h" #include "base/files/scoped_temp_dir.h" #include "base/memory/ref_counted.h" @@ -70,7 +71,8 @@ ASSERT_TRUE(env_); pref_service_ = std::make_unique<TestingPrefServiceSimple>(); - AwBrowserContext::RegisterPrefs(pref_service_->registry()); + AwBrowserProcess::RegisterNetworkContextLocalStatePrefs( + pref_service_->registry()); std::unique_ptr<net::ProxyConfigServiceAndroid> config_service_android; config_service_android.reset(static_cast<net::ProxyConfigServiceAndroid*>(
diff --git a/ash/BUILD.gn b/ash/BUILD.gn index cda44f2..0a0c0db 100644 --- a/ash/BUILD.gn +++ b/ash/BUILD.gn
@@ -369,11 +369,6 @@ "keyboard/virtual_keyboard_container_layout_manager.h", "keyboard/virtual_keyboard_controller.cc", "keyboard/virtual_keyboard_controller.h", - "kiosk_next/kiosk_next_home_controller.cc", - "kiosk_next/kiosk_next_home_controller.h", - "kiosk_next/kiosk_next_shell_controller_impl.cc", - "kiosk_next/kiosk_next_shell_controller_impl.h", - "kiosk_next/kiosk_next_shell_observer.h", "laser/laser_pointer_controller.cc", "laser/laser_pointer_controller.h", "laser/laser_pointer_view.cc", @@ -564,8 +559,6 @@ "shelf/shelf_background_animator.cc", "shelf/shelf_background_animator.h", "shelf/shelf_background_animator_observer.h", - "shelf/shelf_bezel_event_handler.cc", - "shelf/shelf_bezel_event_handler.h", "shelf/shelf_bubble.cc", "shelf/shelf_bubble.h", "shelf/shelf_button.cc", @@ -1668,10 +1661,6 @@ "keyboard/keyboard_controller_impl_unittest.cc", "keyboard/virtual_keyboard_controller_unittest.cc", "keyboard/virtual_keyboard_unittest.cc", - "kiosk_next/kiosk_next_shell_test_util.cc", - "kiosk_next/kiosk_next_shell_test_util.h", - "kiosk_next/mock_kiosk_next_shell_client.cc", - "kiosk_next/mock_kiosk_next_shell_client.h", "laser/laser_pointer_controller_unittest.cc", "laser/laser_segment_utils_unittest.cc", "lock_screen_action/lock_screen_action_background_controller_impl_unittest.cc",
diff --git a/ash/accelerators/exit_warning_handler.cc b/ash/accelerators/exit_warning_handler.cc index a274a69..51dedf1 100644 --- a/ash/accelerators/exit_warning_handler.cc +++ b/ash/accelerators/exit_warning_handler.cc
@@ -147,7 +147,7 @@ params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.accept_events = false; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.delegate = delegate; params.bounds = bounds; params.name = "ExitWarningWindow";
diff --git a/ash/ash_prefs.cc b/ash/ash_prefs.cc index 48d756b..22bf7c1c 100644 --- a/ash/ash_prefs.cc +++ b/ash/ash_prefs.cc
@@ -9,7 +9,6 @@ #include "ash/assistant/assistant_controller.h" #include "ash/detachable_base/detachable_base_handler.h" #include "ash/display/display_prefs.h" -#include "ash/kiosk_next/kiosk_next_shell_controller_impl.h" #include "ash/login/login_screen_controller.h" #include "ash/magnifier/docked_magnifier_controller_impl.h" #include "ash/media/media_controller_impl.h" @@ -39,7 +38,6 @@ BluetoothPowerController::RegisterProfilePrefs(registry); CapsLockNotificationController::RegisterProfilePrefs(registry, for_test); DockedMagnifierControllerImpl::RegisterProfilePrefs(registry, for_test); - KioskNextShellControllerImpl::RegisterProfilePrefs(registry, for_test); LoginScreenController::RegisterProfilePrefs(registry, for_test); LogoutButtonTray::RegisterProfilePrefs(registry); MediaControllerImpl::RegisterProfilePrefs(registry);
diff --git a/ash/assistant/ui/assistant_container_view.cc b/ash/assistant/ui/assistant_container_view.cc index ff5688f..8fe6e2e 100644 --- a/ash/assistant/ui/assistant_container_view.cc +++ b/ash/assistant/ui/assistant_container_view.cc
@@ -312,7 +312,7 @@ views::Widget* widget) const { params->context = delegate_->GetRootWindowForNewWindows(); params->corner_radius = kCornerRadiusDip; - params->keep_on_top = true; + params->z_order = ui::ZOrderLevel::kFloatingWindow; } views::ClientView* AssistantContainerView::CreateClientView(
diff --git a/ash/display/shared_display_edge_indicator.cc b/ash/display/shared_display_edge_indicator.cc index cc3af89..9e795794 100644 --- a/ash/display/shared_display_edge_indicator.cc +++ b/ash/display/shared_display_edge_indicator.cc
@@ -51,7 +51,7 @@ params.context = Shell::GetRootWindowControllerWithDisplayId(display.id()) ->GetRootWindow(); params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; widget->set_focus_on_creation(false); widget->Init(params); widget->SetVisibilityChangedAnimationsEnabled(false);
diff --git a/ash/display/touch_calibrator_view.cc b/ash/display/touch_calibrator_view.cc index 015fd998..18613cd5 100644 --- a/ash/display/touch_calibrator_view.cc +++ b/ash/display/touch_calibrator_view.cc
@@ -87,7 +87,7 @@ views::Widget::InitParams params; params.type = views::Widget::InitParams::TYPE_WINDOW_FRAMELESS; params.name = kWidgetName; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingWindow; params.accept_events = true; params.activatable = views::Widget::InitParams::ACTIVATABLE_NO; params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET;
diff --git a/ash/drag_drop/drag_image_view.cc b/ash/drag_drop/drag_image_view.cc index 8ed7d4b04..73e9da60 100644 --- a/ash/drag_drop/drag_image_view.cc +++ b/ash/drag_drop/drag_image_view.cc
@@ -25,7 +25,6 @@ Widget::InitParams params; params.type = Widget::InitParams::TYPE_TOOLTIP; params.name = "DragWidget"; - params.keep_on_top = true; params.accept_events = false; params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.shadow_type = Widget::InitParams::SHADOW_TYPE_NONE; @@ -48,7 +47,6 @@ DCHECK(root_window); widget_ = CreateDragWidget(root_window); widget_->SetContentsView(this); - widget_->SetAlwaysOnTop(true); // We are owned by the DragDropController. set_owned_by_client();
diff --git a/ash/kiosk_next/OWNERS b/ash/kiosk_next/OWNERS deleted file mode 100644 index 76ae40e1..0000000 --- a/ash/kiosk_next/OWNERS +++ /dev/null
@@ -1,6 +0,0 @@ -agawronska@chromium.org -brunoad@chromium.org -ltenorio@chromium.org -michaelpg@chromium.org - -# COMPONENT: UI>Shell>KioskNext
diff --git a/ash/kiosk_next/kiosk_next_home_controller.cc b/ash/kiosk_next/kiosk_next_home_controller.cc deleted file mode 100644 index 6015dcd8..0000000 --- a/ash/kiosk_next/kiosk_next_home_controller.cc +++ /dev/null
@@ -1,163 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ash/kiosk_next/kiosk_next_home_controller.h" - -#include <memory> - -#include "ash/display/screen_orientation_controller.h" -#include "ash/public/cpp/shell_window_ids.h" -#include "ash/screen_util.h" -#include "ash/shell.h" -#include "ash/wm/container_finder.h" -#include "ash/wm/overview/overview_controller.h" -#include "ash/wm/toplevel_window_event_handler.h" -#include "ash/wm/window_util.h" -#include "ash/wm/wm_event.h" -#include "base/logging.h" -#include "ui/aura/window.h" -#include "ui/base/hit_test.h" -#include "ui/compositor/layer.h" -#include "ui/compositor/layer_animator.h" -#include "ui/compositor/scoped_layer_animation_settings.h" -#include "ui/display/screen.h" -#include "ui/events/event_target.h" -#include "ui/gfx/geometry/rect.h" -#include "ui/gfx/transform.h" - -namespace ash { - -KioskNextHomeController::KioskNextHomeController() { - display::Screen::GetScreen()->AddObserver(this); - - home_screen_container_ = Shell::GetPrimaryRootWindow()->GetChildById( - kShellWindowId_HomeScreenContainer); - home_screen_container_->AddObserver(this); - if (!home_screen_container_->children().empty()) { - DCHECK_EQ(1u, home_screen_container_->children().size()); - home_screen_window_ = home_screen_container_->children()[0]; - } -} - -KioskNextHomeController::~KioskNextHomeController() { - display::Screen::GetScreen()->RemoveObserver(this); - - if (home_screen_container_) - home_screen_container_->RemoveObserver(this); -} - -void KioskNextHomeController::ShowHomeScreenView() { - // Nothing to do because the contents of the app window are always shown - // on the primary display. - // HomeScreenController will show/hide the root home screen window. -} - -aura::Window* KioskNextHomeController::GetHomeScreenWindow() { - return home_screen_window_; -} - -void KioskNextHomeController::UpdateYPositionAndOpacityForHomeLauncher( - int y_position_in_screen, - float opacity, - UpdateAnimationSettingsCallback callback) { - aura::Window* window = GetHomeScreenWindow(); - if (!window) - return; - - const gfx::Transform translation(1.f, 0.f, 0.f, 1.f, 0.f, - static_cast<float>(y_position_in_screen)); - ui::Layer* layer = window->layer(); - layer->GetAnimator()->StopAnimating(); - std::unique_ptr<ui::ScopedLayerAnimationSettings> settings; - if (!callback.is_null()) { - settings = std::make_unique<ui::ScopedLayerAnimationSettings>( - layer->GetAnimator()); - callback.Run(settings.get()); - } - layer->SetOpacity(opacity); - layer->SetTransform(translation); -} - -void KioskNextHomeController::UpdateAfterHomeLauncherShown() {} - -base::Optional<base::TimeDelta> -KioskNextHomeController::GetOptionalAnimationDuration() { - return base::nullopt; -} - -bool KioskNextHomeController::ShouldShowShelfOnHomeScreen() const { - return false; -} - -bool KioskNextHomeController::ShouldShowStatusAreaOnHomeScreen() const { - return true; -} - -void KioskNextHomeController::OnDisplayMetricsChanged( - const display::Display& display, - uint32_t changed_metrics) { - aura::Window* window = GetHomeScreenWindow(); - if (!window) - return; - - // Update the window to reflect the display bounds. - const gfx::Rect bounds = - screen_util::SnapBoundsToDisplayEdge(window->bounds(), window); - window->SetBounds(bounds); - const wm::WMEvent event(wm::WM_EVENT_WORKAREA_BOUNDS_CHANGED); - wm::GetWindowState(window)->OnWMEvent(&event); -} - -void KioskNextHomeController::OnWindowAdded(aura::Window* new_window) { - DCHECK(!home_screen_window_); - DCHECK_EQ(new_window->type(), aura::client::WindowType::WINDOW_TYPE_NORMAL); - home_screen_window_ = new_window; - - Shell::Get()->screen_orientation_controller()->LockOrientationForWindow( - home_screen_window_, OrientationLockType::kLandscape); - Shell::Get()->AddPreTargetHandler(this, ui::EventTarget::Priority::kSystem); -} - -void KioskNextHomeController::OnWillRemoveWindow(aura::Window* window) { - DCHECK_EQ(home_screen_window_, window); - Shell::Get()->RemovePreTargetHandler(this); - home_screen_window_ = nullptr; -} - -void KioskNextHomeController::OnWindowDestroying(aura::Window* window) { - if (window == home_screen_container_) - home_screen_container_ = nullptr; -} - -void KioskNextHomeController::OnGestureEvent(ui::GestureEvent* event) { - aura::Window* target = static_cast<aura::Window*>(event->target()); - int component = wm::GetNonClientComponent(target, event->location()); - - aura::Window* new_target = - ToplevelWindowEventHandler::GetTargetForClientAreaGesture(event, target); - - if (new_target) - target = new_target; - - if (!(target == home_screen_window_ || started_handling_events_)) - return; - - if (component == HTCLIENT && event->type() == ui::ET_GESTURE_SCROLL_BEGIN) { - auto* overview_controller = Shell::Get()->overview_controller(); - if (!overview_controller->InOverviewSession()) - overview_controller->StartOverview(); - started_handling_events_ = true; - } - - if (started_handling_events_) { - event->SetHandled(); - event->StopPropagation(); - - if (event->type() == ui::EventType::ET_GESTURE_SCROLL_END || - event->type() == ui::EventType::ET_GESTURE_END) - started_handling_events_ = false; - } -} - -} // namespace ash
diff --git a/ash/kiosk_next/kiosk_next_home_controller.h b/ash/kiosk_next/kiosk_next_home_controller.h deleted file mode 100644 index 2c24d7f..0000000 --- a/ash/kiosk_next/kiosk_next_home_controller.h +++ /dev/null
@@ -1,67 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef ASH_KIOSK_NEXT_KIOSK_NEXT_HOME_CONTROLLER_H_ -#define ASH_KIOSK_NEXT_KIOSK_NEXT_HOME_CONTROLLER_H_ - -#include "ash/ash_export.h" -#include "ash/home_screen/home_screen_delegate.h" -#include "base/macros.h" -#include "ui/aura/window_observer.h" -#include "ui/display/display_observer.h" -#include "ui/events/event_handler.h" - -namespace ui { -class GestureEvent; -} - -namespace ash { - -// KioskNextHomeController manages the Home window for the Kiosk Next shell. -// TODO(michaelpg): Show a slide-down animation when opening Overview. -// TODO(michaelpg): Suppress tap events in the Kiosk Next Home window when a -// gesture event triggers Overview this way. -class ASH_EXPORT KioskNextHomeController : public HomeScreenDelegate, - public display::DisplayObserver, - public aura::WindowObserver, - public ui::EventHandler { - public: - KioskNextHomeController(); - ~KioskNextHomeController() override; - - // HomeScreenDelegate: - void ShowHomeScreenView() override; - aura::Window* GetHomeScreenWindow() override; - void UpdateYPositionAndOpacityForHomeLauncher( - int y_position_in_screen, - float opacity, - UpdateAnimationSettingsCallback callback) override; - void UpdateAfterHomeLauncherShown() override; - base::Optional<base::TimeDelta> GetOptionalAnimationDuration() override; - bool ShouldShowShelfOnHomeScreen() const override; - bool ShouldShowStatusAreaOnHomeScreen() const override; - - // display::DisplayObserver: - void OnDisplayMetricsChanged(const display::Display& display, - uint32_t changed_metrics) override; - - // aura::WindowObserver: - void OnWindowAdded(aura::Window* new_window) override; - void OnWillRemoveWindow(aura::Window* window) override; - void OnWindowDestroying(aura::Window* window) override; - - // ui::EventHandler: - void OnGestureEvent(ui::GestureEvent* event) override; - - private: - bool started_handling_events_ = false; - aura::Window* home_screen_container_ = nullptr; - aura::Window* home_screen_window_ = nullptr; - - DISALLOW_COPY_AND_ASSIGN(KioskNextHomeController); -}; - -} // namespace ash - -#endif // ASH_KIOSK_NEXT_KIOSK_NEXT_HOME_CONTROLLER_H_
diff --git a/ash/kiosk_next/kiosk_next_shell_controller_impl.cc b/ash/kiosk_next/kiosk_next_shell_controller_impl.cc deleted file mode 100644 index 27e4e63..0000000 --- a/ash/kiosk_next/kiosk_next_shell_controller_impl.cc +++ /dev/null
@@ -1,106 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ash/kiosk_next/kiosk_next_shell_controller_impl.h" - -#include <memory> -#include <utility> - -#include "ash/home_screen/home_screen_controller.h" -#include "ash/kiosk_next/kiosk_next_home_controller.h" -#include "ash/kiosk_next/kiosk_next_shell_observer.h" -#include "ash/public/cpp/ash_features.h" -#include "ash/public/cpp/ash_pref_names.h" -#include "ash/public/cpp/shelf_model.h" -#include "ash/session/session_controller_impl.h" -#include "ash/shell.h" -#include "ash/strings/grit/ash_strings.h" -#include "base/metrics/histogram_macros.h" -#include "chromeos/strings/grit/chromeos_strings.h" -#include "components/account_id/account_id.h" -#include "components/prefs/pref_registry_simple.h" -#include "components/prefs/pref_service.h" -#include "ui/base/l10n/l10n_util.h" - -namespace ash { - -KioskNextShellControllerImpl::KioskNextShellControllerImpl() = default; - -KioskNextShellControllerImpl::~KioskNextShellControllerImpl() = default; - -// static -void KioskNextShellControllerImpl::RegisterProfilePrefs( - PrefRegistrySimple* registry, - bool for_test) { - if (for_test) { - registry->RegisterBooleanPref(prefs::kKioskNextShellEnabled, false, - PrefRegistry::PUBLIC); - return; - } -} - -void KioskNextShellControllerImpl::SetClientAndLaunchSession( - KioskNextShellClient* client) { - DCHECK_NE(!!client, !!client_); - client_ = client; - LaunchKioskNextShellIfEnabled(); -} - -bool KioskNextShellControllerImpl::IsEnabled() { - return kiosk_next_enabled_; -} - -void KioskNextShellControllerImpl::AddObserver( - KioskNextShellObserver* observer) { - observer_list_.AddObserver(observer); -} - -void KioskNextShellControllerImpl::RemoveObserver( - KioskNextShellObserver* observer) { - observer_list_.RemoveObserver(observer); -} - -void KioskNextShellControllerImpl::OnActiveUserPrefServiceChanged( - PrefService* pref_service) { - LaunchKioskNextShellIfEnabled(); -} - -void KioskNextShellControllerImpl::LaunchKioskNextShellIfEnabled() { - SessionControllerImpl* session_controller = - Shell::Get()->session_controller(); - PrefService* pref_service = session_controller->GetPrimaryUserPrefService(); - if (!pref_service) - return; - - if (!client_) - return; - - bool prev_kiosk_next_enabled = kiosk_next_enabled_; - kiosk_next_enabled_ = - base::FeatureList::IsEnabled(features::kKioskNextShell) && - pref_service->GetBoolean(prefs::kKioskNextShellEnabled); - if (!kiosk_next_enabled_ || prev_kiosk_next_enabled) - return; - - // Replace the AppListController with a KioskNextHomeController. - kiosk_next_home_controller_ = std::make_unique<KioskNextHomeController>(); - Shell::Get()->home_screen_controller()->SetDelegate( - kiosk_next_home_controller_.get()); - Shell::Get()->RemoveAppListController(); - - client_->LaunchKioskNextShell( - session_controller->GetPrimaryUserSession()->user_info.account_id); - UMA_HISTOGRAM_BOOLEAN("KioskNextShell.Launched", true); - - // Since the kiosk next shelf only has navigation buttons (back and home), - // its shelf model for apps is empty. - shelf_model_ = std::make_unique<ShelfModel>(); - - // Notify observers that KioskNextShell has been enabled. - for (KioskNextShellObserver& observer : observer_list_) { - observer.OnKioskNextEnabled(); - } -} - -} // namespace ash
diff --git a/ash/kiosk_next/kiosk_next_shell_controller_impl.h b/ash/kiosk_next/kiosk_next_shell_controller_impl.h deleted file mode 100644 index acb5c9b2..0000000 --- a/ash/kiosk_next/kiosk_next_shell_controller_impl.h +++ /dev/null
@@ -1,75 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_CONTROLLER_IMPL_H_ -#define ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_CONTROLLER_IMPL_H_ - -#include <memory> - -#include "ash/ash_export.h" -#include "ash/kiosk_next/kiosk_next_shell_observer.h" -#include "ash/public/cpp/kiosk_next_shell.h" -#include "ash/session/session_observer.h" -#include "base/macros.h" -#include "base/observer_list.h" - -class PrefRegistrySimple; - -namespace ash { - -class KioskNextHomeController; -class ShelfModel; - -// KioskNextShellControllerImpl allows an ash consumer to manage a Kiosk Next -// session. During this session most system functions are disabled and we launch -// a specific app (Kiosk Next Home) that takes the whole screen. -class ASH_EXPORT KioskNextShellControllerImpl : public KioskNextShellController, - public SessionObserver { - public: - KioskNextShellControllerImpl(); - ~KioskNextShellControllerImpl() override; - - // Register prefs related to the Kiosk Next Shell. - static void RegisterProfilePrefs(PrefRegistrySimple* registry, bool for_test); - - // KioskNextShellController: - void SetClientAndLaunchSession(KioskNextShellClient* client) override; - - // Returns if the Kiosk Next Shell is enabled for the current user. If there's - // no signed-in user, this returns false. - bool IsEnabled(); - - void AddObserver(KioskNextShellObserver* observer); - void RemoveObserver(KioskNextShellObserver* observer); - - // SessionObserver: - void OnActiveUserPrefServiceChanged(PrefService* pref_service) override; - - ShelfModel* shelf_model() { return shelf_model_.get(); } - - private: - // Launches Kiosk Next if the pref is enabled and the KioskNextShellClient is - // available. - void LaunchKioskNextShellIfEnabled(); - - KioskNextShellClient* client_ = nullptr; - - base::ObserverList<KioskNextShellObserver> observer_list_; - ScopedSessionObserver session_observer_{this}; - bool kiosk_next_enabled_ = false; - - // Controls the KioskNext home screen when the Kiosk Next Shell is enabled. - std::unique_ptr<KioskNextHomeController> kiosk_next_home_controller_; - - // When KioskNextShell is enabled, only the home button and back button are - // made visible on the Shelf. KioskNextShellControllerImpl therefore hosts its - // own ShelfModel to control the entries visible on the shelf. - std::unique_ptr<ShelfModel> shelf_model_; - - DISALLOW_COPY_AND_ASSIGN(KioskNextShellControllerImpl); -}; - -} // namespace ash - -#endif // ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_CONTROLLER_IMPL_H_
diff --git a/ash/kiosk_next/kiosk_next_shell_observer.h b/ash/kiosk_next/kiosk_next_shell_observer.h deleted file mode 100644 index 9c57e864e..0000000 --- a/ash/kiosk_next/kiosk_next_shell_observer.h +++ /dev/null
@@ -1,21 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_OBSERVER_H_ -#define ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_OBSERVER_H_ - -#include "ash/ash_export.h" -#include "base/observer_list_types.h" - -namespace ash { - -class ASH_EXPORT KioskNextShellObserver : public base::CheckedObserver { - public: - // This method is only called once when KioskNextShell is enabled. - virtual void OnKioskNextEnabled() {} -}; - -} // namespace ash - -#endif // ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_OBSERVER_H_
diff --git a/ash/kiosk_next/kiosk_next_shell_test_util.cc b/ash/kiosk_next/kiosk_next_shell_test_util.cc deleted file mode 100644 index eacbae8..0000000 --- a/ash/kiosk_next/kiosk_next_shell_test_util.cc +++ /dev/null
@@ -1,40 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ash/kiosk_next/kiosk_next_shell_test_util.h" - -#include "ash/public/cpp/ash_pref_names.h" -#include "ash/session/session_controller_impl.h" -#include "ash/session/test_session_controller_client.h" -#include "ash/shell.h" -#include "components/prefs/pref_service.h" - -namespace ash { -namespace { - -const char kTestUserEmail[] = "primary_user1@test.com"; - -} // namespace - -void LogInKioskNextUser( - TestSessionControllerClient* session_controller_client) { - // Create session for user. - session_controller_client->AddUserSession( - kTestUserEmail, user_manager::USER_TYPE_REGULAR, - true /* enable_settings */, true /* provide_pref_service */); - - // Set the user's KioskNextShell preference. - PrefService* pref_service = - Shell::Get()->session_controller()->GetUserPrefServiceForUser( - AccountId::FromUserEmail(kTestUserEmail)); - pref_service->Set(prefs::kKioskNextShellEnabled, base::Value(true)); - - // Start the session after setting the pref. - session_controller_client->SwitchActiveUser( - AccountId::FromUserEmail(kTestUserEmail)); - session_controller_client->SetSessionState( - session_manager::SessionState::ACTIVE); -} - -} // namespace ash
diff --git a/ash/kiosk_next/kiosk_next_shell_test_util.h b/ash/kiosk_next/kiosk_next_shell_test_util.h deleted file mode 100644 index ee7c95a..0000000 --- a/ash/kiosk_next/kiosk_next_shell_test_util.h +++ /dev/null
@@ -1,17 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_TEST_UTIL_H_ -#define ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_TEST_UTIL_H_ - -namespace ash { - -class TestSessionControllerClient; - -// Logs in a user with Kiosk Next enabled. -void LogInKioskNextUser(TestSessionControllerClient* session_controller_client); - -} // namespace ash - -#endif // ASH_KIOSK_NEXT_KIOSK_NEXT_SHELL_TEST_UTIL_H_
diff --git a/ash/kiosk_next/mock_kiosk_next_shell_client.cc b/ash/kiosk_next/mock_kiosk_next_shell_client.cc deleted file mode 100644 index f9f78b7..0000000 --- a/ash/kiosk_next/mock_kiosk_next_shell_client.cc +++ /dev/null
@@ -1,17 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ash/kiosk_next/mock_kiosk_next_shell_client.h" - -namespace ash { - -MockKioskNextShellClient::MockKioskNextShellClient() { - KioskNextShellController::Get()->SetClientAndLaunchSession(this); -} - -MockKioskNextShellClient::~MockKioskNextShellClient() { - KioskNextShellController::Get()->SetClientAndLaunchSession(nullptr); -} - -} // namespace ash
diff --git a/ash/kiosk_next/mock_kiosk_next_shell_client.h b/ash/kiosk_next/mock_kiosk_next_shell_client.h deleted file mode 100644 index 9830ac0..0000000 --- a/ash/kiosk_next/mock_kiosk_next_shell_client.h +++ /dev/null
@@ -1,29 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef ASH_KIOSK_NEXT_MOCK_KIOSK_NEXT_SHELL_CLIENT_H_ -#define ASH_KIOSK_NEXT_MOCK_KIOSK_NEXT_SHELL_CLIENT_H_ - -#include "ash/public/cpp/kiosk_next_shell.h" -#include "base/macros.h" -#include "components/account_id/account_id.h" -#include "testing/gmock/include/gmock/gmock.h" - -namespace ash { - -class MockKioskNextShellClient : public KioskNextShellClient { - public: - MockKioskNextShellClient(); - ~MockKioskNextShellClient() override; - - // KioskNextShellClient: - MOCK_METHOD1(LaunchKioskNextShell, void(const AccountId& account_id)); - - private: - DISALLOW_COPY_AND_ASSIGN(MockKioskNextShellClient); -}; - -} // namespace ash - -#endif // ASH_KIOSK_NEXT_MOCK_KIOSK_NEXT_SHELL_CLIENT_H_
diff --git a/ash/public/cpp/BUILD.gn b/ash/public/cpp/BUILD.gn index c4f4d10e..92f715d8 100644 --- a/ash/public/cpp/BUILD.gn +++ b/ash/public/cpp/BUILD.gn
@@ -111,8 +111,6 @@ "keyboard_shortcut_viewer.h", "kiosk_app_menu.cc", "kiosk_app_menu.h", - "kiosk_next_shell.cc", - "kiosk_next_shell.h", "locale_update_controller.cc", "locale_update_controller.h", "lock_screen_widget_factory.cc",
diff --git a/ash/public/cpp/ash_pref_names.cc b/ash/public/cpp/ash_pref_names.cc index bb76172..4e2777d 100644 --- a/ash/public/cpp/ash_pref_names.cc +++ b/ash/public/cpp/ash_pref_names.cc
@@ -115,14 +115,6 @@ // regardless of the state of a11y features. const char kShouldAlwaysShowAccessibilityMenu[] = "settings.a11y.enable_menu"; -// A boolean pref that stores whether the user is eligible to start the Kiosk -// Next shell. -const char kKioskNextShellEligible[] = "ash.kiosk_next_shell.eligible"; - -// A boolean pref that stores whether the Kiosk Next Shell is enabled. When it -// is, we start it after sign in. -const char kKioskNextShellEnabled[] = "ash.kiosk_next_shell.enabled"; - // A boolean pref storing the enabled status of the Docked Magnifier feature. const char kDockedMagnifierEnabled[] = "ash.docked_magnifier.enabled"; // A double pref storing the scale value of the Docked Magnifier feature by
diff --git a/ash/public/cpp/ash_pref_names.h b/ash/public/cpp/ash_pref_names.h index e26744c..0a837ff 100644 --- a/ash/public/cpp/ash_pref_names.h +++ b/ash/public/cpp/ash_pref_names.h
@@ -45,9 +45,6 @@ ASH_PUBLIC_EXPORT extern const char kAccessibilityDictationEnabled[]; ASH_PUBLIC_EXPORT extern const char kShouldAlwaysShowAccessibilityMenu[]; -ASH_PUBLIC_EXPORT extern const char kKioskNextShellEligible[]; -ASH_PUBLIC_EXPORT extern const char kKioskNextShellEnabled[]; - ASH_PUBLIC_EXPORT extern const char kDockedMagnifierEnabled[]; ASH_PUBLIC_EXPORT extern const char kDockedMagnifierScale[]; ASH_PUBLIC_EXPORT extern const char
diff --git a/ash/public/cpp/kiosk_next_shell.cc b/ash/public/cpp/kiosk_next_shell.cc deleted file mode 100644 index cb9d503f..0000000 --- a/ash/public/cpp/kiosk_next_shell.cc +++ /dev/null
@@ -1,30 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ash/public/cpp/kiosk_next_shell.h" - -#include "base/logging.h" - -namespace ash { - -namespace { -KioskNextShellController* g_instance = nullptr; -} - -// static -KioskNextShellController* KioskNextShellController::Get() { - return g_instance; -} - -KioskNextShellController::KioskNextShellController() { - DCHECK_EQ(nullptr, g_instance); - g_instance = this; -} - -KioskNextShellController::~KioskNextShellController() { - DCHECK_EQ(this, g_instance); - g_instance = nullptr; -} - -} // namespace ash
diff --git a/ash/public/cpp/kiosk_next_shell.h b/ash/public/cpp/kiosk_next_shell.h deleted file mode 100644 index 7011e6c..0000000 --- a/ash/public/cpp/kiosk_next_shell.h +++ /dev/null
@@ -1,42 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef ASH_PUBLIC_CPP_KIOSK_NEXT_SHELL_H_ -#define ASH_PUBLIC_CPP_KIOSK_NEXT_SHELL_H_ - -#include "ash/public/cpp/ash_public_export.h" - -class AccountId; - -namespace ash { - -// Performs browser-side functionality for Kiosk Next, e.g. launching the -// KioskNextShell. -class ASH_PUBLIC_EXPORT KioskNextShellClient { - public: - // Launch the Kiosk Next Shell for the user identified by |account_id|. - virtual void LaunchKioskNextShell(const AccountId& account_id) = 0; - - protected: - virtual ~KioskNextShellClient() = default; -}; - -// Interface that allows Chrome to notify Ash when the KioskNextShellClient is -// ready. -class ASH_PUBLIC_EXPORT KioskNextShellController { - public: - static KioskNextShellController* Get(); - - // Registers the client, and if non-null, launches the Kiosk Next Shell - // session. - virtual void SetClientAndLaunchSession(KioskNextShellClient* client) = 0; - - protected: - KioskNextShellController(); - virtual ~KioskNextShellController(); -}; - -} // namespace ash - -#endif // ASH_PUBLIC_CPP_KIOSK_NEXT_SHELL_H_
diff --git a/ash/shelf/overflow_bubble_view.cc b/ash/shelf/overflow_bubble_view.cc index d7a9712..10e343e 100644 --- a/ash/shelf/overflow_bubble_view.cc +++ b/ash/shelf/overflow_bubble_view.cc
@@ -31,7 +31,7 @@ namespace ash { namespace { -// Padding between the end of the shelf in overview mode and the arrow button +// Padding between the end of the shelf in overflow mode and the arrow button // (if any). constexpr int kDistanceToArrowButton = kShelfButtonSpacing; @@ -41,6 +41,10 @@ // Sum of the shelf button size and the gap between shelf buttons. constexpr int kUnit = kShelfButtonSize + kShelfButtonSpacing; +// Decides whether the current first visible shelf icon of the overflow shelf +// should be hidden or fully shown when gesture scroll ends. +constexpr int kGestureDragThreshold = kShelfButtonSize / 2; + } // namespace //////////////////////////////////////////////////////////////////////////////// @@ -256,10 +260,31 @@ bool OverflowBubbleView::ProcessGestureEvent(const ui::GestureEvent& event) { // Handle scroll-related events, but don't do anything special for begin and // end. - if (event.type() == ui::ET_GESTURE_SCROLL_BEGIN || - event.type() == ui::ET_GESTURE_SCROLL_END) { + if (event.type() == ui::ET_GESTURE_SCROLL_BEGIN) { return true; } + + // Make sure that no visible shelf button is partially shown after gestures. + if (event.type() == ui::ET_GESTURE_END || + event.type() == ui::ET_GESTURE_SCROLL_END) { + int current_scroll_distance = shelf_->IsHorizontalAlignment() + ? scroll_offset_.x() + : scroll_offset_.y(); + const int residue = current_scroll_distance % kUnit; + + // if it does not need to adjust the location of the shelf view, + // return early. + if (current_scroll_distance == CalculateScrollUpperBound() || residue == 0) + return true; + + int offset = residue > kGestureDragThreshold ? kUnit - residue : -residue; + if (shelf_->IsHorizontalAlignment()) + ScrollByXOffset(offset, /*animate=*/true); + else + ScrollByYOffset(offset, /*animate=*/true); + return true; + } + if (event.type() != ui::ET_GESTURE_SCROLL_UPDATE) return false;
diff --git a/ash/shelf/shelf.cc b/ash/shelf/shelf.cc index 0324a082..245fff7 100644 --- a/ash/shelf/shelf.cc +++ b/ash/shelf/shelf.cc
@@ -13,7 +13,6 @@ #include "ash/public/cpp/shelf_model.h" #include "ash/public/cpp/shell_window_ids.h" #include "ash/root_window_controller.h" -#include "ash/shelf/shelf_bezel_event_handler.h" #include "ash/shelf/shelf_controller.h" #include "ash/shelf/shelf_focus_cycler.h" #include "ash/shelf/shelf_layout_manager.h" @@ -34,8 +33,7 @@ // Forwards mouse and gesture events to ShelfLayoutManager for auto-hide. class Shelf::AutoHideEventHandler : public ui::EventHandler { public: - explicit AutoHideEventHandler(ShelfLayoutManager* shelf_layout_manager) - : shelf_layout_manager_(shelf_layout_manager) { + explicit AutoHideEventHandler(Shelf* shelf) : shelf_(shelf) { Shell::Get()->AddPreTargetHandler(this); } ~AutoHideEventHandler() override { @@ -44,16 +42,36 @@ // ui::EventHandler: void OnMouseEvent(ui::MouseEvent* event) override { - shelf_layout_manager_->UpdateAutoHideForMouseEvent( + shelf_->shelf_layout_manager()->UpdateAutoHideForMouseEvent( event, static_cast<aura::Window*>(event->target())); } void OnGestureEvent(ui::GestureEvent* event) override { - shelf_layout_manager_->ProcessGestureEventOfAutoHideShelf( + shelf_->shelf_layout_manager()->ProcessGestureEventOfAutoHideShelf( event, static_cast<aura::Window*>(event->target())); } + void OnTouchEvent(ui::TouchEvent* event) override { + if (shelf_->auto_hide_behavior() != SHELF_AUTO_HIDE_BEHAVIOR_ALWAYS) + return; + + // The event target should be the shelf widget. + aura::Window* target = static_cast<aura::Window*>(event->target()); + if (target != Shelf::ForWindow(target)->shelf_widget()->GetNativeView()) + return; + + // The touch-pressing event may hide the shelf. Lock the shelf's auto hide + // state to give the shelf a chance to handle the touch event before it + // being hidden. + ShelfLayoutManager* shelf_layout_manager = shelf_->shelf_layout_manager(); + if (event->type() == ui::ET_TOUCH_PRESSED && shelf_->IsVisible()) { + shelf_layout_manager->LockAutoHideState(true); + } else if (event->type() == ui::ET_TOUCH_RELEASED || + event->type() == ui::ET_TOUCH_CANCELLED) { + shelf_layout_manager->LockAutoHideState(false); + } + } private: - ShelfLayoutManager* shelf_layout_manager_; + Shelf* shelf_; DISALLOW_COPY_AND_ASSIGN(AutoHideEventHandler); }; @@ -61,7 +79,6 @@ Shelf::Shelf() : shelf_locking_manager_(this), - bezel_event_handler_(std::make_unique<ShelfBezelEventHandler>(this)), shelf_focus_cycler_(std::make_unique<ShelfFocusCycler>(this)) {} Shelf::~Shelf() = default; @@ -347,7 +364,6 @@ void Shelf::WillDeleteShelfLayoutManager() { // Clear event handlers that might forward events to the destroyed instance. auto_hide_event_handler_.reset(); - bezel_event_handler_.reset(); DCHECK(shelf_layout_manager_); shelf_layout_manager_->RemoveObserver(this); @@ -360,8 +376,7 @@ if (new_state != SHELF_AUTO_HIDE) { auto_hide_event_handler_.reset(); } else if (!auto_hide_event_handler_) { - auto_hide_event_handler_ = - std::make_unique<AutoHideEventHandler>(shelf_layout_manager()); + auto_hide_event_handler_ = std::make_unique<AutoHideEventHandler>(this); } }
diff --git a/ash/shelf/shelf.h b/ash/shelf/shelf.h index 9a37ed1..394b8ea 100644 --- a/ash/shelf/shelf.h +++ b/ash/shelf/shelf.h
@@ -30,7 +30,6 @@ namespace ash { enum class AnimationChangeType; -class ShelfBezelEventHandler; class ShelfFocusCycler; class ShelfLayoutManager; class ShelfLayoutManagerTest; @@ -221,9 +220,6 @@ // Forwards mouse and gesture events to ShelfLayoutManager for auto-hide. std::unique_ptr<AutoHideEventHandler> auto_hide_event_handler_; - // Forwards touch gestures on a bezel sensor to the shelf. - std::unique_ptr<ShelfBezelEventHandler> bezel_event_handler_; - // Hands focus off to different parts of the shelf. std::unique_ptr<ShelfFocusCycler> shelf_focus_cycler_;
diff --git a/ash/shelf/shelf_bezel_event_handler.cc b/ash/shelf/shelf_bezel_event_handler.cc deleted file mode 100644 index 1531645..0000000 --- a/ash/shelf/shelf_bezel_event_handler.cc +++ /dev/null
@@ -1,93 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ash/shelf/shelf_bezel_event_handler.h" - -#include "ash/shelf/shelf.h" -#include "ash/shelf/shelf_layout_manager.h" -#include "ash/shelf/shelf_widget.h" -#include "ash/shell.h" -#include "ui/aura/window.h" -#include "ui/display/display.h" -#include "ui/display/screen.h" -#include "ui/events/event.h" -#include "ui/gfx/geometry/point.h" -#include "ui/gfx/geometry/rect.h" -#include "ui/wm/core/coordinate_conversion.h" - -namespace ash { - -ShelfBezelEventHandler::ShelfBezelEventHandler(Shelf* shelf) - : shelf_(shelf), in_touch_drag_(false) { - Shell::Get()->AddPreTargetHandler(this); -} - -ShelfBezelEventHandler::~ShelfBezelEventHandler() { - Shell::Get()->RemovePreTargetHandler(this); -} - -void ShelfBezelEventHandler::OnGestureEvent(ui::GestureEvent* event) { - gfx::Point point_in_screen(event->location()); - aura::Window* target = static_cast<aura::Window*>(event->target()); - ::wm::ConvertPointToScreen(target, &point_in_screen); - gfx::Rect screen = display::Screen::GetScreen() - ->GetDisplayNearestPoint(point_in_screen) - .bounds(); - if ((!screen.Contains(point_in_screen) && - IsShelfOnBezel(screen, point_in_screen)) || - in_touch_drag_) { - if (shelf_->ProcessGestureEvent(*event)) { - switch (event->type()) { - case ui::ET_GESTURE_SCROLL_BEGIN: - in_touch_drag_ = true; - break; - case ui::ET_GESTURE_SCROLL_END: - case ui::ET_SCROLL_FLING_START: - in_touch_drag_ = false; - break; - default: - break; - } - event->StopPropagation(); - } - } -} - -void ShelfBezelEventHandler::OnTouchEvent(ui::TouchEvent* event) { - if (shelf_->auto_hide_behavior() != SHELF_AUTO_HIDE_BEHAVIOR_ALWAYS) - return; - - // The event target should be the shelf widget. - aura::Window* target = static_cast<aura::Window*>(event->target()); - if (target != Shelf::ForWindow(target)->shelf_widget()->GetNativeView()) - return; - - // The touch-pressing event may hide the shelf. Lock the shelf's auto hide - // state to give the shelf a chance to handle the touch event before it being - // hidden. - ShelfLayoutManager* shelf_layout_manager = shelf_->shelf_layout_manager(); - if (event->type() == ui::ET_TOUCH_PRESSED && shelf_->IsVisible()) { - shelf_layout_manager->LockAutoHideState(true); - } else if (event->type() == ui::ET_TOUCH_RELEASED || - event->type() == ui::ET_TOUCH_CANCELLED) { - shelf_layout_manager->LockAutoHideState(false); - } -} - -bool ShelfBezelEventHandler::IsShelfOnBezel(const gfx::Rect& screen, - const gfx::Point& point) const { - switch (shelf_->alignment()) { - case SHELF_ALIGNMENT_BOTTOM: - case SHELF_ALIGNMENT_BOTTOM_LOCKED: - return point.y() >= screen.bottom(); - case SHELF_ALIGNMENT_LEFT: - return point.x() <= screen.x(); - case SHELF_ALIGNMENT_RIGHT: - return point.x() >= screen.right(); - } - NOTREACHED(); - return false; -} - -} // namespace ash
diff --git a/ash/shelf/shelf_bezel_event_handler.h b/ash/shelf/shelf_bezel_event_handler.h deleted file mode 100644 index 3f4ffe39..0000000 --- a/ash/shelf/shelf_bezel_event_handler.h +++ /dev/null
@@ -1,40 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef ASH_SHELF_SHELF_BEZEL_EVENT_HANDLER_H_ -#define ASH_SHELF_SHELF_BEZEL_EVENT_HANDLER_H_ - -#include "base/macros.h" -#include "ui/events/event_handler.h" - -namespace gfx { -class Point; -class Rect; -} - -namespace ash { -class Shelf; - -// Forwards touch gestures on a bezel sensor to the shelf. -class ShelfBezelEventHandler : public ui::EventHandler { - public: - explicit ShelfBezelEventHandler(Shelf* shelf); - ~ShelfBezelEventHandler() override; - - // Overridden from ui::EventHandler: - void OnGestureEvent(ui::GestureEvent* event) override; - void OnTouchEvent(ui::TouchEvent* event) override; - - private: - bool IsShelfOnBezel(const gfx::Rect& screen, const gfx::Point& point) const; - - Shelf* shelf_; - bool in_touch_drag_; - - DISALLOW_COPY_AND_ASSIGN(ShelfBezelEventHandler); -}; - -} // namespace ash - -#endif // ASH_SHELF_SHELF_BEZEL_EVENT_HANDLER_H_
diff --git a/ash/shelf/shelf_layout_manager_unittest.cc b/ash/shelf/shelf_layout_manager_unittest.cc index 6a2fbc4..c8f9b9b 100644 --- a/ash/shelf/shelf_layout_manager_unittest.cc +++ b/ash/shelf/shelf_layout_manager_unittest.cc
@@ -726,16 +726,9 @@ EXPECT_EQ(window_bounds_with_noshelf.ToString(), window->bounds().ToString()); EXPECT_EQ(shelf_hidden.ToString(), GetShelfWidget()->GetWindowBoundsInScreen().ToString()); - // Swipe up from below the shelf where a bezel would be, this should show the - // shelf. + // Swipe up from the bottom of the shelf, this should show the shelf. gfx::Point below_start = edge_to_hide; - if (shelf->IsHorizontalAlignment()) - below_start.set_y(GetShelfWidget()->GetWindowBoundsInScreen().bottom() - 1); - else if (SHELF_ALIGNMENT_LEFT == shelf->alignment()) - below_start.set_x(GetShelfWidget()->GetWindowBoundsInScreen().x()); - else if (SHELF_ALIGNMENT_RIGHT == shelf->alignment()) - below_start.set_x(GetShelfWidget()->GetWindowBoundsInScreen().right() - 1); - generator->GestureScrollSequence(below_start, edge_to_show, kTimeDelta, + generator->GestureScrollSequence(edge_to_hide, edge_to_show, kTimeDelta, kNumScrollSteps); EXPECT_EQ(SHELF_AUTO_HIDE, shelf->GetVisibilityState()); EXPECT_EQ(SHELF_AUTO_HIDE_SHOWN, shelf->GetAutoHideState()); @@ -2247,8 +2240,9 @@ ui::ScopedAnimationDurationScaleMode regular_animations( ui::ScopedAnimationDurationScaleMode::NON_ZERO_DURATION); - gfx::Point start = - GetShelfWidget()->GetWindowBoundsInScreen().CenterPoint(); + display::Display display = + display::Screen::GetScreen()->GetPrimaryDisplay(); + gfx::Point start = display.bounds().bottom_center(); gfx::Point end(start.x(), start.y() - 100); ui::test::EventGenerator* generator = GetEventGenerator(); @@ -2286,11 +2280,8 @@ // Show the shelf first. display::Display display = display::Screen::GetScreen()->GetPrimaryDisplay(); - const int half_width = display.bounds().width() / 2; - const int bottom_edge = display.bounds().bottom(); - generator->MoveMouseTo(half_width, - bottom_edge - kHiddenShelfInScreenPortion / 2); ShelfAnimationWaiter waiter1(visible_bounds); + generator->MoveMouseTo(display.bounds().bottom_center()); waiter1.WaitTillDoneAnimating(); EXPECT_EQ(SHELF_AUTO_HIDE_SHOWN, shelf->GetAutoHideState()); @@ -2346,7 +2337,8 @@ wm::GetWindowState(window_two) ->set_autohide_shelf_when_maximized_or_fullscreen(true); - window_two->SetProperty(aura::client::kAlwaysOnTopKey, true); + window_two->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); auto* shelf_window = shelf->GetWindow(); aura::Window* container = shelf_window->GetRootWindow()->GetChildById( @@ -2842,7 +2834,6 @@ const int time_deltas[] = {10, 50, 100, 500}; const int num_scroll_steps[] = {2, 5, 10, 50}; - const int y_bezel_start_offsets[] = {5, 10, 50}; const int x_offsets[] = {10, 20, 50}; const int y_offsets[] = {70, 100, 300, 500}; @@ -2850,21 +2841,17 @@ for (int num_scroll_steps : num_scroll_steps) { for (int x_offset : x_offsets) { for (int y_offset : y_offsets) { - for (int y_bezel_start_offset : y_bezel_start_offsets) { - const gfx::Point start(display_bounds.bottom_center() + - gfx::Vector2d(0, y_bezel_start_offset)); - const gfx::Point end(start + gfx::Vector2d(x_offset, -y_offset)); - generator->GestureScrollSequence( - start, end, base::TimeDelta::FromMilliseconds(time_delta), - num_scroll_steps); - EXPECT_EQ(SHELF_AUTO_HIDE_SHOWN, shelf->GetAutoHideState()) - << "Failure to show shelf after a swipe up in " << time_delta - << "ms, " << num_scroll_steps << " steps, " - << y_bezel_start_offset << " Y bezel start offset, " << x_offset - << " X-offset and " << y_offset << " Y-offset."; - generator->GestureTapAt(tap_to_hide_shelf_location); - EXPECT_EQ(SHELF_AUTO_HIDE_HIDDEN, shelf->GetAutoHideState()); - } + const gfx::Point start(display_bounds.bottom_center()); + const gfx::Point end(start + gfx::Vector2d(x_offset, -y_offset)); + generator->GestureScrollSequence( + start, end, base::TimeDelta::FromMilliseconds(time_delta), + num_scroll_steps); + EXPECT_EQ(SHELF_AUTO_HIDE_SHOWN, shelf->GetAutoHideState()) + << "Failure to show shelf after a swipe up in " << time_delta + << "ms, " << num_scroll_steps << " steps, " << x_offset + << " X-offset and " << y_offset << " Y-offset."; + generator->GestureTapAt(tap_to_hide_shelf_location); + EXPECT_EQ(SHELF_AUTO_HIDE_HIDDEN, shelf->GetAutoHideState()); } } } @@ -3090,7 +3077,8 @@ aura::Window* window = CreateTestWindow(); window->SetBounds(gfx::Rect(0, 0, 100, 100)); // Set always on top so it is put in the PIP container. - window->SetProperty(aura::client::kAlwaysOnTopKey, true); + window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); window->Show(); const wm::WMEvent pip_event(wm::WM_EVENT_PIP); wm::GetWindowState(window)->OnWMEvent(&pip_event);
diff --git a/ash/shelf/shelf_view.cc b/ash/shelf/shelf_view.cc index 47def11..2e9f451 100644 --- a/ash/shelf/shelf_view.cc +++ b/ash/shelf/shelf_view.cc
@@ -338,10 +338,9 @@ // static const int ShelfView::kMinimumDragDistance = 8; -ShelfView::ShelfView(ShelfModel* model, Shelf* shelf, ShelfWidget* shelf_widget) +ShelfView::ShelfView(ShelfModel* model, Shelf* shelf) : model_(model), shelf_(shelf), - shelf_widget_(shelf_widget), view_model_(std::make_unique<views::ViewModel>()), bounds_animator_(std::make_unique<views::BoundsAnimator>(this)), tooltip_(this), @@ -349,7 +348,6 @@ weak_factory_(this) { DCHECK(model_); DCHECK(shelf_); - DCHECK(shelf_widget_); Shell::Get()->tablet_mode_controller()->AddObserver(this); Shell::Get()->system_tray_model()->virtual_keyboard()->AddObserver(this); Shell::Get()->AddShellObserver(this); @@ -525,7 +523,7 @@ if (!overflow_bubble_) overflow_bubble_.reset(new OverflowBubble(shelf_)); - ShelfView* overflow_view = new ShelfView(model_, shelf_, shelf_widget_); + ShelfView* overflow_view = new ShelfView(model_, shelf_); overflow_view->overflow_mode_ = true; overflow_view->Init(); overflow_view->set_owner_overflow_bubble(overflow_bubble_.get());
diff --git a/ash/shelf/shelf_view.h b/ash/shelf/shelf_view.h index d9e56215..c7f61a8 100644 --- a/ash/shelf/shelf_view.h +++ b/ash/shelf/shelf_view.h
@@ -18,6 +18,7 @@ #include "ash/public/cpp/tablet_mode_observer.h" #include "ash/shelf/overflow_bubble.h" #include "ash/shelf/overflow_bubble_view.h" +#include "ash/shelf/shelf.h" #include "ash/shelf/shelf_button_delegate.h" #include "ash/shelf/shelf_button_pressed_metric_tracker.h" #include "ash/shelf/shelf_tooltip_manager.h" @@ -54,7 +55,6 @@ class OverflowBubble; class OverflowButton; class ScopedRootWindowForNewWindows; -class Shelf; class ShelfAppButton; class ShelfButton; class ShelfModel; @@ -118,7 +118,7 @@ public ash::TabletModeObserver, public VirtualKeyboardModel::Observer { public: - ShelfView(ShelfModel* model, Shelf* shelf, ShelfWidget* shelf_widget); + ShelfView(ShelfModel* model, Shelf* shelf); ~ShelfView() override; Shelf* shelf() const { return shelf_; } @@ -315,7 +315,7 @@ else return std::max(0, last_visible_index_ + 1); } - ShelfWidget* shelf_widget() const { return shelf_widget_; } + ShelfWidget* shelf_widget() const { return shelf_->shelf_widget(); } OverflowBubble* overflow_bubble() { return overflow_bubble_.get(); } views::ViewModel* view_model() { return view_model_.get(); } @@ -547,10 +547,6 @@ // The shelf controller; owned by RootWindowController. Shelf* shelf_; - // The shelf widget for this view. For overflow bubbles, this is the widget - // for the shelf, not for the bubble. - ShelfWidget* shelf_widget_; - // Used to manage the set of active launcher buttons. There is a view per // item in |model_|. std::unique_ptr<views::ViewModel> view_model_;
diff --git a/ash/shelf/shelf_view_unittest.cc b/ash/shelf/shelf_view_unittest.cc index 5b90c8b..e12dfada 100644 --- a/ash/shelf/shelf_view_unittest.cc +++ b/ash/shelf/shelf_view_unittest.cc
@@ -5,6 +5,7 @@ #include "ash/shelf/shelf_view.h" #include <algorithm> +#include <cmath> #include <memory> #include <utility> #include <vector> @@ -511,7 +512,7 @@ ASSERT_NO_FATAL_FAILURE(CheckModelIDs(*id_map)); } - void AddButtonsUntilOverflow() { + void AddAppShortcutsUntilOverflow() { int items_added = 0; while (!shelf_view_->GetOverflowButton()->GetVisible()) { AddAppShortcut(); @@ -710,7 +711,7 @@ // Check the ideal bounds of several items in LTR and RTL UI. TEST_P(ShelfViewTextDirectionTest, GetIdealBoundsOfItemIcon) { ShelfID id_1 = AddAppShortcut(); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); ShelfID id_2 = AddAppShortcut(); ShelfID id_3 = AddAppShortcut(); @@ -761,7 +762,7 @@ } TEST_F(ShelfViewTest, OverflowVisibleIndex) { - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); ASSERT_TRUE(shelf_view_->GetOverflowButton()->GetVisible()); const int last_visible_index = shelf_view_->last_visible_index(); @@ -925,7 +926,7 @@ }; // Setup the shelf so the overflow bubble is visible. - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); test_api_->ShowOverflowBubble(); ShelfViewTestAPI overflow_test_api( test_api_->overflow_bubble()->bubble_view()->shelf_view()); @@ -1171,7 +1172,7 @@ // overflow. Add one more app (which is on the overflow shelf). ShelfID first_app_id = AddAppShortcut(); ShelfID second_app_id = AddAppShortcut(); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); ShelfID overflow_app_id = AddAppShortcut(); // Verify that dragging an app off the shelf will trigger the app getting @@ -1328,7 +1329,7 @@ } TEST_F(ShelfViewTest, ButtonTitlesTest) { - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); EXPECT_EQ(base::UTF8ToUTF16("Launcher"), shelf_view_->GetHomeButton()->GetAccessibleName()); EXPECT_EQ(l10n_util::GetStringUTF16(IDS_ASH_SHELF_BACK_BUTTON_TITLE), @@ -1561,7 +1562,7 @@ // Checks the overflow bubble size when an item is ripped off and re-inserted. TEST_F(ShelfViewTest, OverflowBubbleSize) { - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); // Add one more button to prevent the overflow bubble to disappear upon // dragging an item out on windows (flakiness, see crbug.com/436131). AddAppShortcut(); @@ -1619,7 +1620,7 @@ const SkColor opaque_expected_color = wallpaper_test_api.ApplyColorProducingWallpaper(); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); test_api_->ShowOverflowBubble(); OverflowBubbleView* bubble_view = test_api_->overflow_bubble()->bubble_view(); @@ -1630,7 +1631,7 @@ TEST_F(ShelfViewTest, CheckDragInsertBoundsOfScrolledOverflowBubble) { UpdateDisplay("400x300"); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); // Show overflow bubble. test_api_->ShowOverflowBubble(); @@ -1714,7 +1715,7 @@ // Speeds up animation for test. test_api_for_secondary.SetAnimationDuration(1); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); // Test #1: Test drag insertion bounds of primary shelf. // Show overflow bubble. @@ -1769,32 +1770,41 @@ // Verifies that the arrow buttons of OverflowBubbleView work as expected. TEST_F(ShelfViewTest, CheckOverflowBubbleViewArrowButton) { UpdateDisplay("300x600"); - AddButtonsUntilOverflow(); - - // Add enough shelf items to test the arrow button. - for (int i = 0; i < 5; i++) - AddAppShortcut(); + AddAppShortcutsUntilOverflow(); // Show overflow bubble. test_api_->ShowOverflowBubble(); ASSERT_TRUE(shelf_view_->IsShowingOverflowBubble()); OverflowBubbleView* bubble_view = test_api_->overflow_bubble()->bubble_view(); - int item_count = bubble_view->shelf_view()->last_visible_index() - - bubble_view->shelf_view()->first_visible_index() + 1; - ASSERT_EQ(7, item_count); - OverflowBubbleViewTestAPI bubble_view_api(bubble_view); - views::View* left_arrow_button = bubble_view->left_arrow(); - views::View* right_arrow_button = bubble_view->right_arrow(); - ShelfViewTestAPI test_for_overflow_view( - test_api_->overflow_bubble()->bubble_view()->shelf_view()); - const gfx::Rect overflow_bubble_bounds = bubble_view->GetBoundsInScreen(); const gfx::Size shelf_icon_size(kShelfButtonSize, kShelfButtonSize); const int arrow_button_size = OverflowBubbleView::kArrowButtonSize; const int bubble_view_min_margin = OverflowBubbleView::kMinimumMargin; const int end_padding = OverflowBubbleView::kEndPadding; const int unit = kShelfButtonSize + kShelfButtonSpacing; + // Add sufficient app icons to ensure that it needs to press the right arrow + // buttons twice to reach the end. + int current_item_count = bubble_view->shelf_view()->last_visible_index() - + bubble_view->shelf_view()->first_visible_index() + 1; + const int available_width_for_shortcuts = + GetPrimaryDisplay().work_area().width() - 2 * bubble_view_min_margin - + 2 * end_padding; + const int max_accommodated_shelf_num = + std::ceil(available_width_for_shortcuts / unit); + int additional_item_num = + 2 * max_accommodated_shelf_num - 1 - current_item_count; + while (additional_item_num) { + AddAppShortcut(); + additional_item_num--; + } + + const gfx::Rect overflow_bubble_bounds = bubble_view->GetBoundsInScreen(); + views::View* left_arrow_button = bubble_view->left_arrow(); + views::View* right_arrow_button = bubble_view->right_arrow(); + ShelfViewTestAPI test_for_overflow_view( + test_api_->overflow_bubble()->bubble_view()->shelf_view()); + // Verifies that the overflow bubble has the correct bounds. In detail: // (1) The width of the overflow bubble should be the multiple of |unit|. // (2) The overflow bubble's gap between left and right display edge should @@ -1802,9 +1812,9 @@ EXPECT_EQ( overflow_bubble_bounds.origin().x(), GetPrimaryDisplay().bounds().right() - overflow_bubble_bounds.right()); - const int available_width = + const int available_width_for_bubble = GetPrimaryDisplay().bounds().width() - 2 * bubble_view_min_margin; - const int rd = available_width % unit; + const int rd = available_width_for_bubble % unit; EXPECT_EQ(rd / 2 + bubble_view_min_margin, overflow_bubble_bounds.origin().x()); EXPECT_EQ(0, overflow_bubble_bounds.width() % unit); @@ -1830,7 +1840,6 @@ const gfx::Point right_button_center = right_arrow_button->GetBoundsInScreen().CenterPoint(); GetEventGenerator()->GestureTapAt(right_button_center); - base::RunLoop().RunUntilIdle(); // Verifies that the layout strategy is SHOW_BUTTONS. EXPECT_EQ(OverflowBubbleView::SHOW_BUTTONS, bubble_view->layout_strategy()); @@ -1863,7 +1872,6 @@ // (3) The right button is invisible. // (4) The last visible shelf button has the expected bounds in screen. GetEventGenerator()->GestureTapAt(right_button_center); - base::RunLoop().RunUntilIdle(); EXPECT_EQ(OverflowBubbleView::SHOW_LEFT_ARROW_BUTTON, bubble_view->layout_strategy()); EXPECT_FALSE(right_arrow_button->GetVisible()); @@ -1890,6 +1898,72 @@ EXPECT_FALSE(left_arrow_button->GetVisible()); } +// Verifies that the overflow bubble view handles the gesture events correctly. +TEST_F(ShelfViewTest, CheckGestureDraggingOverflowBubbleView) { + UpdateDisplay("300x600"); + AddAppShortcutsUntilOverflow(); + + // Show overflow bubble. + test_api_->ShowOverflowBubble(); + ASSERT_TRUE(shelf_view_->IsShowingOverflowBubble()); + OverflowBubbleView* bubble_view = test_api_->overflow_bubble()->bubble_view(); + + const int bubble_view_min_margin = OverflowBubbleView::kMinimumMargin; + const int end_padding = OverflowBubbleView::kEndPadding; + const int unit = kShelfButtonSize + kShelfButtonSpacing; + + // Calculates the start point of the gesture drag event. Ensures that the + // start point is not within the bounds of any shelf icon. + ShelfViewTestAPI test_for_overflow_view( + test_api_->overflow_bubble()->bubble_view()->shelf_view()); + const gfx::Rect first_icon_bounds = + test_for_overflow_view + .GetButton(bubble_view->shelf_view()->first_visible_index()) + ->GetBoundsInScreen(); + gfx::Point gesture_drag_point = first_icon_bounds.right_center(); + gesture_drag_point.Offset(1, 0); + + // Verifies that gesture dragging is disabled when no arrow button shows. + ASSERT_EQ(OverflowBubbleView::NOT_SHOW_ARROW_BUTTON, + bubble_view->layout_strategy()); + gfx::Point gesture_end_point = gesture_drag_point; + gesture_end_point.Offset(-kShelfButtonSize, 0); + GetEventGenerator()->GestureScrollSequence( + gesture_drag_point, gesture_end_point, + base::TimeDelta::FromMilliseconds(100), 5); + EXPECT_EQ(0, bubble_view->scroll_offset().x()); + + // Adds enough shelf icons to show the right arrow button. + const int available_width_for_shortcuts = + GetPrimaryDisplay().bounds().width() - 2 * bubble_view_min_margin - + 2 * end_padding; + int max_accommodated_shelf_num = + std::ceil(available_width_for_shortcuts / unit); + while (max_accommodated_shelf_num) { + AddAppShortcut(); + max_accommodated_shelf_num--; + } + ASSERT_EQ(OverflowBubbleView::SHOW_RIGHT_ARROW_BUTTON, + bubble_view->layout_strategy()); + + // Verifies that the small gesutre offset will not scroll the overflow bubble. + gesture_end_point = gesture_drag_point; + gesture_end_point.Offset(-10, 0); + GetEventGenerator()->GestureScrollSequence( + gesture_drag_point, gesture_end_point, + base::TimeDelta::FromMilliseconds(100), 1); + EXPECT_EQ(0, bubble_view->scroll_offset().x()); + + // Verifies that the large gesture offset will scroll the overflow bubble. The + // scroll offset is adjusted to fully show all of shelf icons. + gesture_end_point = gesture_drag_point; + gesture_end_point.Offset(-kShelfButtonSize, 0); + GetEventGenerator()->GestureScrollSequence( + gesture_drag_point, gesture_end_point, + base::TimeDelta::FromMilliseconds(100), 1); + EXPECT_EQ(unit, bubble_view->scroll_offset().x()); +} + // Checks the rip an item off from left aligned shelf in secondary monitor. TEST_F(ShelfViewTest, CheckRipOffFromLeftShelfAlignmentWithMultiMonitor) { UpdateDisplay("800x600,800x600"); @@ -1928,7 +2002,7 @@ // Checks various drag and drop operations from OverflowBubble to Shelf, and // vice versa. TEST_F(ShelfViewTest, CheckDragAndDropFromShelfToOtherShelf) { - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); // Add one more button to prevent the overflow bubble to disappear upon // dragging an item out on windows (flakiness, see crbug.com/425097). AddAppShortcut(); @@ -1947,7 +2021,7 @@ // Checks drag-reorder items within the overflow shelf. TEST_F(ShelfViewTest, TestDragWithinOverflow) { // Prepare the overflow and open it. - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); // Add a couple more to make sure we have things to drag. AddAppShortcut(); AddAppShortcut(); @@ -1994,7 +2068,7 @@ // Checks creating app shortcut for an opened platform app in overflow bubble // should be invisible to the shelf. See crbug.com/605793. TEST_F(ShelfViewTest, CheckOverflowStatusPinOpenedAppToShelf) { - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); // Add a running Platform app. ShelfID platform_app_id = AddApp(); @@ -2068,7 +2142,7 @@ // overflow. Add two more apps (which are on the overflow shelf). ShelfID first_app_id = AddAppShortcut(); ShelfID second_app_id = AddAppShortcut(); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); ShelfID overflow_app_id1 = AddAppShortcut(); ShelfID overflow_app_id2 = AddAppShortcut(); @@ -2138,7 +2212,7 @@ TEST_F(ShelfViewTest, UnpinningCancelsOverflow) { // Add just enough items for overflow; one fewer would not require overflow. const ShelfID first_shelf_id = AddAppShortcut(); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); test_api_->ShowOverflowBubble(); EXPECT_TRUE(shelf_view_->GetOverflowButton()->GetVisible()); EXPECT_TRUE(shelf_view_->IsShowingOverflowBubble()); @@ -2262,7 +2336,7 @@ // Tests that the overflow button does not show a context menu. TEST_F(ShelfViewTest, NoContextMenuOnOverflowButton) { ui::test::EventGenerator* generator = GetEventGenerator(); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); views::View* overflow_button = shelf_view_->GetOverflowButton(); generator->MoveMouseTo(overflow_button->GetBoundsInScreen().CenterPoint()); @@ -3249,7 +3323,7 @@ views::test::InkDropHostViewTestApi(overflow_button_) .SetInkDrop(std::move(overflow_button_ink_drop)); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); EXPECT_TRUE(shelf_view_->GetOverflowButton()->GetVisible()); EXPECT_FALSE(shelf_view_->IsShowingOverflowBubble()); } @@ -3775,7 +3849,7 @@ std::unique_ptr<aura::Window> window = CreateTestWindow(); ::wm::ActivateWindow(window.get()); - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); test_api_->ShowOverflowBubble(); EXPECT_TRUE(::wm::IsActiveWindow(window.get())); } @@ -3827,7 +3901,7 @@ // Add app shortcuts until the overflow button is visible. At this point // there will be two items on the overflow shelf. - AddButtonsUntilOverflow(); + AddAppShortcutsUntilOverflow(); // Add two more shortcuts for a total of four items on the overflow shelf. AddAppShortcut();
diff --git a/ash/shelf/shelf_widget.cc b/ash/shelf/shelf_widget.cc index c876d520..68c4308 100644 --- a/ash/shelf/shelf_widget.cc +++ b/ash/shelf/shelf_widget.cc
@@ -304,7 +304,7 @@ Shell::Get()->wallpaper_controller()), shelf_layout_manager_(new ShelfLayoutManager(this, shelf)), delegate_view_(new DelegateView(this)), - shelf_view_(new ShelfView(ShelfModel::Get(), shelf_, this)), + shelf_view_(new ShelfView(ShelfModel::Get(), shelf_)), login_shelf_view_( new LoginShelfView(RootWindowController::ForWindow(shelf_container) ->lock_screen_action_background_controller())),
diff --git a/ash/shell.cc b/ash/shell.cc index 7816356..0a70bec1 100644 --- a/ash/shell.cc +++ b/ash/shell.cc
@@ -56,7 +56,6 @@ #include "ash/ime/ime_controller.h" #include "ash/keyboard/keyboard_controller_impl.h" #include "ash/keyboard/ui/keyboard_ui_factory.h" -#include "ash/kiosk_next/kiosk_next_shell_controller_impl.h" #include "ash/laser/laser_pointer_controller.h" #include "ash/login/login_screen_controller.h" #include "ash/login_status.h" @@ -713,9 +712,6 @@ // Close all widgets (including the shelf) and destroy all window containers. CloseAllRootWindowChildWindows(); - // Destruct KioskNextShellController after Shelf - kiosk_next_shell_controller_.reset(); - login_screen_controller_.reset(); system_notification_controller_.reset(); // Should be destroyed after Shelf and |system_notification_controller_|. @@ -896,8 +892,7 @@ std::make_unique<MultiDeviceNotificationPresenter>( message_center::MessageCenter::Get(), connector_); } - kiosk_next_shell_controller_ = - std::make_unique<KioskNextShellControllerImpl>(); + tablet_mode_controller_ = std::make_unique<TabletModeController>(); accessibility_focus_ring_controller_ =
diff --git a/ash/shell.h b/ash/shell.h index ae376fd..f964dd0 100644 --- a/ash/shell.h +++ b/ash/shell.h
@@ -129,7 +129,6 @@ class ImmersiveContext; class KeyAccessibilityEnabler; class KeyboardBrightnessControlDelegate; -class KioskNextShellControllerImpl; class KeyboardControllerImpl; class LaserPointerController; class LocaleUpdateControllerImpl; @@ -381,9 +380,6 @@ KeyboardBrightnessControlDelegate* keyboard_brightness_control_delegate() { return keyboard_brightness_control_delegate_.get(); } - KioskNextShellControllerImpl* kiosk_next_shell_controller() { - return kiosk_next_shell_controller_.get(); - } KeyboardControllerImpl* keyboard_controller() { return keyboard_controller_.get(); } @@ -667,7 +663,6 @@ std::unique_ptr<ImmersiveContext> immersive_context_; std::unique_ptr<KeyboardBrightnessControlDelegate> keyboard_brightness_control_delegate_; - std::unique_ptr<KioskNextShellControllerImpl> kiosk_next_shell_controller_; std::unique_ptr<LocaleUpdateControllerImpl> locale_update_controller_; std::unique_ptr<LoginScreenController> login_screen_controller_; std::unique_ptr<LogoutConfirmationController> logout_confirmation_controller_;
diff --git a/ash/shell_unittest.cc b/ash/shell_unittest.cc index b1fc2e0..31c4252e 100644 --- a/ash/shell_unittest.cc +++ b/ash/shell_unittest.cc
@@ -195,7 +195,8 @@ bool always_on_top, aura::Window* expected_container) { views::Widget::InitParams widget_params(type); - widget_params.keep_on_top = always_on_top; + if (always_on_top) + widget_params.z_order = ui::ZOrderLevel::kFloatingWindow; views::Widget* widget = CreateTestWindow(widget_params); widget->Show(); @@ -281,11 +282,11 @@ widget.GetRestoredBounds().CenterPoint()); } -TEST_F(ShellTest, ChangeAlwaysOnTop) { +TEST_F(ShellTest, ChangeZOrderLevel) { views::Widget::InitParams widget_params( views::Widget::InitParams::TYPE_WINDOW); - // Creates a normal window + // Creates a normal window. views::Widget* widget = CreateTestWindow(widget_params); widget->Show(); @@ -293,19 +294,19 @@ EXPECT_TRUE( GetActiveDeskContainer()->Contains(widget->GetNativeWindow()->parent())); - // Flip always-on-top flag. - widget->SetAlwaysOnTop(true); + // Set the z-order to float. + widget->SetZOrderLevel(ui::ZOrderLevel::kFloatingWindow); // And it should in always on top container now. EXPECT_EQ(GetAlwaysOnTopContainer(), widget->GetNativeWindow()->parent()); - // Flip always-on-top flag. - widget->SetAlwaysOnTop(false); + // Put the z-order back to normal. + widget->SetZOrderLevel(ui::ZOrderLevel::kNormal); // It should go back to the active desk container. EXPECT_TRUE( GetActiveDeskContainer()->Contains(widget->GetNativeWindow()->parent())); - // Set the same always-on-top flag again. - widget->SetAlwaysOnTop(false); + // Set the z-order again to the normal value. + widget->SetZOrderLevel(ui::ZOrderLevel::kNormal); // Should have no effect and we are still in the the active desk container. EXPECT_TRUE( GetActiveDeskContainer()->Contains(widget->GetNativeWindow()->parent()));
diff --git a/ash/sticky_keys/sticky_keys_overlay.cc b/ash/sticky_keys/sticky_keys_overlay.cc index cc96f1f..b86db125 100644 --- a/ash/sticky_keys/sticky_keys_overlay.cc +++ b/ash/sticky_keys/sticky_keys_overlay.cc
@@ -211,7 +211,7 @@ params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.accept_events = false; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.bounds = CalculateOverlayBounds(); params.parent = Shell::GetContainer(Shell::GetRootWindowForNewWindows(), kShellWindowId_OverlayContainer);
diff --git a/ash/system/power/power_button_controller.cc b/ash/system/power/power_button_controller.cc index 6bcda10..f71e4c60 100644 --- a/ash/system/power/power_button_controller.cc +++ b/ash/system/power/power_button_controller.cc
@@ -64,7 +64,7 @@ views::Widget::InitParams params( views::Widget::InitParams::TYPE_WINDOW_FRAMELESS); params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingWindow; params.accept_events = true; params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.name = "PowerButtonMenuWindow";
diff --git a/ash/system/session/logout_confirmation_controller_unittest.cc b/ash/system/session/logout_confirmation_controller_unittest.cc index c74750c..1ca732e 100644 --- a/ash/system/session/logout_confirmation_controller_unittest.cc +++ b/ash/system/session/logout_confirmation_controller_unittest.cc
@@ -286,7 +286,7 @@ // Moving the widget to the always-on-top container does not trigger the // dialog because the window didn't close. - widget->SetAlwaysOnTop(true); + widget->SetZOrderLevel(ui::ZOrderLevel::kFloatingWindow); EXPECT_FALSE(controller->dialog_for_testing()); // Closing the window triggers the dialog. @@ -302,7 +302,7 @@ // Create two windows in different containers. std::unique_ptr<views::Widget> normal_widget = CreateTestWidget(); std::unique_ptr<views::Widget> always_on_top_widget = CreateTestWidget(); - always_on_top_widget->SetAlwaysOnTop(true); + always_on_top_widget->SetZOrderLevel(ui::ZOrderLevel::kFloatingWindow); // Closing the last window shows the dialog. always_on_top_widget.reset();
diff --git a/ash/system/toast/toast_overlay.cc b/ash/system/toast/toast_overlay.cc index bc0aa60c..26450a5 100644 --- a/ash/system/toast/toast_overlay.cc +++ b/ash/system/toast/toast_overlay.cc
@@ -231,7 +231,7 @@ params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.accept_events = true; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.bounds = CalculateOverlayBounds(); // Show toasts above the app list and below the lock screen. params.parent = Shell::GetRootWindowForNewWindows()->GetChildById(
diff --git a/ash/system/tray/tray_event_filter.cc b/ash/system/tray/tray_event_filter.cc index ea8827a..e291bf04 100644 --- a/ash/system/tray/tray_event_filter.cc +++ b/ash/system/tray/tray_event_filter.cc
@@ -63,7 +63,7 @@ // from message center. if (container_id == kShellWindowId_StatusContainer && target->type() == aura::client::WINDOW_TYPE_POPUP && target_widget && - target_widget->IsAlwaysOnTop()) { + target_widget->GetZOrderLevel() != ui::ZOrderLevel::kNormal) { return; } // Don't process events that occurred inside a virtual keyboard.
diff --git a/ash/system/tray/tray_event_filter_unittest.cc b/ash/system/tray/tray_event_filter_unittest.cc index 1706348d..550e63ea 100644 --- a/ash/system/tray/tray_event_filter_unittest.cc +++ b/ash/system/tray/tray_event_filter_unittest.cc
@@ -109,8 +109,8 @@ CreateTestWindow(gfx::Rect(), aura::client::WINDOW_TYPE_POPUP); popup_window->set_owned_by_parent(false); popup_widget->GetNativeView()->AddChild(popup_window.get()); - popup_widget->GetNativeView()->SetProperty(aura::client::kAlwaysOnTopKey, - true); + popup_widget->GetNativeView()->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); ShowSystemTrayMainView(); EXPECT_TRUE(IsBubbleShown());
diff --git a/ash/test/ash_test_helper.cc b/ash/test/ash_test_helper.cc index 78ca2364..351eebb8 100644 --- a/ash/test/ash_test_helper.cc +++ b/ash/test/ash_test_helper.cc
@@ -86,8 +86,9 @@ // lap with the native mouse cursor. if (!command_line_->GetProcessCommandLine()->HasSwitch( ::switches::kHostWindowBounds)) { + // TODO(oshima): Disable native events instead of adding offset. command_line_->GetProcessCommandLine()->AppendSwitchASCII( - ::switches::kHostWindowBounds, "1+1-800x600"); + ::switches::kHostWindowBounds, "10+10-800x600"); } // Pre shell creation config init.
diff --git a/ash/wm/always_on_top_controller.cc b/ash/wm/always_on_top_controller.cc index 92b1798..f41a9d9 100644 --- a/ash/wm/always_on_top_controller.cc +++ b/ash/wm/always_on_top_controller.cc
@@ -44,7 +44,11 @@ DCHECK(always_on_top_container_); DCHECK(pip_container_); - if (!window->GetProperty(aura::client::kAlwaysOnTopKey)) { + // On other platforms, there are different window levels. For now, treat any + // window with non-normal level as "always on top". Perhaps the nuance of + // multiple levels will be needed later. + if (window->GetProperty(aura::client::kZOrderingKey) == + ui::ZOrderLevel::kNormal) { aura::Window* root = always_on_top_container_->GetRootWindow(); // TODO(afakhry): Do we need to worry about the context of |window| here? Or @@ -103,7 +107,7 @@ const void* key, intptr_t old) { if (window != always_on_top_container_ && window != pip_container_ && - key == aura::client::kAlwaysOnTopKey) { + key == aura::client::kZOrderingKey) { ReparentWindow(window); } }
diff --git a/ash/wm/always_on_top_controller_unittest.cc b/ash/wm/always_on_top_controller_unittest.cc index 28731c5..caee116 100644 --- a/ash/wm/always_on_top_controller_unittest.cc +++ b/ash/wm/always_on_top_controller_unittest.cc
@@ -80,7 +80,7 @@ } TEST_F(AlwaysOnTopControllerTest, - AlwaysOnTopContainerReturnedForAlwaysOnTopWindow) { + AlwaysOnTopContainerReturnedForFloatingWindow) { RootWindowController* controller = Shell::GetPrimaryRootWindowController(); AlwaysOnTopController* always_on_top_controller = controller->always_on_top_controller(); @@ -88,7 +88,8 @@ const gfx::Rect bounds(100, 100, 200, 200); std::unique_ptr<aura::Window> always_on_top_window( CreateTestWindowInShellWithBounds(bounds)); - always_on_top_window->SetProperty(aura::client::kAlwaysOnTopKey, true); + always_on_top_window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); aura::Window* container = always_on_top_controller->GetContainer(always_on_top_window.get()); @@ -96,7 +97,7 @@ EXPECT_EQ(kShellWindowId_AlwaysOnTopContainer, container->id()); } -TEST_F(AlwaysOnTopControllerTest, PipContainerReturnedForAlwaysOnTopPipWindow) { +TEST_F(AlwaysOnTopControllerTest, PipContainerReturnedForFloatingPipWindow) { RootWindowController* controller = Shell::GetPrimaryRootWindowController(); AlwaysOnTopController* always_on_top_controller = controller->always_on_top_controller(); @@ -108,7 +109,8 @@ wm::WindowState* window_state = wm::GetWindowState(pip_window.get()); const wm::WMEvent enter_pip(wm::WM_EVENT_PIP); window_state->OnWMEvent(&enter_pip); - pip_window->SetProperty(aura::client::kAlwaysOnTopKey, true); + pip_window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); EXPECT_TRUE(window_state->IsPip()); aura::Window* container = @@ -134,11 +136,12 @@ } TEST_F(AlwaysOnTopControllerTest, - AlwaysOnTopWindowMovedBetweenContainersWhenPipStateChanges) { + FloatingWindowMovedBetweenContainersWhenPipStateChanges) { const gfx::Rect bounds(100, 100, 200, 200); std::unique_ptr<aura::Window> window( CreateTestWindowInShellWithBounds(bounds)); - window->SetProperty(aura::client::kAlwaysOnTopKey, true); + window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); EXPECT_EQ(kShellWindowId_AlwaysOnTopContainer, window->parent()->id());
diff --git a/ash/wm/ash_focus_rules_unittest.cc b/ash/wm/ash_focus_rules_unittest.cc index 89b6c45..43e31b4 100644 --- a/ash/wm/ash_focus_rules_unittest.cc +++ b/ash/wm/ash_focus_rules_unittest.cc
@@ -112,7 +112,8 @@ aura::Window* CreateWindowInAlwaysOnTopContainer() { aura::Window* window = CreateWindowInContainer(kShellWindowId_AlwaysOnTopContainer); - window->SetProperty(aura::client::kAlwaysOnTopKey, true); + window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); return window; }
diff --git a/ash/wm/drag_window_resizer_unittest.cc b/ash/wm/drag_window_resizer_unittest.cc index 1578639..2d3baac 100644 --- a/ash/wm/drag_window_resizer_unittest.cc +++ b/ash/wm/drag_window_resizer_unittest.cc
@@ -83,7 +83,8 @@ always_on_top_window_ = window_factory::NewWindow(&delegate2_); always_on_top_window_->SetType(aura::client::WINDOW_TYPE_NORMAL); - always_on_top_window_->SetProperty(aura::client::kAlwaysOnTopKey, true); + always_on_top_window_->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); always_on_top_window_->Init(ui::LAYER_NOT_DRAWN); ParentWindowInPrimaryRootWindow(always_on_top_window_.get()); always_on_top_window_->set_id(2);
diff --git a/ash/wm/overview/overview_grid.cc b/ash/wm/overview/overview_grid.cc index bcdd4ac..7ed98f1b 100644 --- a/ash/wm/overview/overview_grid.cc +++ b/ash/wm/overview/overview_grid.cc
@@ -915,10 +915,14 @@ // Preserves ordering if the category is the same. std::sort(items.begin(), items.end(), [&selected_item](OverviewItem* a, OverviewItem* b) { + // NB: This treats all non-normal z-ordered windows the same. If + // Aura ever adopts z-order levels, this will need to be changed. const bool a_on_top = - a->GetWindow()->GetProperty(aura::client::kAlwaysOnTopKey); + a->GetWindow()->GetProperty(aura::client::kZOrderingKey) != + ui::ZOrderLevel::kNormal; const bool b_on_top = - b->GetWindow()->GetProperty(aura::client::kAlwaysOnTopKey); + b->GetWindow()->GetProperty(aura::client::kZOrderingKey) != + ui::ZOrderLevel::kNormal; if (selected_item && a_on_top && b_on_top) return a == selected_item; if (a_on_top)
diff --git a/ash/wm/overview/overview_grid_unittest.cc b/ash/wm/overview/overview_grid_unittest.cc index c6ea4e1c..bbba7e9 100644 --- a/ash/wm/overview/overview_grid_unittest.cc +++ b/ash/wm/overview/overview_grid_unittest.cc
@@ -149,7 +149,8 @@ // window. So the first window will not animate. auto window1 = CreateTestWindow(gfx::Rect(100, 100)); auto window2 = CreateTestWindow(gfx::Rect(400, 400)); - window2->SetProperty(aura::client::kAlwaysOnTopKey, true); + window2->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); std::vector<gfx::RectF> target_bounds = {gfx::RectF(100.f, 100.f), gfx::RectF(100.f, 100.f)}; CheckAnimationStates({window1.get(), window2.get()}, target_bounds,
diff --git a/ash/wm/overview/overview_session_unittest.cc b/ash/wm/overview/overview_session_unittest.cc index 4a80f212..5510247 100644 --- a/ash/wm/overview/overview_session_unittest.cc +++ b/ash/wm/overview/overview_session_unittest.cc
@@ -2181,8 +2181,10 @@ std::unique_ptr<aura::Window> window6(CreateTestWindow(bounds)); std::unique_ptr<aura::Window> window7(CreateTestWindow(bounds)); std::unique_ptr<aura::Window> window8(CreateTestWindow(bounds)); - window3->SetProperty(aura::client::kAlwaysOnTopKey, true); - window5->SetProperty(aura::client::kAlwaysOnTopKey, true); + window3->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); + window5->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); // Control z order and MRU order. ::wm::ActivateWindow(window8.get());
diff --git a/ash/wm/overview/rounded_label_widget.cc b/ash/wm/overview/rounded_label_widget.cc index 0b851b0..f8b3f5b 100644 --- a/ash/wm/overview/rounded_label_widget.cc +++ b/ash/wm/overview/rounded_label_widget.cc
@@ -79,7 +79,6 @@ views::Widget::InitParams widget_params; widget_params.name = params.name; widget_params.type = views::Widget::InitParams::TYPE_POPUP; - widget_params.keep_on_top = false; widget_params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; widget_params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW;
diff --git a/ash/wm/pip/pip_window_resizer_unittest.cc b/ash/wm/pip/pip_window_resizer_unittest.cc index 28165922..c9157c3 100644 --- a/ash/wm/pip/pip_window_resizer_unittest.cc +++ b/ash/wm/pip/pip_window_resizer_unittest.cc
@@ -117,7 +117,7 @@ views::Widget::InitParams params; params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.bounds = screen_bounds; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingWindow; params.context = root_window; widget->Init(params); widget->Show();
diff --git a/ash/wm/splitview/split_view_controller_unittest.cc b/ash/wm/splitview/split_view_controller_unittest.cc index f3e577fb..385c354 100644 --- a/ash/wm/splitview/split_view_controller_unittest.cc +++ b/ash/wm/splitview/split_view_controller_unittest.cc
@@ -597,11 +597,13 @@ EXPECT_TRUE(!split_view_divider()); split_view_controller()->SnapWindow(window1.get(), SplitViewController::LEFT); EXPECT_TRUE(split_view_divider()); - EXPECT_TRUE(split_view_divider()->divider_widget()->IsAlwaysOnTop()); + EXPECT_NE(ui::ZOrderLevel::kNormal, + split_view_divider()->divider_widget()->GetZOrderLevel()); split_view_controller()->SnapWindow(window2.get(), SplitViewController::RIGHT); EXPECT_TRUE(split_view_divider()); - EXPECT_TRUE(split_view_divider()->divider_widget()->IsAlwaysOnTop()); + EXPECT_NE(ui::ZOrderLevel::kNormal, + split_view_divider()->divider_widget()->GetZOrderLevel()); // Test that activating an non-snappable window ends the split view mode. std::unique_ptr<aura::Window> window3(CreateNonSnappableWindow(bounds)); @@ -2132,7 +2134,8 @@ TEST_F(SplitViewControllerTest, AlwaysOnTopWindow) { const gfx::Rect bounds(0, 0, 400, 400); std::unique_ptr<aura::Window> always_on_top_window(CreateWindow(bounds)); - always_on_top_window->SetProperty(aura::client::kAlwaysOnTopKey, true); + always_on_top_window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); std::unique_ptr<aura::Window> normal_window(CreateWindow(bounds)); split_view_controller()->SnapWindow(always_on_top_window.get(), @@ -2140,15 +2143,18 @@ split_view_controller()->SnapWindow(normal_window.get(), SplitViewController::RIGHT); EXPECT_EQ(split_view_controller()->state(), SplitViewState::kBothSnapped); - EXPECT_TRUE(always_on_top_window->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window->GetProperty(aura::client::kZOrderingKey)); wm::ActivateWindow(always_on_top_window.get()); EXPECT_EQ(split_view_controller()->state(), SplitViewState::kBothSnapped); - EXPECT_TRUE(always_on_top_window->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window->GetProperty(aura::client::kZOrderingKey)); wm::ActivateWindow(normal_window.get()); EXPECT_EQ(split_view_controller()->state(), SplitViewState::kBothSnapped); - EXPECT_TRUE(always_on_top_window->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window->GetProperty(aura::client::kZOrderingKey)); } // Test that pinning a window ends split view mode. @@ -2708,18 +2714,18 @@ SplitViewController::RIGHT); views::Widget* split_divider_widget = split_view_controller()->split_view_divider()->divider_widget(); - EXPECT_TRUE(split_divider_widget->IsAlwaysOnTop()); + EXPECT_NE(ui::ZOrderLevel::kNormal, split_divider_widget->GetZOrderLevel()); std::unique_ptr<WindowResizer> resizer = StartDrag(window1.get(), window1.get()); ASSERT_TRUE(resizer.get()); - EXPECT_FALSE(split_divider_widget->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, split_divider_widget->GetZOrderLevel()); resizer->Drag(gfx::Point(), 0); - EXPECT_FALSE(split_divider_widget->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, split_divider_widget->GetZOrderLevel()); CompleteDrag(std::move(resizer)); - EXPECT_TRUE(split_divider_widget->IsAlwaysOnTop()); + EXPECT_NE(ui::ZOrderLevel::kNormal, split_divider_widget->GetZOrderLevel()); } // Test the functionalities that are related to dragging a maximized window's @@ -4071,7 +4077,8 @@ EXPECT_EQ(split_view_controller()->state(), SplitViewState::kBothSnapped); EXPECT_FALSE(Shell::Get()->overview_controller()->InOverviewSession()); - EXPECT_TRUE(split_view_divider()->divider_widget()->IsAlwaysOnTop()); + EXPECT_NE(ui::ZOrderLevel::kNormal, + split_view_divider()->divider_widget()->GetZOrderLevel()); } // Tests that the divider bar should be placed on top after the drag ends, no @@ -4094,7 +4101,8 @@ DragWindowWithOffset(resizer.get(), 10, 10); CompleteDrag(std::move(resizer)); EXPECT_EQ(split_view_controller()->state(), SplitViewState::kBothSnapped); - EXPECT_TRUE(split_view_divider()->divider_widget()->IsAlwaysOnTop()); + EXPECT_NE(ui::ZOrderLevel::kNormal, + split_view_divider()->divider_widget()->GetZOrderLevel()); // If the dragged window is destroyed after drag ends: resizer = StartDrag(dragged_window.get(), dragged_window.get()); @@ -4104,7 +4112,8 @@ dragged_window.reset(); EXPECT_EQ(split_view_controller()->state(), SplitViewState::kRightSnapped); EXPECT_TRUE(Shell::Get()->overview_controller()->InOverviewSession()); - EXPECT_TRUE(split_view_divider()->divider_widget()->IsAlwaysOnTop()); + EXPECT_NE(ui::ZOrderLevel::kNormal, + split_view_divider()->divider_widget()->GetZOrderLevel()); } TEST_F(SplitViewTabDraggingTest, IgnoreActivatedTabDraggingWindow) {
diff --git a/ash/wm/splitview/split_view_divider.cc b/ash/wm/splitview/split_view_divider.cc index 73ac1b5..30ef609 100644 --- a/ash/wm/splitview/split_view_divider.cc +++ b/ash/wm/splitview/split_view_divider.cc
@@ -454,7 +454,7 @@ void SplitViewDivider::SetAlwaysOnTop(bool on_top) { if (on_top) { - divider_widget_->SetAlwaysOnTop(true); + divider_widget_->SetZOrderLevel(ui::ZOrderLevel::kFloatingUIElement); // Special handling when put divider into always_on_top container. We want // to put it at the bottom so it won't block other always_on_top windows. @@ -464,7 +464,7 @@ always_on_top_container->StackChildAtBottom( divider_widget_->GetNativeWindow()); } else { - divider_widget_->SetAlwaysOnTop(false); + divider_widget_->SetZOrderLevel(ui::ZOrderLevel::kNormal); } }
diff --git a/ash/wm/splitview/split_view_drag_indicators.cc b/ash/wm/splitview/split_view_drag_indicators.cc index c3a7c18f..0e79125 100644 --- a/ash/wm/splitview/split_view_drag_indicators.cc +++ b/ash/wm/splitview/split_view_drag_indicators.cc
@@ -43,7 +43,6 @@ auto widget = std::make_unique<views::Widget>(); views::Widget::InitParams params; params.type = views::Widget::InitParams::TYPE_POPUP; - params.keep_on_top = false; params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; params.accept_events = false;
diff --git a/ash/wm/tablet_mode/tablet_mode_window_manager.cc b/ash/wm/tablet_mode/tablet_mode_window_manager.cc index 423ce7a..78a4b3c7 100644 --- a/ash/wm/tablet_mode/tablet_mode_window_manager.cc +++ b/ash/wm/tablet_mode/tablet_mode_window_manager.cc
@@ -445,9 +445,10 @@ void TabletModeWindowManager::OnWindowPropertyChanged(aura::Window* window, const void* key, intptr_t old) { - // Stop managing |window| if the always-on-top property is added. - if (key == aura::client::kAlwaysOnTopKey && - window->GetProperty(aura::client::kAlwaysOnTopKey)) { + // Stop managing |window| if it is moved to have a non-normal z-order. + if (key == aura::client::kZOrderingKey && + window->GetProperty(aura::client::kZOrderingKey) != + ui::ZOrderLevel::kNormal) { ForgetWindow(window, false /* destroyed */); } } @@ -693,10 +694,12 @@ bool TabletModeWindowManager::ShouldHandleWindow(aura::Window* window) { DCHECK(window); - // Windows with the always-on-top property should be free-floating and thus + // Windows that don't have normal z-ordering should be free-floating and thus // not managed by us. - if (window->GetProperty(aura::client::kAlwaysOnTopKey)) + if (window->GetProperty(aura::client::kZOrderingKey) != + ui::ZOrderLevel::kNormal) { return false; + } // If the changing bounds in the maximized/fullscreen is allowed, then // let the client manage it even in tablet mode.
diff --git a/ash/wm/tablet_mode/tablet_mode_window_manager_unittest.cc b/ash/wm/tablet_mode/tablet_mode_window_manager_unittest.cc index a2845048..ca1e6243 100644 --- a/ash/wm/tablet_mode/tablet_mode_window_manager_unittest.cc +++ b/ash/wm/tablet_mode/tablet_mode_window_manager_unittest.cc
@@ -1529,8 +1529,10 @@ CreateWindow(aura::client::WINDOW_TYPE_NORMAL, rect1)); std::unique_ptr<aura::Window> w2(CreateFixedSizeNonMaximizableWindow( aura::client::WINDOW_TYPE_NORMAL, rect2)); - w1->SetProperty(aura::client::kAlwaysOnTopKey, true); - w2->SetProperty(aura::client::kAlwaysOnTopKey, true); + w1->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); + w2->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); EXPECT_FALSE(wm::GetWindowState(w1.get())->IsMaximized()); EXPECT_FALSE(wm::GetWindowState(w2.get())->IsMaximized()); EXPECT_EQ(rect1.ToString(), w1->bounds().ToString()); @@ -1550,8 +1552,8 @@ // Remove the always-on-top property from both windows while in maximize // mode. The windows should become managed, which means they should be // maximized/centered and no longer be draggable. - w1->SetProperty(aura::client::kAlwaysOnTopKey, false); - w2->SetProperty(aura::client::kAlwaysOnTopKey, false); + w1->SetProperty(aura::client::kZOrderingKey, ui::ZOrderLevel::kNormal); + w2->SetProperty(aura::client::kZOrderingKey, ui::ZOrderLevel::kNormal); EXPECT_EQ(2, manager->GetNumberOfManagedWindows()); EXPECT_TRUE(wm::GetWindowState(w1.get())->IsMaximized()); EXPECT_FALSE(wm::GetWindowState(w2.get())->IsMaximized()); @@ -1563,8 +1565,10 @@ // Applying the always-on-top property to both windows while in maximize // mode should cause both windows to return to their original size, // position, and state. - w1->SetProperty(aura::client::kAlwaysOnTopKey, true); - w2->SetProperty(aura::client::kAlwaysOnTopKey, true); + w1->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); + w2->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); EXPECT_EQ(0, manager->GetNumberOfManagedWindows()); EXPECT_FALSE(wm::GetWindowState(w1.get())->IsMaximized()); EXPECT_FALSE(wm::GetWindowState(w2.get())->IsMaximized()); @@ -1728,7 +1732,8 @@ params.show_on_creation = false; std::unique_ptr<aura::Window> window(CreateWindowInWatchedContainer(params)); wm::GetWindowState(window.get())->set_allow_set_bounds_direct(true); - window->SetProperty(aura::client::kAlwaysOnTopKey, true); + window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); window->Show(); }
diff --git a/ash/wm/window_state.cc b/ash/wm/window_state.cc index 07b226c2..2f4e9f55 100644 --- a/ash/wm/window_state.cc +++ b/ash/wm/window_state.cc
@@ -326,8 +326,9 @@ } } -void WindowState::DisableAlwaysOnTop(aura::Window* window_on_top) { - if (GetAlwaysOnTop() && !IsPip()) { +void WindowState::DisableZOrdering(aura::Window* window_on_top) { + ui::ZOrderLevel z_order = GetZOrdering(); + if (z_order != ui::ZOrderLevel::kNormal && !IsPip()) { // |window_| is hidden first to avoid canceling fullscreen mode when it is // no longer always on top and gets added to default container. This avoids // sending redundant OnFullscreenStateChanged to the layout manager. The @@ -336,7 +337,7 @@ bool visible = window_->IsVisible(); if (visible) window_->Hide(); - window_->SetProperty(aura::client::kAlwaysOnTopKey, false); + window_->SetProperty(aura::client::kZOrderingKey, ui::ZOrderLevel::kNormal); // Technically it is possible that a |window_| could make itself // always_on_top really quickly. This is probably not a realistic case but // check if the two windows are in the same container just in case. @@ -344,14 +345,14 @@ window_->parent()->StackChildAbove(window_on_top, window_); if (visible) window_->Show(); - cached_always_on_top_ = true; + cached_z_order_ = z_order; } } -void WindowState::RestoreAlwaysOnTop() { - if (cached_always_on_top_) { - cached_always_on_top_ = false; - window_->SetProperty(aura::client::kAlwaysOnTopKey, true); +void WindowState::RestoreZOrdering() { + if (cached_z_order_ != ui::ZOrderLevel::kNormal) { + window_->SetProperty(aura::client::kZOrderingKey, cached_z_order_); + cached_z_order_ = ui::ZOrderLevel::kNormal; } } @@ -544,15 +545,15 @@ unminimize_to_restore_bounds_(false), hide_shelf_when_fullscreen_(true), autohide_shelf_when_maximized_or_fullscreen_(false), - cached_always_on_top_(false), + cached_z_order_(ui::ZOrderLevel::kNormal), ignore_property_change_(false), current_state_(new DefaultState(ToWindowStateType(GetShowState()))) { window_->AddObserver(this); OnPrePipStateChange(WindowStateType::kDefault); } -bool WindowState::GetAlwaysOnTop() const { - return window_->GetProperty(aura::client::kAlwaysOnTopKey); +ui::ZOrderLevel WindowState::GetZOrdering() const { + return window_->GetProperty(aura::client::kZOrderingKey); } ui::WindowShowState WindowState::GetShowState() const {
diff --git a/ash/wm/window_state.h b/ash/wm/window_state.h index 0d753828..1f376ef5 100644 --- a/ash/wm/window_state.h +++ b/ash/wm/window_state.h
@@ -174,12 +174,12 @@ // TODO(oshima): Change to use RESTORE event. void Restore(); - // Caches, then disables always on top state and then stacks |window_| below - // |window_on_top| if a |window_| is currently in always on top state. - void DisableAlwaysOnTop(aura::Window* window_on_top); + // Caches, then disables z-ordering state and then stacks |window_| below + // |window_on_top| if |window_| currently has a special z-order. + void DisableZOrdering(aura::Window* window_on_top); - // Restores always on top state that a window might have cached. - void RestoreAlwaysOnTop(); + // Restores the z-ordering state that a window might have cached. + void RestoreZOrdering(); // Invoked when a WMevent occurs, which drives the internal // state machine. @@ -376,8 +376,8 @@ bool HasMaximumWidthOrHeight() const; - // Returns the window's current always_on_top state. - bool GetAlwaysOnTop() const; + // Returns the window's current z-ordering state. + ui::ZOrderLevel GetZOrdering() const; // Returns the window's current show state. ui::WindowShowState GetShowState() const; @@ -451,7 +451,7 @@ bool ignore_keyboard_bounds_change_ = false; bool hide_shelf_when_fullscreen_; bool autohide_shelf_when_maximized_or_fullscreen_; - bool cached_always_on_top_; + ui::ZOrderLevel cached_z_order_; bool allow_set_bounds_direct_ = false; // A property to save the ratio between snapped window width and display
diff --git a/ash/wm/workspace/phantom_window_controller.cc b/ash/wm/workspace/phantom_window_controller.cc index 2ccf65a..59922fe 100644 --- a/ash/wm/workspace/phantom_window_controller.cc +++ b/ash/wm/workspace/phantom_window_controller.cc
@@ -73,7 +73,7 @@ // PhantomWindowController is used by FrameMaximizeButton to highlight the // launcher button. Put the phantom in the same window as the launcher so that // the phantom is visible. - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.name = "PhantomWindow"; params.layer_type = ui::LAYER_SOLID_COLOR;
diff --git a/ash/wm/workspace/workspace_layout_manager.cc b/ash/wm/workspace/workspace_layout_manager.cc index 8ed01ff..99cc601 100644 --- a/ash/wm/workspace/workspace_layout_manager.cc +++ b/ash/wm/workspace/workspace_layout_manager.cc
@@ -152,7 +152,7 @@ backdrop_controller_->OnWindowAddedToLayout(); WindowPositioner::RearrangeVisibleWindowOnShow(child); if (Shell::Get()->screen_pinning_controller()->IsPinned()) - wm::GetWindowState(child)->DisableAlwaysOnTop(nullptr); + wm::GetWindowState(child)->DisableZOrdering(nullptr); } void WorkspaceLayoutManager::OnWillRemoveWindowFromLayout(aura::Window* child) { @@ -302,8 +302,9 @@ void WorkspaceLayoutManager::OnWindowPropertyChanged(aura::Window* window, const void* key, intptr_t old) { - if (key == aura::client::kAlwaysOnTopKey) { - if (window->GetProperty(aura::client::kAlwaysOnTopKey)) { + if (key == aura::client::kZOrderingKey) { + if (window->GetProperty(aura::client::kZOrderingKey) != + ui::ZOrderLevel::kNormal) { aura::Window* container = root_window_controller_->always_on_top_controller()->GetContainer( window); @@ -519,9 +520,9 @@ for (aura::Window* window : windows) { wm::WindowState* window_state = wm::GetWindowState(window); if (active_desk_fullscreen_window) - window_state->DisableAlwaysOnTop(active_desk_fullscreen_window); + window_state->DisableZOrdering(active_desk_fullscreen_window); else - window_state->RestoreAlwaysOnTop(); + window_state->RestoreZOrdering(); } }
diff --git a/ash/wm/workspace/workspace_layout_manager_unittest.cc b/ash/wm/workspace/workspace_layout_manager_unittest.cc index ea208b0a..3790e7db 100644 --- a/ash/wm/workspace/workspace_layout_manager_unittest.cc +++ b/ash/wm/workspace/workspace_layout_manager_unittest.cc
@@ -808,34 +808,37 @@ CreateTestWindowInShellWithBounds(bounds)); std::unique_ptr<aura::Window> always_on_top_window2( CreateTestWindowInShellWithBounds(bounds)); - always_on_top_window1->SetProperty(aura::client::kAlwaysOnTopKey, true); - always_on_top_window2->SetProperty(aura::client::kAlwaysOnTopKey, true); + always_on_top_window1->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); + always_on_top_window2->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); // Making a window fullscreen temporarily suspends always on top state. fullscreen_window->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_FULLSCREEN); - EXPECT_FALSE( - always_on_top_window1->GetProperty(aura::client::kAlwaysOnTopKey)); - EXPECT_FALSE( - always_on_top_window2->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + always_on_top_window1->GetProperty(aura::client::kZOrderingKey)); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + always_on_top_window2->GetProperty(aura::client::kZOrderingKey)); EXPECT_NE(nullptr, wm::GetWindowForFullscreenModeForContext(fullscreen_window.get())); // Adding a new always-on-top window is not affected by fullscreen. std::unique_ptr<aura::Window> always_on_top_window3( CreateTestWindowInShellWithBounds(bounds)); - always_on_top_window3->SetProperty(aura::client::kAlwaysOnTopKey, true); - EXPECT_TRUE( - always_on_top_window3->GetProperty(aura::client::kAlwaysOnTopKey)); + always_on_top_window3->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window3->GetProperty(aura::client::kZOrderingKey)); // Making fullscreen window normal restores always on top windows. fullscreen_window->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_NORMAL); - EXPECT_TRUE( - always_on_top_window1->GetProperty(aura::client::kAlwaysOnTopKey)); - EXPECT_TRUE( - always_on_top_window2->GetProperty(aura::client::kAlwaysOnTopKey)); - EXPECT_TRUE( - always_on_top_window3->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window1->GetProperty(aura::client::kZOrderingKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window2->GetProperty(aura::client::kZOrderingKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window3->GetProperty(aura::client::kZOrderingKey)); EXPECT_EQ(nullptr, wm::GetWindowForFullscreenModeForContext(fullscreen_window.get())); } @@ -851,22 +854,26 @@ wm::WindowState* window_state = wm::GetWindowState(pip_window.get()); const wm::WMEvent enter_pip(wm::WM_EVENT_PIP); window_state->OnWMEvent(&enter_pip); - pip_window->SetProperty(aura::client::kAlwaysOnTopKey, true); + pip_window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); EXPECT_TRUE(window_state->IsPip()); - EXPECT_TRUE(pip_window->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + pip_window->GetProperty(aura::client::kZOrderingKey)); // Making a window fullscreen temporarily suspends always on top state, but // should not do so for PIP. fullscreen_window->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_FULLSCREEN); - EXPECT_TRUE(pip_window->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + pip_window->GetProperty(aura::client::kZOrderingKey)); EXPECT_NE(nullptr, wm::GetWindowForFullscreenModeForContext(fullscreen_window.get())); // Making fullscreen window normal does not affect PIP. fullscreen_window->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_NORMAL); - EXPECT_TRUE(pip_window->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + pip_window->GetProperty(aura::client::kZOrderingKey)); EXPECT_EQ(nullptr, wm::GetWindowForFullscreenModeForContext(fullscreen_window.get())); } @@ -880,32 +887,35 @@ CreateTestWindowInShellWithBounds(bounds)); std::unique_ptr<aura::Window> always_on_top_window2( CreateTestWindowInShellWithBounds(bounds)); - always_on_top_window1->SetProperty(aura::client::kAlwaysOnTopKey, true); - always_on_top_window2->SetProperty(aura::client::kAlwaysOnTopKey, true); + always_on_top_window1->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); + always_on_top_window2->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); // Making a window pinned temporarily suspends always on top state. const bool trusted = false; wm::PinWindow(pinned_window.get(), trusted); - EXPECT_FALSE( - always_on_top_window1->GetProperty(aura::client::kAlwaysOnTopKey)); - EXPECT_FALSE( - always_on_top_window2->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + always_on_top_window1->GetProperty(aura::client::kZOrderingKey)); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + always_on_top_window2->GetProperty(aura::client::kZOrderingKey)); // Adding a new always-on-top window also is affected by pinned mode. std::unique_ptr<aura::Window> always_on_top_window3( CreateTestWindowInShellWithBounds(bounds)); - always_on_top_window3->SetProperty(aura::client::kAlwaysOnTopKey, true); - EXPECT_FALSE( - always_on_top_window3->GetProperty(aura::client::kAlwaysOnTopKey)); + always_on_top_window3->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + always_on_top_window3->GetProperty(aura::client::kZOrderingKey)); // Making pinned window normal restores always on top windows. wm::GetWindowState(pinned_window.get())->Restore(); - EXPECT_TRUE( - always_on_top_window1->GetProperty(aura::client::kAlwaysOnTopKey)); - EXPECT_TRUE( - always_on_top_window2->GetProperty(aura::client::kAlwaysOnTopKey)); - EXPECT_TRUE( - always_on_top_window3->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window1->GetProperty(aura::client::kZOrderingKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window2->GetProperty(aura::client::kZOrderingKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + always_on_top_window3->GetProperty(aura::client::kZOrderingKey)); } TEST_F(WorkspaceLayoutManagerSoloTest, PinnedDoesNotSuspendAlwaysOnTopForPip) { @@ -918,16 +928,19 @@ wm::WindowState* window_state = wm::GetWindowState(pip_window.get()); const wm::WMEvent enter_pip(wm::WM_EVENT_PIP); window_state->OnWMEvent(&enter_pip); - pip_window->SetProperty(aura::client::kAlwaysOnTopKey, true); + pip_window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); EXPECT_TRUE(window_state->IsPip()); - EXPECT_TRUE(pip_window->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + pip_window->GetProperty(aura::client::kZOrderingKey)); } // Making a window pinned temporarily suspends always on top state, except // for PIP. const bool trusted = false; wm::PinWindow(pinned_window.get(), trusted); - EXPECT_TRUE(pip_window->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + pip_window->GetProperty(aura::client::kZOrderingKey)); // Adding a new PIP window should still end up always on top. std::unique_ptr<aura::Window> pip_window2( @@ -936,15 +949,19 @@ wm::WindowState* window_state = wm::GetWindowState(pip_window2.get()); const wm::WMEvent enter_pip(wm::WM_EVENT_PIP); window_state->OnWMEvent(&enter_pip); - pip_window2->SetProperty(aura::client::kAlwaysOnTopKey, true); + pip_window2->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); EXPECT_TRUE(window_state->IsPip()); - EXPECT_TRUE(pip_window2->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + pip_window2->GetProperty(aura::client::kZOrderingKey)); } // Making pinned window normal should not affect existing PIP windows. wm::GetWindowState(pinned_window.get())->Restore(); - EXPECT_TRUE(pip_window->GetProperty(aura::client::kAlwaysOnTopKey)); - EXPECT_TRUE(pip_window2->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + pip_window->GetProperty(aura::client::kZOrderingKey)); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + pip_window2->GetProperty(aura::client::kZOrderingKey)); } // Tests fullscreen window size during root window resize. @@ -1058,7 +1075,8 @@ std::unique_ptr<aura::Window> window( CreateTestWindowInShellWithBounds(gfx::Rect(1, 2, 3, 4))); // window with AlwaysOnTop will be managed by BaseLayoutManager. - window->SetProperty(aura::client::kAlwaysOnTopKey, true); + window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); window->Show(); Shelf* shelf = GetPrimaryShelf(); @@ -1999,7 +2017,8 @@ std::unique_ptr<aura::Window> always_on_top_window( CreateTestWindowInShellWithBounds(gfx::Rect(1, 2, 3, 4))); always_on_top_window->Show(); - always_on_top_window->SetProperty(aura::client::kAlwaysOnTopKey, true); + always_on_top_window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); always_on_top_window->SetProperty(kBackdropWindowMode, BackdropWindowMode::kEnabled); @@ -2009,7 +2028,8 @@ // at this moment. ASSERT_EQ(always_on_top_container->children().size(), 2U); - always_on_top_window->SetProperty(aura::client::kAlwaysOnTopKey, false); + always_on_top_window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kNormal); // The backdrop window will be destroyed immediately after // |always_on_top_window| moves to the default container. EXPECT_TRUE(always_on_top_container->children().empty());
diff --git a/base/android/proguard/chromium_apk.flags b/base/android/proguard/chromium_apk.flags index 968bdb0..21995fe 100644 --- a/base/android/proguard/chromium_apk.flags +++ b/base/android/proguard/chromium_apk.flags
@@ -15,6 +15,14 @@ public static *** CREATOR; } +# Keep all Fragment constructors since they are only usable via reflection. +-keepclassmembers class * extends android.support.v4.app.Fragment { + public <init>(); +} +-keepclassmembers class * extends androidx.fragment.app.Fragment { + public <init>(); +} + # Don't obfuscate Parcelables as they might be marshalled outside Chrome. # If we annotated all Parcelables that get put into Bundles other than # for saveInstanceState (e.g. PendingIntents), then we could actually keep the
diff --git a/base/logging_unittest.cc b/base/logging_unittest.cc index dbabc6d1..e0352d0 100644 --- a/base/logging_unittest.cc +++ b/base/logging_unittest.cc
@@ -38,15 +38,17 @@ #include <fuchsia/logger/cpp/fidl.h> #include <fuchsia/logger/cpp/fidl_test_base.h> #include <lib/fidl/cpp/binding.h> +#include <lib/zx/channel.h> #include <lib/zx/event.h> -#include <lib/zx/port.h> +#include <lib/zx/exception.h> #include <lib/zx/process.h> #include <lib/zx/thread.h> #include <lib/zx/time.h> #include <zircon/process.h> #include <zircon/syscalls/debug.h> -#include <zircon/syscalls/port.h> +#include <zircon/syscalls/exception.h> #include <zircon/types.h> + #include "base/fuchsia/fuchsia_logging.h" #include "base/fuchsia/service_directory_client.h" #endif // OS_FUCHSIA @@ -332,31 +334,33 @@ } #endif -static const unsigned int kExceptionPortKey = 1u; -static const unsigned int kThreadEndedPortKey = 2u; - struct thread_data_t { // For signaling the thread ended properly. - zx::unowned_event event; - // For registering thread termination. - zx::unowned_port port; + zx::event event; + // For catching thread exceptions. Created by the crashing thread. + zx::channel channel; // Location where the thread is expected to crash. int death_location; }; -void* CrashThread(void* arg) { - zx_status_t status; +// Indicates the exception channel has been created successfully. +constexpr zx_signals_t kChannelReadySignal = ZX_USER_SIGNAL_0; +// Indicates an error setting up the crash thread. +constexpr zx_signals_t kCrashThreadErrorSignal = ZX_USER_SIGNAL_1; + +void* CrashThread(void* arg) { thread_data_t* data = (thread_data_t*)arg; int death_location = data->death_location; - // Register the exception handler on the port. - status = zx::thread::self()->bind_exception_port(*data->port, - kExceptionPortKey, 0); + // Register the exception handler. + zx_status_t status = + zx::thread::self()->create_exception_channel(0, &data->channel); if (status != ZX_OK) { - data->event->signal(0, ZX_USER_SIGNAL_0); + data->event.signal(0, kCrashThreadErrorSignal); return nullptr; } + data->event.signal(0, kChannelReadySignal); DO_CHECK(death_location != 1); DO_CHECK(death_location != 2); @@ -364,44 +368,48 @@ // We should never reach this point, signal the thread incorrectly ended // properly. - data->event->signal(0, ZX_USER_SIGNAL_0); + data->event.signal(0, kCrashThreadErrorSignal); return nullptr; } // Runs the CrashThread function in a separate thread. void SpawnCrashThread(int death_location, uintptr_t* child_crash_addr) { - zx::port port; zx::event event; - zx_status_t status; - - status = zx::port::create(0, &port); - ASSERT_EQ(status, ZX_OK); - status = zx::event::create(0, &event); - ASSERT_EQ(status, ZX_OK); - - // Register the thread ended event on the port. - status = event.wait_async(port, kThreadEndedPortKey, ZX_USER_SIGNAL_0, - ZX_WAIT_ASYNC_ONCE); + zx_status_t status = zx::event::create(0, &event); ASSERT_EQ(status, ZX_OK); // Run the thread. - thread_data_t thread_data = {zx::unowned_event(event), zx::unowned_port(port), - death_location}; + thread_data_t thread_data = {std::move(event), zx::channel(), death_location}; pthread_t thread; int ret = pthread_create(&thread, nullptr, CrashThread, &thread_data); ASSERT_EQ(ret, 0); - // Wait on the port. - zx_port_packet_t packet; - status = port.wait(zx::time::infinite(), &packet); + // Wait for the thread to set up its exception channel. + zx_signals_t signals = 0; + status = + thread_data.event.wait_one(kChannelReadySignal | kCrashThreadErrorSignal, + zx::time::infinite(), &signals); + ASSERT_EQ(status, ZX_OK); + ASSERT_EQ(signals, kChannelReadySignal); + + // Wait for the exception and read it out of the channel. + status = + thread_data.channel.wait_one(ZX_CHANNEL_READABLE | ZX_CHANNEL_PEER_CLOSED, + zx::time::infinite(), &signals); ASSERT_EQ(status, ZX_OK); // Check the thread did crash and not terminate. - ASSERT_EQ(packet.key, kExceptionPortKey); + ASSERT_FALSE(signals & ZX_CHANNEL_PEER_CLOSED); + + zx_exception_info_t exception_info; + zx::exception exception; + status = thread_data.channel.read( + 0, &exception_info, exception.reset_and_get_address(), + sizeof(exception_info), 1, nullptr, nullptr); + ASSERT_EQ(status, ZX_OK); // Get the crash address. zx::thread zircon_thread; - status = zx::process::self()->get_child(packet.exception.tid, - ZX_RIGHT_SAME_RIGHTS, &zircon_thread); + status = exception.get_thread(&zircon_thread); ASSERT_EQ(status, ZX_OK); zx_thread_state_general_regs_t buffer; status = zircon_thread.read_state(ZX_THREAD_STATE_GENERAL_REGS, &buffer,
diff --git a/base/memory/platform_shared_memory_region.h b/base/memory/platform_shared_memory_region.h index 1a59564..a04b44a 100644 --- a/base/memory/platform_shared_memory_region.h +++ b/base/memory/platform_shared_memory_region.h
@@ -115,7 +115,11 @@ CREATE_FILE_MAPPING_FAILURE = 6, REDUCE_PERMISSIONS_FAILURE = 7, ALREADY_EXISTS = 8, - kMaxValue = ALREADY_EXISTS + ALLOCATE_FILE_REGION_FAILURE = 9, + FSTAT_FAILURE = 10, + INODES_MISMATCH = 11, + GET_SHMEM_TEMP_DIR_FAILURE = 12, + kMaxValue = GET_SHMEM_TEMP_DIR_FAILURE }; #if defined(OS_LINUX)
diff --git a/base/memory/platform_shared_memory_region_posix.cc b/base/memory/platform_shared_memory_region_posix.cc index 036c6e5..1fe6f81e 100644 --- a/base/memory/platform_shared_memory_region_posix.cc +++ b/base/memory/platform_shared_memory_region_posix.cc
@@ -10,6 +10,7 @@ #include "base/files/file.h" #include "base/files/file_util.h" +#include "base/metrics/histogram_macros.h" #include "base/threading/thread_restrictions.h" #include "build/build_config.h" @@ -18,6 +19,12 @@ namespace { +#if !defined(OS_NACL) +void LogCreateError(PlatformSharedMemoryRegion::CreateError error) { + UMA_HISTOGRAM_ENUMERATION("SharedMemory.CreateError", error); +} +#endif + struct ScopedPathUnlinkerTraits { static const FilePath* InvalidValue() { return nullptr; } @@ -226,11 +233,15 @@ // Untrusted code can't create descriptors or handles. return {}; #else - if (size == 0) + if (size == 0) { + LogCreateError(PlatformSharedMemoryRegion::CreateError::SIZE_ZERO); return {}; + } - if (size > static_cast<size_t>(std::numeric_limits<int>::max())) + if (size > static_cast<size_t>(std::numeric_limits<int>::max())) { + LogCreateError(PlatformSharedMemoryRegion::CreateError::SIZE_TOO_LARGE); return {}; + } CHECK_NE(mode, Mode::kReadOnly) << "Creating a region in read-only mode will " "lead to this region being non-modifiable"; @@ -249,13 +260,18 @@ #else false /* executable */, #endif - &directory)) + &directory)) { + LogCreateError( + PlatformSharedMemoryRegion::CreateError::GET_SHMEM_TEMP_DIR_FAILURE); return {}; + } FilePath path; File shm_file(CreateAndOpenFdForTemporaryFileInDir(directory, &path)); if (!shm_file.IsValid()) { + LogCreateError( + PlatformSharedMemoryRegion::CreateError::CREATE_FILE_MAPPING_FAILURE); PLOG(ERROR) << "Creating shared memory in " << path.value() << " failed"; FilePath dir = path.DirName(); if (access(dir.value().c_str(), W_OK | X_OK) < 0) { @@ -278,34 +294,43 @@ // Also open as readonly so that we can ConvertToReadOnly(). readonly_fd.reset(HANDLE_EINTR(open(path.value().c_str(), O_RDONLY))); if (!readonly_fd.is_valid()) { + LogCreateError( + PlatformSharedMemoryRegion::CreateError::REDUCE_PERMISSIONS_FAILURE); DPLOG(ERROR) << "open(\"" << path.value() << "\", O_RDONLY) failed"; return {}; } } - if (!AllocateFileRegion(&shm_file, 0, size)) + if (!AllocateFileRegion(&shm_file, 0, size)) { + LogCreateError( + PlatformSharedMemoryRegion::CreateError::ALLOCATE_FILE_REGION_FAILURE); return {}; + } if (readonly_fd.is_valid()) { struct stat stat = {}; if (fstat(shm_file.GetPlatformFile(), &stat) != 0) { + LogCreateError(PlatformSharedMemoryRegion::CreateError::FSTAT_FAILURE); DPLOG(ERROR) << "fstat(fd) failed"; return {}; } struct stat readonly_stat = {}; if (fstat(readonly_fd.get(), &readonly_stat) != 0) { + LogCreateError(PlatformSharedMemoryRegion::CreateError::FSTAT_FAILURE); DPLOG(ERROR) << "fstat(readonly_fd) failed"; return {}; } if (stat.st_dev != readonly_stat.st_dev || stat.st_ino != readonly_stat.st_ino) { + LogCreateError(PlatformSharedMemoryRegion::CreateError::INODES_MISMATCH); LOG(ERROR) << "Writable and read-only inodes don't match; bailing"; return {}; } } + LogCreateError(PlatformSharedMemoryRegion::CreateError::SUCCESS); return PlatformSharedMemoryRegion( {ScopedFD(shm_file.TakePlatformFile()), std::move(readonly_fd)}, mode, size, UnguessableToken::Create());
diff --git a/base/message_loop/message_loop_current.cc b/base/message_loop/message_loop_current.cc index 71a45d0..54e2d2b 100644 --- a/base/message_loop/message_loop_current.cc +++ b/base/message_loop/message_loop_current.cc
@@ -51,11 +51,6 @@ current_->RemoveDestructionObserver(destruction_observer); } -scoped_refptr<SingleThreadTaskRunner> MessageLoopCurrent::task_runner() const { - DCHECK(current_->IsBoundToCurrentThread()); - return current_->GetTaskRunner(); -} - void MessageLoopCurrent::SetTaskRunner( scoped_refptr<SingleThreadTaskRunner> task_runner) { DCHECK(current_->IsBoundToCurrentThread());
diff --git a/base/message_loop/message_loop_current.h b/base/message_loop/message_loop_current.h index f259d89..08a1c5e3 100644 --- a/base/message_loop/message_loop_current.h +++ b/base/message_loop/message_loop_current.h
@@ -105,11 +105,6 @@ // DestructionObserver is receiving a notification callback. void RemoveDestructionObserver(DestructionObserver* destruction_observer); - // Forwards to MessageLoop::task_runner(). - // DEPRECATED(https://crbug.com/616447): Use ThreadTaskRunnerHandle::Get() - // instead of MessageLoopCurrent::Get()->task_runner(). - scoped_refptr<SingleThreadTaskRunner> task_runner() const; - // Forwards to MessageLoop::SetTaskRunner(). // DEPRECATED(https://crbug.com/825327): only owners of the MessageLoop // instance should replace its TaskRunner.
diff --git a/base/test/scoped_mock_time_message_loop_task_runner_unittest.cc b/base/test/scoped_mock_time_message_loop_task_runner_unittest.cc index ac3b966..f143ed85 100644 --- a/base/test/scoped_mock_time_message_loop_task_runner_unittest.cc +++ b/base/test/scoped_mock_time_message_loop_task_runner_unittest.cc
@@ -17,6 +17,7 @@ #include "base/message_loop/message_loop_current.h" #include "base/test/test_mock_time_task_runner.h" #include "base/test/test_pending_task.h" +#include "base/threading/thread_task_runner_handle.h" #include "base/time/time.h" #include "testing/gtest/include/gtest/gtest.h" @@ -24,7 +25,7 @@ namespace { TaskRunner* GetCurrentTaskRunner() { - return MessageLoopCurrent::Get()->task_runner().get(); + return ThreadTaskRunnerHandle::Get().get(); } void AssignTrue(bool* out) {
diff --git a/build/chromeos/test_runner.py b/build/chromeos/test_runner.py index b050a8e..6437758 100755 --- a/build/chromeos/test_runner.py +++ b/build/chromeos/test_runner.py
@@ -564,9 +564,9 @@ '--gtest_repeat')] if self._additional_args: - raise TestFormatError( - 'Sanity test should not have additional args: %s' % ( - self._additional_args)) + logging.error( + 'Sanity test should not have additional args: These will be ' + 'ignored: %s', self._additional_args) # VMs don't have the disk space for an unstripped version of Chrome # instrumented for code coverage, so only strip in that case.
diff --git a/build/config/c++/libc++.natvis b/build/config/c++/libc++.natvis index 0616088..2603e2e8 100644 --- a/build/config/c++/libc++.natvis +++ b/build/config/c++/libc++.natvis
@@ -53,7 +53,9 @@ <Type Name="std::__1::basic_string<char,*>"> <!--<Intrinsic Name="is_long" Expression="((__rep*)&__r_)->__s.__size_ & 0x80" />--> - <!-- The above doesn't work for reasons I don't understand. + <!-- The above doesn't work because of https://llvm.org/PR41615 + TODO(thakis): Now that we have clang r362038, try the above approach + again. The below assumes the alternate string layout and little endianness :/ --> <Intrinsic Name="is_long"
diff --git a/build/fuchsia/linux.sdk.sha1 b/build/fuchsia/linux.sdk.sha1 index b240549..6b7e41b 100644 --- a/build/fuchsia/linux.sdk.sha1 +++ b/build/fuchsia/linux.sdk.sha1
@@ -1 +1 @@ -8907715714103854416 \ No newline at end of file +8907684647168301152 \ No newline at end of file
diff --git a/build/fuchsia/mac.sdk.sha1 b/build/fuchsia/mac.sdk.sha1 index dd61703..ab70073 100644 --- a/build/fuchsia/mac.sdk.sha1 +++ b/build/fuchsia/mac.sdk.sha1
@@ -1 +1 @@ -8907715712174591808 \ No newline at end of file +8907684424932579328 \ No newline at end of file
diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn index 5e55af1..4f2641cd 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn
@@ -576,7 +576,6 @@ "/DELAYLOAD:dxgi.dll", "/DELAYLOAD:dxva2.dll", "/DELAYLOAD:esent.dll", - "/DELAYLOAD:gdi32.dll", "/DELAYLOAD:imm32.dll", "/DELAYLOAD:ole32.dll", "/DELAYLOAD:oleacc.dll",
diff --git a/chrome/android/chrome_test_java_sources.gni b/chrome/android/chrome_test_java_sources.gni index 5b9f9cc..dbd1443 100644 --- a/chrome/android/chrome_test_java_sources.gni +++ b/chrome/android/chrome_test_java_sources.gni
@@ -251,6 +251,7 @@ "javatests/src/org/chromium/chrome/browser/ntp/cards/NewTabPageRecyclerViewTest.java", "javatests/src/org/chromium/chrome/browser/ntp/snippets/ArticleSnippetsTest.java", "javatests/src/org/chromium/chrome/browser/offlinepages/MHTMLPageTest.java", + "javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageArchivePublisherBridgeTest.java", "javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageAutoFetchTest.java", "javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageBridgeTest.java", "javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageRequestTest.java",
diff --git a/chrome/android/features/vr/java/src/org/chromium/chrome/browser/vr/ArConsentDialog.java b/chrome/android/features/vr/java/src/org/chromium/chrome/browser/vr/ArConsentDialog.java index 1a268a5..7f228eb 100644 --- a/chrome/android/features/vr/java/src/org/chromium/chrome/browser/vr/ArConsentDialog.java +++ b/chrome/android/features/vr/java/src/org/chromium/chrome/browser/vr/ArConsentDialog.java
@@ -73,7 +73,7 @@ .with(ModalDialogProperties.CANCEL_ON_TOUCH_OUTSIDE, true) .build(); mModalDialogManager = activity.getModalDialogManager(); - mModalDialogManager.showDialog(model, ModalDialogManager.ModalDialogType.APP); + mModalDialogManager.showDialog(model, ModalDialogManager.ModalDialogType.TAB); } @Override @@ -142,6 +142,6 @@ @NativeMethods /* package */ interface Natives { - void onUserConsentResult(long nativeArcoreConsentPrompt, boolean allowed); + void onUserConsentResult(long nativeArCoreConsentPrompt, boolean allowed); } }
diff --git a/chrome/android/java/monochrome_public_bundle.proguard_flags.expected b/chrome/android/java/monochrome_public_bundle.proguard_flags.expected index 730cf54..8d4e368d 100644 --- a/chrome/android/java/monochrome_public_bundle.proguard_flags.expected +++ b/chrome/android/java/monochrome_public_bundle.proguard_flags.expected
@@ -117,6 +117,14 @@ public static *** CREATOR; } +# Keep all Fragment constructors since they are only usable via reflection. +-keepclassmembers class * extends android.support.v4.app.Fragment { + public <init>(); +} +-keepclassmembers class * extends androidx.fragment.app.Fragment { + public <init>(); +} + # Don't obfuscate Parcelables as they might be marshalled outside Chrome. # If we annotated all Parcelables that get put into Bundles other than # for saveInstanceState (e.g. PendingIntents), then we could actually keep the
diff --git a/chrome/android/java/res/values/dimens.xml b/chrome/android/java/res/values/dimens.xml index e3e5050..e4cc550 100644 --- a/chrome/android/java/res/values/dimens.xml +++ b/chrome/android/java/res/values/dimens.xml
@@ -625,8 +625,8 @@ <!-- History Navigation UI Item --> <dimen name="navigation_bubble_border_width">1dp</dimen> - <dimen name="navigation_bubble_default_height">48dp</dimen> - <dimen name="navigation_bubble_bg_vertical_inset">8dp</dimen> + <dimen name="navigation_bubble_default_height">32dp</dimen> + <dimen name="navigation_bubble_bg_vertical_inset">0dp</dimen> <dimen name="navigation_bubble_vertical_padding">4dp</dimen> <dimen name="navigation_bubble_horizontal_padding">8dp</dimen> <dimen name="navigation_bubble_icon_size">20dp</dimen>
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/offlinepages/OfflinePageArchivePublisherBridge.java b/chrome/android/java/src/org/chromium/chrome/browser/offlinepages/OfflinePageArchivePublisherBridge.java index fc92a54..b1375287 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/offlinepages/OfflinePageArchivePublisherBridge.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/offlinepages/OfflinePageArchivePublisherBridge.java
@@ -6,15 +6,28 @@ import android.annotation.TargetApi; import android.app.DownloadManager; +import android.content.ContentResolver; +import android.content.ContentValues; import android.content.Context; import android.net.Uri; import android.os.Build; +import android.os.Environment; +import android.provider.MediaStore.MediaColumns; +import android.text.format.DateUtils; +import org.chromium.base.ContentUriUtils; import org.chromium.base.ContextUtils; import org.chromium.base.Log; +import org.chromium.base.VisibleForTesting; import org.chromium.base.annotations.CalledByNative; import org.chromium.base.annotations.JNINamespace; +import java.io.FileInputStream; +import java.io.InputStream; +import java.io.OutputStream; +import java.lang.reflect.Field; +import java.lang.reflect.Method; + /** * Since the {@link AndroidDownloadManager} can only be accessed from Java, this bridge will * transfer all C++ calls over to Java land for making the call to ADM. This is a one-way bridge, @@ -34,7 +47,8 @@ /** Returns true if DownloadManager is installed on the phone. */ @CalledByNative - private static boolean isAndroidDownloadManagerInstalled() { + @VisibleForTesting + public static boolean isAndroidDownloadManagerInstalled() { DownloadManager downloadManager = getDownloadManager(); return (downloadManager != null); } @@ -50,7 +64,8 @@ * @return the download ID of this item as assigned by the download manager. */ @CalledByNative - private static long addCompletedDownload(String title, String description, String path, + @VisibleForTesting + public static long addCompletedDownload(String title, String description, String path, long length, String uri, String referer) { try { // Call the proper version of the pass through based on the supported API level. @@ -93,7 +108,8 @@ * @return the number of IDs that were removed. */ @CalledByNative - private static int remove(long[] ids) { + @VisibleForTesting + public static int remove(long[] ids) { DownloadManager downloadManager = getDownloadManager(); try { if (downloadManager == null) return 0; @@ -109,4 +125,84 @@ return (DownloadManager) ContextUtils.getApplicationContext().getSystemService( Context.DOWNLOAD_SERVICE); } + + /** + * Adds an archive to the downloads collection on Android Q+. Preferred alternative to + * addCompletedDownload for Android Q and later. + * + * TODO(iwells): Remove reflection once API level 29 is supported. + * + * @param page Offline page to be published. + * @return Content URI referring to the published page. + */ + @CalledByNative + @VisibleForTesting + public static String publishArchiveToDownloadsCollection(OfflinePageItem page) { + assert !org.chromium.base.BuildInfo.isAtLeastQ(); + + final String isPending = "is_pending"; // MediaStore.IS_PENDING + + // Collect all fields for creating intermediate URI. + final long now = System.currentTimeMillis() / 1000; + ContentValues pendingValues = new ContentValues(); + pendingValues.put(MediaColumns.DATE_ADDED, now); + pendingValues.put(MediaColumns.DATE_MODIFIED, now); + pendingValues.put(isPending, 1); + pendingValues.put("download_uri", page.getUrl()); // MediaStore.DownloadColumns.DOWNLOAD_URI + + Uri externalDownloadUri; + try { + // Class android.provider.MediaStore.Downloads added in API level 29. + Class<?> downloadsClazz = Class.forName("android.provider.MediaStore$Downloads"); + Field externalUriField = downloadsClazz.getDeclaredField("EXTERNAL_CONTENT_URI"); + externalDownloadUri = (Uri) externalUriField.get(null); + Field primaryDirectoryField = MediaColumns.class.getDeclaredField("PRIMARY_DIRECTORY"); + pendingValues.put( + (String) primaryDirectoryField.get(null), Environment.DIRECTORY_DOWNLOADS); + } catch (Exception e) { + Log.d(TAG, "Unable to set pending download fields.", e); + return ""; + } + + // Pending URI will expire after 3 days. + long newExpirationTime = (System.currentTimeMillis() + 3 * DateUtils.DAY_IN_MILLIS) / 1000; + pendingValues.put("date_expires", newExpirationTime); + + // Create intermediate URI. + ContentResolver contentResolver = ContextUtils.getApplicationContext().getContentResolver(); + Uri intermediateUri = contentResolver.insert(externalDownloadUri, pendingValues); + if (intermediateUri == null || !ContentUriUtils.isContentUri(intermediateUri.toString())) { + Log.d(TAG, "Failed to create intermediate URI."); + return ""; + } + + // Copy archive to intermediate URI. + try { + // Class android.os.FileUtils added in API level 29. + Class<?> fileUtilsClazz = Class.forName("android.os.FileUtils"); + Method copyMethod = + fileUtilsClazz.getMethod("copy", InputStream.class, OutputStream.class); + + OutputStream out = contentResolver.openOutputStream(intermediateUri); + InputStream in = new FileInputStream(page.getFilePath()); + copyMethod.invoke(null, in, out); + in.close(); + out.close(); + } catch (Exception e) { + Log.d(TAG, "Unable to copy archive to pending URI.", e); + return ""; + } + + // Set display name, MIME type, and pending -> false. + final ContentValues publishValues = new ContentValues(); + publishValues.put(isPending, 0); + publishValues.putNull("date_expires"); + publishValues.put(MediaColumns.DISPLAY_NAME, page.getTitle()); + publishValues.put(MediaColumns.MIME_TYPE, "multipart/related"); + if (contentResolver.update(intermediateUri, publishValues, null, null) != 1) { + Log.d(TAG, "Failed to finish publishing archive."); + } + + return intermediateUri.toString(); + } }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/preferences/password/PasswordEntryEditorPreference.java b/chrome/android/java/src/org/chromium/chrome/browser/preferences/password/PasswordEntryEditorPreference.java deleted file mode 100644 index bb3d5629..0000000 --- a/chrome/android/java/src/org/chromium/chrome/browser/preferences/password/PasswordEntryEditorPreference.java +++ /dev/null
@@ -1,53 +0,0 @@ -// Copyright 2017 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -package org.chromium.chrome.browser.preferences.password; - -import android.app.Activity; -import android.os.Bundle; -import android.preference.Preference; - -import org.chromium.base.Callback; -import org.chromium.chrome.browser.widget.prefeditor.EditorDialog; -import org.chromium.chrome.browser.widget.prefeditor.PasswordEditor; - -/** - * Launches the UI to create a credential. - */ -public class PasswordEntryEditorPreference extends Preference { - final private Activity mActivity; - private EditorDialog mEditorDialog; - private Bundle mExtras; - - public PasswordEntryEditorPreference(Activity activity) { - super(activity); - mActivity = activity; - } - - /** @return The common editor user interface. */ - public EditorDialog getEditorDialog() { - return mEditorDialog; - } - - @Override - protected void onClick() { - mExtras = getExtras(); - preparePasswordEditor(); - } - - private void preparePasswordEditor() { - mEditorDialog = new EditorDialog(mActivity, null /* observer */, null /* runnable */); - PasswordEditor passwordEditor = new PasswordEditor(); - passwordEditor.setEditorDialog(mEditorDialog); - - passwordEditor.edit(null /* toEdit */, new Callback<SavedPasswordEntry>() { - @Override - public void onResult(SavedPasswordEntry credential) { - PasswordManagerHandlerProvider.getInstance() - .getPasswordManagerHandler() - .updatePasswordLists(); - } - }); - } -}
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreInstallUtils.java b/chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreInstallUtils.java index 7394834..ef51870 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreInstallUtils.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreInstallUtils.java
@@ -57,6 +57,11 @@ return sArCoreInstance; } + @CalledByNative + private static ArCoreInstallUtils create(long nativeArCoreInstallUtils) { + return new ArCoreInstallUtils(nativeArCoreInstallUtils); + } + private ArCoreInstallUtils(long nativeArCoreInstallUtils) { mNativeArCoreInstallUtils = nativeArCoreInstallUtils; // Need to be called before trying to access the AR module.
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreJavaUtils.java b/chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreJavaUtils.java index fac78e05..8b8dc7c 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreJavaUtils.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreJavaUtils.java
@@ -4,81 +4,31 @@ package org.chromium.chrome.browser.vr; -import android.app.Activity; import android.content.Context; import android.view.Surface; import dalvik.system.BaseDexClassLoader; -import org.chromium.base.BundleUtils; import org.chromium.base.ContextUtils; import org.chromium.base.Log; import org.chromium.base.StrictModeContext; import org.chromium.base.ThreadUtils; import org.chromium.base.annotations.CalledByNative; import org.chromium.base.annotations.JNINamespace; -import org.chromium.chrome.R; -import org.chromium.chrome.browser.infobar.InfoBarIdentifier; -import org.chromium.chrome.browser.infobar.SimpleConfirmInfoBarBuilder; -import org.chromium.chrome.browser.modules.ModuleInstallUi; import org.chromium.chrome.browser.tab.Tab; -import org.chromium.components.module_installer.ModuleInstaller; /** * Provides ARCore classes access to java-related app functionality. */ @JNINamespace("vr") -public class ArCoreJavaUtils implements ModuleInstallUi.FailureUiListener { +public class ArCoreJavaUtils { private static final String TAG = "ArCoreJavaUtils"; private static final boolean DEBUG_LOGS = false; private long mNativeArCoreJavaUtils; - private boolean mAppInfoInitialized; - private Tab mTab; private ArImmersiveOverlay mArImmersiveOverlay; - // Instance that requested installation of ARCore. - // Should be non-null only if there is a pending request to install ARCore. - private static ArCoreJavaUtils sRequestInstallInstance; - - // Cached ArCoreShim instance - valid only after AR module was installed and - // getArCoreShimInstance() was called. - private static ArCoreShim sArCoreInstance; - - private static ArCoreShim getArCoreShimInstance() { - if (sArCoreInstance != null) return sArCoreInstance; - - try { - sArCoreInstance = - (ArCoreShim) Class.forName("org.chromium.chrome.browser.vr.ArCoreShimImpl") - .newInstance(); - } catch (ClassNotFoundException e) { - // shouldn't happen - we should only call this method once AR module is installed. - throw new RuntimeException(e); - } catch (InstantiationException e) { - throw new RuntimeException(e); - } catch (IllegalAccessException e) { - throw new RuntimeException(e); - } - - return sArCoreInstance; - } - - public static void installArCoreDeviceProviderFactory() { - nativeInstallArCoreDeviceProviderFactory(); - } - - /** - * Gets the current application context. - * - * @return Context The application context. - */ - @CalledByNative - private static Context getApplicationContext() { - return ContextUtils.getApplicationContext(); - } - @CalledByNative private static ArCoreJavaUtils create(long nativeArCoreJavaUtils) { ThreadUtils.assertOnUiThread(); @@ -93,22 +43,19 @@ } } - @Override - public void onRetry() { - if (mNativeArCoreJavaUtils == 0) return; - requestInstallArModule(mTab); - } - - @Override - public void onCancel() { - if (mNativeArCoreJavaUtils == 0) return; - nativeOnRequestInstallArModuleResult(mNativeArCoreJavaUtils, /* success = */ false); + /** + * Gets the current application context. + * + * @return Context The application context. + */ + @CalledByNative + private static Context getApplicationContext() { + return ContextUtils.getApplicationContext(); } private ArCoreJavaUtils(long nativeArCoreJavaUtils) { if (DEBUG_LOGS) Log.i(TAG, "constructor, nativeArCoreJavaUtils=" + nativeArCoreJavaUtils); mNativeArCoreJavaUtils = nativeArCoreJavaUtils; - initializeAppInfo(); } @CalledByNative @@ -151,194 +98,6 @@ mNativeArCoreJavaUtils = 0; } - private void initializeAppInfo() { - mAppInfoInitialized = true; - - // Need to be called before trying to access the AR module. - ModuleInstaller.getInstance().init(); - } - - private @ArCoreShim.Availability int getArCoreInstallStatus() { - return getArCoreShimInstance().checkAvailability(getApplicationContext()); - } - - @CalledByNative - private boolean shouldRequestInstallSupportedArCore() { - @ArCoreShim.Availability - int availability = getArCoreInstallStatus(); - // Skip ARCore installation if we are certain that it is already installed. - // In all other cases, we might as well try to install it and handle installation failures. - return availability != ArCoreShim.Availability.SUPPORTED_INSTALLED; - } - - @CalledByNative - private void requestInstallArModule(Tab tab) { - mTab = tab; - ModuleInstallUi ui = new ModuleInstallUi(mTab, R.string.ar_module_title, this); - ui.showInstallStartUi(); - ModuleInstaller.getInstance().install("ar", success -> { - assert shouldRequestInstallArModule() != success; - - if (success) { - // As per documentation, it's recommended to issue a call to - // ArCoreApk.checkAvailability() early in application lifecycle & ignore the result - // so that subsequent calls can return cached result: - // https://developers.google.com/ar/develop/java/enable-arcore - // This is as early in the app lifecycle as it gets for us - just after installing - // AR module. - getArCoreInstallStatus(); - } - - if (mNativeArCoreJavaUtils != 0) { - if (success) { - ui.showInstallSuccessUi(); - nativeOnRequestInstallArModuleResult(mNativeArCoreJavaUtils, success); - } else { - ui.showInstallFailureUi(); - // early exit - user will be offered a choice to retry & install flow will - // continue from onRetry / onCancel - return; - } - } - }); - } - - @CalledByNative - private void requestInstallSupportedArCore(final Tab tab) { - assert shouldRequestInstallSupportedArCore(); - - @ArCoreShim.Availability - int arCoreAvailability = getArCoreInstallStatus(); - final Activity activity = tab.getActivity(); - String infobarText = null; - String buttonText = null; - switch (arCoreAvailability) { - case ArCoreShim.Availability.UNSUPPORTED_DEVICE_NOT_CAPABLE: - maybeNotifyNativeOnRequestInstallSupportedArCoreResult(false); - break; - case ArCoreShim.Availability.UNKNOWN_CHECKING: - case ArCoreShim.Availability.UNKNOWN_ERROR: - case ArCoreShim.Availability.UNKNOWN_TIMED_OUT: - case ArCoreShim.Availability.SUPPORTED_NOT_INSTALLED: - infobarText = activity.getString(R.string.ar_core_check_infobar_install_text); - buttonText = activity.getString(R.string.app_banner_install); - break; - case ArCoreShim.Availability.SUPPORTED_APK_TOO_OLD: - infobarText = activity.getString(R.string.ar_core_check_infobar_update_text); - buttonText = activity.getString(R.string.update_from_market); - break; - case ArCoreShim.Availability.SUPPORTED_INSTALLED: - assert false; - break; - } - - SimpleConfirmInfoBarBuilder.Listener listener = new SimpleConfirmInfoBarBuilder.Listener() { - @Override - public void onInfoBarDismissed() { - maybeNotifyNativeOnRequestInstallSupportedArCoreResult( - !shouldRequestInstallSupportedArCore()); - } - - @Override - public boolean onInfoBarButtonClicked(boolean isPrimary) { - try { - assert sRequestInstallInstance == null; - @ArCoreShim.InstallStatus - int installStatus = getArCoreShimInstance().requestInstall(activity, true); - - if (installStatus == ArCoreShim.InstallStatus.INSTALL_REQUESTED) { - // Install flow will resume in onArCoreRequestInstallReturned, mark that - // there is active request. Native code notification will be deferred until - // our activity gets resumed. - sRequestInstallInstance = ArCoreJavaUtils.this; - } else if (installStatus == ArCoreShim.InstallStatus.INSTALLED) { - // No need to install - notify native code. - maybeNotifyNativeOnRequestInstallSupportedArCoreResult(true); - } - - } catch (ArCoreShim.UnavailableDeviceNotCompatibleException e) { - sRequestInstallInstance = null; - Log.w(TAG, "ARCore installation request failed with exception: %s", - e.toString()); - - maybeNotifyNativeOnRequestInstallSupportedArCoreResult(false); - } catch (ArCoreShim.UnavailableUserDeclinedInstallationException e) { - maybeNotifyNativeOnRequestInstallSupportedArCoreResult(false); - } - - return false; - } - - @Override - public boolean onInfoBarLinkClicked() { - return false; - } - }; - // TODO(ijamardo, https://crbug.com/838833): Add icon for AR info bar. - SimpleConfirmInfoBarBuilder.create(tab, listener, InfoBarIdentifier.AR_CORE_UPGRADE_ANDROID, - R.drawable.ic_error_outline_googblue_24dp, infobarText, buttonText, null, null, - true); - } - - @CalledByNative - private boolean canRequestInstallArModule() { - // We can only try to install the AR module if we are in a bundle mode. - return BundleUtils.isBundle(); - } - - @CalledByNative - private boolean shouldRequestInstallArModule() { - try { - // Try to find class in AR module that has not been obfuscated. - Class.forName("com.google.ar.core.ArCoreApk"); - return false; - } catch (ClassNotFoundException e) { - return true; - } - } - - private void onArCoreRequestInstallReturned(Activity activity) { - try { - // Since |userRequestedInstall| parameter is false, the below call should - // throw if ARCore is still not installed - no need to check the result. - getArCoreShimInstance().requestInstall(activity, false); - maybeNotifyNativeOnRequestInstallSupportedArCoreResult(true); - } catch (ArCoreShim.UnavailableDeviceNotCompatibleException e) { - Log.w(TAG, "Exception thrown when trying to validate install state of ARCore: %s", - e.toString()); - maybeNotifyNativeOnRequestInstallSupportedArCoreResult(false); - } catch (ArCoreShim.UnavailableUserDeclinedInstallationException e) { - maybeNotifyNativeOnRequestInstallSupportedArCoreResult(false); - } - } - - /** - * This method should be called by the Activity that gets resumed. - * We are only interested in the cases where our current Activity got paused - * as a result of a call to ArCoreApk.requestInstall() method. - */ - public static void onResumeActivityWithNative(Activity activity) { - if (sRequestInstallInstance != null) { - sRequestInstallInstance.onArCoreRequestInstallReturned(activity); - sRequestInstallInstance = null; - } - } - - /** - * Helper used to notify native code about the result of the request to install ARCore. - */ - private void maybeNotifyNativeOnRequestInstallSupportedArCoreResult(boolean success) { - if (mNativeArCoreJavaUtils != 0) { - nativeOnRequestInstallSupportedArCoreResult(mNativeArCoreJavaUtils, success); - } - } - - private static native void nativeInstallArCoreDeviceProviderFactory(); - private native void nativeOnRequestInstallArModuleResult( - long nativeArCoreJavaUtils, boolean success); - private native void nativeOnRequestInstallSupportedArCoreResult( - long nativeArCoreJavaUtils, boolean success); - private native void nativeOnDrawingSurfaceReady( long nativeArCoreJavaUtils, Surface surface, int rotation, int width, int height); private native void nativeOnDrawingSurfaceTouch(
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/vr/ArDelegateImpl.java b/chrome/android/java/src/org/chromium/chrome/browser/vr/ArDelegateImpl.java index 9fc202e..500cb1c5 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/vr/ArDelegateImpl.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/vr/ArDelegateImpl.java
@@ -19,11 +19,11 @@ @Override public void init() { - ArCoreJavaUtils.installArCoreDeviceProviderFactory(); + ArCoreInstallUtils.installArCoreDeviceProviderFactory(); } @Override public void registerOnResumeActivity(Activity activity) { - ArCoreJavaUtils.onResumeActivityWithNative(activity); + ArCoreInstallUtils.onResumeActivityWithNative(activity); } }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/widget/bottomsheet/BottomSheet.java b/chrome/android/java/src/org/chromium/chrome/browser/widget/bottomsheet/BottomSheet.java index 54c5a5c..562d8ae 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/widget/bottomsheet/BottomSheet.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/widget/bottomsheet/BottomSheet.java
@@ -25,6 +25,7 @@ import org.chromium.base.ApiCompatibilityUtils; import org.chromium.base.ObserverList; +import org.chromium.base.Supplier; import org.chromium.base.SysUtils; import org.chromium.base.VisibleForTesting; import org.chromium.chrome.R; @@ -36,8 +37,6 @@ import org.chromium.chrome.browser.native_page.NativePageHost; import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.browser.tab.TabBrowserControlsState; -import org.chromium.chrome.browser.tabmodel.TabLaunchType; -import org.chromium.chrome.browser.tabmodel.TabModelSelector; import org.chromium.chrome.browser.toolbar.top.ActionModeController.ActionBarDelegate; import org.chromium.chrome.browser.toolbar.top.ViewShiftingActionBarDelegate; import org.chromium.chrome.browser.util.AccessibilityUtil; @@ -131,15 +130,6 @@ /** The height ratio for the sheet in the SheetState.HALF state. */ private static final float HALF_HEIGHT_RATIO = 0.75f; - /** The fraction of the width of the screen that, when swiped, will cause the sheet to move. */ - private static final float SWIPE_ALLOWED_FRACTION = 0.2f; - - /** - * The minimum swipe velocity (dp/ms) that should be considered as a user opening the bottom - * sheet intentionally. This is specifically for the 'velocity' swipe logic. - */ - private static final float SHEET_SWIPE_MIN_DP_PER_MS = 0.2f; - /** The desired height of a content that has just been shown or whose height was invalidated. */ private static final float HEIGHT_UNSPECIFIED = -1.0f; @@ -201,7 +191,7 @@ private int mTargetState = SheetState.NONE; /** Used for getting the current tab. */ - protected TabModelSelector mTabModelSelector; + protected Supplier<Tab> mTabSupplier; /** The fullscreen manager for information about toolbar offsets. */ private ChromeFullscreenManager mFullscreenManager; @@ -559,7 +549,7 @@ * @param activity The activity displaying the bottom sheet. */ public void init(View root, ChromeActivity activity) { - mTabModelSelector = activity.getTabModelSelector(); + mTabSupplier = activity.getActivityTabProvider(); mFullscreenManager = activity.getFullscreenManager(); int colorId = R.color.sheet_bg_color; @@ -723,17 +713,9 @@ public int loadUrl(LoadUrlParams params, boolean incognito) { for (BottomSheetObserver o : mObservers) o.onLoadUrl(params.getUrl()); - assert mTabModelSelector != null; - int tabLoadStatus = TabLoadStatus.DEFAULT_PAGE_LOAD; - if (getActiveTab() != null && getActiveTab().isIncognito() == incognito) { - tabLoadStatus = getActiveTab().loadUrl(params); - } else { - // If no compatible tab is active behind the sheet, open a new one. - mTabModelSelector.openNewTab( - params, TabLaunchType.FROM_CHROME_UI, getActiveTab(), incognito); - } + if (getActiveTab() != null) tabLoadStatus = getActiveTab().loadUrl(params); return tabLoadStatus; } @@ -751,7 +733,7 @@ @Override public Tab getActiveTab() { - return mTabModelSelector != null ? mTabModelSelector.getCurrentTab() : null; + return mTabSupplier != null ? mTabSupplier.get() : null; } @Override
diff --git a/chrome/android/java_sources.gni b/chrome/android/java_sources.gni index d65826c..ba37432 100644 --- a/chrome/android/java_sources.gni +++ b/chrome/android/java_sources.gni
@@ -47,6 +47,7 @@ if (enable_arcore) { chrome_java_sources += [ + "java/src/org/chromium/chrome/browser/vr/ArCoreInstallUtils.java", "java/src/org/chromium/chrome/browser/vr/ArCoreJavaUtils.java", "java/src/org/chromium/chrome/browser/vr/ArDelegateImpl.java", "java/src/org/chromium/chrome/browser/vr/ArCoreShim.java",
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageArchivePublisherBridgeTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageArchivePublisherBridgeTest.java new file mode 100644 index 0000000..889bba9 --- /dev/null +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageArchivePublisherBridgeTest.java
@@ -0,0 +1,171 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +package org.chromium.chrome.browser.offlinepages; + +import android.support.test.InstrumentationRegistry; +import android.support.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.runner.RunWith; + +import org.chromium.base.ContentUriUtils; +import org.chromium.base.task.PostTask; +import org.chromium.base.test.util.CommandLineFlags; +import org.chromium.base.test.util.DisableIf; +import org.chromium.base.test.util.MinAndroidSdkLevel; +import org.chromium.chrome.browser.ChromeActivity; +import org.chromium.chrome.browser.ChromeSwitches; +import org.chromium.chrome.browser.offlinepages.OfflinePageBridge.OfflinePageModelObserver; +import org.chromium.chrome.browser.offlinepages.OfflinePageBridge.SavePageCallback; +import org.chromium.chrome.browser.profiles.Profile; +import org.chromium.chrome.test.ChromeActivityTestRule; +import org.chromium.chrome.test.ChromeJUnit4ClassRunner; +import org.chromium.content_public.browser.UiThreadTaskTraits; +import org.chromium.content_public.browser.test.util.TestThreadUtils; +import org.chromium.net.NetworkChangeNotifier; +import org.chromium.net.test.EmbeddedTestServer; + +import java.util.concurrent.Semaphore; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.TimeoutException; + +/** Unit tests for {@link OfflinePageArchivePublisherBridge}. */ +@RunWith(ChromeJUnit4ClassRunner.class) +@CommandLineFlags.Add({ChromeSwitches.DISABLE_FIRST_RUN_EXPERIENCE}) +public class OfflinePageArchivePublisherBridgeTest { + @Rule + public ChromeActivityTestRule<ChromeActivity> mActivityTestRule = + new ChromeActivityTestRule<>(ChromeActivity.class); + + private static final String TEST_PAGE = "/chrome/test/data/android/about.html"; + private static final int TIMEOUT_MS = 5000; + private static final ClientId TEST_CLIENT_ID = + new ClientId(OfflinePageBridge.DOWNLOAD_NAMESPACE, "1234"); + + private OfflinePageBridge mOfflinePageBridge; + private EmbeddedTestServer mTestServer; + private String mTestPage; + + private void initializeBridgeForProfile(final boolean incognitoProfile) + throws InterruptedException { + final Semaphore semaphore = new Semaphore(0); + PostTask.runOrPostTask(UiThreadTaskTraits.DEFAULT, () -> { + Profile profile = Profile.getLastUsedProfile(); + if (incognitoProfile) { + profile = profile.getOffTheRecordProfile(); + } + // Ensure we start in an offline state. + mOfflinePageBridge = OfflinePageBridge.getForProfile(profile); + if (mOfflinePageBridge == null || mOfflinePageBridge.isOfflinePageModelLoaded()) { + semaphore.release(); + return; + } + mOfflinePageBridge.addObserver(new OfflinePageModelObserver() { + @Override + public void offlinePageModelLoaded() { + semaphore.release(); + mOfflinePageBridge.removeObserver(this); + } + }); + }); + Assert.assertTrue(semaphore.tryAcquire(TIMEOUT_MS, TimeUnit.MILLISECONDS)); + if (!incognitoProfile) Assert.assertNotNull(mOfflinePageBridge); + } + + @Before + public void setUp() throws Exception { + mActivityTestRule.startMainActivityOnBlankPage(); + + TestThreadUtils.runOnUiThreadBlocking(() -> { + // Ensure we start in an offline state. + NetworkChangeNotifier.forceConnectivityState(false); + if (!NetworkChangeNotifier.isInitialized()) { + NetworkChangeNotifier.init(); + } + }); + + initializeBridgeForProfile(false); + + mTestServer = EmbeddedTestServer.createAndStartServer(InstrumentationRegistry.getContext()); + mTestPage = mTestServer.getURL(TEST_PAGE); + } + + @After + public void tearDown() throws Exception { + mTestServer.stopAndDestroyServer(); + } + + // TODO(iwells): Change "29" to "Build.VERSION_CODES.Q" when it's available. + @Test + @SmallTest + @DisableIf.Build(sdk_is_greater_than = 28) + public void testAddCompletedDownload() throws InterruptedException, TimeoutException { + Assert.assertTrue(OfflinePageArchivePublisherBridge.isAndroidDownloadManagerInstalled()); + + mActivityTestRule.loadUrl(mTestPage); + savePage(TEST_CLIENT_ID); + OfflinePageItem page = OfflineTestUtil.getAllPages().get(0); + + long downloadId = OfflinePageArchivePublisherBridge.addCompletedDownload(page.getTitle(), + "description", page.getFilePath(), page.getFileSize(), page.getUrl(), ""); + + Assert.assertNotEquals(0L, downloadId); + } + + @Test + @SmallTest + @DisableIf.Build(sdk_is_greater_than = 28) + public void testRemove() throws InterruptedException, TimeoutException { + Assert.assertTrue(OfflinePageArchivePublisherBridge.isAndroidDownloadManagerInstalled()); + + mActivityTestRule.loadUrl(mTestPage); + savePage(TEST_CLIENT_ID); + OfflinePageItem page = OfflineTestUtil.getAllPages().get(0); + + long downloadId = OfflinePageArchivePublisherBridge.addCompletedDownload(page.getTitle(), + "description", page.getFilePath(), page.getFileSize(), page.getUrl(), ""); + + Assert.assertNotEquals(0L, downloadId); + + long[] ids = new long[] {downloadId}; + Assert.assertEquals(1, OfflinePageArchivePublisherBridge.remove(ids)); + } + + @Test + @SmallTest + @MinAndroidSdkLevel(29) + public void testPublishArchiveToDownloadsCollection() + throws InterruptedException, TimeoutException { + // Save a page and publish. + mActivityTestRule.loadUrl(mTestPage); + savePage(TEST_CLIENT_ID); + OfflinePageItem page = OfflineTestUtil.getAllPages().get(0); + + String publishedUri = + OfflinePageArchivePublisherBridge.publishArchiveToDownloadsCollection(page); + Assert.assertFalse(publishedUri.isEmpty()); + Assert.assertTrue(ContentUriUtils.isContentUri(publishedUri)); + Assert.assertTrue(ContentUriUtils.contentUriExists(publishedUri)); + } + + // Returns offline ID. + private void savePage(final ClientId clientId) throws InterruptedException { + final Semaphore semaphore = new Semaphore(0); + TestThreadUtils.runOnUiThreadBlocking(() -> { + mOfflinePageBridge.savePage( + mActivityTestRule.getWebContents(), clientId, new SavePageCallback() { + @Override + public void onSavePageDone(int savePageResult, String url, long offlineId) { + semaphore.release(); + } + }); + }); + Assert.assertTrue(semaphore.tryAcquire(TIMEOUT_MS, TimeUnit.MILLISECONDS)); + } +}
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageRequestTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageRequestTest.java index 77c0d4b..06e8086 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageRequestTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageRequestTest.java
@@ -69,7 +69,7 @@ Tab tab = mActivityTestRule.getActivity().getActivityTab(); // Load and save an offline page. - savePage(testUrl); + savePage(testUrl, CLIENT_ID); Assert.assertFalse(isErrorPage(tab)); Assert.assertFalse(isOfflinePage(tab)); @@ -101,7 +101,7 @@ Tab tab = mActivityTestRule.getActivity().getActivityTab(); // Load and save an offline page for the url with a fragment. - savePage(testUrlWithFragment); + savePage(testUrlWithFragment, CLIENT_ID); Assert.assertFalse(isErrorPage(tab)); Assert.assertFalse(isOfflinePage(tab)); @@ -116,13 +116,47 @@ Assert.assertTrue(isOfflinePage(tab)); } - private void savePage(String url) throws InterruptedException { + @Test + @SmallTest + @DisabledTest(message = "crbug.com/786233") + public void testLoadOfflinePageFromDownloadsOnDisconnectedNetwork() throws Exception { + // Specifically tests saving to and loading from Downloads. + EmbeddedTestServer testServer = + EmbeddedTestServer.createAndStartServer(InstrumentationRegistry.getContext()); + String testUrl = testServer.getURL(TEST_PAGE); + String aboutUrl = testServer.getURL(ABOUT_PAGE); + + Tab tab = mActivityTestRule.getActivity().getActivityTab(); + + // Load and save a persistent offline page using a persistent namespace so that the archive + // will be published. + savePage(testUrl, new ClientId(OfflinePageBridge.DOWNLOAD_NAMESPACE, "1234")); + Assert.assertFalse(isErrorPage(tab)); + Assert.assertFalse(isOfflinePage(tab)); + + // Load another page. + mActivityTestRule.loadUrl(aboutUrl); + Assert.assertFalse(isErrorPage(tab)); + Assert.assertFalse(isOfflinePage(tab)); + + // Stop the server and also disconnect the network. + testServer.stopAndDestroyServer(); + TestThreadUtils.runOnUiThreadBlocking( + () -> { NetworkChangeNotifier.forceConnectivityState(false); }); + + // Load the page that has an offline copy. The offline page should be shown. + mActivityTestRule.loadUrl(testUrl); + Assert.assertFalse(isErrorPage(tab)); + Assert.assertTrue(isOfflinePage(tab)); + } + + private void savePage(String url, ClientId clientId) throws InterruptedException { mActivityTestRule.loadUrl(url); final Semaphore semaphore = new Semaphore(0); TestThreadUtils.runOnUiThreadBlocking(() -> { mOfflinePageBridge.savePage( - mActivityTestRule.getWebContents(), CLIENT_ID, new SavePageCallback() { + mActivityTestRule.getWebContents(), clientId, new SavePageCallback() { @Override public void onSavePageDone(int savePageResult, String url, long offlineId) { Assert.assertEquals(
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/vr/VrBrowserCompositorViewHolderTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/vr/VrBrowserCompositorViewHolderTest.java index 39ced52..bd668be2f 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/vr/VrBrowserCompositorViewHolderTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/vr/VrBrowserCompositorViewHolderTest.java
@@ -6,6 +6,7 @@ import static org.chromium.chrome.test.util.ChromeRestriction.RESTRICTION_TYPE_SVR; +import android.os.Build; import android.support.test.filters.MediumTest; import android.view.ViewGroup; @@ -15,6 +16,7 @@ import org.junit.runner.RunWith; import org.chromium.base.test.util.CommandLineFlags; +import org.chromium.base.test.util.DisableIf; import org.chromium.base.test.util.Restriction; import org.chromium.chrome.R; import org.chromium.chrome.browser.ChromeSwitches; @@ -48,6 +50,8 @@ */ @Test @MediumTest + @DisableIf. + Build(sdk_is_less_than = Build.VERSION_CODES.LOLLIPOP, message = "https://crbug.com/984943") public void testResizeWithCompositorViewHolderDetached() throws InterruptedException, TimeoutException { final AtomicInteger oldWidth = new AtomicInteger();
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/vr/VrBrowserTransitionTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/vr/VrBrowserTransitionTest.java index 7f23715..1d339672 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/vr/VrBrowserTransitionTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/vr/VrBrowserTransitionTest.java
@@ -16,6 +16,7 @@ import android.content.Context; import android.content.Intent; import android.graphics.PointF; +import android.os.Build; import android.support.test.InstrumentationRegistry; import android.support.test.filters.LargeTest; import android.support.test.filters.MediumTest; @@ -29,6 +30,7 @@ import org.chromium.base.StrictModeContext; import org.chromium.base.test.util.CommandLineFlags; +import org.chromium.base.test.util.DisableIf; import org.chromium.base.test.util.Restriction; import org.chromium.chrome.R; import org.chromium.chrome.browser.ChromeSwitches; @@ -127,6 +129,8 @@ @Test @Restriction(RESTRICTION_TYPE_DEVICE_NON_DAYDREAM) @MediumTest + @DisableIf. + Build(sdk_is_less_than = Build.VERSION_CODES.LOLLIPOP, message = "https://crbug.com/984943") public void test2dtoVrShellNfcUnsupported() { enterVrShellNfc(false /* supported */); } @@ -194,6 +198,8 @@ @Test @Restriction(RESTRICTION_TYPE_DEVICE_NON_DAYDREAM) @MediumTest + @DisableIf. + Build(sdk_is_less_than = Build.VERSION_CODES.LOLLIPOP, message = "https://crbug.com/984943") public void test2dtoVrShellto2dUnsupported() { enterExitVrShell(false /* supported */); }
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/vr/WebXrVrDeviceTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/vr/WebXrVrDeviceTest.java index c9e98676..f0ffce827 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/vr/WebXrVrDeviceTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/vr/WebXrVrDeviceTest.java
@@ -25,6 +25,7 @@ import org.chromium.base.test.params.ParameterSet; import org.chromium.base.test.params.ParameterizedRunner; import org.chromium.base.test.util.CommandLineFlags; +import org.chromium.base.test.util.DisableIf; import org.chromium.base.test.util.MinAndroidSdkLevel; import org.chromium.base.test.util.Restriction; import org.chromium.chrome.browser.ChromeSwitches; @@ -95,6 +96,8 @@ @MediumTest @XrActivityRestriction({XrActivityRestriction.SupportedActivity.ALL}) @Restriction(RESTRICTION_TYPE_SVR) + @DisableIf. + Build(sdk_is_less_than = Build.VERSION_CODES.LOLLIPOP, message = "https://crbug.com/984943") // Sensorless still works on older devices since it doesn't rely on anything in the DFM. public void testGvrlessMagicWindowCapabilities() throws InterruptedException { // Make Chrome think that VrCore is not installed
diff --git a/chrome/app/generated_resources.grd b/chrome/app/generated_resources.grd index 6826d3f..0c7cbe9 100644 --- a/chrome/app/generated_resources.grd +++ b/chrome/app/generated_resources.grd
@@ -4985,9 +4985,6 @@ <message name="IDS_NTP_CONFIRM_MSG_RESTORE_DEFAULTS" desc="The text label of the restore default shortcuts button when editing a custom link. (On the New Tab Page)"> Restore default shortcuts </message> - <message name="IDS_NTP_CUSTOM_BG_CUSTOMIZE_BACKGROUND" desc="The title and aria-label for the tooltip for background customization. (On the New Tab Page)"> - Customize this page - </message> <message name="IDS_NTP_CUSTOM_BG_CHROME_WALLPAPERS" desc="The text label of the Chrome backgrounds option for background customization.(On the New Tab Page)"> Chrome backgrounds </message>
diff --git a/chrome/app/generated_resources_grd/IDS_NTP_CUSTOM_BG_CUSTOMIZE_BACKGROUND.png.sha1 b/chrome/app/generated_resources_grd/IDS_NTP_CUSTOM_BG_CUSTOMIZE_BACKGROUND.png.sha1 deleted file mode 100644 index 215f8ad7..0000000 --- a/chrome/app/generated_resources_grd/IDS_NTP_CUSTOM_BG_CUSTOMIZE_BACKGROUND.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -32af17f468186a40fb77e59126316f966d369ef1 \ No newline at end of file
diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn index 0e6093e6..f90d9881 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn
@@ -1533,6 +1533,8 @@ "sharing/sharing_fcm_sender.cc", "sharing/sharing_fcm_sender.h", "sharing/sharing_message_handler.h", + "sharing/sharing_metrics.cc", + "sharing/sharing_metrics.h", "sharing/sharing_service.cc", "sharing/sharing_service.h", "sharing/sharing_service_factory.cc", @@ -4931,6 +4933,10 @@ "supervised_user/experimental/supervised_user_blacklist.h", "supervised_user/experimental/supervised_user_filtering_switches.cc", "supervised_user/experimental/supervised_user_filtering_switches.h", + "supervised_user/kids_chrome_management/kids_chrome_management_client.cc", + "supervised_user/kids_chrome_management/kids_chrome_management_client.h", + "supervised_user/kids_chrome_management/kids_chrome_management_client_factory.cc", + "supervised_user/kids_chrome_management/kids_chrome_management_client_factory.h", "supervised_user/kids_management_url_checker_client.cc", "supervised_user/kids_management_url_checker_client.h", "supervised_user/permission_request_creator.h",
diff --git a/chrome/browser/about_flags.cc b/chrome/browser/about_flags.cc index f16b24e..2473cb3f 100644 --- a/chrome/browser/about_flags.cc +++ b/chrome/browser/about_flags.cc
@@ -3361,11 +3361,6 @@ flag_descriptions::kLookalikeUrlNavigationSuggestionsDescription, kOsAll, FEATURE_VALUE_TYPE(features::kLookalikeUrlNavigationSuggestionsUI)}, - {"sync-USS-autofill-wallet-metadata", - flag_descriptions::kSyncUSSAutofillWalletMetadataName, - flag_descriptions::kSyncUSSAutofillWalletMetadataDescription, kOsAll, - FEATURE_VALUE_TYPE(switches::kSyncUSSAutofillWalletMetadata)}, - {"enable-resampling-input-events", flag_descriptions::kEnableResamplingInputEventsName, flag_descriptions::kEnableResamplingInputEventsDescription, kOsAll,
diff --git a/chrome/browser/android/profiles/profile_downloader_android.cc b/chrome/browser/android/profiles/profile_downloader_android.cc index 45b4d2c..83cfcf7a 100644 --- a/chrome/browser/android/profiles/profile_downloader_android.cc +++ b/chrome/browser/android/profiles/profile_downloader_android.cc
@@ -18,6 +18,7 @@ #include "chrome/browser/profiles/profile_manager.h" #include "chrome/browser/signin/identity_manager_factory.h" #include "components/signin/public/identity_manager/identity_manager.h" +#include "content/public/browser/storage_partition.h" #include "google_apis/gaia/gaia_auth_util.h" #include "third_party/skia/include/core/SkBitmap.h" #include "ui/gfx/android/java_bitmap.h" @@ -62,8 +63,14 @@ return desired_image_side_pixels_; } - Profile* GetBrowserProfile() override { - return profile_; + identity::IdentityManager* GetIdentityManager() override { + return IdentityManagerFactory::GetForProfile(profile_); + } + + network::mojom::URLLoaderFactory* GetURLLoaderFactory() override { + return content::BrowserContext::GetDefaultStoragePartition(profile_) + ->GetURLLoaderFactoryForBrowserProcess() + .get(); } std::string GetCachedPictureURL() const override {
diff --git a/chrome/browser/android/vr/BUILD.gn b/chrome/browser/android/vr/BUILD.gn index e17977b..d6c5c83 100644 --- a/chrome/browser/android/vr/BUILD.gn +++ b/chrome/browser/android/vr/BUILD.gn
@@ -83,9 +83,9 @@ "arcore_device/arcore_gl_thread.h", "arcore_device/arcore_impl.cc", "arcore_device/arcore_impl.h", - "arcore_device/arcore_install_utils.h", "arcore_device/arcore_java_utils.cc", "arcore_device/arcore_java_utils.h", + "arcore_device/arcore_session_utils.h", "arcore_device/arcore_shim.cc", "arcore_device/arcore_shim.h", "arcore_device/type_converters.cc", @@ -222,6 +222,7 @@ if (enable_arcore) { generate_jni("ar_jni_headers") { sources = [ + "//chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreInstallUtils.java", "//chrome/android/java/src/org/chromium/chrome/browser/vr/ArCoreJavaUtils.java", ] }
diff --git a/chrome/browser/android/vr/arcore_device/arcore_consent_prompt.cc b/chrome/browser/android/vr/arcore_device/arcore_consent_prompt.cc index b1fe89a5..1e75f79a 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_consent_prompt.cc +++ b/chrome/browser/android/vr/arcore_device/arcore_consent_prompt.cc
@@ -4,13 +4,17 @@ #include "chrome/browser/android/vr/arcore_device/arcore_consent_prompt.h" +#include <memory> #include <utility> #include "base/bind.h" #include "chrome/android/features/vr/jni_headers/ArConsentDialog_jni.h" #include "chrome/browser/android/tab_android.h" +#include "chrome/browser/android/vr/ar_jni_headers/ArCoreInstallUtils_jni.h" +#include "chrome/browser/android/vr/arcore_device/arcore_device_provider.h" #include "content/public/browser/render_frame_host.h" #include "content/public/browser/web_contents.h" +#include "device/vr/android/arcore/arcore_device_provider_factory.h" using base::android::AttachCurrentThread; using base::android::ScopedJavaLocalRef; @@ -19,7 +23,21 @@ namespace { -ArcoreConsentPrompt* g_instance = nullptr; +class ArCoreDeviceProviderFactoryImpl + : public device::ArCoreDeviceProviderFactory { + public: + ArCoreDeviceProviderFactoryImpl() = default; + ~ArCoreDeviceProviderFactoryImpl() override = default; + std::unique_ptr<device::VRDeviceProvider> CreateDeviceProvider() override; + + private: + DISALLOW_COPY_AND_ASSIGN(ArCoreDeviceProviderFactoryImpl); +}; + +std::unique_ptr<device::VRDeviceProvider> +ArCoreDeviceProviderFactoryImpl::CreateDeviceProvider() { + return std::make_unique<device::ArCoreDeviceProvider>(); +} base::android::ScopedJavaLocalRef<jobject> GetTabFromRenderer( int render_process_id, @@ -44,42 +62,171 @@ } // namespace -ArcoreConsentPrompt::ArcoreConsentPrompt() = default; +ArCoreConsentPrompt::ArCoreConsentPrompt() : weak_ptr_factory_(this) {} -ArcoreConsentPrompt::~ArcoreConsentPrompt() = default; +ArCoreConsentPrompt::~ArCoreConsentPrompt() = default; -void ArcoreConsentPrompt::GetUserPermission( +void ArCoreConsentPrompt::OnUserConsentResult( + JNIEnv* env, + const base::android::JavaParamRef<jobject>& j_caller, + jboolean is_granted) { + jdelegate_.Reset(); + + if (!on_user_consent_callback_) + return; + + if (!is_granted) { + CallDeferredUserConsentCallback(false); + return; + } + + java_install_utils_ = + Java_ArCoreInstallUtils_create(env, reinterpret_cast<jlong>(this)); + + if (java_install_utils_.is_null()) { + CallDeferredUserConsentCallback(false); + return; + } + + RequestArModule(); +} + +// static +void ArCoreConsentPrompt::ShowConsentPrompt( int render_process_id, int render_frame_id, base::OnceCallback<void(bool)> response_callback) { on_user_consent_callback_ = std::move(response_callback); + render_process_id_ = render_process_id; + render_frame_id_ = render_frame_id; JNIEnv* env = AttachCurrentThread(); - ScopedJavaLocalRef<jobject> jdelegate = Java_ArConsentDialog_showDialog( + jdelegate_ = Java_ArConsentDialog_showDialog( env, reinterpret_cast<jlong>(this), - GetTabFromRenderer(render_process_id, render_frame_id)); - if (jdelegate.is_null()) { + GetTabFromRenderer(render_process_id_, render_frame_id_)); + if (jdelegate_.is_null()) { std::move(on_user_consent_callback_).Run(false); } } -void ArcoreConsentPrompt::OnUserConsentResult( - JNIEnv* env, - const base::android::JavaParamRef<jobject>& j_caller, - jboolean is_granted) { - DCHECK(on_user_consent_callback_); - std::move(on_user_consent_callback_).Run(is_granted); +bool ArCoreConsentPrompt::CanRequestInstallArModule() { + return Java_ArCoreInstallUtils_canRequestInstallArModule( + AttachCurrentThread(), java_install_utils_); } -// static -void ArcoreConsentPrompt::ShowConsentPrompt( - int render_process_id, - int render_frame_id, - base::OnceCallback<void(bool)> response_callback) { - if (!g_instance) - g_instance = new ArcoreConsentPrompt(); - g_instance->GetUserPermission(render_process_id, render_frame_id, - std::move(response_callback)); +bool ArCoreConsentPrompt::ShouldRequestInstallArModule() { + return Java_ArCoreInstallUtils_shouldRequestInstallArModule( + AttachCurrentThread(), java_install_utils_); +} + +void ArCoreConsentPrompt::RequestInstallArModule() { + Java_ArCoreInstallUtils_requestInstallArModule( + AttachCurrentThread(), java_install_utils_, + GetTabFromRenderer(render_process_id_, render_frame_id_)); +} + +bool ArCoreConsentPrompt::ShouldRequestInstallSupportedArCore() { + JNIEnv* env = AttachCurrentThread(); + return Java_ArCoreInstallUtils_shouldRequestInstallSupportedArCore( + env, java_install_utils_); +} + +void ArCoreConsentPrompt::RequestInstallSupportedArCore() { + DCHECK(ShouldRequestInstallSupportedArCore()); + + JNIEnv* env = AttachCurrentThread(); + Java_ArCoreInstallUtils_requestInstallSupportedArCore( + env, java_install_utils_, + GetTabFromRenderer(render_process_id_, render_frame_id_)); +} + +void ArCoreConsentPrompt::OnRequestInstallArModuleResult( + JNIEnv* env, + const base::android::JavaParamRef<jobject>& obj, + bool success) { + DVLOG(1) << __func__; + DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); + + if (on_request_ar_module_result_callback_) { + std::move(on_request_ar_module_result_callback_).Run(success); + } +} + +void ArCoreConsentPrompt::OnRequestInstallSupportedArCoreResult( + JNIEnv* env, + const base::android::JavaParamRef<jobject>& obj, + bool success) { + DVLOG(1) << __func__; + DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); + DCHECK(on_request_arcore_install_or_update_result_callback_); + + std::move(on_request_arcore_install_or_update_result_callback_).Run(success); +} + +void ArCoreConsentPrompt::RequestArModule() { + DVLOG(1) << __func__; + if (ShouldRequestInstallArModule()) { + if (!CanRequestInstallArModule()) { + OnRequestArModuleResult(false); + return; + } + + on_request_ar_module_result_callback_ = base::BindOnce( + &ArCoreConsentPrompt::OnRequestArModuleResult, GetWeakPtr()); + RequestInstallArModule(); + return; + } + + OnRequestArModuleResult(true); +} + +void ArCoreConsentPrompt::OnRequestArModuleResult(bool success) { + DVLOG(3) << __func__ << ": success=" << success; + + if (!success) { + CallDeferredUserConsentCallback(false); + return; + } + + RequestArCoreInstallOrUpdate(); +} + +void ArCoreConsentPrompt::RequestArCoreInstallOrUpdate() { + DVLOG(1) << __func__; + DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); + DCHECK(!on_request_arcore_install_or_update_result_callback_); + + if (ShouldRequestInstallSupportedArCore()) { + // ARCore is not installed or requires an update. Store the callback to be + // processed later once installation/update is complete or got cancelled. + on_request_arcore_install_or_update_result_callback_ = base::BindOnce( + &ArCoreConsentPrompt::OnRequestArCoreInstallOrUpdateResult, + GetWeakPtr()); + + RequestInstallSupportedArCore(); + return; + } + + OnRequestArCoreInstallOrUpdateResult(true); +} + +void ArCoreConsentPrompt::OnRequestArCoreInstallOrUpdateResult(bool success) { + DVLOG(1) << __func__; + DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); + + CallDeferredUserConsentCallback(success); +} + +void ArCoreConsentPrompt::CallDeferredUserConsentCallback( + bool is_permission_granted) { + if (on_user_consent_callback_) + std::move(on_user_consent_callback_).Run(is_permission_granted); +} + +static void JNI_ArCoreInstallUtils_InstallArCoreDeviceProviderFactory( + JNIEnv* env) { + device::ArCoreDeviceProviderFactory::Install( + std::make_unique<ArCoreDeviceProviderFactoryImpl>()); } } // namespace vr
diff --git a/chrome/browser/android/vr/arcore_device/arcore_consent_prompt.h b/chrome/browser/android/vr/arcore_device/arcore_consent_prompt.h index 257d5abc..45a27a50 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_consent_prompt.h +++ b/chrome/browser/android/vr/arcore_device/arcore_consent_prompt.h
@@ -7,33 +7,74 @@ #include "base/android/jni_android.h" #include "base/android/jni_weak_ref.h" +#include "base/android/scoped_java_ref.h" #include "base/callback.h" +#include "base/memory/weak_ptr.h" +#include "base/threading/thread_checker.h" #include "chrome/browser/vr/service/arcore_consent_prompt_interface.h" #include "chrome/browser/vr/vr_export.h" namespace vr { -class VR_EXPORT ArcoreConsentPrompt : public ArcoreConsentPromptInterface { +class VR_EXPORT ArCoreConsentPrompt : public ArCoreConsentPromptInterface { public: + ArCoreConsentPrompt(); + ~ArCoreConsentPrompt(); + + // ArCoreConsentPromptInterface: void ShowConsentPrompt( int render_process_id, int render_frame_id, base::OnceCallback<void(bool)> response_callback) override; - ArcoreConsentPrompt(); - ~ArcoreConsentPrompt(); - - // device::VrDevicePermissionProvider: - void GetUserPermission(int render_process_id, - int render_frame_id, - base::OnceCallback<void(bool)> response_callback); - + // Called from Java end. void OnUserConsentResult(JNIEnv* env, const base::android::JavaParamRef<jobject>& j_caller, jboolean is_granted); + void OnRequestInstallArModuleResult( + JNIEnv* env, + const base::android::JavaParamRef<jobject>& obj, + bool success); + void OnRequestInstallSupportedArCoreResult( + JNIEnv* env, + const base::android::JavaParamRef<jobject>& obj, + bool success); private: + // Returns true if AR module installation is supported, false otherwise. + bool CanRequestInstallArModule(); + // Returns true if AR module is not installed, false otherwise. + bool ShouldRequestInstallArModule(); + void RequestInstallArModule(); + bool ShouldRequestInstallSupportedArCore(); + void RequestInstallSupportedArCore(); + + void RequestArModule(); + void OnRequestArModuleResult(bool success); + void RequestArCoreInstallOrUpdate(); + void OnRequestArCoreInstallOrUpdateResult(bool success); + + void CallDeferredUserConsentCallback(bool is_permission_granted); + + base::WeakPtr<ArCoreConsentPrompt> GetWeakPtr() { + return weak_ptr_factory_.GetWeakPtr(); + } + base::OnceCallback<void(bool)> on_user_consent_callback_; + + base::OnceCallback<void(bool)> on_request_ar_module_result_callback_; + base::OnceCallback<void(bool)> + on_request_arcore_install_or_update_result_callback_; + + base::android::ScopedJavaGlobalRef<jobject> jdelegate_; + int render_process_id_; + int render_frame_id_; + + base::android::ScopedJavaGlobalRef<jobject> java_install_utils_; + THREAD_CHECKER(thread_checker_); + + base::WeakPtrFactory<ArCoreConsentPrompt> weak_ptr_factory_; + DISALLOW_COPY_AND_ASSIGN(ArCoreConsentPrompt); }; } // namespace vr
diff --git a/chrome/browser/android/vr/arcore_device/arcore_device.cc b/chrome/browser/android/vr/arcore_device/arcore_device.cc index 535231c7..205e130c 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_device.cc +++ b/chrome/browser/android/vr/arcore_device/arcore_device.cc
@@ -14,8 +14,8 @@ #include "chrome/browser/android/vr/arcore_device/arcore_gl.h" #include "chrome/browser/android/vr/arcore_device/arcore_gl_thread.h" #include "chrome/browser/android/vr/arcore_device/arcore_impl.h" -#include "chrome/browser/android/vr/arcore_device/arcore_install_utils.h" #include "chrome/browser/android/vr/arcore_device/arcore_java_utils.h" +#include "chrome/browser/android/vr/arcore_device/arcore_session_utils.h" #include "chrome/browser/android/vr/mailbox_to_surface_bridge.h" #include "chrome/browser/permissions/permission_manager.h" #include "chrome/browser/permissions/permission_result.h" @@ -74,13 +74,13 @@ std::unique_ptr<ArCoreFactory> arcore_factory, std::unique_ptr<ArImageTransportFactory> ar_image_transport_factory, std::unique_ptr<vr::MailboxToSurfaceBridge> mailbox_to_surface_bridge, - std::unique_ptr<vr::ArCoreInstallUtils> arcore_install_utils) + std::unique_ptr<vr::ArCoreSessionUtils> arcore_session_utils) : VRDeviceBase(mojom::XRDeviceId::ARCORE_DEVICE_ID), main_thread_task_runner_(base::ThreadTaskRunnerHandle::Get()), arcore_factory_(std::move(arcore_factory)), ar_image_transport_factory_(std::move(ar_image_transport_factory)), mailbox_bridge_(std::move(mailbox_to_surface_bridge)), - arcore_install_utils_(std::move(arcore_install_utils)), + arcore_session_utils_(std::move(arcore_session_utils)), session_state_(std::make_unique<ArCoreDevice::SessionState>()), weak_ptr_factory_(this) { // Ensure display_info_ is set to avoid crash in CallDeferredSessionCallback @@ -97,25 +97,16 @@ } ArCoreDevice::ArCoreDevice() - : ArCoreDevice( - std::make_unique<ArCoreImplFactory>(), - std::make_unique<ArImageTransportFactory>(), - std::make_unique<vr::MailboxToSurfaceBridge>(), - std::make_unique<vr::ArCoreJavaUtils>( - base::BindRepeating( - &ArCoreDevice::OnRequestInstallArModuleResult, - base::Unretained(this)), // unretained is fine for callbacks - // since ArCoreDevice owns the - // ArCoreJavaUtils instance - base::BindRepeating( - &ArCoreDevice::OnRequestInstallSupportedArCoreResult, - base::Unretained(this)))) {} + : ArCoreDevice(std::make_unique<ArCoreImplFactory>(), + std::make_unique<ArImageTransportFactory>(), + std::make_unique<vr::MailboxToSurfaceBridge>(), + std::make_unique<vr::ArCoreJavaUtils>()) {} ArCoreDevice::~ArCoreDevice() { CallDeferredRequestSessionCallback(/*success=*/false); // The GL thread must be terminated since it uses our members. For example, // there might still be a posted Initialize() call in flight that uses - // arcore_install_utils_ and arcore_factory_. Ensure that the thread is + // arcore_session_utils_ and arcore_factory_. Ensure that the thread is // stopped before other members get destructed. Don't call Stop() here, // destruction calls Stop() and doing so twice is illegal (null pointer // dereference). @@ -190,15 +181,6 @@ void ArCoreDevice::RequestSessionAfterInitialization(int render_process_id, int render_frame_id) { - session_state_->start_immersive_activity_callback_ = - base::BindOnce(&ArCoreDevice::RequestArSessionConsent, GetWeakPtr(), - render_process_id, render_frame_id); - - RequestArModule(render_process_id, render_frame_id); -} - -void ArCoreDevice::RequestArSessionConsent(int render_process_id, - int render_frame_id) { auto ready_callback = base::BindRepeating(&ArCoreDevice::OnDrawingSurfaceReady, GetWeakPtr()); auto touch_callback = @@ -206,7 +188,7 @@ auto destroyed_callback = base::BindOnce(&ArCoreDevice::OnDrawingSurfaceDestroyed, GetWeakPtr()); - arcore_install_utils_->RequestArSession( + arcore_session_utils_->RequestArSession( render_process_id, render_frame_id, std::move(ready_callback), std::move(touch_callback), std::move(destroyed_callback)); } @@ -250,7 +232,7 @@ DVLOG(1) << __func__; // This may be a no-op in case it's destroyed already. - arcore_install_utils_->DestroyDrawingSurface(); + arcore_session_utils_->DestroyDrawingSurface(); // The GL thread had initialized its context with a drawing_widget based on // the ArImmersiveOverlay's Surface, and the one it has is no longer valid. @@ -276,88 +258,6 @@ mailbox_bridge_ = nullptr; } -void ArCoreDevice::RequestArModule(int render_process_id, int render_frame_id) { - DVLOG(1) << __func__; - if (arcore_install_utils_->ShouldRequestInstallArModule()) { - if (!arcore_install_utils_->CanRequestInstallArModule()) { - OnRequestArModuleResult(render_process_id, render_frame_id, false); - return; - } - - on_request_ar_module_result_callback_ = - base::BindOnce(&ArCoreDevice::OnRequestArModuleResult, GetWeakPtr(), - render_process_id, render_frame_id); - arcore_install_utils_->RequestInstallArModule(render_process_id, - render_frame_id); - return; - } - - OnRequestArModuleResult(render_process_id, render_frame_id, true); -} - -void ArCoreDevice::OnRequestArModuleResult(int render_process_id, - int render_frame_id, - bool success) { - DVLOG(3) << __func__ << ": success=" << success; - - if (!success) { - CallDeferredRequestSessionCallback(/*success=*/false); - return; - } - - RequestArCoreInstallOrUpdate(render_process_id, render_frame_id); -} - -void ArCoreDevice::RequestArCoreInstallOrUpdate(int render_process_id, - int render_frame_id) { - DVLOG(1) << __func__; - DCHECK(IsOnMainThread()); - DCHECK(!on_request_arcore_install_or_update_result_callback_); - - if (arcore_install_utils_->ShouldRequestInstallSupportedArCore()) { - // ARCore is not installed or requires an update. Store the callback to be - // processed later once installation/update is complete or got cancelled. - on_request_arcore_install_or_update_result_callback_ = base::BindOnce( - &ArCoreDevice::OnRequestArCoreInstallOrUpdateResult, GetWeakPtr()); - - arcore_install_utils_->RequestInstallSupportedArCore(render_process_id, - render_frame_id); - return; - } - - OnRequestArCoreInstallOrUpdateResult(true); -} - -void ArCoreDevice::OnRequestArCoreInstallOrUpdateResult(bool success) { - DVLOG(1) << __func__; - DCHECK(IsOnMainThread()); - - if (!success) { - CallDeferredRequestSessionCallback(/*success=*/false); - return; - } - - DCHECK(session_state_->start_immersive_activity_callback_); - std::move(session_state_->start_immersive_activity_callback_).Run(); -} - -void ArCoreDevice::OnRequestInstallArModuleResult(bool success) { - DVLOG(1) << __func__; - DCHECK(IsOnMainThread()); - - if (on_request_ar_module_result_callback_) { - std::move(on_request_ar_module_result_callback_).Run(success); - } -} - -void ArCoreDevice::OnRequestInstallSupportedArCoreResult(bool success) { - DVLOG(1) << __func__; - DCHECK(IsOnMainThread()); - DCHECK(on_request_arcore_install_or_update_result_callback_); - - std::move(on_request_arcore_install_or_update_result_callback_).Run(success); -} - void ArCoreDevice::CallDeferredRequestSessionCallback(bool success) { DVLOG(1) << __func__ << " success=" << success; DCHECK(IsOnMainThread()); @@ -430,7 +330,7 @@ DCHECK(IsOnMainThread()); DCHECK(session_state_->is_arcore_gl_thread_initialized_); - if (!arcore_install_utils_->EnsureLoaded()) { + if (!arcore_session_utils_->EnsureLoaded()) { DLOG(ERROR) << "ARCore was not loaded properly."; OnArCoreGlInitializationComplete(false); return; @@ -445,7 +345,7 @@ PostTaskToGlThread(base::BindOnce( &ArCoreGl::Initialize, session_state_->arcore_gl_thread_->GetArCoreGl()->GetWeakPtr(), - arcore_install_utils_.get(), arcore_factory_.get(), drawing_widget, + arcore_session_utils_.get(), arcore_factory_.get(), drawing_widget, frame_size, rotation, CreateMainThreadCallback(base::BindOnce( &ArCoreDevice::OnArCoreGlInitializationComplete, GetWeakPtr()))));
diff --git a/chrome/browser/android/vr/arcore_device/arcore_device.h b/chrome/browser/android/vr/arcore_device/arcore_device.h index fc2560b..a28c944 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_device.h +++ b/chrome/browser/android/vr/arcore_device/arcore_device.h
@@ -22,7 +22,7 @@ namespace vr { class MailboxToSurfaceBridge; -class ArCoreInstallUtils; +class ArCoreSessionUtils; } // namespace vr namespace device { @@ -37,7 +37,7 @@ std::unique_ptr<ArCoreFactory> arcore_factory, std::unique_ptr<ArImageTransportFactory> ar_image_transport_factory, std::unique_ptr<vr::MailboxToSurfaceBridge> mailbox_to_surface_bridge, - std::unique_ptr<vr::ArCoreInstallUtils> arcore_install_utils); + std::unique_ptr<vr::ArCoreSessionUtils> arcore_session_utils); ArCoreDevice(); ~ArCoreDevice() override; @@ -51,9 +51,6 @@ } private: - void OnRequestInstallArModuleResult(bool success); - void OnRequestInstallSupportedArCoreResult(bool success); - // VRDeviceBase implementation void OnMailboxBridgeReady(); void OnArCoreGlThreadInitialized(); @@ -88,21 +85,11 @@ void RequestSessionAfterInitialization(int render_process_id, int render_frame_id); - void RequestArModule(int render_process_id, int render_frame_id); - void OnRequestArModuleResult(int render_process_id, - int render_frame_id, - bool success); - void RequestArCoreInstallOrUpdate(int render_process_id, int render_frame_id); - void OnRequestArCoreInstallOrUpdateResult(bool success); void CallDeferredRequestSessionCallback(bool success); - void OnRequestAndroidCameraPermissionResult( - base::OnceCallback<void(bool)> callback, - bool was_android_camera_permission_granted); void RequestArCoreGlInitialization(gfx::AcceleratedWidget window, int rotation, const gfx::Size& size); void OnArCoreGlInitializationComplete(bool success); - void RequestArSessionConsent(int render_process_id, int render_frame_id); void OnCreateSessionCallback( mojom::XRRuntime::RequestSessionCallback deferred_callback, @@ -115,7 +102,7 @@ std::unique_ptr<ArCoreFactory> arcore_factory_; std::unique_ptr<ArImageTransportFactory> ar_image_transport_factory_; std::unique_ptr<vr::MailboxToSurfaceBridge> mailbox_bridge_; - std::unique_ptr<vr::ArCoreInstallUtils> arcore_install_utils_; + std::unique_ptr<vr::ArCoreSessionUtils> arcore_session_utils_; // Encapsulates data with session lifetime. struct SessionState {
diff --git a/chrome/browser/android/vr/arcore_device/arcore_device_unittest.cc b/chrome/browser/android/vr/arcore_device/arcore_device_unittest.cc index cc514c7..72706d61 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_device_unittest.cc +++ b/chrome/browser/android/vr/arcore_device/arcore_device_unittest.cc
@@ -11,9 +11,8 @@ #include "base/message_loop/message_loop.h" #include "base/run_loop.h" #include "chrome/browser/android/vr/arcore_device/ar_image_transport.h" -#include "chrome/browser/android/vr/arcore_device/arcore_device.h" #include "chrome/browser/android/vr/arcore_device/arcore_gl.h" -#include "chrome/browser/android/vr/arcore_device/arcore_install_utils.h" +#include "chrome/browser/android/vr/arcore_device/arcore_session_utils.h" #include "chrome/browser/android/vr/arcore_device/fake_arcore.h" #include "chrome/browser/android/vr/mailbox_to_surface_bridge.h" #include "device/vr/public/mojom/vr_service.mojom.h" @@ -82,18 +81,10 @@ base::OnceClosure callback_; }; -class StubArCoreInstallUtils : public vr::ArCoreInstallUtils { +class StubArCoreSessionUtils : public vr::ArCoreSessionUtils { public: - StubArCoreInstallUtils() = default; + StubArCoreSessionUtils() = default; - bool CanRequestInstallArModule() override { return false; } - bool ShouldRequestInstallArModule() override { return false; } - - void RequestInstallArModule(int render_process_id, - int render_frame_id) override {} - bool ShouldRequestInstallSupportedArCore() override { return false; } - void RequestInstallSupportedArCore(int render_process_id, - int render_frame_id) override {} void RequestArSession( int render_process_id, int render_frame_id, @@ -148,7 +139,7 @@ } StubMailboxToSurfaceBridge* bridge; - StubArCoreInstallUtils* install_utils; + StubArCoreSessionUtils* session_utils; mojom::XRFrameDataProviderPtr frame_provider; mojom::XREnvironmentIntegrationProviderAssociatedPtr environment_provider; std::unique_ptr<base::RunLoop> run_loop; @@ -159,13 +150,13 @@ std::unique_ptr<StubMailboxToSurfaceBridge> bridge_ptr = std::make_unique<StubMailboxToSurfaceBridge>(); bridge = bridge_ptr.get(); - std::unique_ptr<StubArCoreInstallUtils> install_utils_ptr = - std::make_unique<StubArCoreInstallUtils>(); - install_utils = install_utils_ptr.get(); + std::unique_ptr<StubArCoreSessionUtils> session_utils_ptr = + std::make_unique<StubArCoreSessionUtils>(); + session_utils = session_utils_ptr.get(); device_ = std::make_unique<ArCoreDevice>( std::make_unique<FakeArCoreFactory>(), std::make_unique<StubArImageTransportFactory>(), std::move(bridge_ptr), - std::move(install_utils_ptr)); + std::move(session_utils_ptr)); } void CreateSession() { @@ -245,7 +236,7 @@ base::BindOnce(callback, &hit_results)); // Have to get frame data to trigger the hit-test calculation. GetFrameData(); - EXPECT_TRUE(hit_results.size() > 0); + EXPECT_FALSE(hit_results.empty()); } } // namespace device
diff --git a/chrome/browser/android/vr/arcore_device/arcore_gl.cc b/chrome/browser/android/vr/arcore_device/arcore_gl.cc index 1bfb8e0..a466b51 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_gl.cc +++ b/chrome/browser/android/vr/arcore_device/arcore_gl.cc
@@ -20,7 +20,7 @@ #include "base/trace_event/traced_value.h" #include "chrome/browser/android/vr/arcore_device/ar_image_transport.h" #include "chrome/browser/android/vr/arcore_device/arcore_impl.h" -#include "chrome/browser/android/vr/arcore_device/arcore_install_utils.h" +#include "chrome/browser/android/vr/arcore_device/arcore_session_utils.h" #include "chrome/browser/android/vr/web_xr_presentation_state.h" #include "device/vr/public/mojom/vr_service.mojom.h" #include "gpu/ipc/common/gpu_memory_buffer_impl_android_hardware_buffer.h" @@ -119,7 +119,7 @@ CloseBindingsIfOpen(); } -void ArCoreGl::Initialize(vr::ArCoreInstallUtils* install_utils, +void ArCoreGl::Initialize(vr::ArCoreSessionUtils* session_utils, ArCoreFactory* arcore_factory, gfx::AcceleratedWidget drawing_widget, const gfx::Size& frame_size, @@ -141,7 +141,7 @@ // Get the activity context. base::android::ScopedJavaLocalRef<jobject> application_context = - install_utils->GetApplicationContext(); + session_utils->GetApplicationContext(); if (!application_context.obj()) { DLOG(ERROR) << "Unable to retrieve the Java context/activity!"; std::move(callback).Run(false);
diff --git a/chrome/browser/android/vr/arcore_device/arcore_gl.h b/chrome/browser/android/vr/arcore_device/arcore_gl.h index 0e13a647..0121a4d8 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_gl.h +++ b/chrome/browser/android/vr/arcore_device/arcore_gl.h
@@ -36,7 +36,7 @@ } // namespace gl namespace vr { -class ArCoreInstallUtils; +class ArCoreSessionUtils; class WebXrPresentationState; } // namespace vr @@ -63,7 +63,7 @@ explicit ArCoreGl(std::unique_ptr<ArImageTransport> ar_image_transport); ~ArCoreGl() override; - void Initialize(vr::ArCoreInstallUtils* install_utils, + void Initialize(vr::ArCoreSessionUtils* session_utils, ArCoreFactory* arcore_factory, gfx::AcceleratedWidget drawing_widget, const gfx::Size& frame_size,
diff --git a/chrome/browser/android/vr/arcore_device/arcore_java_utils.cc b/chrome/browser/android/vr/arcore_device/arcore_java_utils.cc index 111e9a31..54392cd 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_java_utils.cc +++ b/chrome/browser/android/vr/arcore_device/arcore_java_utils.cc
@@ -10,11 +10,9 @@ #include "base/android/jni_string.h" #include "chrome/browser/android/tab_android.h" #include "chrome/browser/android/vr/ar_jni_headers/ArCoreJavaUtils_jni.h" -#include "chrome/browser/android/vr/arcore_device/arcore_device_provider.h" #include "chrome/browser/android/vr/arcore_device/arcore_shim.h" #include "content/public/browser/render_frame_host.h" #include "content/public/browser/web_contents.h" -#include "device/vr/android/arcore/arcore_device_provider_factory.h" using base::android::AttachCurrentThread; using base::android::ScopedJavaLocalRef; @@ -23,29 +21,9 @@ namespace { -class ArCoreDeviceProviderFactoryImpl - : public device::ArCoreDeviceProviderFactory { - public: - ArCoreDeviceProviderFactoryImpl() = default; - ~ArCoreDeviceProviderFactoryImpl() override = default; - std::unique_ptr<device::VRDeviceProvider> CreateDeviceProvider() override; - - private: - DISALLOW_COPY_AND_ASSIGN(ArCoreDeviceProviderFactoryImpl); -}; - -std::unique_ptr<device::VRDeviceProvider> -ArCoreDeviceProviderFactoryImpl::CreateDeviceProvider() { - return std::make_unique<device::ArCoreDeviceProvider>(); -} - } // namespace -ArCoreJavaUtils::ArCoreJavaUtils( - base::RepeatingCallback<void(bool)> ar_module_installation_callback, - base::RepeatingCallback<void(bool)> ar_core_installation_callback) - : ar_module_installation_callback_(ar_module_installation_callback), - ar_core_installation_callback_(ar_core_installation_callback) { +ArCoreJavaUtils::ArCoreJavaUtils() { JNIEnv* env = AttachCurrentThread(); if (!env) return; @@ -61,46 +39,6 @@ Java_ArCoreJavaUtils_onNativeDestroy(env, j_arcore_java_utils_); } -void ArCoreJavaUtils::OnRequestInstallSupportedArCoreResult( - JNIEnv* env, - const base::android::JavaParamRef<jobject>& obj, - bool success) { - ar_core_installation_callback_.Run(success); -} - -bool ArCoreJavaUtils::CanRequestInstallArModule() { - return Java_ArCoreJavaUtils_canRequestInstallArModule(AttachCurrentThread(), - j_arcore_java_utils_); -} - -bool ArCoreJavaUtils::ShouldRequestInstallArModule() { - return Java_ArCoreJavaUtils_shouldRequestInstallArModule( - AttachCurrentThread(), j_arcore_java_utils_); -} - -void ArCoreJavaUtils::RequestInstallArModule(int render_process_id, - int render_frame_id) { - Java_ArCoreJavaUtils_requestInstallArModule( - AttachCurrentThread(), j_arcore_java_utils_, - getTabFromRenderer(render_process_id, render_frame_id)); -} - -bool ArCoreJavaUtils::ShouldRequestInstallSupportedArCore() { - JNIEnv* env = AttachCurrentThread(); - return Java_ArCoreJavaUtils_shouldRequestInstallSupportedArCore( - env, j_arcore_java_utils_); -} - -void ArCoreJavaUtils::RequestInstallSupportedArCore(int render_process_id, - int render_frame_id) { - DCHECK(ShouldRequestInstallSupportedArCore()); - - JNIEnv* env = AttachCurrentThread(); - Java_ArCoreJavaUtils_requestInstallSupportedArCore( - env, j_arcore_java_utils_, - getTabFromRenderer(render_process_id, render_frame_id)); -} - void ArCoreJavaUtils::RequestArSession( int render_process_id, int render_frame_id, @@ -161,13 +99,6 @@ } } -void ArCoreJavaUtils::OnRequestInstallArModuleResult( - JNIEnv* env, - const base::android::JavaParamRef<jobject>& obj, - bool success) { - ar_module_installation_callback_.Run(success); -} - bool ArCoreJavaUtils::EnsureLoaded() { DCHECK(vr::IsArCoreSupported()); @@ -206,10 +137,4 @@ return j_tab_android; } -static void JNI_ArCoreJavaUtils_InstallArCoreDeviceProviderFactory( - JNIEnv* env) { - device::ArCoreDeviceProviderFactory::Install( - std::make_unique<ArCoreDeviceProviderFactoryImpl>()); -} - } // namespace vr
diff --git a/chrome/browser/android/vr/arcore_device/arcore_java_utils.h b/chrome/browser/android/vr/arcore_device/arcore_java_utils.h index 5a5afe5..9e9ac15b 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_java_utils.h +++ b/chrome/browser/android/vr/arcore_device/arcore_java_utils.h
@@ -11,39 +11,26 @@ #include "base/android/scoped_java_ref.h" #include "base/callback.h" #include "base/memory/weak_ptr.h" -#include "chrome/browser/android/vr/arcore_device/arcore_install_utils.h" +#include "chrome/browser/android/vr/arcore_device/arcore_session_utils.h" namespace vr { -class ArCoreJavaUtils : public ArCoreInstallUtils { +class ArCoreJavaUtils : public ArCoreSessionUtils { public: - explicit ArCoreJavaUtils( - base::RepeatingCallback<void(bool)> ar_module_installation_callback, - base::RepeatingCallback<void(bool)> ar_core_installation_callback); + ArCoreJavaUtils(); ~ArCoreJavaUtils() override; - bool ShouldRequestInstallArModule() override; - bool CanRequestInstallArModule() override; - void RequestInstallArModule(int render_process_id, - int render_frame_id) override; - bool ShouldRequestInstallSupportedArCore() override; - void RequestInstallSupportedArCore(int render_process_id, - int render_frame_id) override; + + // ArCoreSessionUtils: void RequestArSession(int render_process_id, int render_frame_id, SurfaceReadyCallback ready_callback, SurfaceTouchCallback touch_callback, SurfaceDestroyedCallback destroyed_callback) override; void DestroyDrawingSurface() override; + bool EnsureLoaded() override; + base::android::ScopedJavaLocalRef<jobject> GetApplicationContext() override; // Methods called from the Java side. - void OnRequestInstallArModuleResult( - JNIEnv* env, - const base::android::JavaParamRef<jobject>& obj, - bool success); - void OnRequestInstallSupportedArCoreResult( - JNIEnv* env, - const base::android::JavaParamRef<jobject>& obj, - bool success); void OnDrawingSurfaceReady( JNIEnv* env, const base::android::JavaParamRef<jobject>& obj, @@ -60,17 +47,11 @@ JNIEnv* env, const base::android::JavaParamRef<jobject>& obj); - bool EnsureLoaded() override; - base::android::ScopedJavaLocalRef<jobject> GetApplicationContext() override; - private: base::android::ScopedJavaLocalRef<jobject> getTabFromRenderer( int render_process_id, int render_frame_id); - base::RepeatingCallback<void(bool)> ar_module_installation_callback_; - base::RepeatingCallback<void(bool)> ar_core_installation_callback_; - base::android::ScopedJavaGlobalRef<jobject> j_arcore_java_utils_; SurfaceReadyCallback surface_ready_callback_;
diff --git a/chrome/browser/android/vr/arcore_device/arcore_install_utils.h b/chrome/browser/android/vr/arcore_device/arcore_session_utils.h similarity index 64% rename from chrome/browser/android/vr/arcore_device/arcore_install_utils.h rename to chrome/browser/android/vr/arcore_device/arcore_session_utils.h index f1156983..1573fbe4 100644 --- a/chrome/browser/android/vr/arcore_device/arcore_install_utils.h +++ b/chrome/browser/android/vr/arcore_device/arcore_session_utils.h
@@ -2,8 +2,8 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef CHROME_BROWSER_ANDROID_VR_ARCORE_DEVICE_ARCORE_INSTALL_UTILS_H_ -#define CHROME_BROWSER_ANDROID_VR_ARCORE_DEVICE_ARCORE_INSTALL_UTILS_H_ +#ifndef CHROME_BROWSER_ANDROID_VR_ARCORE_DEVICE_ARCORE_SESSION_UTILS_H_ +#define CHROME_BROWSER_ANDROID_VR_ARCORE_DEVICE_ARCORE_SESSION_UTILS_H_ #include "base/android/scoped_java_ref.h" #include "base/memory/weak_ptr.h" @@ -30,18 +30,9 @@ base::RepeatingCallback<void(bool touching, const gfx::PointF& location)>; using SurfaceDestroyedCallback = base::OnceClosure; -class ArCoreInstallUtils { +class ArCoreSessionUtils { public: - virtual ~ArCoreInstallUtils() = default; - // Returns true if AR module installation is supported, false otherwise. - virtual bool CanRequestInstallArModule() = 0; - // Returns true if AR module is not installed, false otherwise. - virtual bool ShouldRequestInstallArModule() = 0; - virtual void RequestInstallArModule(int render_process_id, - int render_frame_id) = 0; - virtual bool ShouldRequestInstallSupportedArCore() = 0; - virtual void RequestInstallSupportedArCore(int render_process_id, - int render_frame_id) = 0; + virtual ~ArCoreSessionUtils() = default; virtual bool EnsureLoaded() = 0; virtual base::android::ScopedJavaLocalRef<jobject> GetApplicationContext() = 0; @@ -56,4 +47,4 @@ } // namespace vr -#endif // CHROME_BROWSER_ANDROID_VR_ARCORE_DEVICE_ARCORE_INSTALL_UTILS_H_ +#endif // CHROME_BROWSER_ANDROID_VR_ARCORE_DEVICE_ARCORE_SESSION_UTILS_H_
diff --git a/chrome/browser/android/vr/vr_module_provider.cc b/chrome/browser/android/vr/vr_module_provider.cc index 1004ae4..92abcf8 100644 --- a/chrome/browser/android/vr/vr_module_provider.cc +++ b/chrome/browser/android/vr/vr_module_provider.cc
@@ -88,7 +88,7 @@ static void JNI_VrModuleProvider_Init(JNIEnv* env) { GvrConsentHelper::SetInstance(std::make_unique<vr::GvrConsentHelperImpl>()); #if BUILDFLAG(ENABLE_ARCORE) - ArcoreConsentPromptInterface::SetInstance(new ArcoreConsentPrompt()); + ArCoreConsentPromptInterface::SetInstance(new ArCoreConsentPrompt()); #endif }
diff --git a/chrome/browser/autofill/autofill_keyboard_accessory_adapter.cc b/chrome/browser/autofill/autofill_keyboard_accessory_adapter.cc index 4caa854..35843fa 100644 --- a/chrome/browser/autofill/autofill_keyboard_accessory_adapter.cc +++ b/chrome/browser/autofill/autofill_keyboard_accessory_adapter.cc
@@ -10,6 +10,7 @@ #include "base/bind.h" #include "base/callback.h" #include "base/memory/weak_ptr.h" +#include "base/strings/utf_string_conversions.h" #include "chrome/browser/ui/autofill/autofill_popup_controller.h" #include "chrome/browser/ui/autofill/autofill_popup_layout_model.h" #include "components/autofill/core/browser/ui/popup_item_ids.h" @@ -17,6 +18,22 @@ namespace autofill { +constexpr base::char16 kLabelSeparator = ' '; +constexpr size_t kMaxBulletCount = 8; + +namespace { +base::string16 CreateLabel(const Suggestion& suggestion) { + base::string16 password = + suggestion.additional_label.substr(0, kMaxBulletCount); + // The label contains the signon_realm or is empty. The additional_label can + // never be empty since it must contain a password. + if (suggestion.label.empty()) + return password; + return suggestion.label + kLabelSeparator + password; +} + +} // namespace + AutofillKeyboardAccessoryAdapter::AutofillKeyboardAccessoryAdapter( AutofillPopupController* controller, unsigned int animation_duration_millis, @@ -49,14 +66,19 @@ DCHECK(controller_) << "Call OnSuggestionsChanged only from its owner!"; DCHECK(view_) << "OnSuggestionsChanged called before a View was set!"; + labels_.clear(); front_element_ = base::nullopt; for (int i = 0; i < GetLineCount(); ++i) { const Suggestion& suggestion = controller_->GetSuggestionAt(i); if (suggestion.frontend_id != POPUP_ITEM_ID_CLEAR_FORM && - suggestion.frontend_id != POPUP_ITEM_ID_CREATE_HINT) + suggestion.frontend_id != POPUP_ITEM_ID_CREATE_HINT) { + labels_.push_back(CreateLabel(suggestion)); continue; + } DCHECK(!front_element_.has_value()) << "Additional front item at: " << i; front_element_ = base::Optional<int>(i); + // If there is a special popup item, just reuse the previously used label. + labels_.push_back(controller_->GetElidedLabelAt(i)); } view_->Show(); @@ -75,24 +97,21 @@ const autofill::Suggestion& AutofillKeyboardAccessoryAdapter::GetSuggestionAt( int row) const { - DCHECK(controller_) << "Call OnSuggestionsChanged only from its owner!"; + DCHECK(controller_) << "Call GetSuggestionAt only from its owner!"; return controller_->GetSuggestionAt(OffsetIndexFor(row)); } const base::string16& AutofillKeyboardAccessoryAdapter::GetElidedValueAt( int row) const { - DCHECK(controller_) << "Call OnSuggestionsChanged only from its owner!"; + DCHECK(controller_) << "Call GetElidedValueAt only from its owner!"; return controller_->GetElidedValueAt(OffsetIndexFor(row)); } const base::string16& AutofillKeyboardAccessoryAdapter::GetElidedLabelAt( int row) const { - DCHECK(controller_) << "Call OnSuggestionsChanged only from its owner!"; - const base::string16& label = - controller_->GetElidedLabelAt(OffsetIndexFor(row)); - if (label.empty()) - return GetSuggestionAt(row).additional_label; - return label; + DCHECK(controller_) << "Call GetElidedLabelAt only from its owner!"; + DCHECK(static_cast<size_t>(row) < labels_.size()); + return labels_[OffsetIndexFor(row)]; } bool AutofillKeyboardAccessoryAdapter::GetRemovalConfirmationText(
diff --git a/chrome/browser/autofill/autofill_keyboard_accessory_adapter.h b/chrome/browser/autofill/autofill_keyboard_accessory_adapter.h index 8ad5806..c8b597d4 100644 --- a/chrome/browser/autofill/autofill_keyboard_accessory_adapter.h +++ b/chrome/browser/autofill/autofill_keyboard_accessory_adapter.h
@@ -100,6 +100,9 @@ AutofillPopupController* controller_; // weak. std::unique_ptr<AutofillKeyboardAccessoryAdapter::AccessoryView> view_; + // The labels to be used for the input chips. + std::vector<base::string16> labels_; + // If 0, don't animate suggestion view. const unsigned int animation_duration_millis_;
diff --git a/chrome/browser/autofill/autofill_keyboard_accessory_adapter_unittest.cc b/chrome/browser/autofill/autofill_keyboard_accessory_adapter_unittest.cc index 12ef283..a901596 100644 --- a/chrome/browser/autofill/autofill_keyboard_accessory_adapter_unittest.cc +++ b/chrome/browser/autofill/autofill_keyboard_accessory_adapter_unittest.cc
@@ -5,6 +5,7 @@ #include <cstddef> #include <memory> +#include <string> #include <utility> #include <vector> @@ -51,13 +52,20 @@ DISALLOW_COPY_AND_ASSIGN(MockAccessoryView); }; +Suggestion createPasswordEntry(std::string password, + std::string username, + std::string psl_origin) { + Suggestion s(/*value=*/username, /*label=*/psl_origin, /*icon=*/"", + PopupItemId::POPUP_ITEM_ID_AUTOCOMPLETE_ENTRY); + s.additional_label = ASCIIToUTF16(password); + return s; +} + std::vector<Suggestion> createSuggestions() { std::vector<Suggestion> suggestions = { - Suggestion("*", "A", "", PopupItemId::POPUP_ITEM_ID_AUTOCOMPLETE_ENTRY), - Suggestion("**", "", "", PopupItemId::POPUP_ITEM_ID_AUTOCOMPLETE_ENTRY), - Suggestion("***", "C", "", - PopupItemId::POPUP_ITEM_ID_AUTOCOMPLETE_ENTRY)}; - suggestions[1].additional_label = ASCIIToUTF16("B"); + createPasswordEntry("****************", "Alf", ""), + createPasswordEntry("****************", "Berta", "psl.origin.eg"), + createPasswordEntry("***", "Carl", "")}; return suggestions; } @@ -174,14 +182,23 @@ } TEST_F(AutofillKeyboardAccessoryAdapterTest, UseAdditionalLabelForElidedLabel) { - controller()->set_suggestions(createSuggestions()); + controller()->set_suggestions(createSuggestions(/*clearItemOffset=*/1)); NotifyAboutSuggestions(); - // If there is a label, use it. - EXPECT_EQ(adapter_as_controller()->GetElidedLabelAt(0), ASCIIToUTF16("A")); + // The 1st item is usually not visible (something like clear form) and has an + // empty label. But it needs to be handled since UI might ask for it anyway. + EXPECT_EQ(adapter_as_controller()->GetElidedLabelAt(0), base::string16()); + + // If there is a label, use it but cap at 8 bullets. + EXPECT_EQ(adapter_as_controller()->GetElidedLabelAt(1), + ASCIIToUTF16("********")); // If the label is empty, use the additional label: - EXPECT_EQ(adapter_as_controller()->GetElidedLabelAt(1), ASCIIToUTF16("B")); + EXPECT_EQ(adapter_as_controller()->GetElidedLabelAt(2), + ASCIIToUTF16("psl.origin.eg ********")); + + // If the password has less than 8 bullets, show the exact amount. + EXPECT_EQ(adapter_as_controller()->GetElidedLabelAt(3), ASCIIToUTF16("***")); } TEST_F(AutofillKeyboardAccessoryAdapterTest, ProvideReorderedSuggestions) {
diff --git a/chrome/browser/bookmarks/OWNERS b/chrome/browser/bookmarks/OWNERS index 90b3e80..6cfd65c 100644 --- a/chrome/browser/bookmarks/OWNERS +++ b/chrome/browser/bookmarks/OWNERS
@@ -1 +1,2 @@ sky@chromium.org +# COMPONENT: UI>Browser>Bookmarks
diff --git a/chrome/browser/chromeos/kerberos/kerberos_credentials_manager.cc b/chrome/browser/chromeos/kerberos/kerberos_credentials_manager.cc index e9b4ad7..b78c4e27 100644 --- a/chrome/browser/chromeos/kerberos/kerberos_credentials_manager.cc +++ b/chrome/browser/chromeos/kerberos/kerberos_credentials_manager.cc
@@ -826,11 +826,13 @@ const std::string& principal_name) { // TODO(https://crbug.com/952245): Right now, the reauth dialog is tied to the // settings. Consider creating a standalone reauth dialog. - kerberos_ticket_expiry_notification::Close(primary_profile_); chrome::SettingsWindowManager::GetInstance()->ShowOSSettings( primary_profile_, chrome::kKerberosAccountsSubPage + std::string("?kerberos_reauth=") + net::EscapeQueryParamValue(principal_name, false /* use_plus */)); + + // Close last! |principal_name| is owned by the notification. + kerberos_ticket_expiry_notification::Close(primary_profile_); } } // namespace chromeos
diff --git a/chrome/browser/chromeos/login/oobe_browsertest.cc b/chrome/browser/chromeos/login/oobe_browsertest.cc index 7452adda..b1c6a02 100644 --- a/chrome/browser/chromeos/login/oobe_browsertest.cc +++ b/chrome/browser/chromeos/login/oobe_browsertest.cc
@@ -20,6 +20,10 @@ #include "chrome/common/chrome_switches.h" #include "chrome/test/base/in_process_browser_test.h" #include "chromeos/constants/chromeos_switches.h" +#include "chromeos/dbus/cryptohome/fake_cryptohome_client.h" +#include "chromeos/dbus/cryptohome/key.pb.h" +#include "chromeos/dbus/cryptohome/rpc.pb.h" +#include "chromeos/login/auth/cryptohome_key_constants.h" #include "components/account_id/account_id.h" #include "components/user_manager/known_user.h" #include "components/user_manager/user.h" @@ -81,6 +85,9 @@ chrome::NOTIFICATION_SESSION_STARTED, content::NotificationService::AllSources()); + // Make the MountEx cryptohome call fail iff the |create| field is missing, + // which simulates the real cryptohomed's behavior for the new user mount. + FakeCryptohomeClient::Get()->set_mount_create_required(true); LoginDisplayHost::default_host() ->GetOobeUI() ->GetView<GaiaScreenHandler>() @@ -95,6 +102,23 @@ ->GetAccountId(); EXPECT_FALSE( user_manager::known_user::GetIsUsingSAMLPrincipalsAPI(account_id)); + + // Verify the parameters that were passed to the latest MountEx call. + const cryptohome::AuthorizationRequest& cryptohome_auth = + FakeCryptohomeClient::Get()->get_last_mount_authentication(); + EXPECT_EQ(cryptohome::KeyData::KEY_TYPE_PASSWORD, + cryptohome_auth.key().data().type()); + EXPECT_TRUE(cryptohome_auth.key().data().label().empty()); + EXPECT_FALSE(cryptohome_auth.key().secret().empty()); + const cryptohome::MountRequest& last_mount_request = + FakeCryptohomeClient::Get()->get_last_mount_request(); + ASSERT_TRUE(last_mount_request.has_create()); + ASSERT_EQ(1, last_mount_request.create().keys_size()); + EXPECT_EQ(cryptohome::KeyData::KEY_TYPE_PASSWORD, + last_mount_request.create().keys(0).data().type()); + EXPECT_EQ(kCryptohomeGaiaKeyLabel, + last_mount_request.create().keys(0).data().label()); + EXPECT_FALSE(last_mount_request.create().keys(0).secret().empty()); } IN_PROC_BROWSER_TEST_F(OobeTest, Accelerator) {
diff --git a/chrome/browser/chromeos/login/users/avatar/user_image_manager_impl.cc b/chrome/browser/chromeos/login/users/avatar/user_image_manager_impl.cc index 8a7a72d..5300fb3 100644 --- a/chrome/browser/chromeos/login/users/avatar/user_image_manager_impl.cc +++ b/chrome/browser/chromeos/login/users/avatar/user_image_manager_impl.cc
@@ -32,6 +32,7 @@ #include "chrome/browser/chromeos/profiles/profile_helper.h" #include "chrome/browser/profiles/profile_downloader.h" #include "chrome/browser/profiles/profile_manager.h" +#include "chrome/browser/signin/identity_manager_factory.h" #include "chrome/common/chrome_paths.h" #include "components/policy/policy_constants.h" #include "components/prefs/pref_registry_simple.h" @@ -39,6 +40,7 @@ #include "components/prefs/scoped_user_pref_update.h" #include "components/user_manager/user_image/user_image.h" #include "components/user_manager/user_manager.h" +#include "content/public/browser/storage_partition.h" #include "ui/base/resource/resource_bundle.h" #include "ui/chromeos/resources/grit/ui_chromeos_resources.h" #include "ui/gfx/image/image_skia.h" @@ -791,8 +793,16 @@ return GetCurrentUserImageSize(); } -Profile* UserImageManagerImpl::GetBrowserProfile() { - return ProfileHelper::Get()->GetProfileByUserUnsafe(GetUser()); +identity::IdentityManager* UserImageManagerImpl::GetIdentityManager() { + return IdentityManagerFactory::GetForProfile( + ProfileHelper::Get()->GetProfileByUserUnsafe(GetUser())); +} + +network::mojom::URLLoaderFactory* UserImageManagerImpl::GetURLLoaderFactory() { + return content::BrowserContext::GetDefaultStoragePartition( + ProfileHelper::Get()->GetProfileByUserUnsafe(GetUser())) + ->GetURLLoaderFactoryForBrowserProcess() + .get(); } std::string UserImageManagerImpl::GetCachedPictureURL() const {
diff --git a/chrome/browser/chromeos/login/users/avatar/user_image_manager_impl.h b/chrome/browser/chromeos/login/users/avatar/user_image_manager_impl.h index 10ac558..e94a364 100644 --- a/chrome/browser/chromeos/login/users/avatar/user_image_manager_impl.h +++ b/chrome/browser/chromeos/login/users/avatar/user_image_manager_impl.h
@@ -94,7 +94,8 @@ // ProfileDownloaderDelegate: bool NeedsProfilePicture() const override; int GetDesiredImageSideLength() const override; - Profile* GetBrowserProfile() override; + identity::IdentityManager* GetIdentityManager() override; + network::mojom::URLLoaderFactory* GetURLLoaderFactory() override; std::string GetCachedPictureURL() const override; bool IsPreSignin() const override; void OnProfileDownloadSuccess(ProfileDownloader* downloader) override;
diff --git a/chrome/browser/chromeos/policy/browser_policy_connector_chromeos.cc b/chrome/browser/chromeos/policy/browser_policy_connector_chromeos.cc index 24d5ad4..51b4ed82 100644 --- a/chrome/browser/chromeos/policy/browser_policy_connector_chromeos.cc +++ b/chrome/browser/chromeos/policy/browser_policy_connector_chromeos.cc
@@ -9,6 +9,7 @@ #include "base/bind.h" #include "base/command_line.h" +#include "base/feature_list.h" #include "base/files/file_path.h" #include "base/location.h" #include "base/logging.h" @@ -47,6 +48,7 @@ #include "chrome/browser/chromeos/settings/device_settings_service.h" #include "chrome/browser/chromeos/system/timezone_util.h" #include "chrome/browser/policy/device_management_service_configuration.h" +#include "chrome/common/chrome_features.h" #include "chrome/common/pref_names.h" #include "chromeos/attestation/attestation_flow.h" #include "chromeos/constants/chromeos_paths.h" @@ -248,9 +250,12 @@ device_cloud_external_data_policy_handlers_.emplace_back( std::make_unique<policy::DeviceWallpaperImageExternalDataHandler>( local_state, GetPolicyService())); - device_cloud_external_data_policy_handlers_.emplace_back( - std::make_unique<policy::DeviceWilcoDtcConfigurationExternalDataHandler>( - GetPolicyService())); + if (base::FeatureList::IsEnabled(::features::kWilcoDtc)) { + device_cloud_external_data_policy_handlers_.emplace_back( + std::make_unique< + policy::DeviceWilcoDtcConfigurationExternalDataHandler>( + GetPolicyService())); + } } void BrowserPolicyConnectorChromeOS::PreShutdown() {
diff --git a/chrome/browser/chromeos/policy/device_local_account_policy_store.cc b/chrome/browser/chromeos/policy/device_local_account_policy_store.cc index 4562b5c..3c8f340 100644 --- a/chrome/browser/chromeos/policy/device_local_account_policy_store.cc +++ b/chrome/browser/chromeos/policy/device_local_account_policy_store.cc
@@ -211,7 +211,7 @@ auto validator = std::make_unique<UserCloudPolicyValidator>( std::move(policy_response), background_task_runner()); - validator->ValidateUsername(account_id_, false); + validator->ValidateUsername(account_id_); validator->ValidatePolicyType(dm_protocol::kChromePublicAccountPolicyType); // The timestamp is verified when storing a new policy downloaded from the // server but not when loading a cached policy from disk.
diff --git a/chrome/browser/chromeos/policy/external_data_handlers/device_wilco_dtc_configuration_external_data_handler.cc b/chrome/browser/chromeos/policy/external_data_handlers/device_wilco_dtc_configuration_external_data_handler.cc index 4b137e7..0403f9fb 100644 --- a/chrome/browser/chromeos/policy/external_data_handlers/device_wilco_dtc_configuration_external_data_handler.cc +++ b/chrome/browser/chromeos/policy/external_data_handlers/device_wilco_dtc_configuration_external_data_handler.cc
@@ -34,18 +34,14 @@ void DeviceWilcoDtcConfigurationExternalDataHandler:: OnDeviceExternalDataCleared(const std::string& policy) { - auto* wilco_manager = GetWilcoDtcSupportdManager(); - if (wilco_manager) - wilco_manager->SetConfigurationData(nullptr); + GetWilcoDtcSupportdManager()->SetConfigurationData(nullptr); } void DeviceWilcoDtcConfigurationExternalDataHandler:: OnDeviceExternalDataFetched(const std::string& policy, std::unique_ptr<std::string> data, const base::FilePath& file_path) { - auto* wilco_manager = GetWilcoDtcSupportdManager(); - if (wilco_manager) - wilco_manager->SetConfigurationData(std::move(data)); + GetWilcoDtcSupportdManager()->SetConfigurationData(std::move(data)); } void DeviceWilcoDtcConfigurationExternalDataHandler::Shutdown() {
diff --git a/chrome/browser/chromeos/policy/external_data_handlers/device_wilco_dtc_configuration_external_data_handler_browsertest.cc b/chrome/browser/chromeos/policy/external_data_handlers/device_wilco_dtc_configuration_external_data_handler_browsertest.cc new file mode 100644 index 0000000..4af290a --- /dev/null +++ b/chrome/browser/chromeos/policy/external_data_handlers/device_wilco_dtc_configuration_external_data_handler_browsertest.cc
@@ -0,0 +1,144 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include <cstdint> +#include <memory> +#include <string> + +#include "base/bind.h" +#include "base/callback.h" +#include "base/files/file_path.h" +#include "base/run_loop.h" +#include "base/test/scoped_feature_list.h" +#include "chrome/browser/browser_process.h" +#include "chrome/browser/browser_process_platform_part_chromeos.h" +#include "chrome/browser/chromeos/policy/browser_policy_connector_chromeos.h" +#include "chrome/browser/chromeos/policy/cloud_external_data_manager_base_test_util.h" +#include "chrome/browser/chromeos/policy/device_cloud_policy_store_chromeos.h" +#include "chrome/browser/chromeos/policy/device_policy_builder.h" +#include "chrome/browser/chromeos/policy/device_policy_cros_browser_test.h" +#include "chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.h" +#include "chrome/common/chrome_features.h" +#include "chrome/test/base/in_process_browser_test.h" +#include "components/policy/core/common/external_data_fetcher.h" +#include "components/policy/core/common/policy_map.h" +#include "components/policy/core/common/policy_namespace.h" +#include "components/policy/core/common/policy_service.h" +#include "components/policy/policy_constants.h" +#include "net/test/embedded_test_server/embedded_test_server.h" +#include "testing/gtest/include/gtest/gtest.h" + +namespace policy { + +// Class used to test DeviceWilcoDtcConfigurationExternalPolicyHandler depending +// on the feature flag. +class DeviceWilcoDtcConfigurationExternalPolicyHandlerTest + : public DevicePolicyCrosBrowserTest, + public ::testing::WithParamInterface<bool> { + public: + DeviceWilcoDtcConfigurationExternalPolicyHandlerTest() { + feature_list_.InitWithFeatureState(::features::kWilcoDtc, + IsWilcoDtcFeatureEnabled()); + } + ~DeviceWilcoDtcConfigurationExternalPolicyHandlerTest() override = default; + + protected: + void SetUpOnMainThread() override { + ASSERT_TRUE(embedded_test_server()->Start()); + DevicePolicyCrosBrowserTest::SetUpOnMainThread(); + + policy_change_waiting_run_loop_ = std::make_unique<base::RunLoop>(); + + BrowserPolicyConnectorChromeOS* policy_connector = + g_browser_process->platform_part()->browser_policy_connector_chromeos(); + ASSERT_TRUE(policy_connector); + policy_service_ = policy_connector->GetPolicyService(); + ASSERT_TRUE( + policy_service_->IsInitializationComplete(POLICY_DOMAIN_CHROME)); + policy_change_registrar_ = std::make_unique<PolicyChangeRegistrar>( + policy_service_, PolicyNamespace(POLICY_DOMAIN_CHROME, std::string())); + policy_change_registrar_->Observe( + policy::key::kDeviceWilcoDtcConfiguration, + base::BindRepeating( + &DeviceWilcoDtcConfigurationExternalPolicyHandlerTest :: + PolicyChangedCallback, + base::Unretained(this))); + } + + void TearDownOnMainThread() override { + policy_change_registrar_.reset(); + DevicePolicyCrosBrowserTest::TearDownOnMainThread(); + } + + bool IsWilcoDtcFeatureEnabled() { return GetParam(); } + + void SetDeviceWilcoDtcConfigurationExternalData(const std::string& policy) { + device_policy() + ->payload() + .mutable_device_wilco_dtc_configuration() + ->set_device_wilco_dtc_configuration(policy); + RefreshDevicePolicy(); + WaitUntilPolicyChanged(); + } + + void FetchExternalData() { + const PolicyMap& policies = policy_service_->GetPolicies( + PolicyNamespace(POLICY_DOMAIN_CHROME, std::string())); + const PolicyMap::Entry* policy_entry = + policies.Get(policy::key::kDeviceWilcoDtcConfiguration); + EXPECT_TRUE(policy_entry); + EXPECT_TRUE(policy_entry->external_data_fetcher); + + base::RunLoop run_loop; + std::unique_ptr<std::string> fetched_external_data; + base::FilePath file_path; + policy_entry->external_data_fetcher->Fetch(base::BindOnce( + [](base::OnceClosure quit_closure, std::string* external_data, + std::unique_ptr<std::string> data, const base::FilePath& path) { + *external_data = (data ? *data : ""); + std::move(quit_closure).Run(); + }, + run_loop.QuitClosure(), &external_data_)); + run_loop.Run(); + } + + const std::string& external_data() { return external_data_; } + + private: + void PolicyChangedCallback(const base::Value* old_value, + const base::Value* new_value) { + policy_change_waiting_run_loop_->Quit(); + } + + void WaitUntilPolicyChanged() { + policy_change_waiting_run_loop_->Run(); + policy_change_waiting_run_loop_ = std::make_unique<base::RunLoop>(); + } + + base::test::ScopedFeatureList feature_list_; + std::unique_ptr<base::RunLoop> policy_change_waiting_run_loop_; + PolicyService* policy_service_ = nullptr; // owned by BrowserPolicyConnector. + std::unique_ptr<PolicyChangeRegistrar> policy_change_registrar_; + std::string external_data_; +}; + +// Test that nothing crashes and WilcoDtcConfiguration is successfully passed +// to WilcoDtcSupportdManager if the feature is enabled. +IN_PROC_BROWSER_TEST_P(DeviceWilcoDtcConfigurationExternalPolicyHandlerTest, + FetchExternalData) { + EXPECT_EQ(IsWilcoDtcFeatureEnabled(), + chromeos::WilcoDtcSupportdManager::Get() != nullptr); + SetDeviceWilcoDtcConfigurationExternalData(test::ConstructExternalDataPolicy( + *embedded_test_server(), "policy/wilco_dtc_configuration.json")); + FetchExternalData(); + if (IsWilcoDtcFeatureEnabled()) { + EXPECT_EQ(external_data(), chromeos::WilcoDtcSupportdManager::Get() + ->GetConfigurationDataForTesting()); + } +} + +INSTANTIATE_TEST_SUITE_P(, + DeviceWilcoDtcConfigurationExternalPolicyHandlerTest, + testing::Bool()); +} // namespace policy
diff --git a/chrome/browser/chromeos/policy/system_log_uploader.cc b/chrome/browser/chromeos/policy/system_log_uploader.cc index 9e06dd7e..df74942 100644 --- a/chrome/browser/chromeos/policy/system_log_uploader.cc +++ b/chrome/browser/chromeos/policy/system_log_uploader.cc
@@ -26,6 +26,7 @@ #include "chrome/browser/profiles/profile_manager.h" #include "chrome/common/chrome_features.h" #include "chrome/common/chrome_switches.h" +#include "chrome/common/extensions/extension_constants.h" #include "components/feedback/anonymizer_tool.h" #include "components/policy/core/browser/browser_policy_connector.h" #include "components/user_manager/user_manager.h" @@ -130,7 +131,8 @@ // as pairs (file name, data) and returns. Called on blocking thread. std::unique_ptr<SystemLogUploader::SystemLogs> ReadFiles() { auto system_logs = std::make_unique<SystemLogUploader::SystemLogs>(); - feedback::AnonymizerTool anonymizer; + feedback::AnonymizerTool anonymizer( + extension_misc::kBuiltInFirstPartyExtensionIds); for (const char* file_path : kSystemLogFileNames) { if (!base::PathExists(base::FilePath(file_path))) continue;
diff --git a/chrome/browser/chromeos/preferences.cc b/chrome/browser/chromeos/preferences.cc index d13a4b0..c4afed00 100644 --- a/chrome/browser/chromeos/preferences.cc +++ b/chrome/browser/chromeos/preferences.cc
@@ -197,12 +197,6 @@ hardware_keyboard_id = "xkb:us::eng"; // only for testing. } - registry->RegisterBooleanPref(ash::prefs::kKioskNextShellEligible, - /*default_value=*/false); - - registry->RegisterBooleanPref(ash::prefs::kKioskNextShellEnabled, - /*default_value=*/false, PrefRegistry::PUBLIC); - registry->RegisterBooleanPref(prefs::kPerformanceTracingEnabled, false); // This pref is device specific and must not be synced.
diff --git a/chrome/browser/chromeos/ui/idle_app_name_notification_view.cc b/chrome/browser/chromeos/ui/idle_app_name_notification_view.cc index f91bb3fd..c9990e06 100644 --- a/chrome/browser/chromeos/ui/idle_app_name_notification_view.cc +++ b/chrome/browser/chromeos/ui/idle_app_name_notification_view.cc
@@ -65,7 +65,7 @@ params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; params.ownership = views::Widget::InitParams::NATIVE_WIDGET_OWNS_WIDGET; params.accept_events = false; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.delegate = delegate; params.bounds = bounds; ash_util::SetupWidgetInitParamsForContainer(
diff --git a/chrome/browser/chromeos/ui/kiosk_external_update_notification.cc b/chrome/browser/chromeos/ui/kiosk_external_update_notification.cc index e05a253..3fc79b8 100644 --- a/chrome/browser/chromeos/ui/kiosk_external_update_notification.cc +++ b/chrome/browser/chromeos/ui/kiosk_external_update_notification.cc
@@ -133,7 +133,7 @@ params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; params.ownership = views::Widget::InitParams::NATIVE_WIDGET_OWNS_WIDGET; params.accept_events = false; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.delegate = view_; params.bounds = bounds; // The notification is shown on the primary display.
diff --git a/chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.cc b/chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.cc index bfcb571c..7e1e27e 100644 --- a/chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.cc +++ b/chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.cc
@@ -9,6 +9,7 @@ #include "base/bind.h" #include "base/bind_helpers.h" #include "base/logging.h" +#include "base/strings/string_util.h" #include "chrome/browser/browser_process.h" #include "chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_bridge.h" #include "chrome/browser/net/system_network_context_manager.h" @@ -126,6 +127,11 @@ wilco_dtc_supportd_mojo_proxy->NotifyConfigurationDataChanged(); } +const std::string& WilcoDtcSupportdManager::GetConfigurationDataForTesting() + const { + return configuration_data_ ? *configuration_data_ : base::EmptyString(); +} + void WilcoDtcSupportdManager::OnSessionStateChanged() { session_manager::SessionState session_state = session_manager::SessionManager::Get()->session_state();
diff --git a/chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.h b/chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.h index 547dd4d0..b3ffd4c 100644 --- a/chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.h +++ b/chrome/browser/chromeos/wilco_dtc_supportd/wilco_dtc_supportd_manager.h
@@ -51,6 +51,7 @@ // The nullptr should be passed to clear it. // Notifies the |wilco_dtc_supportd_bridge_| if it is created. void SetConfigurationData(std::unique_ptr<std::string> data); + const std::string& GetConfigurationDataForTesting() const; private: // session_manager::SessionManagerObserver override:
diff --git a/chrome/browser/extensions/api/feedback_private/chrome_feedback_private_delegate.cc b/chrome/browser/extensions/api/feedback_private/chrome_feedback_private_delegate.cc index 1b8de639..33f9d427 100644 --- a/chrome/browser/extensions/api/feedback_private/chrome_feedback_private_delegate.cc +++ b/chrome/browser/extensions/api/feedback_private/chrome_feedback_private_delegate.cc
@@ -33,8 +33,6 @@ #include "chrome/browser/chromeos/system_logs/single_log_file_log_source.h" #include "chrome/browser/extensions/component_loader.h" #include "chrome/browser/extensions/extension_service.h" -#include "chrome/browser/profiles/profile.h" -#include "chrome/browser/ui/ash/kiosk_next_shell_client.h" #include "components/feedback/feedback_util.h" #include "components/feedback/system_logs/system_logs_source.h" #include "extensions/browser/extension_system.h" @@ -200,8 +198,12 @@ constexpr bool scrub = true; if (system_logs::ContainsIwlwifiLogs(feedback_data->sys_info())) { + // TODO (jkardatzke): Modify this so that we are using the same instance of + // the anonymizer for the rest of the logs. + // We can pass null for the 1st party IDs since we are just anonymizing + // wifi data here. system_logs::SystemLogsFetcher* fetcher = - new system_logs::SystemLogsFetcher(scrub); + new system_logs::SystemLogsFetcher(scrub, nullptr); fetcher->AddSource(std::make_unique<system_logs::IwlwifiDumpLogSource>()); fetcher->Fetch(base::BindOnce(&OnFetchedExtraLogs, feedback_data, std::move(callback))); @@ -221,11 +223,6 @@ api::feedback_private::LandingPageType ChromeFeedbackPrivateDelegate::GetLandingPageType( const feedback::FeedbackData& feedback_data) const { - if (KioskNextShellClient::Get() && - KioskNextShellClient::Get()->has_launched()) { - return api::feedback_private::LANDING_PAGE_TYPE_NOLANDINGPAGE; - } - // Googlers using eve get a custom landing page. if (!feedback_util::IsGoogleEmail(feedback_data.user_email())) return api::feedback_private::LANDING_PAGE_TYPE_NORMAL;
diff --git a/chrome/browser/extensions/api/resources_private/resources_private_api.cc b/chrome/browser/extensions/api/resources_private/resources_private_api.cc index ab229e48..6c5eba3 100644 --- a/chrome/browser/extensions/api/resources_private/resources_private_api.cc +++ b/chrome/browser/extensions/api/resources_private/resources_private_api.cc
@@ -20,7 +20,10 @@ #if BUILDFLAG(ENABLE_PDF) #include "pdf/pdf_features.h" -#endif +#if defined(OS_CHROMEOS) +#include "chrome/browser/chromeos/login/ui/login_display_host.h" +#endif // defined(OS_CHROMEOS) +#endif // BUILDFLAG(ENABLE_PDF) #if BUILDFLAG(ENABLE_PRINT_PREVIEW) #include "chrome/common/chrome_features.h" @@ -125,7 +128,14 @@ dict->SetKey("pdfAnnotationsEnabled", base::Value(base::FeatureList::IsEnabled( chrome_pdf::features::kPDFAnnotations))); -#endif + + bool enable_printing = true; +#if defined(OS_CHROMEOS) + // For Chrome OS, enable printing only if we are not at OOBE. + enable_printing = !chromeos::LoginDisplayHost::default_host(); +#endif // defined(OS_CHROMEOS) + dict->SetKey("printingEnabled", base::Value(enable_printing)); +#endif // BUILDFLAG(ENABLE_PDF) #if BUILDFLAG(ENABLE_PRINT_PREVIEW) dict->SetKey("newPrintPreviewLayoutEnabled", base::Value(base::FeatureList::IsEnabled(
diff --git a/chrome/browser/extensions/api/tabs/app_base_window.cc b/chrome/browser/extensions/api/tabs/app_base_window.cc index 324756e..fd82bdb 100644 --- a/chrome/browser/extensions/api/tabs/app_base_window.cc +++ b/chrome/browser/extensions/api/tabs/app_base_window.cc
@@ -105,12 +105,12 @@ GetBaseWindow()->FlashFrame(flash); } -bool AppBaseWindow::IsAlwaysOnTop() const { - return GetBaseWindow()->IsAlwaysOnTop(); +ui::ZOrderLevel AppBaseWindow::GetZOrderLevel() const { + return GetBaseWindow()->GetZOrderLevel(); } -void AppBaseWindow::SetAlwaysOnTop(bool always_on_top) { - GetBaseWindow()->SetAlwaysOnTop(always_on_top); +void AppBaseWindow::SetZOrderLevel(ui::ZOrderLevel level) { + GetBaseWindow()->SetZOrderLevel(level); } NativeAppWindow* AppBaseWindow::GetBaseWindow() const {
diff --git a/chrome/browser/extensions/api/tabs/app_base_window.h b/chrome/browser/extensions/api/tabs/app_base_window.h index d9ccfb5..7e17b85 100644 --- a/chrome/browser/extensions/api/tabs/app_base_window.h +++ b/chrome/browser/extensions/api/tabs/app_base_window.h
@@ -45,8 +45,8 @@ void Restore() override; void SetBounds(const gfx::Rect& bounds) override; void FlashFrame(bool flash) override; - bool IsAlwaysOnTop() const override; - void SetAlwaysOnTop(bool always_on_top) override; + ui::ZOrderLevel GetZOrderLevel() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; NativeAppWindow* GetBaseWindow() const;
diff --git a/chrome/browser/extensions/api/web_navigation/web_navigation_apitest.cc b/chrome/browser/extensions/api/web_navigation/web_navigation_apitest.cc index 887e936..b06f9750 100644 --- a/chrome/browser/extensions/api/web_navigation/web_navigation_apitest.cc +++ b/chrome/browser/extensions/api/web_navigation/web_navigation_apitest.cc
@@ -19,7 +19,6 @@ #include "chrome/app/chrome_command_ids.h" #include "chrome/browser/browser_process.h" #include "chrome/browser/chrome_browser_main.h" -#include "chrome/browser/chrome_notification_types.h" #include "chrome/browser/download/download_browsertest.h" #include "chrome/browser/download/download_prefs.h" #include "chrome/browser/extensions/api/web_navigation/web_navigation_api.h" @@ -67,39 +66,36 @@ // |script| in the last committed RVH and resumes the load when a URL ending in // |until_url_suffix| commits. This class expects |script| to trigger the load // of an URL ending in |until_url_suffix|. -class DelayLoadStartAndExecuteJavascript - : public content::NotificationObserver, - public content::WebContentsObserver { +class DelayLoadStartAndExecuteJavascript : public TabStripModelObserver, + public content::WebContentsObserver { public: - DelayLoadStartAndExecuteJavascript( - const GURL& delay_url, - const std::string& script, - const std::string& until_url_suffix) + DelayLoadStartAndExecuteJavascript(Browser* browser, + const GURL& delay_url, + const std::string& script, + const std::string& until_url_suffix) : content::WebContentsObserver(), delay_url_(delay_url), until_url_suffix_(until_url_suffix), - script_(script), - has_user_gesture_(false), - script_was_executed_(false), - rfh_(nullptr) { - registrar_.Add(this, - chrome::NOTIFICATION_TAB_ADDED, - content::NotificationService::AllSources()); + script_(script) { + tab_strip_observer_.Add(browser->tab_strip_model()); } + ~DelayLoadStartAndExecuteJavascript() override {} - void Observe(int type, - const content::NotificationSource& source, - const content::NotificationDetails& details) override { - if (type != chrome::NOTIFICATION_TAB_ADDED) { - NOTREACHED(); + // TabStripModelObserver: + void OnTabStripModelChanged( + TabStripModel* tab_strip_model, + const TabStripModelChange& change, + const TabStripSelectionChange& selection) override { + if (change.type() != TabStripModelChange::kInserted) return; - } + content::WebContentsObserver::Observe( - content::Details<content::WebContents>(details).ptr()); - registrar_.RemoveAll(); + change.GetInsert()->contents[0].contents); + tab_strip_observer_.RemoveAll(); } + // WebContentsObserver: void DidStartNavigation( content::NavigationHandle* navigation_handle) override { if (navigation_handle->GetURL() != delay_url_ || !rfh_) @@ -128,7 +124,7 @@ if (script_was_executed_ && base::EndsWith(navigation_handle->GetURL().spec(), until_url_suffix_, base::CompareCase::SENSITIVE)) { - content::WebContentsObserver::Observe(NULL); + content::WebContentsObserver::Observe(nullptr); if (throttle_) throttle_->Unblock(); } @@ -168,16 +164,16 @@ bool throttled_ = false; }; - content::NotificationRegistrar registrar_; - base::WeakPtr<WillStartRequestObserverThrottle> throttle_; + ScopedObserver<TabStripModel, TabStripModelObserver> tab_strip_observer_{ + this}; GURL delay_url_; std::string until_url_suffix_; std::string script_; - bool has_user_gesture_; - bool script_was_executed_; - content::RenderFrameHost* rfh_; + bool has_user_gesture_ = false; + bool script_was_executed_ = false; + content::RenderFrameHost* rfh_ = nullptr; DISALLOW_COPY_AND_ASSIGN(DelayLoadStartAndExecuteJavascript); }; @@ -499,13 +495,11 @@ // See crossProcess/d.html. DelayLoadStartAndExecuteJavascript call_script( - embedded_test_server()->GetURL("/test1"), - "navigate2()", + browser(), embedded_test_server()->GetURL("/test1"), "navigate2()", "empty.html"); DelayLoadStartAndExecuteJavascript call_script_user_gesture( - embedded_test_server()->GetURL("/test2"), - "navigate2()", + browser(), embedded_test_server()->GetURL("/test2"), "navigate2()", "empty.html"); call_script_user_gesture.set_has_user_gesture(true); @@ -518,14 +512,12 @@ // See crossProcessFragment/f.html. DelayLoadStartAndExecuteJavascript call_script3( - embedded_test_server()->GetURL("/test3"), - "updateFragment()", + browser(), embedded_test_server()->GetURL("/test3"), "updateFragment()", base::StringPrintf("f.html?%u#foo", embedded_test_server()->port())); // See crossProcessFragment/g.html. DelayLoadStartAndExecuteJavascript call_script4( - embedded_test_server()->GetURL("/test4"), - "updateFragment()", + browser(), embedded_test_server()->GetURL("/test4"), "updateFragment()", base::StringPrintf("g.html?%u#foo", embedded_test_server()->port())); ASSERT_TRUE(RunExtensionTest("webnavigation/crossProcessFragment")) @@ -537,20 +529,17 @@ // See crossProcessHistory/e.html. DelayLoadStartAndExecuteJavascript call_script2( - embedded_test_server()->GetURL("/test2"), - "updateHistory()", + browser(), embedded_test_server()->GetURL("/test2"), "updateHistory()", "empty.html"); // See crossProcessHistory/h.html. DelayLoadStartAndExecuteJavascript call_script5( - embedded_test_server()->GetURL("/test5"), - "updateHistory()", + browser(), embedded_test_server()->GetURL("/test5"), "updateHistory()", "empty.html"); // See crossProcessHistory/i.html. DelayLoadStartAndExecuteJavascript call_script6( - embedded_test_server()->GetURL("/test6"), - "updateHistory()", + browser(), embedded_test_server()->GetURL("/test6"), "updateHistory()", "empty.html"); ASSERT_TRUE(RunExtensionTest("webnavigation/crossProcessHistory"))
diff --git a/chrome/browser/extensions/extension_tab_util.cc b/chrome/browser/extensions/extension_tab_util.cc index 848a6d9..eb78de66 100644 --- a/chrome/browser/extensions/extension_tab_util.cc +++ b/chrome/browser/extensions/extension_tab_util.cc
@@ -443,7 +443,9 @@ result->SetBoolean(tabs_constants::kFocusedKey, window->IsActive()); const Profile* profile = browser.profile(); result->SetBoolean(tabs_constants::kIncognitoKey, profile->IsOffTheRecord()); - result->SetBoolean(tabs_constants::kAlwaysOnTopKey, window->IsAlwaysOnTop()); + result->SetBoolean( + tabs_constants::kAlwaysOnTopKey, + window->GetZOrderLevel() == ui::ZOrderLevel::kFloatingWindow); std::string window_state; if (window->IsMinimized()) {
diff --git a/chrome/browser/favicon/OWNERS b/chrome/browser/favicon/OWNERS index c888e8735..77ebe9f 100644 --- a/chrome/browser/favicon/OWNERS +++ b/chrome/browser/favicon/OWNERS
@@ -4,3 +4,4 @@ # Temporary owner, for refactoring changes only. caitkp@chromium.org +# COMPONENT: UI>Browser>History
diff --git a/chrome/browser/feedback/system_logs/about_system_logs_fetcher.cc b/chrome/browser/feedback/system_logs/about_system_logs_fetcher.cc index 5cadd2e..c5d9aea 100644 --- a/chrome/browser/feedback/system_logs/about_system_logs_fetcher.cc +++ b/chrome/browser/feedback/system_logs/about_system_logs_fetcher.cc
@@ -21,7 +21,8 @@ SystemLogsFetcher* BuildAboutSystemLogsFetcher() { const bool scrub_data = false; - SystemLogsFetcher* fetcher = new SystemLogsFetcher(scrub_data); + // We aren't anonymizing, so we can pass null for the 1st party IDs. + SystemLogsFetcher* fetcher = new SystemLogsFetcher(scrub_data, nullptr); fetcher->AddSource(std::make_unique<ChromeInternalLogSource>()); fetcher->AddSource(std::make_unique<MemoryDetailsLogSource>());
diff --git a/chrome/browser/feedback/system_logs/chrome_system_logs_fetcher.cc b/chrome/browser/feedback/system_logs/chrome_system_logs_fetcher.cc index d00e945..6d2fcdd 100644 --- a/chrome/browser/feedback/system_logs/chrome_system_logs_fetcher.cc +++ b/chrome/browser/feedback/system_logs/chrome_system_logs_fetcher.cc
@@ -8,6 +8,7 @@ #include "chrome/browser/feedback/system_logs/log_sources/chrome_internal_log_source.h" #include "chrome/browser/feedback/system_logs/log_sources/crash_ids_source.h" #include "chrome/browser/feedback/system_logs/log_sources/memory_details_log_source.h" +#include "chrome/common/extensions/extension_constants.h" #include "components/feedback/system_logs/system_logs_fetcher.h" #if defined(OS_CHROMEOS) @@ -23,7 +24,8 @@ SystemLogsFetcher* BuildChromeSystemLogsFetcher() { const bool scrub_data = true; - SystemLogsFetcher* fetcher = new SystemLogsFetcher(scrub_data); + SystemLogsFetcher* fetcher = new SystemLogsFetcher( + scrub_data, extension_misc::kBuiltInFirstPartyExtensionIds); fetcher->AddSource(std::make_unique<ChromeInternalLogSource>()); fetcher->AddSource(std::make_unique<CrashIdsSource>());
diff --git a/chrome/browser/flag-metadata.json b/chrome/browser/flag-metadata.json index 5d395b1..c645382c 100644 --- a/chrome/browser/flag-metadata.json +++ b/chrome/browser/flag-metadata.json
@@ -2953,11 +2953,6 @@ "expiry_milestone": 80 }, { - "name": "sync-USS-autofill-wallet-metadata", - "owners": [ "jkrcal", "//components/sync/OWNERS" ], - "expiry_milestone": 76 - }, - { "name": "sync-support-secondary-account", "owners": [ "treib", "//components/sync/OWNERS" ], "expiry_milestone": 76
diff --git a/chrome/browser/flag_descriptions.cc b/chrome/browser/flag_descriptions.cc index 74266ecf..909c321 100644 --- a/chrome/browser/flag_descriptions.cc +++ b/chrome/browser/flag_descriptions.cc
@@ -1826,11 +1826,6 @@ "a signed-in account that has not been chosen as Chrome's primary account. " "This only has an effect if sync-standalone-transport is also enabled."; -const char kSyncUSSAutofillWalletMetadataName[] = - "Enable USS for autofill wallet metadata"; -const char kSyncUSSAutofillWalletMetadataDescription[] = - "Enables the new implementation of autofill walet metadata sync"; - const char kSyncSandboxName[] = "Use Chrome Sync sandbox"; const char kSyncSandboxDescription[] = "Connects to the testing server for Chrome Sync.";
diff --git a/chrome/browser/flag_descriptions.h b/chrome/browser/flag_descriptions.h index acf6e01..7393d1f0 100644 --- a/chrome/browser/flag_descriptions.h +++ b/chrome/browser/flag_descriptions.h
@@ -1088,9 +1088,6 @@ extern const char kSyncSupportSecondaryAccountName[]; extern const char kSyncSupportSecondaryAccountDescription[]; -extern const char kSyncUSSAutofillWalletMetadataName[]; -extern const char kSyncUSSAutofillWalletMetadataDescription[]; - extern const char kTabEngagementReportingName[]; extern const char kTabEngagementReportingDescription[];
diff --git a/chrome/browser/history/OWNERS b/chrome/browser/history/OWNERS index cdbd5d8..6f0ac8e 100644 --- a/chrome/browser/history/OWNERS +++ b/chrome/browser/history/OWNERS
@@ -3,3 +3,4 @@ per-file thumbnail_database.*=pkotwicz@chromium.org per-file download_database.*=benjhayden@chromium.org +# COMPONENT: UI>Browser>History
diff --git a/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.cc b/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.cc index 2377d7d..ec4b4662 100644 --- a/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.cc +++ b/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.cc
@@ -7,6 +7,7 @@ #include <errno.h> #include <utility> +#include "base/android/build_info.h" #include "base/android/jni_android.h" #include "base/android/jni_array.h" #include "base/android/jni_string.h" @@ -17,16 +18,16 @@ #include "base/strings/utf_string_conversions.h" #include "base/task_runner_util.h" #include "chrome/android/chrome_jni_headers/OfflinePageArchivePublisherBridge_jni.h" +#include "chrome/browser/offline_pages/android/offline_page_bridge.h" #include "components/offline_pages/core/archive_manager.h" #include "components/offline_pages/core/model/offline_page_model_utils.h" #include "components/offline_pages/core/offline_store_utils.h" -using base::android::ScopedJavaLocalRef; - namespace offline_pages { namespace { +using base::android::ScopedJavaLocalRef; using offline_pages::SavePageResult; // Creates a singleton Delegate. @@ -35,15 +36,25 @@ return &delegate; } +bool ShouldUseDownloadsCollection() { + return base::android::BuildInfo::GetInstance()->is_at_least_q(); +} + // Helper function to do the move and register synchronously. Make sure this is // called from a background thread. PublishArchiveResult MoveAndRegisterArchive( const offline_pages::OfflinePageItem& offline_page, const base::FilePath& publish_directory, OfflinePageArchivePublisherImpl::Delegate* delegate) { - PublishArchiveResult archive_result; + // For Android Q+, use the downloads collection rather than DownloadManager. + if (ShouldUseDownloadsCollection()) { + return delegate->AddCompletedDownload(offline_page); + } + + OfflinePageItem published_page(offline_page); + // Calculate the new file name. - base::FilePath new_file_path = + published_page.file_path = offline_pages::model_utils::GenerateUniqueFilenameForOfflinePage( offline_page.title, offline_page.url, publish_directory); @@ -54,9 +65,8 @@ } // Move the file. - bool moved = base::Move(offline_page.file_path, new_file_path); + bool moved = base::Move(offline_page.file_path, published_page.file_path); if (!moved) { - archive_result.move_result = SavePageResult::FILE_MOVE_FAILED; DVPLOG(0) << "OfflinePage publishing file move failure " << __func__; if (!base::PathExists(offline_page.file_path)) { @@ -67,38 +77,26 @@ DVLOG(0) << "Target directory does not exist, " << publish_directory << " " << __func__; } - return archive_result; + return PublishArchiveResult::Failure(SavePageResult::FILE_MOVE_FAILED); } // Tell the download manager about our file, get back an id. if (!delegate->IsDownloadManagerInstalled()) { - archive_result.move_result = SavePageResult::ADD_TO_DOWNLOAD_MANAGER_FAILED; - return archive_result; + return PublishArchiveResult::Failure( + SavePageResult::ADD_TO_DOWNLOAD_MANAGER_FAILED); } - // TODO(petewil): Handle empty page title. - std::string page_title = base::UTF16ToUTF8(offline_page.title); - // We use the title for a description, since the add to the download manager - // fails without a description, and we don't have anything better to use. - int64_t download_id = delegate->AddCompletedDownload( - page_title, page_title, - offline_pages::store_utils::ToDatabaseFilePath(new_file_path), - offline_page.file_size, offline_page.url.spec(), std::string()); - if (download_id == 0LL) { - archive_result.move_result = SavePageResult::ADD_TO_DOWNLOAD_MANAGER_FAILED; - return archive_result; - } - - // Put results into the result object. - archive_result.move_result = SavePageResult::SUCCESS; - archive_result.new_file_path = new_file_path; - archive_result.download_id = download_id; - - return archive_result; + return delegate->AddCompletedDownload(published_page); } } // namespace +// static +PublishArchiveResult PublishArchiveResult::Failure( + SavePageResult save_page_result) { + return {save_page_result, PublishedArchiveId()}; +} + OfflinePageArchivePublisherImpl::OfflinePageArchivePublisherImpl( ArchiveManager* archive_manager) : archive_manager_(archive_manager), delegate_(GetDefaultDelegate()) {} @@ -122,7 +120,18 @@ } void OfflinePageArchivePublisherImpl::UnpublishArchives( - const std::vector<int64_t>& download_manager_ids) const { + const std::vector<PublishedArchiveId>& publish_ids) const { + std::vector<int64_t> download_manager_ids; + + for (auto& id : publish_ids) { + if (id.download_id == kArchivePublishedWithoutDownloadId) { + DCHECK(id.new_file_path.IsContentUri()); + base::DeleteFile(id.new_file_path, false); + } else if (id.download_id != kArchiveNotPublished) { + download_manager_ids.push_back(id.download_id); + } + } + delegate_->Remove(download_manager_ids); } @@ -136,28 +145,51 @@ return is_installed; } -int64_t OfflinePageArchivePublisherImpl::Delegate::AddCompletedDownload( - const std::string& title, - const std::string& description, - const std::string& path, - int64_t length, - const std::string& uri, - const std::string& referer) { +PublishArchiveResult +OfflinePageArchivePublisherImpl::Delegate::AddCompletedDownload( + const OfflinePageItem& page) { JNIEnv* env = base::android::AttachCurrentThread(); + + if (ShouldUseDownloadsCollection()) { + base::FilePath new_file_path = base::FilePath(ConvertJavaStringToUTF8( + Java_OfflinePageArchivePublisherBridge_publishArchiveToDownloadsCollection( + env, + android::OfflinePageBridge::ConvertToJavaOfflinePage(env, page)))); + + if (new_file_path.empty()) + return PublishArchiveResult::Failure(SavePageResult::FILE_MOVE_FAILED); + + return {SavePageResult::SUCCESS, + {kArchivePublishedWithoutDownloadId, new_file_path}}; + } + + // TODO(petewil): Handle empty page title. + std::string page_title = base::UTF16ToUTF8(page.title); + // Convert strings to jstring references. ScopedJavaLocalRef<jstring> j_title = - base::android::ConvertUTF8ToJavaString(env, title); + base::android::ConvertUTF8ToJavaString(env, page_title); + // We use the title for a description, since the add to the download manager + // fails without a description, and we don't have anything better to use. ScopedJavaLocalRef<jstring> j_description = - base::android::ConvertUTF8ToJavaString(env, description); - ScopedJavaLocalRef<jstring> j_path = - base::android::ConvertUTF8ToJavaString(env, path); + base::android::ConvertUTF8ToJavaString(env, page_title); + ScopedJavaLocalRef<jstring> j_path = base::android::ConvertUTF8ToJavaString( + env, offline_pages::store_utils::ToDatabaseFilePath(page.file_path)); ScopedJavaLocalRef<jstring> j_uri = - base::android::ConvertUTF8ToJavaString(env, uri); + base::android::ConvertUTF8ToJavaString(env, page.url.spec()); ScopedJavaLocalRef<jstring> j_referer = - base::android::ConvertUTF8ToJavaString(env, referer); + base::android::ConvertUTF8ToJavaString(env, std::string()); - return Java_OfflinePageArchivePublisherBridge_addCompletedDownload( - env, j_title, j_description, j_path, length, j_uri, j_referer); + int64_t download_id = + Java_OfflinePageArchivePublisherBridge_addCompletedDownload( + env, j_title, j_description, j_path, page.file_size, j_uri, + j_referer); + DCHECK_NE(download_id, kArchivePublishedWithoutDownloadId); + if (download_id == kArchiveNotPublished) + return PublishArchiveResult::Failure( + SavePageResult::ADD_TO_DOWNLOAD_MANAGER_FAILED); + + return {SavePageResult::SUCCESS, {download_id, page.file_path}}; } int OfflinePageArchivePublisherImpl::Delegate::Remove(
diff --git a/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.h b/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.h index 40fe4fe..0740e4fe 100644 --- a/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.h +++ b/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.h
@@ -31,18 +31,11 @@ // Returns true if a system download manager is available on this platform. virtual bool IsDownloadManagerInstalled(); - // Returns the download manager ID of the download, which we will place in - // the offline pages database as part of the offline page item. - // TODO(petewil): it might make sense to move all these params into a - // struct. - virtual int64_t AddCompletedDownload(const std::string& title, - const std::string& description, - const std::string& path, - int64_t length, - const std::string& uri, - const std::string& referer); + // Adds the archive to downloads. + virtual PublishArchiveResult AddCompletedDownload( + const OfflinePageItem& page); - // Returns the number of pages removed. + // Removes pages from downloads, returning the number of pages removed. virtual int Remove( const std::vector<int64_t>& android_download_manager_ids); @@ -63,7 +56,7 @@ PublishArchiveDoneCallback publish_done_callback) const override; void UnpublishArchives( - const std::vector<int64_t>& download_manager_ids) const override; + const std::vector<PublishedArchiveId>& publish_ids) const override; private: ArchiveManager* archive_manager_;
diff --git a/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl_unittest.cc b/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl_unittest.cc index 66f829e..56089bc 100644 --- a/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl_unittest.cc +++ b/chrome/browser/offline_pages/android/offline_page_archive_publisher_impl_unittest.cc
@@ -4,6 +4,7 @@ #include "chrome/browser/offline_pages/android/offline_page_archive_publisher_impl.h" +#include "base/android/build_info.h" #include "base/bind.h" #include "base/files/file_path.h" #include "base/files/file_util.h" @@ -86,14 +87,11 @@ : download_id_(id_to_use), last_removed_id_(0), installed_(installed) {} bool IsDownloadManagerInstalled() override { return installed_; } - int64_t AddCompletedDownload(const std::string& title, - const std::string& description, - const std::string& path, - int64_t length, - const std::string& uri, - const std::string& referer) override { - return download_id_; + PublishArchiveResult AddCompletedDownload( + const OfflinePageItem& page) override { + return {SavePageResult::SUCCESS, {download_id_, page.file_path}}; } + int Remove( const std::vector<int64_t>& android_download_manager_ids) override { int count = static_cast<int>(android_download_manager_ids.size()); @@ -144,16 +142,26 @@ PumpLoop(); EXPECT_EQ(SavePageResult::SUCCESS, publish_archive_result().move_result); - EXPECT_EQ(kDownloadId, publish_archive_result().download_id); - // Check there is a file in the new location. - EXPECT_TRUE(public_archive_dir_path().IsParent( - publish_archive_result().new_file_path)); - EXPECT_TRUE(base::PathExists(publish_archive_result().new_file_path)); - // Check there is no longer a file in the old location. - EXPECT_FALSE(base::PathExists(old_file_path)); + EXPECT_EQ(kDownloadId, publish_archive_result().id.download_id); + + // The file move should not happen on Android Q and later. + if (!base::android::BuildInfo::GetInstance()->is_at_least_q()) { + // Check there is a file in the new location. + EXPECT_TRUE(public_archive_dir_path().IsParent( + publish_archive_result().id.new_file_path)); + EXPECT_TRUE(base::PathExists(publish_archive_result().id.new_file_path)); + // Check there is no longer a file in the old location. + EXPECT_FALSE(base::PathExists(old_file_path)); + } else { + EXPECT_FALSE(public_archive_dir_path().IsParent( + publish_archive_result().id.new_file_path)); + // new_file_path should be the same as the page's file path. + EXPECT_TRUE(base::PathExists(publish_archive_result().id.new_file_path)); + EXPECT_TRUE(base::PathExists(old_file_path)); + } } -TEST_F(OfflinePageArchivePublisherImplTest, UnpublishArchive) { +TEST_F(OfflinePageArchivePublisherImplTest, UnpublishArchives) { ArchiveManager archive_manager(temporary_dir_path(), private_archive_dir_path(), public_archive_dir_path(), task_runner()); @@ -162,7 +170,14 @@ OfflinePageArchivePublisherImpl publisher(&archive_manager); publisher.SetDelegateForTesting(&delegate); - std::vector<int64_t> ids_to_remove = {kDownloadId}; + // This needs to be very close to a real content URI or DeleteContentUri will + // throw an exception. + base::FilePath test_content_uri = + base::FilePath("content://downloads/download/43"); + + std::vector<PublishedArchiveId> ids_to_remove{ + {kDownloadId, base::FilePath()}, + {kArchivePublishedWithoutDownloadId, test_content_uri}}; publisher.UnpublishArchives(std::move(ids_to_remove)); EXPECT_EQ(kDownloadId, delegate.last_removed_id());
diff --git a/chrome/browser/password_manager/password_manager_browsertest.cc b/chrome/browser/password_manager/password_manager_browsertest.cc index c5a7b464..b8ee315 100644 --- a/chrome/browser/password_manager/password_manager_browsertest.cc +++ b/chrome/browser/password_manager/password_manager_browsertest.cc
@@ -1455,17 +1455,13 @@ .get()); ASSERT_TRUE(password_store->IsEmpty()); - // Navigate to a page requiring HTTP auth. Wait for the tab to get the correct - // WebContents, but don't wait for navigation, which only finishes after - // authentication. - ui_test_utils::NavigateToURLWithDisposition( - browser(), http_test_server.GetURL("/basic_auth"), - WindowOpenDisposition::CURRENT_TAB, ui_test_utils::BROWSER_TEST_NONE); - content::NavigationController* nav_controller = &WebContents()->GetController(); - NavigationObserver nav_observer(WebContents()); WindowedAuthNeededObserver auth_needed_observer(nav_controller); + + // Navigate to a page requiring HTTP auth. + ui_test_utils::NavigateToURL(browser(), + http_test_server.GetURL("/basic_auth")); auth_needed_observer.Wait(); WindowedAuthSuppliedObserver auth_supplied_observer(nav_controller); @@ -1473,6 +1469,7 @@ ASSERT_EQ(1u, login_observer.handlers().size()); LoginHandler* handler = *login_observer.handlers().begin(); ASSERT_TRUE(handler); + NavigationObserver nav_observer(WebContents()); // Any username/password will work. handler->SetAuth(base::UTF8ToUTF16("user"), base::UTF8ToUTF16("pwd")); auth_supplied_observer.Wait(); @@ -2953,9 +2950,8 @@ content::NavigationController* nav_controller = &WebContents()->GetController(); WindowedAuthNeededObserver auth_needed_observer(nav_controller); - ui_test_utils::NavigateToURLWithDisposition( - browser(), http_test_server.GetURL("/basic_auth"), - WindowOpenDisposition::CURRENT_TAB, ui_test_utils::BROWSER_TEST_NONE); + ui_test_utils::NavigateToURL(browser(), + http_test_server.GetURL("/basic_auth")); auth_needed_observer.Wait(); // The auth dialog caused a query to PasswordStore, make sure it was @@ -2984,9 +2980,7 @@ content::NavigationController* controller = &WebContents()->GetController(); WindowedAuthNeededObserver auth_needed_waiter(controller); - ui_test_utils::NavigateToURLWithDisposition( - browser(), test_page, WindowOpenDisposition::CURRENT_TAB, - ui_test_utils::BROWSER_TEST_NONE); + ui_test_utils::NavigateToURL(browser(), test_page); auth_needed_waiter.Wait(); BubbleObserver(WebContents()).WaitForManagementState(); @@ -3676,19 +3670,16 @@ // should not work. ui_test_utils::NavigateToURL(browser(), GURL("about:blank")); - // Navigate to a page requiring HTTP auth. Wait for the tab to get the - // correct WebContents, but don't wait for navigation, which only finishes - // after authentication. - ui_test_utils::NavigateToURLWithDisposition( - browser(), http_test_server.GetURL("/basic_auth"), - WindowOpenDisposition::CURRENT_TAB, ui_test_utils::BROWSER_TEST_NONE); - content::NavigationController* nav_controller = &WebContents()->GetController(); - NavigationObserver nav_observer(WebContents()); WindowedAuthNeededObserver auth_needed_observer(nav_controller); + // Navigate to a page requiring HTTP auth + ui_test_utils::NavigateToURL(browser(), + http_test_server.GetURL("/basic_auth")); + auth_needed_observer.Wait(); + NavigationObserver nav_observer(WebContents()); WindowedAuthSuppliedObserver auth_supplied_observer(nav_controller); // Offer valid credentials on the auth challenge. ASSERT_EQ(1u, login_observer.handlers().size()); @@ -3752,19 +3743,15 @@ std::string path("/basic_auth"); if (is_realm_empty) path += "/empty_realm"; - // Navigate to a page requiring HTTP auth. Wait for the tab to get the - // correct WebContents, but don't wait for navigation, which only finishes - // after authentication. - ui_test_utils::NavigateToURLWithDisposition( - browser(), http_test_server.GetURL(path), - WindowOpenDisposition::CURRENT_TAB, ui_test_utils::BROWSER_TEST_NONE); content::NavigationController* nav_controller = &WebContents()->GetController(); - NavigationObserver nav_observer(WebContents()); WindowedAuthNeededObserver auth_needed_observer(nav_controller); + // Navigate to a page requiring HTTP auth. + ui_test_utils::NavigateToURL(browser(), http_test_server.GetURL(path)); auth_needed_observer.Wait(); + NavigationObserver nav_observer(WebContents()); WindowedAuthSuppliedObserver auth_supplied_observer(nav_controller); ASSERT_EQ(1u, login_observer.handlers().size());
diff --git a/chrome/browser/pdf/pdf_extension_test.cc b/chrome/browser/pdf/pdf_extension_test.cc index e6c11a7..e90d0c4 100644 --- a/chrome/browser/pdf/pdf_extension_test.cc +++ b/chrome/browser/pdf/pdf_extension_test.cc
@@ -683,9 +683,14 @@ IN_PROC_BROWSER_TEST_F(PDFAnnotationsTest, MAYBE_AnnotationsFeatureEnabled) { RunTestsInFile("annotations_feature_enabled_test.js", "test.pdf"); } + IN_PROC_BROWSER_TEST_F(PDFExtensionTest, AnnotationsFeatureDisabled) { RunTestsInFile("annotations_feature_disabled_test.js", "test.pdf"); } + +IN_PROC_BROWSER_TEST_F(PDFExtensionTest, Printing) { + RunTestsInFile("printing_icon_test.js", "test.pdf"); +} #endif // TODO(tsepez): See https://crbug.com/696650.
diff --git a/chrome/browser/prefs/browser_prefs.cc b/chrome/browser/prefs/browser_prefs.cc index 1b19c582..a7e8cbe 100644 --- a/chrome/browser/prefs/browser_prefs.cc +++ b/chrome/browser/prefs/browser_prefs.cc
@@ -51,6 +51,7 @@ #include "chrome/browser/prefs/session_startup_pref.h" #include "chrome/browser/previews/previews_lite_page_decider.h" #include "chrome/browser/previews/previews_offline_helper.h" +#include "chrome/browser/previews/previews_prober.h" #include "chrome/browser/profiles/chrome_version_service.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/profiles/profile_attributes_entry.h" @@ -730,6 +731,7 @@ PrefsTabHelper::RegisterProfilePrefs(registry, locale); PreviewsLitePageDecider::RegisterProfilePrefs(registry); PreviewsOfflineHelper::RegisterProfilePrefs(registry); + PreviewsProber::RegisterProfilePrefs(registry); Profile::RegisterProfilePrefs(registry); ProfileImpl::RegisterProfilePrefs(registry); ProfileNetworkContextService::RegisterProfilePrefs(registry);
diff --git a/chrome/browser/previews/previews_prober.cc b/chrome/browser/previews/previews_prober.cc index c68ce58a..62b7386 100644 --- a/chrome/browser/previews/previews_prober.cc +++ b/chrome/browser/previews/previews_prober.cc
@@ -15,6 +15,9 @@ #include "base/time/default_tick_clock.h" #include "build/build_config.h" #include "chrome/browser/previews/proto/previews_prober_cache_entry.pb.h" +#include "components/prefs/pref_registry_simple.h" +#include "components/prefs/pref_service.h" +#include "components/prefs/scoped_user_pref_update.h" #include "content/public/browser/browser_thread.h" #include "content/public/browser/network_service_instance.h" #include "net/base/load_flags.h" @@ -32,11 +35,19 @@ namespace { +const char kCachePrefKeyPrefix[] = "previews.prober.cache"; + std::string NameForClient(PreviewsProber::ClientName name) { switch (name) { case PreviewsProber::ClientName::kLitepages: return "litepages"; } + NOTREACHED(); + return std::string(); +} + +std::string PrefKeyForName(const std::string& name) { + return base::StringPrintf("%s.%s", kCachePrefKeyPrefix, name.c_str()); } std::string HttpMethodToString(PreviewsProber::HttpMethod http_method) { @@ -187,6 +198,7 @@ PreviewsProber::PreviewsProber( Delegate* delegate, scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, + PrefService* pref_service, const ClientName name, const GURL& url, const HttpMethod http_method, @@ -197,6 +209,7 @@ base::TimeDelta revalidate_cache_after) : PreviewsProber(delegate, url_loader_factory, + pref_service, name, url, http_method, @@ -211,6 +224,7 @@ PreviewsProber::PreviewsProber( Delegate* delegate, scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, + PrefService* pref_service, const ClientName name, const GURL& url, const HttpMethod http_method, @@ -223,6 +237,7 @@ const base::Clock* clock) : delegate_(delegate), name_(NameForClient(name)), + pref_key_(PrefKeyForName(NameForClient(name))), url_(url), http_method_(http_method), headers_(headers), @@ -237,8 +252,11 @@ clock_(clock), is_active_(false), network_connection_tracker_(nullptr), - url_loader_factory_(url_loader_factory) { + pref_service_(pref_service), + url_loader_factory_(url_loader_factory), + weak_factory_(this) { DCHECK(delegate_); + DCHECK(pref_service_); // The NetworkConnectionTracker can only be used directly on the UI thread. // Otherwise we use the cross-thread call. @@ -250,6 +268,8 @@ base::BindOnce(&PreviewsProber::AddSelfAsNetworkConnectionObserver, weak_factory_.GetWeakPtr())); } + cached_probe_results_ = + pref_service_->GetDictionary(pref_key_)->CreateDeepCopy(); } PreviewsProber::~PreviewsProber() { @@ -258,6 +278,15 @@ network_connection_tracker_->RemoveNetworkConnectionObserver(this); } +// static +void PreviewsProber::RegisterProfilePrefs(PrefRegistrySimple* registry) { + for (int i = 0; i <= static_cast<int>(PreviewsProber::ClientName::kMaxValue); + i++) { + registry->RegisterDictionaryPref(PrefKeyForName( + NameForClient(static_cast<PreviewsProber::ClientName>(i)))); + } +} + void PreviewsProber::AddSelfAsNetworkConnectionObserver( network::NetworkConnectionTracker* network_connection_tracker) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); @@ -497,11 +526,13 @@ return; } - cached_probe_results_->SetKey(GetCacheKeyForCurrentNetwork(), - std::move(encoded.value())); + DictionaryPrefUpdate update(pref_service_, pref_key_); + update->SetKey(GetCacheKeyForCurrentNetwork(), std::move(encoded.value())); - if (cached_probe_results_->DictSize() > max_cache_entries_) - RemoveOldestDictionaryEntry(cached_probe_results_.get()); + if (update.Get()->DictSize() > max_cache_entries_) + RemoveOldestDictionaryEntry(update.Get()); + + cached_probe_results_ = update.Get()->CreateDeepCopy(); } std::string PreviewsProber::GetCacheKeyForCurrentNetwork() const {
diff --git a/chrome/browser/previews/previews_prober.h b/chrome/browser/previews/previews_prober.h index 54e8812..46dd1ca 100644 --- a/chrome/browser/previews/previews_prober.h +++ b/chrome/browser/previews/previews_prober.h
@@ -30,6 +30,9 @@ #include "base/android/application_status_listener.h" #endif +class PrefRegistrySimple; +class PrefService; + namespace network { class NetworkConnectionTracker; class SimpleURLLoader; @@ -65,7 +68,9 @@ // prefs. enum class ClientName { // TODO(crbug.com/971918): Use in litepages. - kLitepages, + kLitepages = 0, + + kMaxValue = kLitepages, }; // This enum describes the different algorithms that can be used to calculate @@ -125,6 +130,7 @@ PreviewsProber( Delegate* delegate, scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, + PrefService* pref_service, ClientName name, const GURL& url, HttpMethod http_method, @@ -135,6 +141,9 @@ base::TimeDelta revalidate_cache_after); ~PreviewsProber() override; + // Registers the prefs used in this class. + static void RegisterProfilePrefs(PrefRegistrySimple* registry); + // Sends a probe now if the prober is currently inactive. If the probe is // active (i.e.: there are probes in flight), this is a no-op. If // |send_only_in_foreground| is set, the probe will only be sent when the app @@ -157,6 +166,7 @@ PreviewsProber( Delegate* delegate, scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, + PrefService* pref_service, ClientName name, const GURL& url, HttpMethod http_method, @@ -190,6 +200,9 @@ // traffic annotations. const std::string name_; + // The pref key for used to recording |cached_probe_results_| to disk. + const std::string pref_key_; + // The URL that will be probed. const GURL url_; @@ -244,6 +257,9 @@ // any thread. network::NetworkConnectionTracker* network_connection_tracker_; + // Reference for saving |cached_probe_results_| to prefs. + PrefService* pref_service_; + // Used for setting up the |url_loader_|. scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory_;
diff --git a/chrome/browser/previews/previews_prober_browsertest.cc b/chrome/browser/previews/previews_prober_browsertest.cc index f51f5a13..1cb89de 100644 --- a/chrome/browser/previews/previews_prober_browsertest.cc +++ b/chrome/browser/previews/previews_prober_browsertest.cc
@@ -129,6 +129,7 @@ PreviewsProber::TimeoutPolicy timeout_policy; PreviewsProber prober(&delegate, browser()->profile()->GetURLLoaderFactory(), + browser()->profile()->GetPrefs(), PreviewsProber::ClientName::kLitepages, url, PreviewsProber::HttpMethod::kGet, headers, retry_policy, timeout_policy, 1, base::TimeDelta::FromDays(1)); @@ -150,6 +151,7 @@ timeout_policy.base_timeout = base::TimeDelta::FromMilliseconds(1); PreviewsProber prober(&delegate, browser()->profile()->GetURLLoaderFactory(), + browser()->profile()->GetPrefs(), PreviewsProber::ClientName::kLitepages, url, PreviewsProber::HttpMethod::kGet, headers, retry_policy, timeout_policy, 1, base::TimeDelta::FromDays(1)); @@ -167,6 +169,7 @@ PreviewsProber::TimeoutPolicy timeout_policy; PreviewsProber prober(&delegate, browser()->profile()->GetURLLoaderFactory(), + browser()->profile()->GetPrefs(), PreviewsProber::ClientName::kLitepages, url, PreviewsProber::HttpMethod::kGet, headers, retry_policy, timeout_policy, 1, base::TimeDelta::FromDays(1));
diff --git a/chrome/browser/previews/previews_prober_unittest.cc b/chrome/browser/previews/previews_prober_unittest.cc index 9485abf8..cdb2ea6 100644 --- a/chrome/browser/previews/previews_prober_unittest.cc +++ b/chrome/browser/previews/previews_prober_unittest.cc
@@ -5,6 +5,9 @@ #include "chrome/browser/previews/previews_prober.h" #include "build/build_config.h" +#include "components/pref_registry/pref_registry_syncable.h" +#include "components/prefs/pref_service.h" +#include "components/prefs/testing_pref_service.h" #include "content/public/test/test_browser_thread_bundle.h" #include "net/base/load_flags.h" #include "net/base/net_errors.h" @@ -49,6 +52,7 @@ TestPreviewsProber( PreviewsProber::Delegate* delegate, scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, + PrefService* pref_service, const PreviewsProber::ClientName name, const GURL& url, const HttpMethod http_method, @@ -61,6 +65,7 @@ const base::Clock* clock) : PreviewsProber(delegate, url_loader_factory, + pref_service, name, url, http_method, @@ -81,7 +86,12 @@ test_shared_loader_factory_( base::MakeRefCounted<network::WeakWrapperSharedURLLoaderFactory>( &test_url_loader_factory_)), - test_delegate_() {} + test_delegate_(), + test_prefs_() {} + + void SetUp() override { + PreviewsProber::RegisterProfilePrefs(test_prefs_.registry()); + } std::unique_ptr<PreviewsProber> NewProber() { return NewProberWithPolicies(PreviewsProber::RetryPolicy(), @@ -107,7 +117,7 @@ net::HttpRequestHeaders headers; headers.SetHeader("X-Testing", "Hello world"); return std::make_unique<TestPreviewsProber>( - delegate, test_shared_loader_factory_, + delegate, test_shared_loader_factory_, &test_prefs_, PreviewsProber::ClientName::kLitepages, kTestUrl, PreviewsProber::HttpMethod::kGet, headers, retry_policy, timeout_policy, 1, kCacheRevalidateAfter, thread_bundle_.GetMockTickClock(), @@ -175,6 +185,7 @@ network::TestURLLoaderFactory test_url_loader_factory_; scoped_refptr<network::SharedURLLoaderFactory> test_shared_loader_factory_; TestDelegate test_delegate_; + TestingPrefServiceSimple test_prefs_; }; TEST_F(PreviewsProberTest, OK) { @@ -307,6 +318,29 @@ EXPECT_TRUE(prober->is_active()); } +TEST_F(PreviewsProberTest, PersistentCache) { + std::unique_ptr<PreviewsProber> prober = NewProber(); + EXPECT_EQ(prober->LastProbeWasSuccessful(), base::nullopt); + + prober->SendNowIfInactive(false); + VerifyRequest(); + + MakeResponseAndWait(net::HTTP_OK, net::OK); + EXPECT_TRUE(prober->LastProbeWasSuccessful().value()); + EXPECT_FALSE(prober->is_active()); + + // Create a new prober instance and verify the cached probe result is used. + prober = NewProber(); + EXPECT_TRUE(prober->LastProbeWasSuccessful().value()); + EXPECT_FALSE(prober->is_active()); + + // Fast forward past the cache revalidation and check that the revalidation + // time was also persisted. + FastForward(kCacheRevalidateAfter); + EXPECT_TRUE(prober->LastProbeWasSuccessful().value()); + EXPECT_TRUE(prober->is_active()); +} + #if defined(OS_ANDROID) TEST_F(PreviewsProberTest, StartInForeground) { std::unique_ptr<PreviewsProber> prober = NewProber();
diff --git a/chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.cc b/chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.cc index 6c61fc3..b771ba3 100644 --- a/chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.cc +++ b/chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.cc
@@ -147,7 +147,6 @@ #include "chrome/browser/extensions/browser_context_keyed_service_factories.h" #include "chrome/browser/extensions/extension_management.h" #include "chrome/browser/ui/web_applications/web_app_metrics_factory.h" -#include "chrome/browser/ui/web_applications/web_app_ui_service_factory.h" #include "chrome/browser/web_applications/web_app_provider_factory.h" #include "extensions/browser/api/networking_private/networking_private_delegate_factory.h" #include "extensions/browser/browser_context_keyed_service_factories.h" @@ -405,7 +404,6 @@ #endif #if BUILDFLAG(ENABLE_EXTENSIONS) web_app::WebAppProviderFactory::GetInstance(); - web_app::WebAppUiServiceFactory::GetInstance(); web_app::WebAppMetricsFactory::GetInstance(); #endif WebDataServiceFactory::GetInstance();
diff --git a/chrome/browser/profiles/gaia_info_update_service.cc b/chrome/browser/profiles/gaia_info_update_service.cc index 7d35e26..7e36982 100644 --- a/chrome/browser/profiles/gaia_info_update_service.cc +++ b/chrome/browser/profiles/gaia_info_update_service.cc
@@ -22,6 +22,7 @@ #include "components/signin/public/base/signin_pref_names.h" #include "components/signin/public/identity_manager/account_info.h" #include "content/public/browser/notification_details.h" +#include "content/public/browser/storage_partition.h" #include "third_party/skia/include/core/SkBitmap.h" #include "ui/gfx/image/image.h" @@ -87,8 +88,14 @@ return 256; } -Profile* GAIAInfoUpdateService::GetBrowserProfile() { - return profile_; +identity::IdentityManager* GAIAInfoUpdateService::GetIdentityManager() { + return IdentityManagerFactory::GetForProfile(profile_); +} + +network::mojom::URLLoaderFactory* GAIAInfoUpdateService::GetURLLoaderFactory() { + return content::BrowserContext::GetDefaultStoragePartition(profile_) + ->GetURLLoaderFactoryForBrowserProcess() + .get(); } std::string GAIAInfoUpdateService::GetCachedPictureURL() const {
diff --git a/chrome/browser/profiles/gaia_info_update_service.h b/chrome/browser/profiles/gaia_info_update_service.h index 4ea91688..a6abf69 100644 --- a/chrome/browser/profiles/gaia_info_update_service.h +++ b/chrome/browser/profiles/gaia_info_update_service.h
@@ -37,7 +37,8 @@ // ProfileDownloaderDelegate: bool NeedsProfilePicture() const override; int GetDesiredImageSideLength() const override; - Profile* GetBrowserProfile() override; + identity::IdentityManager* GetIdentityManager() override; + network::mojom::URLLoaderFactory* GetURLLoaderFactory() override; std::string GetCachedPictureURL() const override; bool IsPreSignin() const override; void OnProfileDownloadSuccess(ProfileDownloader* downloader) override;
diff --git a/chrome/browser/profiles/profile_downloader.cc b/chrome/browser/profiles/profile_downloader.cc index 7030449..408fab22 100644 --- a/chrome/browser/profiles/profile_downloader.cc +++ b/chrome/browser/profiles/profile_downloader.cc
@@ -21,13 +21,10 @@ #include "chrome/browser/profiles/profile.h" #include "chrome/browser/profiles/profile_downloader_delegate.h" #include "chrome/browser/profiles/profile_manager.h" -#include "chrome/browser/signin/identity_manager_factory.h" #include "components/signin/public/base/avatar_icon_util.h" #include "components/signin/public/identity_manager/access_token_fetcher.h" #include "components/signin/public/identity_manager/access_token_info.h" #include "components/signin/public/identity_manager/account_info.h" -#include "content/public/browser/browser_thread.h" -#include "content/public/browser/storage_partition.h" #include "google_apis/gaia/gaia_constants.h" #include "net/base/load_flags.h" #include "net/http/http_status_code.h" @@ -35,8 +32,6 @@ #include "skia/ext/image_operations.h" #include "url/gurl.h" -using content::BrowserThread; - namespace { // Template for optional authorization header when using an OAuth access token. @@ -47,8 +42,7 @@ ProfileDownloader::ProfileDownloader(ProfileDownloaderDelegate* delegate) : delegate_(delegate), picture_status_(PICTURE_FAILED), - identity_manager_(IdentityManagerFactory::GetForProfile( - delegate_->GetBrowserProfile())), + identity_manager_(delegate_->GetIdentityManager()), identity_manager_observer_(this), waiting_for_account_info_(false) { DCHECK(delegate_); @@ -60,8 +54,8 @@ } void ProfileDownloader::StartForAccount(const std::string& account_id) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); VLOG(1) << "Starting profile downloader..."; - DCHECK_CURRENTLY_ON(BrowserThread::UI); if (!identity_manager_) { // This can happen in some test paths. @@ -228,10 +222,7 @@ } network::mojom::URLLoaderFactory* loader_factory = - content::BrowserContext::GetDefaultStoragePartition( - delegate_->GetBrowserProfile()) - ->GetURLLoaderFactoryForBrowserProcess() - .get(); + delegate_->GetURLLoaderFactory(); simple_loader_ = network::SimpleURLLoader::Create(std::move(resource_request), traffic_annotation); @@ -242,7 +233,7 @@ void ProfileDownloader::OnURLLoaderComplete( std::unique_ptr<std::string> response_body) { - DCHECK_CURRENTLY_ON(BrowserThread::UI); + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); int response_code = -1; if (simple_loader_->ResponseInfo() && simple_loader_->ResponseInfo()->headers) response_code = simple_loader_->ResponseInfo()->headers->response_code(); @@ -272,7 +263,7 @@ } void ProfileDownloader::OnImageDecoded(const SkBitmap& decoded_image) { - DCHECK_CURRENTLY_ON(BrowserThread::UI); + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); int image_size = delegate_->GetDesiredImageSideLength(); profile_picture_ = skia::ImageOperations::Resize( decoded_image, @@ -284,7 +275,7 @@ } void ProfileDownloader::OnDecodeImageFailed() { - DCHECK_CURRENTLY_ON(BrowserThread::UI); + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); delegate_->OnProfileDownloadFailure( this, ProfileDownloaderDelegate::IMAGE_DECODE_FAILED); }
diff --git a/chrome/browser/profiles/profile_downloader.h b/chrome/browser/profiles/profile_downloader.h index 60d22b4..f75acd85 100644 --- a/chrome/browser/profiles/profile_downloader.h +++ b/chrome/browser/profiles/profile_downloader.h
@@ -11,6 +11,7 @@ #include "base/gtest_prod_util.h" #include "base/macros.h" #include "base/scoped_observer.h" +#include "base/sequence_checker.h" #include "base/strings/string16.h" #include "chrome/browser/image_decoder.h" #include "components/signin/public/identity_manager/account_info.h" @@ -112,6 +113,8 @@ // can be downloaded. void StartFetchingOAuth2AccessToken(); + SEQUENCE_CHECKER(sequence_checker_); + ProfileDownloaderDelegate* delegate_; std::string account_id_; std::string auth_token_;
diff --git a/chrome/browser/profiles/profile_downloader_delegate.h b/chrome/browser/profiles/profile_downloader_delegate.h index 3015112..a7aec77 100644 --- a/chrome/browser/profiles/profile_downloader_delegate.h +++ b/chrome/browser/profiles/profile_downloader_delegate.h
@@ -9,9 +9,18 @@ #include "base/strings/string16.h" -class Profile; class ProfileDownloader; +namespace identity { +class IdentityManager; +} // namespace identity + +namespace network { +namespace mojom { +class URLLoaderFactory; +} // namespace mojom +} // namespace network + // Reports on success or failure of Profile download. It is OK to delete the // |ProfileImageDownloader| instance in any of these handlers. class ProfileDownloaderDelegate { @@ -39,8 +48,11 @@ // cached URL. virtual std::string GetCachedPictureURL() const = 0; - // Returns the browser profile associated with this download request. - virtual Profile* GetBrowserProfile() = 0; + // Returns the IdentityManager associated with this download request. + virtual identity::IdentityManager* GetIdentityManager() = 0; + + // Returns the URLLoaderFactory to use for this download request. + virtual network::mojom::URLLoaderFactory* GetURLLoaderFactory() = 0; // Returns true if the profile download is taking place before the user has // signed in. This can happen for example on Android and will trigger some
diff --git a/chrome/browser/profiles/profile_downloader_unittest.cc b/chrome/browser/profiles/profile_downloader_unittest.cc index 6684cf1..437c11ad 100644 --- a/chrome/browser/profiles/profile_downloader_unittest.cc +++ b/chrome/browser/profiles/profile_downloader_unittest.cc
@@ -7,15 +7,18 @@ #include "base/bind.h" #include "base/strings/string_util.h" #include "base/strings/utf_string_conversions.h" +#include "base/test/scoped_task_environment.h" #include "chrome/browser/profiles/profile_downloader_delegate.h" +#include "chrome/browser/signin/identity_manager_factory.h" #include "chrome/browser/signin/identity_test_environment_profile_adaptor.h" #include "chrome/browser/signin/test_signin_client_builder.h" #include "chrome/test/base/testing_profile.h" #include "components/signin/public/base/test_signin_client.h" #include "components/signin/public/identity_manager/account_info.h" #include "components/signin/public/identity_manager/identity_manager.h" -#include "content/public/test/test_browser_thread_bundle.h" +#include "components/signin/public/identity_manager/identity_test_environment.h" #include "net/url_request/test_url_fetcher_factory.h" +#include "services/network/test/test_url_loader_factory.h" #include "testing/gtest/include/gtest/gtest.h" namespace { @@ -35,35 +38,22 @@ public ProfileDownloaderDelegate, public identity::IdentityManager::DiagnosticsObserver { protected: - ProfileDownloaderTest() - : thread_bundle_(content::TestBrowserThreadBundle::IO_MAINLOOP) {} - ~ProfileDownloaderTest() override {} - - void SetUp() override { - TestingProfile::Builder builder; - - profile_ = IdentityTestEnvironmentProfileAdaptor:: - CreateProfileForIdentityTestEnvironment(builder); - - profile_downloader_.reset(new ProfileDownloader(this)); - - identity_test_env_profile_adaptor_ = - std::make_unique<IdentityTestEnvironmentProfileAdaptor>(profile_.get()); - identity_test_env_ = - identity_test_env_profile_adaptor_->identity_test_env(); - DCHECK(identity_test_env_); - - identity_test_env_->identity_manager()->AddDiagnosticsObserver(this); + ProfileDownloaderTest() : profile_downloader_(this) { + identity_test_env_.identity_manager()->AddDiagnosticsObserver(this); } - - void TearDown() override { - identity_test_env_->identity_manager()->RemoveDiagnosticsObserver(this); + ~ProfileDownloaderTest() override { + identity_test_env_.identity_manager()->RemoveDiagnosticsObserver(this); } bool NeedsProfilePicture() const override { return true; } int GetDesiredImageSideLength() const override { return 128; } - std::string GetCachedPictureURL() const override { return ""; } - Profile* GetBrowserProfile() override { return profile_.get(); } + std::string GetCachedPictureURL() const override { return std::string(); } + identity::IdentityManager* GetIdentityManager() override { + return identity_test_env_.identity_manager(); + } + network::mojom::URLLoaderFactory* GetURLLoaderFactory() override { + return &test_url_loader_factory_; + } bool IsPreSignin() const override { return false; } void OnProfileDownloadSuccess(ProfileDownloader* downloader) override { @@ -74,7 +64,7 @@ void SimulateUserInfoSuccess(const std::string& picture_url, const AccountInfo& account_info) { - identity_test_env_->SimulateSuccessfulFetchOfAccountInfo( + identity_test_env_.SimulateSuccessfulFetchOfAccountInfo( account_info.account_id, account_info.email, account_info.gaia, kTestHostedDomain, kTestFullName, kTestGivenName, kTestLocale, picture_url); @@ -97,24 +87,23 @@ on_access_token_request_callback_ = std::move(callback); } - content::TestBrowserThreadBundle thread_bundle_; - std::unique_ptr<Profile> profile_; - std::unique_ptr<IdentityTestEnvironmentProfileAdaptor> - identity_test_env_profile_adaptor_; - identity::IdentityTestEnvironment* identity_test_env_; + base::test::ScopedTaskEnvironment scoped_task_environment_; + network::TestURLLoaderFactory test_url_loader_factory_; + identity::IdentityTestEnvironment identity_test_env_; + ProfileDownloader profile_downloader_; + base::OnceClosure on_access_token_request_callback_; std::string account_id_for_access_token_request_; - std::unique_ptr<ProfileDownloader> profile_downloader_; }; TEST_F(ProfileDownloaderTest, FetchAccessToken) { AccountInfo account_info = - identity_test_env_->MakeAccountAvailable(kTestEmail); - identity_test_env_->SetRefreshTokenForAccount(account_info.account_id); + identity_test_env_.MakeAccountAvailable(kTestEmail); + identity_test_env_.SetRefreshTokenForAccount(account_info.account_id); base::RunLoop run_loop; set_on_access_token_requested_callback(run_loop.QuitClosure()); - profile_downloader_->StartForAccount(account_info.account_id); + profile_downloader_.StartForAccount(account_info.account_id); run_loop.Run(); EXPECT_EQ(account_info.account_id, account_id_for_access_token_request_); @@ -122,63 +111,63 @@ TEST_F(ProfileDownloaderTest, AccountInfoReady) { AccountInfo account_info = - identity_test_env_->MakeAccountAvailable(kTestEmail); + identity_test_env_.MakeAccountAvailable(kTestEmail); SimulateUserInfoSuccess(kTestValidPictureURL, account_info); ASSERT_EQ(ProfileDownloader::PICTURE_FAILED, - profile_downloader_->GetProfilePictureStatus()); + profile_downloader_.GetProfilePictureStatus()); base::RunLoop run_loop; set_on_access_token_requested_callback(run_loop.QuitClosure()); - profile_downloader_->StartForAccount(account_info.account_id); + profile_downloader_.StartForAccount(account_info.account_id); run_loop.Run(); - profile_downloader_->StartFetchingImage(); - ASSERT_EQ(kTestValidPictureURL, profile_downloader_->GetProfilePictureURL()); + profile_downloader_.StartFetchingImage(); + ASSERT_EQ(kTestValidPictureURL, profile_downloader_.GetProfilePictureURL()); } TEST_F(ProfileDownloaderTest, AccountInfoNotReady) { AccountInfo account_info = - identity_test_env_->MakeAccountAvailable(kTestEmail); + identity_test_env_.MakeAccountAvailable(kTestEmail); ASSERT_EQ(ProfileDownloader::PICTURE_FAILED, - profile_downloader_->GetProfilePictureStatus()); + profile_downloader_.GetProfilePictureStatus()); base::RunLoop run_loop; set_on_access_token_requested_callback(run_loop.QuitClosure()); - profile_downloader_->StartForAccount(account_info.account_id); + profile_downloader_.StartForAccount(account_info.account_id); run_loop.Run(); - profile_downloader_->StartFetchingImage(); + profile_downloader_.StartFetchingImage(); SimulateUserInfoSuccess(kTestValidPictureURL, account_info); - ASSERT_EQ(kTestValidPictureURL, profile_downloader_->GetProfilePictureURL()); + ASSERT_EQ(kTestValidPictureURL, profile_downloader_.GetProfilePictureURL()); } // Regression test for http://crbug.com/854907 TEST_F(ProfileDownloaderTest, AccountInfoNoPictureDoesNotCrash) { AccountInfo account_info = - identity_test_env_->MakeAccountAvailable(kTestEmail); + identity_test_env_.MakeAccountAvailable(kTestEmail); SimulateUserInfoSuccess(kNoPictureURLFound, account_info); base::RunLoop run_loop; set_on_access_token_requested_callback(run_loop.QuitClosure()); - profile_downloader_->StartForAccount(account_info.account_id); + profile_downloader_.StartForAccount(account_info.account_id); run_loop.Run(); - profile_downloader_->StartFetchingImage(); + profile_downloader_.StartFetchingImage(); - EXPECT_TRUE(profile_downloader_->GetProfilePictureURL().empty()); + EXPECT_TRUE(profile_downloader_.GetProfilePictureURL().empty()); ASSERT_EQ(ProfileDownloader::PICTURE_DEFAULT, - profile_downloader_->GetProfilePictureStatus()); + profile_downloader_.GetProfilePictureStatus()); } // Regression test for http://crbug.com/854907 TEST_F(ProfileDownloaderTest, AccountInfoInvalidPictureURLDoesNotCrash) { AccountInfo account_info = - identity_test_env_->MakeAccountAvailable(kTestEmail); + identity_test_env_.MakeAccountAvailable(kTestEmail); SimulateUserInfoSuccess(kTestInvalidPictureURL, account_info); base::RunLoop run_loop; set_on_access_token_requested_callback(run_loop.QuitClosure()); - profile_downloader_->StartForAccount(account_info.account_id); + profile_downloader_.StartForAccount(account_info.account_id); run_loop.Run(); - profile_downloader_->StartFetchingImage(); + profile_downloader_.StartFetchingImage(); - EXPECT_TRUE(profile_downloader_->GetProfilePictureURL().empty()); + EXPECT_TRUE(profile_downloader_.GetProfilePictureURL().empty()); ASSERT_EQ(ProfileDownloader::PICTURE_FAILED, - profile_downloader_->GetProfilePictureStatus()); + profile_downloader_.GetProfilePictureStatus()); }
diff --git a/chrome/browser/resources/downloads/manager.html b/chrome/browser/resources/downloads/manager.html index acd701b..d736a5f 100644 --- a/chrome/browser/resources/downloads/manager.html +++ b/chrome/browser/resources/downloads/manager.html
@@ -9,6 +9,7 @@ <link rel="import" href="chrome://resources/cr_components/managed_footnote/managed_footnote.html"> <link rel="import" href="chrome://resources/cr_elements/cr_toast/cr_toast_manager.html"> <link rel="import" href="chrome://resources/cr_elements/hidden_style_css.html"> +<link rel="import" href="chrome://resources/cr_elements/shared_style_css.html"> <link rel="import" href="chrome://resources/cr_elements/shared_vars_css.html"> <link rel="import" href="chrome://resources/html/cr.html"> <link rel="import" href="chrome://resources/html/cr/ui.html"> @@ -20,7 +21,7 @@ <dom-module id="downloads-manager"> <template> - <style include="cr-hidden-style"> + <style include="cr-shared-style cr-hidden-style"> :host { display: flex; flex: 1 0; @@ -42,10 +43,6 @@ z-index: 1; } - #drop-shadow { - @apply --cr-container-shadow; - } - :host([has-shadow_]) #drop-shadow { opacity: var(--cr-container-shadow-max-opacity); } @@ -125,7 +122,7 @@ <downloads-toolbar id="toolbar" spinner-active="{{spinnerActive_}}" role="none" on-search-changed="onSearchChanged_"> </downloads-toolbar> - <div id="drop-shadow"></div> + <div id="drop-shadow" class="cr-container-shadow"></div> <div id="mainContainer" on-scroll="onScroll_"> <managed-footnote hidden="[[inSearchMode_]]"></managed-footnote> <iron-list id="downloadsList" items="[[items_]]"
diff --git a/chrome/browser/resources/history/app.html b/chrome/browser/resources/history/app.html index 736edaf..2e14bd0 100644 --- a/chrome/browser/resources/history/app.html +++ b/chrome/browser/resources/history/app.html
@@ -1,5 +1,6 @@ <link rel="import" href="chrome://resources/html/polymer.html"> +<link rel="import" href="chrome://resources/cr_elements/shared_style_css.html"> <link rel="import" href="chrome://resources/cr_elements/shared_vars_css.html"> <link rel="import" href="chrome://resources/html/cr/ui.html"> <link rel="import" href="chrome://resources/html/cr/ui/command.html"> @@ -19,7 +20,7 @@ <dom-module id="history-app"> <template> - <style include="shared-style"> + <style include="cr-shared-style shared-style"> :host { color: var(--cr-primary-text-color); display: block; @@ -48,10 +49,6 @@ height: 100%; } - #drop-shadow { - @apply --cr-container-shadow; - } - :host([toolbar-shadow_]) #drop-shadow { opacity: var(--cr-container-shadow-max-opacity); } @@ -76,7 +73,7 @@ queryState_.searchTerm)]]"> </history-toolbar> - <div id="drop-shadow"></div> + <div id="drop-shadow" class="cr-container-shadow"></div> <div id="main-container"> <history-side-bar id="content-side-bar" selected-page="{{selectedPage_}}" footer-info="[[footerInfo]]"
diff --git a/chrome/browser/resources/local_ntp/customize.js b/chrome/browser/resources/local_ntp/customize.js index 00e4bc5..24c276f4 100644 --- a/chrome/browser/resources/local_ntp/customize.js +++ b/chrome/browser/resources/local_ntp/customize.js
@@ -1403,7 +1403,7 @@ const menu = $(customize.IDS.MENU); $(customize.IDS.OPTIONS_TITLE).textContent = - configData.translatedStrings.customizeBackground; + configData.translatedStrings.customizeThisPage; if (configData.richerPicker) { // Store the main menu title so it can be restored if needed. @@ -1411,12 +1411,12 @@ $(customize.IDS.MENU_TITLE).textContent; } - $(customize.IDS.EDIT_BG_ICON) + $(customize.IDS.EDIT_BG) .setAttribute( 'aria-label', configData.translatedStrings.customizeThisPage); - $(customize.IDS.EDIT_BG_ICON) - .setAttribute('title', configData.translatedStrings.customizeBackground); + $(customize.IDS.EDIT_BG) + .setAttribute('title', configData.translatedStrings.customizeThisPage); // Selecting a local image for the background should close the picker. if (configData.richerPicker) {
diff --git a/chrome/browser/resources/local_ntp/externs.js b/chrome/browser/resources/local_ntp/externs.js index 92ed52f..4669cc4 100644 --- a/chrome/browser/resources/local_ntp/externs.js +++ b/chrome/browser/resources/local_ntp/externs.js
@@ -373,7 +373,6 @@ configData.translatedStrings.connectionError; configData.translatedStrings.connectionErrorNoPeriod; configData.translatedStrings.copyLink; -configData.translatedStrings.customizeBackground; configData.translatedStrings.customizeButtonLabel; configData.translatedStrings.customizeThisPage; configData.translatedStrings.dailyRefresh;
diff --git a/chrome/browser/resources/pdf/elements/viewer-pdf-toolbar/viewer-pdf-toolbar.html b/chrome/browser/resources/pdf/elements/viewer-pdf-toolbar/viewer-pdf-toolbar.html index 2f87e5e..f6454c97 100644 --- a/chrome/browser/resources/pdf/elements/viewer-pdf-toolbar/viewer-pdf-toolbar.html +++ b/chrome/browser/resources/pdf/elements/viewer-pdf-toolbar/viewer-pdf-toolbar.html
@@ -204,8 +204,8 @@ title$="{{strings.tooltipDownload}}"></cr-icon-button> <cr-icon-button id="print" iron-icon="cr:print" on-click="print" - aria-label$="{{strings.tooltipPrint}}" - title$="{{strings.tooltipPrint}}"></cr-icon-button> + hidden="[[!printingEnabled]]" title$="{{strings.tooltipPrint}}" + aria-label$="{{strings.tooltipPrint}}"></cr-icon-button> <viewer-toolbar-dropdown id="bookmarks" selected
diff --git a/chrome/browser/resources/pdf/elements/viewer-pdf-toolbar/viewer-pdf-toolbar.js b/chrome/browser/resources/pdf/elements/viewer-pdf-toolbar/viewer-pdf-toolbar.js index 8e18564a..006aa5c 100644 --- a/chrome/browser/resources/pdf/elements/viewer-pdf-toolbar/viewer-pdf-toolbar.js +++ b/chrome/browser/resources/pdf/elements/viewer-pdf-toolbar/viewer-pdf-toolbar.js
@@ -80,6 +80,14 @@ value: false, }, + /** + * Whether the Printing feature is enabled. + */ + printingEnabled: { + type: Boolean, + value: false, + }, + strings: Object, },
diff --git a/chrome/browser/resources/pdf/pdf_viewer.js b/chrome/browser/resources/pdf/pdf_viewer.js index b62ace3b..02763ae0 100644 --- a/chrome/browser/resources/pdf/pdf_viewer.js +++ b/chrome/browser/resources/pdf/pdf_viewer.js
@@ -777,6 +777,7 @@ $('toolbar').strings = strings; $('toolbar').pdfAnnotationsEnabled = loadTimeData.getBoolean('pdfAnnotationsEnabled'); + $('toolbar').printingEnabled = loadTimeData.getBoolean('printingEnabled'); $('zoom-toolbar').setStrings(strings); $('password-screen').strings = strings; $('error-screen').strings = strings;
diff --git a/chrome/browser/resources/settings/a11y_page/a11y_page.html b/chrome/browser/resources/settings/a11y_page/a11y_page.html index a4acf13..98535e1 100644 --- a/chrome/browser/resources/settings/a11y_page/a11y_page.html +++ b/chrome/browser/resources/settings/a11y_page/a11y_page.html
@@ -19,101 +19,96 @@ <dom-module id="settings-a11y-page"> <template> <style include="settings-shared"></style> + <template is="dom-if" if="[[showCaptionSettings_]]"> + <cr-link-row class="hr" id="captions" label="$i18n{captionsTitle}" + on-click="onCaptionsClick_"> + </cr-link-row> + </template> <settings-animated-pages id="pages" current-route="{{currentRoute}}" section="a11y" focus-config="[[focusConfig_]]"> - <if expr="not chromeos"> +<if expr="not chromeos"> + <div route-path="default"> + <settings-toggle-button + id="a11yImageLabels" + hidden$="[[!showAccessibilityLabelsSetting_]]" + pref="{{prefs.settings.a11y.enable_accessibility_image_labels}}" + on-change="onToggleAccessibilityImageLabels_" + label="$i18n{accessibleImageLabelsTitle}" + sub-label="$i18n{accessibleImageLabelsSubtitle}"> + </settings-toggle-button> + <cr-link-row class="hr" label="$i18n{moreFeaturesLink}" + on-click="onMoreFeaturesLinkClick_" sub-label="$i18n{a11yWebStore}" + external> + </cr-link-row> + </div> +</if> +<if expr="chromeos or is_linux or is_win"> + <template is="dom-if" if="[[showCaptionSettings_]]"> + <template is="dom-if" route-path="/captions"> + <settings-subpage + associated-control="[[$$('#captions')]]" + page-title="$i18n{captionsTitle}"> + <settings-captions prefs="{{prefs}}"></settings-captions> + </settings-subpage> + </template> + </template> +</if> +<if expr="chromeos"> + <template is="dom-if" if="[[pageVisibility.webstoreLink]]"> <div route-path="default"> - <template is="dom-if" if="[[showCaptionSettings_]]"> - <cr-link-row class="hr" id="captions" label="$i18n{captionsTitle}" - on-click="onTapCaptions_"> - </cr-link-row> - </template> - <if expr="not chromeos"> - <settings-toggle-button id="a11yImageLabels" - hidden$="[[!showAccessibilityLabelsSetting_]]" - pref="{{prefs.settings.a11y.enable_accessibility_image_labels}}" - on-change="onToggleAccessibilityImageLabels_" - label="$i18n{accessibleImageLabelsTitle}" - sub-label="$i18n{accessibleImageLabelsSubtitle}"> - </settings-toggle-button> - <cr-link-row class="hr" label="$i18n{moreFeaturesLink}" - on-click="onMoreFeaturesLinkClick_" - sub-label="$i18n{a11yWebStore}" external></cr-link-row> - </if> + <settings-toggle-button + id="a11yImageLabels" + hidden$="[[!showAccessibilityLabelsSetting_]]" + pref="{{prefs.settings.a11y.enable_accessibility_image_labels}}" + on-change="onToggleAccessibilityImageLabels_" + label="$i18n{accessibleImageLabelsTitle}" + sub-label="$i18n{accessibleImageLabelsSubtitle}"> + </settings-toggle-button> + <settings-toggle-button id="optionsInMenuToggle" + label="$i18n{optionsInMenuLabel}" + pref="{{prefs.settings.a11y.enable_menu}}"> + </settings-toggle-button> + <cr-link-row class="hr" id="subpage-trigger" + label="$i18n{manageAccessibilityFeatures}" + on-click="onManageAccessibilityFeaturesTap_" + sub-label="$i18n{moreFeaturesLinkDescription}"> + </cr-link-row> </div> - </if> - <if expr="chromeos"> - <template is="dom-if" if="[[pageVisibility.webstoreLink]]"> - <div route-path="default"> - <template is="dom-if" if="[[showCaptionSettings_]]"> - <cr-link-row class="hr" id="captions" - label="$i18n{captionsTitle}" - on-click="onTapCaptions_"> - </cr-link-row> - </template> - <settings-toggle-button id="a11yImageLabels" - hidden$="[[!showAccessibilityLabelsSetting_]]" - pref="{{prefs.settings.a11y.enable_accessibility_image_labels}}" - on-change="onToggleAccessibilityImageLabels_" - label="$i18n{accessibleImageLabelsTitle}" - sub-label="$i18n{accessibleImageLabelsSubtitle}"> - </settings-toggle-button> - <settings-toggle-button id="optionsInMenuToggle" - label="$i18n{optionsInMenuLabel}" - pref="{{prefs.settings.a11y.enable_menu}}"> - </settings-toggle-button> - <cr-link-row class="hr" id="subpage-trigger" - label="$i18n{manageAccessibilityFeatures}" - on-click="onManageAccessibilityFeaturesTap_" - sub-label="$i18n{moreFeaturesLinkDescription}"> - </cr-link-row> - </div> - <template is="dom-if" route-path="/manageAccessibility"> + <template is="dom-if" route-path="/manageAccessibility"> + <settings-subpage + associated-control="[[$$('#subpage-trigger')]]" + page-title="$i18n{manageAccessibilityFeatures}"> + <settings-manage-a11y-page prefs="{{prefs}}"> + </settings-manage-a11y-page> + </settings-subpage> + </template> + <template is="dom-if" route-path="/manageAccessibility/tts"> + <settings-subpage + associated-control="[[$$('#subpage-trigger')]]" + page-title="$i18n{manageTtsSettings}"> + <settings-tts-subpage prefs="{{prefs}}"> + </settings-tts-subpage> + </settings-subpage> + </template> + <template is="dom-if" if="[[showExperimentalSwitchAccess_]]"> + <template is="dom-if" + route-path="/manageAccessibility/switchAccess"> <settings-subpage associated-control="[[$$('#subpage-trigger')]]" - page-title="$i18n{manageAccessibilityFeatures}"> - <settings-manage-a11y-page prefs="{{prefs}}"> - </settings-manage-a11y-page> - </settings-subpage> - </template> - <template is="dom-if" route-path="/manageAccessibility/tts"> - <settings-subpage - associated-control="[[$$('#subpage-trigger')]]" - page-title="$i18n{manageTtsSettings}"> - <settings-tts-subpage prefs="{{prefs}}"> - </settings-tts-subpage> - </settings-subpage> - </template> - <template is="dom-if" if="[[showExperimentalSwitchAccess_]]"> - <template is="dom-if" - route-path="/manageAccessibility/switchAccess"> - <settings-subpage associated-control="[[$$('#subpage-trigger')]]" - page-title="$i18n{manageSwitchAccessSettings}"> - <settings-switch-access-subpage prefs="{{prefs.settings.a11y}}"> - </settings-switch-access-subpage> - </settings-subpage> - </template> - </template> - </template> - <cr-link-row class="hr" - label="$i18n{moreFeaturesLink}" - on-click="onMoreFeaturesLinkClick_" - sub-label="$i18n{a11yWebStore}" - hidden="[[pageVisibility.webstoreLink]]" external></cr-link-row> - </if> - - <if expr="chromeos or is_linux or is_win"> - <template is="dom-if" if="[[showCaptionSettings_]]"> - <template is="dom-if" route-path="/captions"> - <settings-subpage - associated-control="[[$$('#captions')]]" - page-title="$i18n{captionsTitle}"> - <settings-captions prefs="{{prefs}}"></settings-captions> + page-title="$i18n{manageSwitchAccessSettings}"> + <settings-switch-access-subpage prefs="{{prefs.settings.a11y}}"> + </settings-switch-access-subpage> </settings-subpage> </template> </template> - </if> + </template> +</if> </settings-animated-pages> - +<if expr="chromeos"> + <cr-link-row class="hr" label="$i18n{moreFeaturesLink}" + on-click="onMoreFeaturesLinkClick_" sub-label="$i18n{a11yWebStore}" + hidden="[[pageVisibility.webstoreLink]]" external> + </cr-link-row> +</if> </template> <script src="a11y_page.js"></script> </dom-module>
diff --git a/chrome/browser/resources/settings/a11y_page/a11y_page.js b/chrome/browser/resources/settings/a11y_page/a11y_page.js index e1cfc426..a32699fa 100644 --- a/chrome/browser/resources/settings/a11y_page/a11y_page.js +++ b/chrome/browser/resources/settings/a11y_page/a11y_page.js
@@ -137,7 +137,7 @@ }, /** @private */ - onTapCaptions_: function() { + onCaptionsClick_: function() { // Open the system captions dialog for Mac. // <if expr="is_macosx"> settings.CaptionsBrowserProxyImpl.getInstance().openSystemCaptionsDialog();
diff --git a/chrome/browser/search/local_ntp_source.cc b/chrome/browser/search/local_ntp_source.cc index e8137e5f..ff230b5 100644 --- a/chrome/browser/search/local_ntp_source.cc +++ b/chrome/browser/search/local_ntp_source.cc
@@ -194,8 +194,6 @@ // Custom Backgrounds AddString(translated_strings.get(), "customizeButtonLabel", IDS_NTP_CUSTOMIZE_BUTTON_LABEL); - AddString(translated_strings.get(), "customizeBackground", - IDS_NTP_CUSTOM_BG_CUSTOMIZE_BACKGROUND); AddString(translated_strings.get(), "defaultWallpapers", IDS_NTP_CUSTOM_BG_CHROME_WALLPAPERS); AddString(translated_strings.get(), "uploadImage",
diff --git a/chrome/browser/sessions/OWNERS b/chrome/browser/sessions/OWNERS index aab6f95..54670587 100644 --- a/chrome/browser/sessions/OWNERS +++ b/chrome/browser/sessions/OWNERS
@@ -7,3 +7,4 @@ per-file session_restore_android*=felipeg@chromium.org per-file session_restore*chromeos*=xiyuan@chromium.org +# COMPONENT: UI>Browser>Sessions
diff --git a/chrome/browser/sharing/ack_message_handler.cc b/chrome/browser/sharing/ack_message_handler.cc index 93d460e..5f93d0f 100644 --- a/chrome/browser/sharing/ack_message_handler.cc +++ b/chrome/browser/sharing/ack_message_handler.cc
@@ -4,11 +4,22 @@ #include "chrome/browser/sharing/ack_message_handler.h" +#include "chrome/browser/sharing/proto/sharing_message.pb.h" + AckMessageHandler::AckMessageHandler() = default; AckMessageHandler::~AckMessageHandler() = default; void AckMessageHandler::OnMessage( const chrome_browser_sharing::SharingMessage& message) { - // TODO + for (AckMessageObserver& observer : observers_) + observer.OnAckReceived(message.ack_message().original_message_id()); +} + +void AckMessageHandler::AddObserver(AckMessageObserver* observer) { + observers_.AddObserver(observer); +} + +void AckMessageHandler::RemoveObserver(AckMessageObserver* observer) { + observers_.RemoveObserver(observer); }
diff --git a/chrome/browser/sharing/ack_message_handler.h b/chrome/browser/sharing/ack_message_handler.h index 84f8633..8e00dad 100644 --- a/chrome/browser/sharing/ack_message_handler.h +++ b/chrome/browser/sharing/ack_message_handler.h
@@ -5,19 +5,41 @@ #ifndef CHROME_BROWSER_SHARING_ACK_MESSAGE_HANDLER_H_ #define CHROME_BROWSER_SHARING_ACK_MESSAGE_HANDLER_H_ +#include <string> + #include "base/macros.h" +#include "base/observer_list.h" #include "chrome/browser/sharing/sharing_message_handler.h" +// Class to managae ack message and notify observers. class AckMessageHandler : public SharingMessageHandler { public: + // Interface for objects observing ack message received events. + class AckMessageObserver : public base::CheckedObserver { + public: + // Called when an ack message is received, where the identifier of original + // message is |message_id|. + virtual void OnAckReceived(const std::string& message_id) = 0; + }; + AckMessageHandler(); ~AckMessageHandler() override; + // Add an observer ack message received events. An observer should not be + // added more than once. + void AddObserver(AckMessageObserver* observer); + + // Removes the given observer from ack message received events. Does nothing + // if this observer has not been added. + void RemoveObserver(AckMessageObserver* observer); + // SharingMessageHandler implementation: void OnMessage( const chrome_browser_sharing::SharingMessage& message) override; private: + base::ObserverList<AckMessageObserver> observers_; + DISALLOW_COPY_AND_ASSIGN(AckMessageHandler); };
diff --git a/chrome/browser/sharing/ack_message_handler_unittest.cc b/chrome/browser/sharing/ack_message_handler_unittest.cc new file mode 100644 index 0000000..2681295 --- /dev/null +++ b/chrome/browser/sharing/ack_message_handler_unittest.cc
@@ -0,0 +1,47 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/sharing/ack_message_handler.h" + +#include "chrome/browser/sharing/proto/sharing_message.pb.h" +#include "testing/gtest/include/gtest/gtest.h" + +using SharingMessage = chrome_browser_sharing::SharingMessage; +using namespace testing; + +namespace { + +const char kTestMessageId[] = "test_message_id"; + +class TestObserver : public AckMessageHandler::AckMessageObserver { + public: + void OnAckReceived(const std::string& message_id) override { + received_message_id_ = message_id; + } + + const std::string& received_message_id() { return received_message_id_; } + + private: + std::string received_message_id_; +}; + +class AckMessageHandlerTest : public Test { + protected: + AckMessageHandlerTest() { ack_message_handler_.AddObserver(&test_observer_); } + + AckMessageHandler ack_message_handler_; + TestObserver test_observer_; +}; + +} // namespace + +TEST_F(AckMessageHandlerTest, OnMessage) { + SharingMessage sharing_message; + sharing_message.mutable_ack_message()->set_original_message_id( + kTestMessageId); + + ack_message_handler_.OnMessage(sharing_message); + + EXPECT_EQ(kTestMessageId, test_observer_.received_message_id()); +}
diff --git a/chrome/browser/sharing/click_to_call/click_to_call_context_menu_observer.cc b/chrome/browser/sharing/click_to_call/click_to_call_context_menu_observer.cc index 67c4499..91d3ab5 100644 --- a/chrome/browser/sharing/click_to_call/click_to_call_context_menu_observer.cc +++ b/chrome/browser/sharing/click_to_call/click_to_call_context_menu_observer.cc
@@ -12,6 +12,7 @@ #include "chrome/browser/renderer_context_menu/render_view_context_menu.h" #include "chrome/browser/sharing/click_to_call/click_to_call_constants.h" #include "chrome/browser/sharing/click_to_call/feature.h" +#include "chrome/browser/sharing/sharing_metrics.h" #include "chrome/browser/sharing/sharing_service.h" #include "chrome/browser/sharing/sharing_service_factory.h" #include "chrome/grit/generated_resources.h" @@ -59,6 +60,7 @@ url_ = params.link_url; devices_ = sharing_service_->GetDeviceCandidates( static_cast<int>(SharingDeviceCapability::kTelephony)); + LogClickToCallDevicesToShow(devices_.size()); if (devices_.empty()) return; @@ -148,8 +150,7 @@ AsWeakPtr())); } -void ClickToCallContextMenuObserver::OnMessageSent( - base::Optional<std::string> message_id) const { +void ClickToCallContextMenuObserver::OnMessageSent(bool sucess) const { // TODO(himanshujaju) Add metrics. }
diff --git a/chrome/browser/sharing/click_to_call/click_to_call_context_menu_observer.h b/chrome/browser/sharing/click_to_call/click_to_call_context_menu_observer.h index 44d622a6..8bf38c0 100644 --- a/chrome/browser/sharing/click_to_call/click_to_call_context_menu_observer.h +++ b/chrome/browser/sharing/click_to_call/click_to_call_context_menu_observer.h
@@ -65,7 +65,7 @@ void SendClickToCallMessage(int chosen_device_index); - void OnMessageSent(base::Optional<std::string> message_id) const; + void OnMessageSent(bool sucess) const; gfx::ImageSkia GetContextMenuIcon() const;
diff --git a/chrome/browser/sharing/sharing_device_registration.cc b/chrome/browser/sharing/sharing_device_registration.cc index b524865..8bb3035 100644 --- a/chrome/browser/sharing/sharing_device_registration.cc +++ b/chrome/browser/sharing/sharing_device_registration.cc
@@ -51,8 +51,8 @@ auto registration = sharing_sync_preference_->GetFCMRegistration(); if (registration && registration->authorized_entity == authorized_entity && (base::Time::Now() - registration->timestamp < kRegistrationExpiration)) { - // Authorized entity hasn't changed nor has expired, return success. - std::move(callback).Run(Result::SUCCESS); + // Authorized entity hasn't changed nor has expired, skip to next step. + RetrieveEncrpytionInfo(std::move(callback), registration->fcm_token); return; } @@ -72,11 +72,9 @@ instance_id::InstanceID::Result result) { switch (result) { case instance_id::InstanceID::SUCCESS: - gcm_driver_->GetEncryptionInfo( - kSharingFCMAppID, - base::BindOnce(&SharingDeviceRegistration::OnEncryptionInfoReceived, - weak_ptr_factory_.GetWeakPtr(), std::move(callback), - authorized_entity, fcm_registration_token)); + sharing_sync_preference_->SetFCMRegistration( + {authorized_entity, fcm_registration_token, base::Time::Now()}); + RetrieveEncrpytionInfo(std::move(callback), fcm_registration_token); break; case instance_id::InstanceID::NETWORK_ERROR: case instance_id::InstanceID::SERVER_ERROR: @@ -91,9 +89,18 @@ } } +void SharingDeviceRegistration::RetrieveEncrpytionInfo( + RegistrationCallback callback, + const std::string& fcm_registration_token) { + gcm_driver_->GetEncryptionInfo( + kSharingFCMAppID, + base::BindOnce(&SharingDeviceRegistration::OnEncryptionInfoReceived, + weak_ptr_factory_.GetWeakPtr(), std::move(callback), + fcm_registration_token)); +} + void SharingDeviceRegistration::OnEncryptionInfoReceived( RegistrationCallback callback, - const std::string& authorized_entity, const std::string& fcm_registration_token, std::string p256dh, std::string auth_secret) { @@ -109,8 +116,6 @@ fcm_registration_token, std::move(p256dh), std::move(auth_secret), device_capabilities); sharing_sync_preference_->SetSyncDevice(local_device_info->guid(), device); - sharing_sync_preference_->SetFCMRegistration( - {authorized_entity, fcm_registration_token, base::Time::Now()}); std::move(callback).Run(Result::SUCCESS); }
diff --git a/chrome/browser/sharing/sharing_device_registration.h b/chrome/browser/sharing/sharing_device_registration.h index 0ad2557..2bec442 100644 --- a/chrome/browser/sharing/sharing_device_registration.h +++ b/chrome/browser/sharing/sharing_device_registration.h
@@ -84,10 +84,13 @@ void OnFCMTokenDeleted(RegistrationCallback callback, instance_id::InstanceID::Result result); + // Retrieve encryption info from GCMDriver. + void RetrieveEncrpytionInfo(RegistrationCallback callback, + const std::string& fcm_registration_token); + // Callback function responsible for saving device registration information in // SharingSyncPreference. void OnEncryptionInfoReceived(RegistrationCallback callback, - const std::string& authorization_entity, const std::string& fcm_registration_token, std::string p256dh, std::string auth_secret);
diff --git a/chrome/browser/sharing/sharing_device_registration_unittest.cc b/chrome/browser/sharing/sharing_device_registration_unittest.cc index 5622d3d..acb7d0a4 100644 --- a/chrome/browser/sharing/sharing_device_registration_unittest.cc +++ b/chrome/browser/sharing/sharing_device_registration_unittest.cc
@@ -35,7 +35,9 @@ const char kFCMToken[] = "test_fcm_token"; const char kFCMToken2[] = "test_fcm_token_2"; const char kDevicep256dh[] = "test_p256_dh"; +const char kDevicep256dh2[] = "test_p256_dh_2"; const char kDeviceAuthSecret[] = "test_auth_secret"; +const char kDeviceAuthSecret2[] = "test_auth_secret_2"; class MockInstanceIDDriver : public InstanceIDDriver { public: @@ -104,11 +106,19 @@ void GetEncryptionInfo(const std::string& app_id, GetEncryptionInfoCallback callback) override { - std::move(callback).Run(kDevicep256dh, kDeviceAuthSecret); + std::move(callback).Run(p256dh_, auth_secret_); + } + + void SetEncryptionInfo(const std::string& p256dh, + const std::string& auth_secret) { + p256dh_ = p256dh; + auth_secret_ = auth_secret; } private: DISALLOW_COPY_AND_ASSIGN(FakeEncryptionGCMDriver); + std::string p256dh_ = kDevicep256dh; + std::string auth_secret_ = kDeviceAuthSecret; }; class SharingDeviceRegistrationTest : public testing::Test { @@ -222,18 +232,34 @@ } TEST_F(SharingDeviceRegistrationTest, RegisterDeviceTest_VapidKeysUnchanged) { + SetInstanceIDFCMToken(kFCMToken); SetInstanceIDFCMResult(InstanceID::Result::SUCCESS); + std::string guid = + fake_local_device_info_provider_.GetLocalDeviceInfo()->guid(); RegisterDeviceSync(); EXPECT_EQ(SharingDeviceRegistration::Result::SUCCESS, result_); - // Set instance ID result to error. InstanceID shouldn't be invoked. - SetInstanceIDFCMResult(InstanceID::Result::UNKNOWN_ERROR); + // Instance ID now returns a new token, however it shouldn't be invoked. + SetInstanceIDFCMToken(kFCMToken2); + // GCMDriver now returns new encryption info. + fake_encryption_gcm_driver_.SetEncryptionInfo(kDevicep256dh2, + kDeviceAuthSecret2); + // Register device again without changing VAPID keys. RegisterDeviceSync(); EXPECT_EQ(SharingDeviceRegistration::Result::SUCCESS, result_); + + auto it = devices_.find(guid); + ASSERT_NE(devices_.end(), it); + SharingSyncPreference::Device device(std::move(it->second)); + // Encryption info is updated with new value. + EXPECT_EQ(kDeviceAuthSecret2, device.auth_secret); + EXPECT_EQ(kDevicep256dh2, device.p256dh); + // FCM token is not updated. + EXPECT_EQ(kFCMToken, device.fcm_token); } TEST_F(SharingDeviceRegistrationTest, RegisterDeviceTest_Expired) {
diff --git a/chrome/browser/sharing/sharing_fcm_handler.cc b/chrome/browser/sharing/sharing_fcm_handler.cc index 82b12df..4052063 100644 --- a/chrome/browser/sharing/sharing_fcm_handler.cc +++ b/chrome/browser/sharing/sharing_fcm_handler.cc
@@ -7,6 +7,7 @@ #include "chrome/browser/sharing/fcm_constants.h" #include "chrome/browser/sharing/sharing_fcm_sender.h" #include "chrome/browser/sharing/sharing_message_handler.h" +#include "chrome/browser/sharing/sharing_metrics.h" #include "chrome/browser/sharing/sharing_service_factory.h" #include "components/gcm_driver/gcm_driver.h" @@ -72,6 +73,8 @@ DCHECK(sharing_message.payload_case() != SharingMessage::PAYLOAD_NOT_SET) << "No payload set in SharingMessage received"; + LogSharingMessageReceived(sharing_message.payload_case()); + auto it = sharing_handlers_.find(sharing_message.payload_case()); if (it == sharing_handlers_.end()) { LOG(ERROR) << "No handler found for payload : "
diff --git a/chrome/browser/sharing/sharing_fcm_handler.h b/chrome/browser/sharing/sharing_fcm_handler.h index 3e2a7ac7..42a80a2b 100644 --- a/chrome/browser/sharing/sharing_fcm_handler.h +++ b/chrome/browser/sharing/sharing_fcm_handler.h
@@ -37,11 +37,13 @@ virtual void StopListening(); // Registers |handler| for handling |payload_case| SharingMessage. - void AddSharingHandler(const SharingMessage::PayloadCase& payload_case, - SharingMessageHandler* handler); + virtual void AddSharingHandler( + const SharingMessage::PayloadCase& payload_case, + SharingMessageHandler* handler); // Removes SharingMessageHandler registered for |payload_case|. - void RemoveSharingHandler(const SharingMessage::PayloadCase& payload_case); + virtual void RemoveSharingHandler( + const SharingMessage::PayloadCase& payload_case); // GCMAppHandler overrides. void ShutdownHandler() override;
diff --git a/chrome/browser/sharing/sharing_metrics.cc b/chrome/browser/sharing/sharing_metrics.cc new file mode 100644 index 0000000..8d1ee3a9 --- /dev/null +++ b/chrome/browser/sharing/sharing_metrics.cc
@@ -0,0 +1,51 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/sharing/sharing_metrics.h" + +#include "base/metrics/histogram_functions.h" + +namespace { + +// These values are persisted to logs. Entries should not be renumbered and +// numeric values should never be reused. +enum class SharingMessageType { + kUnknownMessage = 0, + kPingMessage = 1, + kAckMessage = 2, + kClickToCallMessage = 3, + kMaxValue = kClickToCallMessage, +}; + +SharingMessageType PayloadCaseToMessageType( + chrome_browser_sharing::SharingMessage::PayloadCase payload_case) { + switch (payload_case) { + case chrome_browser_sharing::SharingMessage::PAYLOAD_NOT_SET: + return SharingMessageType::kUnknownMessage; + case chrome_browser_sharing::SharingMessage::kPingMessage: + return SharingMessageType::kPingMessage; + case chrome_browser_sharing::SharingMessage::kAckMessage: + return SharingMessageType::kAckMessage; + case chrome_browser_sharing::SharingMessage::kClickToCallMessage: + return SharingMessageType::kClickToCallMessage; + } +} + +} // namespace + +void LogSharingMessageReceived( + chrome_browser_sharing::SharingMessage::PayloadCase payload_case) { + base::UmaHistogramEnumeration("Sharing.MessageReceivedType", + PayloadCaseToMessageType(payload_case)); +} + +void LogClickToCallDevicesToShow(int count) { + base::UmaHistogramExactLinear("Sharing.ClickToCallDevicesToShow", count, + /*value_max=*/20); +} + +void LogClickToCallAppsToShow(int count) { + base::UmaHistogramExactLinear("Sharing.ClickToCallAppsToShow", count, + /*value_max=*/20); +}
diff --git a/chrome/browser/sharing/sharing_metrics.h b/chrome/browser/sharing/sharing_metrics.h new file mode 100644 index 0000000..c1f13278 --- /dev/null +++ b/chrome/browser/sharing/sharing_metrics.h
@@ -0,0 +1,23 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CHROME_BROWSER_SHARING_SHARING_METRICS_H_ +#define CHROME_BROWSER_SHARING_SHARING_METRICS_H_ + +#include "chrome/browser/sharing/proto/sharing_message.pb.h" + +// Logs the |payload_case| to UMA. This should be called when a SharingMessage +// is received. +void LogSharingMessageReceived( + chrome_browser_sharing::SharingMessage::PayloadCase payload_case); + +// Logs the number of available devices that are about to be shown in a UI for +// picking a device to start a phone call on. +void LogClickToCallDevicesToShow(int count); + +// Logs the number of available apps that are about to be shown in a UI for +// picking an app to start a phone call with. +void LogClickToCallAppsToShow(int count); + +#endif // CHROME_BROWSER_SHARING_SHARING_METRICS_H_
diff --git a/chrome/browser/sharing/sharing_service.cc b/chrome/browser/sharing/sharing_service.cc index 5e620b8..b17f47e2 100644 --- a/chrome/browser/sharing/sharing_service.cc +++ b/chrome/browser/sharing/sharing_service.cc
@@ -31,6 +31,12 @@ namespace { // TODO(knollr): Should this be configurable or shared between similar features? constexpr base::TimeDelta kDeviceExpiration = base::TimeDelta::FromDays(2); + +// Amount of time before a message is considered timeout if no ack is received. +constexpr base::TimeDelta kSendMessageTimeout = + base::TimeDelta::FromSeconds(10); + +// Backoff policy for registration retry. constexpr net::BackoffEntry::Policy kRetryBackoffPolicy = { // Number of initial errors (in sequence) to ignore before applying // exponential back-off rules. @@ -87,6 +93,7 @@ fcm_handler_->AddSharingHandler( chrome_browser_sharing::SharingMessage::kAckMessage, &ack_message_handler_); + ack_message_handler_.AddObserver(this); fcm_handler_->AddSharingHandler( chrome_browser_sharing::SharingMessage::kPingMessage, &ping_message_handler_); @@ -116,6 +123,8 @@ } SharingService::~SharingService() { + ack_message_handler_.RemoveObserver(this); + if (sync_service_ && sync_service_->HasObserver(this)) sync_service_->RemoveObserver(this); } @@ -180,8 +189,41 @@ base::TimeDelta time_to_live, chrome_browser_sharing::SharingMessage message, SendMessageCallback callback) { - fcm_sender_->SendMessageToDevice(device_guid, time_to_live, - std::move(message), std::move(callback)); + fcm_sender_->SendMessageToDevice( + device_guid, time_to_live, std::move(message), + base::BindOnce(&SharingService::OnMessageSent, + weak_ptr_factory_.GetWeakPtr(), std::move(callback))); +} + +void SharingService::OnMessageSent(SendMessageCallback callback, + base::Optional<std::string> message_id) { + if (!message_id) { + std::move(callback).Run(false); + return; + } + + send_message_callbacks_.emplace(*message_id, std::move(callback)); + + base::PostDelayedTaskWithTraits( + FROM_HERE, {base::TaskPriority::BEST_EFFORT, content::BrowserThread::UI}, + base::BindOnce(&SharingService::InvokeSendMessageCallback, + weak_ptr_factory_.GetWeakPtr(), *message_id, false), + kSendMessageTimeout); +} + +void SharingService::OnAckReceived(const std::string& message_id) { + InvokeSendMessageCallback(message_id, /*success=*/true); +} + +void SharingService::InvokeSendMessageCallback(const std::string& message_id, + bool result) { + auto iter = send_message_callbacks_.find(message_id); + if (iter == send_message_callbacks_.end()) + return; + + SendMessageCallback callback = std::move(iter->second); + send_message_callbacks_.erase(iter); + std::move(callback).Run(result); } void SharingService::RegisterHandler(
diff --git a/chrome/browser/sharing/sharing_service.h b/chrome/browser/sharing/sharing_service.h index b51f288..c0f65ca 100644 --- a/chrome/browser/sharing/sharing_service.h +++ b/chrome/browser/sharing/sharing_service.h
@@ -5,6 +5,7 @@ #ifndef CHROME_BROWSER_SHARING_SHARING_SERVICE_H_ #define CHROME_BROWSER_SHARING_SHARING_SERVICE_H_ +#include <map> #include <memory> #include <string> #include <vector> @@ -40,10 +41,11 @@ // Class to manage lifecycle of sharing feature, and provide APIs to send // sharing messages to other devices. -class SharingService : public KeyedService, syncer::SyncServiceObserver { +class SharingService : public KeyedService, + syncer::SyncServiceObserver, + AckMessageHandler::AckMessageObserver { public: - using SendMessageCallback = - base::OnceCallback<void(base::Optional<std::string>)>; + using SendMessageCallback = base::OnceCallback<void(bool)>; enum class State { // Device is unregistered with FCM and Sharing is unavailable. @@ -95,10 +97,16 @@ void OnSyncShutdown(syncer::SyncService* sync) override; void OnStateChanged(syncer::SyncService* sync) override; + // AckMessageHandler::AckMessageObserver override. + void OnAckReceived(const std::string& message_id) override; + void RegisterDevice(); void UnregisterDevice(); void OnDeviceRegistered(SharingDeviceRegistration::Result result); void OnDeviceUnregistered(SharingDeviceRegistration::Result result); + void OnMessageSent(SendMessageCallback callback, + base::Optional<std::string> message_id); + void InvokeSendMessageCallback(const std::string& message_id, bool result); // Returns true if sync is active and sync preference is enabled. bool IsSyncEnabled() const; @@ -115,6 +123,7 @@ PingMessageHandler ping_message_handler_; net::BackoffEntry backoff_entry_; State state_; + std::map<std::string, SendMessageCallback> send_message_callbacks_; #if defined(OS_ANDROID) ClickToCallMessageHandler click_to_call_message_handler_;
diff --git a/chrome/browser/sharing/sharing_service_unittest.cc b/chrome/browser/sharing/sharing_service_unittest.cc index 6ce5bb4..3937587 100644 --- a/chrome/browser/sharing/sharing_service_unittest.cc +++ b/chrome/browser/sharing/sharing_service_unittest.cc
@@ -9,10 +9,12 @@ #include "base/guid.h" #include "base/memory/ptr_util.h" +#include "base/optional.h" #include "base/test/scoped_feature_list.h" #include "base/test/scoped_task_environment.h" #include "chrome/browser/sharing/fake_local_device_info_provider.h" #include "chrome/browser/sharing/features.h" +#include "chrome/browser/sharing/proto/sharing_message.pb.h" #include "chrome/browser/sharing/sharing_device_info.h" #include "chrome/browser/sharing/sharing_device_registration.h" #include "chrome/browser/sharing/sharing_fcm_handler.h" @@ -41,22 +43,35 @@ const char kAuthSecret[] = "auth_secret"; const char kFcmToken[] = "fcm_token"; const char kDeviceName[] = "other_name"; +const char kMessageId[] = "message_id"; const int kTtlSeconds = 10; -class MockGCMDriver : public gcm::FakeGCMDriver { +class FakeGCMDriver : public gcm::FakeGCMDriver { public: - MockGCMDriver() {} - ~MockGCMDriver() override {} + FakeGCMDriver() {} + ~FakeGCMDriver() override {} - MOCK_METHOD8(SendWebPushMessage, - void(const std::string& app_id, - const std::string& authorized_entity, - const std::string& p256dh, - const std::string& auth_secret, - const std::string& fcm_token, - crypto::ECPrivateKey* vapid_key, - gcm::WebPushMessage message, - gcm::GCMDriver::SendWebPushMessageCallback callback)); + void SendWebPushMessage( + const std::string& app_id, + const std::string& authorized_entity, + const std::string& p256dh, + const std::string& auth_secret, + const std::string& fcm_token, + crypto::ECPrivateKey* vapid_key, + gcm::WebPushMessage message, + gcm::GCMDriver::SendWebPushMessageCallback callback) override { + p256dh_ = p256dh; + auth_secret_ = auth_secret; + fcm_token_ = fcm_token; + std::move(callback).Run(base::make_optional(kMessageId)); + } + + const std::string& p256dh() { return p256dh_; } + const std::string& auth_secret() { return auth_secret_; } + const std::string& fcm_token() { return fcm_token_; } + + private: + std::string p256dh_, auth_secret_, fcm_token_; }; class MockInstanceIDDriver : public InstanceIDDriver { @@ -69,12 +84,33 @@ }; class MockSharingFCMHandler : public SharingFCMHandler { + using SharingMessage = chrome_browser_sharing::SharingMessage; + public: MockSharingFCMHandler() : SharingFCMHandler(nullptr, nullptr) {} ~MockSharingFCMHandler() = default; MOCK_METHOD0(StartListening, void()); MOCK_METHOD0(StopListening, void()); + + void AddSharingHandler(const SharingMessage::PayloadCase& payload_case, + SharingMessageHandler* handler) override { + sharing_handlers_[payload_case] = handler; + } + + void RemoveSharingHandler( + const SharingMessage::PayloadCase& payload_case) override { + sharing_handlers_.erase(payload_case); + } + + SharingMessageHandler* GetSharingHandler( + const SharingMessage::PayloadCase& payload_case) { + return sharing_handlers_[payload_case]; + } + + private: + std::map<SharingMessage::PayloadCase, SharingMessageHandler*> + sharing_handlers_; }; class FakeSharingDeviceRegistration : public SharingDeviceRegistration { @@ -122,16 +158,20 @@ sync_prefs_ = new SharingSyncPreference(&prefs_); sharing_device_registration_ = new FakeSharingDeviceRegistration( sync_prefs_, &mock_instance_id_driver_, vapid_key_manager_, - &mock_gcm_driver_, &fake_local_device_info_provider_); + &fake_gcm_driver_, &fake_local_device_info_provider_); vapid_key_manager_ = new VapidKeyManager(sync_prefs_); - fcm_sender_ = new SharingFCMSender(&mock_gcm_driver_, + fcm_sender_ = new SharingFCMSender(&fake_gcm_driver_, &fake_local_device_info_provider_, sync_prefs_, vapid_key_manager_); fcm_handler_ = new NiceMock<MockSharingFCMHandler>(); SharingSyncPreference::RegisterProfilePrefs(prefs_.registry()); } - void OnMessageSent(base::Optional<std::string> message_id) {} + void OnMessageSent(bool success) { + send_message_success_ = base::make_optional(success); + } + + base::Optional<bool> send_message_success() { return send_message_success_; } protected: static std::unique_ptr<syncer::DeviceInfo> CreateFakeDeviceInfo( @@ -170,9 +210,9 @@ FakeLocalDeviceInfoProvider fake_local_device_info_provider_; syncer::TestSyncService test_sync_service_; sync_preferences::TestingPrefServiceSyncable prefs_; + FakeGCMDriver fake_gcm_driver_; NiceMock<MockInstanceIDDriver> mock_instance_id_driver_; - NiceMock<MockGCMDriver> mock_gcm_driver_; NiceMock<MockSharingFCMHandler>* fcm_handler_; SharingSyncPreference* sync_prefs_; @@ -182,6 +222,7 @@ private: std::unique_ptr<SharingService> sharing_service_ = nullptr; + base::Optional<bool> send_message_success_; }; } // namespace @@ -288,22 +329,70 @@ EXPECT_EQ(id2, candidates[0].guid()); } -TEST_F(SharingServiceTest, SendMessageToDevice) { +TEST_F(SharingServiceTest, SendMessageToDeviceSuccess) { std::string id = base::GenerateGUID(); std::unique_ptr<syncer::DeviceInfo> device_info = CreateFakeDeviceInfo(id, kDeviceName); device_info_tracker_.Add(device_info.get()); sync_prefs_->SetSyncDevice(id, CreateFakeSyncDevice()); - EXPECT_CALL(mock_gcm_driver_, - SendWebPushMessage(_, _, Eq(kP256dh), Eq(kAuthSecret), - Eq(kFcmToken), _, _, _)) - .Times(1); GetSharingService()->SendMessageToDevice( id, base::TimeDelta::FromSeconds(kTtlSeconds), chrome_browser_sharing::SharingMessage(), base::BindOnce(&SharingServiceTest::OnMessageSent, base::Unretained(this))); + + EXPECT_EQ(kP256dh, fake_gcm_driver_.p256dh()); + EXPECT_EQ(kAuthSecret, fake_gcm_driver_.auth_secret()); + EXPECT_EQ(kFcmToken, fake_gcm_driver_.fcm_token()); + + // Simulate ack message received by AckMessageHandler. + SharingMessageHandler* ack_message_handler = fcm_handler_->GetSharingHandler( + chrome_browser_sharing::SharingMessage::kAckMessage); + EXPECT_TRUE(ack_message_handler); + + chrome_browser_sharing::SharingMessage ack_message; + ack_message.mutable_ack_message()->set_original_message_id(kMessageId); + ack_message_handler->OnMessage(ack_message); + + EXPECT_TRUE(send_message_success().has_value()); + EXPECT_TRUE(*send_message_success()); +} + +TEST_F(SharingServiceTest, SendMessageToDeviceExpired) { + std::string id = base::GenerateGUID(); + std::unique_ptr<syncer::DeviceInfo> device_info = + CreateFakeDeviceInfo(id, kDeviceName); + device_info_tracker_.Add(device_info.get()); + sync_prefs_->SetSyncDevice(id, CreateFakeSyncDevice()); + + GetSharingService()->SendMessageToDevice( + id, base::TimeDelta::FromSeconds(kTtlSeconds), + chrome_browser_sharing::SharingMessage(), + base::BindOnce(&SharingServiceTest::OnMessageSent, + base::Unretained(this))); + + EXPECT_EQ(kP256dh, fake_gcm_driver_.p256dh()); + EXPECT_EQ(kAuthSecret, fake_gcm_driver_.auth_secret()); + EXPECT_EQ(kFcmToken, fake_gcm_driver_.fcm_token()); + + // Advance time so send message will expire. + scoped_task_environment_.FastForwardBy(base::TimeDelta::FromSeconds(10)); + EXPECT_TRUE(send_message_success().has_value()); + EXPECT_FALSE(*send_message_success()); + + // Simulate ack message received by AckMessageHandler, which will be + // disregarded. + SharingMessageHandler* ack_message_handler = fcm_handler_->GetSharingHandler( + chrome_browser_sharing::SharingMessage::kAckMessage); + EXPECT_TRUE(ack_message_handler); + + chrome_browser_sharing::SharingMessage ack_message; + ack_message.mutable_ack_message()->set_original_message_id(kMessageId); + ack_message_handler->OnMessage(ack_message); + + EXPECT_TRUE(send_message_success().has_value()); + EXPECT_FALSE(*send_message_success()); } TEST_F(SharingServiceTest, DeviceRegistration) {
diff --git a/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.cc b/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.cc new file mode 100644 index 0000000..16a7a43df --- /dev/null +++ b/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.cc
@@ -0,0 +1,358 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.h" + +#include <utility> + +#include "base/json/json_reader.h" +#include "base/logging.h" +#include "base/optional.h" +#include "base/strings/stringprintf.h" +#include "base/time/time.h" +#include "chrome/browser/profiles/profile.h" +#include "chrome/browser/signin/identity_manager_factory.h" +#include "chrome/browser/supervised_user/supervised_user_constants.h" +#include "components/google/core/common/google_util.h" +#include "components/signin/public/identity_manager/access_token_info.h" +#include "components/signin/public/identity_manager/identity_manager.h" +#include "components/signin/public/identity_manager/primary_account_access_token_fetcher.h" +#include "content/public/browser/browser_context.h" +#include "content/public/browser/storage_partition.h" +#include "google_apis/gaia/google_service_auth_error.h" +#include "google_apis/google_api_keys.h" +#include "net/base/escape.h" +#include "net/base/load_flags.h" +#include "net/http/http_status_code.h" +#include "net/traffic_annotation/network_traffic_annotation.h" +#include "net/url_request/url_request_status.h" +#include "services/identity/public/cpp/scope_set.h" +#include "services/network/public/cpp/resource_request.h" +#include "services/network/public/cpp/shared_url_loader_factory.h" +#include "services/network/public/cpp/simple_url_loader.h" +#include "url/gurl.h" +#include "url/url_constants.h" + +namespace { + +enum class RequestMethod { + kClassifyUrl, + kListFamilyMembers, + kRequestRestrictedUrlAccess, +}; + +constexpr char kClassifyUrlDataContentType[] = + "application/x-www-form-urlencoded"; + +// Constants for ClassifyURL. +constexpr char kClassifyUrlRequestApiPath[] = + "https://kidsmanagement-pa.googleapis.com/kidsmanagement/v1/people/" + "me:classifyUrl"; +constexpr char kClassifyUrlKidPermissionScope[] = + "https://www.googleapis.com/auth/kid.permission"; +constexpr char kClassifyUrlOauthConsumerName[] = "kids_url_classifier"; +constexpr char kClassifyUrlDataFormat[] = "url=%s®ion_code=%s"; +constexpr char kClassifyUrlAllowed[] = "allowed"; +constexpr char kClassifyUrlRestricted[] = "restricted"; + +// TODO(crbug.com/980273): remove conversion methods when experiment flag is +// fully flipped. More info on crbug.com/978130. + +// Converts the ClassifyUrlRequest proto to a serialized string in the +// format that the Kids Management API receives. +std::string GetClassifyURLRequestString( + kids_chrome_management::ClassifyUrlRequest* request_proto) { + std::string query = + net::EscapeQueryParamValue(request_proto->url(), true /* use_plus */); + return base::StringPrintf(kClassifyUrlDataFormat, query.c_str(), + request_proto->region_code().c_str()); +} + +// Converts the serialized string returned by the Kids Management API to a +// ClassifyUrlResponse proto object. +std::unique_ptr<kids_chrome_management::ClassifyUrlResponse> +GetClassifyURLResponseProto(const std::string& response) { + base::Optional<base::Value> optional_value = base::JSONReader::Read(response); + const base::DictionaryValue* dict = nullptr; + + auto response_proto = + std::make_unique<kids_chrome_management::ClassifyUrlResponse>(); + + if (!optional_value || !optional_value.value().GetAsDictionary(&dict)) { + DLOG(WARNING) + << "GetClassifyURLResponseProto failed to parse response dictionary"; + response_proto->set_display_classification( + kids_chrome_management::ClassifyUrlResponse:: + UNKNOWN_DISPLAY_CLASSIFICATION); + return response_proto; + } + + const base::Value* classification_value = + dict->FindKey("displayClassification"); + if (!classification_value) { + DLOG(WARNING) + << "GetClassifyURLResponseProto failed to parse displayClassification"; + response_proto->set_display_classification( + kids_chrome_management::ClassifyUrlResponse:: + UNKNOWN_DISPLAY_CLASSIFICATION); + return response_proto; + } + + const std::string classification_string = classification_value->GetString(); + if (classification_string == kClassifyUrlAllowed) { + response_proto->set_display_classification( + kids_chrome_management::ClassifyUrlResponse::ALLOWED); + } else if (classification_string == kClassifyUrlRestricted) { + response_proto->set_display_classification( + kids_chrome_management::ClassifyUrlResponse::RESTRICTED); + } else { + DLOG(WARNING) + << "GetClassifyURLResponseProto expected a valid displayClassification"; + response_proto->set_display_classification( + kids_chrome_management::ClassifyUrlResponse:: + UNKNOWN_DISPLAY_CLASSIFICATION); + } + + return response_proto; +} + +} // namespace + +struct KidsChromeManagementClient::KidsChromeManagementRequest { + KidsChromeManagementRequest( + std::unique_ptr<google::protobuf::MessageLite> request_proto, + KidsChromeManagementClient::KidsChromeManagementCallback callback, + std::unique_ptr<network::ResourceRequest> resource_request, + const net::NetworkTrafficAnnotationTag traffic_annotation, + const char* oauth_consumer_name, + const char* scope, + const RequestMethod method) + : request_proto(std::move(request_proto)), + callback(std::move(callback)), + resource_request(std::move(resource_request)), + traffic_annotation(traffic_annotation), + access_token_expired(false), + oauth_consumer_name(oauth_consumer_name), + scope(scope), + method(method) {} + + KidsChromeManagementRequest(KidsChromeManagementRequest&&) = default; + + ~KidsChromeManagementRequest() { DCHECK(!callback); } + + std::unique_ptr<google::protobuf::MessageLite> request_proto; + KidsChromeManagementCallback callback; + std::unique_ptr<network::ResourceRequest> resource_request; + const net::NetworkTrafficAnnotationTag traffic_annotation; + std::unique_ptr<identity::PrimaryAccountAccessTokenFetcher> + access_token_fetcher; + bool access_token_expired; + const char* oauth_consumer_name; + const char* scope; + const RequestMethod method; +}; + +KidsChromeManagementClient::KidsChromeManagementClient(Profile* profile) { + url_loader_factory_ = + content::BrowserContext::GetDefaultStoragePartition(profile) + ->GetURLLoaderFactoryForBrowserProcess(); + + identity_manager_ = IdentityManagerFactory::GetForProfile(profile); +} + +KidsChromeManagementClient::~KidsChromeManagementClient() = default; + +void KidsChromeManagementClient::ClassifyURL( + std::unique_ptr<kids_chrome_management::ClassifyUrlRequest> request_proto, + KidsChromeManagementCallback callback) { + DVLOG(1) << "Checking URL: " << request_proto->url(); + + auto resource_request = std::make_unique<network::ResourceRequest>(); + resource_request->url = GURL(kClassifyUrlRequestApiPath); + resource_request->method = "POST"; + resource_request->load_flags = + net::LOAD_DO_NOT_SEND_COOKIES | net::LOAD_DO_NOT_SAVE_COOKIES; + + const net::NetworkTrafficAnnotationTag traffic_annotation = + net::DefineNetworkTrafficAnnotation( + "kids_chrome_management_client_classify_url", R"( + semantics { + sender: "Supervised Users" + description: + "Checks whether a given URL (or set of URLs) is considered safe by " + "a Google Family Link web restrictions API." + trigger: + "If the parent enabled this feature for the child account, this is " + "sent for every navigation." + data: + "An OAuth2 access token identifying and authenticating the " + "Google account, and the URL to be checked." + destination: GOOGLE_OWNED_SERVICE + } + policy { + cookies_allowed: NO + setting: + "This feature is only used in child accounts and cannot be " + "disabled by settings. Parent accounts can disable it in the " + "family dashboard." + policy_exception_justification: + "Enterprise admins don't have control over this feature " + "because it can't be enabled on enterprise environements." + })"); + + auto kids_chrome_request = std::make_unique<KidsChromeManagementRequest>( + std::move(request_proto), std::move(callback), + std::move(resource_request), traffic_annotation, + kClassifyUrlOauthConsumerName, kClassifyUrlKidPermissionScope, + RequestMethod::kClassifyUrl); + + MakeHTTPRequest(std::move(kids_chrome_request)); +} + +void KidsChromeManagementClient::MakeHTTPRequest( + std::unique_ptr<KidsChromeManagementRequest> kids_chrome_request) { + requests_in_progress_.push_front(std::move(kids_chrome_request)); + + StartFetching(requests_in_progress_.begin()); +} + +// Helpful reading for the next 4 methods: +// https://chromium.googlesource.com/chromium/src.git/+/master/docs/callback.md#partial-binding-of-parameters-currying + +void KidsChromeManagementClient::StartFetching( + KidsChromeRequestList::iterator it) { + KidsChromeManagementRequest* req = it->get(); + + identity::ScopeSet scopes{req->scope}; + + req->access_token_fetcher = + std::make_unique<identity::PrimaryAccountAccessTokenFetcher>( + req->oauth_consumer_name, identity_manager_, scopes, + base::BindOnce( + &KidsChromeManagementClient::OnAccessTokenFetchComplete, + base::Unretained(this), it), + identity::PrimaryAccountAccessTokenFetcher::Mode::kImmediate); +} + +void KidsChromeManagementClient::OnAccessTokenFetchComplete( + KidsChromeRequestList::iterator it, + GoogleServiceAuthError error, + identity::AccessTokenInfo token_info) { + if (error.state() != GoogleServiceAuthError::NONE) { + DLOG(WARNING) << "Token error: " << error.ToString(); + + std::unique_ptr<google::protobuf::MessageLite> response_proto = nullptr; + DispatchResult(it, std::move(response_proto), + KidsChromeManagementClient::ErrorCode::kTokenError); + return; + } + + KidsChromeManagementRequest* req = it->get(); + + req->resource_request->headers.SetHeader( + net::HttpRequestHeaders::kAuthorization, + base::StringPrintf(supervised_users::kAuthorizationHeaderFormat, + token_info.token.c_str())); + + std::string request_data; + // TODO(crbug.com/980273): remove this when experiment flag is fully flipped. + if (req->method == RequestMethod::kClassifyUrl) { + request_data = GetClassifyURLRequestString( + static_cast<kids_chrome_management::ClassifyUrlRequest*>( + req->request_proto.get())); + } else { + DVLOG(1) << "Could not detect the request proto's class."; + std::unique_ptr<google::protobuf::MessageLite> response_proto = nullptr; + DispatchResult(it, std::move(response_proto), + KidsChromeManagementClient::ErrorCode::kServiceError); + return; + } + + std::unique_ptr<network::SimpleURLLoader> simple_url_loader = + network::SimpleURLLoader::Create(std::move(req->resource_request), + req->traffic_annotation); + + simple_url_loader->AttachStringForUpload(request_data, + kClassifyUrlDataContentType); + + simple_url_loader->DownloadToString( + url_loader_factory_.get(), + base::BindOnce(&KidsChromeManagementClient::OnSimpleLoaderComplete, + base::Unretained(this), it, std::move(simple_url_loader), + token_info), + /*max_body_size*/ 128); +} + +void KidsChromeManagementClient::OnSimpleLoaderComplete( + KidsChromeRequestList::iterator it, + std::unique_ptr<network::SimpleURLLoader> simple_url_loader, + identity::AccessTokenInfo token_info, + std::unique_ptr<std::string> response_body) { + int response_code = -1; + + if (simple_url_loader->ResponseInfo() && + simple_url_loader->ResponseInfo()->headers) { + response_code = simple_url_loader->ResponseInfo()->headers->response_code(); + + KidsChromeManagementRequest* req = it->get(); + // Handle first HTTP_UNAUTHORIZED response by removing access token and + // restarting the request from the beginning (fetching access token). + if (response_code == net::HTTP_UNAUTHORIZED && !req->access_token_expired) { + DLOG(WARNING) << "Access token expired:\n" << token_info.token; + req->access_token_expired = true; + identity::ScopeSet scopes{req->scope}; + identity_manager_->RemoveAccessTokenFromCache( + identity_manager_->GetPrimaryAccountId(), scopes, token_info.token); + StartFetching(it); + return; + } + } + + std::unique_ptr<google::protobuf::MessageLite> response_proto = nullptr; + + int net_error = simple_url_loader->NetError(); + + if (net_error != net::OK) { + DLOG(WARNING) << "Network error " << net_error; + DispatchResult(it, std::move(response_proto), + KidsChromeManagementClient::ErrorCode::kNetworkError); + return; + } + + if (response_code != net::HTTP_OK) { + DLOG(WARNING) << "Response: " << response_body.get(); + DispatchResult(it, std::move(response_proto), + KidsChromeManagementClient::ErrorCode::kHttpError); + return; + } + + // |response_body| is nullptr only in case of failure. + if (!response_body) { + DLOG(WARNING) << "URL request failed! Letting through..."; + DispatchResult(it, std::move(response_proto), + KidsChromeManagementClient::ErrorCode::kNetworkError); + return; + } + + if (it->get()->method == RequestMethod::kClassifyUrl) { + response_proto = GetClassifyURLResponseProto(*response_body); + } else { + DVLOG(1) << "Could not detect the request proto class."; + DispatchResult(it, std::move(response_proto), + KidsChromeManagementClient::ErrorCode::kServiceError); + return; + } + + DispatchResult(it, std::move(response_proto), + KidsChromeManagementClient::ErrorCode::kSuccess); +} + +void KidsChromeManagementClient::DispatchResult( + KidsChromeRequestList::iterator it, + std::unique_ptr<google::protobuf::MessageLite> response_proto, + ErrorCode error) { + std::move(it->get()->callback).Run(std::move(response_proto), error); + + requests_in_progress_.erase(it); +}
diff --git a/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.h b/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.h new file mode 100644 index 0000000..10a5a1a --- /dev/null +++ b/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.h
@@ -0,0 +1,114 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CHROME_BROWSER_SUPERVISED_USER_KIDS_CHROME_MANAGEMENT_KIDS_CHROME_MANAGEMENT_CLIENT_H_ +#define CHROME_BROWSER_SUPERVISED_USER_KIDS_CHROME_MANAGEMENT_KIDS_CHROME_MANAGEMENT_CLIENT_H_ + +#include <list> +#include <memory> +#include <string> + +#include "base/callback.h" +#include "base/macros.h" +#include "base/memory/scoped_refptr.h" +#include "chrome/browser/supervised_user/kids_chrome_management/kidschromemanagement_messages.pb.h" +#include "components/keyed_service/core/keyed_service.h" +#include "third_party/protobuf/src/google/protobuf/message_lite.h" + +namespace identity { +struct AccessTokenInfo; +class IdentityManager; +} // namespace identity + +namespace network { +class SharedURLLoaderFactory; +class SimpleURLLoader; +} // namespace network + +class GoogleServiceAuthError; +class Profile; + +// Provides an interface between Family Link RPC clients (e.g. +// KidsManagementURLChecker) and the Kids Chrome Management Service. +// Communicates with the server and performs HTTP requests. +class KidsChromeManagementClient : public KeyedService { + public: + enum class ErrorCode { + kSuccess = 0, + kTokenError, // Failed to get OAuth2 token. + kNetworkError, // Network failure. + kHttpError, // HTTP error. + kServiceError, // Service returned an error or malformed reply. + }; + + using KidsChromeManagementCallback = base::OnceCallback<void( + std::unique_ptr<google::protobuf::MessageLite> response_proto, + ErrorCode error_code)>; + + explicit KidsChromeManagementClient(Profile* profile); + + ~KidsChromeManagementClient() override; + + // Each of the next three methods is the interface to an RPC client. + // They receive only what's necessary for a request: + // - The request proto, specific to each RPC. + // - The callback that will receive the response proto and error code. + + // Interface to KidsManagementURLCheckerClient. Classifies a URL as safe + // or restricted for a supervised user. + void ClassifyURL( + std::unique_ptr<kids_chrome_management::ClassifyUrlRequest> request_proto, + KidsChromeManagementCallback callback); + + // TODO(crbug.com/979618): implement ListFamilyMembers method. + + // TODO(crbug.com/979619): implement RequestRestrictedURLAccess method. + + private: + // Every request must be represented by an instance of this struct. It will be + // added to a request list and its iterator will be passed along to the + // callbacks with request-specific information. + struct KidsChromeManagementRequest; + + // Using a list ensures that iterators won't be invalidated when other + // elements are added/erased. + using KidsChromeRequestList = + std::list<std::unique_ptr<KidsChromeManagementRequest>>; + + // Starts the execution flow by adding the request struct iterator to the + // execution list. + void MakeHTTPRequest( + std::unique_ptr<KidsChromeManagementRequest> kids_chrome_request); + + // Fetches the user's access token. + void StartFetching(KidsChromeRequestList::iterator it); + + void OnAccessTokenFetchComplete( + KidsChromeRequestList::iterator kids_chrome_request, + GoogleServiceAuthError auth_error, + identity::AccessTokenInfo token_info); + + void OnSimpleLoaderComplete( + KidsChromeRequestList::iterator kids_chrome_request, + std::unique_ptr<network::SimpleURLLoader> simple_url_loader, + identity::AccessTokenInfo token_info, + std::unique_ptr<std::string> response_body); + + // Calls the callback provided by the existing RPC client with the response + // proto and/or error codes. + void DispatchResult( + KidsChromeRequestList::iterator kids_chrome_request, + std::unique_ptr<google::protobuf::MessageLite> response_proto, + ErrorCode error); + + scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory_; + identity::IdentityManager* identity_manager_; + + // List of requests in execution. + KidsChromeRequestList requests_in_progress_; + + DISALLOW_COPY_AND_ASSIGN(KidsChromeManagementClient); +}; + +#endif // CHROME_BROWSER_SUPERVISED_USER_KIDS_CHROME_MANAGEMENT_KIDS_CHROME_MANAGEMENT_CLIENT_H_
diff --git a/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client_factory.cc b/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client_factory.cc new file mode 100644 index 0000000..f502b0ea --- /dev/null +++ b/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client_factory.cc
@@ -0,0 +1,35 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client_factory.h" + +#include "chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.h" +#include "components/keyed_service/content/browser_context_dependency_manager.h" + +// static +KidsChromeManagementClient* +KidsChromeManagementClientFactory::GetForBrowserContext(Profile* profile) { + return static_cast<KidsChromeManagementClient*>( + GetInstance()->GetServiceForBrowserContext(profile, true)); +} + +// static +KidsChromeManagementClientFactory* +KidsChromeManagementClientFactory::GetInstance() { + static base::NoDestructor<KidsChromeManagementClientFactory> factory; + return factory.get(); +} + +KidsChromeManagementClientFactory::KidsChromeManagementClientFactory() + : BrowserContextKeyedServiceFactory( + "KidsChromeManagementClientFactory", + BrowserContextDependencyManager::GetInstance()) {} + +KidsChromeManagementClientFactory::~KidsChromeManagementClientFactory() = + default; + +KeyedService* KidsChromeManagementClientFactory::BuildServiceInstanceFor( + content::BrowserContext* context) const { + return new KidsChromeManagementClient(static_cast<Profile*>(context)); +}
diff --git a/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client_factory.h b/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client_factory.h new file mode 100644 index 0000000..7d836db --- /dev/null +++ b/chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client_factory.h
@@ -0,0 +1,44 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CHROME_BROWSER_SUPERVISED_USER_KIDS_CHROME_MANAGEMENT_KIDS_CHROME_MANAGEMENT_CLIENT_FACTORY_H_ +#define CHROME_BROWSER_SUPERVISED_USER_KIDS_CHROME_MANAGEMENT_KIDS_CHROME_MANAGEMENT_CLIENT_FACTORY_H_ + +#include "base/macros.h" +#include "base/no_destructor.h" +#include "chrome/browser/profiles/profile.h" +#include "components/keyed_service/content/browser_context_keyed_service_factory.h" + +namespace content { +class BrowserContext; +} + +class KidsChromeManagementClient; + +// Singleton that owns all KidsChromeManagementClient instances and associates +// them with Profiles. Listens for the Profile's destruction +// notification and cleans up the associated KidsChromeManagementClient. +class KidsChromeManagementClientFactory + : public BrowserContextKeyedServiceFactory { + public: + static KidsChromeManagementClient* GetForBrowserContext(Profile* profile); + + static KidsChromeManagementClientFactory* GetInstance(); + + private: + friend class base::NoDestructor<KidsChromeManagementClientFactory>; + + KidsChromeManagementClientFactory(); + ~KidsChromeManagementClientFactory() override; + + // The context parameter is guaranteed to be a Profile* because this is what + // GetForBrowserContext receives. It's only declared as a BrowserContext* + // because this method is overriding another one from the parent class. + KeyedService* BuildServiceInstanceFor( + content::BrowserContext* context) const override; + + DISALLOW_COPY_AND_ASSIGN(KidsChromeManagementClientFactory); +}; + +#endif // CHROME_BROWSER_SUPERVISED_USER_KIDS_CHROME_MANAGEMENT_KIDS_CHROME_MANAGEMENT_CLIENT_FACTORY_H_
diff --git a/chrome/browser/supervised_user/legacy/custodian_profile_downloader_service.cc b/chrome/browser/supervised_user/legacy/custodian_profile_downloader_service.cc index 2340cf4..f5efd3a 100644 --- a/chrome/browser/supervised_user/legacy/custodian_profile_downloader_service.cc +++ b/chrome/browser/supervised_user/legacy/custodian_profile_downloader_service.cc
@@ -9,6 +9,7 @@ #include "chrome/common/pref_names.h" #include "components/prefs/pref_service.h" #include "components/signin/public/identity_manager/identity_manager.h" +#include "content/public/browser/storage_partition.h" #include "google_apis/gaia/gaia_auth_util.h" CustodianProfileDownloaderService::CustodianProfileDownloaderService( @@ -58,9 +59,18 @@ return std::string(); } -Profile* CustodianProfileDownloaderService::GetBrowserProfile() { +identity::IdentityManager* +CustodianProfileDownloaderService::GetIdentityManager() { DCHECK(custodian_profile_); - return custodian_profile_; + return IdentityManagerFactory::GetForProfile(custodian_profile_); +} + +network::mojom::URLLoaderFactory* +CustodianProfileDownloaderService::GetURLLoaderFactory() { + DCHECK(custodian_profile_); + return content::BrowserContext::GetDefaultStoragePartition(custodian_profile_) + ->GetURLLoaderFactoryForBrowserProcess() + .get(); } bool CustodianProfileDownloaderService::IsPreSignin() const {
diff --git a/chrome/browser/supervised_user/legacy/custodian_profile_downloader_service.h b/chrome/browser/supervised_user/legacy/custodian_profile_downloader_service.h index d257193..26f473e 100644 --- a/chrome/browser/supervised_user/legacy/custodian_profile_downloader_service.h +++ b/chrome/browser/supervised_user/legacy/custodian_profile_downloader_service.h
@@ -10,6 +10,8 @@ #include "chrome/browser/profiles/profile_downloader_delegate.h" #include "components/keyed_service/core/keyed_service.h" +class Profile; + class CustodianProfileDownloaderService : public KeyedService, public ProfileDownloaderDelegate { public: @@ -34,7 +36,8 @@ bool NeedsProfilePicture() const override; int GetDesiredImageSideLength() const override; std::string GetCachedPictureURL() const override; - Profile* GetBrowserProfile() override; + identity::IdentityManager* GetIdentityManager() override; + network::mojom::URLLoaderFactory* GetURLLoaderFactory() override; bool IsPreSignin() const override; void OnProfileDownloadSuccess(ProfileDownloader* downloader) override; void OnProfileDownloadFailure(
diff --git a/chrome/browser/sync/test/integration/two_client_autofill_sync_test.cc b/chrome/browser/sync/test/integration/two_client_autofill_sync_test.cc index fc10f85..572ad32 100644 --- a/chrome/browser/sync/test/integration/two_client_autofill_sync_test.cc +++ b/chrome/browser/sync/test/integration/two_client_autofill_sync_test.cc
@@ -189,7 +189,7 @@ // Flaky on all platform. See crbug.com/971666 IN_PROC_BROWSER_TEST_F(TwoClientAutofillProfileSyncTest, - DISABLED_AddDuplicateProfiles_OneIsVerified) { + AddDuplicateProfiles_OneIsVerified) { ASSERT_TRUE(SetupClients()); base::HistogramTester histograms;
diff --git a/chrome/browser/themes/browser_theme_pack.cc b/chrome/browser/themes/browser_theme_pack.cc index 2173f5d..7c534e9 100644 --- a/chrome/browser/themes/browser_theme_pack.cc +++ b/chrome/browser/themes/browser_theme_pack.cc
@@ -599,6 +599,42 @@ SetColor(id, color); } +void BrowserThemePack::SetTint(int id, color_utils::HSL tint) { + DCHECK(tints_); + + int first_available_index = -1; + for (size_t i = 0; i < kTintTableLength; ++i) { + if (tints_[i].id == id) { + tints_[i].hsl = tint; + return; + } + if (tints_[i].id == -1 && first_available_index == -1) + first_available_index = i; + } + + DCHECK_NE(-1, first_available_index); + tints_[first_available_index].id = id; + tints_[first_available_index].hsl = tint; +} + +void BrowserThemePack::SetDisplayProperty(int id, int value) { + DCHECK(display_properties_); + + int first_available_index = -1; + for (size_t i = 0; i < kDisplayPropertiesSize; ++i) { + if (display_properties_[i].id == id) { + display_properties_[i].property = value; + return; + } + if (display_properties_[i].id == -1 && first_available_index == -1) + first_available_index = i; + } + + DCHECK_NE(-1, first_available_index); + display_properties_[first_available_index].id = id; + display_properties_[first_available_index].property = value; +} + SkColor BrowserThemePack::ComputeImageColor(const gfx::Image& image, int height) { // Include all colors in the analysis. @@ -760,6 +796,14 @@ pack->SetColor(TP::COLOR_TOOLBAR, colors.active_tab_color); pack->SetColor(TP::COLOR_TAB_TEXT, colors.active_tab_text_color); + + // Always use alternate logo (not colorful one) even for white/grey/black + // backgrounds. + pack->SetDisplayProperty(TP::NTP_LOGO_ALTERNATE, 1); + + // Don't change frame color for inactive window. + pack->SetTint(TP::TINT_FRAME_INACTIVE, {-1, -1, -1}); + pack->SetTint(TP::TINT_FRAME_INCOGNITO_INACTIVE, {-1, -1, -1}); } BrowserThemePack::BrowserThemePack(ThemeType theme_type) @@ -811,9 +855,7 @@ if (tints_) { for (size_t i = 0; i < kTintTableLength; ++i) { if (tints_[i].id == id) { - hsl->h = tints_[i].h; - hsl->s = tints_[i].s; - hsl->l = tints_[i].l; + *hsl = tints_[i].hsl; return true; } } @@ -1035,9 +1077,7 @@ tints_ = new TintEntry[kTintTableLength]; for (size_t i = 0; i < kTintTableLength; ++i) { tints_[i].id = -1; - tints_[i].h = -1; - tints_[i].s = -1; - tints_[i].l = -1; + tints_[i].hsl = {-1, -1, -1}; } } @@ -1103,9 +1143,7 @@ it != temp_tints.end() && count < kTintTableLength; ++it, ++count) { tints_[count].id = it->first; - tints_[count].h = it->second.h; - tints_[count].s = it->second.s; - tints_[count].l = it->second.l; + tints_[count].hsl = it->second; } }
diff --git a/chrome/browser/themes/browser_theme_pack.h b/chrome/browser/themes/browser_theme_pack.h index 4943e5e..1b5f5286 100644 --- a/chrome/browser/themes/browser_theme_pack.h +++ b/chrome/browser/themes/browser_theme_pack.h
@@ -118,7 +118,7 @@ ~BrowserThemePack() override; // Modifies |colors_| to set the entry with identifier |id| to |color|. Only - // valid to call after BuildColorsFromJSON(), which creates |colors_|. + // valid to call after InitColors(), which creates |colors_|. void SetColor(int id, SkColor color); // If |colors_| does not already contain an entry with identifier |id|, @@ -127,6 +127,14 @@ // Only valid to call after BuildColorsFromJSON(), which creates |colors_|. void SetColorIfUnspecified(int id, SkColor color); + // Sets the value for |id| in |tints_|. Only valid to call after InitTints(), + // which creates |tints_|. + void SetTint(int id, color_utils::HSL tint); + + // Sets the value for |id| in |display_properties_|. Only valid to call after + // InitDisplayProperties(), which creates |display_properties_|. + void SetDisplayProperty(int id, int value); + // Calculates the dominant color of the top |height| rows of |image|. SkColor ComputeImageColor(const gfx::Image& image, int height); @@ -293,9 +301,7 @@ // will point directly to mmapped data. struct TintEntry { int32_t id; - double h; - double s; - double l; + color_utils::HSL hsl; }* tints_ = nullptr; struct ColorPair {
diff --git a/chrome/browser/themes/browser_theme_pack_unittest.cc b/chrome/browser/themes/browser_theme_pack_unittest.cc index 7a7bc7d..38b4436 100644 --- a/chrome/browser/themes/browser_theme_pack_unittest.cc +++ b/chrome/browser/themes/browser_theme_pack_unittest.cc
@@ -1137,6 +1137,24 @@ EXPECT_NE(frame_color, toolbar_color); EXPECT_GE(color_utils::GetContrastRatio(frame_color, toolbar_color), kAutogeneratedThemeActiveTabMinContrast); + + int ntp_logo_alternate; + EXPECT_TRUE( + pack->GetDisplayProperty(TP::NTP_LOGO_ALTERNATE, &ntp_logo_alternate)); + EXPECT_EQ(1, ntp_logo_alternate); + + color_utils::HSL hsl; + EXPECT_TRUE(pack->GetTint(TP::TINT_FRAME_INACTIVE, &hsl)); + EXPECT_EQ(-1, hsl.h); + EXPECT_EQ(-1, hsl.s); + EXPECT_EQ(-1, hsl.l); + + color_utils::HSL incognito_hsl; + EXPECT_TRUE( + pack->GetTint(TP::TINT_FRAME_INCOGNITO_INACTIVE, &incognito_hsl)); + EXPECT_EQ(-1, incognito_hsl.h); + EXPECT_EQ(-1, incognito_hsl.s); + EXPECT_EQ(-1, incognito_hsl.l); } }
diff --git a/chrome/browser/ui/BUILD.gn b/chrome/browser/ui/BUILD.gn index 6efb3ac..e1ce4ef 100644 --- a/chrome/browser/ui/BUILD.gn +++ b/chrome/browser/ui/BUILD.gn
@@ -1453,8 +1453,6 @@ "ash/keyboard/chrome_keyboard_ui_factory.h", "ash/keyboard/chrome_keyboard_web_contents.cc", "ash/keyboard/chrome_keyboard_web_contents.h", - "ash/kiosk_next_shell_client.cc", - "ash/kiosk_next_shell_client.h", "ash/launcher/app_shortcut_launcher_item_controller.cc", "ash/launcher/app_shortcut_launcher_item_controller.h", "ash/launcher/app_window_launcher_controller.cc", @@ -2974,6 +2972,8 @@ "views/session_crashed_bubble_view.h", "views/sharing/click_to_call/click_to_call_dialog_view.cc", "views/sharing/click_to_call/click_to_call_dialog_view.h", + "views/sharing/click_to_call/click_to_call_icon_view.cc", + "views/sharing/click_to_call/click_to_call_icon_view.h", "views/simple_message_box_views.cc", "views/simple_message_box_views.h", "views/status_bubble_views.cc", @@ -3690,10 +3690,8 @@ "web_applications/web_app_metrics.h", "web_applications/web_app_metrics_factory.cc", "web_applications/web_app_metrics_factory.h", - "web_applications/web_app_ui_service.cc", - "web_applications/web_app_ui_service.h", - "web_applications/web_app_ui_service_factory.cc", - "web_applications/web_app_ui_service_factory.h", + "web_applications/web_app_ui_manager_impl.cc", + "web_applications/web_app_ui_manager_impl.h", "webui/extensions/extension_basic_info.cc", "webui/extensions/extension_basic_info.h", "webui/extensions/extension_icon_source.cc",
diff --git a/chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.cc b/chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.cc index 45c2f08..c9a73db7 100644 --- a/chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.cc +++ b/chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.cc
@@ -31,7 +31,6 @@ #include "chrome/browser/ui/ash/cast_config_controller_media_router.h" #include "chrome/browser/ui/ash/chrome_new_window_client.h" #include "chrome/browser/ui/ash/ime_controller_client.h" -#include "chrome/browser/ui/ash/kiosk_next_shell_client.h" #include "chrome/browser/ui/ash/launcher/chrome_launcher_controller.h" #include "chrome/browser/ui/ash/login_screen_client.h" #include "chrome/browser/ui/ash/media_client_impl.h" @@ -202,11 +201,6 @@ // Initialize TabScrubber after the Ash Shell has been initialized. TabScrubber::GetInstance(); - - if (base::FeatureList::IsEnabled(ash::features::kKioskNextShell)) { - kiosk_next_shell_client_ = std::make_unique<KioskNextShellClient>(); - kiosk_next_shell_client_->Init(); - } } void ChromeBrowserMainExtraPartsAsh::PostBrowserStart() { @@ -242,7 +236,6 @@ display_settings_handler_.reset(); media_client_.reset(); login_screen_client_.reset(); - kiosk_next_shell_client_.reset(); // Initialized in PreProfileInit: system_tray_client_.reset();
diff --git a/chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.h b/chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.h index dc07dfe..31b405b6 100644 --- a/chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.h +++ b/chrome/browser/ui/ash/chrome_browser_main_extra_parts_ash.h
@@ -26,7 +26,6 @@ class CastConfigControllerMediaRouter; class ChromeNewWindowClient; class ImeControllerClient; -class KioskNextShellClient; class LoginScreenClient; class MediaClientImpl; class MobileDataNotifications; @@ -101,7 +100,6 @@ #endif // Initialized in PostProfileInit in all configs: - std::unique_ptr<KioskNextShellClient> kiosk_next_shell_client_; std::unique_ptr<LoginScreenClient> login_screen_client_; std::unique_ptr<MediaClientImpl> media_client_; std::unique_ptr<policy::DisplaySettingsHandler> display_settings_handler_;
diff --git a/chrome/browser/ui/ash/kiosk_next_shell_client.cc b/chrome/browser/ui/ash/kiosk_next_shell_client.cc deleted file mode 100644 index b32d313..0000000 --- a/chrome/browser/ui/ash/kiosk_next_shell_client.cc +++ /dev/null
@@ -1,37 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "chrome/browser/ui/ash/kiosk_next_shell_client.h" - -#include "base/logging.h" - -namespace { - -KioskNextShellClient* g_kiosk_next_shell_client_instance = nullptr; - -} // namespace - -KioskNextShellClient::KioskNextShellClient() { - DCHECK(!g_kiosk_next_shell_client_instance); - g_kiosk_next_shell_client_instance = this; -} - -KioskNextShellClient::~KioskNextShellClient() { - DCHECK_EQ(this, g_kiosk_next_shell_client_instance); - g_kiosk_next_shell_client_instance = nullptr; - ash::KioskNextShellController::Get()->SetClientAndLaunchSession(nullptr); -} - -void KioskNextShellClient::Init() { - ash::KioskNextShellController::Get()->SetClientAndLaunchSession(this); -} - -// static -KioskNextShellClient* KioskNextShellClient::Get() { - return g_kiosk_next_shell_client_instance; -} - -void KioskNextShellClient::LaunchKioskNextShell(const AccountId& account_id) { - // TODO(https://crbug.com/977019): Finish cleaning up this class. -}
diff --git a/chrome/browser/ui/ash/kiosk_next_shell_client.h b/chrome/browser/ui/ash/kiosk_next_shell_client.h deleted file mode 100644 index 081fc87..0000000 --- a/chrome/browser/ui/ash/kiosk_next_shell_client.h +++ /dev/null
@@ -1,33 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CHROME_BROWSER_UI_ASH_KIOSK_NEXT_SHELL_CLIENT_H_ -#define CHROME_BROWSER_UI_ASH_KIOSK_NEXT_SHELL_CLIENT_H_ - -#include "ash/public/cpp/kiosk_next_shell.h" -#include "base/macros.h" - -class KioskNextShellClient : public ash::KioskNextShellClient { - public: - KioskNextShellClient(); - ~KioskNextShellClient() override; - - void Init(); - - // Returns the singleton KioskNextShellClient instance, if it exists. - static KioskNextShellClient* Get(); - - // ash::KioskNextShellClient: - void LaunchKioskNextShell(const AccountId& account_id) override; - - bool has_launched() const { return has_launched_; } - - private: - // True once the KioskNextShell has been launched. - bool has_launched_ = false; - - DISALLOW_COPY_AND_ASSIGN(KioskNextShellClient); -}; - -#endif // CHROME_BROWSER_UI_ASH_KIOSK_NEXT_SHELL_CLIENT_H_
diff --git a/chrome/browser/ui/ash/launcher/app_window_base.cc b/chrome/browser/ui/ash/launcher/app_window_base.cc index 51d70fe..2805a7c2 100644 --- a/chrome/browser/ui/ash/launcher/app_window_base.cc +++ b/chrome/browser/ui/ash/launcher/app_window_base.cc
@@ -103,11 +103,11 @@ NOTREACHED(); } -bool AppWindowBase::IsAlwaysOnTop() const { +ui::ZOrderLevel AppWindowBase::GetZOrderLevel() const { NOTREACHED(); - return false; + return ui::ZOrderLevel::kNormal; } -void AppWindowBase::SetAlwaysOnTop(bool always_on_top) { +void AppWindowBase::SetZOrderLevel(ui::ZOrderLevel level) { NOTREACHED(); }
diff --git a/chrome/browser/ui/ash/launcher/app_window_base.h b/chrome/browser/ui/ash/launcher/app_window_base.h index a01e8bb..27db0892 100644 --- a/chrome/browser/ui/ash/launcher/app_window_base.h +++ b/chrome/browser/ui/ash/launcher/app_window_base.h
@@ -58,8 +58,8 @@ void Restore() override; void SetBounds(const gfx::Rect& bounds) override; void FlashFrame(bool flash) override; - bool IsAlwaysOnTop() const override; - void SetAlwaysOnTop(bool always_on_top) override; + ui::ZOrderLevel GetZOrderLevel() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; private: ash::ShelfID shelf_id_;
diff --git a/chrome/browser/ui/autofill/payments/autofill_ui_util.cc b/chrome/browser/ui/autofill/payments/autofill_ui_util.cc index d339f5f..03c81431 100644 --- a/chrome/browser/ui/autofill/payments/autofill_ui_util.cc +++ b/chrome/browser/ui/autofill/payments/autofill_ui_util.cc
@@ -54,6 +54,7 @@ ->GetOmniboxPageActionIconContainer() ->UpdatePageActionIcon(icon_type); break; + case PageActionIconType::kClickToCall: case PageActionIconType::kFind: case PageActionIconType::kIntentPicker: case PageActionIconType::kNativeFileSystemAccess:
diff --git a/chrome/browser/ui/cocoa/apps/native_app_window_cocoa_browsertest.mm b/chrome/browser/ui/cocoa/apps/native_app_window_cocoa_browsertest.mm index ce6103d..30a4180 100644 --- a/chrome/browser/ui/cocoa/apps/native_app_window_cocoa_browsertest.mm +++ b/chrome/browser/ui/cocoa/apps/native_app_window_cocoa_browsertest.mm
@@ -35,7 +35,6 @@ #import "ui/base/test/scoped_fake_nswindow_focus.h" #include "ui/base/test/scoped_fake_nswindow_fullscreen.h" #import "ui/base/test/windowed_nsnotification_observer.h" -#import "ui/gfx/mac/nswindow_frame_controls.h" using extensions::AppWindow; using extensions::PlatformAppBrowserTest; @@ -46,6 +45,10 @@ namespace { +bool IsNSWindowFloating(NSWindow* window) { + return [window level] != NSNormalWindowLevel; +} + class NativeAppWindowCocoaBrowserTest : public PlatformAppBrowserTest { protected: NativeAppWindowCocoaBrowserTest() {} @@ -239,7 +242,7 @@ app_window->fullscreen_types_for_test()); EXPECT_FALSE(window->IsFullscreen()); EXPECT_FALSE([ns_window styleMask] & NSFullScreenWindowMask); - EXPECT_TRUE(gfx::IsNSWindowAlwaysOnTop(ns_window)); + EXPECT_TRUE(IsNSWindowFloating(ns_window)); [ns_window toggleFullScreen:nil]; [waiter waitForEnterCount:1 exitCount:0]; @@ -247,7 +250,7 @@ AppWindow::FULLSCREEN_TYPE_OS); EXPECT_TRUE(window->IsFullscreen()); EXPECT_TRUE([ns_window styleMask] & NSFullScreenWindowMask); - EXPECT_FALSE(gfx::IsNSWindowAlwaysOnTop(ns_window)); + EXPECT_FALSE(IsNSWindowFloating(ns_window)); app_window->Restore(); EXPECT_FALSE(window->IsFullscreenOrPending()); @@ -256,7 +259,7 @@ app_window->fullscreen_types_for_test()); EXPECT_FALSE(window->IsFullscreen()); EXPECT_FALSE([ns_window styleMask] & NSFullScreenWindowMask); - EXPECT_TRUE(gfx::IsNSWindowAlwaysOnTop(ns_window)); + EXPECT_TRUE(IsNSWindowFloating(ns_window)); app_window->Fullscreen(); EXPECT_TRUE(window->IsFullscreenOrPending()); @@ -265,7 +268,7 @@ AppWindow::FULLSCREEN_TYPE_WINDOW_API); EXPECT_TRUE(window->IsFullscreen()); EXPECT_TRUE([ns_window styleMask] & NSFullScreenWindowMask); - EXPECT_FALSE(gfx::IsNSWindowAlwaysOnTop(ns_window)); + EXPECT_FALSE(IsNSWindowFloating(ns_window)); [ns_window toggleFullScreen:nil]; [waiter waitForEnterCount:2 exitCount:2]; @@ -273,7 +276,7 @@ app_window->fullscreen_types_for_test()); EXPECT_FALSE(window->IsFullscreen()); EXPECT_FALSE([ns_window styleMask] & NSFullScreenWindowMask); - EXPECT_TRUE(gfx::IsNSWindowAlwaysOnTop(ns_window)); + EXPECT_TRUE(IsNSWindowFloating(ns_window)); } // Test Minimize, Restore combinations with their native equivalents.
diff --git a/chrome/browser/ui/extensions/hosted_app_browser_controller.cc b/chrome/browser/ui/extensions/hosted_app_browser_controller.cc index ac91e9f4..70e1549 100644 --- a/chrome/browser/ui/extensions/hosted_app_browser_controller.cc +++ b/chrome/browser/ui/extensions/hosted_app_browser_controller.cc
@@ -16,8 +16,9 @@ #include "chrome/browser/ui/location_bar/location_bar.h" #include "chrome/browser/ui/tabs/tab_strip_model.h" #include "chrome/browser/ui/web_applications/web_app_dialog_manager.h" -#include "chrome/browser/ui/web_applications/web_app_ui_service.h" #include "chrome/browser/web_applications/components/web_app_helpers.h" +#include "chrome/browser/web_applications/components/web_app_ui_manager.h" +#include "chrome/browser/web_applications/web_app_provider.h" #include "chrome/common/chrome_features.h" #include "chrome/common/extensions/api/url_handlers/url_handlers_parser.h" #include "chrome/common/extensions/manifest_handlers/app_launch_info.h" @@ -304,19 +305,19 @@ } bool HostedAppBrowserController::CanUninstall() const { - auto* web_app_ui_service = - web_app::WebAppUiService::Get(browser()->profile()); - DCHECK(web_app_ui_service); - return web_app_ui_service->dialog_manager().CanUninstallWebApp(extension_id_); + return web_app::WebAppProvider::Get(browser()->profile()) + ->ui_manager() + .dialog_manager() + .CanUninstallWebApp(extension_id_); } void HostedAppBrowserController::Uninstall() { - auto* web_app_ui_service = - web_app::WebAppUiService::Get(browser()->profile()); - DCHECK(web_app_ui_service); - web_app_ui_service->dialog_manager().UninstallWebApp( - extension_id_, web_app::WebAppDialogManager::UninstallSource::kAppMenu, - browser()->window(), base::DoNothing()); + web_app::WebAppProvider::Get(browser()->profile()) + ->ui_manager() + .dialog_manager() + .UninstallWebApp(extension_id_, + web_app::WebAppDialogManager::UninstallSource::kAppMenu, + browser()->window(), base::DoNothing()); } bool HostedAppBrowserController::IsInstalled() const {
diff --git a/chrome/browser/ui/hats/hats_service.cc b/chrome/browser/ui/hats/hats_service.cc index 724eec8..547c776 100644 --- a/chrome/browser/ui/hats/hats_service.cc +++ b/chrome/browser/ui/hats/hats_service.cc
@@ -8,10 +8,12 @@ #include "base/metrics/field_trial_params.h" #include "base/rand_util.h" +#include "chrome/browser/browser_process.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/ui/browser_finder.h" #include "chrome/browser/ui/browser_window.h" #include "chrome/common/chrome_features.h" +#include "components/metrics_services_manager/metrics_services_manager.h" namespace { // Which survey we're triggering @@ -57,6 +59,11 @@ } bool HatsService::ShouldShowSurvey(const std::string& trigger) const { + bool consent_given = + g_browser_process->GetMetricsServicesManager()->IsMetricsConsentGiven(); + if (!consent_given) + return false; + if ((trigger_ == trigger || trigger_ == kHatsSurveyTriggerDefault) && !launch_hats_) { if (base::RandDouble() < probability_) {
diff --git a/chrome/browser/ui/hats/hats_service_browsertest.cc b/chrome/browser/ui/hats/hats_service_browsertest.cc index 4c3c371b..c7df0e7 100644 --- a/chrome/browser/ui/hats/hats_service_browsertest.cc +++ b/chrome/browser/ui/hats/hats_service_browsertest.cc
@@ -5,16 +5,38 @@ #include "base/bind.h" #include "base/macros.h" #include "base/metrics/user_metrics.h" +#include "base/optional.h" #include "base/test/scoped_feature_list.h" +#include "chrome/browser/browser_process.h" +#include "chrome/browser/metrics/chrome_metrics_service_accessor.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/hats/hats_service.h" #include "chrome/browser/ui/hats/hats_service_factory.h" #include "chrome/common/chrome_features.h" #include "chrome/test/base/in_process_browser_test.h" +#include "components/metrics_services_manager/metrics_services_manager.h" #include "content/public/test/browser_test.h" namespace { +class ScopedEnableMetricsConsent { + public: + ScopedEnableMetricsConsent() { + ChromeMetricsServiceAccessor::SetMetricsAndCrashReportingForTesting( + &enable_metrics_consent_); + } + + ~ScopedEnableMetricsConsent() { + ChromeMetricsServiceAccessor::SetMetricsAndCrashReportingForTesting( + nullptr); + } + + private: + const bool enable_metrics_consent_ = true; + + DISALLOW_COPY_AND_ASSIGN(ScopedEnableMetricsConsent); +}; + class HatsServiceBrowserTestBase : public InProcessBrowserTest { protected: HatsServiceBrowserTestBase() @@ -35,6 +57,8 @@ return HatsServiceFactory::GetForProfile(browser()->profile(), true); } + void EnableMetricsConsent() { enable_metrics_consent_.emplace(); } + bool HatsDialogShowRequested() { return hats_dialog_show_requested_; } private: @@ -47,6 +71,7 @@ bool hats_dialog_show_requested_ = false; base::ActionCallback on_hats_dialog_show_; + base::Optional<ScopedEnableMetricsConsent> enable_metrics_consent_; DISALLOW_COPY_AND_ASSIGN(HatsServiceBrowserTestBase); }; @@ -117,7 +142,17 @@ } // namespace +IN_PROC_BROWSER_TEST_F(HatsServiceProbabilityOne, NoShowConsentNotGiven) { + ASSERT_FALSE( + g_browser_process->GetMetricsServicesManager()->IsMetricsConsentGiven()); + GetHatsService()->LaunchSatisfactionSurvey(); + EXPECT_FALSE(HatsDialogShowRequested()); +} + IN_PROC_BROWSER_TEST_F(HatsServiceProbabilityOne, AlwaysShow) { + EnableMetricsConsent(); + ASSERT_TRUE( + g_browser_process->GetMetricsServicesManager()->IsMetricsConsentGiven()); GetHatsService()->LaunchSatisfactionSurvey(); EXPECT_TRUE(HatsDialogShowRequested()); }
diff --git a/chrome/browser/ui/login/login_handler.cc b/chrome/browser/ui/login/login_handler.cc index b4b5540..947fd1a8 100644 --- a/chrome/browser/ui/login/login_handler.cc +++ b/chrome/browser/ui/login/login_handler.cc
@@ -103,6 +103,11 @@ } LoginHandler::~LoginHandler() { + password_manager::HttpAuthManager* http_auth_manager = + GetHttpAuthManagerForLogin(); + if (http_auth_manager) + http_auth_manager->OnPasswordFormDismissed(); + if (!WasAuthHandled()) { auth_required_callback_.Reset();
diff --git a/chrome/browser/ui/page_action/page_action_icon_container.h b/chrome/browser/ui/page_action/page_action_icon_container.h index bea765d5..e75e878 100644 --- a/chrome/browser/ui/page_action/page_action_icon_container.h +++ b/chrome/browser/ui/page_action/page_action_icon_container.h
@@ -19,6 +19,7 @@ kTranslate, kZoom, kNativeFileSystemAccess, + kClickToCall, }; class PageActionIconContainer {
diff --git a/chrome/browser/ui/startup/credential_provider_signin_dialog_win.cc b/chrome/browser/ui/startup/credential_provider_signin_dialog_win.cc index 059df2b..1daaef32 100644 --- a/chrome/browser/ui/startup/credential_provider_signin_dialog_win.cc +++ b/chrome/browser/ui/startup/credential_provider_signin_dialog_win.cc
@@ -483,7 +483,7 @@ std::make_unique<ChromeWebContentsHandler>()); views::Widget::InitParams init_params( views::Widget::InitParams::TYPE_WINDOW_FRAMELESS); - init_params.keep_on_top = true; + init_params.z_order = ui::ZOrderLevel::kFloatingWindow; views::WebDialogView* web_view = view.release(); init_params.name = "GCPW"; // Used for debugging only. init_params.delegate = web_view;
diff --git a/chrome/browser/ui/views/apps/chrome_native_app_window_views.cc b/chrome/browser/ui/views/apps/chrome_native_app_window_views.cc index 1bb22d5..337c1fab 100644 --- a/chrome/browser/ui/views/apps/chrome_native_app_window_views.cc +++ b/chrome/browser/ui/views/apps/chrome_native_app_window_views.cc
@@ -120,7 +120,8 @@ if (IsFrameless()) init_params.shadow_type = views::Widget::InitParams::SHADOW_TYPE_NONE; } - init_params.keep_on_top = create_params.always_on_top; + if (create_params.always_on_top) + init_params.z_order = ui::ZOrderLevel::kFloatingWindow; init_params.visible_on_all_workspaces = create_params.visible_on_all_workspaces; @@ -205,8 +206,8 @@ return ui::SHOW_STATE_NORMAL; } -bool ChromeNativeAppWindowViews::IsAlwaysOnTop() const { - return widget()->IsAlwaysOnTop(); +ui::ZOrderLevel ChromeNativeAppWindowViews::GetZOrderLevel() const { + return widget()->GetZOrderLevel(); } // views::WidgetDelegate implementation.
diff --git a/chrome/browser/ui/views/apps/chrome_native_app_window_views.h b/chrome/browser/ui/views/apps/chrome_native_app_window_views.h index 50a2422c..9398263 100644 --- a/chrome/browser/ui/views/apps/chrome_native_app_window_views.h +++ b/chrome/browser/ui/views/apps/chrome_native_app_window_views.h
@@ -39,7 +39,7 @@ // ui::BaseWindow implementation. gfx::Rect GetRestoredBounds() const override; ui::WindowShowState GetRestoredState() const override; - bool IsAlwaysOnTop() const override; + ui::ZOrderLevel GetZOrderLevel() const override; // WidgetDelegate implementation. gfx::ImageSkia GetWindowAppIcon() override;
diff --git a/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura.cc b/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura.cc index d97a1dfa..695e59c0 100644 --- a/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura.cc +++ b/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura.cc
@@ -105,8 +105,8 @@ return GetRestorableState(restore_state); } -bool ChromeNativeAppWindowViewsAura::IsAlwaysOnTop() const { - return widget()->IsAlwaysOnTop(); +ui::ZOrderLevel ChromeNativeAppWindowViewsAura::GetZOrderLevel() const { + return widget()->GetZOrderLevel(); } void ChromeNativeAppWindowViewsAura::UpdateShape(
diff --git a/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura.h b/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura.h index 229eeb1..07801e5b 100644 --- a/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura.h +++ b/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura.h
@@ -33,7 +33,7 @@ // ui::BaseWindow implementation. ui::WindowShowState GetRestoredState() const override; - bool IsAlwaysOnTop() const override; + ui::ZOrderLevel GetZOrderLevel() const override; // NativeAppWindow implementation. void UpdateShape(std::unique_ptr<ShapeRects> rects) override;
diff --git a/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura_ash.cc b/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura_ash.cc index 467a359..eef33b99 100644 --- a/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura_ash.cc +++ b/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura_ash.cc
@@ -24,7 +24,6 @@ #include "chrome/browser/profiles/profile.h" #include "chrome/browser/profiles/profiles_state.h" #include "chrome/browser/ui/ash/ash_util.h" -#include "chrome/browser/ui/ash/kiosk_next_shell_client.h" #include "chrome/browser/ui/ash/multi_user/multi_user_context_menu.h" #include "chrome/browser/ui/ash/tablet_mode_client.h" #include "chrome/browser/ui/exclusive_access/exclusive_access_manager.h" @@ -63,13 +62,6 @@ state == SessionState::LOGIN_SECONDARY; } -// Return true if |app_window| is a Kiosk Next Home app in a KioskNext session. -bool IsKioskNextHomeWindow(const AppWindow* app_window) { - return KioskNextShellClient::Get() && - KioskNextShellClient::Get()->has_launched() && - app_window->extension_id() == extension_misc::kKioskNextHomeAppId; -} - } // namespace ChromeNativeAppWindowViewsAuraAsh::ChromeNativeAppWindowViewsAuraAsh() @@ -120,8 +112,6 @@ container_id = ash::kShellWindowId_ImeWindowParentContainer; else if (create_params.show_on_lock_screen) container_id = ash::kShellWindowId_LockActionHandlerContainer; - else if (IsKioskNextHomeWindow(app_window())) - container_id = ash::kShellWindowId_HomeScreenContainer; if (container_id.has_value()) { ash_util::SetupWidgetInitParamsForContainer(init_params, *container_id); @@ -212,8 +202,8 @@ return GetRestorableState(restore_state); } -bool ChromeNativeAppWindowViewsAuraAsh::IsAlwaysOnTop() const { - return widget()->IsAlwaysOnTop(); +ui::ZOrderLevel ChromeNativeAppWindowViewsAuraAsh::GetZOrderLevel() const { + return widget()->GetZOrderLevel(); } ///////////////////////////////////////////////////////////////////////////////
diff --git a/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura_ash.h b/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura_ash.h index d729967c..44649449 100644 --- a/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura_ash.h +++ b/chrome/browser/ui/views/apps/chrome_native_app_window_views_aura_ash.h
@@ -62,7 +62,7 @@ // ui::BaseWindow: gfx::Rect GetRestoredBounds() const override; ui::WindowShowState GetRestoredState() const override; - bool IsAlwaysOnTop() const override; + ui::ZOrderLevel GetZOrderLevel() const override; // views::ContextMenuController: void ShowContextMenuForViewImpl(views::View* source,
diff --git a/chrome/browser/ui/views/frame/browser_view.cc b/chrome/browser/ui/views/frame/browser_view.cc index 41e26f3..a598ed4f 100644 --- a/chrome/browser/ui/views/frame/browser_view.cc +++ b/chrome/browser/ui/views/frame/browser_view.cc
@@ -706,11 +706,11 @@ frame_->FlashFrame(flash); } -bool BrowserView::IsAlwaysOnTop() const { - return false; +ui::ZOrderLevel BrowserView::GetZOrderLevel() const { + return ui::ZOrderLevel::kNormal; } -void BrowserView::SetAlwaysOnTop(bool always_on_top) { +void BrowserView::SetZOrderLevel(ui::ZOrderLevel level) { // Not implemented for browser windows. NOTIMPLEMENTED(); }
diff --git a/chrome/browser/ui/views/frame/browser_view.h b/chrome/browser/ui/views/frame/browser_view.h index a7dc6e3..ec20ded0 100644 --- a/chrome/browser/ui/views/frame/browser_view.h +++ b/chrome/browser/ui/views/frame/browser_view.h
@@ -290,8 +290,8 @@ void Deactivate() override; bool IsActive() const override; void FlashFrame(bool flash) override; - bool IsAlwaysOnTop() const override; - void SetAlwaysOnTop(bool always_on_top) override; + ui::ZOrderLevel GetZOrderLevel() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; gfx::NativeWindow GetNativeWindow() const override; void SetTopControlsShownRatio(content::WebContents* web_contents, float ratio) override;
diff --git a/chrome/browser/ui/views/ime/ime_window_view.cc b/chrome/browser/ui/views/ime/ime_window_view.cc index e6516d8..2a14d105 100644 --- a/chrome/browser/ui/views/ime/ime_window_view.cc +++ b/chrome/browser/ui/views/ime/ime_window_view.cc
@@ -38,7 +38,7 @@ params.delegate = this; params.wants_mouse_events_when_inactive = true; params.remove_standard_frame = false; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingWindow; params.activatable = views::Widget::InitParams::ACTIVATABLE_NO; params.visible_on_all_workspaces = false; params.bounds = bounds;
diff --git a/chrome/browser/ui/views/location_bar/icon_label_bubble_view.cc b/chrome/browser/ui/views/location_bar/icon_label_bubble_view.cc index 9bc1f70c..993ff8eb 100644 --- a/chrome/browser/ui/views/location_bar/icon_label_bubble_view.cc +++ b/chrome/browser/ui/views/location_bar/icon_label_bubble_view.cc
@@ -314,6 +314,9 @@ } void IconLabelBubbleView::AnimationEnded(const gfx::Animation* animation) { + if (animation != &slide_animation_) + return views::LabelButton::AnimationEnded(animation); + if (!is_animation_paused_) { // If there is no separator to show, then that means we want the text to // disappear after animating. @@ -326,11 +329,17 @@ } void IconLabelBubbleView::AnimationProgressed(const gfx::Animation* animation) { + if (animation != &slide_animation_) + return views::LabelButton::AnimationProgressed(animation); + if (!is_animation_paused_) PreferredSizeChanged(); } void IconLabelBubbleView::AnimationCanceled(const gfx::Animation* animation) { + if (animation != &slide_animation_) + return views::LabelButton::AnimationCanceled(animation); + AnimationEnded(animation); }
diff --git a/chrome/browser/ui/views/location_bar/location_bar_view.cc b/chrome/browser/ui/views/location_bar/location_bar_view.cc index e3a8db2..a47ae57 100644 --- a/chrome/browser/ui/views/location_bar/location_bar_view.cc +++ b/chrome/browser/ui/views/location_bar/location_bar_view.cc
@@ -26,6 +26,7 @@ #include "chrome/browser/search_engines/template_url_service_factory.h" #include "chrome/browser/send_tab_to_self/send_tab_to_self_desktop_util.h" #include "chrome/browser/send_tab_to_self/send_tab_to_self_util.h" +#include "chrome/browser/sharing/click_to_call/feature.h" #include "chrome/browser/ssl/security_state_tab_helper.h" #include "chrome/browser/themes/theme_properties.h" #include "chrome/browser/themes/theme_service.h" @@ -229,6 +230,8 @@ // the left most icon. if (send_tab_to_self::IsSendingEnabled()) params.types_enabled.push_back(PageActionIconType::kSendTabToSelf); + if (base::FeatureList::IsEnabled(kClickToCallUI)) + params.types_enabled.push_back(PageActionIconType::kClickToCall); if (!base::FeatureList::IsEnabled( autofill::features::kAutofillEnableToolbarStatusChip)) { params.types_enabled.push_back(PageActionIconType::kManagePasswords);
diff --git a/chrome/browser/ui/views/overlay/overlay_window_views.cc b/chrome/browser/ui/views/overlay/overlay_window_views.cc index f5bae7b..58dd745 100644 --- a/chrome/browser/ui/views/overlay/overlay_window_views.cc +++ b/chrome/browser/ui/views/overlay/overlay_window_views.cc
@@ -233,7 +233,7 @@ views::Widget::InitParams params(views::Widget::InitParams::TYPE_WINDOW); params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.bounds = CalculateAndUpdateWindowBounds(); - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingWindow; params.visible_on_all_workspaces = true; params.remove_standard_frame = true; params.name = "PictureInPictureWindow";
diff --git a/chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.cc b/chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.cc index 250ba4d5..04049111 100644 --- a/chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.cc +++ b/chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.cc
@@ -15,6 +15,7 @@ #include "chrome/browser/ui/views/passwords/manage_passwords_icon_views.h" #include "chrome/browser/ui/views/reader_mode/reader_mode_icon_view.h" #include "chrome/browser/ui/views/send_tab_to_self/send_tab_to_self_icon_view.h" +#include "chrome/browser/ui/views/sharing/click_to_call/click_to_call_icon_view.h" #include "chrome/browser/ui/views/translate/translate_icon_view.h" #include "ui/views/layout/box_layout.h" @@ -86,6 +87,11 @@ params.page_action_icon_delegate); page_action_icons_.push_back(native_file_system_icon_); break; + case PageActionIconType::kClickToCall: + click_to_call_icon_view_ = + new ClickToCallIconView(params.page_action_icon_delegate); + page_action_icons_.push_back(click_to_call_icon_view_); + break; case PageActionIconType::kLocalCardMigration: case PageActionIconType::kSaveCard: NOTREACHED(); @@ -132,6 +138,8 @@ return send_tab_to_self_icon_view_; case PageActionIconType::kNativeFileSystemAccess: return native_file_system_icon_; + case PageActionIconType::kClickToCall: + return click_to_call_icon_view_; case PageActionIconType::kLocalCardMigration: case PageActionIconType::kSaveCard: NOTREACHED();
diff --git a/chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.h b/chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.h index a9177a1..595c91eb 100644 --- a/chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.h +++ b/chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.h
@@ -16,6 +16,7 @@ #include "ui/views/view.h" class Browser; +class ClickToCallIconView; class CommandUpdater; class FindBarIcon; class IntentPickerView; @@ -92,6 +93,7 @@ TranslateIconView* translate_icon_ = nullptr; NativeFileSystemAccessIconView* native_file_system_icon_ = nullptr; ReaderModeIconView* reader_mode_icon_ = nullptr; + ClickToCallIconView* click_to_call_icon_view_ = nullptr; std::vector<PageActionIconView*> page_action_icons_; ScopedObserver<zoom::ZoomEventManager, zoom::ZoomEventManagerObserver>
diff --git a/chrome/browser/ui/views/screen_capture_notification_ui_views.cc b/chrome/browser/ui/views/screen_capture_notification_ui_views.cc index 0d4e2304..e66ede2 100644 --- a/chrome/browser/ui/views/screen_capture_notification_ui_views.cc +++ b/chrome/browser/ui/views/screen_capture_notification_ui_views.cc
@@ -196,7 +196,7 @@ params.ownership = views::Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; params.remove_standard_frame = true; - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.name = "ScreenCaptureNotificationUIViews"; #if defined(OS_CHROMEOS) @@ -208,7 +208,6 @@ widget->set_frame_type(views::Widget::FRAME_TYPE_FORCE_CUSTOM); widget->Init(params); - widget->SetAlwaysOnTop(true); SetBackground(views::CreateSolidBackground(GetNativeTheme()->GetSystemColor( ui::NativeTheme::kColorId_DialogBackground)));
diff --git a/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.cc b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.cc index e478b20..2de9c33 100644 --- a/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.cc +++ b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.cc
@@ -3,9 +3,16 @@ // found in the LICENSE file. #include "chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.h" + #include "base/strings/utf_string_conversions.h" #include "chrome/app/vector_icons/vector_icons.h" +#include "chrome/browser/sharing/sharing_metrics.h" +#include "chrome/browser/ui/browser_finder.h" #include "chrome/browser/ui/views/chrome_layout_provider.h" +#include "chrome/browser/ui/views/frame/browser_view.h" +#include "chrome/browser/ui/views/frame/toolbar_button_provider.h" +#include "chrome/browser/ui/views/hover_button.h" +#include "chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.h" #include "ui/gfx/paint_vector_icon.h" #include "ui/views/layout/box_layout.h" #include "ui/views/layout/fill_layout.h" @@ -13,6 +20,9 @@ #include "base/logging.h" namespace { +// Global instance of the bubble view. +ClickToCallDialogView* g_bubble_ = nullptr; + // Icon sizes in DIP. // TODO: Confirm the number with the team designer. constexpr int kPrimaryIconSize = 20; @@ -44,6 +54,35 @@ } // namespace +// static +ClickToCallDialogView* ClickToCallDialogView::GetBubbleView() { + return g_bubble_; +} + +// static +void ClickToCallDialogView::Show( + content::WebContents* web_contents, + std::unique_ptr<ClickToCallSharingDialogController> controller) { + Browser* browser = chrome::FindBrowserWithWebContents(web_contents); + if (g_bubble_ || !browser) + return; + + BrowserView* browser_view = BrowserView::GetBrowserViewForBrowser(browser); + views::View* anchor_view = + browser_view->toolbar_button_provider()->GetAnchorView(); + PageActionIconView* icon = + browser_view->toolbar_button_provider() + ->GetOmniboxPageActionIconContainerView() + ->GetPageActionIconView(PageActionIconType::kClickToCall); + + g_bubble_ = new ClickToCallDialogView(anchor_view, icon, web_contents, + std::move(controller)); + views::BubbleDialogDelegateView::CreateBubble(g_bubble_)->Show(); + + icon->Update(); + DCHECK(icon->GetVisible()); +} + ClickToCallDialogView::ClickToCallDialogView( views::View* anchor_view, PageActionIconView* icon_view, @@ -104,6 +143,7 @@ views::BoxLayout::Orientation::kVertical)); AddChildView(dialog_view); // Devices: + LogClickToCallDevicesToShow(devices_.size()); for (const auto& device : devices_) { auto dialog_button = std::make_unique<HoverButton>( this, CreateDeviceIcon(device.device_type()), @@ -116,6 +156,7 @@ } // Apps: + LogClickToCallAppsToShow(apps_.size()); for (const auto& app : apps_) { auto dialog_button = std::make_unique<HoverButton>(this, app.name); // TODO(yasmo): Create Icon View. @@ -143,3 +184,9 @@ base::string16 ClickToCallDialogView::GetWindowTitle() const { return base::UTF8ToUTF16(controller_->GetTitle()); } + +void ClickToCallDialogView::WindowClosing() { + DCHECK_EQ(g_bubble_, this); + g_bubble_ = nullptr; + icon_view_->Update(); +}
diff --git a/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.h b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.h index 61b84a50..da44816 100644 --- a/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.h +++ b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.h
@@ -6,28 +6,28 @@ #define CHROME_BROWSER_UI_VIEWS_SHARING_CLICK_TO_CALL_CLICK_TO_CALL_DIALOG_VIEW_H_ #include <memory> -#include <string> #include <vector> #include "chrome/browser/sharing/click_to_call/click_to_call_sharing_dialog_controller.h" #include "chrome/browser/sharing/sharing_device_info.h" -#include "chrome/browser/ui/browser_finder.h" -#include "chrome/browser/ui/views/frame/browser_view.h" -#include "chrome/browser/ui/views/frame/toolbar_button_provider.h" -#include "chrome/browser/ui/views/hover_button.h" #include "chrome/browser/ui/views/location_bar/location_bar_bubble_delegate_view.h" -#include "chrome/browser/ui/views/page_action/omnibox_page_action_icon_container_view.h" #include "ui/views/controls/button/button.h" namespace views { class View; } // namespace views +class HoverButton; class PageActionIconView; class ClickToCallDialogView : public views::ButtonListener, public LocationBarBubbleDelegateView { public: + static ClickToCallDialogView* GetBubbleView(); + static void Show( + content::WebContents* web_contents, + std::unique_ptr<ClickToCallSharingDialogController> controller); + // Bubble will be anchored to |anchor_view|. ClickToCallDialogView( views::View* anchor_view, @@ -40,6 +40,7 @@ // views::WidgetDelegateView: bool ShouldShowCloseButton() const override; base::string16 GetWindowTitle() const override; + void WindowClosing() override; // views::DialogDelegate: int GetDialogButtons() const override;
diff --git a/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view_unittest.cc b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view_unittest.cc index 56d9918..3931fc7 100644 --- a/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view_unittest.cc +++ b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view_unittest.cc
@@ -9,6 +9,7 @@ #include "base/strings/utf_string_conversions.h" #include "base/test/simple_test_clock.h" +#include "chrome/browser/ui/views/hover_button.h" #include "chrome/test/base/testing_profile.h" #include "chrome/test/views/chrome_views_test_base.h" #include "components/send_tab_to_self/target_device_info.h"
diff --git a/chrome/browser/ui/views/sharing/click_to_call/click_to_call_icon_view.cc b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_icon_view.cc new file mode 100644 index 0000000..dd6b582 --- /dev/null +++ b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_icon_view.cc
@@ -0,0 +1,138 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/ui/views/sharing/click_to_call/click_to_call_icon_view.h" + +#include <algorithm> + +#include "base/memory/ptr_util.h" +#include "chrome/app/vector_icons/vector_icons.h" +#include "chrome/browser/ui/views/sharing/click_to_call/click_to_call_dialog_view.h" +#include "ui/base/l10n/l10n_util.h" +#include "ui/gfx/animation/throb_animation.h" +#include "ui/gfx/geometry/rect.h" +#include "ui/gfx/scoped_canvas.h" +#include "ui/strings/grit/ui_strings.h" +#include "ui/views/animation/ink_drop.h" + +namespace { +// Height of the loader bar in DIP. +constexpr float kLoaderHeight = 4.0f; +// Width of the loader bar in percent of its range. +constexpr float kLoaderWidth = 0.2f; +} // namespace + +ClickToCallIconView::ClickToCallIconView(PageActionIconView::Delegate* delegate) + : PageActionIconView(/*command_updater=*/nullptr, + /*command_id=*/0, + delegate) { + SetVisible(false); + UpdateLoaderColor(); +} + +ClickToCallIconView::~ClickToCallIconView() = default; + +views::BubbleDialogDelegateView* ClickToCallIconView::GetBubble() const { + return ClickToCallDialogView::GetBubbleView(); +} + +bool ClickToCallIconView::Update() { + const bool is_bubble_showing = IsBubbleShowing(); + const bool is_visible = is_bubble_showing || loading_animation_; + const bool visibility_changed = GetVisible() != is_visible; + SetVisible(is_visible); + UpdateInkDrop(is_bubble_showing); + return visibility_changed; +} + +void ClickToCallIconView::StartLoadingAnimation() { + if (loading_animation_) + return; + loading_animation_ = std::make_unique<gfx::ThrobAnimation>(this); + loading_animation_->SetTweenType(gfx::Tween::LINEAR); + loading_animation_->SetThrobDuration(750); + loading_animation_->StartThrobbing(-1); + SchedulePaint(); +} + +void ClickToCallIconView::StopLoadingAnimation() { + if (!loading_animation_) + return; + loading_animation_.reset(); + SchedulePaint(); +} + +void ClickToCallIconView::PaintButtonContents(gfx::Canvas* canvas) { + PageActionIconView::PaintButtonContents(canvas); + if (!loading_animation_) + return; + + // TODO(knollr): Add support for this animation to PageActionIconView if other + // features need it as well. + + gfx::ScopedCanvas scoped_canvas(canvas); + const float scale = canvas->UndoDeviceScaleFactor(); + const gfx::Rect icon_bounds = + gfx::ScaleToEnclosedRect(image()->bounds(), scale); + const float progress = loading_animation_->GetCurrentValue(); + const float range = icon_bounds.width(); + const float offset = icon_bounds.x(); + + // Calculate start and end in percent of range. + float start = std::max(0.0f, (progress - kLoaderWidth) / (1 - kLoaderWidth)); + float end = std::min(1.0f, progress / (1 - kLoaderWidth)); + // Convert percentages to actual location. + start = start * (range - kLoaderHeight); + end = end * (range - kLoaderHeight) + kLoaderHeight; + + gfx::RectF bounds(start + offset, icon_bounds.bottom() - kLoaderHeight, + end - start, kLoaderHeight); + + cc::PaintFlags flags; + flags.setAntiAlias(true); + flags.setStyle(cc::PaintFlags::kFill_Style); + flags.setColor(loader_color_); + canvas->DrawRoundRect(bounds, bounds.height() / 2, flags); +} + +void ClickToCallIconView::AnimationProgressed(const gfx::Animation* animation) { + if (animation != loading_animation_.get()) + return PageActionIconView::AnimationProgressed(animation); + SchedulePaint(); +} + +void ClickToCallIconView::OnThemeChanged() { + PageActionIconView::OnThemeChanged(); + UpdateLoaderColor(); +} + +void ClickToCallIconView::UpdateInkDrop(bool activate) { + auto target_state = + activate ? views::InkDropState::ACTIVATED : views::InkDropState::HIDDEN; + if (GetInkDrop()->GetTargetInkDropState() != target_state) + AnimateInkDrop(target_state, /*event=*/nullptr); +} + +void ClickToCallIconView::UpdateLoaderColor() { + loader_color_ = GetNativeTheme()->GetSystemColor( + ui::NativeTheme::kColorId_ProminentButtonColor); +} + +bool ClickToCallIconView::IsTriggerableEvent(const ui::Event& event) { + // We do nothing when the icon is clicked. + return false; +} + +void ClickToCallIconView::OnExecuting( + PageActionIconView::ExecuteSource execute_source) {} + +const gfx::VectorIcon& ClickToCallIconView::GetVectorIcon() const { + // TODO(crbug.com/972059): Should we have our own icon? + return kSendTabToSelfIcon; +} + +base::string16 ClickToCallIconView::GetTextForTooltipAndAccessibleName() const { + return l10n_util::GetStringUTF16( + IDS_BROWSER_SHARING_CLICK_TO_CALL_DIALOG_TITLE_LABEL); +}
diff --git a/chrome/browser/ui/views/sharing/click_to_call/click_to_call_icon_view.h b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_icon_view.h new file mode 100644 index 0000000..3721c17c --- /dev/null +++ b/chrome/browser/ui/views/sharing/click_to_call/click_to_call_icon_view.h
@@ -0,0 +1,65 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CHROME_BROWSER_UI_VIEWS_SHARING_CLICK_TO_CALL_CLICK_TO_CALL_ICON_VIEW_H_ +#define CHROME_BROWSER_UI_VIEWS_SHARING_CLICK_TO_CALL_CLICK_TO_CALL_ICON_VIEW_H_ + +#include <memory> + +#include "base/macros.h" +#include "base/strings/string16.h" +#include "chrome/browser/ui/views/page_action/page_action_icon_view.h" +#include "third_party/skia/include/core/SkColor.h" +#include "ui/gfx/vector_icon_types.h" + +namespace gfx { +class Canvas; +class ThrobAnimation; +} // namespace gfx + +namespace ui { +class Event; +} // namespace ui + +// The location bar icon to show the click to call bubble where the user can +// choose to send a phone number to a target device or use an OS handler app. +class ClickToCallIconView : public PageActionIconView { + public: + explicit ClickToCallIconView(PageActionIconView::Delegate* delegate); + ~ClickToCallIconView() override; + + // PageActionIconView: + views::BubbleDialogDelegateView* GetBubble() const override; + bool Update() override; + base::string16 GetTextForTooltipAndAccessibleName() const override; + + // views::Button: + void PaintButtonContents(gfx::Canvas* canvas) override; + + // views::View: + void OnThemeChanged() override; + + void StartLoadingAnimation(); + void StopLoadingAnimation(); + + protected: + // PageActionIconView: + void OnExecuting(PageActionIconView::ExecuteSource execute_source) override; + const gfx::VectorIcon& GetVectorIcon() const override; + bool IsTriggerableEvent(const ui::Event& event) override; + + // gfx::AnimationDelegate: + void AnimationProgressed(const gfx::Animation* animation) override; + + private: + void UpdateInkDrop(bool activate); + void UpdateLoaderColor(); + + SkColor loader_color_; + std::unique_ptr<gfx::ThrobAnimation> loading_animation_; + + DISALLOW_COPY_AND_ASSIGN(ClickToCallIconView); +}; + +#endif // CHROME_BROWSER_UI_VIEWS_SHARING_CLICK_TO_CALL_CLICK_TO_CALL_ICON_VIEW_H_
diff --git a/chrome/browser/ui/views/simple_message_box_views.cc b/chrome/browser/ui/views/simple_message_box_views.cc index 83e16bc..7128fa3 100644 --- a/chrome/browser/ui/views/simple_message_box_views.cc +++ b/chrome/browser/ui/views/simple_message_box_views.cc
@@ -162,7 +162,7 @@ // attach to, move the dialog's widget on top so other windows do not obscure // it. if (!parent) - widget->SetAlwaysOnTop(true); + widget->SetZOrderLevel(ui::ZOrderLevel::kFloatingWindow); #endif widget->Show();
diff --git a/chrome/browser/ui/views/tabs/tab_drag_controller_interactive_uitest.cc b/chrome/browser/ui/views/tabs/tab_drag_controller_interactive_uitest.cc index 0474a235..cbb3578 100644 --- a/chrome/browser/ui/views/tabs/tab_drag_controller_interactive_uitest.cc +++ b/chrome/browser/ui/views/tabs/tab_drag_controller_interactive_uitest.cc
@@ -828,7 +828,8 @@ std::unique_ptr<aura::Window> masked_window( aura::test::CreateTestWindowWithDelegate( &masked_window_delegate, 10, bounds, browser_window->parent())); - masked_window->SetProperty(aura::client::kAlwaysOnTopKey, true); + masked_window->SetProperty(aura::client::kZOrderingKey, + ui::ZOrderLevel::kFloatingWindow); auto targeter = std::make_unique<aura::WindowTargeter>(); targeter->SetInsets(gfx::Insets(0, bounds.width() - 10, 0, 0)); masked_window->SetEventTargeter(std::move(targeter));
diff --git a/chrome/browser/ui/views/tabs/tab_strip.cc b/chrome/browser/ui/views/tabs/tab_strip.cc index b249d17..a1f84bc 100644 --- a/chrome/browser/ui/views/tabs/tab_strip.cc +++ b/chrome/browser/ui/views/tabs/tab_strip.cc
@@ -2721,7 +2721,7 @@ arrow_window = new views::Widget; views::Widget::InitParams params(views::Widget::InitParams::TYPE_POPUP); - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.opacity = views::Widget::InitParams::TRANSLUCENT_WINDOW; params.accept_events = false; params.bounds = gfx::Rect(g_drop_indicator_width, g_drop_indicator_height);
diff --git a/chrome/browser/ui/views/task_manager_view.cc b/chrome/browser/ui/views/task_manager_view.cc index ca236a0..9352a52 100644 --- a/chrome/browser/ui/views/task_manager_view.cc +++ b/chrome/browser/ui/views/task_manager_view.cc
@@ -357,7 +357,7 @@ void TaskManagerView::InitAlwaysOnTopState() { RetrieveSavedAlwaysOnTopState(); - GetWidget()->SetAlwaysOnTop(is_always_on_top_); + GetWidget()->SetZOrderLevel(ui::ZOrderLevel::kFloatingWindow); } void TaskManagerView::ActivateSelectedTab() {
diff --git a/chrome/browser/ui/views/try_chrome_dialog_win/try_chrome_dialog.cc b/chrome/browser/ui/views/try_chrome_dialog_win/try_chrome_dialog.cc index cca4faeb..c8f9491 100644 --- a/chrome/browser/ui/views/try_chrome_dialog_win/try_chrome_dialog.cc +++ b/chrome/browser/ui/views/try_chrome_dialog_win/try_chrome_dialog.cc
@@ -1193,7 +1193,7 @@ // This propagation can cause views to change their size requirements. const gfx::Size preferred = popup_->GetContentsView()->GetPreferredSize(); popup_->SetBounds(context_->ComputePopupBounds(popup_, preferred)); - popup_->SetAlwaysOnTop(true); + popup_->SetZOrderLevel(ui::ZOrderLevel::kFloatingWindow); popup_->ShowInactive(); delegate_->SetToastLocation(context_->GetToastLocation());
diff --git a/chrome/browser/ui/web_applications/web_app_ui_service.cc b/chrome/browser/ui/web_applications/web_app_ui_manager_impl.cc similarity index 72% rename from chrome/browser/ui/web_applications/web_app_ui_service.cc rename to chrome/browser/ui/web_applications/web_app_ui_manager_impl.cc index dc95e29..a6682c7 100644 --- a/chrome/browser/ui/web_applications/web_app_ui_service.cc +++ b/chrome/browser/ui/web_applications/web_app_ui_manager_impl.cc
@@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#include "chrome/browser/ui/web_applications/web_app_ui_service.h" +#include "chrome/browser/ui/web_applications/web_app_ui_manager_impl.h" #include <utility> @@ -11,7 +11,6 @@ #include "chrome/browser/ui/browser_list.h" #include "chrome/browser/ui/web_applications/app_browser_controller.h" #include "chrome/browser/ui/web_applications/web_app_dialog_manager.h" -#include "chrome/browser/ui/web_applications/web_app_ui_service_factory.h" #include "chrome/browser/web_applications/system_web_app_manager.h" #include "chrome/browser/web_applications/web_app_provider.h" @@ -23,13 +22,11 @@ namespace web_app { // static -WebAppUiService* WebAppUiService::Get(Profile* profile) { - return WebAppUiServiceFactory::GetForProfile(profile); +std::unique_ptr<WebAppUiManager> WebAppUiManager::Create(Profile* profile) { + return std::make_unique<WebAppUiManagerImpl>(profile); } -WebAppUiService::WebAppUiService(Profile* profile) : profile_(profile) { - provider_ = WebAppProvider::Get(profile_); - +WebAppUiManagerImpl::WebAppUiManagerImpl(Profile* profile) : profile_(profile) { for (Browser* browser : *BrowserList::GetInstance()) { base::Optional<AppId> app_id = GetAppIdForBrowser(browser); if (!app_id.has_value()) @@ -39,20 +36,19 @@ } BrowserList::AddObserver(this); - provider_->set_ui_delegate(this); dialog_manager_ = std::make_unique<WebAppDialogManager>(profile); } -WebAppUiService::~WebAppUiService() { - provider_->set_ui_delegate(nullptr); -} - -void WebAppUiService::Shutdown() { +WebAppUiManagerImpl::~WebAppUiManagerImpl() { BrowserList::RemoveObserver(this); } -size_t WebAppUiService::GetNumWindowsForApp(const AppId& app_id) { +WebAppDialogManager& WebAppUiManagerImpl::dialog_manager() { + return *dialog_manager_; +} + +size_t WebAppUiManagerImpl::GetNumWindowsForApp(const AppId& app_id) { auto it = num_windows_for_apps_map_.find(app_id); if (it == num_windows_for_apps_map_.end()) return 0; @@ -60,8 +56,9 @@ return it->second; } -void WebAppUiService::NotifyOnAllAppWindowsClosed(const AppId& app_id, - base::OnceClosure callback) { +void WebAppUiManagerImpl::NotifyOnAllAppWindowsClosed( + const AppId& app_id, + base::OnceClosure callback) { const size_t num_windows_for_app = GetNumWindowsForApp(app_id); if (num_windows_for_app == 0) { base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE, @@ -72,14 +69,15 @@ windows_closed_requests_map_[app_id].push_back(std::move(callback)); } -void WebAppUiService::MigrateOSAttributes(const AppId& from, const AppId& to) { +void WebAppUiManagerImpl::MigrateOSAttributes(const AppId& from, + const AppId& to) { #if defined(OS_CHROMEOS) app_list::AppListSyncableServiceFactory::GetForProfile(profile_) ->TransferItemAttributes(from, to); #endif } -void WebAppUiService::OnBrowserAdded(Browser* browser) { +void WebAppUiManagerImpl::OnBrowserAdded(Browser* browser) { base::Optional<AppId> app_id = GetAppIdForBrowser(browser); if (!app_id.has_value()) return; @@ -87,7 +85,7 @@ ++num_windows_for_apps_map_[app_id.value()]; } -void WebAppUiService::OnBrowserRemoved(Browser* browser) { +void WebAppUiManagerImpl::OnBrowserRemoved(Browser* browser) { base::Optional<AppId> app_id_opt = GetAppIdForBrowser(browser); if (!app_id_opt.has_value()) return; @@ -111,7 +109,8 @@ windows_closed_requests_map_.erase(app_id); } -base::Optional<AppId> WebAppUiService::GetAppIdForBrowser(Browser* browser) { +base::Optional<AppId> WebAppUiManagerImpl::GetAppIdForBrowser( + Browser* browser) { if (browser->profile() != profile_) return base::nullopt;
diff --git a/chrome/browser/ui/web_applications/web_app_ui_service.h b/chrome/browser/ui/web_applications/web_app_ui_manager_impl.h similarity index 60% rename from chrome/browser/ui/web_applications/web_app_ui_service.h rename to chrome/browser/ui/web_applications/web_app_ui_manager_impl.h index 5bf41cc..6e2c2c6b 100644 --- a/chrome/browser/ui/web_applications/web_app_ui_service.h +++ b/chrome/browser/ui/web_applications/web_app_ui_manager_impl.h
@@ -2,8 +2,8 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_SERVICE_H_ -#define CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_SERVICE_H_ +#ifndef CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_MANAGER_IMPL_H_ +#define CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_MANAGER_IMPL_H_ #include <map> #include <memory> @@ -14,8 +14,7 @@ #include "base/memory/weak_ptr.h" #include "base/optional.h" #include "chrome/browser/ui/browser_list_observer.h" -#include "chrome/browser/web_applications/components/web_app_ui_delegate.h" -#include "components/keyed_service/core/keyed_service.h" +#include "chrome/browser/web_applications/components/web_app_ui_manager.h" class Profile; class Browser; @@ -26,27 +25,21 @@ class WebAppDialogManager; // This KeyedService is a UI counterpart for WebAppProvider. -class WebAppUiService : public KeyedService, - public BrowserListObserver, - public WebAppUiDelegate { +class WebAppUiManagerImpl : public BrowserListObserver, public WebAppUiManager { public: - static WebAppUiService* Get(Profile* profile); + static WebAppUiManagerImpl* Get(Profile* profile); - explicit WebAppUiService(Profile* profile); - ~WebAppUiService() override; + explicit WebAppUiManagerImpl(Profile* profile); + ~WebAppUiManagerImpl() override; - // KeyedService - void Shutdown() override; - - WebAppDialogManager& dialog_manager() { return *dialog_manager_; } - - // WebAppUiDelegate + // WebAppUiManager: + WebAppDialogManager& dialog_manager() override; size_t GetNumWindowsForApp(const AppId& app_id) override; void NotifyOnAllAppWindowsClosed(const AppId& app_id, base::OnceClosure callback) override; void MigrateOSAttributes(const AppId& from, const AppId& to) override; - // BrowserListObserver + // BrowserListObserver: void OnBrowserAdded(Browser* browser) override; void OnBrowserRemoved(Browser* browser) override; @@ -55,17 +48,16 @@ std::unique_ptr<WebAppDialogManager> dialog_manager_; - WebAppProvider* provider_; Profile* profile_; std::map<AppId, std::vector<base::OnceClosure>> windows_closed_requests_map_; std::map<AppId, size_t> num_windows_for_apps_map_; - base::WeakPtrFactory<WebAppUiService> weak_ptr_factory_{this}; + base::WeakPtrFactory<WebAppUiManagerImpl> weak_ptr_factory_{this}; - DISALLOW_COPY_AND_ASSIGN(WebAppUiService); + DISALLOW_COPY_AND_ASSIGN(WebAppUiManagerImpl); }; } // namespace web_app -#endif // CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_SERVICE_H_ +#endif // CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_MANAGER_IMPL_H_
diff --git a/chrome/browser/ui/web_applications/web_app_ui_service_browsertest.cc b/chrome/browser/ui/web_applications/web_app_ui_manager_impl_browsertest.cc similarity index 80% rename from chrome/browser/ui/web_applications/web_app_ui_service_browsertest.cc rename to chrome/browser/ui/web_applications/web_app_ui_manager_impl_browsertest.cc index 653be5e..c4cc9b3 100644 --- a/chrome/browser/ui/web_applications/web_app_ui_service_browsertest.cc +++ b/chrome/browser/ui/web_applications/web_app_ui_manager_impl_browsertest.cc
@@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#include "chrome/browser/ui/web_applications/web_app_ui_service.h" +#include "chrome/browser/ui/web_applications/web_app_ui_manager_impl.h" #include "base/barrier_closure.h" #include "base/test/bind_test_util.h" @@ -72,7 +72,7 @@ const GURL kFooUrl = GURL("https://foo.example"); const GURL kBarUrl = GURL("https://bar.example"); -class WebAppUiServiceBrowserTest : public InProcessBrowserTest { +class WebAppUiManagerImplBrowserTest : public InProcessBrowserTest { protected: Profile* profile() { return browser()->profile(); } @@ -88,28 +88,25 @@ return extensions::browsertest_util::LaunchAppBrowser(profile(), app); } - WebAppUiService* ui_service() { return WebAppUiService::Get(profile()); } + WebAppUiManager& ui_manager() { + return WebAppProviderBase::GetProviderBase(profile())->ui_manager(); + } }; -IN_PROC_BROWSER_TEST_F(WebAppUiServiceBrowserTest, +IN_PROC_BROWSER_TEST_F(WebAppUiManagerImplBrowserTest, GetNumWindowsForApp_AppWindowsAdded) { - // Should not crash. - auto& ui_delegate = WebAppProvider::Get(browser()->profile())->ui_delegate(); - auto* ui_service = WebAppUiService::Get(browser()->profile()); - EXPECT_EQ(&ui_delegate, ui_service); - // Zero apps on start: - EXPECT_EQ(0u, ui_service->GetNumWindowsForApp(AppId())); + EXPECT_EQ(0u, ui_manager().GetNumWindowsForApp(AppId())); const auto* foo_app = InstallWebApp(kFooUrl); LaunchApp(foo_app); - EXPECT_EQ(1u, ui_service->GetNumWindowsForApp(foo_app->id())); + EXPECT_EQ(1u, ui_manager().GetNumWindowsForApp(foo_app->id())); LaunchApp(foo_app); - EXPECT_EQ(2u, ui_service->GetNumWindowsForApp(foo_app->id())); + EXPECT_EQ(2u, ui_manager().GetNumWindowsForApp(foo_app->id())); } -IN_PROC_BROWSER_TEST_F(WebAppUiServiceBrowserTest, +IN_PROC_BROWSER_TEST_F(WebAppUiManagerImplBrowserTest, GetNumWindowsForApp_AppWindowsRemoved) { const auto* foo_app = InstallWebApp(kFooUrl); auto* foo_window1 = LaunchApp(foo_app); @@ -118,21 +115,21 @@ const auto* bar_app = InstallWebApp(kBarUrl); LaunchApp(bar_app); - EXPECT_EQ(2u, ui_service()->GetNumWindowsForApp(foo_app->id())); - EXPECT_EQ(1u, ui_service()->GetNumWindowsForApp(bar_app->id())); + EXPECT_EQ(2u, ui_manager().GetNumWindowsForApp(foo_app->id())); + EXPECT_EQ(1u, ui_manager().GetNumWindowsForApp(bar_app->id())); CloseAndWait(foo_window1); - EXPECT_EQ(1u, ui_service()->GetNumWindowsForApp(foo_app->id())); - EXPECT_EQ(1u, ui_service()->GetNumWindowsForApp(bar_app->id())); + EXPECT_EQ(1u, ui_manager().GetNumWindowsForApp(foo_app->id())); + EXPECT_EQ(1u, ui_manager().GetNumWindowsForApp(bar_app->id())); CloseAndWait(foo_window2); - EXPECT_EQ(0u, ui_service()->GetNumWindowsForApp(foo_app->id())); - EXPECT_EQ(1u, ui_service()->GetNumWindowsForApp(bar_app->id())); + EXPECT_EQ(0u, ui_manager().GetNumWindowsForApp(foo_app->id())); + EXPECT_EQ(1u, ui_manager().GetNumWindowsForApp(bar_app->id())); } -IN_PROC_BROWSER_TEST_F(WebAppUiServiceBrowserTest, +IN_PROC_BROWSER_TEST_F(WebAppUiManagerImplBrowserTest, NotifyOnAllAppWindowsClosed_NoOpenedWindows) { const auto* foo_app = InstallWebApp(kFooUrl); const auto* bar_app = InstallWebApp(kBarUrl); @@ -140,14 +137,14 @@ base::RunLoop run_loop; // Should return early; no windows for |foo_app|. - ui_service()->NotifyOnAllAppWindowsClosed(foo_app->id(), - run_loop.QuitClosure()); + ui_manager().NotifyOnAllAppWindowsClosed(foo_app->id(), + run_loop.QuitClosure()); run_loop.Run(); } // Tests that the callback is correctly called when there is more than one // app window. -IN_PROC_BROWSER_TEST_F(WebAppUiServiceBrowserTest, +IN_PROC_BROWSER_TEST_F(WebAppUiManagerImplBrowserTest, NotifyOnAllAppWindowsClosed_MultipleOpenedWindows) { const auto* foo_app = InstallWebApp(kFooUrl); const auto* bar_app = InstallWebApp(kBarUrl); @@ -161,11 +158,11 @@ bool callback_ran = false; base::RunLoop run_loop; - ui_service()->NotifyOnAllAppWindowsClosed(foo_app->id(), - base::BindLambdaForTesting([&]() { - callback_ran = true; - run_loop.Quit(); - })); + ui_manager().NotifyOnAllAppWindowsClosed(foo_app->id(), + base::BindLambdaForTesting([&]() { + callback_ran = true; + run_loop.Quit(); + })); CloseAndWait(foo_window1); // The callback shouldn't have run yet because there is still one window @@ -182,12 +179,13 @@ } #if defined(OS_CHROMEOS) -class WebAppUiServiceMigrationBrowserTest : public WebAppUiServiceBrowserTest { +class WebAppUiServiceMigrationBrowserTest + : public WebAppUiManagerImplBrowserTest { public: void SetUp() override { // Disable System Web Apps so that the Internal Apps are installed. scoped_feature_list_.InitAndDisableFeature(features::kSystemWebApps); - WebAppUiServiceBrowserTest::SetUp(); + WebAppUiManagerImplBrowserTest::SetUp(); } private:
diff --git a/chrome/browser/ui/web_applications/web_app_ui_service_factory.cc b/chrome/browser/ui/web_applications/web_app_ui_service_factory.cc deleted file mode 100644 index 1c2cb9d8..0000000 --- a/chrome/browser/ui/web_applications/web_app_ui_service_factory.cc +++ /dev/null
@@ -1,57 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "chrome/browser/ui/web_applications/web_app_ui_service_factory.h" - -#include "chrome/browser/profiles/profile.h" -#include "chrome/browser/ui/web_applications/web_app_ui_service.h" -#include "chrome/browser/web_applications/components/web_app_utils.h" -#include "chrome/browser/web_applications/web_app_provider_factory.h" -#include "components/keyed_service/content/browser_context_dependency_manager.h" - -#if defined(OS_CHROMEOS) -#include "chrome/browser/ui/app_list/app_list_syncable_service_factory.h" -#endif - -namespace web_app { - -// static -WebAppUiService* WebAppUiServiceFactory::GetForProfile(Profile* profile) { - return static_cast<WebAppUiService*>( - WebAppUiServiceFactory::GetInstance()->GetServiceForBrowserContext( - profile, true /* create */)); -} - -// static -WebAppUiServiceFactory* WebAppUiServiceFactory::GetInstance() { - return base::Singleton<WebAppUiServiceFactory>::get(); -} - -WebAppUiServiceFactory::WebAppUiServiceFactory() - : BrowserContextKeyedServiceFactory( - "WebAppUiService", - BrowserContextDependencyManager::GetInstance()) { - DependsOn(WebAppProviderFactory::GetInstance()); -#if defined(OS_CHROMEOS) - DependsOn(app_list::AppListSyncableServiceFactory::GetInstance()); -#endif -} - -WebAppUiServiceFactory::~WebAppUiServiceFactory() = default; - -KeyedService* WebAppUiServiceFactory::BuildServiceInstanceFor( - content::BrowserContext* context) const { - return new WebAppUiService(Profile::FromBrowserContext(context)); -} - -bool WebAppUiServiceFactory::ServiceIsCreatedWithBrowserContext() const { - return true; -} - -content::BrowserContext* WebAppUiServiceFactory::GetBrowserContextToUse( - content::BrowserContext* context) const { - return GetBrowserContextForWebApps(context); -} - -} // namespace web_app
diff --git a/chrome/browser/ui/web_applications/web_app_ui_service_factory.h b/chrome/browser/ui/web_applications/web_app_ui_service_factory.h deleted file mode 100644 index 1f5683c9..0000000 --- a/chrome/browser/ui/web_applications/web_app_ui_service_factory.h +++ /dev/null
@@ -1,48 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_SERVICE_FACTORY_H_ -#define CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_SERVICE_FACTORY_H_ - -#include "base/macros.h" -#include "base/memory/singleton.h" -#include "components/keyed_service/content/browser_context_keyed_service_factory.h" - -namespace content { -class BrowserContext; -} - -class Profile; - -namespace web_app { - -class WebAppUiService; - -// Singleton that owns all WebAppUiServices and associates them -// with Profile. -class WebAppUiServiceFactory : public BrowserContextKeyedServiceFactory { - public: - static WebAppUiService* GetForProfile(Profile* profile); - - static WebAppUiServiceFactory* GetInstance(); - - private: - friend struct base::DefaultSingletonTraits<WebAppUiServiceFactory>; - - WebAppUiServiceFactory(); - ~WebAppUiServiceFactory() override; - - // BrowserContextKeyedServiceFactory - KeyedService* BuildServiceInstanceFor( - content::BrowserContext* context) const override; - bool ServiceIsCreatedWithBrowserContext() const override; - content::BrowserContext* GetBrowserContextToUse( - content::BrowserContext* context) const override; - - DISALLOW_COPY_AND_ASSIGN(WebAppUiServiceFactory); -}; - -} // namespace web_app - -#endif // CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_UI_SERVICE_FACTORY_H_
diff --git a/chrome/browser/ui/webui/chromeos/account_manager_welcome_dialog.cc b/chrome/browser/ui/webui/chromeos/account_manager_welcome_dialog.cc index ae19e2b9..d678bfe 100644 --- a/chrome/browser/ui/webui/chromeos/account_manager_welcome_dialog.cc +++ b/chrome/browser/ui/webui/chromeos/account_manager_welcome_dialog.cc
@@ -66,7 +66,7 @@ void AccountManagerWelcomeDialog::AdjustWidgetInitParams( views::Widget::InitParams* params) { - params->keep_on_top = false; + params->z_order = ui::ZOrderLevel::kNormal; params->type = views::Widget::InitParams::Type::TYPE_WINDOW_FRAMELESS; params->shadow_type = views::Widget::InitParams::ShadowType::SHADOW_TYPE_DROP; params->shadow_elevation = wm::kShadowElevationActiveWindow;
diff --git a/chrome/browser/ui/webui/chromeos/account_migration_welcome_dialog.cc b/chrome/browser/ui/webui/chromeos/account_migration_welcome_dialog.cc index 51ff02f..33407733 100644 --- a/chrome/browser/ui/webui/chromeos/account_migration_welcome_dialog.cc +++ b/chrome/browser/ui/webui/chromeos/account_migration_welcome_dialog.cc
@@ -63,7 +63,7 @@ void AccountMigrationWelcomeDialog::AdjustWidgetInitParams( views::Widget::InitParams* params) { - params->keep_on_top = false; + params->z_order = ui::ZOrderLevel::kNormal; params->type = views::Widget::InitParams::Type::TYPE_WINDOW_FRAMELESS; params->shadow_type = views::Widget::InitParams::ShadowType::SHADOW_TYPE_DROP; params->shadow_elevation = wm::kShadowElevationActiveWindow;
diff --git a/chrome/browser/ui/webui/chromeos/assistant_optin/assistant_optin_ui.cc b/chrome/browser/ui/webui/chromeos/assistant_optin/assistant_optin_ui.cc index f296b04..5a7d3eb 100644 --- a/chrome/browser/ui/webui/chromeos/assistant_optin/assistant_optin_ui.cc +++ b/chrome/browser/ui/webui/chromeos/assistant_optin/assistant_optin_ui.cc
@@ -142,7 +142,7 @@ void AssistantOptInDialog::AdjustWidgetInitParams( views::Widget::InitParams* params) { - params->keep_on_top = false; + params->z_order = ui::ZOrderLevel::kNormal; } void AssistantOptInDialog::GetDialogSize(gfx::Size* size) const {
diff --git a/chrome/browser/ui/webui/chromeos/system_web_dialog_browsertest.cc b/chrome/browser/ui/webui/chromeos/system_web_dialog_browsertest.cc index b3af756..ce3b17a 100644 --- a/chrome/browser/ui/webui/chromeos/system_web_dialog_browsertest.cc +++ b/chrome/browser/ui/webui/chromeos/system_web_dialog_browsertest.cc
@@ -81,7 +81,8 @@ dialog->ShowSystemDialog(); EXPECT_FALSE(ash::ShellTestApi().IsSystemModalWindowOpen()); aura::Window* window_to_test = dialog->dialog_window(); - EXPECT_TRUE(window_to_test->GetProperty(aura::client::kAlwaysOnTopKey)); + EXPECT_NE(ui::ZOrderLevel::kNormal, + window_to_test->GetProperty(aura::client::kZOrderingKey)); } using SystemWebDialogTest = InProcessBrowserTest;
diff --git a/chrome/browser/ui/webui/chromeos/system_web_dialog_delegate.cc b/chrome/browser/ui/webui/chromeos/system_web_dialog_delegate.cc index 0d2c11b..6fcd5cd 100644 --- a/chrome/browser/ui/webui/chromeos/system_web_dialog_delegate.cc +++ b/chrome/browser/ui/webui/chromeos/system_web_dialog_delegate.cc
@@ -160,7 +160,7 @@ views::Widget::InitParams extra_params; // If unparented and not modal, keep it on top (see header comment). if (!parent && GetDialogModalType() == ui::MODAL_TYPE_NONE) - extra_params.keep_on_top = true; + extra_params.z_order = ui::ZOrderLevel::kFloatingWindow; AdjustWidgetInitParams(&extra_params); dialog_window_ = chrome::ShowWebDialogWithParams(parent, browser_context, this, &extra_params);
diff --git a/chrome/browser/ui/webui/signin/inline_login_handler_dialog_chromeos.cc b/chrome/browser/ui/webui/signin/inline_login_handler_dialog_chromeos.cc index 856ad1a2..3f4e487 100644 --- a/chrome/browser/ui/webui/signin/inline_login_handler_dialog_chromeos.cc +++ b/chrome/browser/ui/webui/signin/inline_login_handler_dialog_chromeos.cc
@@ -49,7 +49,7 @@ void InlineLoginHandlerDialogChromeOS::AdjustWidgetInitParams( views::Widget::InitParams* params) { - params->keep_on_top = false; + params->z_order = ui::ZOrderLevel::kNormal; } gfx::Size InlineLoginHandlerDialogChromeOS::GetMaximumDialogSize() {
diff --git a/chrome/browser/vr/service/arcore_consent_prompt_interface.cc b/chrome/browser/vr/service/arcore_consent_prompt_interface.cc index b7ecf750..80ece6d9 100644 --- a/chrome/browser/vr/service/arcore_consent_prompt_interface.cc +++ b/chrome/browser/vr/service/arcore_consent_prompt_interface.cc
@@ -7,17 +7,17 @@ namespace vr { namespace { -ArcoreConsentPromptInterface* g_arcore_consent_prompt = nullptr; +ArCoreConsentPromptInterface* g_arcore_consent_prompt = nullptr; } // static -void ArcoreConsentPromptInterface::SetInstance( - ArcoreConsentPromptInterface* instance) { +void ArCoreConsentPromptInterface::SetInstance( + ArCoreConsentPromptInterface* instance) { g_arcore_consent_prompt = instance; } // static -ArcoreConsentPromptInterface* ArcoreConsentPromptInterface::GetInstance() { +ArCoreConsentPromptInterface* ArCoreConsentPromptInterface::GetInstance() { return g_arcore_consent_prompt; }
diff --git a/chrome/browser/vr/service/arcore_consent_prompt_interface.h b/chrome/browser/vr/service/arcore_consent_prompt_interface.h index 442c908..44249ecf 100644 --- a/chrome/browser/vr/service/arcore_consent_prompt_interface.h +++ b/chrome/browser/vr/service/arcore_consent_prompt_interface.h
@@ -12,10 +12,10 @@ // TODO(crbug.com/968233): Unify consent flow. // This class solves layering problem until the above bug gets fixed. -class VR_EXPORT ArcoreConsentPromptInterface { +class VR_EXPORT ArCoreConsentPromptInterface { public: - static void SetInstance(ArcoreConsentPromptInterface*); - static ArcoreConsentPromptInterface* GetInstance(); + static void SetInstance(ArCoreConsentPromptInterface*); + static ArCoreConsentPromptInterface* GetInstance(); virtual void ShowConsentPrompt( int render_process_id,
diff --git a/chrome/browser/vr/service/xr_device_impl.cc b/chrome/browser/vr/service/xr_device_impl.cc index a0052f5..5a464fd 100644 --- a/chrome/browser/vr/service/xr_device_impl.cc +++ b/chrome/browser/vr/service/xr_device_impl.cc
@@ -205,12 +205,14 @@ #if BUILDFLAG(ENABLE_ARCORE) if (!render_frame_host_) { // Reject promise. - std::move(callback).Run(nullptr); + std::move(callback).Run( + device::mojom::RequestSessionResult::NewFailureReason( + device::mojom::RequestSessionError::INVALID_CLIENT)); } else { if (IsXrDeviceConsentPromptDisabledForTesting()) { DoRequestSession(std::move(options), std::move(callback)); } else { - ArcoreConsentPromptInterface::GetInstance()->ShowConsentPrompt( + ArCoreConsentPromptInterface::GetInstance()->ShowConsentPrompt( render_frame_host_->GetProcess()->GetID(), render_frame_host_->GetRoutingID(), base::BindOnce(&XRDeviceImpl::OnConsentResult,
diff --git a/chrome/browser/wake_lock/wake_lock_browsertest.cc b/chrome/browser/wake_lock/wake_lock_browsertest.cc index 0753014..d75567a0 100644 --- a/chrome/browser/wake_lock/wake_lock_browsertest.cc +++ b/chrome/browser/wake_lock/wake_lock_browsertest.cc
@@ -14,6 +14,8 @@ #include "content/public/common/content_switches.h" #include "content/public/test/browser_test_utils.h" #include "net/test/embedded_test_server/embedded_test_server.h" +#include "net/test/embedded_test_server/http_request.h" +#include "net/test/embedded_test_server/http_response.h" #include "testing/gmock/include/gmock/gmock-matchers.h" namespace { @@ -49,35 +51,107 @@ DISALLOW_COPY_AND_ASSIGN(PermissionRequestObserver); }; +// Handles HTTP requests to |path| with |content| as the response body. +// |content| is expected to be JavaScript; the response mime type is always set +// to "text/javascript". +// Invokes |done_callback| after serving the HTTP request. +std::unique_ptr<net::test_server::HttpResponse> RespondWithJS( + const std::string& path, + const std::string& content, + base::OnceClosure done_callback, + const net::test_server::HttpRequest& request) { + GURL request_url = request.GetURL(); + if (request_url.path() != path) + return nullptr; + + auto response = std::make_unique<net::test_server::BasicHttpResponse>(); + response->set_content_type("text/javascript"); + response->set_content(content); + std::move(done_callback).Run(); + return response; +} + } // namespace class WakeLockBrowserTest : public InProcessBrowserTest { protected: // InProcessBrowserTest: void SetUpCommandLine(base::CommandLine* command_line) override; - void SetUpOnMainThread() override; + + // Shorthand for starting the embedded web server and navigating to + // simple.html. + // Tests calling this usually call content::ExecuteScriptAndExtractString() + // afterwards to run custom code on the dummy page. + void NavigateToSimplePage(); + + // Registers a handle for "/js-response" in the embedded web server that + // responds with |script| as the response body, and then navigates to |path|. + // |path| usually points to a page that will somehow make a request to + // "/js-response". + void NavigateToAndRespondWithScript(const std::string& path, + const std::string& script); }; void WakeLockBrowserTest::SetUpCommandLine(base::CommandLine* command_line) { command_line->AppendSwitchASCII(switches::kEnableBlinkFeatures, "WakeLock"); } -void WakeLockBrowserTest::SetUpOnMainThread() { - // Navigate to a secure context. - embedded_test_server()->ServeFilesFromSourceDirectory("content/test/data"); +void WakeLockBrowserTest::NavigateToSimplePage() { ASSERT_TRUE(embedded_test_server()->Start()); - ui_test_utils::NavigateToURL( - browser(), - embedded_test_server()->GetURL("localhost", "/simple_page.html")); - auto* web_contents = browser()->tab_strip_model()->GetActiveWebContents(); - EXPECT_THAT( - web_contents->GetMainFrame()->GetLastCommittedOrigin().Serialize(), - testing::StartsWith("http://localhost:")); + ui_test_utils::NavigateToURL(browser(), + embedded_test_server()->GetURL("/simple.html")); +} + +void WakeLockBrowserTest::NavigateToAndRespondWithScript( + const std::string& path, + const std::string& script) { + base::RunLoop loop; + embedded_test_server()->RegisterRequestHandler(base::BindRepeating( + &RespondWithJS, "/js-response", script, loop.QuitClosure())); + ASSERT_TRUE(embedded_test_server()->Start()); + ui_test_utils::NavigateToURL(browser(), embedded_test_server()->GetURL(path)); + loop.Run(); +} + +// https://w3c.github.io/wake-lock/#request-static-method +// Screen locks are never allowed from workers. +IN_PROC_BROWSER_TEST_F(WakeLockBrowserTest, RequestScreenLockFromWorker) { + PermissionRequestObserver observer( + browser()->tab_strip_model()->GetActiveWebContents()); + const std::string kWorkerScript = + "WakeLock.request('screen').catch(err => self.postMessage(err.name))"; + NavigateToAndRespondWithScript( + "/workers/create_dedicated_worker.html?worker_url=/js-response", + kWorkerScript); + EXPECT_EQ( + "NotAllowedError", + content::EvalJs(browser()->tab_strip_model()->GetActiveWebContents(), + "waitForMessage();")); + EXPECT_EQ(observer.request_shown(), false); +} + +// Requests for a system lock should always be denied, and there should be no +// permission prompt. +IN_PROC_BROWSER_TEST_F(WakeLockBrowserTest, RequestSystemLockFromWorker) { + PermissionRequestObserver observer( + browser()->tab_strip_model()->GetActiveWebContents()); + const std::string kWorkerScript = + "WakeLock.request('system').catch(err => self.postMessage(err.name))"; + NavigateToAndRespondWithScript( + "/workers/create_dedicated_worker.html?worker_url=/js-response", + kWorkerScript); + EXPECT_EQ( + "NotAllowedError", + content::EvalJs(browser()->tab_strip_model()->GetActiveWebContents(), + "waitForMessage();")); + EXPECT_EQ(observer.request_shown(), false); } IN_PROC_BROWSER_TEST_F(WakeLockBrowserTest, RequestPermissionScreen) { // Requests for a screen lock should always be granted, and there should be no // permission prompt. + NavigateToSimplePage(); + PermissionRequestObserver observer( browser()->tab_strip_model()->GetActiveWebContents()); std::string response; @@ -94,6 +168,8 @@ RequestPermissionScreenNoUserGesture) { // Requests for a screen lock should always be granted, and there should be no // permission prompt. + NavigateToSimplePage(); + PermissionRequestObserver observer( browser()->tab_strip_model()->GetActiveWebContents()); std::string response; @@ -109,6 +185,8 @@ IN_PROC_BROWSER_TEST_F(WakeLockBrowserTest, RequestPermissionSystem) { // Requests for a system lock should always be denied, and there should be no // permission prompt. + NavigateToSimplePage(); + PermissionRequestObserver observer( browser()->tab_strip_model()->GetActiveWebContents()); std::string response; @@ -125,6 +203,8 @@ RequestPermissionSystemNoUserGesture) { // Requests for a system lock should always be denied, and there should be no // permission prompt. + NavigateToSimplePage(); + PermissionRequestObserver observer( browser()->tab_strip_model()->GetActiveWebContents()); std::string response;
diff --git a/chrome/browser/web_applications/BUILD.gn b/chrome/browser/web_applications/BUILD.gn index cad27f69..00d0ad6f 100644 --- a/chrome/browser/web_applications/BUILD.gn +++ b/chrome/browser/web_applications/BUILD.gn
@@ -86,8 +86,8 @@ "test/test_web_app_database.h", "test/test_web_app_database_factory.cc", "test/test_web_app_database_factory.h", - "test/test_web_app_ui_delegate.cc", - "test/test_web_app_ui_delegate.h", + "test/test_web_app_ui_manager.cc", + "test/test_web_app_ui_manager.h", "test/test_web_app_url_loader.cc", "test/test_web_app_url_loader.h", "test/web_app_test.cc",
diff --git a/chrome/browser/web_applications/bookmark_apps/system_web_app_manager_unittest.cc b/chrome/browser/web_applications/bookmark_apps/system_web_app_manager_unittest.cc index 717598a..28b60337 100644 --- a/chrome/browser/web_applications/bookmark_apps/system_web_app_manager_unittest.cc +++ b/chrome/browser/web_applications/bookmark_apps/system_web_app_manager_unittest.cc
@@ -20,7 +20,7 @@ #include "chrome/browser/web_applications/test/test_app_registrar.h" #include "chrome/browser/web_applications/test/test_pending_app_manager.h" #include "chrome/browser/web_applications/test/test_system_web_app_manager.h" -#include "chrome/browser/web_applications/test/test_web_app_ui_delegate.h" +#include "chrome/browser/web_applications/test/test_web_app_ui_manager.h" #include "chrome/browser/web_applications/web_app_provider.h" #include "chrome/common/chrome_features.h" #include "chrome/common/pref_names.h" @@ -83,6 +83,10 @@ std::make_unique<TestSystemWebAppManager>(profile()); system_web_app_manager_ = system_web_app_manager.get(); provider->SetSystemWebAppManager(std::move(system_web_app_manager)); + + auto ui_manager = std::make_unique<TestWebAppUiManager>(); + ui_manager_ = ui_manager.get(); + provider->SetWebAppUiManager(std::move(ui_manager)); } void SimulatePreviouslyInstalledApp( @@ -104,14 +108,14 @@ return system_web_app_manager_; } - TestWebAppUiDelegate* ui_delegate() { return &ui_delegate_; } + TestWebAppUiManager* ui_manager() { return ui_manager_; } private: base::test::ScopedFeatureList scoped_feature_list_; TestAppRegistrar* test_app_registrar_ = nullptr; TestPendingAppManager* test_pending_app_manager_ = nullptr; TestSystemWebAppManager* system_web_app_manager_ = nullptr; - TestWebAppUiDelegate ui_delegate_; + TestWebAppUiManager* ui_manager_ = nullptr; DISALLOW_COPY_AND_ASSIGN(SystemWebAppManagerTest); }; @@ -127,7 +131,7 @@ system_apps[SystemAppType::SETTINGS] = {kAppUrl1}; system_web_app_manager()->SetSystemApps(std::move(system_apps)); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); @@ -146,7 +150,7 @@ system_apps[SystemAppType::DISCOVER] = {kAppUrl2}; system_web_app_manager()->SetSystemApps(std::move(system_apps)); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); const auto& apps_to_install = pending_app_manager()->install_requests(); @@ -164,7 +168,7 @@ system_apps[SystemAppType::SETTINGS] = {kAppUrl1}; system_web_app_manager()->SetSystemApps(std::move(system_apps)); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); @@ -189,7 +193,7 @@ system_web_app_manager()->SetSystemApps(system_apps); system_web_app_manager()->set_current_version(base::Version("1.0.0.0")); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(1u, pending_app_manager()->install_requests().size()); @@ -198,7 +202,7 @@ // install. system_apps[SystemAppType::DISCOVER] = {kAppUrl2}; system_web_app_manager()->SetSystemApps(system_apps); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(3u, pending_app_manager()->install_requests().size()); @@ -208,14 +212,14 @@ base::test::ScopedFeatureList disable_feature_list; disable_feature_list.InitWithFeatures({}, {features::kSystemWebApps}); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(2u, pending_app_manager()->uninstall_requests().size()); } // Re-enabling System Web Apps installs without a version change. - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(5u, pending_app_manager()->install_requests().size()); @@ -233,7 +237,7 @@ system_web_app_manager()->SetSystemApps(system_apps); system_web_app_manager()->set_current_version(base::Version("1.0.0.0")); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(1u, install_requests.size()); @@ -245,7 +249,7 @@ // force reinstall. system_apps[SystemAppType::DISCOVER] = {kAppUrl2}; system_web_app_manager()->SetSystemApps(system_apps); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(3u, install_requests.size()); @@ -257,7 +261,7 @@ // Bump the version number, and an update will trigger, and force // reinstallation of both apps. system_web_app_manager()->set_current_version(base::Version("2.0.0.0")); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(5u, install_requests.size()); @@ -271,7 +275,7 @@ base::test::ScopedFeatureList disable_feature_list; disable_feature_list.InitWithFeatures({}, {features::kSystemWebApps}); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(2u, pending_app_manager()->uninstall_requests().size()); @@ -280,7 +284,7 @@ } // Re-enabling System Web Apps installs even without a version change. - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(7u, install_requests.size()); @@ -293,7 +297,7 @@ // change. system_apps[SystemAppType::SETTINGS] = {kAppUrl3}; system_web_app_manager()->SetSystemApps(system_apps); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); EXPECT_EQ(9u, install_requests.size()); @@ -313,7 +317,7 @@ histograms.ExpectTotalCount( SystemWebAppManager::kInstallResultHistogramName, 0); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); histograms.ExpectTotalCount( @@ -330,7 +334,7 @@ pending_app_manager()->SetInstallResultCode( InstallResultCode::kInstallManagerDestroyed); - system_web_app_manager()->Start(ui_delegate()); + system_web_app_manager()->Start(); base::RunLoop().RunUntilIdle(); histograms.ExpectTotalCount( SystemWebAppManager::kInstallResultHistogramName, 3);
diff --git a/chrome/browser/web_applications/bookmark_apps/test_web_app_provider.cc b/chrome/browser/web_applications/bookmark_apps/test_web_app_provider.cc index 276a3b7..431f3cd2 100644 --- a/chrome/browser/web_applications/bookmark_apps/test_web_app_provider.cc +++ b/chrome/browser/web_applications/bookmark_apps/test_web_app_provider.cc
@@ -13,6 +13,7 @@ #include "chrome/browser/web_applications/components/install_manager.h" #include "chrome/browser/web_applications/components/pending_app_manager.h" #include "chrome/browser/web_applications/components/policy/web_app_policy_manager.h" +#include "chrome/browser/web_applications/components/web_app_ui_manager.h" #include "chrome/browser/web_applications/components/web_app_utils.h" #include "chrome/browser/web_applications/system_web_app_manager.h" #include "chrome/browser/web_applications/test/test_system_web_app_manager.h" @@ -56,6 +57,12 @@ ConnectSubsystems(); } +void TestWebAppProvider::SetWebAppUiManager( + std::unique_ptr<WebAppUiManager> ui_manager) { + ui_manager_ = std::move(ui_manager); + ConnectSubsystems(); +} + void TestWebAppProvider::SetSystemWebAppManager( std::unique_ptr<SystemWebAppManager> system_web_app_manager) { system_web_app_manager_ = std::move(system_web_app_manager);
diff --git a/chrome/browser/web_applications/bookmark_apps/test_web_app_provider.h b/chrome/browser/web_applications/bookmark_apps/test_web_app_provider.h index 72ad9b5b..6e9191a 100644 --- a/chrome/browser/web_applications/bookmark_apps/test_web_app_provider.h +++ b/chrome/browser/web_applications/bookmark_apps/test_web_app_provider.h
@@ -41,6 +41,7 @@ void SetInstallFinalizer(std::unique_ptr<InstallFinalizer> install_finalizer); void SetPendingAppManager( std::unique_ptr<PendingAppManager> pending_app_manager); + void SetWebAppUiManager(std::unique_ptr<WebAppUiManager> ui_manager); void SetSystemWebAppManager( std::unique_ptr<SystemWebAppManager> system_web_app_manager); void SetWebAppPolicyManager(
diff --git a/chrome/browser/web_applications/components/BUILD.gn b/chrome/browser/web_applications/components/BUILD.gn index ff23d591..8925106 100644 --- a/chrome/browser/web_applications/components/BUILD.gn +++ b/chrome/browser/web_applications/components/BUILD.gn
@@ -47,7 +47,7 @@ "web_app_shortcut_win.h", "web_app_tab_helper_base.cc", "web_app_tab_helper_base.h", - "web_app_ui_delegate.h", + "web_app_ui_manager.h", "web_app_url_loader.cc", "web_app_url_loader.h", "web_app_utils.cc",
diff --git a/chrome/browser/web_applications/components/pending_app_manager.cc b/chrome/browser/web_applications/components/pending_app_manager.cc index c55cb9cc..f5258f4 100644 --- a/chrome/browser/web_applications/components/pending_app_manager.cc +++ b/chrome/browser/web_applications/components/pending_app_manager.cc
@@ -35,8 +35,10 @@ PendingAppManager::~PendingAppManager() = default; void PendingAppManager::SetSubsystems(AppRegistrar* registrar, + WebAppUiManager* ui_manager, InstallFinalizer* finalizer) { registrar_ = registrar; + ui_manager_ = ui_manager; finalizer_ = finalizer; }
diff --git a/chrome/browser/web_applications/components/pending_app_manager.h b/chrome/browser/web_applications/components/pending_app_manager.h index 3b6e412..3e529995 100644 --- a/chrome/browser/web_applications/components/pending_app_manager.h +++ b/chrome/browser/web_applications/components/pending_app_manager.h
@@ -25,6 +25,7 @@ class AppRegistrar; class InstallFinalizer; +class WebAppUiManager; // PendingAppManager installs, uninstalls, and updates apps. // @@ -48,7 +49,9 @@ PendingAppManager(); virtual ~PendingAppManager(); - void SetSubsystems(AppRegistrar* registrar, InstallFinalizer* finalizer); + void SetSubsystems(AppRegistrar* registrar, + WebAppUiManager* ui_manager, + InstallFinalizer* finalizer); virtual void Shutdown() = 0; @@ -99,6 +102,7 @@ protected: AppRegistrar* registrar() { return registrar_; } + WebAppUiManager* ui_manager() { return ui_manager_; } InstallFinalizer* finalizer() { return finalizer_; } private: @@ -127,6 +131,7 @@ void OnAppSynchronized(InstallSource source, const GURL& app_url); AppRegistrar* registrar_ = nullptr; + WebAppUiManager* ui_manager_ = nullptr; InstallFinalizer* finalizer_ = nullptr; base::flat_map<InstallSource, SynchronizeRequest> synchronize_requests_;
diff --git a/chrome/browser/web_applications/components/web_app_provider_base.h b/chrome/browser/web_applications/components/web_app_provider_base.h index 7a8f45d8..9f4d003 100644 --- a/chrome/browser/web_applications/components/web_app_provider_base.h +++ b/chrome/browser/web_applications/components/web_app_provider_base.h
@@ -17,7 +17,7 @@ class InstallManager; class AppRegistrar; class WebAppPolicyManager; -class WebAppUiDelegate; +class WebAppUiManager; class WebAppProviderBase : public KeyedService { public: @@ -39,7 +39,7 @@ // present. It's currently only present for Bookmark Apps. virtual WebAppPolicyManager* policy_manager() = 0; - virtual WebAppUiDelegate& ui_delegate() = 0; + virtual WebAppUiManager& ui_manager() = 0; DISALLOW_COPY_AND_ASSIGN(WebAppProviderBase); };
diff --git a/chrome/browser/web_applications/components/web_app_ui_delegate.h b/chrome/browser/web_applications/components/web_app_ui_manager.h similarity index 69% rename from chrome/browser/web_applications/components/web_app_ui_delegate.h rename to chrome/browser/web_applications/components/web_app_ui_manager.h index 4eb84b37..ea27722 100644 --- a/chrome/browser/web_applications/components/web_app_ui_delegate.h +++ b/chrome/browser/web_applications/components/web_app_ui_manager.h
@@ -2,18 +2,28 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_WEB_APP_UI_DELEGATE_H_ -#define CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_WEB_APP_UI_DELEGATE_H_ +#ifndef CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_WEB_APP_UI_MANAGER_H_ +#define CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_WEB_APP_UI_MANAGER_H_ #include "base/callback_forward.h" #include "chrome/browser/web_applications/components/web_app_helpers.h" +class Profile; + namespace web_app { +class WebAppDialogManager; + // Pure virtual interface used to perform Web App UI operations or listen to Web // App UI events. -class WebAppUiDelegate { +class WebAppUiManager { public: + static std::unique_ptr<WebAppUiManager> Create(Profile* profile); + + virtual ~WebAppUiManager() = default; + + virtual WebAppDialogManager& dialog_manager() = 0; + virtual size_t GetNumWindowsForApp(const AppId& app_id) = 0; virtual void NotifyOnAllAppWindowsClosed(const AppId& app_id, @@ -26,4 +36,4 @@ } // namespace web_app -#endif // CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_WEB_APP_UI_DELEGATE_H_ +#endif // CHROME_BROWSER_WEB_APPLICATIONS_COMPONENTS_WEB_APP_UI_MANAGER_H_
diff --git a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.cc b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.cc index 8b2ea4e..88452b6 100644 --- a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.cc +++ b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.cc
@@ -15,8 +15,7 @@ #include "chrome/browser/profiles/profile.h" #include "chrome/browser/web_applications/components/app_registrar.h" #include "chrome/browser/web_applications/components/web_app_constants.h" -#include "chrome/browser/web_applications/components/web_app_provider_base.h" -#include "chrome/browser/web_applications/components/web_app_ui_delegate.h" +#include "chrome/browser/web_applications/components/web_app_ui_manager.h" #include "chrome/browser/web_applications/extensions/bookmark_app_install_finalizer.h" #include "content/public/browser/web_contents.h" @@ -112,10 +111,6 @@ url_loader_ = std::move(url_loader); } -web_app::WebAppUiDelegate& PendingBookmarkAppManager::GetUiDelegate() { - return web_app::WebAppProviderBase::GetProviderBase(profile_)->ui_delegate(); -} - void PendingBookmarkAppManager::MaybeStartNextInstallation() { if (current_task_and_callback_) return; @@ -145,8 +140,8 @@ if (registrar()->IsInstalled(app_id.value())) { if (install_options.wait_for_windows_closed && - GetUiDelegate().GetNumWindowsForApp(app_id.value()) != 0) { - GetUiDelegate().NotifyOnAllAppWindowsClosed( + ui_manager()->GetNumWindowsForApp(app_id.value()) != 0) { + ui_manager()->NotifyOnAllAppWindowsClosed( app_id.value(), base::BindOnce(&PendingBookmarkAppManager::Install, weak_ptr_factory_.GetWeakPtr(), install_options,
diff --git a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h index 9e28954..dcac748 100644 --- a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h +++ b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h
@@ -30,7 +30,7 @@ namespace web_app { class AppRegistrar; class InstallFinalizer; -class WebAppUiDelegate; +class WebAppUiManager; } // namespace web_app namespace extensions { @@ -70,7 +70,7 @@ private: struct TaskAndCallback; - web_app::WebAppUiDelegate& GetUiDelegate(); + web_app::WebAppUiManager& GetUiManager(); void MaybeStartNextInstallation();
diff --git a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager_unittest.cc b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager_unittest.cc index 4ad1639..0e77f0a8 100644 --- a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager_unittest.cc +++ b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager_unittest.cc
@@ -25,7 +25,7 @@ #include "chrome/browser/web_applications/extensions/bookmark_app_registrar.h" #include "chrome/browser/web_applications/test/test_app_registrar.h" #include "chrome/browser/web_applications/test/test_install_finalizer.h" -#include "chrome/browser/web_applications/test/test_web_app_ui_delegate.h" +#include "chrome/browser/web_applications/test/test_web_app_ui_manager.h" #include "chrome/browser/web_applications/test/test_web_app_url_loader.h" #include "chrome/browser/web_applications/web_app_provider.h" #include "chrome/test/base/chrome_render_view_host_test_harness.h" @@ -185,12 +185,9 @@ void SetUp() override { ChromeRenderViewHostTestHarness::SetUp(); registrar_ = std::make_unique<web_app::TestAppRegistrar>(); - ui_delegate_ = std::make_unique<web_app::TestWebAppUiDelegate>(); + ui_manager_ = std::make_unique<web_app::TestWebAppUiManager>(); install_finalizer_ = std::make_unique<web_app::TestInstallFinalizer>(); task_factory_ = std::make_unique<TestBookmarkAppInstallationTaskFactory>(); - - web_app::WebAppProvider::Get(profile())->set_ui_delegate( - ui_delegate_.get()); } void TearDown() override { @@ -262,7 +259,8 @@ std::unique_ptr<PendingBookmarkAppManager> GetPendingBookmarkAppManagerWithTestMocks() { auto manager = std::make_unique<PendingBookmarkAppManager>(profile()); - manager->SetSubsystems(registrar_.get(), install_finalizer_.get()); + manager->SetSubsystems(registrar_.get(), ui_manager_.get(), + install_finalizer_.get()); manager->SetTaskFactoryForTesting(base::BindRepeating( &TestBookmarkAppInstallationTaskFactory::CreateInstallationTask, base::Unretained(task_factory_.get()))); @@ -305,7 +303,7 @@ web_app::TestAppRegistrar* registrar() { return registrar_.get(); } - web_app::TestWebAppUiDelegate* ui_delegate() { return ui_delegate_.get(); } + web_app::TestWebAppUiManager* ui_manager() { return ui_manager_.get(); } web_app::TestWebAppUrlLoader* url_loader() { return url_loader_; } @@ -316,7 +314,7 @@ private: std::unique_ptr<TestBookmarkAppInstallationTaskFactory> task_factory_; std::unique_ptr<web_app::TestAppRegistrar> registrar_; - std::unique_ptr<web_app::TestWebAppUiDelegate> ui_delegate_; + std::unique_ptr<web_app::TestWebAppUiManager> ui_manager_; std::unique_ptr<web_app::TestInstallFinalizer> install_finalizer_; web_app::TestWebAppUrlLoader* url_loader_ = nullptr; @@ -1284,7 +1282,7 @@ install_options.wait_for_windows_closed = true; task_factory()->SetNextInstallationTaskResult( kFooWebAppUrl, web_app::InstallResultCode::kSuccess); - ui_delegate()->SetNumWindowsForApp(GenerateFakeAppId(kFooWebAppUrl), 0); + ui_manager()->SetNumWindowsForApp(GenerateFakeAppId(kFooWebAppUrl), 0); url_loader()->SetNextLoadUrlResult( kFooWebAppUrl, web_app::WebAppUrlLoader::Result::kUrlLoaded); @@ -1327,7 +1325,7 @@ install_options.wait_for_windows_closed = true; task_factory()->SetNextInstallationTaskResult( kFooWebAppUrl, web_app::InstallResultCode::kSuccess); - ui_delegate()->SetNumWindowsForApp(GenerateFakeAppId(kFooWebAppUrl), 1); + ui_manager()->SetNumWindowsForApp(GenerateFakeAppId(kFooWebAppUrl), 1); url_loader()->SetNextLoadUrlResult( kFooWebAppUrl, web_app::WebAppUrlLoader::Result::kUrlLoaded); install_finalizer()->SetNextUninstallExternalWebAppResult(kFooWebAppUrl,
diff --git a/chrome/browser/web_applications/system_web_app_manager.cc b/chrome/browser/web_applications/system_web_app_manager.cc index cec9fc8..a908c5d65 100644 --- a/chrome/browser/web_applications/system_web_app_manager.cc +++ b/chrome/browser/web_applications/system_web_app_manager.cc
@@ -16,7 +16,7 @@ #include "chrome/browser/web_applications/components/app_registrar.h" #include "chrome/browser/web_applications/components/web_app_constants.h" #include "chrome/browser/web_applications/components/web_app_install_utils.h" -#include "chrome/browser/web_applications/components/web_app_ui_delegate.h" +#include "chrome/browser/web_applications/components/web_app_ui_manager.h" #include "chrome/common/chrome_features.h" #include "chrome/common/pref_names.h" #include "chrome/common/webui_url_constants.h" @@ -98,14 +98,14 @@ SystemWebAppManager::~SystemWebAppManager() = default; void SystemWebAppManager::SetSubsystems(PendingAppManager* pending_app_manager, - AppRegistrar* registrar) { + AppRegistrar* registrar, + WebAppUiManager* ui_manager) { pending_app_manager_ = pending_app_manager; registrar_ = registrar; + ui_manager_ = ui_manager; } -void SystemWebAppManager::Start(WebAppUiDelegate* ui_delegate) { - ui_delegate_ = ui_delegate; - +void SystemWebAppManager::Start() { std::map<AppId, GURL> installed_apps = registrar_->GetExternallyInstalledApps(InstallSource::kSystemInstalled); @@ -138,7 +138,7 @@ void SystemWebAppManager::InstallSystemAppsForTesting() { on_apps_synchronized_.reset(new base::OneShotEvent()); system_app_infos_ = CreateSystemWebApps(); - Start(ui_delegate_); + Start(); // Wait for the System Web Apps to install. base::RunLoop run_loop; @@ -218,7 +218,7 @@ void SystemWebAppManager::MigrateSystemWebApps( std::set<SystemAppType> already_installed) { - DCHECK(ui_delegate_); + DCHECK(ui_manager_); for (const auto& type_and_info : system_app_infos_) { // Migrate if a migration source is specified and the app has been newly @@ -235,8 +235,8 @@ << " could not be found when running migration."; continue; } - ui_delegate_->MigrateOSAttributes(type_and_info.second.migration_source, - *system_app_id); + ui_manager_->MigrateOSAttributes(type_and_info.second.migration_source, + *system_app_id); } } }
diff --git a/chrome/browser/web_applications/system_web_app_manager.h b/chrome/browser/web_applications/system_web_app_manager.h index 7c99ae6..015a094 100644 --- a/chrome/browser/web_applications/system_web_app_manager.h +++ b/chrome/browser/web_applications/system_web_app_manager.h
@@ -31,7 +31,7 @@ namespace web_app { -class WebAppUiDelegate; +class WebAppUiManager; // An enum that lists the different System Apps that exist. Can be used to // retrieve the App ID from the underlying Web App system. @@ -68,9 +68,10 @@ virtual ~SystemWebAppManager(); void SetSubsystems(PendingAppManager* pending_app_manager, - AppRegistrar* registrar); + AppRegistrar* registrar, + WebAppUiManager* ui_manager); - void Start(WebAppUiDelegate* ui_delegate); + void Start(); static bool IsEnabled(); @@ -127,7 +128,7 @@ AppRegistrar* registrar_ = nullptr; - WebAppUiDelegate* ui_delegate_ = nullptr; + WebAppUiManager* ui_manager_ = nullptr; base::WeakPtrFactory<SystemWebAppManager> weak_ptr_factory_{this};
diff --git a/chrome/browser/web_applications/test/test_pending_app_manager.cc b/chrome/browser/web_applications/test/test_pending_app_manager.cc index d0aae4e..440043d 100644 --- a/chrome/browser/web_applications/test/test_pending_app_manager.cc +++ b/chrome/browser/web_applications/test/test_pending_app_manager.cc
@@ -24,7 +24,7 @@ deduped_uninstall_count_(0), registrar_(registrar) { // TODO(crbug.com/973324): Wire this up to a TestInstallFinalizer. - SetSubsystems(registrar, nullptr); + SetSubsystems(registrar, nullptr, nullptr); } TestPendingAppManager::~TestPendingAppManager() = default;
diff --git a/chrome/browser/web_applications/test/test_web_app_ui_delegate.cc b/chrome/browser/web_applications/test/test_web_app_ui_delegate.cc deleted file mode 100644 index 2ff9c80..0000000 --- a/chrome/browser/web_applications/test/test_web_app_ui_delegate.cc +++ /dev/null
@@ -1,41 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "chrome/browser/web_applications/test/test_web_app_ui_delegate.h" - -#include <utility> - -#include "base/callback.h" -#include "base/stl_util.h" -#include "base/test/bind_test_util.h" -#include "base/threading/thread_task_runner_handle.h" - -namespace web_app { - -TestWebAppUiDelegate::TestWebAppUiDelegate() = default; - -TestWebAppUiDelegate::~TestWebAppUiDelegate() = default; - -void TestWebAppUiDelegate::SetNumWindowsForApp(const AppId& app_id, - size_t num_windows_for_app) { - app_id_to_num_windows_map_[app_id] = num_windows_for_app; -} - -size_t TestWebAppUiDelegate::GetNumWindowsForApp(const AppId& app_id) { - DCHECK(base::Contains(app_id_to_num_windows_map_, app_id)); - return app_id_to_num_windows_map_[app_id]; -} - -void TestWebAppUiDelegate::NotifyOnAllAppWindowsClosed( - const AppId& app_id, - base::OnceClosure callback) { - base::ThreadTaskRunnerHandle::Get()->PostTask( - FROM_HERE, base::BindLambdaForTesting( - [&, app_id, callback = std::move(callback)]() mutable { - app_id_to_num_windows_map_[app_id] = 0; - std::move(callback).Run(); - })); -} - -} // namespace web_app
diff --git a/chrome/browser/web_applications/test/test_web_app_ui_manager.cc b/chrome/browser/web_applications/test/test_web_app_ui_manager.cc new file mode 100644 index 0000000..cf9016e --- /dev/null +++ b/chrome/browser/web_applications/test/test_web_app_ui_manager.cc
@@ -0,0 +1,48 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/web_applications/test/test_web_app_ui_manager.h" + +#include <utility> + +#include "base/callback.h" +#include "base/stl_util.h" +#include "base/test/bind_test_util.h" +#include "base/threading/thread_task_runner_handle.h" + +namespace web_app { + +TestWebAppUiManager::TestWebAppUiManager() = default; + +TestWebAppUiManager::~TestWebAppUiManager() = default; + +WebAppDialogManager& TestWebAppUiManager::dialog_manager() { + // TODO(crbug.com/973324): Implement a TestWebAppDialogManager to return here. + NOTIMPLEMENTED(); + static WebAppDialogManager* manager = nullptr; + return *manager; +} + +void TestWebAppUiManager::SetNumWindowsForApp(const AppId& app_id, + size_t num_windows_for_app) { + app_id_to_num_windows_map_[app_id] = num_windows_for_app; +} + +size_t TestWebAppUiManager::GetNumWindowsForApp(const AppId& app_id) { + DCHECK(base::Contains(app_id_to_num_windows_map_, app_id)); + return app_id_to_num_windows_map_[app_id]; +} + +void TestWebAppUiManager::NotifyOnAllAppWindowsClosed( + const AppId& app_id, + base::OnceClosure callback) { + base::ThreadTaskRunnerHandle::Get()->PostTask( + FROM_HERE, base::BindLambdaForTesting( + [&, app_id, callback = std::move(callback)]() mutable { + app_id_to_num_windows_map_[app_id] = 0; + std::move(callback).Run(); + })); +} + +} // namespace web_app
diff --git a/chrome/browser/web_applications/test/test_web_app_ui_delegate.h b/chrome/browser/web_applications/test/test_web_app_ui_manager.h similarity index 66% rename from chrome/browser/web_applications/test/test_web_app_ui_delegate.h rename to chrome/browser/web_applications/test/test_web_app_ui_manager.h index ecd44999..360842c 100644 --- a/chrome/browser/web_applications/test/test_web_app_ui_delegate.h +++ b/chrome/browser/web_applications/test/test_web_app_ui_manager.h
@@ -2,24 +2,25 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef CHROME_BROWSER_WEB_APPLICATIONS_TEST_TEST_WEB_APP_UI_DELEGATE_H_ -#define CHROME_BROWSER_WEB_APPLICATIONS_TEST_TEST_WEB_APP_UI_DELEGATE_H_ +#ifndef CHROME_BROWSER_WEB_APPLICATIONS_TEST_TEST_WEB_APP_UI_MANAGER_H_ +#define CHROME_BROWSER_WEB_APPLICATIONS_TEST_TEST_WEB_APP_UI_MANAGER_H_ #include <map> #include "base/macros.h" -#include "chrome/browser/web_applications/components/web_app_ui_delegate.h" +#include "chrome/browser/web_applications/components/web_app_ui_manager.h" namespace web_app { -class TestWebAppUiDelegate : public WebAppUiDelegate { +class TestWebAppUiManager : public WebAppUiManager { public: - TestWebAppUiDelegate(); - virtual ~TestWebAppUiDelegate(); + TestWebAppUiManager(); + ~TestWebAppUiManager() override; void SetNumWindowsForApp(const AppId& app_id, size_t num_windows_for_app); - // WebAppUiDelegate + // WebAppUiManager: + WebAppDialogManager& dialog_manager() override; size_t GetNumWindowsForApp(const AppId& app_id) override; void NotifyOnAllAppWindowsClosed(const AppId& app_id, base::OnceClosure callback) override; @@ -28,9 +29,9 @@ private: std::map<AppId, size_t> app_id_to_num_windows_map_; - DISALLOW_COPY_AND_ASSIGN(TestWebAppUiDelegate); + DISALLOW_COPY_AND_ASSIGN(TestWebAppUiManager); }; } // namespace web_app -#endif // CHROME_BROWSER_WEB_APPLICATIONS_TEST_TEST_WEB_APP_UI_DELEGATE_H_ +#endif // CHROME_BROWSER_WEB_APPLICATIONS_TEST_TEST_WEB_APP_UI_MANAGER_H_
diff --git a/chrome/browser/web_applications/web_app_provider.cc b/chrome/browser/web_applications/web_app_provider.cc index bc2d9ebf..9cedf1a 100644 --- a/chrome/browser/web_applications/web_app_provider.cc +++ b/chrome/browser/web_applications/web_app_provider.cc
@@ -21,6 +21,7 @@ #include "chrome/browser/web_applications/components/web_app_constants.h" #include "chrome/browser/web_applications/components/web_app_helpers.h" #include "chrome/browser/web_applications/components/web_app_install_utils.h" +#include "chrome/browser/web_applications/components/web_app_ui_manager.h" #include "chrome/browser/web_applications/components/web_app_utils.h" #include "chrome/browser/web_applications/extensions/bookmark_app_install_finalizer.h" #include "chrome/browser/web_applications/extensions/bookmark_app_registrar.h" @@ -84,6 +85,8 @@ else CreateBookmarkAppsSubsystems(profile_); + ui_manager_ = WebAppUiManager::Create(profile); + notification_registrar_.Add(this, chrome::NOTIFICATION_PROFILE_DESTROYED, content::Source<Profile>(profile_)); @@ -114,9 +117,9 @@ return web_app_policy_manager_.get(); } -WebAppUiDelegate& WebAppProvider::ui_delegate() { - DCHECK(ui_delegate_); - return *ui_delegate_; +WebAppUiManager& WebAppProvider::ui_manager() { + DCHECK(ui_manager_); + return *ui_manager_; } SystemWebAppManager& WebAppProvider::system_web_app_manager() { @@ -127,6 +130,7 @@ // Destroy subsystems. // The order of destruction is the reverse order of creation: // TODO(calamity): Make subsystem destruction happen in destructor. + ui_manager_.reset(); web_app_policy_manager_.reset(); system_web_app_manager_.reset(); pending_app_manager_.reset(); @@ -189,11 +193,11 @@ return; } - pending_app_manager_->SetSubsystems(registrar_.get(), + pending_app_manager_->SetSubsystems(registrar_.get(), ui_manager_.get(), install_finalizer_.get()); web_app_policy_manager_->SetSubsystems(pending_app_manager_.get()); system_web_app_manager_->SetSubsystems(pending_app_manager_.get(), - registrar_.get()); + registrar_.get(), ui_manager_.get()); } void WebAppProvider::OnRegistryReady() { @@ -201,8 +205,7 @@ if (!base::FeatureList::IsEnabled(features::kDesktopPWAsWithoutExtensions)) { web_app_policy_manager_->Start(); - DCHECK(ui_delegate_); - system_web_app_manager_->Start(ui_delegate_); + system_web_app_manager_->Start(); // Start ExternalWebApps subsystem: ScanForExternalWebApps(
diff --git a/chrome/browser/web_applications/web_app_provider.h b/chrome/browser/web_applications/web_app_provider.h index 850d1a0c..4dae6142 100644 --- a/chrome/browser/web_applications/web_app_provider.h +++ b/chrome/browser/web_applications/web_app_provider.h
@@ -38,7 +38,7 @@ class WebAppTabHelperBase; class SystemWebAppManager; class AppRegistrar; -class WebAppUiDelegate; +class WebAppUiManager; // Forward declarations for new extension-independent subsystems. class WebAppDatabase; @@ -79,7 +79,7 @@ InstallManager& install_manager() override; PendingAppManager& pending_app_manager() override; WebAppPolicyManager* policy_manager() override; - WebAppUiDelegate& ui_delegate() override; + WebAppUiManager& ui_manager() override; WebAppDatabaseFactory& database_factory() { return *database_factory_; } WebAppSyncManager& sync_manager() { return *sync_manager_; } @@ -89,10 +89,6 @@ SystemWebAppManager& system_web_app_manager(); - void set_ui_delegate(WebAppUiDelegate* ui_delegate) { - ui_delegate_ = ui_delegate; - } - static void RegisterProfilePrefs(user_prefs::PrefRegistrySyncable* registry); static WebAppTabHelperBase* CreateTabHelper( content::WebContents* web_contents); @@ -131,7 +127,7 @@ std::unique_ptr<WebAppDatabase> database_; std::unique_ptr<WebAppIconManager> icon_manager_; std::unique_ptr<WebAppSyncManager> sync_manager_; - WebAppUiDelegate* ui_delegate_ = nullptr; + std::unique_ptr<WebAppUiManager> ui_manager_; // New generalized subsystems: std::unique_ptr<AppRegistrar> registrar_;
diff --git a/chrome/common/chrome_features.cc b/chrome/common/chrome_features.cc index 09c8578..4142b67 100644 --- a/chrome/common/chrome_features.cc +++ b/chrome/common/chrome_features.cc
@@ -362,7 +362,7 @@ // Enables committed error pages instead of transient navigation entries for // HTTP auth interstitial pages (i.e. HTTP auth prompts initiated cross-origin). const base::Feature kHTTPAuthCommittedInterstitials{ - "HTTPAuthCommittedInterstitials", base::FEATURE_DISABLED_BY_DEFAULT}; + "HTTPAuthCommittedInterstitials", base::FEATURE_ENABLED_BY_DEFAULT}; // Enables navigation suggestions UI for lookalike URLs (e.g. internationalized // domain names that are visually similar to popular domains or to domains with
diff --git a/chrome/common/extensions/docs/templates/articles/messaging.html b/chrome/common/extensions/docs/templates/articles/messaging.html index 3e87517..8b8d3ae 100644 --- a/chrome/common/extensions/docs/templates/articles/messaging.html +++ b/chrome/common/extensions/docs/templates/articles/messaging.html
@@ -280,7 +280,7 @@ <p> This will expose the messaging API to any page which matches the URL patterns you specify. The URL pattern must contain at least a -<a href="http://en.wikipedia.org/wiki/Second-level_domain">second-level domain</a> +<a href="https://en.wikipedia.org/wiki/Second-level_domain">second-level domain</a> - that is, hostname patterns like "*", "*.com", "*.co.uk", and "*.appspot.com" are prohibited. From the web page, use the @@ -334,12 +334,32 @@ <h2 id="security-considerations">Security considerations</h2> +<h3 id="content-scripts-are-less-trustworthy"> + Content scripts are less trustworthy +</h3> + +<p> +<a href="security#content_scripts">Content scripts are less trustworthy</a> +than the extension background page (e.g., a malicious web page might be able +to compromise the renderer process where the content scripts run). +Assume that messages from a content script might have been crafted by an +attacker and make sure to +<a href="security#sanitize">validate and sanitize all input</a>. +Assume any data sent to the content script might leak to the web page. +Limit the scope of privileged actions that can be triggered by +messages received from content scripts. +</p> + +<h3 id="cross-site-scripting">Cross-site scripting</h3> + <p> When receiving a message from a content script or another extension, your -background page should be careful not to fall victim to <a -href="http://en.wikipedia.org/wiki/Cross-site_scripting">cross-site -scripting</a>. Specifically, avoid using dangerous APIs such as the -below: +scripts should be careful not to fall victim to <a +href="https://en.wikipedia.org/wiki/Cross-site_scripting">cross-site +scripting</a>. This advice applies to scripts running inside the extension +background page as well as to content scripts running inside other web origins. + +Specifically, avoid using dangerous APIs such as the ones below: </p> <pre data-filename="background.js"> chrome.tabs.sendMessage(tab.id, {greeting: "hello"}, function(response) {
diff --git a/chrome/common/extensions/docs/templates/articles/security.html b/chrome/common/extensions/docs/templates/articles/security.html index 86d7a56..664a57e 100644 --- a/chrome/common/extensions/docs/templates/articles/security.html +++ b/chrome/common/extensions/docs/templates/articles/security.html
@@ -221,16 +221,53 @@ <h2 id="content_scripts">Use Content Scripts Carefully</h2> <p> While <a href="/content_scripts">content scripts</a> live in an - <a href="/content_scripts#execution-environment">isolated world</a>, - they are not immune from attacks. - Content scripts are the only part of an extension - that interacts directly with the web page. - Because of this, - hostile websites may manipulate parts of the DOM the content script depends on, - or exploit surprising web standard behavior, such as - <a href="https://html.spec.whatwg.org/#dom-window-nameditem">named items</a>. + <a href="/content_scripts#isolated_world">isolated world</a>, + they are not immune from attacks: + <ul> + <li> + Content scripts are the only part of an extension that interacts + directly with the web page. Because of this, hostile web pages may + manipulate parts of the DOM the content script depends on, or exploit + surprising web standard behavior, such as + <a href="https://html.spec.whatwg.org/#dom-window-nameditem">named items</a>. + </li><li> + To interact with DOM of web pages, content scripts need to execute in + the same renderer process as the web page. This makes content scripts + vulnerable to leaking data via side channel attacks (e.g., + <a href="https://spectreattack.com/">Spectre</a>), + and to being taken over by an attacker if a malicious web page + compromises the renderer process. + </li> + </ul> +</p><p> Sensitive work should be performed in a dedicated process, - such as the extension's <a href="/background_page">background script</a>. + such as the extension's <a href="/background_pages">background script</a>. + Avoid accidentally exposing extension privileges to content scripts: + <ul> + <li> + Assume that + <a href="/messaging#content-scripts-are-less-trustworthy" + >messages from a content script</a> + might have been crafted by an attacker (e.g. + <a href="#sanitize">validate and sanitize</a> + all input and protect your scripts from + <a href="/messaging#cross-site-scripting">cross-site scripting</a>). + </li><li> + Assume any data sent to the content script might leak to the web page. + Do not send sensitive data (e.g. secrets from the extension, data from + other web origins, browsing history) to content scripts. + </li><li> + Limit the scope of privileged actions that can be triggered + by content scripts. Do not allow content scripts to + <a href="/xhr#xhr-vs-content-scripts" + >trigger requests to arbitrary URLs</a> + or pass arbitrary arguments to extension APIs (e.g., do not + allow passing arbitrary URLs to + <a href="https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API" + ><code>fetch</code></a> or + <a href="/tabs#method-create"><code>chrome.tabs.create</code></a> API). + </li> + </ul> </p> <h2 id="sanitize">Register and Sanitize Inputs</h2> <p> @@ -269,7 +306,7 @@ }); </pre> <p> - Prevent an extension from executing an attackers script by + Prevent an extension from executing an attacker's script by sanitizing user inputs and incoming data, even from the extension itself and approved sources. <a href="/security#avoid">Avoid executable APIs</a>.
diff --git a/chrome/common/extensions/docs/templates/articles/xhr.html b/chrome/common/extensions/docs/templates/articles/xhr.html index 5df449a..c1ee41b 100644 --- a/chrome/common/extensions/docs/templates/articles/xhr.html +++ b/chrome/common/extensions/docs/templates/articles/xhr.html
@@ -150,9 +150,10 @@ <p> When performing cross-origin requests on behalf of a content script, be careful -to guard against a malicious webpage that might try to impersonate a content -script. In particular, do not allow content scripts to request an arbitrary -URL. +to <a href="security#content_scripts" + >guard against malicious web pages</a> that might try to impersonate a +content script. In particular, do not allow content scripts to request an +arbitrary URL. </p> <p> @@ -166,7 +167,7 @@ chrome.runtime.onMessage.addListener( function(request, sender, sendResponse) { if (request.contentScriptQuery == 'fetchUrl') { - // WARNING: SECURITY PROBLEM - a malicious webpage may abuse + // WARNING: SECURITY PROBLEM - a malicious web page may abuse // the message handler to get access to arbitrary cross-origin // resources. fetch(request.url) @@ -188,7 +189,7 @@ <p> In the approach above, the content script can ask the extension to fetch any -URL that the extension has access to. A malicious website may be able to forge +URL that the extension has access to. A malicious web page may be able to forge such messages and trick the extension into giving access to cross-origin resources. </p>
diff --git a/chrome/common/extensions/extension_constants.cc b/chrome/common/extensions/extension_constants.cc index 4375692..0f1a64f 100644 --- a/chrome/common/extensions/extension_constants.cc +++ b/chrome/common/extensions/extension_constants.cc
@@ -45,6 +45,50 @@ const char kMediaRouterStableExtensionId[] = "pkedcjkdefgpdelpbcmbmeomcjbeemfm"; const char kCloudReportingExtensionId[] = "oempjldejiginopiohodkdoklcjklbaa"; +const char* const kBuiltInFirstPartyExtensionIds[] = { + kCalculatorAppId, + kCalendarAppId, + kChromeRemoteDesktopAppId, + kCloudPrintAppId, + kDataSaverExtensionId, + kDocsOfflineExtensionId, + kDriveHostedAppId, + kEnterpriseWebStoreAppId, + kGmailAppId, + kGoogleDocAppId, + kGoogleMapsAppId, + kGooglePhotosAppId, + kGooglePlayBooksAppId, + kGooglePlayMoviesAppId, + kGooglePlayMusicAppId, + kGooglePlusAppId, + kGoogleSheetsAppId, + kGoogleSlidesAppId, + kHTermAppId, + kHTermDevAppId, + kIdentityApiUiAppId, + kCroshBuiltinAppId, + kTextEditorAppId, + kInAppPaymentsSupportAppId, + kMediaRouterStableExtensionId, + kCloudReportingExtensionId, +#if defined(OS_CHROMEOS) + kAssessmentAssistantExtensionId, + kAutoclickExtensionId, + kSelectToSpeakExtensionId, + kSwitchAccessExtensionId, + kFirstRunDialogId, + kEspeakSpeechSynthesisExtensionId, + kGoogleSpeechSynthesisExtensionId, + kWallpaperManagerId, + kZipArchiverExtensionId, + kChromeCameraAppId, + kChromeCameraAppDevId, + kKioskNextHomeAppId, +#endif // defined(OS_CHROMEOS) + nullptr, // Null-terminated array. +}; + #if defined(OS_CHROMEOS) const char kAssessmentAssistantExtensionId[] = "gndmhdcefbhlchkhipcnnbkcmicncehk"; @@ -76,7 +120,8 @@ const char kChromeCameraAppDevId[] = "flgnmkgjffmkephdokeeliiopbjaafpm"; const char kChromeCameraAppPath[] = "chromeos/camera"; const char kKioskNextHomeAppId[] = "nbaolgedfgoedkjbfmpediclncanmpbc"; -#endif + +#endif // defined(CHROME_OS) const char kAppStateNotInstalled[] = "not_installed"; const char kAppStateInstalled[] = "installed";
diff --git a/chrome/common/extensions/extension_constants.h b/chrome/common/extensions/extension_constants.h index 6ce77369..bfbb9d2 100644 --- a/chrome/common/extensions/extension_constants.h +++ b/chrome/common/extensions/extension_constants.h
@@ -105,6 +105,9 @@ // The extension id of the Chrome Reporting extension. extern const char kCloudReportingExtensionId[]; +// A list of all the first party extension IDs, last entry is null. +extern const char* const kBuiltInFirstPartyExtensionIds[]; + // The buckets used for app launches. enum AppLaunchBucket { // Launch from NTP apps section while maximized.
diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn index 934d479a..b116e3f 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn
@@ -1223,7 +1223,7 @@ "../browser/ui/views/webauthn/authenticator_dialog_view_browsertest.cc", "../browser/ui/views/webview_accessibility_browsertest.cc", "../browser/ui/web_applications/bookmark_app_browsertest.cc", - "../browser/ui/web_applications/web_app_ui_service_browsertest.cc", + "../browser/ui/web_applications/web_app_ui_manager_impl_browsertest.cc", "../browser/ui/webauthn/authenticator_dialog_browsertest.cc", "../browser/ui/webui/bookmarks/bookmarks_browsertest.cc", "../browser/ui/webui/bookmarks/bookmarks_browsertest.h", @@ -2142,6 +2142,7 @@ "../browser/chromeos/policy/device_system_use_24hour_clock_browsertest.cc", "../browser/chromeos/policy/display_resolution_handler_browsertest.cc", "../browser/chromeos/policy/display_rotation_default_handler_browsertest.cc", + "../browser/chromeos/policy/external_data_handlers/device_wilco_dtc_configuration_external_data_handler_browsertest.cc", "../browser/chromeos/policy/force_maximize_on_first_run_chromeos_browsertest.cc", "../browser/chromeos/policy/login_policy_test_base.cc", "../browser/chromeos/policy/login_policy_test_base.h", @@ -3091,6 +3092,7 @@ "../browser/sessions/chrome_serialized_navigation_driver_unittest.cc", "../browser/sessions/restore_on_startup_policy_handler_unittest.cc", "../browser/sessions/session_common_utils_unittest.cc", + "../browser/sharing/ack_message_handler_unittest.cc", "../browser/sharing/fake_local_device_info_provider.cc", "../browser/sharing/fake_local_device_info_provider.h", "../browser/sharing/sharing_device_registration_unittest.cc",
diff --git a/chrome/test/base/test_browser_window.cc b/chrome/test/base/test_browser_window.cc index 357352a..5ebb72d 100644 --- a/chrome/test/base/test_browser_window.cc +++ b/chrome/test/base/test_browser_window.cc
@@ -64,8 +64,8 @@ return false; } -bool TestBrowserWindow::IsAlwaysOnTop() const { - return false; +ui::ZOrderLevel TestBrowserWindow::GetZOrderLevel() const { + return ui::ZOrderLevel::kNormal; } gfx::NativeWindow TestBrowserWindow::GetNativeWindow() const {
diff --git a/chrome/test/base/test_browser_window.h b/chrome/test/base/test_browser_window.h index 8edcb3e..a2aa2fe 100644 --- a/chrome/test/base/test_browser_window.h +++ b/chrome/test/base/test_browser_window.h
@@ -54,8 +54,8 @@ void Deactivate() override {} bool IsActive() const override; void FlashFrame(bool flash) override {} - bool IsAlwaysOnTop() const override; - void SetAlwaysOnTop(bool always_on_top) override {} + ui::ZOrderLevel GetZOrderLevel() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override {} gfx::NativeWindow GetNativeWindow() const override; void SetTopControlsShownRatio(content::WebContents* web_contents, float ratio) override;
diff --git a/chrome/test/data/pdf/printing_icon_test.js b/chrome/test/data/pdf/printing_icon_test.js new file mode 100644 index 0000000..f9c31687 --- /dev/null +++ b/chrome/test/data/pdf/printing_icon_test.js
@@ -0,0 +1,22 @@ +// Copyright 2019 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +chrome.test.runTests([ + function testPrintingEnabled() { + const toolbar = document.body.querySelector('#toolbar'); + toolbar.printingEnabled = true; + const printIcon = toolbar.shadowRoot.querySelector('#print'); + chrome.test.assertTrue(!!printIcon); + chrome.test.assertFalse(printIcon.hidden); + chrome.test.succeed(); + }, + function testPrintingDisabled() { + const toolbar = document.body.querySelector('#toolbar'); + toolbar.printingEnabled = false; + const printIcon = toolbar.shadowRoot.querySelector('#print'); + chrome.test.assertTrue(!!printIcon); + chrome.test.assertTrue(printIcon.hidden); + chrome.test.succeed(); + }, +]);
diff --git a/chrome/test/data/policy/wilco_dtc_configuration.json b/chrome/test/data/policy/wilco_dtc_configuration.json new file mode 100644 index 0000000..0147f0c --- /dev/null +++ b/chrome/test/data/policy/wilco_dtc_configuration.json
@@ -0,0 +1 @@ +[{"sample_name":"name"}]
diff --git a/chrome/test/delayload/delayloads_unittest.cc b/chrome/test/delayload/delayloads_unittest.cc index d2307288..ee97aa14 100644 --- a/chrome/test/delayload/delayloads_unittest.cc +++ b/chrome/test/delayload/delayloads_unittest.cc
@@ -158,7 +158,7 @@ EXPECT_EQ(nullptr, ::GetModuleHandle(L"user32.dll")); } -TEST_F(DelayloadsTest, ChromeChildDllDelayloadsCheck) { +TEST_F(DelayloadsTest, DISABLED_ChromeChildDllDelayloadsCheck) { base::FilePath dll; ASSERT_TRUE(base::PathService::Get(base::DIR_EXE, &dll)); dll = dll.Append(L"chrome_child.dll"); @@ -209,7 +209,7 @@ } } -TEST_F(DelayloadsTest, ChromeChildDllLoadSanityTest) { +TEST_F(DelayloadsTest, DISABLED_ChromeChildDllLoadSanityTest) { // On Win7 we expect this test to result in user32.dll getting loaded. As a // result, we need to ensure it is executed in its own test process. This // "test" will re-launch with custom parameters to accomplish that.
diff --git a/chromeos/dbus/cryptohome/fake_cryptohome_client.cc b/chromeos/dbus/cryptohome/fake_cryptohome_client.cc index 4645a05..158b71f 100644 --- a/chromeos/dbus/cryptohome/fake_cryptohome_client.cc +++ b/chromeos/dbus/cryptohome/fake_cryptohome_client.cc
@@ -611,6 +611,8 @@ request.force_dircrypto_if_available()) { error = cryptohome::CRYPTOHOME_ERROR_MOUNT_OLD_ENCRYPTION; } + if (mount_create_required_ && !request.has_create()) + error = cryptohome::CRYPTOHOME_ERROR_ACCOUNT_NOT_FOUND; reply.set_error(error); ReturnProtobufMethodCallback(reply, std::move(callback)); }
diff --git a/chromeos/dbus/cryptohome/fake_cryptohome_client.h b/chromeos/dbus/cryptohome/fake_cryptohome_client.h index 2d9d4e0..18820fa 100644 --- a/chromeos/dbus/cryptohome/fake_cryptohome_client.h +++ b/chromeos/dbus/cryptohome/fake_cryptohome_client.h
@@ -248,6 +248,13 @@ // Changes the behavior of TpmIsEnabled(). void set_tpm_is_enabled(bool value) { tpm_is_enabled_ = value; } + // Sets whether the MountEx() call should fail when the |create| field is not + // provided (the error code will be CRYPTOHOME_ERROR_ACCOUNT_NOT_FOUND). + // This allows to simulate the behavior during the new user profile creation. + void set_mount_create_required(bool mount_create_required) { + mount_create_required_ = mount_create_required; + } + // Sets the unmount result of Unmount() call. void set_unmount_result(bool result) { unmount_result_ = result; } @@ -337,11 +344,18 @@ void NotifyLowDiskSpace(uint64_t disk_free_bytes); // MountEx getters. + const cryptohome::MountRequest& get_last_mount_request() const { + return last_mount_request_; + } bool to_migrate_from_ecryptfs() const { return last_mount_request_.to_migrate_from_ecryptfs(); } bool hidden_mount() const { return last_mount_request_.hidden_mount(); } bool public_mount() const { return last_mount_request_.public_mount(); } + const cryptohome::AuthorizationRequest& get_last_mount_authentication() + const { + return last_mount_auth_request_; + } const std::string& get_secret_for_last_mount_authentication() const { return last_mount_auth_request_.key().secret(); } @@ -411,6 +425,7 @@ int remove_firmware_management_parameters_from_tpm_call_count_; int async_call_id_; + bool mount_create_required_ = false; bool unmount_result_; std::vector<uint8_t> system_salt_;
diff --git a/components/bookmark_bar_strings_grdp/OWNERS b/components/bookmark_bar_strings_grdp/OWNERS index 166b0f10..555d7e4 100644 --- a/components/bookmark_bar_strings_grdp/OWNERS +++ b/components/bookmark_bar_strings_grdp/OWNERS
@@ -1 +1,2 @@ file://components/bookmarks/OWNERS +# COMPONENT: UI>Browser>Bookmarks
diff --git a/components/bookmarks/OWNERS b/components/bookmarks/OWNERS index 90b3e80..327326d4 100644 --- a/components/bookmarks/OWNERS +++ b/components/bookmarks/OWNERS
@@ -1 +1,3 @@ sky@chromium.org + +# COMPONENT: UI>Browser>Bookmarks
diff --git a/components/exo/client_controlled_shell_surface.cc b/components/exo/client_controlled_shell_surface.cc index ff704fe..1116ec2c 100644 --- a/components/exo/client_controlled_shell_surface.cc +++ b/components/exo/client_controlled_shell_surface.cc
@@ -401,8 +401,10 @@ if (!widget_) CreateShellSurfaceWidget(ui::SHOW_STATE_NORMAL); - widget_->GetNativeWindow()->SetProperty(aura::client::kAlwaysOnTopKey, - always_on_top); + widget_->GetNativeWindow()->SetProperty(aura::client::kZOrderingKey, + always_on_top + ? ui::ZOrderLevel::kFloatingWindow + : ui::ZOrderLevel::kNormal); } void ClientControlledShellSurface::SetImeBlocked(bool ime_blocked) {
diff --git a/components/favicon/OWNERS b/components/favicon/OWNERS index 6581507..68d5c7cc 100644 --- a/components/favicon/OWNERS +++ b/components/favicon/OWNERS
@@ -1,3 +1,4 @@ mastiz@chromium.org pkotwicz@chromium.org sky@chromium.org +# COMPONENT: UI>Browser>History
diff --git a/components/feedback/anonymizer_tool.cc b/components/feedback/anonymizer_tool.cc index d6d6fbb4..4f77281 100644 --- a/components/feedback/anonymizer_tool.cc +++ b/components/feedback/anonymizer_tool.cc
@@ -353,8 +353,9 @@ } // namespace -AnonymizerTool::AnonymizerTool() - : custom_patterns_with_context_(base::size(kCustomPatternsWithContext)), +AnonymizerTool::AnonymizerTool(const char* const* first_party_extension_ids) + : first_party_extension_ids_(first_party_extension_ids), + custom_patterns_with_context_(base::size(kCustomPatternsWithContext)), custom_patterns_without_context_( base::size(kCustomPatternsWithoutContext)) { DETACH_FROM_SEQUENCE(sequence_checker_); @@ -477,11 +478,49 @@ return result; } -bool WhitelistMatchedId(re2::StringPiece matched_id) { - bool is_safe_chrome_resource = - matched_id.starts_with("chrome://resources/") && - !matched_id.contains("?"); - return is_safe_chrome_resource; +// This takes a |url| argument and returns true if the URL is whitelisted and +// does NOT need to be redacted, returns false otherwise. +bool IsUrlWhitelisted(re2::StringPiece url, + const char* const* first_party_extension_ids) { + // We do not whitelist anything with a query parameter. + if (url.contains("?")) + return false; + + // Check for whitelisting of chrome:// URLs. + if (url.starts_with("chrome://")) { + // We allow everything in chrome://resources/. + if (url.starts_with("chrome://resources/")) + return true; + + // We allow chrome://*/crisper.js. + if (url.ends_with("/crisper.js")) + return true; + + return false; + } + + // If the whitelist is null, then don't check it. + if (!first_party_extension_ids) + return false; + + // Whitelist URLs of the format chrome-extension://<first-party-id>/*.js + if (!url.starts_with("chrome-extension://")) + return false; + + // These must end with a .js extension. + if (!url.ends_with(".js")) + return false; + + int i = 0; + const char* test_id = first_party_extension_ids[i]; + const re2::StringPiece url_sub = + url.substr(sizeof("chrome-extension://") - 1); + while (test_id) { + if (url_sub.starts_with(test_id)) + return true; + test_id = first_party_extension_ids[++i]; + } + return false; } std::string AnonymizerTool::AnonymizeCustomPatternWithoutContext( @@ -499,7 +538,7 @@ re2::StringPiece skipped; re2::StringPiece matched_id; while (FindAndConsumeAndGetSkipped(&text, *re, &skipped, &matched_id)) { - if (WhitelistMatchedId(matched_id)) { + if (IsUrlWhitelisted(matched_id, first_party_extension_ids_)) { skipped.AppendToString(&result); matched_id.AppendToString(&result); continue; @@ -527,8 +566,10 @@ } AnonymizerToolContainer::AnonymizerToolContainer( - scoped_refptr<base::SequencedTaskRunner> task_runner) - : anonymizer_(new AnonymizerTool), task_runner_(task_runner) {} + scoped_refptr<base::SequencedTaskRunner> task_runner, + const char* const* first_party_extension_ids) + : anonymizer_(new AnonymizerTool(first_party_extension_ids)), + task_runner_(task_runner) {} AnonymizerToolContainer::~AnonymizerToolContainer() { task_runner_->DeleteSoon(FROM_HERE, std::move(anonymizer_));
diff --git a/components/feedback/anonymizer_tool.h b/components/feedback/anonymizer_tool.h index a4e2d3a..9aea4ba 100644 --- a/components/feedback/anonymizer_tool.h +++ b/components/feedback/anonymizer_tool.h
@@ -32,7 +32,10 @@ class AnonymizerTool { public: - AnonymizerTool(); + // |first_party_extension_ids| is a null terminated array of all the 1st + // party extension IDs whose URLs won't be redacted. It is OK to pass null for + // that value if it's OK to redact those URLs or they won't be present. + AnonymizerTool(const char* const* first_party_extension_ids); ~AnonymizerTool(); // Returns an anonymized version of |input|. PII-sensitive data (such as MAC @@ -57,6 +60,10 @@ const CustomPatternWithoutContext& pattern, std::map<std::string, std::string>* identifier_space); + // Null-terminated list of first party extension IDs. We need to have this + // passed into us because we can't refer to the code where these are defined. + const char* const* first_party_extension_ids_; // Not owned. + // Map of MAC addresses discovered in anonymized strings to anonymized // representations. 11:22:33:44:55:66 gets anonymized to 11:22:33:00:00:01, // where the first three bytes represent the manufacturer. The last three @@ -88,7 +95,8 @@ : public base::RefCountedThreadSafe<AnonymizerToolContainer> { public: explicit AnonymizerToolContainer( - scoped_refptr<base::SequencedTaskRunner> task_runner); + scoped_refptr<base::SequencedTaskRunner> task_runner, + const char* const* first_party_extension_ids); // Returns a pointer to the instance of this anonymier. May only be called // on |task_runner_|.
diff --git a/components/feedback/anonymizer_tool_unittest.cc b/components/feedback/anonymizer_tool_unittest.cc index 4f490481..7a8faecb 100644 --- a/components/feedback/anonymizer_tool_unittest.cc +++ b/components/feedback/anonymizer_tool_unittest.cc
@@ -10,6 +10,9 @@ namespace feedback { +const char kFakeFirstPartyID[] = "nkoccljplnhpfnfiajclkommnmllphnl"; +const char* const kFakeFirstPartyExtensionIDs[] = {kFakeFirstPartyID, nullptr}; + class AnonymizerToolTest : public testing::Test { protected: std::string AnonymizeMACAddresses(const std::string& input) { @@ -35,7 +38,7 @@ space); } - AnonymizerTool anonymizer_; + AnonymizerTool anonymizer_{kFakeFirstPartyExtensionIDs}; }; TEST_F(AnonymizerToolTest, Anonymize) { @@ -347,8 +350,16 @@ "aa:aa:aa:00:00:01"}, {"chrome://resources/foo", // Secure chrome resource, whitelisted. "chrome://resources/foo"}, + {"chrome://settings/crisper.js", // Whitelisted settings URLs. + "chrome://settings/crisper.js"}, + // Whitelisted first party extension. + {"chrome-extension://nkoccljplnhpfnfiajclkommnmllphnl/foobar.js", + "chrome-extension://nkoccljplnhpfnfiajclkommnmllphnl/foobar.js"}, {"chrome://resources/f?user=bar", // Potentially PII in parameter. - "<URL: 2>"}}; + "<URL: 2>"}, + {"chrome-extension://nkoccljplnhpfnfiajclkommnmllphnl/foobar.js?bar=x", + "<URL: 3>"}, // Potentially PII in parameter. + }; std::string anon_input; std::string anon_output; for (const auto& s : data) {
diff --git a/components/feedback/system_logs/system_logs_fetcher.cc b/components/feedback/system_logs/system_logs_fetcher.cc index 56eda8a6..62ed817 100644 --- a/components/feedback/system_logs/system_logs_fetcher.cc +++ b/components/feedback/system_logs/system_logs_fetcher.cc
@@ -46,7 +46,9 @@ } // namespace -SystemLogsFetcher::SystemLogsFetcher(bool scrub_data) +SystemLogsFetcher::SystemLogsFetcher( + bool scrub_data, + const char* const first_party_extension_ids[]) : response_(std::make_unique<SystemLogsResponse>()), num_pending_requests_(0), task_runner_for_anonymizer_(base::CreateSequencedTaskRunnerWithTraits( @@ -55,7 +57,8 @@ base::TaskPriority::USER_VISIBLE, base::TaskShutdownBehavior::CONTINUE_ON_SHUTDOWN})) { if (scrub_data) - anonymizer_ = std::make_unique<feedback::AnonymizerTool>(); + anonymizer_ = + std::make_unique<feedback::AnonymizerTool>(first_party_extension_ids); } SystemLogsFetcher::~SystemLogsFetcher() {
diff --git a/components/feedback/system_logs/system_logs_fetcher.h b/components/feedback/system_logs/system_logs_fetcher.h index f34bf81..d6a5394 100644 --- a/components/feedback/system_logs/system_logs_fetcher.h +++ b/components/feedback/system_logs/system_logs_fetcher.h
@@ -43,8 +43,12 @@ // }; class SystemLogsFetcher { public: - // If scrub_data is true, logs will be anonymized. - explicit SystemLogsFetcher(bool scrub_data); + // If |scrub_data| is true, logs will be anonymized. + // |first_party_extension_ids| is a null terminated array of all the 1st + // party extension IDs whose URLs won't be redacted. It is OK to pass null for + // that value if it's OK to redact those URLs or they won't be present. + explicit SystemLogsFetcher(bool scrub_data, + const char* const first_party_extension_ids[]); ~SystemLogsFetcher(); // Adds a source to use when fetching.
diff --git a/components/history/OWNERS b/components/history/OWNERS index 90b3e80..3a86eb84 100644 --- a/components/history/OWNERS +++ b/components/history/OWNERS
@@ -1 +1,2 @@ sky@chromium.org +# COMPONENT: UI>Browser>History
diff --git a/components/history/ios/OWNERS b/components/history/ios/OWNERS new file mode 100644 index 0000000..8836311c --- /dev/null +++ b/components/history/ios/OWNERS
@@ -0,0 +1,2 @@ +# COMPONENT: Mobile>iOSWeb +# TEAM: ios-directory-owners@chromium.org
diff --git a/components/metrics_services_manager/metrics_services_manager.cc b/components/metrics_services_manager/metrics_services_manager.cc index 67244bbb..45b13b13 100644 --- a/components/metrics_services_manager/metrics_services_manager.cc +++ b/components/metrics_services_manager/metrics_services_manager.cc
@@ -177,4 +177,8 @@ return client_->IsMetricsReportingEnabled(); } +bool MetricsServicesManager::IsMetricsConsentGiven() const { + return client_->IsMetricsConsentGiven(); +} + } // namespace metrics_services_manager
diff --git a/components/metrics_services_manager/metrics_services_manager.h b/components/metrics_services_manager/metrics_services_manager.h index 638c2fc..38c955cf 100644 --- a/components/metrics_services_manager/metrics_services_manager.h +++ b/components/metrics_services_manager/metrics_services_manager.h
@@ -82,6 +82,9 @@ // Gets the current state of metric reporting. bool IsMetricsReportingEnabled() const; + // Gets the current state of metrics consent. + bool IsMetricsConsentGiven() const; + private: // Update the managed services when permissions for recording/uploading // metrics change.
diff --git a/components/offline_pages/core/BUILD.gn b/components/offline_pages/core/BUILD.gn index 36655d4..23d262f 100644 --- a/components/offline_pages/core/BUILD.gn +++ b/components/offline_pages/core/BUILD.gn
@@ -48,8 +48,8 @@ "model/startup_maintenance_task.h", "model/store_visuals_task.cc", "model/store_visuals_task.h", - "model/update_file_path_task.cc", - "model/update_file_path_task.h", + "model/update_publish_id_task.cc", + "model/update_publish_id_task.h", "model/visuals_availability_task.cc", "model/visuals_availability_task.h", "offline_clock.cc", @@ -170,7 +170,7 @@ "model/persistent_page_consistency_check_task_unittest.cc", "model/startup_maintenance_task_unittest.cc", "model/store_visuals_task_unittest.cc", - "model/update_file_path_task_unittest.cc", + "model/update_publish_id_task_unittest.cc", "model/visuals_availability_task_unittest.cc", "offline_event_logger_unittest.cc", "offline_page_feature_unittest.cc",
diff --git a/components/offline_pages/core/model/offline_page_item_generator.cc b/components/offline_pages/core/model/offline_page_item_generator.cc index 619b017..7a883d5 100644 --- a/components/offline_pages/core/model/offline_page_item_generator.cc +++ b/components/offline_pages/core/model/offline_page_item_generator.cc
@@ -33,9 +33,11 @@ item.access_count = access_count_; item.digest = digest_; item.file_missing_time = file_missing_time_; - if (use_offline_id_as_system_download_id_) { + if (use_offline_id_as_system_download_id_) item.system_download_id = item.offline_id; - } + else + item.system_download_id = system_download_id_; + return item; } @@ -108,4 +110,8 @@ use_offline_id_as_system_download_id_ = enable; } +void OfflinePageItemGenerator::SetSystemDownloadId(int64_t system_download_id) { + system_download_id_ = system_download_id; +} + } // namespace offline_pages
diff --git a/components/offline_pages/core/model/offline_page_item_generator.h b/components/offline_pages/core/model/offline_page_item_generator.h index e8605bc..c07e62a68 100644 --- a/components/offline_pages/core/model/offline_page_item_generator.h +++ b/components/offline_pages/core/model/offline_page_item_generator.h
@@ -8,6 +8,7 @@ #include <string> #include "components/offline_pages/core/client_namespace_constants.h" +#include "components/offline_pages/core/offline_page_archive_publisher.h" #include "components/offline_pages/core/offline_page_item.h" class GURL; @@ -38,6 +39,7 @@ void SetDigest(const std::string& digest); void SetFileMissingTime(base::Time file_missing_time); void SetUseOfflineIdAsSystemDownloadId(bool enable); + void SetSystemDownloadId(int64_t system_download_id); private: std::string namespace_ = kDefaultNamespace; @@ -52,6 +54,7 @@ base::FilePath archive_dir_; std::string digest_; base::Time file_missing_time_; + int64_t system_download_id_ = kArchiveNotPublished; bool use_offline_id_as_system_download_id_ = false; };
diff --git a/components/offline_pages/core/model/offline_page_model_taskified.cc b/components/offline_pages/core/model/offline_page_model_taskified.cc index ae9e082..539deee 100644 --- a/components/offline_pages/core/model/offline_page_model_taskified.cc +++ b/components/offline_pages/core/model/offline_page_model_taskified.cc
@@ -28,7 +28,7 @@ #include "components/offline_pages/core/model/persistent_page_consistency_check_task.h" #include "components/offline_pages/core/model/startup_maintenance_task.h" #include "components/offline_pages/core/model/store_visuals_task.h" -#include "components/offline_pages/core/model/update_file_path_task.h" +#include "components/offline_pages/core/model/update_publish_id_task.h" #include "components/offline_pages/core/model/visuals_availability_task.h" #include "components/offline_pages/core/offline_clock.h" #include "components/offline_pages/core/offline_page_feature.h" @@ -478,8 +478,8 @@ add_page_start_time - publish_start_time); OfflinePageItem page = offline_page; - page.file_path = publish_results.new_file_path; - page.system_download_id = publish_results.download_id; + page.file_path = publish_results.id.new_file_path; + page.system_download_id = publish_results.id.download_id; AddPage(page, base::BindOnce( &OfflinePageModelTaskified::OnAddPageForSavePageDone, @@ -501,21 +501,22 @@ PublishPageCallback publish_done_callback, const OfflinePageItem& offline_page, PublishArchiveResult publish_results) { - base::FilePath file_path = publish_results.new_file_path; SavePageResult result = publish_results.move_result; // Call the callback with success == false if we failed to move the page. if (result != SavePageResult::SUCCESS) { - std::move(publish_done_callback).Run(file_path, result); + std::move(publish_done_callback) + .Run(publish_results.id.new_file_path, result); return; } // Update the OfflinePageModel with the new location for the page, which is - // found in move_results.new_file_path, and with the download ID found at - // move_results.download_id. Return the updated offline_page to the callback. - auto task = std::make_unique<UpdateFilePathTask>( - store_.get(), offline_page.offline_id, file_path, + // found in move_results.id.new_file_path, and with the download ID found at + // move_results.id.download_id. Return the updated offline_page to the + // callback. + auto task = std::make_unique<UpdatePublishIdTask>( + store_.get(), offline_page.offline_id, publish_results.id, base::BindOnce(&OnUpdateFilePathDone, std::move(publish_done_callback), - file_path, result)); + publish_results.id.new_file_path, result)); task_queue_.AddTask(std::move(task)); } @@ -566,7 +567,7 @@ DeletePageResult result, const std::vector<OfflinePageItem>& deleted_items) { UMA_HISTOGRAM_ENUMERATION("OfflinePages.DeletePageResult", result); - std::vector<int64_t> system_download_ids; + std::vector<PublishedArchiveId> publish_ids; // Notify observers and run callback. for (const auto& item : deleted_items) { @@ -576,15 +577,15 @@ offline_event_logger_.RecordPageDeleted(item.offline_id); for (Observer& observer : observers_) observer.OfflinePageDeleted(item); - if (item.system_download_id != 0) - system_download_ids.push_back(item.system_download_id); + + publish_ids.emplace_back(item.system_download_id, item.file_path); } // Remove the page from the system download manager. We don't need to wait for // completion before calling the delete page callback. - task_runner_->PostTask( - FROM_HERE, base::BindOnce(&OfflinePageModelTaskified::Unpublish, - archive_publisher_.get(), system_download_ids)); + task_runner_->PostTask(FROM_HERE, + base::BindOnce(&OfflinePageModelTaskified::Unpublish, + archive_publisher_.get(), publish_ids)); if (!callback.is_null()) std::move(callback).Run(result); @@ -610,9 +611,9 @@ void OfflinePageModelTaskified::Unpublish( OfflinePageArchivePublisher* publisher, - const std::vector<int64_t>& system_download_ids) { - if (system_download_ids.size() > 0) - publisher->UnpublishArchives(system_download_ids); + const std::vector<PublishedArchiveId>& publish_ids) { + if (!publish_ids.empty()) + publisher->UnpublishArchives(publish_ids); } void OfflinePageModelTaskified::ScheduleMaintenanceTasks() { @@ -662,10 +663,8 @@ void OfflinePageModelTaskified::OnPersistentPageConsistencyCheckDone( bool success, - const std::vector<int64_t>& pages_deleted) { - // TODO(https://crbug.com/834909): Use the temporary hidden bit in - // DownloadUIAdapter instead of removing directly. - Unpublish(archive_publisher_.get(), pages_deleted); + const std::vector<PublishedArchiveId>& ids_of_deleted_pages) { + Unpublish(archive_publisher_.get(), ids_of_deleted_pages); } void OfflinePageModelTaskified::OnClearCachedPagesDone(
diff --git a/components/offline_pages/core/model/offline_page_model_taskified.h b/components/offline_pages/core/model/offline_page_model_taskified.h index f481149..74ee8b4 100644 --- a/components/offline_pages/core/model/offline_page_model_taskified.h +++ b/components/offline_pages/core/model/offline_page_model_taskified.h
@@ -170,7 +170,7 @@ ClearStorageTask::ClearStorageResult result); void OnPersistentPageConsistencyCheckDone( bool success, - const std::vector<int64_t>& pages_deleted); + const std::vector<PublishedArchiveId>& ids_of_deleted_pages); // Callback for when PublishArchive has completd. void PublishArchiveDone(SavePageCallback save_page_callback, @@ -185,7 +185,7 @@ // Method for unpublishing the page from downloads. static void Unpublish(OfflinePageArchivePublisher* publisher, - const std::vector<int64_t>& system_download_ids); + const std::vector<PublishedArchiveId>& publish_ids); // Other utility methods. void RemovePagesMatchingUrlAndNamespace(const OfflinePageItem& page);
diff --git a/components/offline_pages/core/model/offline_page_model_taskified_unittest.cc b/components/offline_pages/core/model/offline_page_model_taskified_unittest.cc index d57291a..e0b5dc8 100644 --- a/components/offline_pages/core/model/offline_page_model_taskified_unittest.cc +++ b/components/offline_pages/core/model/offline_page_model_taskified_unittest.cc
@@ -882,7 +882,8 @@ EXPECT_EQ(last_deleted_page().offline_id, page1.offline_id); EXPECT_EQ(1UL, test_utils::GetFileCountInDirectory(temporary_dir_path())); EXPECT_EQ(1LL, store_test_util()->GetPageCount()); - EXPECT_EQ(page1.system_download_id, publisher()->last_removed_id()); + EXPECT_EQ(page1.system_download_id, + publisher()->last_removed_id().download_id); histogram_tester()->ExpectUniqueSample( "OfflinePages.DeletePageCount", static_cast<int>( @@ -1493,7 +1494,8 @@ EXPECT_EQ(0UL, test_utils::GetFileCountInDirectory(public_archive_dir_path())); EXPECT_EQ(1LL, store_test_util()->GetPageCount()); - EXPECT_EQ(page.system_download_id, publisher()->last_removed_id()); + EXPECT_EQ(page.system_download_id, + publisher()->last_removed_id().download_id); histogram_tester()->ExpectTotalCount( "OfflinePages.ConsistencyCheck.Persistent.Result", 3); }
diff --git a/components/offline_pages/core/model/offline_page_test_utils.cc b/components/offline_pages/core/model/offline_page_test_utils.cc index 9d1431f..47a2070 100644 --- a/components/offline_pages/core/model/offline_page_test_utils.cc +++ b/components/offline_pages/core/model/offline_page_test_utils.cc
@@ -10,6 +10,7 @@ #include "base/strings/string_number_conversions.h" #include "base/strings/utf_string_conversions.h" #include "base/values.h" +#include "components/offline_pages/core/offline_page_archive_publisher.h" #include "components/offline_pages/core/offline_page_item.h" #include "components/offline_pages/core/offline_page_visuals.h" #include "components/offline_pages/core/offline_store_utils.h" @@ -69,7 +70,7 @@ if (!item.request_origin.empty()) { value.SetKey("request_origin", Value(item.request_origin)); } - if (item.system_download_id != 0) { + if (item.system_download_id != kArchiveNotPublished) { value.SetKey("system_download_id", Value(std::to_string(item.system_download_id))); }
diff --git a/components/offline_pages/core/model/persistent_page_consistency_check_task.cc b/components/offline_pages/core/model/persistent_page_consistency_check_task.cc index 6d5484fc..c2b9d44 100644 --- a/components/offline_pages/core/model/persistent_page_consistency_check_task.cc +++ b/components/offline_pages/core/model/persistent_page_consistency_check_task.cc
@@ -9,6 +9,7 @@ #include <vector> #include "base/bind.h" +#include "base/files/file_path.h" #include "base/files/file_util.h" #include "base/metrics/histogram_macros.h" #include "base/numerics/safe_conversions.h" @@ -80,12 +81,12 @@ const ClientPolicyController* policy_controller, base::Time check_time, sql::Database* db) { - std::vector<int64_t> download_ids_of_deleted_pages; + std::vector<PublishedArchiveId> publish_ids_of_deleted_pages; sql::Transaction transaction(db); if (!transaction.Begin()) return {SyncOperationResult::TRANSACTION_BEGIN_ERROR, - download_ids_of_deleted_pages}; + publish_ids_of_deleted_pages}; std::vector<OfflinePageItem> persistent_page_infos = GetPersistentPages(policy_controller, db); @@ -103,7 +104,9 @@ } else { if (check_time - item.file_missing_time > kExpireThreshold) { page_ids_to_delete.push_back(item.offline_id); - download_ids_of_deleted_pages.push_back(item.system_download_id); + + publish_ids_of_deleted_pages.emplace_back(item.system_download_id, + item.file_path); } } } @@ -113,7 +116,7 @@ !MarkPagesAsMissing(pages_found_missing, check_time, db) || !MarkPagesAsReappeared(pages_reappeared, db)) { return {SyncOperationResult::DB_OPERATION_ERROR, - download_ids_of_deleted_pages}; + publish_ids_of_deleted_pages}; } if (page_ids_to_delete.size() > 0) { @@ -134,9 +137,9 @@ if (!transaction.Commit()) return {SyncOperationResult::TRANSACTION_COMMIT_ERROR, - download_ids_of_deleted_pages}; + publish_ids_of_deleted_pages}; - return {SyncOperationResult::SUCCESS, download_ids_of_deleted_pages}; + return {SyncOperationResult::SUCCESS, publish_ids_of_deleted_pages}; } } // namespace @@ -145,8 +148,8 @@ PersistentPageConsistencyCheckTask::CheckResult::CheckResult( SyncOperationResult result, - const std::vector<int64_t>& system_download_ids) - : result(result), download_ids_of_deleted_pages(system_download_ids) {} + const std::vector<PublishedArchiveId>& ids_of_deleted_pages) + : result(result), ids_of_deleted_pages(ids_of_deleted_pages) {} PersistentPageConsistencyCheckTask::CheckResult::CheckResult( const CheckResult& other) = default; @@ -196,7 +199,7 @@ if (check_result.result != SyncOperationResult::SUCCESS) { std::move(callback_).Run(false, {}); } else { - std::move(callback_).Run(true, check_result.download_ids_of_deleted_pages); + std::move(callback_).Run(true, check_result.ids_of_deleted_pages); } TaskComplete(); }
diff --git a/components/offline_pages/core/model/persistent_page_consistency_check_task.h b/components/offline_pages/core/model/persistent_page_consistency_check_task.h index 8209281..9e3a006 100644 --- a/components/offline_pages/core/model/persistent_page_consistency_check_task.h +++ b/components/offline_pages/core/model/persistent_page_consistency_check_task.h
@@ -9,6 +9,7 @@ #include "base/macros.h" #include "base/memory/weak_ptr.h" +#include "components/offline_pages/core/offline_page_archive_publisher.h" #include "components/offline_pages/core/offline_store_types.h" #include "components/offline_pages/task/task.h" @@ -23,20 +24,20 @@ // missing entries back to normal. class PersistentPageConsistencyCheckTask : public Task { public: - using PersistentPageConsistencyCheckCallback = - base::OnceCallback<void(bool success, - const std::vector<int64_t>& pages_deleted)>; + using PersistentPageConsistencyCheckCallback = base::OnceCallback<void( + bool success, + const std::vector<PublishedArchiveId>& ids_of_deleted_pages)>; struct CheckResult { CheckResult(); CheckResult(SyncOperationResult result, - const std::vector<int64_t>& system_download_ids); + const std::vector<PublishedArchiveId>& ids_of_deleted_pages); CheckResult(const CheckResult& other); CheckResult& operator=(const CheckResult& other); ~CheckResult(); SyncOperationResult result; - std::vector<int64_t> download_ids_of_deleted_pages; + std::vector<PublishedArchiveId> ids_of_deleted_pages; }; PersistentPageConsistencyCheckTask(
diff --git a/components/offline_pages/core/model/persistent_page_consistency_check_task_unittest.cc b/components/offline_pages/core/model/persistent_page_consistency_check_task_unittest.cc index 74c996c5..d52c5540 100644 --- a/components/offline_pages/core/model/persistent_page_consistency_check_task_unittest.cc +++ b/components/offline_pages/core/model/persistent_page_consistency_check_task_unittest.cc
@@ -15,10 +15,12 @@ #include "components/offline_pages/core/client_namespace_constants.h" #include "components/offline_pages/core/model/model_task_test_base.h" #include "components/offline_pages/core/model/offline_page_test_utils.h" +#include "components/offline_pages/core/offline_page_archive_publisher.h" #include "testing/gtest/include/gtest/gtest.h" using testing::A; using testing::Eq; +using testing::IsEmpty; using testing::UnorderedElementsAre; namespace offline_pages { @@ -82,14 +84,16 @@ EXPECT_EQ(1UL, test_utils::GetFileCountInDirectory(PublicDir())); base::MockCallback<PersistentPageConsistencyCheckCallback> callback; - EXPECT_CALL(callback, - Run(Eq(true), UnorderedElementsAre(page2.system_download_id, - page5.system_download_id))); + EXPECT_CALL( + callback, + Run(Eq(true), + UnorderedElementsAre( + PublishedArchiveId{page2.system_download_id, page2.file_path}, + PublishedArchiveId{page5.system_download_id, page5.file_path}))); - auto task = std::make_unique<PersistentPageConsistencyCheckTask>( + RunTask(std::make_unique<PersistentPageConsistencyCheckTask>( store(), archive_manager(), policy_controller(), base::Time::Now(), - callback.Get()); - RunTask(std::move(task)); + callback.Get())); EXPECT_EQ(4LL, store_test_util()->GetPageCount()); EXPECT_EQ(1UL, test_utils::GetFileCountInDirectory(PrivateDir())); @@ -116,4 +120,41 @@ static_cast<int>(SyncOperationResult::SUCCESS), 1); } +#if defined(OS_WIN) +#define MAYBE_ClearExpiredPersistentPagesByFilePath \ + DISABLED_ClearExpiredPersistentPagesByFilePath +#else +#define MAYBE_ClearExpiredPersistentPagesByFilePath \ + ClearExpiredPersistentPagesByFilePath +#endif +TEST_F(PersistentPageConsistencyCheckTaskTest, + MAYBE_ClearExpiredPersistentPagesByFilePath) { + base::Time expire_time = base::Time::Now() - base::TimeDelta::FromDays(400); + // |page| will be deleted from DB, since it's been expired for longer than + // threshold. + generator()->SetSystemDownloadId(kArchivePublishedWithoutDownloadId); + generator()->SetNamespace(kDownloadNamespace); + generator()->SetArchiveDirectory(PublicDir()); + generator()->SetFileMissingTime(expire_time); + OfflinePageItem page = AddPageWithoutFile(); + + EXPECT_EQ(1LL, store_test_util()->GetPageCount()); + + base::MockCallback<PersistentPageConsistencyCheckCallback> callback; + EXPECT_CALL(callback, + Run(Eq(true), UnorderedElementsAre(PublishedArchiveId{ + page.system_download_id, page.file_path}))); + + RunTask(std::make_unique<PersistentPageConsistencyCheckTask>( + store(), archive_manager(), policy_controller(), base::Time::Now(), + callback.Get())); + + EXPECT_FALSE(store_test_util()->GetPageByOfflineId(page.offline_id)); + histogram_tester()->ExpectUniqueSample( + "OfflinePages.ConsistencyCheck.Persistent.ExpiredEntryCount", 1, 1); + histogram_tester()->ExpectUniqueSample( + "OfflinePages.ConsistencyCheck.Persistent.Result", + static_cast<int>(SyncOperationResult::SUCCESS), 1); +} + } // namespace offline_pages
diff --git a/components/offline_pages/core/model/update_file_path_task.cc b/components/offline_pages/core/model/update_file_path_task.cc deleted file mode 100644 index 90b8c00..0000000 --- a/components/offline_pages/core/model/update_file_path_task.cc +++ /dev/null
@@ -1,75 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "components/offline_pages/core/model/update_file_path_task.h" - -#include "base/bind.h" -#include "components/offline_pages/core/client_namespace_constants.h" -#include "components/offline_pages/core/model/offline_page_model_utils.h" -#include "components/offline_pages/core/offline_page_metadata_store.h" -#include "components/offline_pages/core/offline_store_utils.h" -#include "sql/database.h" -#include "sql/statement.h" -#include "sql/transaction.h" - -namespace offline_pages { - -namespace { - -bool UpdateFilePathSync(const base::FilePath& new_file_path, - int64_t offline_id, - sql::Database* db) { - sql::Transaction transaction(db); - if (!transaction.Begin()) - return false; - - // Update the file_path to point to the new path. - static const char kSqlUpdate[] = - "UPDATE OR IGNORE offlinepages_v1" - " SET file_path = ?" - " WHERE offline_id = ?"; - sql::Statement update_statement( - db->GetCachedStatement(SQL_FROM_HERE, kSqlUpdate)); - update_statement.BindString( - 0, offline_pages::store_utils::ToDatabaseFilePath(new_file_path)); - update_statement.BindInt64(1, offline_id); - - if (!update_statement.Run()) - return false; - - if (!transaction.Commit()) - return false; - - return true; -} - -} // namespace - -UpdateFilePathTask::UpdateFilePathTask(OfflinePageMetadataStore* store, - int64_t offline_id, - const base::FilePath& file_path, - UpdateFilePathDoneCallback callback) - : store_(store), - offline_id_(offline_id), - file_path_(file_path), - callback_(std::move(callback)) { - DCHECK(store_); -} - -UpdateFilePathTask::~UpdateFilePathTask() {} - -void UpdateFilePathTask::Run() { - store_->Execute(base::BindOnce(&UpdateFilePathSync, file_path_, offline_id_), - base::BindOnce(&UpdateFilePathTask::OnUpdateFilePathDone, - weak_ptr_factory_.GetWeakPtr()), - false); -} - -void UpdateFilePathTask::OnUpdateFilePathDone(bool result) { - // Forward the updated offline page to the callback - std::move(callback_).Run(result); - TaskComplete(); -} - -} // namespace offline_pages
diff --git a/components/offline_pages/core/model/update_file_path_task.h b/components/offline_pages/core/model/update_file_path_task.h deleted file mode 100644 index 55238aa3..0000000 --- a/components/offline_pages/core/model/update_file_path_task.h +++ /dev/null
@@ -1,50 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef COMPONENTS_OFFLINE_PAGES_CORE_MODEL_UPDATE_FILE_PATH_TASK_H_ -#define COMPONENTS_OFFLINE_PAGES_CORE_MODEL_UPDATE_FILE_PATH_TASK_H_ - -#include "base/files/file_path.h" -#include "base/macros.h" -#include "base/memory/weak_ptr.h" -#include "components/offline_pages/core/model/get_pages_task.h" -#include "components/offline_pages/core/offline_page_model.h" -#include "components/offline_pages/task/task.h" - -namespace offline_pages { - -using ReadResult = GetPagesTask::ReadResult; - -class OfflinePageMetadataStore; - -// Task that updates the file path in the metadata store. It takes the offline -// ID of the page accessed, the new file path, and the completion callback. -class UpdateFilePathTask : public Task { - public: - UpdateFilePathTask(OfflinePageMetadataStore* store, - int64_t offline_id, - const base::FilePath& file_path, - UpdateFilePathDoneCallback callback); - ~UpdateFilePathTask() override; - - // Task implementation. - void Run() override; - - private: - void OnUpdateFilePathDone(bool result); - - // The metadata store used to update the page. Not owned. - OfflinePageMetadataStore* store_; - - int64_t offline_id_; - base::FilePath file_path_; - UpdateFilePathDoneCallback callback_; - - base::WeakPtrFactory<UpdateFilePathTask> weak_ptr_factory_{this}; - DISALLOW_COPY_AND_ASSIGN(UpdateFilePathTask); -}; - -} // namespace offline_pages - -#endif // COMPONENTS_OFFLINE_PAGES_CORE_MODEL_UPDATE_FILE_PATH_TASK_H_
diff --git a/components/offline_pages/core/model/update_file_path_task_unittest.cc b/components/offline_pages/core/model/update_file_path_task_unittest.cc deleted file mode 100644 index 9ab3267..0000000 --- a/components/offline_pages/core/model/update_file_path_task_unittest.cc +++ /dev/null
@@ -1,66 +0,0 @@ -// Copyright 2018 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "components/offline_pages/core/model/update_file_path_task.h" - -#include <memory> - -#include "base/bind.h" -#include "base/files/file_path.h" -#include "components/offline_pages/core/model/model_task_test_base.h" -#include "components/offline_pages/core/model/offline_page_item_generator.h" -#include "testing/gtest/include/gtest/gtest.h" - -namespace offline_pages { - -namespace { - -// Callback to check results of task. -class UpdateFilePathTaskTestCallback { - public: - UpdateFilePathTaskTestCallback() : called_(false), success_(false) {} - - bool called() const { return called_; } - - bool success() const { return success_; } - - void Run(bool success) { - called_ = true; - success_ = success; - } - - base::WeakPtr<UpdateFilePathTaskTestCallback> GetWeakPtr() { - return weak_ptr_factory_.GetWeakPtr(); - } - - private: - bool called_; - bool success_; - base::WeakPtrFactory<UpdateFilePathTaskTestCallback> weak_ptr_factory_{this}; -}; -} // namespace - -class UpdateFilePathTaskTest : public ModelTaskTestBase {}; - -TEST_F(UpdateFilePathTaskTest, UpdateFilePath) { - OfflinePageItem page = generator()->CreateItem(); - store_test_util()->InsertItem(page); - base::FilePath new_file_path(FILE_PATH_LITERAL("/new/path/to/file")); - UpdateFilePathTaskTestCallback done_callback; - - // Build and run a task to change the file path in the offline page model. - auto task = std::make_unique<UpdateFilePathTask>( - store(), page.offline_id, new_file_path, - base::BindOnce(&UpdateFilePathTaskTestCallback::Run, - done_callback.GetWeakPtr())); - RunTask(std::move(task)); - - auto offline_page = store_test_util()->GetPageByOfflineId(page.offline_id); - - EXPECT_EQ(new_file_path, offline_page->file_path); - EXPECT_TRUE(done_callback.called()); - EXPECT_TRUE(done_callback.success()); -} - -} // namespace offline_pages
diff --git a/components/offline_pages/core/model/update_publish_id_task.cc b/components/offline_pages/core/model/update_publish_id_task.cc new file mode 100644 index 0000000..771c7163 --- /dev/null +++ b/components/offline_pages/core/model/update_publish_id_task.cc
@@ -0,0 +1,78 @@ +// Copyright 2018 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/offline_pages/core/model/update_publish_id_task.h" + +#include "base/bind.h" +#include "components/offline_pages/core/client_namespace_constants.h" +#include "components/offline_pages/core/model/offline_page_model_utils.h" +#include "components/offline_pages/core/offline_page_metadata_store.h" +#include "components/offline_pages/core/offline_store_utils.h" +#include "sql/database.h" +#include "sql/statement.h" +#include "sql/transaction.h" + +namespace offline_pages { + +namespace { + +bool UpdatePublishIdSync(const PublishedArchiveId& publish_id, + int64_t offline_id, + sql::Database* db) { + sql::Transaction transaction(db); + if (!transaction.Begin()) + return false; + + // Update the file_path to point to the new path. + static const char kSqlUpdate[] = + "UPDATE OR IGNORE offlinepages_v1" + " SET file_path=?,system_download_id=?" + " WHERE offline_id=?"; + sql::Statement update_statement( + db->GetCachedStatement(SQL_FROM_HERE, kSqlUpdate)); + update_statement.BindString(0, offline_pages::store_utils::ToDatabaseFilePath( + publish_id.new_file_path)); + update_statement.BindInt64(1, publish_id.download_id); + update_statement.BindInt64(2, offline_id); + + if (!update_statement.Run()) + return false; + + if (!transaction.Commit()) + return false; + + return true; +} + +} // namespace + +UpdatePublishIdTask::UpdatePublishIdTask( + OfflinePageMetadataStore* store, + int64_t offline_id, + const PublishedArchiveId& publish_id, + base::OnceCallback<void(bool)> callback) + : store_(store), + offline_id_(offline_id), + publish_id_(publish_id), + callback_(std::move(callback)) { + DCHECK(store_); +} + +UpdatePublishIdTask::~UpdatePublishIdTask() {} + +void UpdatePublishIdTask::Run() { + store_->Execute( + base::BindOnce(&UpdatePublishIdSync, publish_id_, offline_id_), + base::BindOnce(&UpdatePublishIdTask::OnUpdatePublishIdDone, + weak_ptr_factory_.GetWeakPtr()), + false); +} + +void UpdatePublishIdTask::OnUpdatePublishIdDone(bool result) { + // Forward the updated offline page to the callback + std::move(callback_).Run(result); + TaskComplete(); +} + +} // namespace offline_pages
diff --git a/components/offline_pages/core/model/update_publish_id_task.h b/components/offline_pages/core/model/update_publish_id_task.h new file mode 100644 index 0000000..338735bf --- /dev/null +++ b/components/offline_pages/core/model/update_publish_id_task.h
@@ -0,0 +1,53 @@ +// Copyright 2018 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef COMPONENTS_OFFLINE_PAGES_CORE_MODEL_UPDATE_PUBLISH_ID_TASK_H_ +#define COMPONENTS_OFFLINE_PAGES_CORE_MODEL_UPDATE_PUBLISH_ID_TASK_H_ + +#include "base/callback.h" +#include "base/files/file_path.h" +#include "base/macros.h" +#include "base/memory/weak_ptr.h" +#include "components/offline_pages/core/model/get_pages_task.h" +#include "components/offline_pages/core/offline_page_archive_publisher.h" +#include "components/offline_pages/core/offline_page_model.h" +#include "components/offline_pages/core/offline_page_types.h" +#include "components/offline_pages/task/task.h" + +namespace offline_pages { + +using ReadResult = GetPagesTask::ReadResult; + +class OfflinePageMetadataStore; + +// Task that updates the file path in the metadata store. It takes the offline +// ID of the page accessed, the new file path, and the completion callback. +class UpdatePublishIdTask : public Task { + public: + UpdatePublishIdTask(OfflinePageMetadataStore* store, + int64_t offline_id, + const PublishedArchiveId& publish_id, + base::OnceCallback<void(bool)> callback); + ~UpdatePublishIdTask() override; + + // Task implementation. + void Run() override; + + private: + void OnUpdatePublishIdDone(bool result); + + // The metadata store used to update the page. Not owned. + OfflinePageMetadataStore* store_; + + int64_t offline_id_; + PublishedArchiveId publish_id_; + base::OnceCallback<void(bool)> callback_; + + base::WeakPtrFactory<UpdatePublishIdTask> weak_ptr_factory_{this}; + DISALLOW_COPY_AND_ASSIGN(UpdatePublishIdTask); +}; + +} // namespace offline_pages + +#endif // COMPONENTS_OFFLINE_PAGES_CORE_MODEL_UPDATE_PUBLISH_ID_TASK_H_
diff --git a/components/offline_pages/core/model/update_publish_id_task_unittest.cc b/components/offline_pages/core/model/update_publish_id_task_unittest.cc new file mode 100644 index 0000000..ecaac3c --- /dev/null +++ b/components/offline_pages/core/model/update_publish_id_task_unittest.cc
@@ -0,0 +1,43 @@ +// Copyright 2018 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/offline_pages/core/model/update_publish_id_task.h" + +#include <memory> + +#include "base/bind.h" +#include "base/files/file_path.h" +#include "base/test/mock_callback.h" +#include "components/offline_pages/core/model/model_task_test_base.h" +#include "components/offline_pages/core/model/offline_page_item_generator.h" +#include "testing/gtest/include/gtest/gtest.h" + +namespace offline_pages { + +class UpdatePublishIdTaskTest : public ModelTaskTestBase {}; + +TEST_F(UpdatePublishIdTaskTest, UpdatePublishId) { + OfflinePageItem page = generator()->CreateItem(); + store_test_util()->InsertItem(page); + base::FilePath new_file_path(FILE_PATH_LITERAL("/new/path/to/file")); + int64_t new_system_download_id = 42LL; + + base::MockCallback<base::OnceCallback<void(bool)>> callback; + + EXPECT_CALL(callback, Run(true)); + + // Build and run a task to change the file path in the offline page model. + auto task = std::make_unique<UpdatePublishIdTask>( + store(), page.offline_id, + PublishedArchiveId(new_system_download_id, new_file_path), + callback.Get()); + RunTask(std::move(task)); + + auto offline_page = store_test_util()->GetPageByOfflineId(page.offline_id); + + EXPECT_EQ(new_file_path, offline_page->file_path); + EXPECT_EQ(new_system_download_id, offline_page->system_download_id); +} + +} // namespace offline_pages
diff --git a/components/offline_pages/core/offline_page_archive_publisher.h b/components/offline_pages/core/offline_page_archive_publisher.h index 364f2aa..5d90657 100644 --- a/components/offline_pages/core/offline_page_archive_publisher.h +++ b/components/offline_pages/core/offline_page_archive_publisher.h
@@ -19,11 +19,38 @@ namespace offline_pages { +// These constants are used to set offline_page_item.download_id when no +// download ID is available. +const int64_t kArchiveNotPublished = 0LL; +const int64_t kArchivePublishedWithoutDownloadId = -1LL; + +// Identifies one published archive. Before Android Q, a published archive is +// assigned a download ID; on Q and later, a published archive is assigned a +// content URI. +struct PublishedArchiveId { + PublishedArchiveId() = default; + PublishedArchiveId(int64_t download_id, const base::FilePath& new_file_path) + : download_id(download_id), new_file_path(new_file_path) {} + bool operator==(const PublishedArchiveId& other) const { + return download_id == other.download_id && + new_file_path == other.new_file_path; + } + + // Identifier returned by Android DownloadManager when present, or + // kArchivePublishedWithoutDownloadManager otherwise. Set to + // kArchiveNotPublished if publishing failed. + int64_t download_id = kArchiveNotPublished; + + // The published archive's path or content URI; empty if publishing failed. + base::FilePath new_file_path; +}; + // The result of publishing an offline page to Downloads. struct PublishArchiveResult { SavePageResult move_result; - base::FilePath new_file_path; - int64_t download_id; + PublishedArchiveId id; + + static PublishArchiveResult Failure(SavePageResult save_page_result); }; // Interface of a class responsible for publishing offline page archives to @@ -43,9 +70,9 @@ const scoped_refptr<base::SequencedTaskRunner>& background_task_runner, PublishArchiveDoneCallback publish_done_callback) const = 0; - // Removes the archives identified by |download_manager_ids| from downloads. + // Removes archives from downloads. virtual void UnpublishArchives( - const std::vector<int64_t>& download_manager_ids) const = 0; + const std::vector<PublishedArchiveId>& archive_ids) const = 0; }; } // namespace offline_pages
diff --git a/components/offline_pages/core/offline_page_test_archive_publisher.cc b/components/offline_pages/core/offline_page_test_archive_publisher.cc index 895b264..d1f774f 100644 --- a/components/offline_pages/core/offline_page_test_archive_publisher.cc +++ b/components/offline_pages/core/offline_page_test_archive_publisher.cc
@@ -25,7 +25,6 @@ archive_attempt_failure_(false), use_verbatim_archive_path_(false), download_id_(download_id_to_use), - last_removed_id_(0LL), archive_manager_(archive_manager) {} OfflinePageTestArchivePublisher::~OfflinePageTestArchivePublisher() { @@ -42,7 +41,6 @@ if (archive_attempt_failure_) { publish_archive_result.move_result = SavePageResult::FILE_MOVE_FAILED; - publish_archive_result.download_id = 0LL; } else { publish_archive_result.move_result = SavePageResult::SUCCESS; @@ -51,13 +49,13 @@ // published archive path is built using publish_directory. The tests should // be fixed and this special case should be removed. if (use_verbatim_archive_path_) { - publish_archive_result.new_file_path = offline_page.file_path; + publish_archive_result.id.new_file_path = offline_page.file_path; } else { - publish_archive_result.new_file_path = + publish_archive_result.id.new_file_path = archive_manager_->GetPublicArchivesDir().Append( offline_page.file_path.BaseName()); } - publish_archive_result.download_id = download_id_; + publish_archive_result.id.download_id = download_id_; } background_task_runner->PostTask( @@ -66,9 +64,9 @@ } void OfflinePageTestArchivePublisher::UnpublishArchives( - const std::vector<int64_t>& download_manager_ids) const { - if (!download_manager_ids.empty()) - last_removed_id_ = download_manager_ids.back(); + const std::vector<PublishedArchiveId>& archive_ids) const { + if (!archive_ids.empty()) + last_removed_id_ = archive_ids.back(); } } // namespace offline_pages
diff --git a/components/offline_pages/core/offline_page_test_archive_publisher.h b/components/offline_pages/core/offline_page_test_archive_publisher.h index a570038..d18cd40 100644 --- a/components/offline_pages/core/offline_page_test_archive_publisher.h +++ b/components/offline_pages/core/offline_page_test_archive_publisher.h
@@ -35,7 +35,7 @@ PublishArchiveDoneCallback publish_done_callback) const override; void UnpublishArchives( - const std::vector<int64_t>& download_manager_ids) const override; + const std::vector<PublishedArchiveId>& archive_ids) const override; void set_archive_attempt_failure(bool fail) { archive_attempt_failure_ = fail; @@ -47,7 +47,7 @@ void use_verbatim_archive_path(bool use) { use_verbatim_archive_path_ = use; } - int64_t last_removed_id() const { return last_removed_id_; } + PublishedArchiveId last_removed_id() const { return last_removed_id_; } private: bool expect_publish_archive_called_; @@ -55,7 +55,7 @@ bool archive_attempt_failure_; bool use_verbatim_archive_path_; int64_t download_id_; - mutable int64_t last_removed_id_; + mutable PublishedArchiveId last_removed_id_; ArchiveManager* archive_manager_; };
diff --git a/components/offline_pages/core/offline_page_types.h b/components/offline_pages/core/offline_page_types.h index 72f8d96..777dbb3f 100644 --- a/components/offline_pages/core/offline_page_types.h +++ b/components/offline_pages/core/offline_page_types.h
@@ -110,7 +110,6 @@ // Callbacks used for publishing an offline page. using PublishPageCallback = base::OnceCallback<void(const base::FilePath&, SavePageResult)>; -using UpdateFilePathDoneCallback = base::OnceCallback<void(bool)>; } // namespace offline_pages
diff --git a/components/omnibox/common/omnibox_features.cc b/components/omnibox/common/omnibox_features.cc index 8dda09e9d..882e47eb 100644 --- a/components/omnibox/common/omnibox_features.cc +++ b/components/omnibox/common/omnibox_features.cc
@@ -149,7 +149,7 @@ // other search suggestions provided by the default search provider. This // feature is a narrow subset of kOmniboxSuggestionTransparencyOptions. const base::Feature kOmniboxUICuesForSearchHistoryMatches{ - "OmniboxUICuesForSearchHistoryMatches", base::FEATURE_DISABLED_BY_DEFAULT}; + "OmniboxUICuesForSearchHistoryMatches", base::FEATURE_ENABLED_BY_DEFAULT}; // Feature that shows an alternate separator before the description of // omnibox matches. In English, this changes the separator from '-' to '|'. @@ -240,7 +240,7 @@ // are exceptions in this regard and this experiment makes this more consistent. const base::Feature kUIExperimentShowPlaceholderWhenCaretShowing{ "OmniboxUIExperimentShowPlaceholderWhenCaretShowing", - base::FEATURE_DISABLED_BY_DEFAULT}; + base::FEATURE_ENABLED_BY_DEFAULT}; // Feature used to enable speculatively starting a service worker associated // with the destination of the default match when the user's input looks like a
diff --git a/components/password_manager/content/browser/content_password_manager_driver.cc b/components/password_manager/content/browser/content_password_manager_driver.cc index 8dc21a0e..8ffccfe 100644 --- a/components/password_manager/content/browser/content_password_manager_driver.cc +++ b/components/password_manager/content/browser/content_password_manager_driver.cc
@@ -179,7 +179,7 @@ return is_main_frame_; } -GURL ContentPasswordManagerDriver::GetLastCommittedURL() const { +const GURL& ContentPasswordManagerDriver::GetLastCommittedURL() const { return render_frame_host_->GetLastCommittedURL(); }
diff --git a/components/password_manager/content/browser/content_password_manager_driver.h b/components/password_manager/content/browser/content_password_manager_driver.h index 2e1c5116..f4b5cb5 100644 --- a/components/password_manager/content/browser/content_password_manager_driver.h +++ b/components/password_manager/content/browser/content_password_manager_driver.h
@@ -77,7 +77,7 @@ void SendLoggingAvailability() override; autofill::AutofillDriver* GetAutofillDriver() override; bool IsMainFrame() const override; - GURL GetLastCommittedURL() const override; + const GURL& GetLastCommittedURL() const override; void DidNavigateFrame(content::NavigationHandle* navigation_handle); // Notify the renderer that the user wants to generate password manually.
diff --git a/components/password_manager/core/browser/http_auth_manager.h b/components/password_manager/core/browser/http_auth_manager.h index 585cd07..ab886a9a 100644 --- a/components/password_manager/core/browser/http_auth_manager.h +++ b/components/password_manager/core/browser/http_auth_manager.h
@@ -36,6 +36,9 @@ // Called by the LoginHandler instance. virtual void OnPasswordFormSubmitted( const autofill::PasswordForm& password_form) = 0; + + // Called by the LoginHandler instance when the password form is dismissed. + virtual void OnPasswordFormDismissed() = 0; }; } // namespace password_manager
diff --git a/components/password_manager/core/browser/http_auth_manager_impl.cc b/components/password_manager/core/browser/http_auth_manager_impl.cc index 1de5d5fb..13e66d38 100644 --- a/components/password_manager/core/browser/http_auth_manager_impl.cc +++ b/components/password_manager/core/browser/http_auth_manager_impl.cc
@@ -88,7 +88,27 @@ ProvisionallySaveForm(password_form); } +void HttpAuthManagerImpl::OnPasswordFormDismissed() { + form_dismissed_ = true; +} + void HttpAuthManagerImpl::OnDidFinishMainFrameNavigation() { + // Only pay attention to the navigation if the password form (a native browser + // UI for HTTP auth) has been dismissed. This is necessary because of + // committed interstitials (https://crbug.com/963307), when the server sends + // an empty response body with a 401/407 response. In this case, the renderer + // synthesizes contents for the response and renders it underneath the auth + // prompt, which looks like a second navigation commit from the browser + // process's perspective (https://crbug.com/943610). Clearing |form_manager_| + // on this second commit would be premature and break password saving, so + // defer it until the password form is actually dismissed. If error pages are + // changed to no longer double-commit, we can remove the |form_dismissed_| + // logic. + if (!form_dismissed_) + return; + + form_dismissed_ = false; + // The login was successful if and only if there were no HTTP errors. if (!client_->WasLastNavigationHTTPError()) { OnLoginSuccesfull();
diff --git a/components/password_manager/core/browser/http_auth_manager_impl.h b/components/password_manager/core/browser/http_auth_manager_impl.h index 2ec9a6c..f6fca7c 100644 --- a/components/password_manager/core/browser/http_auth_manager_impl.h +++ b/components/password_manager/core/browser/http_auth_manager_impl.h
@@ -39,6 +39,7 @@ void DetachObserver(HttpAuthObserver* observer) override; void OnPasswordFormSubmitted( const autofill::PasswordForm& password_form) override; + void OnPasswordFormDismissed() override; // Called by a PasswordManagerClient when it decides that a HTTP auth dialog // can be auto-filled. It notifies the observer about new credentials given @@ -69,6 +70,10 @@ // Single password form manager to handle the http-auth request form. std::unique_ptr<NewPasswordFormManager> form_manager_; + + // When set to true, the password form has been dismissed and |form_manager_| + // will be cleared on next navigation. + bool form_dismissed_ = false; }; } // namespace password_manager
diff --git a/components/password_manager/core/browser/http_auth_manager_unittest.cc b/components/password_manager/core/browser/http_auth_manager_unittest.cc index af68ae9..3da807da 100644 --- a/components/password_manager/core/browser/http_auth_manager_unittest.cc +++ b/components/password_manager/core/browser/http_auth_manager_unittest.cc
@@ -185,6 +185,7 @@ submitted_form.username_value = ASCIIToUTF16("user"); submitted_form.password_value = ASCIIToUTF16("1234"); httpauth_manager()->OnPasswordFormSubmitted(submitted_form); + httpauth_manager()->OnPasswordFormDismissed(); // Expect save prompt on successful submission. std::unique_ptr<PasswordFormManagerForUI> form_manager_to_save;
diff --git a/components/password_manager/core/browser/password_manager_driver.h b/components/password_manager/core/browser/password_manager_driver.h index e5fac7b..2b154bf 100644 --- a/components/password_manager/core/browser/password_manager_driver.h +++ b/components/password_manager/core/browser/password_manager_driver.h
@@ -100,7 +100,7 @@ virtual bool IsMainFrame() const = 0; // Returns the last committed URL of the frame. - virtual GURL GetLastCommittedURL() const = 0; + virtual const GURL& GetLastCommittedURL() const = 0; private: DISALLOW_COPY_AND_ASSIGN(PasswordManagerDriver);
diff --git a/components/password_manager/core/browser/stub_password_manager_driver.cc b/components/password_manager/core/browser/stub_password_manager_driver.cc index 93c499a..b1c289b2 100644 --- a/components/password_manager/core/browser/stub_password_manager_driver.cc +++ b/components/password_manager/core/browser/stub_password_manager_driver.cc
@@ -57,8 +57,8 @@ return true; } -GURL StubPasswordManagerDriver::GetLastCommittedURL() const { - return GURL(); +const GURL& StubPasswordManagerDriver::GetLastCommittedURL() const { + return GURL::EmptyGURL(); } } // namespace password_manager
diff --git a/components/password_manager/core/browser/stub_password_manager_driver.h b/components/password_manager/core/browser/stub_password_manager_driver.h index b3e04fb..a2676b2 100644 --- a/components/password_manager/core/browser/stub_password_manager_driver.h +++ b/components/password_manager/core/browser/stub_password_manager_driver.h
@@ -34,7 +34,7 @@ PasswordAutofillManager* GetPasswordAutofillManager() override; autofill::AutofillDriver* GetAutofillDriver() override; bool IsMainFrame() const override; - GURL GetLastCommittedURL() const override; + const GURL& GetLastCommittedURL() const override; private: DISALLOW_COPY_AND_ASSIGN(StubPasswordManagerDriver);
diff --git a/components/policy/core/common/cloud/cloud_policy_validator.cc b/components/policy/core/common/cloud/cloud_policy_validator.cc index 5820cbd..f601b28 100644 --- a/components/policy/core/common/cloud/cloud_policy_validator.cc +++ b/components/policy/core/common/cloud/cloud_policy_validator.cc
@@ -128,18 +128,28 @@ void CloudPolicyValidatorBase::ValidateUser(const AccountId& account_id) { validation_flags_ |= VALIDATE_USER; - account_id_ = account_id; + username_ = account_id.GetUserEmail(); + gaia_id_ = account_id.GetGaiaId(); // Always canonicalize when falls back to username check, // because it checks only for regular users. canonicalize_user_ = true; } -void CloudPolicyValidatorBase::ValidateUsername( +void CloudPolicyValidatorBase::ValidateUsernameAndGaiaId( const std::string& expected_user, - bool canonicalize) { + const std::string& gaia_id) { validation_flags_ |= VALIDATE_USER; - account_id_ = AccountId::FromUserEmail(expected_user); - canonicalize_user_ = canonicalize; + username_ = expected_user; + gaia_id_ = gaia_id; + canonicalize_user_ = false; +} + +void CloudPolicyValidatorBase::ValidateUsername( + const std::string& expected_user) { + validation_flags_ |= VALIDATE_USER; + username_ = expected_user; + gaia_id_.clear(); + canonicalize_user_ = false; } void CloudPolicyValidatorBase::ValidateDomain( @@ -546,9 +556,8 @@ } if (policy_data_->has_gaia_id() && !policy_data_->gaia_id().empty() && - account_id_.GetAccountType() == AccountType::GOOGLE && - !account_id_.GetGaiaId().empty()) { - std::string expected = account_id_.GetGaiaId(); + !gaia_id_.empty()) { + std::string expected = gaia_id_; std::string actual = policy_data_->gaia_id(); if (expected != actual) { @@ -560,7 +569,7 @@ UMA_HISTOGRAM_ENUMERATION(kMetricPolicyUserVerification, MetricPolicyUserVerification::kGaiaIdSucceeded); } else { - std::string expected = account_id_.GetUserEmail(); + std::string expected = username_; std::string actual = policy_data_->username(); if (canonicalize_user_) { expected = gaia::CanonicalizeEmail(gaia::SanitizeEmail(expected)); @@ -573,8 +582,7 @@ MetricPolicyUserVerification::kUsernameFailed); return VALIDATION_BAD_USER; } - if (account_id_.GetAccountType() != AccountType::GOOGLE || - account_id_.GetGaiaId().empty()) { + if (gaia_id_.empty()) { UMA_HISTOGRAM_ENUMERATION( kMetricPolicyUserVerification, MetricPolicyUserVerification::kUsernameSucceeded);
diff --git a/components/policy/core/common/cloud/cloud_policy_validator.h b/components/policy/core/common/cloud/cloud_policy_validator.h index 5c4a231d..49ce06c 100644 --- a/components/policy/core/common/cloud/cloud_policy_validator.h +++ b/components/policy/core/common/cloud/cloud_policy_validator.h
@@ -172,9 +172,15 @@ void ValidateUser(const AccountId& account_id); // Instruct the validator to check that the username in the policy blob - // matches |expected_user|. If |canonicalize| is set to true, both values are - // canonicalized before comparison. - void ValidateUsername(const std::string& expected_user, bool canonicalize); + // matches |expected_user|. + // This is used for DeviceLocalAccounts that doesn't have AccountId. + void ValidateUsername(const std::string& expected_user); + + // Instruct the validator to check that the username in the policy blob + // matches the user credentials. It checks GAIA ID if policy blob has it, + // otherwise falls back to username check. + void ValidateUsernameAndGaiaId(const std::string& expected_user, + const std::string& gaia_id); // Instruct the validator to check that the policy blob is addressed to // |expected_domain|. This uses the domain part of the username field in the @@ -265,6 +271,7 @@ VALIDATE_CACHED_KEY = 1 << 9, VALIDATE_DEVICE_ID = 1 << 10, VALIDATE_VALUES = 1 << 11, + VALIDATE_USERNAME = 1 << 12, }; // Create a new validator that checks |policy_response|. @@ -355,7 +362,8 @@ ValidateTimestampOption timestamp_option_; ValidateDMTokenOption dm_token_option_; ValidateDeviceIdOption device_id_option_; - AccountId account_id_; + std::string username_; + std::string gaia_id_; bool canonicalize_user_; std::string domain_; std::string dm_token_;
diff --git a/components/policy/core/common/cloud/cloud_policy_validator_unittest.cc b/components/policy/core/common/cloud/cloud_policy_validator_unittest.cc index d542e7b4..0f03aba2 100644 --- a/components/policy/core/common/cloud/cloud_policy_validator_unittest.cc +++ b/components/policy/core/common/cloud/cloud_policy_validator_unittest.cc
@@ -105,10 +105,10 @@ std::move(policy_response), base::ThreadTaskRunnerHandle::Get()); validator->ValidateTimestamp(timestamp_, timestamp_option_); if (validate_by_gaia_id_) { - validator->ValidateUser( - AccountId::FromGaiaId(PolicyBuilder::kFakeGaiaId)); + validator->ValidateUsernameAndGaiaId(/*username=*/std::string(), + PolicyBuilder::kFakeGaiaId); } else { - validator->ValidateUsername(PolicyBuilder::kFakeUsername, true); + validator->ValidateUsername(PolicyBuilder::kFakeUsername); } if (!owning_domain_.empty()) validator->ValidateDomain(owning_domain_);
diff --git a/components/policy/core/common/cloud/component_cloud_policy_service.cc b/components/policy/core/common/cloud/component_cloud_policy_service.cc index 6e24e83..ec8b27e2 100644 --- a/components/policy/core/common/cloud/component_cloud_policy_service.cc +++ b/components/policy/core/common/cloud/component_cloud_policy_service.cc
@@ -19,7 +19,6 @@ #include "base/sequenced_task_runner.h" #include "base/single_thread_task_runner.h" #include "base/threading/thread_task_runner_handle.h" -#include "components/account_id/account_id.h" #include "components/policy/core/common/cloud/cloud_policy_constants.h" #include "components/policy/core/common/cloud/cloud_policy_refresh_scheduler.h" #include "components/policy/core/common/cloud/component_cloud_policy_store.h" @@ -85,7 +84,8 @@ void ClearCache(); // The passed credentials will be used to validate the policies. - void SetCredentials(const AccountId& account_id, + void SetCredentials(const std::string& username, + const std::string& gaia_id, const std::string& dm_token, const std::string& device_id, const std::string& public_key, @@ -164,17 +164,18 @@ } void ComponentCloudPolicyService::Backend::SetCredentials( - const AccountId& account_id, + const std::string& username, + const std::string& gaia_id, const std::string& dm_token, const std::string& device_id, const std::string& public_key, int public_key_version) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - DCHECK(account_id.is_valid()); + DCHECK(!username.empty()); DCHECK(!dm_token.empty()); - DVLOG(1) << "Updating credentials: account id = " << account_id + DVLOG(1) << "Updating credentials: username = " << username << ", public_key_version = " << public_key_version; - store_.SetCredentials(account_id, dm_token, device_id, public_key, + store_.SetCredentials(username, gaia_id, dm_token, device_id, public_key, public_key_version); has_credentials_set_ = true; // Trigger an additional update against the last fetched policies. This helps @@ -416,9 +417,6 @@ // session starts. std::string username = policy->username(); std::string gaia_id = policy->gaia_id(); - AccountId account_id = - gaia_id.empty() ? AccountId::FromUserEmail(username) - : AccountId::FromUserEmailGaiaId(username, gaia_id); std::string request_token = policy->request_token(); std::string device_id = policy->has_device_id() ? policy->device_id() : std::string(); @@ -427,8 +425,8 @@ policy->has_public_key_version() ? policy->public_key_version() : -1; backend_task_runner_->PostTask( FROM_HERE, base::BindOnce(&Backend::SetCredentials, - base::Unretained(backend_.get()), account_id, - request_token, device_id, public_key, + base::Unretained(backend_.get()), username, + gaia_id, request_token, device_id, public_key, public_key_version)); }
diff --git a/components/policy/core/common/cloud/component_cloud_policy_store.cc b/components/policy/core/common/cloud/component_cloud_policy_store.cc index 7c77c58..a0292ef 100644 --- a/components/policy/core/common/cloud/component_cloud_policy_store.cc +++ b/components/policy/core/common/cloud/component_cloud_policy_store.cc
@@ -130,16 +130,18 @@ return it == cached_hashes_.end() ? base::EmptyString() : it->second; } -void ComponentCloudPolicyStore::SetCredentials(const AccountId& account_id, +void ComponentCloudPolicyStore::SetCredentials(const std::string& username, + const std::string& gaia_id, const std::string& dm_token, const std::string& device_id, const std::string& public_key, int public_key_version) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - DCHECK(!account_id_.is_valid() || account_id == account_id_); + DCHECK(username_.empty() || username == username_); DCHECK(dm_token_.empty() || dm_token == dm_token_); DCHECK(device_id_.empty() || device_id == device_id_); - account_id_ = account_id; + username_ = username; + gaia_id_ = gaia_id; dm_token_ = dm_token; device_id_ = device_id; public_key_ = public_key; @@ -315,7 +317,7 @@ return false; } - if (!account_id_.is_valid() || dm_token_.empty() || device_id_.empty() || + if (username_.empty() || dm_token_.empty() || device_id_.empty() || public_key_.empty() || public_key_version_ == -1) { LOG(WARNING) << "Credentials are not loaded yet."; return false; @@ -332,7 +334,7 @@ std::move(proto), scoped_refptr<base::SequencedTaskRunner>()); validator->ValidateTimestamp(time_not_before, CloudPolicyValidatorBase::TIMESTAMP_VALIDATED); - validator->ValidateUser(account_id_); + validator->ValidateUsernameAndGaiaId(username_, gaia_id_); validator->ValidateDMToken(dm_token_, ComponentCloudPolicyValidator::DM_TOKEN_REQUIRED); validator->ValidateDeviceId(device_id_,
diff --git a/components/policy/core/common/cloud/component_cloud_policy_store.h b/components/policy/core/common/cloud/component_cloud_policy_store.h index b7404dc0..2ab7fd5 100644 --- a/components/policy/core/common/cloud/component_cloud_policy_store.h +++ b/components/policy/core/common/cloud/component_cloud_policy_store.h
@@ -12,7 +12,6 @@ #include "base/macros.h" #include "base/sequence_checker.h" #include "base/time/time.h" -#include "components/account_id/account_id.h" #include "components/policy/core/common/cloud/resource_cache.h" #include "components/policy/core/common/policy_bundle.h" #include "components/policy/core/common/policy_namespace.h" @@ -88,7 +87,8 @@ // The passed credentials are used to validate the cached data, and data // stored later. // All ValidatePolicy() requests without credentials fail. - void SetCredentials(const AccountId& account_id, + void SetCredentials(const std::string& username, + const std::string& gaia_id, const std::string& dm_token, const std::string& device_id, const std::string& public_key, @@ -151,7 +151,8 @@ ResourceCache* const cache_; // The following fields contain credentials used for validating the policy. - AccountId account_id_; + std::string username_; + std::string gaia_id_; std::string dm_token_; std::string device_id_; std::string public_key_;
diff --git a/components/policy/core/common/cloud/component_cloud_policy_store_unittest.cc b/components/policy/core/common/cloud/component_cloud_policy_store_unittest.cc index b067896..67f12c3f 100644 --- a/components/policy/core/common/cloud/component_cloud_policy_store_unittest.cc +++ b/components/policy/core/common/cloud/component_cloud_policy_store_unittest.cc
@@ -17,7 +17,6 @@ #include "base/optional.h" #include "base/test/test_simple_task_runner.h" #include "base/time/time.h" -#include "components/account_id/account_id.h" #include "components/policy/core/common/cloud/cloud_policy_constants.h" #include "components/policy/core/common/cloud/policy_builder.h" #include "components/policy/core/common/cloud/resource_cache.h" @@ -98,10 +97,10 @@ temp_dir_.GetPath(), base::MakeRefCounted<base::TestSimpleTaskRunner>(), /* max_cache_size */ base::nullopt)); store_ = CreateStore(); - store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, - PolicyBuilder::kFakePublicKeyVersion); + store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakePublicKeyVersion); } void SetupExpectBundleWithScope( @@ -325,7 +324,8 @@ TEST_F(ComponentCloudPolicyStoreTest, ValidateNoCredentialsUser) { store_ = CreateStore(); - store_->SetCredentials(AccountId(), PolicyBuilder::kFakeToken, + store_->SetCredentials(/*username=*/std::string(), /*gaia_id=*/std::string(), + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, PolicyBuilder::kFakePublicKeyVersion); EXPECT_FALSE(store_->ValidatePolicy(kTestPolicyNS, CreateResponse(), @@ -335,10 +335,10 @@ TEST_F(ComponentCloudPolicyStoreTest, ValidateNoCredentialsDMToken) { store_ = CreateStore(); - store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - std::string() /* dm_token */, - PolicyBuilder::kFakeDeviceId, public_key_, - PolicyBuilder::kFakePublicKeyVersion); + store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + std::string() /* dm_token */, PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakePublicKeyVersion); EXPECT_FALSE(store_->ValidatePolicy(kTestPolicyNS, CreateResponse(), nullptr /* policy_data */, nullptr /* payload */)); @@ -346,8 +346,8 @@ TEST_F(ComponentCloudPolicyStoreTest, ValidateNoCredentialsDeviceId) { store_ = CreateStore(); - store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, + store_->SetCredentials(PolicyBuilder::kFakeUsername, + PolicyBuilder::kFakeGaiaId, PolicyBuilder::kFakeToken, std::string() /* device_id */, public_key_, PolicyBuilder::kFakePublicKeyVersion); EXPECT_FALSE(store_->ValidatePolicy(kTestPolicyNS, CreateResponse(), @@ -358,9 +358,9 @@ TEST_F(ComponentCloudPolicyStoreTest, ValidateNoCredentialsPublicKey) { store_ = CreateStore(); store_->SetCredentials( - PolicyBuilder::GetFakeAccountIdForTesting(), PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, std::string() /* public_key */, - PolicyBuilder::kFakePublicKeyVersion); + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, + std::string() /* public_key */, PolicyBuilder::kFakePublicKeyVersion); EXPECT_FALSE(store_->ValidatePolicy(kTestPolicyNS, CreateResponse(), nullptr /* policy_data */, nullptr /* payload */)); @@ -370,8 +370,9 @@ StoreTestPolicy(store_.get()); another_store_ = CreateStore(); another_store_->SetCredentials( - PolicyBuilder::GetFakeAccountIdForTesting(), PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, -1 /* public_key_version */); + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, + -1 /* public_key_version */); another_store_->Load(); EXPECT_TRUE(IsStoreEmpty(*another_store_)); EXPECT_TRUE(LoadCacheExtensionsSubkeys().empty()); @@ -380,9 +381,9 @@ TEST_F(ComponentCloudPolicyStoreTest, ValidateWrongCredentialsDMToken) { StoreTestPolicy(store_.get()); another_store_ = CreateStore(); - another_store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - "wrongtoken", PolicyBuilder::kFakeDeviceId, - public_key_, + another_store_->SetCredentials(PolicyBuilder::kFakeUsername, + PolicyBuilder::kFakeGaiaId, "wrongtoken", + PolicyBuilder::kFakeDeviceId, public_key_, PolicyBuilder::kFakePublicKeyVersion); another_store_->Load(); EXPECT_TRUE(IsStoreEmpty(*another_store_)); @@ -393,8 +394,9 @@ StoreTestPolicy(store_.get()); another_store_ = CreateStore(); another_store_->SetCredentials( - PolicyBuilder::GetFakeAccountIdForTesting(), PolicyBuilder::kFakeToken, - "wrongdeviceid", public_key_, PolicyBuilder::kFakePublicKeyVersion); + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, "wrongdeviceid", public_key_, + PolicyBuilder::kFakePublicKeyVersion); another_store_->Load(); EXPECT_TRUE(IsStoreEmpty(*another_store_)); EXPECT_TRUE(LoadCacheExtensionsSubkeys().empty()); @@ -403,10 +405,10 @@ TEST_F(ComponentCloudPolicyStoreTest, ValidateWrongCredentialsPublicKey) { StoreTestPolicy(store_.get()); another_store_ = CreateStore(); - another_store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, "wrongkey", - PolicyBuilder::kFakePublicKeyVersion); + another_store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, "wrongkey", + PolicyBuilder::kFakePublicKeyVersion); another_store_->Load(); EXPECT_TRUE(IsStoreEmpty(*another_store_)); EXPECT_TRUE(LoadCacheExtensionsSubkeys().empty()); @@ -416,10 +418,10 @@ ValidateWrongCredentialsPublicKeyVersion) { StoreTestPolicy(store_.get()); another_store_ = CreateStore(); - another_store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, - PolicyBuilder::kFakePublicKeyVersion + 1); + another_store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakePublicKeyVersion + 1); another_store_->Load(); EXPECT_TRUE(IsStoreEmpty(*another_store_)); EXPECT_TRUE(LoadCacheExtensionsSubkeys().empty()); @@ -510,10 +512,10 @@ // Loading from the cache validates the policy data again. another_store_ = CreateStore(); - another_store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, - PolicyBuilder::kFakePublicKeyVersion); + another_store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakePublicKeyVersion); another_store_->Load(); EXPECT_TRUE(another_store_->policy().Equals(expected_bundle_)); EXPECT_EQ(TestPolicyHash(), another_store_->GetCachedHash(kTestPolicyNS)); @@ -522,8 +524,8 @@ TEST_F(ComponentCloudPolicyStoreTest, StoreAndLoadMachineLevelUserPolicy) { store_ = CreateStore(dm_protocol::kChromeMachineLevelExtensionCloudPolicyType); - store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, + store_->SetCredentials(PolicyBuilder::kFakeUsername, + PolicyBuilder::kFakeGaiaId, PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, PolicyBuilder::kFakePublicKeyVersion); @@ -536,10 +538,10 @@ another_store_ = CreateStore(dm_protocol::kChromeMachineLevelExtensionCloudPolicyType); - another_store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, - PolicyBuilder::kFakePublicKeyVersion); + another_store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakePublicKeyVersion); another_store_->Load(); EXPECT_TRUE(another_store_->policy().Equals(expected_bundle_)); EXPECT_EQ(TestPolicyHash(), another_store_->GetCachedHash(kTestPolicyNS)); @@ -548,8 +550,8 @@ TEST_F(ComponentCloudPolicyStoreTest, StoreAndLoadPolicyWithCloudPriority) { store_ = CreateStore(dm_protocol::kChromeMachineLevelExtensionCloudPolicyType, POLICY_SOURCE_PRIORITY_CLOUD); - store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, + store_->SetCredentials(PolicyBuilder::kFakeUsername, + PolicyBuilder::kFakeGaiaId, PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, PolicyBuilder::kFakePublicKeyVersion); @@ -564,10 +566,10 @@ another_store_ = CreateStore(dm_protocol::kChromeMachineLevelExtensionCloudPolicyType, POLICY_SOURCE_PRIORITY_CLOUD); - another_store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, - PolicyBuilder::kFakePublicKeyVersion); + another_store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakePublicKeyVersion); another_store_->Load(); EXPECT_TRUE(another_store_->policy().Equals(expected_bundle_)); EXPECT_EQ(TestPolicyHash(), another_store_->GetCachedHash(kTestPolicyNS)); @@ -577,8 +579,8 @@ StoreAndLoadPolicyWithDifferentCloudPriority) { store_ = CreateStore(dm_protocol::kChromeMachineLevelExtensionCloudPolicyType, POLICY_SOURCE_CLOUD); - store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, + store_->SetCredentials(PolicyBuilder::kFakeUsername, + PolicyBuilder::kFakeGaiaId, PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, PolicyBuilder::kFakePublicKeyVersion); @@ -594,10 +596,10 @@ another_store_ = CreateStore(dm_protocol::kChromeMachineLevelExtensionCloudPolicyType, POLICY_SOURCE_PRIORITY_CLOUD); - another_store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, - PolicyBuilder::kFakePublicKeyVersion); + another_store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakePublicKeyVersion); another_store_->Load(); EXPECT_TRUE(another_store_->policy().Equals(expected_bundle_)); EXPECT_EQ(TestPolicyHash(), another_store_->GetCachedHash(kTestPolicyNS)); @@ -649,10 +651,10 @@ another_store_ = CreateStore(); const PolicyBundle empty_bundle; EXPECT_TRUE(another_store_->policy().Equals(empty_bundle)); - another_store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, - PolicyBuilder::kFakePublicKeyVersion); + another_store_->SetCredentials( + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakePublicKeyVersion); another_store_->Load(); EXPECT_TRUE(another_store_->policy().Equals(expected_bundle_)); @@ -667,8 +669,8 @@ // And they aren't loaded anymore either. yet_another_store_ = CreateStore(); yet_another_store_->SetCredentials( - PolicyBuilder::GetFakeAccountIdForTesting(), PolicyBuilder::kFakeToken, - PolicyBuilder::kFakeDeviceId, public_key_, + PolicyBuilder::kFakeUsername, PolicyBuilder::kFakeGaiaId, + PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, PolicyBuilder::kFakePublicKeyVersion); yet_another_store_->Load(); EXPECT_TRUE(yet_another_store_->policy().Equals(empty_bundle));
diff --git a/components/policy/core/common/cloud/component_cloud_policy_updater_unittest.cc b/components/policy/core/common/cloud/component_cloud_policy_updater_unittest.cc index 8b781b4..cc079834 100644 --- a/components/policy/core/common/cloud/component_cloud_policy_updater_unittest.cc +++ b/components/policy/core/common/cloud/component_cloud_policy_updater_unittest.cc
@@ -123,8 +123,8 @@ store_ = std::make_unique<ComponentCloudPolicyStore>( &store_delegate_, cache_.get(), dm_protocol::kChromeExtensionPolicyType, POLICY_SOURCE_CLOUD); - store_->SetCredentials(PolicyBuilder::GetFakeAccountIdForTesting(), - PolicyBuilder::kFakeToken, + store_->SetCredentials(PolicyBuilder::kFakeUsername, + PolicyBuilder::kFakeGaiaId, PolicyBuilder::kFakeToken, PolicyBuilder::kFakeDeviceId, public_key_, PolicyBuilder::kFakePublicKeyVersion); auto url_loader_factory =
diff --git a/components/prefs/pref_member.h b/components/prefs/pref_member.h index 188f04a..f2166e6 100644 --- a/components/prefs/pref_member.h +++ b/components/prefs/pref_member.h
@@ -34,7 +34,6 @@ #include "base/macros.h" #include "base/memory/ref_counted.h" #include "base/sequenced_task_runner.h" -#include "base/single_thread_task_runner.h" #include "base/values.h" #include "components/prefs/pref_observer.h" #include "components/prefs/prefs_export.h" @@ -193,18 +192,11 @@ subtle::PrefMemberBase::Destroy(); } - // Moves the PrefMember to another thread, allowing read accesses from there. - // Forwarder to MoveToSequence. - // TODO(crbug.com/978036): Remove after all callers use MoveToSequence - void MoveToThread(scoped_refptr<base::SingleThreadTaskRunner> task_runner) { - MoveToSequence(task_runner); - } - // Moves the PrefMember to another sequence, allowing read accesses from // there. Changes from the PrefService will be propagated asynchronously // via PostTask. - // This method should only be used from the thread the PrefMember is currently - // on, which is the UI thread by default. + // This method should only be used from the sequence the PrefMember is + // currently on, which is the UI thread by default. void MoveToSequence(scoped_refptr<base::SequencedTaskRunner> task_runner) { subtle::PrefMemberBase::MoveToSequence(task_runner); } @@ -212,8 +204,8 @@ // Check whether the pref is managed, i.e. controlled externally through // enterprise configuration management (e.g. windows group policy). Returns // false for unknown prefs. - // This method should only be used from the thread the PrefMember is currently - // on, which is the UI thread unless changed by |MoveToSequence|. + // This method should only be used from the sequence the PrefMember is + // currently on, which is the UI thread unless changed by |MoveToSequence|. bool IsManaged() const { VerifyPref(); return internal_->IsManaged(); @@ -222,16 +214,16 @@ // Checks whether the pref can be modified by the user. This returns false // when the pref is managed by a policy or an extension, and when a command // line flag overrides the pref. - // This method should only be used from the thread the PrefMember is currently - // on, which is the UI thread unless changed by |MoveToSequence|. + // This method should only be used from the sequence the PrefMember is + // currently on, which is the UI thread unless changed by |MoveToSequence|. bool IsUserModifiable() const { VerifyPref(); return internal_->IsUserModifiable(); } // Retrieve the value of the member variable. - // This method should only be used from the thread the PrefMember is currently - // on, which is the UI thread unless changed by |MoveToSequence|. + // This method should only be used from the sequence the PrefMember is + // currently on, which is the UI thread unless changed by |MoveToSequence|. ValueType GetValue() const { VerifyPref(); return internal_->value();
diff --git a/components/query_parser/OWNERS b/components/query_parser/OWNERS index 90b3e80..45babcb 100644 --- a/components/query_parser/OWNERS +++ b/components/query_parser/OWNERS
@@ -1 +1,2 @@ sky@chromium.org +# COMPONENT: Internals
diff --git a/components/remote_cocoa/app_shim/native_widget_ns_window_bridge.mm b/components/remote_cocoa/app_shim/native_widget_ns_window_bridge.mm index aeb1b4a..d1b8eef 100644 --- a/components/remote_cocoa/app_shim/native_widget_ns_window_bridge.mm +++ b/components/remote_cocoa/app_shim/native_widget_ns_window_bridge.mm
@@ -385,8 +385,13 @@ // If |window_| was already visible then add it as a child window immediately. // As in OnVisibilityChanged, do not set a parent for sheets. - if (window_visible_ && ![window_ isSheet]) + if (window_visible_ && ![window_ isSheet]) { + // Attaching a window to be a child window resets the window level, so + // restore the window level afterwards. + NSInteger window_level = [window_ level]; [parent_->ns_window() addChildWindow:window_ ordered:NSWindowAbove]; + [window_ setLevel:window_level]; + } } void NativeWidgetNSWindowBridge::CreateSelectFileDialog( @@ -958,8 +963,13 @@ // Sheets don't need a parentWindow set, and setting one causes graphical // glitches (http://crbug.com/605098). - if (parent_ && ![window_ isSheet]) + if (parent_ && ![window_ isSheet]) { + // Attaching a window to be a child window resets the window level, so + // restore the window level afterwards. + NSInteger window_level = [window_ level]; [parent_->ns_window() addChildWindow:window_ ordered:NSWindowAbove]; + [window_ setLevel:window_level]; + } } else { ReleaseCapture(); // Capture on hidden windows is not permitted.
diff --git a/components/undo/OWNERS b/components/undo/OWNERS index 40c070a..d207324d 100644 --- a/components/undo/OWNERS +++ b/components/undo/OWNERS
@@ -1,2 +1,3 @@ sky@chromium.org tom.cassiotis@gmail.com +# COMPONENT: Internals
diff --git a/components/undo_strings_grdp/OWNERS b/components/undo_strings_grdp/OWNERS index 3c4cda0..85b05d41 100644 --- a/components/undo_strings_grdp/OWNERS +++ b/components/undo_strings_grdp/OWNERS
@@ -1 +1,2 @@ file://components/undo/OWNERS +# COMPONENT: Internals
diff --git a/components/viz/service/hit_test/hit_test_manager_fuzzer.cc b/components/viz/service/hit_test/hit_test_manager_fuzzer.cc index 59387f8d..cb9ed54c 100644 --- a/components/viz/service/hit_test/hit_test_manager_fuzzer.cc +++ b/components/viz/service/hit_test/hit_test_manager_fuzzer.cc
@@ -61,6 +61,7 @@ viz::HitTestRegion hit_test_region; hit_test_region.flags = fuzz->ConsumeIntegral<uint32_t>(); + hit_test_region.async_hit_test_reasons = fuzz->ConsumeIntegral<uint32_t>(); if (fuzz->ConsumeBool()) hit_test_region.flags |= viz::HitTestRegionFlags::kHitTestChildSurface; hit_test_region.frame_sink_id = viz::FrameSinkId( @@ -111,6 +112,8 @@ if (fuzz->ConsumeBool()) { hit_test_region_list.emplace(); hit_test_region_list->flags = fuzz->ConsumeIntegral<uint32_t>(); + hit_test_region_list->async_hit_test_reasons = + fuzz->ConsumeIntegral<uint32_t>(); if (fuzz->ConsumeBool()) hit_test_region_list->flags |= viz::HitTestRegionFlags::kHitTestChildSurface;
diff --git a/content/browser/accessibility/browser_accessibility.cc b/content/browser/accessibility/browser_accessibility.cc index 285aa85..b8e7d3f 100644 --- a/content/browser/accessibility/browser_accessibility.cc +++ b/content/browser/accessibility/browser_accessibility.cc
@@ -1398,6 +1398,11 @@ return descendants; } +std::string BrowserAccessibility::GetLanguage() const { + DCHECK(node_) << "Did you forget to call BrowserAccessibility::Init?"; + return node()->GetLanguage(); +} + gfx::NativeViewAccessible BrowserAccessibility::GetNativeViewAccessible() { // TODO(703369) On Windows, where we have started to migrate to an // AXPlatformNode implementation, the BrowserAccessibilityWin subclass has
diff --git a/content/browser/accessibility/browser_accessibility.h b/content/browser/accessibility/browser_accessibility.h index 840be08..9509c88 100644 --- a/content/browser/accessibility/browser_accessibility.h +++ b/content/browser/accessibility/browser_accessibility.h
@@ -482,6 +482,8 @@ const std::vector<gfx::NativeViewAccessible> GetDescendants() const override; + std::string GetLanguage() const override; + bool IsTable() const override; base::Optional<int> GetTableColCount() const override; base::Optional<int> GetTableRowCount() const override;
diff --git a/content/browser/accessibility/browser_accessibility_auralinux_unittest.cc b/content/browser/accessibility/browser_accessibility_auralinux_unittest.cc index 308e1a94..0dd46559 100644 --- a/content/browser/accessibility/browser_accessibility_auralinux_unittest.cc +++ b/content/browser/accessibility/browser_accessibility_auralinux_unittest.cc
@@ -294,4 +294,238 @@ manager.reset(); } +TEST_F(BrowserAccessibilityAuraLinuxTest, + TestTextAttributesInContentEditables) { + auto has_attribute = [](AtkAttributeSet* attributes, + AtkTextAttribute text_attribute, + base::Optional<const char*> expected_value) { + const char* name = atk_text_attribute_get_name(text_attribute); + while (attributes) { + const AtkAttribute* attribute = + static_cast<AtkAttribute*>(attributes->data); + if (!g_strcmp0(attribute->name, name)) { + if (!expected_value.has_value()) + return true; + if (!g_strcmp0(attribute->value, *expected_value)) + return true; + } + attributes = g_slist_next(attributes); + } + return false; + }; + + ui::AXNodeData root; + root.id = 1; + root.role = ax::mojom::Role::kRootWebArea; + root.AddState(ax::mojom::State::kFocusable); + + ui::AXNodeData div_editable; + div_editable.id = 2; + div_editable.role = ax::mojom::Role::kGenericContainer; + div_editable.AddState(ax::mojom::State::kEditable); + div_editable.AddState(ax::mojom::State::kFocusable); + div_editable.AddStringAttribute(ax::mojom::StringAttribute::kFontFamily, + "Helvetica"); + + ui::AXNodeData text_before; + text_before.id = 3; + text_before.role = ax::mojom::Role::kStaticText; + text_before.AddState(ax::mojom::State::kEditable); + text_before.SetName("Before "); + text_before.AddTextStyle(ax::mojom::TextStyle::kBold); + text_before.AddTextStyle(ax::mojom::TextStyle::kItalic); + + ui::AXNodeData link; + link.id = 4; + link.role = ax::mojom::Role::kLink; + link.AddState(ax::mojom::State::kEditable); + link.AddState(ax::mojom::State::kFocusable); + link.AddState(ax::mojom::State::kLinked); + link.SetName("lnk"); + link.AddTextStyle(ax::mojom::TextStyle::kUnderline); + + ui::AXNodeData link_text; + link_text.id = 5; + link_text.role = ax::mojom::Role::kStaticText; + link_text.AddState(ax::mojom::State::kEditable); + link_text.AddState(ax::mojom::State::kFocusable); + link_text.AddState(ax::mojom::State::kLinked); + link_text.SetName("lnk"); + link_text.AddTextStyle(ax::mojom::TextStyle::kUnderline); + link_text.AddStringAttribute(ax::mojom::StringAttribute::kLanguage, "fr"); + + // The name "lnk" is misspelled. + std::vector<int32_t> marker_types{ + static_cast<int32_t>(ax::mojom::MarkerType::kSpelling)}; + std::vector<int32_t> marker_starts{0}; + std::vector<int32_t> marker_ends{3}; + link_text.AddIntListAttribute(ax::mojom::IntListAttribute::kMarkerTypes, + marker_types); + link_text.AddIntListAttribute(ax::mojom::IntListAttribute::kMarkerStarts, + marker_starts); + link_text.AddIntListAttribute(ax::mojom::IntListAttribute::kMarkerEnds, + marker_ends); + + ui::AXNodeData text_after; + text_after.id = 6; + text_after.role = ax::mojom::Role::kStaticText; + text_after.AddState(ax::mojom::State::kEditable); + text_after.SetName(" after."); + // Leave text style as normal. + + root.child_ids.push_back(div_editable.id); + div_editable.child_ids = {text_before.id, link.id, text_after.id}; + link.child_ids.push_back(link_text.id); + + ui::AXTreeUpdate update = MakeAXTreeUpdate(root, div_editable, text_before, + link, link_text, text_after); + + std::unique_ptr<BrowserAccessibilityManager> manager( + BrowserAccessibilityManager::Create( + update, test_browser_accessibility_delegate_.get(), + new BrowserAccessibilityFactory())); + + ASSERT_NE(nullptr, manager->GetRoot()); + BrowserAccessibilityAuraLinux* ax_root = + ToBrowserAccessibilityAuraLinux(manager->GetRoot()); + ASSERT_NE(nullptr, ax_root); + ASSERT_EQ(1U, ax_root->PlatformChildCount()); + + BrowserAccessibilityAuraLinux* ax_div = + ToBrowserAccessibilityAuraLinux(ax_root->PlatformGetChild(0)); + ASSERT_NE(nullptr, ax_div); + ASSERT_EQ(3U, ax_div->PlatformChildCount()); + + BrowserAccessibilityAuraLinux* ax_before = + ToBrowserAccessibilityAuraLinux(ax_div->PlatformGetChild(0)); + ASSERT_NE(nullptr, ax_before); + BrowserAccessibilityAuraLinux* ax_link = + ToBrowserAccessibilityAuraLinux(ax_div->PlatformGetChild(1)); + ASSERT_NE(nullptr, ax_link); + ASSERT_EQ(1U, ax_link->PlatformChildCount()); + BrowserAccessibilityAuraLinux* ax_after = + ToBrowserAccessibilityAuraLinux(ax_div->PlatformGetChild(2)); + ASSERT_NE(nullptr, ax_after); + + BrowserAccessibilityAuraLinux* ax_link_text = + ToBrowserAccessibilityAuraLinux(ax_link->PlatformGetChild(0)); + ASSERT_NE(nullptr, ax_link_text); + + AtkObject* root_atk_object = ax_root->GetNode()->GetNativeViewAccessible(); + AtkObject* ax_div_atk_object = ax_div->GetNode()->GetNativeViewAccessible(); + + ASSERT_EQ(1, atk_text_get_character_count(ATK_TEXT(root_atk_object))); + ASSERT_EQ(15, atk_text_get_character_count(ATK_TEXT(ax_div_atk_object))); + + // Test the style of the root. + int start_offset, end_offset; + AtkAttributeSet* attributes = atk_text_get_run_attributes( + ATK_TEXT(root_atk_object), 0, &start_offset, &end_offset); + + ASSERT_EQ(0, start_offset); + ASSERT_EQ(1, end_offset); + + ASSERT_TRUE( + has_attribute(attributes, ATK_TEXT_ATTR_FAMILY_NAME, "Helvetica")); + atk_attribute_set_free(attributes); + + // Test the style of text_before. + for (int offset = 0; offset < 7; ++offset) { + start_offset = end_offset = -1; + attributes = atk_text_get_run_attributes( + ATK_TEXT(ax_div_atk_object), offset, &start_offset, &end_offset); + + EXPECT_EQ(0, start_offset); + EXPECT_EQ(7, end_offset); + + ASSERT_TRUE( + has_attribute(attributes, ATK_TEXT_ATTR_FAMILY_NAME, "Helvetica")); + ASSERT_TRUE(has_attribute(attributes, ATK_TEXT_ATTR_WEIGHT, "700")); + ASSERT_TRUE(has_attribute(attributes, ATK_TEXT_ATTR_STYLE, "italic")); + + atk_attribute_set_free(attributes); + } + + // Test the style of the link. + AtkObject* ax_link_text_atk_object = + ax_link_text->GetNode()->GetNativeViewAccessible(); + for (int offset = 0; offset < 3; offset++) { + start_offset = end_offset = -1; + attributes = atk_text_get_run_attributes( + ATK_TEXT(ax_link_text_atk_object), offset, &start_offset, &end_offset); + + EXPECT_EQ(0, start_offset); + EXPECT_EQ(3, end_offset); + + ASSERT_TRUE( + has_attribute(attributes, ATK_TEXT_ATTR_FAMILY_NAME, "Helvetica")); + ASSERT_FALSE( + has_attribute(attributes, ATK_TEXT_ATTR_WEIGHT, base::nullopt)); + ASSERT_FALSE(has_attribute(attributes, ATK_TEXT_ATTR_STYLE, base::nullopt)); + ASSERT_TRUE(has_attribute(attributes, ATK_TEXT_ATTR_UNDERLINE, "single")); + ASSERT_TRUE(has_attribute(attributes, ATK_TEXT_ATTR_LANGUAGE, "fr")); + + // For compatibility with Firefox, spelling attributes should also be + // propagated to the parent of static text leaves. + ASSERT_TRUE(has_attribute(attributes, ATK_TEXT_ATTR_UNDERLINE, "error")); + ASSERT_TRUE(has_attribute(attributes, ATK_TEXT_ATTR_INVALID, "spelling")); + + atk_attribute_set_free(attributes); + } + + // Test the style of text_after. + for (int offset = 8; offset < 15; ++offset) { + start_offset = end_offset = -1; + attributes = atk_text_get_run_attributes( + ATK_TEXT(ax_div_atk_object), offset, &start_offset, &end_offset); + EXPECT_EQ(8, start_offset); + EXPECT_EQ(15, end_offset); + + ASSERT_TRUE( + has_attribute(attributes, ATK_TEXT_ATTR_FAMILY_NAME, "Helvetica")); + ASSERT_FALSE( + has_attribute(attributes, ATK_TEXT_ATTR_WEIGHT, base::nullopt)); + ASSERT_FALSE(has_attribute(attributes, ATK_TEXT_ATTR_STYLE, base::nullopt)); + ASSERT_FALSE( + has_attribute(attributes, ATK_TEXT_ATTR_UNDERLINE, base::nullopt)); + ASSERT_FALSE( + has_attribute(attributes, ATK_TEXT_ATTR_INVALID, base::nullopt)); + + atk_attribute_set_free(attributes); + } + + // Test the style of the static text nodes. + AtkObject* ax_before_atk_object = + ax_before->GetNode()->GetNativeViewAccessible(); + start_offset = end_offset = -1; + attributes = atk_text_get_run_attributes(ATK_TEXT(ax_before_atk_object), 6, + &start_offset, &end_offset); + EXPECT_EQ(0, start_offset); + EXPECT_EQ(7, end_offset); + ASSERT_TRUE( + has_attribute(attributes, ATK_TEXT_ATTR_FAMILY_NAME, "Helvetica")); + ASSERT_TRUE(has_attribute(attributes, ATK_TEXT_ATTR_WEIGHT, "700")); + ASSERT_TRUE(has_attribute(attributes, ATK_TEXT_ATTR_STYLE, "italic")); + ASSERT_FALSE( + has_attribute(attributes, ATK_TEXT_ATTR_UNDERLINE, base::nullopt)); + ASSERT_FALSE(has_attribute(attributes, ATK_TEXT_ATTR_INVALID, base::nullopt)); + atk_attribute_set_free(attributes); + + AtkObject* ax_after_atk_object = + ax_after->GetNode()->GetNativeViewAccessible(); + attributes = atk_text_get_run_attributes(ATK_TEXT(ax_after_atk_object), 6, + &start_offset, &end_offset); + EXPECT_EQ(0, start_offset); + EXPECT_EQ(7, end_offset); + ASSERT_TRUE( + has_attribute(attributes, ATK_TEXT_ATTR_FAMILY_NAME, "Helvetica")); + ASSERT_FALSE(has_attribute(attributes, ATK_TEXT_ATTR_WEIGHT, base::nullopt)); + ASSERT_FALSE(has_attribute(attributes, ATK_TEXT_ATTR_STYLE, "italic")); + ASSERT_FALSE( + has_attribute(attributes, ATK_TEXT_ATTR_UNDERLINE, base::nullopt)); + atk_attribute_set_free(attributes); + + manager.reset(); +} + } // namespace content
diff --git a/content/browser/accessibility/browser_accessibility_cocoa.mm b/content/browser/accessibility/browser_accessibility_cocoa.mm index 3720fdd5..6ca7a34 100644 --- a/content/browser/accessibility/browser_accessibility_cocoa.mm +++ b/content/browser/accessibility/browser_accessibility_cocoa.mm
@@ -231,10 +231,27 @@ return AXPlatformRange(std::move(anchor), std::move(focus)); } +BrowserAccessibilityPositionInstance CreateTreePosition( + const BrowserAccessibility& object, + int offset) { + // A tree position is one for which the |offset| argument refers to a child + // index instead of a character offset inside a text object. + if (!object.instance_active()) + return BrowserAccessibilityPosition::CreateNullPosition(); + + const BrowserAccessibilityManager* manager = object.manager(); + DCHECK(manager); + return BrowserAccessibilityPosition::CreateTreePosition( + manager->ax_tree_id(), object.GetId(), offset); +} + BrowserAccessibilityPositionInstance CreateTextPosition( const BrowserAccessibility& object, int offset, ax::mojom::TextAffinity affinity) { + // A text position is one for which the |offset| argument refers to a + // character offset inside a text object. As such, text positions are only + // valid on platform leaf objects, e.g. static text nodes and text fields. if (!object.instance_active()) return BrowserAccessibilityPosition::CreateNullPosition(); @@ -244,16 +261,20 @@ manager->ax_tree_id(), object.GetId(), offset, affinity); } -AXPlatformRange CreateTextRange(const BrowserAccessibility& start_object, - int start_offset, - ax::mojom::TextAffinity start_affinity, - const BrowserAccessibility& end_object, - int end_offset, - ax::mojom::TextAffinity end_affinity) { +AXPlatformRange CreateAXPlatformRange(const BrowserAccessibility& start_object, + int start_offset, + ax::mojom::TextAffinity start_affinity, + const BrowserAccessibility& end_object, + int end_offset, + ax::mojom::TextAffinity end_affinity) { BrowserAccessibilityPositionInstance anchor = - CreateTextPosition(start_object, start_offset, start_affinity); + start_object.IsTextOnlyObject() + ? CreateTextPosition(start_object, start_offset, start_affinity) + : CreateTreePosition(start_object, start_offset); BrowserAccessibilityPositionInstance focus = - CreateTextPosition(end_object, end_offset, end_affinity); + end_object.IsTextOnlyObject() + ? CreateTextPosition(end_object, end_offset, end_affinity) + : CreateTreePosition(end_object, end_offset); // |AXPlatformRange| takes ownership of its anchor and focus. return AXPlatformRange(std::move(anchor), std::move(focus)); } @@ -2026,6 +2047,9 @@ if (!focusObject) return nil; + // |anchorOffset| and / or |focusOffset| refer to a character offset if + // |anchorObject| / |focusObject| are text-only objects. Otherwise, they + // should be treated as child indices. int anchorOffset = manager->GetTreeData().sel_anchor_offset; int focusOffset = manager->GetTreeData().sel_focus_offset; if (anchorOffset < 0 || focusOffset < 0) @@ -2036,9 +2060,9 @@ ax::mojom::TextAffinity focusAffinity = manager->GetTreeData().sel_focus_affinity; - return CreateTextMarkerRange(CreateTextRange(*anchorObject, anchorOffset, - anchorAffinity, *focusObject, - focusOffset, focusAffinity)); + return CreateTextMarkerRange( + CreateAXPlatformRange(*anchorObject, anchorOffset, anchorAffinity, + *focusObject, focusOffset, focusAffinity)); } - (NSValue*)size {
diff --git a/content/browser/accessibility/browser_accessibility_com_win.cc b/content/browser/accessibility/browser_accessibility_com_win.cc index 92c65f2..899e66d 100644 --- a/content/browser/accessibility/browser_accessibility_com_win.cc +++ b/content/browser/accessibility/browser_accessibility_com_win.cc
@@ -1809,48 +1809,6 @@ AXPlatformNodeWin::Init(delegate); } -base::string16 BrowserAccessibilityComWin::GetInvalidValue() const { - const BrowserAccessibilityWin* target = owner(); - // The aria-invalid=spelling/grammar need to be exposed as text attributes for - // a range matching the visual underline representing the error. - if (static_cast<ax::mojom::InvalidState>( - target->GetIntAttribute(ax::mojom::IntAttribute::kInvalidState)) == - ax::mojom::InvalidState::kNone && - target->IsTextOnlyObject() && target->PlatformGetParent()) { - // Text nodes need to reflect the invalid state of their parent object, - // otherwise spelling and grammar errors communicated through aria-invalid - // won't be reflected in text attributes. - target = static_cast<BrowserAccessibilityWin*>(target->PlatformGetParent()); - } - - base::string16 invalid_value; - // Note: spelling+grammar errors case is disallowed and not supported. It - // could possibly arise with aria-invalid on the ancestor of a spelling error, - // but this is not currently described in any spec and no real-world use cases - // have been found. - switch (static_cast<ax::mojom::InvalidState>( - target->GetIntAttribute(ax::mojom::IntAttribute::kInvalidState))) { - case ax::mojom::InvalidState::kNone: - case ax::mojom::InvalidState::kFalse: - break; - case ax::mojom::InvalidState::kTrue: - return invalid_value = L"true"; - case ax::mojom::InvalidState::kOther: { - base::string16 aria_invalid_value; - if (target->GetString16Attribute( - ax::mojom::StringAttribute::kAriaInvalidValue, - &aria_invalid_value)) { - SanitizeStringAttributeForIA2(aria_invalid_value, &aria_invalid_value); - invalid_value = aria_invalid_value; - } else { - // Set the attribute to L"true", since we cannot be more specific. - invalid_value = L"true"; - } - } - } - return invalid_value; -} - std::vector<base::string16> BrowserAccessibilityComWin::ComputeTextAttributes() const { std::vector<base::string16> attributes; @@ -1936,7 +1894,7 @@ // Screen readers look at the text attributes to determine if something is // misspelled, so we need to propagate any spelling attributes from immediate // parents of text-only objects. - base::string16 invalid_value = GetInvalidValue(); + base::string16 invalid_value = base::UTF8ToUTF16(GetInvalidValue()); if (!invalid_value.empty()) attributes.push_back(L"invalid:" + invalid_value);
diff --git a/content/browser/accessibility/browser_accessibility_com_win.h b/content/browser/accessibility/browser_accessibility_com_win.h index 97994fa..bf33f4c9 100644 --- a/content/browser/accessibility/browser_accessibility_com_win.h +++ b/content/browser/accessibility/browser_accessibility_com_win.h
@@ -444,8 +444,6 @@ HRESULT GetStringAttributeAsBstr(ax::mojom::StringAttribute attribute, BSTR* value_bstr); - base::string16 GetInvalidValue() const; - // Merges the given spelling attributes, i.e. document marker information, // into the given text attributes starting at the given character offset. This // is required for two reasons: 1. Document markers that are present on text
diff --git a/content/browser/cache_storage/cache_storage_cache.h b/content/browser/cache_storage/cache_storage_cache.h index 1489eb8d..e9147612 100644 --- a/content/browser/cache_storage/cache_storage_cache.h +++ b/content/browser/cache_storage/cache_storage_cache.h
@@ -143,6 +143,11 @@ int64_t trace_id, CacheEntriesCallback callback) = 0; + // Try to determine the initialization state of the cache. Unknown may be + // returned for cross-sequence clients using the cross-sequence wrappers. + enum class InitState { Unknown, Initializing, Initialized }; + virtual InitState GetInitState() const = 0; + protected: virtual ~CacheStorageCache() = default; };
diff --git a/content/browser/cache_storage/cache_storage_dispatcher_host.cc b/content/browser/cache_storage/cache_storage_dispatcher_host.cc index 953d44bd..31a73261 100644 --- a/content/browser/cache_storage/cache_storage_dispatcher_host.cc +++ b/content/browser/cache_storage/cache_storage_dispatcher_host.cc
@@ -89,8 +89,15 @@ "request", CacheStorageTracedValue(request), "options", CacheStorageTracedValue(match_options)); + content::CacheStorageCache* cache = cache_handle_.value(); + bool cache_initialized = + cache ? cache->GetInitState() == + content::CacheStorageCache::InitState::Initialized + : false; + auto cb = base::BindOnce( - [](base::TimeTicks start_time, bool ignore_search, int64_t trace_id, + [](base::TimeTicks start_time, bool ignore_search, + bool cache_initialized, int64_t trace_id, blink::mojom::CacheStorageCache::MatchCallback callback, blink::mojom::CacheStorageError error, blink::mojom::FetchAPIResponsePtr response) { @@ -101,6 +108,10 @@ UMA_HISTOGRAM_LONG_TIMES( "ServiceWorkerCache.Cache.Browser.Match.IgnoreSearch", elapsed); } + if (cache_initialized) { + UMA_HISTOGRAM_LONG_TIMES( + "ServiceWorkerCache.Cache.Browser.Match.Initialized", elapsed); + } if (error == CacheStorageError::kErrorNotFound) { UMA_HISTOGRAM_LONG_TIMES( "ServiceWorkerCache.Cache.Browser.Match.Miss", elapsed); @@ -127,10 +138,9 @@ std::move(callback).Run( blink::mojom::MatchResult::NewResponse(std::move(response))); }, - base::TimeTicks::Now(), match_options->ignore_search, trace_id, - std::move(callback)); + base::TimeTicks::Now(), match_options->ignore_search, cache_initialized, + trace_id, std::move(callback)); - content::CacheStorageCache* cache = cache_handle_.value(); if (!cache) { std::move(cb).Run(CacheStorageError::kErrorNotFound, nullptr); return;
diff --git a/content/browser/cache_storage/cross_sequence/cross_sequence_cache_storage_cache.cc b/content/browser/cache_storage/cross_sequence/cross_sequence_cache_storage_cache.cc index 84ffbe5..dc2c5c9 100644 --- a/content/browser/cache_storage/cross_sequence/cross_sequence_cache_storage_cache.cc +++ b/content/browser/cache_storage/cross_sequence/cross_sequence_cache_storage_cache.cc
@@ -242,6 +242,13 @@ WrapCallbackForCurrentSequence(std::move(callback))); } +CacheStorageCache::InitState CrossSequenceCacheStorageCache::GetInitState() + const { + // We don't really know when the real cache on the other sequence becomes + // initialized. + return InitState::Unknown; +} + CrossSequenceCacheStorageCache::~CrossSequenceCacheStorageCache() { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); }
diff --git a/content/browser/cache_storage/cross_sequence/cross_sequence_cache_storage_cache.h b/content/browser/cache_storage/cross_sequence/cross_sequence_cache_storage_cache.h index 1b0c7a83..36dc9c2 100644 --- a/content/browser/cache_storage/cross_sequence/cross_sequence_cache_storage_cache.h +++ b/content/browser/cache_storage/cross_sequence/cross_sequence_cache_storage_cache.h
@@ -76,6 +76,8 @@ int64_t trace_id, CacheEntriesCallback callback) override; + InitState GetInitState() const override; + private: friend class base::RefCounted<CrossSequenceCacheStorageCache>; ~CrossSequenceCacheStorageCache() override;
diff --git a/content/browser/cache_storage/legacy/legacy_cache_storage_cache.cc b/content/browser/cache_storage/legacy/legacy_cache_storage_cache.cc index 2cd3b2ed..5eb3460a1 100644 --- a/content/browser/cache_storage/legacy/legacy_cache_storage_cache.cc +++ b/content/browser/cache_storage/legacy/legacy_cache_storage_cache.cc
@@ -2043,6 +2043,11 @@ std::move(callback).Run(CacheStorageError::kSuccess, std::move(entries)); } +CacheStorageCache::InitState LegacyCacheStorageCache::GetInitState() const { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + return initializing_ ? InitState::Initializing : InitState::Initialized; +} + void LegacyCacheStorageCache::Delete(blink::mojom::BatchOperationPtr operation, ErrorCallback callback) { DCHECK(BACKEND_OPEN == backend_state_ || initializing_); @@ -2250,6 +2255,7 @@ } void LegacyCacheStorageCache::InitBackend() { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); DCHECK_EQ(BACKEND_UNINITIALIZED, backend_state_); DCHECK(!initializing_); DCHECK(!scheduler_->ScheduledOperations()); @@ -2337,6 +2343,7 @@ CacheStorageError cache_create_error, int64_t cache_size, int64_t cache_padding) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); cache_size_ = cache_size; cache_padding_ = cache_padding;
diff --git a/content/browser/cache_storage/legacy/legacy_cache_storage_cache.h b/content/browser/cache_storage/legacy/legacy_cache_storage_cache.h index 33622c79..9bd5679 100644 --- a/content/browser/cache_storage/legacy/legacy_cache_storage_cache.h +++ b/content/browser/cache_storage/legacy/legacy_cache_storage_cache.h
@@ -163,6 +163,8 @@ int64_t trace_id, CacheEntriesCallback callback) override; + InitState GetInitState() const override; + // Async operations in progress will cancel and not run their callbacks. ~LegacyCacheStorageCache() override;
diff --git a/content/browser/push_messaging/push_messaging_manager.cc b/content/browser/push_messaging/push_messaging_manager.cc index cfcdb90..c8c04277 100644 --- a/content/browser/push_messaging/push_messaging_manager.cc +++ b/content/browser/push_messaging/push_messaging_manager.cc
@@ -599,9 +599,7 @@ RegisterData data, blink::mojom::PushRegistrationStatus status) { DCHECK_CURRENTLY_ON(BrowserThread::IO); - std::move(data.callback) - .Run(status, base::nullopt /* endpoint */, nullptr /* options */, - base::nullopt /* p256dh */, base::nullopt /* auth */); + std::move(data.callback).Run(status, nullptr /* subscription */); RecordRegistrationStatus(status); } @@ -627,7 +625,8 @@ push_subscription_id); std::move(data.callback) - .Run(status, endpoint, std::move(data.options), p256dh, auth); + .Run(status, blink::mojom::PushSubscription::New( + endpoint, std::move(data.options), p256dh, auth)); RecordRegistrationStatus(status); } @@ -856,9 +855,7 @@ break; } } - std::move(callback).Run(get_status, base::nullopt /* endpoint */, - nullptr /* options */, base::nullopt /* p256dh */, - base::nullopt /* auth */); + std::move(callback).Run(get_status, nullptr /* subscription */); RecordGetRegistrationStatus(get_status); } @@ -888,8 +885,9 @@ base::PostTaskWithTraits( FROM_HERE, {BrowserThread::IO}, - base::BindOnce(std::move(callback), status, endpoint, - std::move(options), p256dh, auth)); + base::BindOnce(std::move(callback), status, + blink::mojom::PushSubscription::New( + endpoint, std::move(options), p256dh, auth))); RecordGetRegistrationStatus(status); } else { @@ -903,8 +901,7 @@ base::BindOnce( std::move(callback), blink::mojom::PushGetRegistrationStatus::RENDERER_SHUTDOWN, - base::nullopt /* endpoint */, nullptr /* options */, - base::nullopt /* p256dh */, base::nullopt /* auth */)); + nullptr /* subscription */)); return; } @@ -932,11 +929,9 @@ blink::mojom::PushGetRegistrationStatus get_status, blink::mojom::PushUnregistrationStatus unsubscribe_status) { DCHECK_CURRENTLY_ON(BrowserThread::UI); - base::PostTaskWithTraits( - FROM_HERE, {BrowserThread::IO}, - base::BindOnce(std::move(callback), get_status, - base::nullopt /* endpoint */, nullptr /* options */, - base::nullopt /* p256dh */, base::nullopt /* auth */)); + base::PostTaskWithTraits(FROM_HERE, {BrowserThread::IO}, + base::BindOnce(std::move(callback), get_status, + nullptr /* subscription */)); } // Helper methods on both IO and UI threads, merged from
diff --git a/content/browser/service_worker/fake_service_worker.cc b/content/browser/service_worker/fake_service_worker.cc index 7e54f64..59b10c9 100644 --- a/content/browser/service_worker/fake_service_worker.cc +++ b/content/browser/service_worker/fake_service_worker.cc
@@ -140,6 +140,13 @@ std::move(callback).Run(blink::mojom::ServiceWorkerEventStatus::COMPLETED); } +void FakeServiceWorker::DispatchPushSubscriptionChangeEvent( + blink::mojom::PushSubscriptionPtr old_subscription, + blink::mojom::PushSubscriptionPtr new_subscription, + DispatchPushSubscriptionChangeEventCallback callback) { + std::move(callback).Run(blink::mojom::ServiceWorkerEventStatus::COMPLETED); +} + void FakeServiceWorker::DispatchSyncEvent(const std::string& tag, bool last_chance, base::TimeDelta timeout,
diff --git a/content/browser/service_worker/fake_service_worker.h b/content/browser/service_worker/fake_service_worker.h index 0b88c82..b82bb2c5 100644 --- a/content/browser/service_worker/fake_service_worker.h +++ b/content/browser/service_worker/fake_service_worker.h
@@ -82,6 +82,10 @@ DispatchNotificationCloseEventCallback callback) override; void DispatchPushEvent(const base::Optional<std::string>& payload, DispatchPushEventCallback callback) override; + void DispatchPushSubscriptionChangeEvent( + blink::mojom::PushSubscriptionPtr old_subscription, + blink::mojom::PushSubscriptionPtr new_subscription, + DispatchPushSubscriptionChangeEventCallback callback) override; void DispatchSyncEvent(const std::string& tag, bool last_chance, base::TimeDelta timeout,
diff --git a/content/browser/webauth/authenticator_impl_unittest.cc b/content/browser/webauth/authenticator_impl_unittest.cc index f8746898..92ce948 100644 --- a/content/browser/webauth/authenticator_impl_unittest.cc +++ b/content/browser/webauth/authenticator_impl_unittest.cc
@@ -341,7 +341,7 @@ } // namespace class AuthenticatorTestBase : public content::RenderViewHostTestHarness { - public: + protected: AuthenticatorTestBase() { ResetVirtualDevice(); } ~AuthenticatorTestBase() override {} @@ -354,19 +354,22 @@ std::move(virtual_device_factory)); } - protected: device::test::VirtualFidoDeviceFactory* virtual_device_factory_; + +#if defined(OS_WIN) + device::ScopedFakeWinWebAuthnApi win_webauthn_api_ = + device::ScopedFakeWinWebAuthnApi::MakeUnavailable(); +#endif // defined(OS_WIN) }; class AuthenticatorImplTest : public AuthenticatorTestBase { - public: + protected: ~AuthenticatorImplTest() override {} - protected: void TearDown() override { // The |RenderFrameHost| must outlive |AuthenticatorImpl|. authenticator_impl_.reset(); - content::RenderViewHostTestHarness::TearDown(); + AuthenticatorTestBase::TearDown(); } void NavigateAndCommit(const GURL& url) { @@ -2309,9 +2312,8 @@ for (const bool is_uvpaa : {false, true}) { SCOPED_TRACE(is_uvpaa ? "is_uvpaa" : "!is_uvpaa"); - device::ScopedFakeWinWebAuthnApi fake_api; - fake_api.set_available(enable_win_webauthn_api); - fake_api.set_is_uvpaa(is_uvpaa); + win_webauthn_api_.set_available(enable_win_webauthn_api); + win_webauthn_api_.set_is_uvpaa(is_uvpaa); mojo::Remote<blink::mojom::Authenticator> authenticator = ConnectToAuthenticator(); @@ -3954,13 +3956,15 @@ // The canned response returned by the Windows API fake is for acme.com. NavigateAndCommit(GURL("https://acme.com")); TestServiceManagerContext smc; + // AuthenticatorTestBase default-disables |win_webauthn_api_|. + win_webauthn_api_.set_available(true); for (const bool supports_cred_protect : {false, true}) { SCOPED_TRACE(testing::Message() << "supports_cred_protect: " << supports_cred_protect); - device::ScopedFakeWinWebAuthnApi fake_api; - fake_api.set_version(supports_cred_protect ? WEBAUTHN_API_VERSION_2 - : WEBAUTHN_API_VERSION_1); + win_webauthn_api_.set_version(supports_cred_protect + ? WEBAUTHN_API_VERSION_2 + : WEBAUTHN_API_VERSION_1); PublicKeyCredentialCreationOptionsPtr options = make_credential_options(); options->relying_party = device::PublicKeyCredentialRpEntity(); @@ -3988,10 +3992,9 @@ #endif // defined(OS_WIN) class InternalAuthenticatorImplTest : public AuthenticatorTestBase { - public: + protected: InternalAuthenticatorImplTest() = default; - protected: void TearDown() override { // The |RenderFrameHost| must outlive |AuthenticatorImpl|. internal_authenticator_impl_.reset();
diff --git a/content/renderer/BUILD.gn b/content/renderer/BUILD.gn index 2541452..64430295 100644 --- a/content/renderer/BUILD.gn +++ b/content/renderer/BUILD.gn
@@ -214,10 +214,6 @@ "media/stream/user_media_client_impl.h", "media/stream/user_media_processor.cc", "media/stream/user_media_processor.h", - "media/stream/webmediaplayer_ms.cc", - "media/stream/webmediaplayer_ms.h", - "media/stream/webmediaplayer_ms_compositor.cc", - "media/stream/webmediaplayer_ms_compositor.h", "media/video_capture/local_video_capturer_source.cc", "media/video_capture/local_video_capturer_source.h", "media/video_capture/video_capture_impl.cc",
diff --git a/content/renderer/input/main_thread_event_queue.cc b/content/renderer/input/main_thread_event_queue.cc index cd94fbf..6f46970 100644 --- a/content/renderer/input/main_thread_event_queue.cc +++ b/content/renderer/input/main_thread_event_queue.cc
@@ -477,8 +477,9 @@ } void MainThreadEventQueue::RafFallbackTimerFired() { - UMA_HISTOGRAM_BOOLEAN("Event.MainThreadEventQueue.FlushQueueNoBeginMainFrame", - true); + // This fallback fires when the browser doesn't produce main frames for a + // variety of reasons. (eg. Tab gets hidden). We definitely don't want input + // to stay forever in the queue. DispatchRafAlignedInput(base::TimeTicks::Now()); }
diff --git a/content/renderer/input/render_widget_input_handler.cc b/content/renderer/input/render_widget_input_handler.cc index e23bdc9..aeba64d9 100644 --- a/content/renderer/input/render_widget_input_handler.cc +++ b/content/renderer/input/render_widget_input_handler.cc
@@ -126,12 +126,6 @@ UMA_HISTOGRAM_CUSTOM_COUNTS("Event.PassiveListeners.Latency", GetEventLatencyMicros(event_timestamp, now), 1, 10000000, 100); - } else if (enum_value == - PASSIVE_LISTENER_UMA_ENUM_FORCED_NON_BLOCKING_DUE_TO_FLING) { - base::TimeTicks now = base::TimeTicks::Now(); - UMA_HISTOGRAM_CUSTOM_COUNTS( - "Event.PassiveListeners.ForcedNonBlockingLatencyDueToFling", - GetEventLatencyMicros(event_timestamp, now), 1, 10000000, 100); } } }
diff --git a/content/renderer/media/media_factory.cc b/content/renderer/media/media_factory.cc index e1af2918..5d45575 100644 --- a/content/renderer/media/media_factory.cc +++ b/content/renderer/media/media_factory.cc
@@ -22,7 +22,6 @@ #include "content/renderer/media/render_media_log.h" #include "content/renderer/media/renderer_webmediaplayer_delegate.h" #include "content/renderer/media/stream/media_stream_renderer_factory_impl.h" -#include "content/renderer/media/stream/webmediaplayer_ms.h" #include "content/renderer/render_frame_impl.h" #include "content/renderer/render_thread_impl.h" #include "content/renderer/render_view_impl.h" @@ -48,6 +47,7 @@ #include "third_party/blink/public/platform/web_surface_layer_bridge.h" #include "third_party/blink/public/platform/web_video_frame_submitter.h" #include "third_party/blink/public/web/blink.h" +#include "third_party/blink/public/web/modules/mediastream/webmediaplayer_ms.h" #include "third_party/blink/public/web/web_local_frame.h" #include "url/origin.h" @@ -541,7 +541,7 @@ CreateSubmitter(&video_frame_compositor_task_runner, settings); DCHECK(layer_tree_view); - return new WebMediaPlayerMS( + return new blink::WebMediaPlayerMS( frame, client, GetWebMediaPlayerDelegate(), std::make_unique<RenderMediaLog>( url::Origin(security_origin).GetURL(),
diff --git a/content/renderer/media/media_factory.h b/content/renderer/media/media_factory.h index b40de60..5c30320 100644 --- a/content/renderer/media/media_factory.h +++ b/content/renderer/media/media_factory.h
@@ -137,7 +137,7 @@ media::RendererWebMediaPlayerDelegate* GetWebMediaPlayerDelegate(); // Creates a blink::WebMediaStreamRendererFactory used for creating audio and - // video renderers for WebMediaPlayerMS. + // video renderers for blink::WebMediaPlayerMS. std::unique_ptr<blink::WebMediaStreamRendererFactory> CreateMediaStreamRendererFactory();
diff --git a/content/renderer/media/stream/media_stream_center.cc b/content/renderer/media/stream/media_stream_center.cc index d7a8670..13b31206 100644 --- a/content/renderer/media/stream/media_stream_center.cc +++ b/content/renderer/media/stream/media_stream_center.cc
@@ -12,7 +12,6 @@ #include "base/logging.h" #include "content/renderer/media/stream/processed_local_audio_source.h" #include "media/base/sample_format.h" -#include "third_party/blink/public/platform/modules/mediastream/media_stream_audio_track.h" #include "third_party/blink/public/platform/modules/mediastream/web_platform_media_stream_source.h" #include "third_party/blink/public/platform/modules/mediastream/webaudio_media_stream_source.h" #include "third_party/blink/public/platform/web_media_stream_source.h" @@ -21,10 +20,6 @@ #include "third_party/blink/public/web/modules/mediastream/media_stream_video_source.h" #include "third_party/blink/public/web/modules/mediastream/media_stream_video_track.h" #include "third_party/blink/public/web/modules/mediastream/webaudio_media_stream_audio_sink.h" -#include "third_party/blink/public/web/web_frame.h" - -using blink::WebFrame; -using blink::WebView; namespace content {
diff --git a/content/test/BUILD.gn b/content/test/BUILD.gn index 73b8cae0..ab15e71a 100644 --- a/content/test/BUILD.gn +++ b/content/test/BUILD.gn
@@ -1921,7 +1921,6 @@ "../renderer/media/stream/media_stream_device_observer_unittest.cc", "../renderer/media/stream/processed_local_audio_source_unittest.cc", "../renderer/media/stream/user_media_client_impl_unittest.cc", - "../renderer/media/stream/webmediaplayer_ms_unittest.cc", "../renderer/media/video_capture/video_capture_impl_manager_unittest.cc", "../renderer/media/video_capture/video_capture_impl_unittest.cc", "../renderer/media/webrtc/fake_rtc_rtp_transceiver.cc",
diff --git a/content/test/data/accessibility/event/text-changed-expected-auralinux.txt b/content/test/data/accessibility/event/text-changed-expected-auralinux.txt index d6e866e..268d5e7b 100644 --- a/content/test/data/accessibility/event/text-changed-expected-auralinux.txt +++ b/content/test/data/accessibility/event/text-changed-expected-auralinux.txt
@@ -1,7 +1,7 @@ -CHILDREN-CHANGED index:0 CHILD:(role=ROLE_ENTRY) role=ROLE_TEXT ENABLED,SENSITIVE,SHOWING,VISIBLE -CHILDREN-CHANGED index:0 CHILD:(role=ROLE_ENTRY) role=ROLE_TEXT ENABLED,SENSITIVE,SHOWING,VISIBLE CHILDREN-CHANGED index:0 CHILD:(role=ROLE_TEXT) role=ROLE_PARAGRAPH ENABLED,SENSITIVE,SHOWING,VISIBLE CHILDREN-CHANGED index:0 CHILD:(role=ROLE_TEXT) role=ROLE_PARAGRAPH ENABLED,SENSITIVE,SHOWING,VISIBLE +CHILDREN-CHANGED index:0 CHILD:(role=ROLE_TEXT) role=ROLE_TEXT ENABLED,SENSITIVE,SHOWING,VISIBLE +CHILDREN-CHANGED index:0 CHILD:(role=ROLE_TEXT) role=ROLE_TEXT ENABLED,SENSITIVE,SHOWING,VISIBLE NAME-CHANGED:Modified Div role=ROLE_TEXT name='Modified Div' ENABLED,SENSITIVE,SHOWING,VISIBLE NAME-CHANGED:Modified Heading role=ROLE_TEXT name='Modified Heading' ENABLED,SENSITIVE,SHOWING,VISIBLE STATE-CHANGE:DEFUNCT:TRUE role=ROLE_INVALID name='(null)' DEFUNCT
diff --git a/device/fido/bio/enrollment_handler_unittest.cc b/device/fido/bio/enrollment_handler_unittest.cc index 479cc55..9d79882 100644 --- a/device/fido/bio/enrollment_handler_unittest.cc +++ b/device/fido/bio/enrollment_handler_unittest.cc
@@ -10,11 +10,16 @@ #include "base/bind.h" #include "base/callback.h" #include "base/test/scoped_task_environment.h" +#include "build/build_config.h" #include "device/fido/bio/enrollment_handler.h" #include "device/fido/fido_transport_protocol.h" #include "device/fido/test_callback_receiver.h" #include "device/fido/virtual_fido_device_factory.h" +#if defined(OS_WIN) +#include "device/fido/win/fake_webauthn_api.h" +#endif // defined(OS_WIN) + namespace device { namespace { @@ -68,6 +73,11 @@ test::TestCallbackReceiver<> ready_callback_; test::ValueCallbackReceiver<FidoReturnCode> error_callback_; test::VirtualFidoDeviceFactory virtual_device_factory_; + +#if defined(OS_WIN) + device::ScopedFakeWinWebAuthnApi win_webauthn_api_ = + device::ScopedFakeWinWebAuthnApi::MakeUnavailable(); +#endif // defined(OS_WIN) }; // Tests bio enrollment handler against device without PIN support.
diff --git a/device/fido/ble_adapter_manager_unittest.cc b/device/fido/ble_adapter_manager_unittest.cc index d004f68..572da48 100644 --- a/device/fido/ble_adapter_manager_unittest.cc +++ b/device/fido/ble_adapter_manager_unittest.cc
@@ -11,6 +11,7 @@ #include "base/bind_helpers.h" #include "base/run_loop.h" #include "base/test/scoped_task_environment.h" +#include "build/build_config.h" #include "device/bluetooth/bluetooth_adapter_factory.h" #include "device/bluetooth/test/mock_bluetooth_adapter.h" #include "device/bluetooth/test/mock_bluetooth_device.h" @@ -21,6 +22,10 @@ #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" +#if defined(OS_WIN) +#include "device/fido/win/fake_webauthn_api.h" +#endif // defined(OS_WIN) + namespace device { namespace { @@ -137,6 +142,12 @@ std::make_unique<MockObserver>(); std::unique_ptr<FidoDiscoveryFactory> fido_discovery_factory_ = std::make_unique<FidoDiscoveryFactory>(); + +#if defined(OS_WIN) + device::ScopedFakeWinWebAuthnApi win_webauthn_api_ = + device::ScopedFakeWinWebAuthnApi::MakeUnavailable(); +#endif // defined(OS_WIN) + std::unique_ptr<FakeFidoRequestHandlerBase> fake_request_handler_ = std::make_unique<FakeFidoRequestHandlerBase>( mock_observer_.get(),
diff --git a/device/fido/credential_management_handler_unittest.cc b/device/fido/credential_management_handler_unittest.cc index 4604d65..1d2db36 100644 --- a/device/fido/credential_management_handler_unittest.cc +++ b/device/fido/credential_management_handler_unittest.cc
@@ -9,6 +9,7 @@ #include "base/bind.h" #include "base/strings/strcat.h" #include "base/test/scoped_task_environment.h" +#include "build/build_config.h" #include "device/fido/credential_management.h" #include "device/fido/fido_constants.h" #include "device/fido/fido_request_handler_base.h" @@ -18,6 +19,10 @@ #include "device/fido/virtual_fido_device_factory.h" #include "testing/gtest/include/gtest/gtest.h" +#if defined(OS_WIN) +#include "device/fido/win/fake_webauthn_api.h" +#endif // defined(OS_WIN) + namespace device { namespace { @@ -61,6 +66,11 @@ test::ValueCallbackReceiver<CtapDeviceResponseCode> delete_callback_; test::ValueCallbackReceiver<FidoReturnCode> finished_callback_; test::VirtualFidoDeviceFactory virtual_device_factory_; + +#if defined(OS_WIN) + device::ScopedFakeWinWebAuthnApi win_webauthn_api_ = + device::ScopedFakeWinWebAuthnApi::MakeUnavailable(); +#endif // defined(OS_WIN) }; TEST_F(CredentialManagementHandlerTest, Test) {
diff --git a/device/fido/fido_request_handler_unittest.cc b/device/fido/fido_request_handler_unittest.cc index e5196d5..835a8a2cc 100644 --- a/device/fido/fido_request_handler_unittest.cc +++ b/device/fido/fido_request_handler_unittest.cc
@@ -333,6 +333,11 @@ test::FakeFidoDiscovery* discovery_; test::FakeFidoDiscovery* ble_discovery_; FakeHandlerCallbackReceiver cb_; + +#if defined(OS_WIN) + device::ScopedFakeWinWebAuthnApi win_webauthn_api_ = + device::ScopedFakeWinWebAuthnApi::MakeUnavailable(); +#endif // defined(OS_WIN) }; TEST_F(FidoRequestHandlerTest, TestSingleDeviceSuccess) { @@ -705,24 +710,28 @@ #if defined(OS_WIN) TEST_F(FidoRequestHandlerTest, TransportAvailabilityOfWindowsAuthenticator) { - ScopedFakeWinWebAuthnApi scoped_fake_win_webauthn_api; - scoped_fake_win_webauthn_api.set_available(true); + for (const bool api_available : {false, true}) { + SCOPED_TRACE(::testing::Message() << "api_available=" << api_available); + win_webauthn_api_.set_available(api_available); - TestObserver observer; - ForgeNextHidDiscovery(); - EmptyRequestHandler request_handler( - {FidoTransportProtocol::kUsbHumanInterfaceDevice}, - &fake_discovery_factory_); - request_handler.SetPlatformAuthenticatorOrMarkUnavailable(base::nullopt); - request_handler.set_observer(&observer); - scoped_task_environment_.FastForwardUntilNoTasksRemain(); + TestObserver observer; + ForgeNextHidDiscovery(); + EmptyRequestHandler request_handler( + {FidoTransportProtocol::kUsbHumanInterfaceDevice}, + &fake_discovery_factory_); + request_handler.SetPlatformAuthenticatorOrMarkUnavailable(base::nullopt); + request_handler.set_observer(&observer); + scoped_task_environment_.FastForwardUntilNoTasksRemain(); - auto transport_availability_info = - observer.WaitForTransportAvailabilityInfo(); - EXPECT_TRUE(transport_availability_info.available_transports.empty()); - EXPECT_TRUE(transport_availability_info.has_win_native_api_authenticator); - EXPECT_EQ("WinWebAuthnApiAuthenticator", - transport_availability_info.win_native_api_authenticator_id); + auto transport_availability_info = + observer.WaitForTransportAvailabilityInfo(); + EXPECT_EQ(transport_availability_info.available_transports.empty(), + api_available); + EXPECT_EQ(transport_availability_info.has_win_native_api_authenticator, + api_available); + EXPECT_EQ(transport_availability_info.win_native_api_authenticator_id, + api_available ? "WinWebAuthnApiAuthenticator" : ""); + } } #endif // defined(OS_WIN)
diff --git a/device/fido/get_assertion_handler_unittest.cc b/device/fido/get_assertion_handler_unittest.cc index 3744659b..bb2accd 100644 --- a/device/fido/get_assertion_handler_unittest.cc +++ b/device/fido/get_assertion_handler_unittest.cc
@@ -189,6 +189,11 @@ TestGetAssertionRequestCallback get_assertion_cb_; base::flat_set<FidoTransportProtocol> supported_transports_ = GetAllTransportProtocols(); + +#if defined(OS_WIN) + device::ScopedFakeWinWebAuthnApi win_webauthn_api_ = + device::ScopedFakeWinWebAuthnApi::MakeUnavailable(); +#endif // defined(OS_WIN) }; TEST_F(FidoGetAssertionHandlerTest, TransportAvailabilityInfo) { @@ -788,6 +793,11 @@ TEST(GetAssertionRequestHandlerTest, IncorrectTransportType) { base::test::ScopedTaskEnvironment scoped_task_environment{ base::test::ScopedTaskEnvironment::TimeSource::MOCK_TIME}; +#if defined(OS_WIN) + device::ScopedFakeWinWebAuthnApi win_webauthn_api_ = + device::ScopedFakeWinWebAuthnApi::MakeUnavailable(); +#endif // defined(OS_WIN) + device::test::VirtualFidoDeviceFactory virtual_device_factory; virtual_device_factory.SetSupportedProtocol(device::ProtocolVersion::kCtap2); ASSERT_TRUE(virtual_device_factory.mutable_state()->InjectRegistration(
diff --git a/device/fido/make_credential_handler_unittest.cc b/device/fido/make_credential_handler_unittest.cc index a6f0336..e391fd0 100644 --- a/device/fido/make_credential_handler_unittest.cc +++ b/device/fido/make_credential_handler_unittest.cc
@@ -9,6 +9,7 @@ #include "base/bind_helpers.h" #include "base/test/scoped_task_environment.h" #include "base/threading/thread_task_runner_handle.h" +#include "build/build_config.h" #include "components/cbor/reader.h" #include "components/cbor/values.h" #include "device/bluetooth/bluetooth_adapter_factory.h" @@ -32,6 +33,10 @@ #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" +#if defined(OS_WIN) +#include "device/fido/win/fake_webauthn_api.h" +#endif // defined(OS_WIN) + using ::testing::_; using ::testing::DoAll; using ::testing::Invoke; @@ -153,6 +158,11 @@ TestMakeCredentialRequestCallback cb_; base::flat_set<FidoTransportProtocol> supported_transports_ = GetAllTransportProtocols(); + +#if defined(OS_WIN) + device::ScopedFakeWinWebAuthnApi win_webauthn_api_ = + device::ScopedFakeWinWebAuthnApi::MakeUnavailable(); +#endif // defined(OS_WIN) }; TEST_F(FidoMakeCredentialHandlerTest, TransportAvailabilityInfo) {
diff --git a/device/fido/win/fake_webauthn_api.cc b/device/fido/win/fake_webauthn_api.cc index 1943e20..1a5dd16f 100644 --- a/device/fido/win/fake_webauthn_api.cc +++ b/device/fido/win/fake_webauthn_api.cc
@@ -123,4 +123,11 @@ WinWebAuthnApi::ClearDefaultForTesting(); } +// static +ScopedFakeWinWebAuthnApi ScopedFakeWinWebAuthnApi::MakeUnavailable() { + ScopedFakeWinWebAuthnApi api; + api.set_available(false); + return api; +} + } // namespace device
diff --git a/device/fido/win/fake_webauthn_api.h b/device/fido/win/fake_webauthn_api.h index d0e8fcdb..be9c576 100644 --- a/device/fido/win/fake_webauthn_api.h +++ b/device/fido/win/fake_webauthn_api.h
@@ -63,10 +63,21 @@ }; // ScopedFakeWinWebAuthnApi overrides the value returned -// by WinWebAuthnApi::GetDefault with itself for the duration of its +// by WinWebAuthnApi::GetDefault() with itself for the duration of its // lifetime. class ScopedFakeWinWebAuthnApi : public FakeWinWebAuthnApi { public: + // MakeUnavailable() returns a ScopedFakeWinWebAuthnApi that simulates a + // system where the native WebAuthn API is unavailable. + // + // Tests that instantiate a FidoDiscoveryFactory and FidoRequestHandler + // should instantiate a ScopedFakeWinWebAuthnApi with this method to avoid + // invoking the real Windows WebAuthn API on systems where it is available. + // Note that individual tests can call set_available(true) prior to + // instantiating the FidoRequestHandler in order to make the fake simulate an + // available API. + static ScopedFakeWinWebAuthnApi MakeUnavailable(); + ScopedFakeWinWebAuthnApi(); ~ScopedFakeWinWebAuthnApi() override; };
diff --git a/device/gamepad/abstract_haptic_gamepad.cc b/device/gamepad/abstract_haptic_gamepad.cc index 89612485..368091ec 100644 --- a/device/gamepad/abstract_haptic_gamepad.cc +++ b/device/gamepad/abstract_haptic_gamepad.cc
@@ -24,6 +24,8 @@ void AbstractHapticGamepad::Shutdown() { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); + if (is_shut_down_) + return; if (playing_effect_callback_) { sequence_id_++; SetZeroVibration();
diff --git a/docs/updating_clang.md b/docs/updating_clang.md index adff33f..0109854 100644 --- a/docs/updating_clang.md +++ b/docs/updating_clang.md
@@ -30,9 +30,8 @@ gs://chromium-browser-clang/$x/translation_unit-$rev.tgz ; \ gsutil.py cp -n -a public-read gs://chromium-browser-clang-staging/$x/llvm-code-coverage-$rev.tgz \ gs://chromium-browser-clang/$x/llvm-code-coverage-$rev.tgz ; \ - done - $ gsutil.py cp -n -a public-read gs://chromium-browser-clang-staging/Mac/lld-$rev.tgz \ - gs://chromium-browser-clang/Mac/lld-$rev.tgz + done && gsutil.py cp -n -a public-read gs://chromium-browser-clang-staging/Mac/lld-$rev.tgz \ + gs://chromium-browser-clang/Mac/lld-$rev.tgz ``` 1. Run the goma package update script to push these packages to goma. If you do
diff --git a/extensions/browser/api/feedback_private/log_source_access_manager.cc b/extensions/browser/api/feedback_private/log_source_access_manager.cc index f667c9c..2b9001c 100644 --- a/extensions/browser/api/feedback_private/log_source_access_manager.cc +++ b/extensions/browser/api/feedback_private/log_source_access_manager.cc
@@ -81,7 +81,8 @@ base::TaskShutdownBehavior::CONTINUE_ON_SHUTDOWN})), anonymizer_container_( base::MakeRefCounted<feedback::AnonymizerToolContainer>( - task_runner_for_anonymizer_)), + task_runner_for_anonymizer_, + /* first_party_extension_ids= */ nullptr)), weak_factory_(this) {} LogSourceAccessManager::~LogSourceAccessManager() {}
diff --git a/extensions/browser/app_window/app_window.cc b/extensions/browser/app_window/app_window.cc index 33758e7..bee0690 100644 --- a/extensions/browser/app_window/app_window.cc +++ b/extensions/browser/app_window/app_window.cc
@@ -729,7 +729,9 @@ ExtensionsBrowserClient::Get()->IsScreensaverInDemoMode( extension_id())) && !IntersectsWithTaskbar()) { - native_app_window_->SetAlwaysOnTop(always_on_top); + native_app_window_->SetZOrderLevel(always_on_top + ? ui::ZOrderLevel::kFloatingWindow + : ui::ZOrderLevel::kNormal); } OnNativeWindowChanged(); @@ -854,18 +856,19 @@ void AppWindow::UpdateNativeAlwaysOnTop() { DCHECK(cached_always_on_top_); - bool is_on_top = native_app_window_->IsAlwaysOnTop(); + bool is_on_top = + native_app_window_->GetZOrderLevel() == ui::ZOrderLevel::kFloatingWindow; bool fullscreen = IsFullscreen(); bool intersects_taskbar = IntersectsWithTaskbar(); if (is_on_top && (fullscreen || intersects_taskbar)) { // When entering fullscreen or overlapping the taskbar, ensure windows are // not always-on-top. - native_app_window_->SetAlwaysOnTop(false); + native_app_window_->SetZOrderLevel(ui::ZOrderLevel::kNormal); } else if (!is_on_top && !fullscreen && !intersects_taskbar) { // When exiting fullscreen and moving away from the taskbar, reinstate // always-on-top. - native_app_window_->SetAlwaysOnTop(true); + native_app_window_->SetZOrderLevel(ui::ZOrderLevel::kFloatingWindow); } }
diff --git a/extensions/browser/app_window/app_window_interactive_uitest.cc b/extensions/browser/app_window/app_window_interactive_uitest.cc index 44b46e6..d3e2a6a7 100644 --- a/extensions/browser/app_window/app_window_interactive_uitest.cc +++ b/extensions/browser/app_window/app_window_interactive_uitest.cc
@@ -13,29 +13,35 @@ class AppWindowTest : public PlatformAppBrowserTest { protected: void CheckAlwaysOnTopToFullscreen(AppWindow* window) { - ASSERT_TRUE(window->GetBaseWindow()->IsAlwaysOnTop()); + ASSERT_EQ(ui::ZOrderLevel::kFloatingWindow, + window->GetBaseWindow()->GetZOrderLevel()); // The always-on-top property should be temporarily disabled when the window // enters fullscreen. window->Fullscreen(); - EXPECT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); // From the API's point of view, the always-on-top property is enabled. EXPECT_TRUE(window->IsAlwaysOnTop()); // The always-on-top property is restored when the window exits fullscreen. window->Restore(); - EXPECT_TRUE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + window->GetBaseWindow()->GetZOrderLevel()); } void CheckNormalToFullscreen(AppWindow* window) { // If the always-on-top property is false, it should remain this way when // entering and exiting fullscreen mode. - ASSERT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + ASSERT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); window->Fullscreen(); - EXPECT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); window->Restore(); - EXPECT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); } void CheckFullscreenToAlwaysOnTop(AppWindow* window) { @@ -44,14 +50,16 @@ // Now enable always-on-top at runtime and ensure the property does not get // applied immediately because the window is in fullscreen mode. window->SetAlwaysOnTop(true); - EXPECT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); // From the API's point of view, the always-on-top property is enabled. EXPECT_TRUE(window->IsAlwaysOnTop()); // Ensure the always-on-top property is applied when exiting fullscreen. window->Restore(); - EXPECT_TRUE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + window->GetBaseWindow()->GetZOrderLevel()); } }; @@ -147,13 +155,15 @@ ASSERT_TRUE(window); EXPECT_TRUE(window->GetBaseWindow()->IsFullscreenOrPending()); - EXPECT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); // From the API's point of view, the always-on-top property is enabled. EXPECT_TRUE(window->IsAlwaysOnTop()); window->Restore(); - EXPECT_TRUE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, + window->GetBaseWindow()->GetZOrderLevel()); CloseAppWindow(window); } @@ -174,13 +184,16 @@ // Disable always-on-top while in fullscreen mode. window->Fullscreen(); - EXPECT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); window->SetAlwaysOnTop(false); - EXPECT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); // Ensure that always-on-top remains disabled. window->Restore(); - EXPECT_FALSE(window->GetBaseWindow()->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, + window->GetBaseWindow()->GetZOrderLevel()); CloseAppWindow(window); }
diff --git a/extensions/components/native_app_window/native_app_window_views.cc b/extensions/components/native_app_window/native_app_window_views.cc index 35aa2fb8..f1b3c80 100644 --- a/extensions/components/native_app_window/native_app_window_views.cc +++ b/extensions/components/native_app_window/native_app_window_views.cc
@@ -63,7 +63,8 @@ // Stub implementation. See also ChromeNativeAppWindowViews. views::Widget::InitParams init_params(views::Widget::InitParams::TYPE_WINDOW); init_params.delegate = this; - init_params.keep_on_top = create_params.always_on_top; + if (create_params.always_on_top) + init_params.z_order = ui::ZOrderLevel::kFloatingWindow; widget_->Init(init_params); widget_->CenterWindow( create_params.GetInitialWindowBounds(gfx::Insets()).size()); @@ -163,13 +164,13 @@ widget_->FlashFrame(flash); } -bool NativeAppWindowViews::IsAlwaysOnTop() const { +ui::ZOrderLevel NativeAppWindowViews::GetZOrderLevel() const { // Stub implementation. See also ChromeNativeAppWindowViews. - return widget_->IsAlwaysOnTop(); + return widget_->GetZOrderLevel(); } -void NativeAppWindowViews::SetAlwaysOnTop(bool always_on_top) { - widget_->SetAlwaysOnTop(always_on_top); +void NativeAppWindowViews::SetZOrderLevel(ui::ZOrderLevel order) { + widget_->SetZOrderLevel(order); } gfx::NativeView NativeAppWindowViews::GetHostView() const {
diff --git a/extensions/components/native_app_window/native_app_window_views.h b/extensions/components/native_app_window/native_app_window_views.h index a537c42..7682a6ae 100644 --- a/extensions/components/native_app_window/native_app_window_views.h +++ b/extensions/components/native_app_window/native_app_window_views.h
@@ -85,8 +85,8 @@ void Restore() override; void SetBounds(const gfx::Rect& bounds) override; void FlashFrame(bool flash) override; - bool IsAlwaysOnTop() const override; - void SetAlwaysOnTop(bool always_on_top) override; + ui::ZOrderLevel GetZOrderLevel() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; // WidgetDelegate implementation. void OnWidgetMove() override;
diff --git a/extensions/shell/browser/shell_native_app_window.cc b/extensions/shell/browser/shell_native_app_window.cc index 33b3bf5..dd836d3 100644 --- a/extensions/shell/browser/shell_native_app_window.cc +++ b/extensions/shell/browser/shell_native_app_window.cc
@@ -72,11 +72,11 @@ NOTIMPLEMENTED(); } -bool ShellNativeAppWindow::IsAlwaysOnTop() const { - return false; +ui::ZOrderLevel ShellNativeAppWindow::GetZOrderLevel() const { + return ui::ZOrderLevel::kNormal; } -void ShellNativeAppWindow::SetAlwaysOnTop(bool always_on_top) { +void ShellNativeAppWindow::SetZOrderLevel(ui::ZOrderLevel level) { NOTIMPLEMENTED(); }
diff --git a/extensions/shell/browser/shell_native_app_window.h b/extensions/shell/browser/shell_native_app_window.h index a00a052..b25bafb3 100644 --- a/extensions/shell/browser/shell_native_app_window.h +++ b/extensions/shell/browser/shell_native_app_window.h
@@ -32,8 +32,8 @@ void Minimize() override; void Restore() override; void FlashFrame(bool flash) override; - bool IsAlwaysOnTop() const override; - void SetAlwaysOnTop(bool always_on_top) override; + ui::ZOrderLevel GetZOrderLevel() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; // web_modal::ModalDialogHost overrides: gfx::NativeView GetHostView() const override;
diff --git a/extensions/shell/browser/system_logs/shell_system_logs_fetcher.cc b/extensions/shell/browser/system_logs/shell_system_logs_fetcher.cc index afe5d054..1458d88e 100644 --- a/extensions/shell/browser/system_logs/shell_system_logs_fetcher.cc +++ b/extensions/shell/browser/system_logs/shell_system_logs_fetcher.cc
@@ -12,7 +12,9 @@ SystemLogsFetcher* BuildShellSystemLogsFetcher( content::BrowserContext* browser_context) { // Deletes itself after Fetch() is completes. - SystemLogsFetcher* fetcher = new SystemLogsFetcher(true /* scrub_data */); + SystemLogsFetcher* fetcher = + new SystemLogsFetcher(/* scrub_data= */ true, + /* first_party_extension_ids= */ nullptr); fetcher->AddSource(std::make_unique<BasicLogSource>(browser_context)); return fetcher; }
diff --git a/google_apis/gaia/oauth2_api_call_flow_unittest.cc b/google_apis/gaia/oauth2_api_call_flow_unittest.cc index cd7a481..1a9ba79 100644 --- a/google_apis/gaia/oauth2_api_call_flow_unittest.cc +++ b/google_apis/gaia/oauth2_api_call_flow_unittest.cc
@@ -10,8 +10,8 @@ #include <string> #include <utility> -#include "base/message_loop/message_loop.h" #include "base/run_loop.h" +#include "base/test/scoped_task_environment.h" #include "base/time/time.h" #include "google_apis/gaia/gaia_urls.h" #include "google_apis/gaia/google_service_auth_error.h" @@ -100,7 +100,7 @@ AddFetchResult(url, succeeds, status, std::string()); } - base::MessageLoop message_loop_; + base::test::ScopedTaskEnvironment scoped_task_environment_; network::TestURLLoaderFactory test_url_loader_factory_; scoped_refptr<network::SharedURLLoaderFactory> shared_factory_; StrictMock<MockApiCallFlow> flow_;
diff --git a/gpu/command_buffer/service/shared_image_factory.cc b/gpu/command_buffer/service/shared_image_factory.cc index ae3be77e..648a3cb 100644 --- a/gpu/command_buffer/service/shared_image_factory.cc +++ b/gpu/command_buffer/service/shared_image_factory.cc
@@ -152,7 +152,9 @@ // TODO(ericrk): Make this generic in the future. bool allow_legacy_mailbox = false; SharedImageBackingFactory* factory = nullptr; - if (!using_vulkan_) { + if (backing_factory_for_testing_) { + factory = backing_factory_for_testing_; + } else if (!using_vulkan_) { allow_legacy_mailbox = true; factory = gl_backing_factory_.get(); } else { @@ -262,6 +264,11 @@ return true; } +void SharedImageFactory::RegisterSharedImageBackingFactoryForTesting( + SharedImageBackingFactory* factory) { + backing_factory_for_testing_ = factory; +} + bool SharedImageFactory::IsSharedBetweenThreads(uint32_t usage) { // If |shared_image_manager_| is thread safe, it means the display is running // on a separate thread (which uses a separate GL context or VkDeviceQueue). @@ -273,6 +280,9 @@ uint32_t usage, bool* allow_legacy_mailbox, gfx::GpuMemoryBufferType gmb_type) { + if (backing_factory_for_testing_) + return backing_factory_for_testing_; + bool using_dawn = usage & SHARED_IMAGE_USAGE_WEBGPU; bool vulkan_usage = using_vulkan_ && (usage & SHARED_IMAGE_USAGE_DISPLAY); bool gl_usage = usage & SHARED_IMAGE_USAGE_GLES2;
diff --git a/gpu/command_buffer/service/shared_image_factory.h b/gpu/command_buffer/service/shared_image_factory.h index 9587dffc..eacfd41 100644 --- a/gpu/command_buffer/service/shared_image_factory.h +++ b/gpu/command_buffer/service/shared_image_factory.h
@@ -97,6 +97,9 @@ bool RegisterBacking(std::unique_ptr<SharedImageBacking> backing, bool allow_legacy_mailbox); + void RegisterSharedImageBackingFactoryForTesting( + SharedImageBackingFactory* factory); + private: bool IsSharedBetweenThreads(uint32_t usage); SharedImageBackingFactory* GetFactoryByUsage( @@ -128,6 +131,8 @@ // Used for creating DXGI Swap Chain. std::unique_ptr<SwapChainFactoryDXGI> swap_chain_factory_; #endif // OS_WIN + + SharedImageBackingFactory* backing_factory_for_testing_ = nullptr; }; class GPU_GLES2_EXPORT SharedImageRepresentationFactory {
diff --git a/gpu/ipc/common/gpu_memory_buffer_impl_native_pixmap.cc b/gpu/ipc/common/gpu_memory_buffer_impl_native_pixmap.cc index 86a63c1..10b67c9d 100644 --- a/gpu/ipc/common/gpu_memory_buffer_impl_native_pixmap.cc +++ b/gpu/ipc/common/gpu_memory_buffer_impl_native_pixmap.cc
@@ -87,6 +87,8 @@ bool GpuMemoryBufferImplNativePixmap::Map() { DCHECK(!mapped_); + DCHECK_EQ(gfx::NumberOfPlanesForBufferFormat(GetFormat()), + handle_.planes.size()); mapped_ = pixmap_->Map(); return mapped_; }
diff --git a/ios/chrome/app/BUILD.gn b/ios/chrome/app/BUILD.gn index 32cc9d3..426d1a02 100644 --- a/ios/chrome/app/BUILD.gn +++ b/ios/chrome/app/BUILD.gn
@@ -19,12 +19,18 @@ source_set("app") { configs += [ "//build/config/compiler:enable_arc" ] sources = [ + "app_startup_parameters.h", + "app_startup_parameters.mm", "deferred_initialization_runner.h", "deferred_initialization_runner.mm", ] deps = [ "//base", + "//ios/chrome/browser", + "//ios/chrome/browser/payments:constants", + "//net", + "//url", ] libs = [ "Foundation.framework" ] @@ -34,6 +40,7 @@ configs += [ "//build/config/compiler:enable_arc" ] testonly = true sources = [ + "app_startup_parameters_unittest.mm", "chrome_overlay_window_testing.h", "deferred_initialization_runner_unittest.mm", "firebase_utils_unittest.mm",
diff --git a/ios/chrome/browser/app_startup_parameters.h b/ios/chrome/app/app_startup_parameters.h similarity index 93% rename from ios/chrome/browser/app_startup_parameters.h rename to ios/chrome/app/app_startup_parameters.h index c7a5f16..c50efa4 100644 --- a/ios/chrome/browser/app_startup_parameters.h +++ b/ios/chrome/app/app_startup_parameters.h
@@ -2,8 +2,8 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef IOS_CHROME_BROWSER_APP_STARTUP_PARAMETERS_H_ -#define IOS_CHROME_BROWSER_APP_STARTUP_PARAMETERS_H_ +#ifndef IOS_CHROME_APP_APP_STARTUP_PARAMETERS_H_ +#define IOS_CHROME_APP_APP_STARTUP_PARAMETERS_H_ #import <Foundation/Foundation.h> @@ -62,4 +62,4 @@ @end -#endif // IOS_CHROME_BROWSER_APP_STARTUP_PARAMETERS_H_ +#endif // IOS_CHROME_APP_APP_STARTUP_PARAMETERS_H_
diff --git a/ios/chrome/browser/app_startup_parameters.mm b/ios/chrome/app/app_startup_parameters.mm similarity index 97% rename from ios/chrome/browser/app_startup_parameters.mm rename to ios/chrome/app/app_startup_parameters.mm index 11ba0724..ec733641 100644 --- a/ios/chrome/browser/app_startup_parameters.mm +++ b/ios/chrome/app/app_startup_parameters.mm
@@ -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 "ios/chrome/browser/app_startup_parameters.h" +#import "ios/chrome/app/app_startup_parameters.h" #include "base/stl_util.h" #include "ios/chrome/browser/chrome_url_constants.h"
diff --git a/ios/chrome/browser/app_startup_parameters_unittest.mm b/ios/chrome/app/app_startup_parameters_unittest.mm similarity index 90% rename from ios/chrome/browser/app_startup_parameters_unittest.mm rename to ios/chrome/app/app_startup_parameters_unittest.mm index d02f09cb..dc4c110 100644 --- a/ios/chrome/browser/app_startup_parameters_unittest.mm +++ b/ios/chrome/app/app_startup_parameters_unittest.mm
@@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#include "ios/chrome/browser/app_startup_parameters.h" +#include "ios/chrome/app/app_startup_parameters.h" #include "base/stl_util.h" #include "testing/gtest/include/gtest/gtest.h" @@ -26,10 +26,14 @@ TEST_F(AppStartupParametersTest, QueryParametersPaymentRequest) { const UniversalLinkDecodeTestCase test_cases[] = { { - GURL("https://goo.gl/ioschrome/"), {}, false, + GURL("https://goo.gl/ioschrome/"), + {}, + false, }, { - GURL("https://goo.gl/ioschrome?payment-request-id"), {}, false, + GURL("https://goo.gl/ioschrome?payment-request-id"), + {}, + false, }, { GURL("https://goo.gl/ioschrome?payment-request-id=092831-af18l-324"
diff --git a/ios/chrome/app/application_delegate/BUILD.gn b/ios/chrome/app/application_delegate/BUILD.gn index ea798dd8..3944bc9b 100644 --- a/ios/chrome/app/application_delegate/BUILD.gn +++ b/ios/chrome/app/application_delegate/BUILD.gn
@@ -168,6 +168,7 @@ ":application_delegate_internal", "//base", "//base/test:test_support", + "//ios/chrome/app", "//ios/chrome/app:app_internal", "//ios/chrome/app:mode", "//ios/chrome/browser",
diff --git a/ios/chrome/app/application_delegate/app_state_unittest.mm b/ios/chrome/app/application_delegate/app_state_unittest.mm index 1663d522..4ae10a6 100644 --- a/ios/chrome/app/application_delegate/app_state_unittest.mm +++ b/ios/chrome/app/application_delegate/app_state_unittest.mm
@@ -9,6 +9,7 @@ #include "base/bind.h" #include "base/ios/block_types.h" #include "base/mac/scoped_block.h" +#import "ios/chrome/app/app_startup_parameters.h" #import "ios/chrome/app/application_delegate/app_navigation.h" #import "ios/chrome/app/application_delegate/app_state_testing.h" #import "ios/chrome/app/application_delegate/browser_launcher.h" @@ -21,7 +22,6 @@ #import "ios/chrome/app/application_delegate/user_activity_handler.h" #import "ios/chrome/app/main_application_delegate.h" #import "ios/chrome/app/startup/content_suggestions_scheduler_notifications.h" -#import "ios/chrome/browser/app_startup_parameters.h" #include "ios/chrome/browser/browser_state/test_chrome_browser_state.h" #include "ios/chrome/browser/chrome_url_constants.h" #import "ios/chrome/browser/device_sharing/device_sharing_manager.h"
diff --git a/ios/chrome/app/application_delegate/fake_startup_information.mm b/ios/chrome/app/application_delegate/fake_startup_information.mm index 03a8b00..612466a 100644 --- a/ios/chrome/app/application_delegate/fake_startup_information.mm +++ b/ios/chrome/app/application_delegate/fake_startup_information.mm
@@ -5,7 +5,7 @@ #include "ios/chrome/app/application_delegate/fake_startup_information.h" #include "base/time/time.h" -#include "ios/chrome/browser/app_startup_parameters.h" +#import "ios/chrome/app/app_startup_parameters.h" #if !defined(__has_feature) || !__has_feature(objc_arc) #error "This file requires ARC support."
diff --git a/ios/chrome/app/application_delegate/tab_opening.h b/ios/chrome/app/application_delegate/tab_opening.h index 202dd57..96e85829 100644 --- a/ios/chrome/app/application_delegate/tab_opening.h +++ b/ios/chrome/app/application_delegate/tab_opening.h
@@ -6,8 +6,8 @@ #define IOS_CHROME_APP_APPLICATION_DELEGATE_TAB_OPENING_H_ #include "base/ios/block_types.h" +#import "ios/chrome/app/app_startup_parameters.h" #include "ios/chrome/app/application_mode.h" -#import "ios/chrome/browser/app_startup_parameters.h" #include "ui/base/page_transition_types.h" @class AppState;
diff --git a/ios/chrome/app/application_delegate/user_activity_handler.mm b/ios/chrome/app/application_delegate/user_activity_handler.mm index 785f5da..f7b45d0 100644 --- a/ios/chrome/app/application_delegate/user_activity_handler.mm +++ b/ios/chrome/app/application_delegate/user_activity_handler.mm
@@ -14,13 +14,13 @@ #include "base/strings/sys_string_conversions.h" #include "components/handoff/handoff_utility.h" #include "components/search_engines/template_url_service.h" +#import "ios/chrome/app/app_startup_parameters.h" #import "ios/chrome/app/application_delegate/startup_information.h" #import "ios/chrome/app/application_delegate/tab_opening.h" #include "ios/chrome/app/application_mode.h" #import "ios/chrome/app/spotlight/actions_spotlight_manager.h" #import "ios/chrome/app/spotlight/spotlight_util.h" #include "ios/chrome/app/startup/chrome_app_startup_parameters.h" -#include "ios/chrome/browser/app_startup_parameters.h" #include "ios/chrome/browser/chrome_url_constants.h" #include "ios/chrome/browser/metrics/first_user_action_recorder.h" #include "ios/chrome/browser/search_engines/template_url_service_factory.h"
diff --git a/ios/chrome/app/application_delegate/user_activity_handler_unittest.mm b/ios/chrome/app/application_delegate/user_activity_handler_unittest.mm index e78d98d..c087b51 100644 --- a/ios/chrome/app/application_delegate/user_activity_handler_unittest.mm +++ b/ios/chrome/app/application_delegate/user_activity_handler_unittest.mm
@@ -13,6 +13,7 @@ #include "base/strings/sys_string_conversions.h" #include "base/test/scoped_command_line.h" #include "components/handoff/handoff_utility.h" +#import "ios/chrome/app/app_startup_parameters.h" #include "ios/chrome/app/application_delegate/fake_startup_information.h" #include "ios/chrome/app/application_delegate/mock_tab_opener.h" #include "ios/chrome/app/application_delegate/startup_information.h" @@ -21,7 +22,6 @@ #include "ios/chrome/app/main_controller.h" #include "ios/chrome/app/spotlight/actions_spotlight_manager.h" #import "ios/chrome/app/spotlight/spotlight_util.h" -#include "ios/chrome/browser/app_startup_parameters.h" #include "ios/chrome/browser/chrome_switches.h" #include "ios/chrome/browser/chrome_url_constants.h" #import "ios/chrome/browser/tabs/tab_model.h"
diff --git a/ios/chrome/app/spotlight/BUILD.gn b/ios/chrome/app/spotlight/BUILD.gn index a5a2c55..f8cd548 100644 --- a/ios/chrome/app/spotlight/BUILD.gn +++ b/ios/chrome/app/spotlight/BUILD.gn
@@ -26,6 +26,7 @@ "//components/favicon_base", "//components/history/core/browser", "//components/suggestions", + "//ios/chrome/app", "//ios/chrome/app/strings", "//ios/chrome/browser", "//ios/chrome/browser/bookmarks",
diff --git a/ios/chrome/app/spotlight/actions_spotlight_manager.mm b/ios/chrome/app/spotlight/actions_spotlight_manager.mm index 153fa99d..5c1844b 100644 --- a/ios/chrome/app/spotlight/actions_spotlight_manager.mm +++ b/ios/chrome/app/spotlight/actions_spotlight_manager.mm
@@ -9,7 +9,7 @@ #include "base/mac/foundation_util.h" #include "base/metrics/histogram_macros.h" #include "base/strings/sys_string_conversions.h" -#include "ios/chrome/browser/app_startup_parameters.h" +#import "ios/chrome/app/app_startup_parameters.h" #include "ios/chrome/common/app_group/app_group_constants.h" #include "ios/chrome/grit/ios_strings.h" #include "net/base/mac/url_conversions.h"
diff --git a/ios/chrome/app/startup/BUILD.gn b/ios/chrome/app/startup/BUILD.gn index 84b0503..f4f7b1e 100644 --- a/ios/chrome/app/startup/BUILD.gn +++ b/ios/chrome/app/startup/BUILD.gn
@@ -51,6 +51,7 @@ "//base", "//components/ntp_snippets", "//components/search_engines:search_engines", + "//ios/chrome/app", "//ios/chrome/browser", "//ios/chrome/browser/browser_state", "//ios/chrome/browser/first_run", @@ -76,6 +77,7 @@ deps = [ ":startup", "//base", + "//ios/chrome/app", "//ios/chrome/browser", "//ios/chrome/common/app_group", "//testing/gtest",
diff --git a/ios/chrome/app/startup/chrome_app_startup_parameters.h b/ios/chrome/app/startup/chrome_app_startup_parameters.h index 4de3a10..3b5cb04 100644 --- a/ios/chrome/app/startup/chrome_app_startup_parameters.h +++ b/ios/chrome/app/startup/chrome_app_startup_parameters.h
@@ -7,7 +7,7 @@ #import <UIKit/UIKit.h> -#import "ios/chrome/browser/app_startup_parameters.h" +#import "ios/chrome/app/app_startup_parameters.h" #import "ios/chrome/browser/first_run/first_run_metrics.h" // Values of the UMA Startup.MobileSessionCallerApp histogram.
diff --git a/ios/chrome/app/startup/chrome_app_startup_parameters_unittest.mm b/ios/chrome/app/startup/chrome_app_startup_parameters_unittest.mm index eb1a586a..824bbe2 100644 --- a/ios/chrome/app/startup/chrome_app_startup_parameters_unittest.mm +++ b/ios/chrome/app/startup/chrome_app_startup_parameters_unittest.mm
@@ -7,7 +7,7 @@ #import <Foundation/Foundation.h> #include "base/strings/stringprintf.h" -#include "ios/chrome/browser/app_startup_parameters.h" +#import "ios/chrome/app/app_startup_parameters.h" #include "ios/chrome/browser/chrome_url_constants.h" #include "ios/chrome/common/app_group/app_group_constants.h" #include "testing/gtest_mac.h"
diff --git a/ios/chrome/browser/BUILD.gn b/ios/chrome/browser/BUILD.gn index ccc170f4..7e0b6e8 100644 --- a/ios/chrome/browser/BUILD.gn +++ b/ios/chrome/browser/BUILD.gn
@@ -25,8 +25,6 @@ source_set("browser") { configs += [ "//build/config/compiler:enable_arc" ] sources = [ - "app_startup_parameters.h", - "app_startup_parameters.mm", "application_context.cc", "application_context.h", "arch_util.cc", @@ -241,7 +239,6 @@ configs += [ "//build/config/compiler:enable_arc" ] testonly = true sources = [ - "app_startup_parameters_unittest.mm", "browser_about_rewriter_unittest.cc", "chrome_browser_provider_observer_bridge_unittest.mm", "chrome_url_util_unittest.mm",
diff --git a/ios/chrome/browser/infobars/BUILD.gn b/ios/chrome/browser/infobars/BUILD.gn index fcbde61..5ad5e83e 100644 --- a/ios/chrome/browser/infobars/BUILD.gn +++ b/ios/chrome/browser/infobars/BUILD.gn
@@ -42,7 +42,6 @@ "infobar_badge_tab_helper.h", "infobar_badge_tab_helper.mm", "infobar_badge_tab_helper_delegate.h", - "legacy_infobar_badge_tab_helper_delegate.h", ] deps = [ ":infobars",
diff --git a/ios/chrome/browser/infobars/infobar_badge_tab_helper.h b/ios/chrome/browser/infobars/infobar_badge_tab_helper.h index b0af5f4..3bd98ec 100644 --- a/ios/chrome/browser/infobars/infobar_badge_tab_helper.h +++ b/ios/chrome/browser/infobars/infobar_badge_tab_helper.h
@@ -32,11 +32,6 @@ static void CreateForWebState(web::WebState* web_state); // Sets the InfobarBadgeTabHelperDelegate to |delegate|. void SetDelegate(id<InfobarBadgeTabHelperDelegate> delegate); - // Sets the LegacyInfobarBadgeTabHelperDelegate to |delegate|. - // TODO(crbug.com/980800): Remove once BadgeMediator is the receiver of - // |delegate_|. - void SetLegacyDelegate( - id<LegacyInfobarBadgeTabHelperDelegate> legacy_delegate); // Updates Infobar badge for the case where Infobar of |infobar_type| was // accepted. void UpdateBadgeForInfobarAccepted(InfobarType infobar_type); @@ -44,14 +39,6 @@ // Returns all BadgeItems for the TabHelper Webstate. std::vector<id<BadgeItem>> GetInfobarBadgeItems(); - // Returns wheter an Infobar badge is being displayed for the TabHelper - // Webstate. - bool is_infobar_displaying(); - // Returns whether the Infobar badge is accepted. - bool is_badge_accepted(); - // Returns the type of the Infobar being displayed. - InfobarType infobar_type(); - ~InfobarBadgeTabHelper() override; private: @@ -74,15 +61,6 @@ // Holds the state of each displaying badge keyed by its InfobarType. std::unordered_map<InfobarType, InfobarBadgeModel*> infobar_badge_models_; - // Returns wheter an Infobar is being displayed. - bool is_infobar_displaying_; - // The type of the Infobar being displayed. - InfobarType infobar_type_; - // Returns whether the Infobar badge is accepted. - bool is_badge_accepted_ = false; - // Legacy delegate which displays the Infobar badge. - __weak id<LegacyInfobarBadgeTabHelperDelegate> legacy_delegate_ = nil; - WEB_STATE_USER_DATA_KEY_DECL(); DISALLOW_COPY_AND_ASSIGN(InfobarBadgeTabHelper); };
diff --git a/ios/chrome/browser/infobars/infobar_badge_tab_helper.mm b/ios/chrome/browser/infobars/infobar_badge_tab_helper.mm index 0cd581d8..c12768b 100644 --- a/ios/chrome/browser/infobars/infobar_badge_tab_helper.mm +++ b/ios/chrome/browser/infobars/infobar_badge_tab_helper.mm
@@ -8,7 +8,6 @@ #include "ios/chrome/browser/infobars/infobar_badge_model.h" #include "ios/chrome/browser/infobars/infobar_badge_tab_helper_delegate.h" #include "ios/chrome/browser/infobars/infobar_manager_impl.h" -#include "ios/chrome/browser/infobars/legacy_infobar_badge_tab_helper_delegate.h" #import "ios/chrome/browser/ui/infobars/infobar_feature.h" #import "ios/chrome/browser/ui/infobars/infobar_ui_delegate.h" #import "ios/web/public/web_state/web_state.h" @@ -33,23 +32,13 @@ delegate_ = delegate; } -void InfobarBadgeTabHelper::SetLegacyDelegate( - id<LegacyInfobarBadgeTabHelperDelegate> legacy_delegate) { - legacy_delegate_ = legacy_delegate; -} - void InfobarBadgeTabHelper::UpdateBadgeForInfobarAccepted( InfobarType infobar_type) { - if (legacy_delegate_) { - legacy_delegate_.badgeState |= InfobarBadgeStateAccepted; - is_badge_accepted_ = true; - } else { InfobarBadgeModel* badgeModel = [[InfobarBadgeModel alloc] initWithInfobarType:infobar_type accepted:YES]; [delegate_ updateInfobarBadge:badgeModel]; infobar_badge_models_[infobar_type] = badgeModel; - } } std::vector<id<BadgeItem>> InfobarBadgeTabHelper::GetInfobarBadgeItems() { @@ -61,24 +50,12 @@ return infobar_badges_items; } -bool InfobarBadgeTabHelper::is_infobar_displaying() { - return is_infobar_displaying_; -} - -InfobarType InfobarBadgeTabHelper::infobar_type() { - return infobar_type_; -} - -bool InfobarBadgeTabHelper::is_badge_accepted() { - return is_badge_accepted_; -} - InfobarBadgeTabHelper::~InfobarBadgeTabHelper() = default; #pragma mark - Private InfobarBadgeTabHelper::InfobarBadgeTabHelper(web::WebState* web_state) - : infobar_observer_(this), is_infobar_displaying_(false) { + : infobar_observer_(this) { infobars::InfoBarManager* infoBarManager = InfoBarManagerImpl::FromWebState(web_state); if (infoBarManager) { @@ -90,11 +67,6 @@ void InfobarBadgeTabHelper::OnInfoBarAdded(infobars::InfoBar* infobar) { this->UpdateBadgeForInfobar(infobar, true); - // Set the badgeState to None to allow for selecting the infobar when the - // banner is being presented. - if (legacy_delegate_) { - legacy_delegate_.badgeState = InfobarBadgeStateNone; - } } void InfobarBadgeTabHelper::OnInfoBarRemoved(infobars::InfoBar* infobar, @@ -114,12 +86,6 @@ InfoBarIOS* infobar_ios = static_cast<InfoBarIOS*>(infobar); id<InfobarUIDelegate> controller_ = infobar_ios->InfobarUIDelegate(); if (IsInfobarUIRebootEnabled() && controller_.hasBadge) { - if (legacy_delegate_) { - is_infobar_displaying_ = display; - infobar_type_ = controller_.infobarType; - [legacy_delegate_ displayBadge:display type:infobar_type_]; - return; - } InfobarType infobar_type = controller_.infobarType; if (display) { InfobarBadgeModel* new_badge =
diff --git a/ios/chrome/browser/infobars/infobar_badge_tab_helper_unittest.mm b/ios/chrome/browser/infobars/infobar_badge_tab_helper_unittest.mm index 38b3e82..11df463 100644 --- a/ios/chrome/browser/infobars/infobar_badge_tab_helper_unittest.mm +++ b/ios/chrome/browser/infobars/infobar_badge_tab_helper_unittest.mm
@@ -9,10 +9,11 @@ #include "base/test/scoped_task_environment.h" #include "ios/chrome/browser/browser_state/test_chrome_browser_state.h" #include "ios/chrome/browser/infobars/infobar.h" +#include "ios/chrome/browser/infobars/infobar_badge_tab_helper_delegate.h" #include "ios/chrome/browser/infobars/infobar_container_ios.h" #include "ios/chrome/browser/infobars/infobar_manager_impl.h" #import "ios/chrome/browser/infobars/infobar_type.h" -#include "ios/chrome/browser/infobars/legacy_infobar_badge_tab_helper_delegate.h" +#import "ios/chrome/browser/ui/badges/badge_item.h" #import "ios/chrome/browser/ui/infobars/coordinators/infobar_confirm_coordinator.h" #import "ios/chrome/browser/ui/infobars/infobar_badge_ui_delegate.h" #import "ios/chrome/browser/ui/infobars/infobar_container_consumer.h" @@ -30,16 +31,27 @@ // InfobarTabHelperDelegate for testing. @interface InfobarBadgeTabHelperTestDelegate - : NSObject <LegacyInfobarBadgeTabHelperDelegate> + : NSObject <InfobarBadgeTabHelperDelegate> @property(nonatomic, assign) BOOL displayingBadge; -@property(nonatomic, assign) InfobarType infobarType; +@property(nonatomic, assign) BOOL badgeIsTappable; +@property(nonatomic, assign) BOOL badgeIsAccepted; +@property(nonatomic, assign) BadgeType badgeType; @end @implementation InfobarBadgeTabHelperTestDelegate -@synthesize badgeState = _badgeState; -- (void)displayBadge:(BOOL)display type:(InfobarType)infobarType { - self.displayingBadge = display; - self.infobarType = infobarType; +- (void)updateInfobarBadge:(id<BadgeItem>)badgeItem { + self.badgeIsTappable = badgeItem.isTappable; + self.badgeIsAccepted = badgeItem.isAccepted; + self.badgeType = badgeItem.badgeType; +} +- (void)addInfobarBadge:(id<BadgeItem>)badgeItem { + self.displayingBadge = YES; + self.badgeIsTappable = badgeItem.isTappable; + self.badgeIsAccepted = badgeItem.isAccepted; + self.badgeType = badgeItem.badgeType; +} +- (void)removeInfobarBadge:(id<BadgeItem>)badgeItem { + self.displayingBadge = NO; } @end @@ -123,7 +135,7 @@ // Create the InfobarBadgeTabHelper for web_state_ and set its delegate. InfobarBadgeTabHelper::CreateForWebState(&web_state_); - tab_helper()->SetLegacyDelegate(infobar_badge_tab_delegate_); + tab_helper()->SetDelegate(infobar_badge_tab_delegate_); // Configure the fake InfobarContainerCoordinator, and set its baseVC as // rootVC. @@ -140,7 +152,20 @@ infobar_container_model_.reset( new InfoBarContainerIOS(infobar_container_coordinator_, nil)); infobar_container_model_->ChangeInfoBarManager(GetInfobarManager()); + } + ~InfobarBadgeTabHelperTest() override { + if (infobar_container_coordinator_.bannerIsPresenting) { + [infobar_container_coordinator_ dismissBanner]; + EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( + base::test::ios::kWaitForUIElementTimeout, ^bool { + return !infobar_container_coordinator_.bannerIsPresenting; + })); + } + } + + // Adds an Infobar to the InfobarManager. + void AddInfoBar() { // Create and configure the InfobarCoordinator. TestInfoBarDelegate* test_infobar_delegate = new TestInfoBarDelegate(@"Title"); @@ -158,16 +183,6 @@ std::make_unique<InfoBarIOS>(coordinator, std::move(infobar_delegate))); } - ~InfobarBadgeTabHelperTest() override { - if (infobar_container_coordinator_.bannerIsPresenting) { - [infobar_container_coordinator_ dismissBanner]; - EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( - base::test::ios::kWaitForUIElementTimeout, ^bool { - return !infobar_container_coordinator_.bannerIsPresenting; - })); - } - } - // Returns InfobarBadgeTabHelper attached to web_state_. InfobarBadgeTabHelper* tab_helper() { return InfobarBadgeTabHelper::FromWebState(&web_state_); @@ -190,45 +205,40 @@ ScopedKeyWindow scoped_key_window_; }; -// Test each UpdateBadge public method individually. -TEST_F(InfobarBadgeTabHelperTest, TestInfobarBadgeStates) { +// Test the badge state after changes to the state of an Infobar. Infobar badges +// should always be tappable. +TEST_F(InfobarBadgeTabHelperTest, TestInfobarBadgeState) { + EXPECT_FALSE(infobar_badge_tab_delegate_.displayingBadge); + EXPECT_FALSE(infobar_badge_tab_delegate_.badgeIsTappable); + EXPECT_FALSE(infobar_badge_tab_delegate_.badgeIsAccepted); + AddInfoBar(); + EXPECT_TRUE(infobar_badge_tab_delegate_.displayingBadge); + EXPECT_TRUE(infobar_badge_tab_delegate_.badgeIsTappable); + EXPECT_FALSE(infobar_badge_tab_delegate_.badgeIsAccepted); // Test that accepting the Infobar sets the badge to accepted state. tab_helper()->UpdateBadgeForInfobarAccepted( InfobarType::kInfobarTypePasswordSave); - EXPECT_TRUE(infobar_badge_tab_delegate_.badgeState & - InfobarBadgeStateAccepted); + EXPECT_TRUE(infobar_badge_tab_delegate_.badgeIsTappable); + EXPECT_TRUE(infobar_badge_tab_delegate_.badgeIsAccepted); } -// Test the initial badge state once the banner has been presented. -TEST_F(InfobarBadgeTabHelperTest, TestInfobarBadgeStateOnBannerPresentation) { - EXPECT_TRUE(infobar_badge_tab_delegate_.displayingBadge); - EXPECT_FALSE(infobar_badge_tab_delegate_.badgeState); -} - -// Test that the correct InfobarType is set. -TEST_F(InfobarBadgeTabHelperTest, TestInfobarBadgeType) { - EXPECT_EQ(infobar_badge_tab_delegate_.infobarType, - InfobarType::kInfobarTypePasswordSave); -} - -// Tests that the InfobarBadge is still being displayed after dismissing the +// Tests that the InfobarBadge has not been removed after dismissing the // InfobarBanner. TEST_F(InfobarBadgeTabHelperTest, TestInfobarBadgeOnBannerDismissal) { + AddInfoBar(); [infobar_container_coordinator_ dismissBanner]; EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( base::test::ios::kWaitForUIElementTimeout, ^bool { return !infobar_container_coordinator_.bannerIsPresenting; })); EXPECT_TRUE(infobar_badge_tab_delegate_.displayingBadge); - EXPECT_FALSE(infobar_badge_tab_delegate_.badgeState & - InfobarBadgeStateSelected); } // Test that the Accepted badge state remains after dismissing the // InfobarBanner. TEST_F(InfobarBadgeTabHelperTest, TestInfobarBadgeOnBannerAccepted) { - EXPECT_FALSE(infobar_badge_tab_delegate_.badgeState & - InfobarBadgeStateAccepted); + AddInfoBar(); + EXPECT_FALSE(infobar_badge_tab_delegate_.badgeIsAccepted); tab_helper()->UpdateBadgeForInfobarAccepted( InfobarType::kInfobarTypePasswordSave); [infobar_container_coordinator_ dismissBanner]; @@ -236,12 +246,12 @@ base::test::ios::kWaitForUIElementTimeout, ^bool { return !infobar_container_coordinator_.bannerIsPresenting; })); - EXPECT_TRUE(infobar_badge_tab_delegate_.badgeState & - InfobarBadgeStateAccepted); + EXPECT_TRUE(infobar_badge_tab_delegate_.badgeIsAccepted); } // Test that removing the InfobarView doesn't stop displaying the badge. TEST_F(InfobarBadgeTabHelperTest, TestInfobarBadgeOnInfobarViewRemoval) { + AddInfoBar(); [infobar_container_coordinator_ dismissBanner]; EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( base::test::ios::kWaitForUIElementTimeout, ^bool { @@ -253,6 +263,7 @@ // Test that destroying the InfobarView stops displaying the badge. TEST_F(InfobarBadgeTabHelperTest, TestInfobarBadgeOnInfobarDestroyal) { + AddInfoBar(); [infobar_container_coordinator_ dismissBanner]; EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( base::test::ios::kWaitForUIElementTimeout, ^bool {
diff --git a/ios/chrome/browser/infobars/legacy_infobar_badge_tab_helper_delegate.h b/ios/chrome/browser/infobars/legacy_infobar_badge_tab_helper_delegate.h deleted file mode 100644 index ab88661..0000000 --- a/ios/chrome/browser/infobars/legacy_infobar_badge_tab_helper_delegate.h +++ /dev/null
@@ -1,35 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef IOS_CHROME_BROWSER_INFOBARS_LEGACY_INFOBAR_BADGE_TAB_HELPER_DELEGATE_H_ -#define IOS_CHROME_BROWSER_INFOBARS_LEGACY_INFOBAR_BADGE_TAB_HELPER_DELEGATE_H_ - -#import <Foundation/Foundation.h> - -#import "ios/chrome/browser/infobars/infobar_type.h" - -// States for the InfobarBadge. -typedef NS_OPTIONS(NSUInteger, InfobarBadgeState) { - // Default state. e.g. the Banner is being displayed or there's nothing - // presenting. - InfobarBadgeStateNone = 0, - // The InfobarBadge is selected. e.g. The InfobarBadge was tapped so the - // InfobarModal has been presented. - InfobarBadgeStateSelected = 1 << 0, - // The InfobarBadge is accepted. e.g. The Infobar was accepted/confirmed, and - // the Infobar action has taken place. - InfobarBadgeStateAccepted = 1 << 1, -}; - -@protocol LegacyInfobarBadgeTabHelperDelegate - -// Asks the delegate to display or stop displaying a badge. -- (void)displayBadge:(BOOL)display type:(InfobarType)infobarType; - -// Current state for the displayed InfobarBadge. -@property(nonatomic, assign) InfobarBadgeState badgeState; - -@end - -#endif // IOS_CHROME_BROWSER_INFOBARS_LEGACY_INFOBAR_BADGE_TAB_HELPER_DELEGATE_H_
diff --git a/ios/chrome/browser/passwords/ios_chrome_password_manager_driver.h b/ios/chrome/browser/passwords/ios_chrome_password_manager_driver.h index 9e6131675..c04645e 100644 --- a/ios/chrome/browser/passwords/ios_chrome_password_manager_driver.h +++ b/ios/chrome/browser/passwords/ios_chrome_password_manager_driver.h
@@ -74,7 +74,7 @@ override; autofill::AutofillDriver* GetAutofillDriver() override; bool IsMainFrame() const override; - GURL GetLastCommittedURL() const override; + const GURL& GetLastCommittedURL() const override; private: id<PasswordManagerDriverDelegate> delegate_; // (weak)
diff --git a/ios/chrome/browser/passwords/ios_chrome_password_manager_driver.mm b/ios/chrome/browser/passwords/ios_chrome_password_manager_driver.mm index eec5d9b..ae40530 100644 --- a/ios/chrome/browser/passwords/ios_chrome_password_manager_driver.mm +++ b/ios/chrome/browser/passwords/ios_chrome_password_manager_driver.mm
@@ -94,6 +94,6 @@ return true; } -GURL IOSChromePasswordManagerDriver::GetLastCommittedURL() const { +const GURL& IOSChromePasswordManagerDriver::GetLastCommittedURL() const { return delegate_.lastCommittedURL; }
diff --git a/ios/chrome/browser/ui/alert_view_controller/alert_view_controller.mm b/ios/chrome/browser/ui/alert_view_controller/alert_view_controller.mm index 85be464..f941af9 100644 --- a/ios/chrome/browser/ui/alert_view_controller/alert_view_controller.mm +++ b/ios/chrome/browser/ui/alert_view_controller/alert_view_controller.mm
@@ -19,9 +19,6 @@ namespace { -// The alpha of the black chrome behind the alert view. -constexpr CGFloat kBackgroundAlpha = 0.4; - // Properties of the alert shadow. constexpr CGFloat kShadowOffsetX = 0; constexpr CGFloat kShadowOffsetY = 15; @@ -61,9 +58,6 @@ constexpr CGFloat kTextfieldInset = 8; -// Colors for the action buttons. -constexpr int kButtonTextDestructiveColor = 0xdf322f; - // This is how many bits UIViewAnimationCurve needs to be shifted to be in // UIViewAnimationOptions format. Must match the one in UIView.h. constexpr NSUInteger kUIViewAnimationCurveToOptionsShift = 16; @@ -136,8 +130,7 @@ - (void)loadView { [super loadView]; - self.view.backgroundColor = - [[UIColor blackColor] colorWithAlphaComponent:kBackgroundAlpha]; + self.view.backgroundColor = [UIColor colorNamed:kScrimBackgroundColor]; self.view.accessibilityViewIsModal = YES; self.tapRecognizer = [[UITapGestureRecognizer alloc] @@ -399,7 +392,7 @@ textColor = [UIColor colorNamed:kTintColor]; } else { // Style is UIAlertActionStyleDestructive font = [UIFont preferredFontForTextStyle:UIFontTextStyleBody]; - textColor = UIColorFromRGB(kButtonTextDestructiveColor); + textColor = [UIColor colorNamed:kDestructiveTintColor]; } button.titleLabel.font = font; button.titleLabel.adjustsFontForContentSizeCategory = YES;
diff --git a/ios/chrome/browser/ui/badges/BUILD.gn b/ios/chrome/browser/ui/badges/BUILD.gn index 7a12b716..ae6609d0 100644 --- a/ios/chrome/browser/ui/badges/BUILD.gn +++ b/ios/chrome/browser/ui/badges/BUILD.gn
@@ -14,8 +14,6 @@ configs += [ "//build/config/compiler:enable_arc" ] sources = [ "badge_consumer.h", - "badge_coordinator.h", - "badge_coordinator.mm", "badge_mediator.h", "badge_mediator.mm", ]
diff --git a/ios/chrome/browser/ui/badges/badge_coordinator.h b/ios/chrome/browser/ui/badges/badge_coordinator.h deleted file mode 100644 index 0ff3606c..0000000 --- a/ios/chrome/browser/ui/badges/badge_coordinator.h +++ /dev/null
@@ -1,26 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef IOS_CHROME_BROWSER_UI_BADGES_BADGE_COORDINATOR_H_ -#define IOS_CHROME_BROWSER_UI_BADGES_BADGE_COORDINATOR_H_ - -#import "ios/chrome/browser/ui/coordinators/chrome_coordinator.h" - -@protocol BadgeConsumer; -class WebStateList; - -// Coordinator that presents badges. -@interface BadgeCoordinator : ChromeCoordinator - -// The ViewController that the Coordinator is managing. -// TODO(crbug.com/981925): Replace this property with a getter once -// BadgeCoordinator manages its own view controller. -@property(nonatomic, weak) UIViewController<BadgeConsumer>* viewController; - -// The WebStateList for this Coordinator. -@property(nonatomic, assign) WebStateList* webStateList; - -@end - -#endif // IOS_CHROME_BROWSER_UI_BADGES_BADGE_COORDINATOR_H_
diff --git a/ios/chrome/browser/ui/badges/badge_coordinator.mm b/ios/chrome/browser/ui/badges/badge_coordinator.mm deleted file mode 100644 index 54dfbcab..0000000 --- a/ios/chrome/browser/ui/badges/badge_coordinator.mm +++ /dev/null
@@ -1,35 +0,0 @@ -// Copyright 2019 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#import "ios/chrome/browser/ui/badges/badge_coordinator.h" - -#import "ios/chrome/browser/ui/badges/badge_mediator.h" -#import "ios/chrome/browser/ui/infobars/infobar_feature.h" - -#if !defined(__has_feature) || !__has_feature(objc_arc) -#error "This file requires ARC support." -#endif - -@interface BadgeCoordinator () - -// The coordinator's mediator. -@property(nonatomic, strong) BadgeMediator* mediator; - -@end - -@implementation BadgeCoordinator - -- (void)start { - if (IsInfobarUIRebootEnabled()) { - self.mediator = [[BadgeMediator alloc] initWithConsumer:self.viewController - webStateList:self.webStateList]; - } -} - -- (void)stop { - [self.mediator disconnect]; - self.mediator = nil; -} - -@end
diff --git a/ios/chrome/browser/ui/content_suggestions/BUILD.gn b/ios/chrome/browser/ui/content_suggestions/BUILD.gn index 1596af3..fe0304c3 100644 --- a/ios/chrome/browser/ui/content_suggestions/BUILD.gn +++ b/ios/chrome/browser/ui/content_suggestions/BUILD.gn
@@ -135,6 +135,7 @@ "//ios/chrome/browser/ui/toolbar/public", "//ios/chrome/browser/ui/toolbar/resources:tab_toolbar_shadow_color", "//ios/chrome/browser/ui/util:util", + "//ios/chrome/common/colors", "//ios/chrome/common/favicon", "//ios/chrome/common/ui_util", "//ios/web/common",
diff --git a/ios/chrome/browser/ui/content_suggestions/cells/BUILD.gn b/ios/chrome/browser/ui/content_suggestions/cells/BUILD.gn index 3cce84d3..32204cd7 100644 --- a/ios/chrome/browser/ui/content_suggestions/cells/BUILD.gn +++ b/ios/chrome/browser/ui/content_suggestions/cells/BUILD.gn
@@ -63,6 +63,7 @@ "//ios/chrome/browser/ui/ntp_tile_views:constants", "//ios/chrome/browser/ui/util", "//ios/chrome/common", + "//ios/chrome/common/colors", "//ios/chrome/common/favicon", "//ios/chrome/common/ui_util", "//ui/base",
diff --git a/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_articles_header_item.mm b/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_articles_header_item.mm index 8d7df3a..34e54a8 100644 --- a/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_articles_header_item.mm +++ b/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_articles_header_item.mm
@@ -5,6 +5,8 @@ #import "ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_articles_header_item.h" #import "ios/chrome/browser/ui/util/uikit_ui_util.h" +#import "ios/chrome/common/colors/UIColor+cr_semantic_colors.h" +#import "ios/chrome/common/colors/semantic_color_names.h" #import "ios/chrome/common/ui_util/constraints_ui_util.h" #include "ios/chrome/grit/ios_strings.h" #include "ui/base/l10n/l10n_util.h" @@ -16,8 +18,6 @@ namespace { // Leading and trailing margin for label and button. const CGFloat kTextMargin = 13; -// Color for label text. -const int kLabelColorRGB = 0x6D6D72; } #pragma mark - ContentSuggestionsArticlesHeaderItem @@ -90,11 +90,12 @@ _label = [[UILabel alloc] init]; _label.translatesAutoresizingMaskIntoConstraints = NO; _label.font = [UIFont preferredFontForTextStyle:UIFontTextStyleFootnote]; - _label.textColor = UIColorFromRGB(kLabelColorRGB, 1.0); + _label.textColor = UIColor.cr_secondaryLabelColor; _label.adjustsFontForContentSizeCategory = YES; _label.adjustsFontSizeToFitWidth = YES; _button = [UIButton buttonWithType:UIButtonTypeSystem]; + _button.tintColor = [UIColor colorNamed:kTintColor]; _button.translatesAutoresizingMaskIntoConstraints = NO; _button.titleLabel.font = [UIFont preferredFontForTextStyle:UIFontTextStyleFootnote];
diff --git a/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_cell.mm b/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_cell.mm index a789eb5..fc916d18 100644 --- a/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_cell.mm +++ b/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_cell.mm
@@ -8,6 +8,7 @@ #import "ios/chrome/browser/ui/util/i18n_string.h" #include "ios/chrome/browser/ui/util/ui_util.h" #import "ios/chrome/browser/ui/util/uikit_ui_util.h" +#import "ios/chrome/common/colors/UIColor+cr_semantic_colors.h" #import "ios/chrome/common/favicon/favicon_view.h" #import "ios/chrome/common/ui_util/constraints_ui_util.h" #import "ios/third_party/material_components_ios/src/components/Typography/src/MaterialTypography.h" @@ -113,8 +114,7 @@ [[self class] configureTitleLabel:_titleLabel]; _additionalInformationLabel.font = [[self class] additionalInformationFont]; _faviconView.font = [[MDCTypography fontLoader] mediumFontOfSize:10]; - _additionalInformationLabel.textColor = - [UIColor colorWithWhite:0 alpha:0.54]; + _additionalInformationLabel.textColor = UIColor.cr_secondaryLabelColor; [self applyConstraints]; } @@ -374,7 +374,7 @@ // Configures the |titleLabel|. + (void)configureTitleLabel:(UILabel*)titleLabel { - titleLabel.textColor = [UIColor colorWithWhite:0 alpha:0.8]; + titleLabel.textColor = UIColor.cr_labelColor; UIFontDescriptor* descriptor = [[UIFontDescriptor preferredFontDescriptorWithTextStyle:UIFontTextStyleSubheadline] fontDescriptorWithSymbolicTraits:UIFontDescriptorTraitBold];
diff --git a/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_footer_item.mm b/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_footer_item.mm index 7cbe8a7b..da14003 100644 --- a/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_footer_item.mm +++ b/ios/chrome/browser/ui/content_suggestions/cells/content_suggestions_footer_item.mm
@@ -6,6 +6,7 @@ #import "ios/chrome/browser/ui/colors/MDCPalette+CrAdditions.h" #include "ios/chrome/browser/ui/util/ui_util.h" +#import "ios/chrome/common/colors/semantic_color_names.h" #import "ios/chrome/common/ui_util/constraints_ui_util.h" #import "ios/third_party/material_components_ios/src/components/ActivityIndicator/src/MaterialActivityIndicator.h" @@ -84,9 +85,10 @@ self = [super initWithFrame:frame]; if (self) { _activityIndicator = [[MDCActivityIndicator alloc] init]; - _activityIndicator.cycleColors = @[ [[MDCPalette cr_bluePalette] tint500] ]; + _activityIndicator.cycleColors = @[ [UIColor colorNamed:kTintColor] ]; _activityIndicator.translatesAutoresizingMaskIntoConstraints = NO; _button = [UIButton buttonWithType:UIButtonTypeSystem]; + _button.tintColor = [UIColor colorNamed:kTintColor]; _button.translatesAutoresizingMaskIntoConstraints = NO; _button.titleLabel.font = [UIFont preferredFontForTextStyle:UIFontTextStyleFootnote];
diff --git a/ios/chrome/browser/ui/content_suggestions/content_suggestions_view_controller.mm b/ios/chrome/browser/ui/content_suggestions/content_suggestions_view_controller.mm index adba584..2bc1829 100644 --- a/ios/chrome/browser/ui/content_suggestions/content_suggestions_view_controller.mm +++ b/ios/chrome/browser/ui/content_suggestions/content_suggestions_view_controller.mm
@@ -27,6 +27,7 @@ #import "ios/chrome/browser/ui/toolbar/public/toolbar_utils.h" #import "ios/chrome/browser/ui/ui_feature_flags.h" #import "ios/chrome/browser/ui/util/uikit_ui_util.h" +#import "ios/chrome/common/colors/UIColor+cr_semantic_colors.h" #import "ios/chrome/common/ui_util/constraints_ui_util.h" #if !defined(__has_feature) || !__has_feature(objc_arc) @@ -309,8 +310,8 @@ self.traitCollection.preferredContentSizeCategory) { [self.collectionViewLayout invalidateLayout]; [self.headerSynchronizer updateFakeOmniboxOnCollectionScroll]; - [self.headerSynchronizer updateConstraints]; } + [self.headerSynchronizer updateConstraints]; [self updateOverscrollActionsState]; } @@ -469,8 +470,17 @@ cellBackgroundColorAtIndexPath:(nonnull NSIndexPath*)indexPath { if ([self.collectionUpdater shouldUseCustomStyleForSection:indexPath.section]) { - return [UIColor clearColor]; + return UIColor.clearColor; } + // MDCCollectionView doesn't support dynamic colors, so they have to be + // resolved now. + // TODO(crbug.com/984928): Clean up once dynamic color support is added. +#if defined(__IPHONE_13_0) && (__IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_13_0) + if (@available(iOS 13, *)) { + return [ntp_home::kNTPBackgroundColor() + resolvedColorWithTraitCollection:self.traitCollection]; + } +#endif return ntp_home::kNTPBackgroundColor(); }
diff --git a/ios/chrome/browser/ui/ntp_tile_views/BUILD.gn b/ios/chrome/browser/ui/ntp_tile_views/BUILD.gn index 228fd5e..70af4d1 100644 --- a/ios/chrome/browser/ui/ntp_tile_views/BUILD.gn +++ b/ios/chrome/browser/ui/ntp_tile_views/BUILD.gn
@@ -23,6 +23,7 @@ "resources:ntp_recent_icon", "//base", "//ios/chrome/browser/ui/util", + "//ios/chrome/common/colors", "//ios/chrome/common/favicon", "//ios/chrome/common/ui_util", "//ios/third_party/material_components_ios",
diff --git a/ios/chrome/browser/ui/ntp_tile_views/ntp_tile_view.mm b/ios/chrome/browser/ui/ntp_tile_views/ntp_tile_view.mm index 4379e528..81990c3be 100644 --- a/ios/chrome/browser/ui/ntp_tile_views/ntp_tile_view.mm +++ b/ios/chrome/browser/ui/ntp_tile_views/ntp_tile_view.mm
@@ -5,6 +5,7 @@ #import "ios/chrome/browser/ui/ntp_tile_views/ntp_tile_view.h" #import "ios/chrome/browser/ui/util/dynamic_type_util.h" +#import "ios/chrome/common/colors/UIColor+cr_semantic_colors.h" #import "ios/chrome/common/ui_util/constraints_ui_util.h" #if !defined(__has_feature) || !__has_feature(objc_arc) @@ -16,7 +17,6 @@ const NSInteger kLabelNumLines = 2; const CGFloat kSpaceIconTitle = 10; const CGFloat kIconSize = 56; -const CGFloat kTitleAlpha = 0.54; const CGFloat kPreferredMaxWidth = 73; } // namespace @@ -27,7 +27,7 @@ self = [super initWithFrame:frame]; if (self) { _titleLabel = [[UILabel alloc] init]; - _titleLabel.textColor = [UIColor colorWithWhite:0 alpha:kTitleAlpha]; + _titleLabel.textColor = UIColor.cr_secondaryLabelColor; _titleLabel.font = [self titleLabelFont]; _titleLabel.textAlignment = NSTextAlignmentCenter; _titleLabel.preferredMaxLayoutWidth = kPreferredMaxWidth;
diff --git a/ios/chrome/browser/ui/tab_grid/grid/resources/BUILD.gn b/ios/chrome/browser/ui/tab_grid/grid/resources/BUILD.gn index 2e88b9ff9..3bffe21 100644 --- a/ios/chrome/browser/ui/tab_grid/grid/resources/BUILD.gn +++ b/ios/chrome/browser/ui/tab_grid/grid/resources/BUILD.gn
@@ -7,7 +7,6 @@ imageset("grid_cell_close_button") { sources = [ "grid_cell_close_button.imageset/Contents.json", - "grid_cell_close_button.imageset/grid_cell_close_button.png", "grid_cell_close_button.imageset/grid_cell_close_button@2x.png", "grid_cell_close_button.imageset/grid_cell_close_button@3x.png", ]
diff --git a/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/Contents.json b/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/Contents.json index 39ec32c..5137979d 100644 --- a/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/Contents.json +++ b/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/Contents.json
@@ -2,11 +2,6 @@ "images": [ { "idiom": "universal", - "scale": "1x", - "filename": "grid_cell_close_button.png" - }, - { - "idiom": "universal", "scale": "2x", "filename": "grid_cell_close_button@2x.png" },
diff --git a/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button.png b/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button.png deleted file mode 100644 index 6c24ca9..0000000 --- a/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button@2x.png b/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button@2x.png index ce373fc..811e9c5 100644 --- a/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button@2x.png +++ b/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button@2x.png Binary files differ
diff --git a/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button@3x.png b/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button@3x.png index fcfe06fb..d074ce3 100644 --- a/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button@3x.png +++ b/ios/chrome/browser/ui/tab_grid/grid/resources/grid_cell_close_button.imageset/grid_cell_close_button@3x.png Binary files differ
diff --git a/ios/chrome/browser/ui/table_view/cells/table_view_image_item.mm b/ios/chrome/browser/ui/table_view/cells/table_view_image_item.mm index cb9a5d6..0ad9745e 100644 --- a/ios/chrome/browser/ui/table_view/cells/table_view_image_item.mm +++ b/ios/chrome/browser/ui/table_view/cells/table_view_image_item.mm
@@ -45,11 +45,6 @@ cell.textLabel.text = self.title; cell.detailTextLabel.text = self.detailText; - UIColor* cellBackgroundColor = styler.cellBackgroundColor - ? styler.cellBackgroundColor - : styler.tableViewBackgroundColor; - cell.imageView.backgroundColor = cellBackgroundColor; - cell.textLabel.backgroundColor = cellBackgroundColor; if (self.textColor) { cell.textLabel.textColor = self.textColor; } else if (styler.cellTitleColor) {
diff --git a/ios/chrome/browser/ui/tabs/BUILD.gn b/ios/chrome/browser/ui/tabs/BUILD.gn index 9b5ffed..6d64c71e 100644 --- a/ios/chrome/browser/ui/tabs/BUILD.gn +++ b/ios/chrome/browser/ui/tabs/BUILD.gn
@@ -61,6 +61,7 @@ "//ios/chrome/browser/web_state_list", "//ios/chrome/common", "//ios/chrome/common:common_extension", + "//ios/chrome/common/colors", "//ios/chrome/common/ui_util", "//ios/third_party/material_components_ios", "//ios/web",
diff --git a/ios/chrome/browser/ui/tabs/resources/BUILD.gn b/ios/chrome/browser/ui/tabs/resources/BUILD.gn index db1e1bd3..e6d7ab6 100644 --- a/ios/chrome/browser/ui/tabs/resources/BUILD.gn +++ b/ios/chrome/browser/ui/tabs/resources/BUILD.gn
@@ -17,7 +17,6 @@ sources = [ "tabstrip_background_tab.imageset/Contents.json", "tabstrip_background_tab.imageset/tabstrip_background_tab@2x~ipad.png", - "tabstrip_background_tab.imageset/tabstrip_background_tab~ipad.png", ] } @@ -25,7 +24,6 @@ sources = [ "tabstrip_foreground_tab.imageset/Contents.json", "tabstrip_foreground_tab.imageset/tabstrip_foreground_tab@2x~ipad.png", - "tabstrip_foreground_tab.imageset/tabstrip_foreground_tab~ipad.png", ] } @@ -33,7 +31,6 @@ sources = [ "tabstrip_incognito_background_tab.imageset/Contents.json", "tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab@2x~ipad.png", - "tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab~ipad.png", ] } @@ -41,7 +38,6 @@ sources = [ "tabstrip_incognito_foreground_tab.imageset/Contents.json", "tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab@2x~ipad.png", - "tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab~ipad.png", ] } @@ -49,7 +45,6 @@ sources = [ "tabstrip_new_tab.imageset/Contents.json", "tabstrip_new_tab.imageset/tabstrip_new_tab@2x~ipad.png", - "tabstrip_new_tab.imageset/tabstrip_new_tab~ipad.png", ] } @@ -57,7 +52,6 @@ sources = [ "tabstrip_new_tab_incognito.imageset/Contents.json", "tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito@2x~ipad.png", - "tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito~ipad.png", ] } @@ -65,7 +59,6 @@ sources = [ "tabstrip_new_tab_incognito_pressed.imageset/Contents.json", "tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed@2x~ipad.png", - "tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed~ipad.png", ] } @@ -73,7 +66,6 @@ sources = [ "tabstrip_new_tab_pressed.imageset/Contents.json", "tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed@2x~ipad.png", - "tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed~ipad.png", ] }
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/Contents.json b/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/Contents.json index a2758fc..8ea30cd 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/Contents.json +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/Contents.json
@@ -4,11 +4,6 @@ "idiom": "ipad", "scale": "2x", "filename": "tabstrip_background_tab@2x~ipad.png" - }, - { - "idiom": "ipad", - "scale": "1x", - "filename": "tabstrip_background_tab~ipad.png" } ], "info": {
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/tabstrip_background_tab@2x~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/tabstrip_background_tab@2x~ipad.png index 85c4b254..ed2681c 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/tabstrip_background_tab@2x~ipad.png +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/tabstrip_background_tab@2x~ipad.png Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/tabstrip_background_tab~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/tabstrip_background_tab~ipad.png deleted file mode 100644 index 40f2ab47..0000000 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_background_tab.imageset/tabstrip_background_tab~ipad.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/Contents.json b/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/Contents.json index e634944..02c1a19 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/Contents.json +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/Contents.json
@@ -4,11 +4,6 @@ "idiom": "ipad", "scale": "2x", "filename": "tabstrip_foreground_tab@2x~ipad.png" - }, - { - "idiom": "ipad", - "scale": "1x", - "filename": "tabstrip_foreground_tab~ipad.png" } ], "info": {
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/tabstrip_foreground_tab@2x~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/tabstrip_foreground_tab@2x~ipad.png index 811fbf4e..458102f 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/tabstrip_foreground_tab@2x~ipad.png +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/tabstrip_foreground_tab@2x~ipad.png Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/tabstrip_foreground_tab~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/tabstrip_foreground_tab~ipad.png deleted file mode 100644 index b3bd98b9..0000000 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_foreground_tab.imageset/tabstrip_foreground_tab~ipad.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/Contents.json b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/Contents.json index 6afb4234..53bafe4 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/Contents.json +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/Contents.json
@@ -4,11 +4,6 @@ "idiom": "ipad", "scale": "2x", "filename": "tabstrip_incognito_background_tab@2x~ipad.png" - }, - { - "idiom": "ipad", - "scale": "1x", - "filename": "tabstrip_incognito_background_tab~ipad.png" } ], "info": {
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab@2x~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab@2x~ipad.png index 54ea7f7..cd601ff 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab@2x~ipad.png +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab@2x~ipad.png Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab~ipad.png deleted file mode 100644 index ced490b7..0000000 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_background_tab.imageset/tabstrip_incognito_background_tab~ipad.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/Contents.json b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/Contents.json index de4c499..cd4f3b90 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/Contents.json +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/Contents.json
@@ -4,11 +4,6 @@ "idiom": "ipad", "scale": "2x", "filename": "tabstrip_incognito_foreground_tab@2x~ipad.png" - }, - { - "idiom": "ipad", - "scale": "1x", - "filename": "tabstrip_incognito_foreground_tab~ipad.png" } ], "info": {
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab@2x~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab@2x~ipad.png index 8c2a610..e3bab5ee 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab@2x~ipad.png +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab@2x~ipad.png Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab~ipad.png deleted file mode 100644 index 9bf059c..0000000 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_incognito_foreground_tab.imageset/tabstrip_incognito_foreground_tab~ipad.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/Contents.json b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/Contents.json index 2e858e9..3f9550b 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/Contents.json +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/Contents.json
@@ -4,11 +4,6 @@ "idiom": "ipad", "scale": "2x", "filename": "tabstrip_new_tab@2x~ipad.png" - }, - { - "idiom": "ipad", - "scale": "1x", - "filename": "tabstrip_new_tab~ipad.png" } ], "info": {
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/tabstrip_new_tab@2x~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/tabstrip_new_tab@2x~ipad.png index e727c629..1817e4e 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/tabstrip_new_tab@2x~ipad.png +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/tabstrip_new_tab@2x~ipad.png Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/tabstrip_new_tab~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/tabstrip_new_tab~ipad.png deleted file mode 100644 index b70411dc0..0000000 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab.imageset/tabstrip_new_tab~ipad.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/Contents.json b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/Contents.json index 69a44e1..104b951 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/Contents.json +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/Contents.json
@@ -4,11 +4,6 @@ "idiom": "ipad", "scale": "2x", "filename": "tabstrip_new_tab_incognito@2x~ipad.png" - }, - { - "idiom": "ipad", - "scale": "1x", - "filename": "tabstrip_new_tab_incognito~ipad.png" } ], "info": {
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito@2x~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito@2x~ipad.png index 48959e1d..1817e4e 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito@2x~ipad.png +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito@2x~ipad.png Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito~ipad.png deleted file mode 100644 index 16c7603d..0000000 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito.imageset/tabstrip_new_tab_incognito~ipad.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/Contents.json b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/Contents.json index ce746087..7788e94 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/Contents.json +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/Contents.json
@@ -4,11 +4,6 @@ "idiom": "ipad", "scale": "2x", "filename": "tabstrip_new_tab_incognito_pressed@2x~ipad.png" - }, - { - "idiom": "ipad", - "scale": "1x", - "filename": "tabstrip_new_tab_incognito_pressed~ipad.png" } ], "info": {
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed@2x~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed@2x~ipad.png index 48959e1d..1f822d0 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed@2x~ipad.png +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed@2x~ipad.png Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed~ipad.png deleted file mode 100644 index 16c7603d..0000000 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_incognito_pressed.imageset/tabstrip_new_tab_incognito_pressed~ipad.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/Contents.json b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/Contents.json index 0e1b733..948e49a 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/Contents.json +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/Contents.json
@@ -4,11 +4,6 @@ "idiom": "ipad", "scale": "2x", "filename": "tabstrip_new_tab_pressed@2x~ipad.png" - }, - { - "idiom": "ipad", - "scale": "1x", - "filename": "tabstrip_new_tab_pressed~ipad.png" } ], "info": {
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed@2x~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed@2x~ipad.png index 80c1e6c..1f822d0 100644 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed@2x~ipad.png +++ b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed@2x~ipad.png Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed~ipad.png b/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed~ipad.png deleted file mode 100644 index 0c2d990..0000000 --- a/ios/chrome/browser/ui/tabs/resources/tabstrip_new_tab_pressed.imageset/tabstrip_new_tab_pressed~ipad.png +++ /dev/null Binary files differ
diff --git a/ios/chrome/browser/ui/tabs/tab_strip_controller.mm b/ios/chrome/browser/ui/tabs/tab_strip_controller.mm index 53754e3..24980e3 100644 --- a/ios/chrome/browser/ui/tabs/tab_strip_controller.mm +++ b/ios/chrome/browser/ui/tabs/tab_strip_controller.mm
@@ -69,7 +69,7 @@ const NSTimeInterval kDragAndDropLongPressDuration = 0.4; // Tab dimensions. -const CGFloat kTabOverlap = 26.0; +const CGFloat kTabOverlap = 32.0; const CGFloat kTabOverlapForCompactLayout = 30.0; const CGFloat kNewTabOverlap = 13.0;
diff --git a/ios/chrome/browser/ui/tabs/tab_view.mm b/ios/chrome/browser/ui/tabs/tab_view.mm index ed25877..cde4ca1 100644 --- a/ios/chrome/browser/ui/tabs/tab_view.mm +++ b/ios/chrome/browser/ui/tabs/tab_view.mm
@@ -41,7 +41,7 @@ const CGFloat kTabCloseLeftInset = 0.0; const CGFloat kTabCloseBottomInset = 0.0; const CGFloat kTabCloseRightInset = 0.0; -const CGFloat kTabBackgroundLeftCapInset = 24.0; +const CGFloat kTabBackgroundLeftCapInset = 34.0; const CGFloat kFaviconLeftInset = 23.5; const CGFloat kFaviconVerticalOffset = 2.0; const CGFloat kTabStripLineMargin = 2.5;
diff --git a/ios/web_view/internal/passwords/web_view_password_manager_driver.h b/ios/web_view/internal/passwords/web_view_password_manager_driver.h index 1a28e29..6b526732 100644 --- a/ios/web_view/internal/passwords/web_view_password_manager_driver.h +++ b/ios/web_view/internal/passwords/web_view_password_manager_driver.h
@@ -63,7 +63,7 @@ override; autofill::AutofillDriver* GetAutofillDriver() override; bool IsMainFrame() const override; - GURL GetLastCommittedURL() const override; + const GURL& GetLastCommittedURL() const override; private: __weak id<CWVPasswordManagerDriverDelegate> delegate_;
diff --git a/ios/web_view/internal/passwords/web_view_password_manager_driver.mm b/ios/web_view/internal/passwords/web_view_password_manager_driver.mm index 89e1f07b..90eea3c 100644 --- a/ios/web_view/internal/passwords/web_view_password_manager_driver.mm +++ b/ios/web_view/internal/passwords/web_view_password_manager_driver.mm
@@ -80,7 +80,7 @@ return true; } -GURL WebViewPasswordManagerDriver::GetLastCommittedURL() const { +const GURL& WebViewPasswordManagerDriver::GetLastCommittedURL() const { return delegate_.lastCommittedURL; } } // namespace ios_web_view
diff --git a/media/gpu/vaapi/vaapi_wrapper.cc b/media/gpu/vaapi/vaapi_wrapper.cc index 80ba10a..944fe2a 100644 --- a/media/gpu/vaapi/vaapi_wrapper.cc +++ b/media/gpu/vaapi/vaapi_wrapper.cc
@@ -1357,7 +1357,7 @@ va_attrib_extbuf.width = size.width(); va_attrib_extbuf.height = size.height(); - const size_t num_planes = gfx::NumberOfPlanesForBufferFormat(buffer_format); + const size_t num_planes = pixmap->GetNumberOfPlanes(); for (size_t i = 0; i < num_planes; ++i) { va_attrib_extbuf.pitches[i] = pixmap->GetDmaBufPitch(i); va_attrib_extbuf.offsets[i] = pixmap->GetDmaBufOffset(i);
diff --git a/net/quic/platform/impl/quic_mem_slice_storage_impl.cc b/net/quic/platform/impl/quic_mem_slice_storage_impl.cc index f0c4fe94..420b675f 100644 --- a/net/quic/platform/impl/quic_mem_slice_storage_impl.cc +++ b/net/quic/platform/impl/quic_mem_slice_storage_impl.cc
@@ -35,6 +35,11 @@ } } +void QuicMemSliceStorageImpl::Append(QuicMemSliceImpl mem_slice) { + buffers_.push_back(*mem_slice.impl()); + lengths_.push_back(mem_slice.length()); +} + QuicMemSliceStorageImpl::QuicMemSliceStorageImpl( const QuicMemSliceStorageImpl& other) = default; QuicMemSliceStorageImpl::QuicMemSliceStorageImpl(
diff --git a/net/quic/platform/impl/quic_mem_slice_storage_impl.h b/net/quic/platform/impl/quic_mem_slice_storage_impl.h index 9e91fff..3b56cd07 100644 --- a/net/quic/platform/impl/quic_mem_slice_storage_impl.h +++ b/net/quic/platform/impl/quic_mem_slice_storage_impl.h
@@ -33,6 +33,8 @@ buffers_.data(), lengths_.data(), buffers_.size())); } + void Append(QuicMemSliceImpl mem_slice); + private: std::vector<scoped_refptr<net::IOBuffer>> buffers_; std::vector<size_t> lengths_;
diff --git a/net/quic/quic_connection_logger.cc b/net/quic/quic_connection_logger.cc index 3077f080..cdae0879 100644 --- a/net/quic/quic_connection_logger.cc +++ b/net/quic/quic_connection_logger.cc
@@ -628,6 +628,7 @@ } void QuicConnectionLogger::OnIncomingAck( + quic::QuicPacketNumber ack_packet_number, const quic::QuicAckFrame& frame, quic::QuicTime ack_receive_time, quic::QuicPacketNumber largest_observed,
diff --git a/net/quic/quic_connection_logger.h b/net/quic/quic_connection_logger.h index edc4823..d987bf5 100644 --- a/net/quic/quic_connection_logger.h +++ b/net/quic/quic_connection_logger.h
@@ -51,7 +51,8 @@ quic::QuicPacketNumber original_packet_number, quic::TransmissionType transmission_type, quic::QuicTime sent_time) override; - void OnIncomingAck(const quic::QuicAckFrame& frame, + void OnIncomingAck(quic::QuicPacketNumber ack_packet_number, + const quic::QuicAckFrame& frame, quic::QuicTime ack_receive_time, quic::QuicPacketNumber largest_observed, bool rtt_updated,
diff --git a/net/quic/quic_flags_list.h b/net/quic/quic_flags_list.h index 88eb3b5..7ba1ceb73 100644 --- a/net/quic/quic_flags_list.h +++ b/net/quic/quic_flags_list.h
@@ -241,7 +241,7 @@ // If true, ignore TLPR if there is no pending stream data. QUIC_FLAG(bool, FLAGS_quic_reloadable_flag_quic_ignore_tlpr_if_no_pending_stream_data, - false) + true) // If true, when detecting losses, use packets_acked of corresponding packet // number space. @@ -305,3 +305,23 @@ bool, FLAGS_quic_reloadable_flag_quic_reject_unprocessable_packets_statelessly, false) + +// When true, QuicConnectionId::Hash uses SipHash instead of XOR. +QUIC_FLAG(bool, FLAGS_quic_restart_flag_quic_connection_id_use_siphash, false) + +// If true, when RTO fires and there is no packet to be RTOed, let connection +// send. +QUIC_FLAG(bool, FLAGS_quic_reloadable_flag_quic_fix_rto_retransmission, true) + +// If true, QuicSession::GetOrCreateDynamicStream() is deprecated, and its +// contents are moved to GetOrCreateStream(). +QUIC_FLAG(bool, + FLAGS_quic_reloadable_flag_quic_inline_getorcreatedynamicstream, + false) + +// Maximum number of tracked packets. +QUIC_FLAG(int64_t, FLAGS_quic_max_tracked_packet_count, 10000) + +// If true, HTTP request header names sent from QuicSpdyClientBase(and +// descendents) will be automatically converted to lower case. +QUIC_FLAG(bool, FLAGS_quic_client_convert_http_header_name_to_lowercase, true)
diff --git a/services/device/generic_sensor/platform_sensor_accelerometer_mac.h b/services/device/generic_sensor/platform_sensor_accelerometer_mac.h index 8e8dbb0..957cadf 100644 --- a/services/device/generic_sensor/platform_sensor_accelerometer_mac.h +++ b/services/device/generic_sensor/platform_sensor_accelerometer_mac.h
@@ -17,8 +17,8 @@ // Implementation of PlatformSensor for macOS to query the accelerometer // sensor. // This is a single instance object per browser process which is created by -// The singleton PlatformSensorProviderMac. If there are no clients, this -// instance is not created. +// PlatformSensorProviderMac. If there are no clients, this instance is not +// created. class PlatformSensorAccelerometerMac : public PlatformSensor { public: // Construct a platform sensor of type ACCELEROMETER, given a buffer |mapping|
diff --git a/services/device/generic_sensor/platform_sensor_ambient_light_mac.h b/services/device/generic_sensor/platform_sensor_ambient_light_mac.h index 012647b4..26ed839 100644 --- a/services/device/generic_sensor/platform_sensor_ambient_light_mac.h +++ b/services/device/generic_sensor/platform_sensor_ambient_light_mac.h
@@ -15,8 +15,8 @@ // Implementation of PlatformSensor for macOS to query the ambient light sensor. // This is a single instance object per browser process which is created by -// The singleton PlatformSensorProviderMac. If there are no clients, this -// instance is not created. +// PlatformSensorProviderMac. If there are no clients, this instance is not +// created. class PlatformSensorAmbientLightMac : public PlatformSensor { public: // Construct a platform sensor of AMBIENT_LIGHT, given a buffer |mapping|
diff --git a/services/device/generic_sensor/platform_sensor_and_provider_unittest.cc b/services/device/generic_sensor/platform_sensor_and_provider_unittest.cc index b8dbcf0..cfb1558b 100644 --- a/services/device/generic_sensor/platform_sensor_and_provider_unittest.cc +++ b/services/device/generic_sensor/platform_sensor_and_provider_unittest.cc
@@ -6,7 +6,6 @@ #include "base/bind.h" #include "base/macros.h" -#include "base/memory/singleton.h" #include "base/test/scoped_task_environment.h" #include "services/device/generic_sensor/fake_platform_sensor_and_provider.h" #include "testing/gtest/include/gtest/gtest.h"
diff --git a/services/device/generic_sensor/platform_sensor_provider_android.cc b/services/device/generic_sensor/platform_sensor_provider_android.cc index 6348b759..2980627c 100644 --- a/services/device/generic_sensor/platform_sensor_provider_android.cc +++ b/services/device/generic_sensor/platform_sensor_provider_android.cc
@@ -9,7 +9,6 @@ #include "base/android/scoped_java_ref.h" #include "base/memory/ref_counted.h" -#include "base/memory/singleton.h" #include "services/device/generic_sensor/absolute_orientation_euler_angles_fusion_algorithm_using_accelerometer_and_magnetometer.h" #include "services/device/generic_sensor/jni_headers/PlatformSensorProvider_jni.h" #include "services/device/generic_sensor/linear_acceleration_fusion_algorithm_using_accelerometer.h"
diff --git a/services/device/generic_sensor/platform_sensor_provider_linux.cc b/services/device/generic_sensor/platform_sensor_provider_linux.cc index 8a1b19f..dfbc2ad 100644 --- a/services/device/generic_sensor/platform_sensor_provider_linux.cc +++ b/services/device/generic_sensor/platform_sensor_provider_linux.cc
@@ -9,7 +9,6 @@ #include "base/bind.h" #include "base/memory/ref_counted.h" -#include "base/memory/singleton.h" #include "base/task/post_task.h" #include "base/task_runner_util.h" #include "services/device/generic_sensor/absolute_orientation_euler_angles_fusion_algorithm_using_accelerometer_and_magnetometer.h"
diff --git a/services/device/generic_sensor/platform_sensor_provider_winrt.cc b/services/device/generic_sensor/platform_sensor_provider_winrt.cc index 2d3e5087..c2b0981 100644 --- a/services/device/generic_sensor/platform_sensor_provider_winrt.cc +++ b/services/device/generic_sensor/platform_sensor_provider_winrt.cc
@@ -4,10 +4,6 @@ #include "services/device/generic_sensor/platform_sensor_provider_winrt.h" -#include <comdef.h> - -#include "base/memory/singleton.h" - namespace device { PlatformSensorProviderWinrt::PlatformSensorProviderWinrt() = default; @@ -21,4 +17,4 @@ callback.Run(nullptr); } -} // namespace device \ No newline at end of file +} // namespace device
diff --git a/services/device/generic_sensor/platform_sensor_provider_winrt.h b/services/device/generic_sensor/platform_sensor_provider_winrt.h index 01a07b0..2486595 100644 --- a/services/device/generic_sensor/platform_sensor_provider_winrt.h +++ b/services/device/generic_sensor/platform_sensor_provider_winrt.h
@@ -7,11 +7,6 @@ #include "services/device/generic_sensor/platform_sensor_provider.h" -namespace base { -template <typename T> -struct DefaultSingletonTraits; -} // namespace base - namespace device { class PlatformSensorReaderWin; @@ -34,8 +29,6 @@ const CreateSensorCallback& callback) override; private: - friend struct base::DefaultSingletonTraits<PlatformSensorProviderWinrt>; - void SensorReaderCreated( mojom::SensorType type, SensorReadingSharedBuffer* reading_buffer, @@ -49,4 +42,4 @@ } // namespace device -#endif // SERVICES_DEVICE_GENERIC_SENSOR_PLATFORM_SENSOR_PROVIDER_WINRT_H_ \ No newline at end of file +#endif // SERVICES_DEVICE_GENERIC_SENSOR_PLATFORM_SENSOR_PROVIDER_WINRT_H_
diff --git a/services/device/generic_sensor/sensor_provider_impl.h b/services/device/generic_sensor/sensor_provider_impl.h index f5c2eb5..9a13f0a 100644 --- a/services/device/generic_sensor/sensor_provider_impl.h +++ b/services/device/generic_sensor/sensor_provider_impl.h
@@ -17,9 +17,9 @@ class PlatformSensor; // Implementation of SensorProvider mojo interface. Owns an instance of -// PlatformSensorProvider singleton to create platform specific instances -// of PlatformSensor which are used by SensorImpl. A single instance of this -// class is owned by DeviceService. +// PlatformSensorProvider to create platform specific instances of +// PlatformSensor which are used by SensorImpl. A single instance of this class +// is owned by DeviceService. class SensorProviderImpl final : public mojom::SensorProvider { public: explicit SensorProviderImpl(std::unique_ptr<PlatformSensorProvider> provider);
diff --git a/services/device/generic_sensor/windows/README.md b/services/device/generic_sensor/windows/README.md index 8772437..b8013b7 100644 --- a/services/device/generic_sensor/windows/README.md +++ b/services/device/generic_sensor/windows/README.md
@@ -162,8 +162,6 @@ const CreateSensorCallback& callback) override; private: - friend struct base::DefaultSingletonTraits<PlatformSensorProviderWinrt>; - PlatformSensorProviderWinrt(); std::unique_ptr<PlatformSensorReaderWin> CreateSensorReader( @@ -516,17 +514,7 @@ return PlatformSensorReaderWinrt::Create(type); } -// static -PlatformSensorProviderWinrt* PlatformSensorProviderWinrt::GetInstance() { - return base::Singleton< - PlatformSensorProviderWinrt, - base::LeakySingletonTraits<PlatformSensorProviderWinrt>>::get(); -} - -PlatformSensorProviderWinrt::PlatformSensorProviderWinrt() - : com_sta_task_runner_(base::CreateCOMSTATaskRunnerWithTraits( - base::TaskPriority::USER_VISIBLE)), - sensor_reader_creator_(std::make_unique<SensorReaderCreator>()) {} +PlatformSensorProviderWinrt::PlatformSensorProviderWinrt() = default; PlatformSensorProviderWinrt::~PlatformSensorProviderWinrt() = default;
diff --git a/services/network/cors/preflight_controller.cc b/services/network/cors/preflight_controller.cc index 9c3dc5a..e0c7be8 100644 --- a/services/network/cors/preflight_controller.cc +++ b/services/network/cors/preflight_controller.cc
@@ -92,6 +92,7 @@ preflight_request->headers.SetHeader( header_names::kAccessControlRequestMethod, request.method); + preflight_request->headers.SetHeader("Sec-Fetch-Mode", "cors"); std::string request_headers = CreateAccessControlRequestHeadersHeader( request.headers, request.is_revalidating);
diff --git a/services/network/cors/preflight_controller_unittest.cc b/services/network/cors/preflight_controller_unittest.cc index f13ad806..10ab49e 100644 --- a/services/network/cors/preflight_controller_unittest.cc +++ b/services/network/cors/preflight_controller_unittest.cc
@@ -110,6 +110,21 @@ header_names::kAccessControlRequestHeaders, &header)); } +TEST(PreflightControllerCreatePreflightRequestTest, IncludeSecFetchModeHeader) { + ResourceRequest request; + request.mode = mojom::RequestMode::kCors; + request.credentials_mode = mojom::CredentialsMode::kOmit; + request.request_initiator = url::Origin(); + request.headers.SetHeader("X-Custom-Header", "foobar"); + + std::unique_ptr<ResourceRequest> preflight = + PreflightController::CreatePreflightRequestForTesting(request); + + std::string header; + EXPECT_TRUE(preflight->headers.GetHeader("Sec-Fetch-Mode", &header)); + EXPECT_EQ("cors", header); +} + TEST(PreflightControllerCreatePreflightRequestTest, IncludeNonSimpleHeader) { ResourceRequest request; request.mode = mojom::RequestMode::kCors;
diff --git a/services/service_manager/OWNERS b/services/service_manager/OWNERS index 65373b29..ca156a7 100644 --- a/services/service_manager/OWNERS +++ b/services/service_manager/OWNERS
@@ -4,3 +4,4 @@ per-file manifest.json=set noparent per-file manifest.json=file://ipc/SECURITY_OWNERS +# COMPONENT: Internals>Services
diff --git a/styleguide/c++/blink-c++.md b/styleguide/c++/blink-c++.md index db74e67..47db5ac 100644 --- a/styleguide/c++/blink-c++.md +++ b/styleguide/c++/blink-c++.md
@@ -191,16 +191,58 @@ }; ``` -## Prefer enums to bools for function parameters +## Prefer enums or StrongAliases to bare bools for function parameters Prefer enums to bools for function parameters if callers are likely to be passing constants, since named constants are easier to read at the call site. -An exception to this rule is a setter function, where the name of the function -already makes clear what the boolean is. +Alternatively, you can use base::util::StrongAlias<Tag, bool>. An exception to +this rule is a setter function, where the name of the function already makes +clear what the boolean is. **Good:** ```c++ +class FrameLoader { +public: + enum class CloseType { + kNotForReload, + kForReload, + }; + + bool ShouldClose(CloseType) { + if (type == CloseType::kForReload) { + ... + } else { + DCHECK_EQ(type, CloseType::kNotForReload); + ... + } + } +}; + // An named enum value makes it clear what the parameter is for. -if (frame_->Loader().ShouldClose(CloseType::kNotForReload)) { +if (frame_->Loader().ShouldClose(FrameLoader::CloseType::kNotForReload)) { + // No need to use enums for boolean setters, since the meaning is clear. + frame_->SetIsClosing(true); + + // ... +``` + +**Good:** +```c++ +class FrameLoader { +public: + using ForReload = base::util::StrongAlias<class ForReloadTag, bool>; + + bool ShouldClose(ForReload) { + // A StrongAlias<_, bool> can be tested like a bool. + if (for_reload) { + ... + } else { + ... + } + } +}; + +// Using a StrongAlias makes it clear what the parameter is for. +if (frame_->Loader().ShouldClose(FrameLoader::ForReload(false))) { // No need to use enums for boolean setters, since the meaning is clear. frame_->SetIsClosing(true); @@ -209,6 +251,17 @@ **Bad:** ```c++ +class FrameLoader { +public: + bool ShouldClose(bool for_reload) { + if (for_reload) { + ... + } else { + ... + } + } +}; + // Not obvious what false means here. if (frame_->Loader().ShouldClose(false)) { frame_->SetIsClosing(ClosingState::kTrue);
diff --git a/testing/buildbot/chromium.gpu.fyi.json b/testing/buildbot/chromium.gpu.fyi.json index 8071c03..8e37cd2 100644 --- a/testing/buildbot/chromium.gpu.fyi.json +++ b/testing/buildbot/chromium.gpu.fyi.json
@@ -4491,7 +4491,6 @@ "${buildername}", "--use-skia-gold" ], - "experiment_percentage": 100, "isolate_name": "telemetry_gpu_integration_test", "merge": { "args": [], @@ -4528,51 +4527,6 @@ }, { "args": [ - "pixel", - "--show-stdout", - "--browser=android-webview-instrumentation", - "--passthrough", - "-v", - "--extra-browser-args=--enable-logging=stderr --js-flags=--expose-gc", - "--dont-restore-color-profile-after-test", - "--refimg-cloud-storage-bucket", - "chromium-gpu-archive/reference-images", - "--os-type", - "android", - "--build-revision", - "${got_revision}", - "--test-machine-name", - "${buildername}" - ], - "isolate_name": "telemetry_gpu_integration_test", - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_isolated_script_merge.py" - }, - "name": "android_webview_pixel_test", - "non_precommit_args": [ - "--upload-refimg-to-cloud-storage" - ], - "precommit_args": [ - "--download-refimg-from-cloud-storage" - ], - "should_retry_with_patch": false, - "swarming": { - "can_use_on_swarming_builders": true, - "containment_type": "AUTO", - "dimension_sets": [ - { - "device_os": "MMB29Q", - "device_os_type": "userdebug", - "device_type": "bullhead", - "os": "Android" - } - ], - "idempotent": false - } - }, - { - "args": [ "--gtest-benchmark-name=angle_perftests", "-v", "--one-frame-only", @@ -6819,7 +6773,6 @@ "${buildername}", "--use-skia-gold" ], - "experiment_percentage": 100, "isolate_name": "telemetry_gpu_integration_test", "merge": { "args": [], @@ -6854,52 +6807,6 @@ "idempotent": false, "service_account": "chrome-gpu-gold@chops-service-accounts.iam.gserviceaccount.com" } - }, - { - "args": [ - "pixel", - "--show-stdout", - "--browser=android-chromium", - "--passthrough", - "-v", - "--extra-browser-args=--enable-logging=stderr --js-flags=--expose-gc \"--use-vulkan=native --disable-vulkan-fallback-to-gl-for-testing --enable-features=UseSkiaRenderer\"", - "--dont-restore-color-profile-after-test", - "--refimg-cloud-storage-bucket", - "chromium-gpu-archive/reference-images", - "--os-type", - "android", - "--build-revision", - "${got_revision}", - "--test-machine-name", - "${buildername}" - ], - "isolate_name": "telemetry_gpu_integration_test", - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_isolated_script_merge.py" - }, - "name": "pixel_test", - "non_precommit_args": [ - "--upload-refimg-to-cloud-storage" - ], - "precommit_args": [ - "--download-refimg-from-cloud-storage" - ], - "should_retry_with_patch": false, - "swarming": { - "can_use_on_swarming_builders": true, - "containment_type": "AUTO", - "dimension_sets": [ - { - "device_os": "P", - "device_os_type": "userdebug", - "device_type": "walleye", - "os": "Android", - "pool": "Chrome-GPU" - } - ], - "idempotent": false - } } ] },
diff --git a/testing/buildbot/test_suites.pyl b/testing/buildbot/test_suites.pyl index c3883de..1435aec6 100644 --- a/testing/buildbot/test_suites.pyl +++ b/testing/buildbot/test_suites.pyl
@@ -155,26 +155,6 @@ }, 'android_webview_gpu_telemetry_tests': { - 'pixel': { - 'name': 'android_webview_pixel_test', - 'args': [ - '--dont-restore-color-profile-after-test', - '--refimg-cloud-storage-bucket', - 'chromium-gpu-archive/reference-images', - '--os-type', - '${os_type}', - '--build-revision', - '${got_revision}', - '--test-machine-name', - '${buildername}', - ], - 'non_precommit_args': [ - '--upload-refimg-to-cloud-storage', - ], - 'precommit_args': [ - '--download-refimg-from-cloud-storage', - ], - }, 'pixel_skia': { 'name': 'android_webview_pixel_skia_gold_test', 'args': [ @@ -207,7 +187,6 @@ 'swarming': { 'service_account': 'chrome-gpu-gold@chops-service-accounts.iam.gserviceaccount.com' }, - 'experiment_percentage': 100, 'telemetry_test_name': 'pixel', }, }, @@ -3685,27 +3664,6 @@ }, 'gpu_skia_renderer_vulkan_telemetry_tests': { - 'pixel': { - 'name': 'pixel_test', - 'args': [ - '--dont-restore-color-profile-after-test', - '--refimg-cloud-storage-bucket', - 'chromium-gpu-archive/reference-images', - '--os-type', - '${os_type}', - '--build-revision', - '${got_revision}', - '--test-machine-name', - '${buildername}', - '--extra-browser-args="--use-vulkan=native --disable-vulkan-fallback-to-gl-for-testing --enable-features=UseSkiaRenderer"', - ], - 'non_precommit_args': [ - '--upload-refimg-to-cloud-storage', - ], - 'precommit_args': [ - '--download-refimg-from-cloud-storage', - ], - }, 'pixel_skia': { 'name': 'pixel_skia_gold_test', 'args': [ @@ -3739,7 +3697,6 @@ 'swarming': { 'service_account': 'chrome-gpu-gold@chops-service-accounts.iam.gserviceaccount.com' }, - 'experiment_percentage': 100, 'telemetry_test_name': 'pixel', }, },
diff --git a/third_party/blink/public/BUILD.gn b/third_party/blink/public/BUILD.gn index 948d2ea..a16d936 100644 --- a/third_party/blink/public/BUILD.gn +++ b/third_party/blink/public/BUILD.gn
@@ -386,6 +386,7 @@ "web/modules/mediastream/video_track_adapter_settings.h", "web/modules/mediastream/web_media_stream_utils.h", "web/modules/mediastream/webaudio_media_stream_audio_sink.h", + "web/modules/mediastream/webmediaplayer_ms.h", "web/modules/peerconnection/media_stream_remote_video_source.h", "web/modules/service_worker/web_service_worker_context_client.h", "web/modules/service_worker/web_service_worker_context_proxy.h",
diff --git a/third_party/blink/public/mojom/push_messaging/push_messaging.mojom b/third_party/blink/public/mojom/push_messaging/push_messaging.mojom index d3a4ae1..31ac74a 100644 --- a/third_party/blink/public/mojom/push_messaging/push_messaging.mojom +++ b/third_party/blink/public/mojom/push_messaging/push_messaging.mojom
@@ -15,6 +15,13 @@ array<uint8> application_server_key; }; +struct PushSubscription { + url.mojom.Url endpoint; + PushSubscriptionOptions options; + array<uint8> p256dh; + array<uint8> auth; +}; + enum PushErrorType { ABORT = 0, NETWORK = 1, @@ -29,11 +36,7 @@ Subscribe(int64 service_worker_registration_id, PushSubscriptionOptions options, bool user_gesture) - => (PushRegistrationStatus status, - url.mojom.Url? endpoint, - PushSubscriptionOptions? options, - array<uint8>? p256dh, - array<uint8>? auth); + => (PushRegistrationStatus status, PushSubscription? subscription); // We use the value of |error_type| as a flag. If |error_type| == NONE, it // means no error and returns |did_unsubscribe|. Else, it means there is an @@ -45,8 +48,5 @@ GetSubscription(int64 service_worker_registration_id) => (PushGetRegistrationStatus status, - url.mojom.Url? endpoint, - PushSubscriptionOptions? options, - array<uint8>? p256dh, - array<uint8>? auth); + PushSubscription? subscription); };
diff --git a/third_party/blink/public/mojom/service_worker/service_worker.mojom b/third_party/blink/public/mojom/service_worker/service_worker.mojom index 0e84aed..3ea8f70 100644 --- a/third_party/blink/public/mojom/service_worker/service_worker.mojom +++ b/third_party/blink/public/mojom/service_worker/service_worker.mojom
@@ -12,6 +12,7 @@ import "third_party/blink/public/mojom/messaging/transferable_message.mojom"; import "third_party/blink/public/mojom/notifications/notification.mojom"; import "third_party/blink/public/mojom/payments/payment_app.mojom"; +import "third_party/blink/public/mojom/push_messaging/push_messaging.mojom"; import "third_party/blink/public/mojom/service_worker/dispatch_fetch_event_params.mojom"; import "third_party/blink/public/mojom/service_worker/service_worker_client.mojom"; import "third_party/blink/public/mojom/service_worker/service_worker_error_type.mojom"; @@ -226,6 +227,12 @@ // content, or null. DispatchPushEvent(string? payload) => (ServiceWorkerEventStatus status); + // Whenever a PushSubscription changes, a change event is generated with (optionally) + // the previous subscription and the new subscription. + DispatchPushSubscriptionChangeEvent( + PushSubscription old_subscription, + PushSubscription new_subscription) + => (ServiceWorkerEventStatus status); // Arguments are passed to the event handler as parameters of SyncEvent. // Ref: https://wicg.github.io/BackgroundSync/spec/#sync-event // |timeout| is the amount of time to allow this event to finish.
diff --git a/third_party/blink/public/web/modules/mediastream/DEPS b/third_party/blink/public/web/modules/mediastream/DEPS index aa6e1ec..cfad1b2 100644 --- a/third_party/blink/public/web/modules/mediastream/DEPS +++ b/third_party/blink/public/web/modules/mediastream/DEPS
@@ -7,8 +7,11 @@ "+base/single_thread_task_runner.h", "+base/synchronization/lock.h", "+base/threading/thread_checker.h", + "+build/build_config.h", "+media/base", "+media/capture", + "+media/renderers/paint_canvas_video_renderer.h", + "+media/video/gpu_video_accelerator_factories.h", "+ui/gfx/geometry/size.h" ]
diff --git a/content/renderer/media/stream/webmediaplayer_ms.h b/third_party/blink/public/web/modules/mediastream/webmediaplayer_ms.h similarity index 71% rename from content/renderer/media/stream/webmediaplayer_ms.h rename to third_party/blink/public/web/modules/mediastream/webmediaplayer_ms.h index 0c7c7e2..4ec0c25 100644 --- a/content/renderer/media/stream/webmediaplayer_ms.h +++ b/third_party/blink/public/web/modules/mediastream/webmediaplayer_ms.h
@@ -2,8 +2,8 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef CONTENT_RENDERER_MEDIA_STREAM_WEBMEDIAPLAYER_MS_H_ -#define CONTENT_RENDERER_MEDIA_STREAM_WEBMEDIAPLAYER_MS_H_ +#ifndef THIRD_PARTY_BLINK_PUBLIC_WEB_MODULES_MEDIASTREAM_WEBMEDIAPLAYER_MS_H_ +#define THIRD_PARTY_BLINK_PUBLIC_WEB_MODULES_MEDIASTREAM_WEBMEDIAPLAYER_MS_H_ #include <memory> #include <string> @@ -14,28 +14,18 @@ #include "base/synchronization/lock.h" #include "base/threading/thread_checker.h" #include "build/build_config.h" -#include "content/common/content_export.h" #include "media/renderers/paint_canvas_video_renderer.h" #include "media/video/gpu_video_accelerator_factories.h" #include "third_party/blink/public/platform/media/webmediaplayer_delegate.h" +#include "third_party/blink/public/platform/web_common.h" #include "third_party/blink/public/platform/web_media_player.h" #include "third_party/blink/public/platform/web_media_stream.h" #include "third_party/blink/public/platform/web_surface_layer_bridge.h" -namespace blink { -class WebLocalFrame; -class WebMediaPlayerClient; -class WebMediaStreamAudioRenderer; -class WebMediaStreamRendererFactory; -class WebMediaStreamVideoRenderer; -class WebString; -class WebVideoFrameSubmitter; -} - namespace media { class GpuMemoryBufferVideoFramePool; class MediaLog; -} +} // namespace media namespace cc { class VideoLayer; @@ -45,15 +35,23 @@ namespace gles2 { class GLES2Interface; } -} +} // namespace gpu -namespace content { +namespace blink { using CreateSurfaceLayerBridgeCB = - base::OnceCallback<std::unique_ptr<blink::WebSurfaceLayerBridge>( - blink::WebSurfaceLayerBridgeObserver*, + base::OnceCallback<std::unique_ptr<WebSurfaceLayerBridge>( + WebSurfaceLayerBridgeObserver*, cc::UpdateSubmissionStateCB)>; +class MediaStreamInternalFrameWrapper; +class WebLocalFrame; +class WebMediaPlayerClient; +class WebMediaStreamAudioRenderer; class WebMediaPlayerMSCompositor; +class WebMediaStreamRendererFactory; +class WebMediaStreamVideoRenderer; +class WebString; +class WebVideoFrameSubmitter; // WebMediaPlayerMS delegates calls from WebCore::MediaPlayerPrivate to // Chrome's media player when "src" is from media stream. @@ -63,43 +61,42 @@ // // WebMediaPlayerMS works with multiple objects, the most important ones are: // -// blink::WebMediaStreamVideoRenderer +// WebMediaStreamVideoRenderer // provides video frames for rendering. // -// blink::WebMediaPlayerClient +// WebMediaPlayerClient // WebKit client of this media player object. -class CONTENT_EXPORT WebMediaPlayerMS - : public blink::WebMediaStreamObserver, - public blink::WebMediaPlayer, - public blink::WebMediaPlayerDelegate::Observer, - public blink::WebSurfaceLayerBridgeObserver { +class BLINK_MODULES_EXPORT WebMediaPlayerMS + : public WebMediaStreamObserver, + public WebMediaPlayer, + public WebMediaPlayerDelegate::Observer, + public WebSurfaceLayerBridgeObserver { public: // Construct a WebMediaPlayerMS with reference to the client, and - // a MediaStreamClient which provides blink::WebMediaStreamVideoRenderer. + // a MediaStreamClient which provides WebMediaStreamVideoRenderer. // |delegate| must not be null. WebMediaPlayerMS( - blink::WebLocalFrame* frame, - blink::WebMediaPlayerClient* client, - blink::WebMediaPlayerDelegate* delegate, + WebLocalFrame* frame, + WebMediaPlayerClient* client, + WebMediaPlayerDelegate* delegate, std::unique_ptr<media::MediaLog> media_log, - std::unique_ptr<blink::WebMediaStreamRendererFactory> factory, + std::unique_ptr<WebMediaStreamRendererFactory> factory, scoped_refptr<base::SingleThreadTaskRunner> main_render_task_runner, scoped_refptr<base::SingleThreadTaskRunner> io_task_runner, scoped_refptr<base::SingleThreadTaskRunner> compositor_task_runner, scoped_refptr<base::SingleThreadTaskRunner> media_task_runner, scoped_refptr<base::TaskRunner> worker_task_runner, media::GpuVideoAcceleratorFactories* gpu_factories, - const blink::WebString& sink_id, + const WebString& sink_id, CreateSurfaceLayerBridgeCB create_bridge_callback, - std::unique_ptr<blink::WebVideoFrameSubmitter> submitter_, - blink::WebMediaPlayer::SurfaceLayerMode surface_layer_mode); + std::unique_ptr<WebVideoFrameSubmitter> submitter_, + WebMediaPlayer::SurfaceLayerMode surface_layer_mode); ~WebMediaPlayerMS() override; - blink::WebMediaPlayer::LoadTiming Load( - LoadType load_type, - const blink::WebMediaPlayerSource& source, - CorsMode cors_mode) override; + WebMediaPlayer::LoadTiming Load(LoadType load_type, + const WebMediaPlayerSource& source, + CorsMode cors_mode) override; // WebSurfaceLayerBridgeObserver implementation. void OnWebLayerUpdated() override; @@ -114,16 +111,15 @@ void SetRate(double rate) override; void SetVolume(double volume) override; void OnRequestPictureInPicture() override; - void SetSinkId( - const blink::WebString& sink_id, - blink::WebSetSinkIdCompleteCallback completion_callback) override; - void SetPreload(blink::WebMediaPlayer::Preload preload) override; - blink::WebTimeRanges Buffered() const override; - blink::WebTimeRanges Seekable() const override; + void SetSinkId(const WebString& sink_id, + WebSetSinkIdCompleteCallback completion_callback) override; + void SetPreload(WebMediaPlayer::Preload preload) override; + WebTimeRanges Buffered() const override; + WebTimeRanges Seekable() const override; // Methods for painting. void Paint(cc::PaintCanvas* canvas, - const blink::WebRect& rect, + const WebRect& rect, cc::PaintFlags& flags, int already_uploaded_id, VideoFrameUploadMetadata* out_metadata) override; @@ -138,9 +134,9 @@ bool HasAudio() const override; // Dimensions of the video. - blink::WebSize NaturalSize() const override; + WebSize NaturalSize() const override; - blink::WebSize VisibleRect() const override; + WebSize VisibleRect() const override; // Getters of playback state. bool Paused() const override; @@ -149,13 +145,12 @@ double CurrentTime() const override; // Internal states of loading and network. - blink::WebMediaPlayer::NetworkState GetNetworkState() const override; - blink::WebMediaPlayer::ReadyState GetReadyState() const override; + WebMediaPlayer::NetworkState GetNetworkState() const override; + WebMediaPlayer::ReadyState GetReadyState() const override; - blink::WebMediaPlayer::SurfaceLayerMode GetVideoSurfaceLayerMode() - const override; + WebMediaPlayer::SurfaceLayerMode GetVideoSurfaceLayerMode() const override; - blink::WebString GetErrorMessage() const override; + WebString GetErrorMessage() const override; bool DidLoadingProgress() override; bool WouldTaintOrigin() const override; @@ -169,7 +164,7 @@ bool HasAvailableVideoFrame() const override; - // blink::WebMediaPlayerDelegate::Observer implementation. + // WebMediaPlayerDelegate::Observer implementation. void OnFrameHidden() override; void OnFrameClosed() override; void OnFrameShown() override; @@ -227,14 +222,14 @@ bool flip_y, bool premultiply_alpha) override; - // blink::WebMediaStreamObserver implementation - void TrackAdded(const blink::WebMediaStreamTrack& track) override; - void TrackRemoved(const blink::WebMediaStreamTrack& track) override; + // WebMediaStreamObserver implementation + void TrackAdded(const WebMediaStreamTrack& track) override; + void TrackRemoved(const WebMediaStreamTrack& track) override; void ActiveStateChanged(bool is_active) override; int GetDelegateId() override; base::Optional<viz::SurfaceId> GetSurfaceId() override; - base::WeakPtr<blink::WebMediaPlayer> AsWeakPtr() override; + base::WeakPtr<WebMediaPlayer> AsWeakPtr() override; void OnDisplayTypeChanged(WebMediaPlayer::DisplayType) override; @@ -255,11 +250,11 @@ // Helpers that set the network/ready state and notifies the client if // they've changed. - void SetNetworkState(blink::WebMediaPlayer::NetworkState state); - void SetReadyState(blink::WebMediaPlayer::ReadyState state); + void SetNetworkState(WebMediaPlayer::NetworkState state); + void SetReadyState(WebMediaPlayer::ReadyState state); // Getter method to |client_|. - blink::WebMediaPlayerClient* get_client() { return client_; } + WebMediaPlayerClient* get_client() { return client_; } // To be run when tracks are added or removed. void Reload(); @@ -270,27 +265,27 @@ void SetGpuMemoryBufferVideoForTesting( media::GpuMemoryBufferVideoFramePool* gpu_memory_buffer_pool); - blink::WebLocalFrame* const frame_; + std::unique_ptr<MediaStreamInternalFrameWrapper> internal_frame_; - blink::WebMediaPlayer::NetworkState network_state_; - blink::WebMediaPlayer::ReadyState ready_state_; + WebMediaPlayer::NetworkState network_state_; + WebMediaPlayer::ReadyState ready_state_; - const blink::WebTimeRanges buffered_; + const WebTimeRanges buffered_; - blink::WebMediaPlayerClient* const client_; + WebMediaPlayerClient* const client_; // WebMediaPlayer notifies the |delegate_| of playback state changes using // |delegate_id_|; an id provided after registering with the delegate. The // WebMediaPlayer may also receive directives (play, pause) from the delegate - // via the blink::WebMediaPlayerDelegate::Observer interface after + // via the WebMediaPlayerDelegate::Observer interface after // registration. // - // NOTE: HTMLMediaElement is a Blink::PausableObject, and will receive a - // call to contextDestroyed() when Blink::Document::shutdown() is called. + // NOTE: HTMLMediaElement is a PausableObject, and will receive a + // call to contextDestroyed() when Document::shutdown() is called. // Document::shutdown() is called before the frame detaches (and before the // frame is destroyed). RenderFrameImpl owns of |delegate_|, and is guaranteed // to outlive |this|. It is therefore safe use a raw pointer directly. - blink::WebMediaPlayerDelegate* delegate_; + WebMediaPlayerDelegate* delegate_; int delegate_id_; // Inner class used for transfering frames on compositor thread to @@ -298,12 +293,11 @@ class FrameDeliverer; std::unique_ptr<FrameDeliverer> frame_deliverer_; - scoped_refptr<blink::WebMediaStreamVideoRenderer> - video_frame_provider_; // Weak + scoped_refptr<WebMediaStreamVideoRenderer> video_frame_provider_; // Weak scoped_refptr<cc::VideoLayer> video_layer_; - scoped_refptr<blink::WebMediaStreamAudioRenderer> audio_renderer_; // Weak + scoped_refptr<WebMediaStreamAudioRenderer> audio_renderer_; // Weak media::PaintCanvasVideoRenderer video_renderer_; bool paused_; @@ -311,7 +305,7 @@ std::unique_ptr<media::MediaLog> media_log_; - std::unique_ptr<blink::WebMediaStreamRendererFactory> renderer_factory_; + std::unique_ptr<WebMediaStreamRendererFactory> renderer_factory_; const scoped_refptr<base::SingleThreadTaskRunner> main_render_task_runner_; const scoped_refptr<base::SingleThreadTaskRunner> io_task_runner_; @@ -326,11 +320,11 @@ scoped_refptr<WebMediaPlayerMSCompositor> compositor_; - const std::string initial_audio_output_device_id_; + const WebString initial_audio_output_device_id_; // The last volume received by setVolume() and the last volume multiplier from // OnVolumeMultiplierUpdate(). The multiplier is typical 1.0, but may be less - // if the blink::WebMediaPlayerDelegate has requested a volume reduction + // if the WebMediaPlayerDelegate has requested a volume reduction // (ducking) for a transient sound. Playout volume is derived by volume * // multiplier. double volume_; @@ -339,22 +333,22 @@ // True if playback should be started upon the next call to OnShown(). Only // used on Android. bool should_play_upon_shown_; - blink::WebMediaStream web_stream_; + WebMediaStream web_stream_; // IDs of the tracks currently played. - blink::WebString current_video_track_id_; - blink::WebString current_audio_track_id_; + WebString current_video_track_id_; + WebString current_audio_track_id_; CreateSurfaceLayerBridgeCB create_bridge_callback_; - std::unique_ptr<blink::WebVideoFrameSubmitter> submitter_; + std::unique_ptr<WebVideoFrameSubmitter> submitter_; // Whether the use of a surface layer instead of a video layer is enabled. - blink::WebMediaPlayer::SurfaceLayerMode surface_layer_mode_ = - blink::WebMediaPlayer::SurfaceLayerMode::kNever; + WebMediaPlayer::SurfaceLayerMode surface_layer_mode_ = + WebMediaPlayer::SurfaceLayerMode::kNever; // Owns the weblayer and obtains/maintains SurfaceIds for // kUseSurfaceLayerForVideo feature. - std::unique_ptr<blink::WebSurfaceLayerBridge> bridge_; + std::unique_ptr<WebSurfaceLayerBridge> bridge_; // Whether the video is known to be opaque or not. bool opaque_ = true; @@ -367,6 +361,6 @@ DISALLOW_COPY_AND_ASSIGN(WebMediaPlayerMS); }; -} // namespace content +} // namespace blink -#endif // CONTENT_RENDERER_MEDIA_STREAM_WEBMEDIAPLAYER_MS_H_ +#endif // THIRD_PARTY_BLINK_PUBLIC_WEB_MODULES_MEDIASTREAM_WEBMEDIAPLAYER_MS_H_
diff --git a/third_party/blink/renderer/core/animation/animation_input_helpers.cc b/third_party/blink/renderer/core/animation/animation_input_helpers.cc index f542174..9981603 100644 --- a/third_party/blink/renderer/core/animation/animation_input_helpers.cc +++ b/third_party/blink/renderer/core/animation/animation_input_helpers.cc
@@ -222,7 +222,7 @@ !IsSVGPrefixed(property)) return nullptr; - if (IsSVGSMILElement(svg_element)) + if (IsA<SVGSMILElement>(svg_element)) return nullptr; String unprefixed_property = RemoveSVGPrefix(property);
diff --git a/third_party/blink/renderer/core/css/css_paint_image_generator.h b/third_party/blink/renderer/core/css/css_paint_image_generator.h index 8e12c17..916a456 100644 --- a/third_party/blink/renderer/core/css/css_paint_image_generator.h +++ b/third_party/blink/renderer/core/css/css_paint_image_generator.h
@@ -52,7 +52,8 @@ // The |container_size| is the container size with subpixel snapping. virtual scoped_refptr<Image> Paint(const ImageResourceObserver&, const FloatSize& container_size, - const CSSStyleValueVector*) = 0; + const CSSStyleValueVector*, + float device_scale_factor) = 0; virtual const Vector<CSSPropertyID>& NativeInvalidationProperties() const = 0; virtual const Vector<AtomicString>& CustomInvalidationProperties() const = 0;
diff --git a/third_party/blink/renderer/core/css/css_paint_value.cc b/third_party/blink/renderer/core/css/css_paint_value.cc index 5aeda58..a4c875a 100644 --- a/third_party/blink/renderer/core/css/css_paint_value.cc +++ b/third_party/blink/renderer/core/css/css_paint_value.cc
@@ -11,7 +11,9 @@ #include "third_party/blink/renderer/core/css/cssom/paint_worklet_input.h" #include "third_party/blink/renderer/core/css/cssom/style_value_factory.h" #include "third_party/blink/renderer/core/css/properties/computed_style_utils.h" +#include "third_party/blink/renderer/core/frame/local_frame.h" #include "third_party/blink/renderer/core/layout/layout_object.h" +#include "third_party/blink/renderer/core/page/page.h" #include "third_party/blink/renderer/platform/graphics/image.h" #include "third_party/blink/renderer/platform/wtf/text/string_builder.h" @@ -72,13 +74,24 @@ if (!ParseInputArguments(document)) return nullptr; + // TODO(crbug.com/946515): Break dependency on LayoutObject. + const LayoutObject& layout_object = static_cast<const LayoutObject&>(client); + + // TODO(crbug.com/716231): Remove this hack once zoom_for_dsf is enabled on + // all platforms (currently not enabled on Mac). + float device_scale_factor = 1; + if (layout_object.GetFrame() && layout_object.GetFrame()->GetPage()) { + // The value of DeviceScaleFactorDeprecated would be 1 on a platform where + // zoom_for_dsf is enabled, even if we run chrome with + // --force-device-scale-factor with a value that is not 1. + device_scale_factor = + layout_object.GetFrame()->GetPage()->DeviceScaleFactorDeprecated(); + } + // For Off-Thread PaintWorklet, we just collect the necessary inputs together // and defer the actual JavaScript call until much later (during cc Raster). if (RuntimeEnabledFeatures::OffMainThreadCSSPaintEnabled()) { if (paint_off_thread_) { - // TODO(crbug.com/946515): Break dependency on LayoutObject. - const LayoutObject& layout_object = - static_cast<const LayoutObject&>(client); Vector<CSSPropertyID> native_properties = generator_->NativeInvalidationProperties(); Vector<AtomicString> custom_properties = @@ -102,7 +115,8 @@ } } - return generator_->Paint(client, target_size, parsed_input_arguments_); + return generator_->Paint(client, target_size, parsed_input_arguments_, + device_scale_factor); } void CSSPaintValue::BuildInputArgumentValues(
diff --git a/third_party/blink/renderer/core/css/css_paint_value_test.cc b/third_party/blink/renderer/core/css/css_paint_value_test.cc index d412d5f..7fead39 100644 --- a/third_party/blink/renderer/core/css/css_paint_value_test.cc +++ b/third_party/blink/renderer/core/css/css_paint_value_test.cc
@@ -66,10 +66,11 @@ .WillByDefault(ReturnRef(input_argument_types_)); } - MOCK_METHOD3(Paint, + MOCK_METHOD4(Paint, scoped_refptr<Image>(const ImageResourceObserver&, const FloatSize& container_size, - const CSSStyleValueVector*)); + const CSSStyleValueVector*, + float device_scale_factor)); MOCK_CONST_METHOD0(NativeInvalidationProperties, Vector<CSSPropertyID>&()); MOCK_CONST_METHOD0(CustomInvalidationProperties, Vector<AtomicString>&()); MOCK_CONST_METHOD0(HasAlpha, bool()); @@ -118,7 +119,7 @@ // Initially the generator is not ready, so GetImage should fail (and no paint // should happen). - EXPECT_CALL(*mock_generator, Paint(_, _, _)).Times(0); + EXPECT_CALL(*mock_generator, Paint(_, _, _, _)).Times(0); EXPECT_FALSE( paint_value->GetImage(*target, GetDocument(), style, target_size)); @@ -127,7 +128,7 @@ // In off-thread CSS Paint, the actual paint call is deferred and so will // never happen. if (!RuntimeEnabledFeatures::OffMainThreadCSSPaintEnabled()) { - EXPECT_CALL(*mock_generator, Paint(_, _, _)) + EXPECT_CALL(*mock_generator, Paint(_, _, _, _)) .WillRepeatedly( Return(PaintGeneratedImage::Create(nullptr, target_size))); }
diff --git a/third_party/blink/renderer/core/css/properties/computed_style_utils.cc b/third_party/blink/renderer/core/css/properties/computed_style_utils.cc index fa8511a..18f6fd0 100644 --- a/third_party/blink/renderer/core/css/properties/computed_style_utils.cc +++ b/third_party/blink/renderer/core/css/properties/computed_style_utils.cc
@@ -2295,6 +2295,23 @@ return pair; } +CSSValuePair* ComputedStyleUtils::ValuesForPlaceShorthand( + const StylePropertyShorthand& shorthand, + const ComputedStyle& style, + const LayoutObject* layout_object, + Node* styled_node, + bool allow_visited_style) { + const CSSValue* align_value = + shorthand.properties()[0]->CSSValueFromComputedStyle( + style, layout_object, styled_node, allow_visited_style); + const CSSValue* justify_value = + shorthand.properties()[1]->CSSValueFromComputedStyle( + style, layout_object, styled_node, allow_visited_style); + + return MakeGarbageCollected<CSSValuePair>(align_value, justify_value, + CSSValuePair::kDropIdenticalValues); +} + static CSSValue* ExpandNoneLigaturesValue() { CSSValueList* list = CSSValueList::CreateSpaceSeparated(); list->Append(*CSSIdentifierValue::Create(CSSValueID::kNoCommonLigatures));
diff --git a/third_party/blink/renderer/core/css/properties/computed_style_utils.h b/third_party/blink/renderer/core/css/properties/computed_style_utils.h index 96ad29e..2b3f3d0c 100644 --- a/third_party/blink/renderer/core/css/properties/computed_style_utils.h +++ b/third_party/blink/renderer/core/css/properties/computed_style_utils.h
@@ -197,6 +197,11 @@ const LayoutObject*, Node*, bool allow_visited_style); + static CSSValuePair* ValuesForPlaceShorthand(const StylePropertyShorthand&, + const ComputedStyle&, + const LayoutObject*, + Node*, + bool allow_visited_style); static CSSValue* ValuesForFontVariantProperty(const ComputedStyle&, const LayoutObject*, Node*,
diff --git a/third_party/blink/renderer/core/css/properties/shorthands/shorthands_custom.cc b/third_party/blink/renderer/core/css/properties/shorthands/shorthands_custom.cc index 0ddf9c8..4679ae1 100644 --- a/third_party/blink/renderer/core/css/properties/shorthands/shorthands_custom.cc +++ b/third_party/blink/renderer/core/css/properties/shorthands/shorthands_custom.cc
@@ -2591,9 +2591,7 @@ const LayoutObject* layout_object, Node* styled_node, bool allow_visited_style) const { - // TODO (jfernandez): The spec states that we should return the specified - // value. - return ComputedStyleUtils::ValuesForShorthandProperty( + return ComputedStyleUtils::ValuesForPlaceShorthand( placeContentShorthand(), style, layout_object, styled_node, allow_visited_style); } @@ -2645,9 +2643,7 @@ const LayoutObject* layout_object, Node* styled_node, bool allow_visited_style) const { - // TODO (jfernandez): The spec states that we should return the specified - // value. - return ComputedStyleUtils::ValuesForShorthandProperty( + return ComputedStyleUtils::ValuesForPlaceShorthand( placeItemsShorthand(), style, layout_object, styled_node, allow_visited_style); } @@ -2698,9 +2694,7 @@ const LayoutObject* layout_object, Node* styled_node, bool allow_visited_style) const { - // TODO (jfernandez): The spec states that we should return the specified - // value. - return ComputedStyleUtils::ValuesForShorthandProperty( + return ComputedStyleUtils::ValuesForPlaceShorthand( placeSelfShorthand(), style, layout_object, styled_node, allow_visited_style); }
diff --git a/third_party/blink/renderer/core/dom/element.cc b/third_party/blink/renderer/core/dom/element.cc index 71f098b..c43e895 100644 --- a/third_party/blink/renderer/core/dom/element.cc +++ b/third_party/blink/renderer/core/dom/element.cc
@@ -4473,7 +4473,10 @@ } StyleRecalcChange change(StyleRecalcChange::kRecalcDescendants); - if (text_node_changed) + // Remaining text part should be next to first-letter pseudo element. + // See http://crbug.com/984389 for details. + if (text_node_changed || remaining_text_layout_object->PreviousSibling() != + element->GetLayoutObject()) change = change.ForceReattachLayoutTree(); element->RecalcStyle(change);
diff --git a/third_party/blink/renderer/core/dom/events/event.cc b/third_party/blink/renderer/core/dom/events/event.cc index b47c354..5539e59 100644 --- a/third_party/blink/renderer/core/dom/events/event.cc +++ b/third_party/blink/renderer/core/dom/events/event.cc
@@ -245,7 +245,6 @@ void Event::preventDefault() { if (handling_passive_ != PassiveMode::kNotPassive && handling_passive_ != PassiveMode::kNotPassiveDefault) { - prevent_default_called_during_passive_ = true; const LocalDOMWindow* window = event_path_ ? event_path_->GetWindowEventContext().Window() : nullptr; @@ -312,7 +311,6 @@ void Event::SetHandlingPassive(PassiveMode mode) { handling_passive_ = mode; - prevent_default_called_during_passive_ = false; } HeapVector<Member<EventTarget>> Event::PathInternal(ScriptState* script_state,
diff --git a/third_party/blink/renderer/core/dom/events/event.h b/third_party/blink/renderer/core/dom/events/event.h index ef3858e..2274afba 100644 --- a/third_party/blink/renderer/core/dom/events/event.h +++ b/third_party/blink/renderer/core/dom/events/event.h
@@ -279,10 +279,6 @@ void SetHandlingPassive(PassiveMode); - bool PreventDefaultCalledDuringPassive() const { - return prevent_default_called_during_passive_; - } - bool PreventDefaultCalledOnUncancelableEvent() const { return prevent_default_called_on_uncancelable_event_; } @@ -332,9 +328,6 @@ unsigned was_initialized_ : 1; unsigned is_trusted_ : 1; - // Whether preventDefault was called when |handling_passive_| is - // true. This field is reset on each call to SetHandlingPassive. - unsigned prevent_default_called_during_passive_ : 1; // Whether preventDefault was called on uncancelable event. unsigned prevent_default_called_on_uncancelable_event_ : 1;
diff --git a/third_party/blink/renderer/core/dom/events/event_target.cc b/third_party/blink/renderer/core/dom/events/event_target.cc index b891311..a5e25db 100644 --- a/third_party/blink/renderer/core/dom/events/event_target.cc +++ b/third_party/blink/renderer/core/dom/events/event_target.cc
@@ -906,7 +906,6 @@ break; event.SetHandlingPassive(EventPassiveMode(registered_listener)); - bool passive_forced = registered_listener.PassiveForcedForDocumentTarget(); probe::UserCallback probe(context, nullptr, event.type(), false, this); probe::AsyncTask async_task(context, listener, "event", @@ -927,17 +926,6 @@ now - event.PlatformTimeStamp()); } - if (passive_forced) { - DEFINE_STATIC_LOCAL(EnumerationHistogram, passive_forced_histogram, - ("Event.PassiveForcedEventDispatchCancelled", - kPassiveForcedListenerResultTypeMax)); - PassiveForcedListenerResultType breakage_type = kPreventDefaultNotCalled; - if (event.PreventDefaultCalledDuringPassive()) - breakage_type = kDocumentLevelTouchPreventDefaultCalled; - - passive_forced_histogram.Count(breakage_type); - } - event.SetHandlingPassive(Event::PassiveMode::kNotPassive); CHECK_LE(i, size);
diff --git a/third_party/blink/renderer/core/dom/events/event_target_test.cc b/third_party/blink/renderer/core/dom/events/event_target_test.cc index 6f9250e3..b0247e2 100644 --- a/third_party/blink/renderer/core/dom/events/event_target_test.cc +++ b/third_party/blink/renderer/core/dom/events/event_target_test.cc
@@ -8,49 +8,12 @@ namespace blink { -enum PassiveForcedListenerResultType { - kPreventDefaultNotCalled, - kDocumentLevelTouchPreventDefaultCalled -}; - class EventTargetTest : public RenderingTest { public: EventTargetTest() = default; ~EventTargetTest() override = default; }; -TEST_F(EventTargetTest, PreventDefaultNotCalled) { - GetDocument().GetSettings()->SetScriptEnabled(true); - HistogramTester histogram_tester; - GetDocument().GetFrame()->GetScriptController().ExecuteScriptInMainWorld( - "window.addEventListener('touchstart', function(e) {}, {});" - "window.dispatchEvent(new TouchEvent('touchstart', " - "{cancelable: " - "false}));"); - - histogram_tester.ExpectTotalCount("Event.PassiveForcedEventDispatchCancelled", - 1); - histogram_tester.ExpectUniqueSample( - "Event.PassiveForcedEventDispatchCancelled", kPreventDefaultNotCalled, 1); -} - -TEST_F(EventTargetTest, PreventDefaultCalled) { - GetDocument().GetSettings()->SetScriptEnabled(true); - HistogramTester histogram_tester; - GetDocument().GetFrame()->GetScriptController().ExecuteScriptInMainWorld( - "window.addEventListener('touchstart', function(e) " - "{e.preventDefault();}, {});" - "window.dispatchEvent(new TouchEvent('touchstart', " - "{cancelable: " - "false}));"); - - histogram_tester.ExpectTotalCount("Event.PassiveForcedEventDispatchCancelled", - 1); - histogram_tester.ExpectUniqueSample( - "Event.PassiveForcedEventDispatchCancelled", - kDocumentLevelTouchPreventDefaultCalled, 1); -} - TEST_F(EventTargetTest, UseCountPassiveTouchEventListener) { EXPECT_FALSE( GetDocument().IsUseCounted(WebFeature::kPassiveTouchEventListener));
diff --git a/third_party/blink/renderer/core/events/event_type_names.json5 b/third_party/blink/renderer/core/events/event_type_names.json5 index 2ed6257..4fdda0dc 100644 --- a/third_party/blink/renderer/core/events/event_type_names.json5 +++ b/third_party/blink/renderer/core/events/event_type_names.json5
@@ -222,6 +222,7 @@ "progress", "processorerror", "push", + "pushsubscriptionchange", "quicstream", "ratechange", "reading",
diff --git a/third_party/blink/renderer/core/html/parser/html_parser_scheduler.cc b/third_party/blink/renderer/core/html/parser/html_parser_scheduler.cc index c8fbb18..156092ec 100644 --- a/third_party/blink/renderer/core/html/parser/html_parser_scheduler.cc +++ b/third_party/blink/renderer/core/html/parser/html_parser_scheduler.cc
@@ -37,13 +37,12 @@ SpeculationsPumpSession::SpeculationsPumpSession(unsigned& nesting_level) : NestingLevelIncrementer(nesting_level), - start_time_(CurrentTime()), processed_element_tokens_(0) {} SpeculationsPumpSession::~SpeculationsPumpSession() = default; -inline double SpeculationsPumpSession::ElapsedTime() const { - return CurrentTime() - start_time_; +inline base::TimeDelta SpeculationsPumpSession::ElapsedTime() const { + return start_time_.Elapsed(); } void SpeculationsPumpSession::AddedElementTokens(size_t count) { @@ -103,7 +102,8 @@ if (ThreadScheduler::Current()->ShouldYieldForHighPriorityWork()) return true; - const double kParserTimeLimit = 0.5; + const base::TimeDelta kParserTimeLimit = + base::TimeDelta::FromMilliseconds(500); if (session.ElapsedTime() > kParserTimeLimit) return true;
diff --git a/third_party/blink/renderer/core/html/parser/html_parser_scheduler.h b/third_party/blink/renderer/core/html/parser/html_parser_scheduler.h index 0c15cad..d947fcd 100644 --- a/third_party/blink/renderer/core/html/parser/html_parser_scheduler.h +++ b/third_party/blink/renderer/core/html/parser/html_parser_scheduler.h
@@ -29,6 +29,7 @@ #include "base/macros.h" #include "base/memory/scoped_refptr.h" #include "base/single_thread_task_runner.h" +#include "base/timer/elapsed_timer.h" #include "third_party/blink/renderer/core/html/parser/nesting_level_incrementer.h" #include "third_party/blink/renderer/platform/scheduler/public/post_cancellable_task.h" #include "third_party/blink/renderer/platform/wtf/allocator/allocator.h" @@ -44,12 +45,12 @@ SpeculationsPumpSession(unsigned& nesting_level); ~SpeculationsPumpSession(); - double ElapsedTime() const; + base::TimeDelta ElapsedTime() const; void AddedElementTokens(size_t count); size_t ProcessedElementTokens() const { return processed_element_tokens_; } private: - double start_time_; + base::ElapsedTimer start_time_; size_t processed_element_tokens_; };
diff --git a/third_party/blink/renderer/core/input/fallback_cursor_event_manager.cc b/third_party/blink/renderer/core/input/fallback_cursor_event_manager.cc index 0be5aea..7da8a25 100644 --- a/third_party/blink/renderer/core/input/fallback_cursor_event_manager.cc +++ b/third_party/blink/renderer/core/input/fallback_cursor_event_manager.cc
@@ -392,6 +392,8 @@ HitTestResult hit_test_result = HitTest(root_frame_->GetDocument()->GetLayoutView(), location); Node* node = hit_test_result.InnerNode(); + if (!node) + return; // Click on input boxes or media node should hide the cursor. if (HasEditableStyle(*node) || node->IsMediaElement()) {
diff --git a/third_party/blink/renderer/core/layout/layout_analyzer.cc b/third_party/blink/renderer/core/layout/layout_analyzer.cc index 3778ade79..075b463d 100644 --- a/third_party/blink/renderer/core/layout/layout_analyzer.cc +++ b/third_party/blink/renderer/core/layout/layout_analyzer.cc
@@ -47,7 +47,6 @@ } void LayoutAnalyzer::Reset() { - start_ms_ = CurrentTimeMS(); depth_ = 0; for (size_t i = 0; i < kNumCounters; ++i) { counters_[i] = 0;
diff --git a/third_party/blink/renderer/core/layout/layout_analyzer.h b/third_party/blink/renderer/core/layout/layout_analyzer.h index ebacd99..aaa0145 100644 --- a/third_party/blink/renderer/core/layout/layout_analyzer.h +++ b/third_party/blink/renderer/core/layout/layout_analyzer.h
@@ -88,7 +88,6 @@ private: const char* NameForCounter(Counter) const; - double start_ms_; unsigned depth_; unsigned counters_[kNumCounters]; DISALLOW_COPY_AND_ASSIGN(LayoutAnalyzer);
diff --git a/third_party/blink/renderer/core/layout/layout_text_fragment_test.cc b/third_party/blink/renderer/core/layout/layout_text_fragment_test.cc index 165d4b05..3ab39f3 100644 --- a/third_party/blink/renderer/core/layout/layout_text_fragment_test.cc +++ b/third_party/blink/renderer/core/layout/layout_text_fragment_test.cc
@@ -4,6 +4,7 @@ #include "third_party/blink/renderer/core/layout/layout_text_fragment.h" +#include "third_party/blink/renderer/core/dom/first_letter_pseudo_element.h" #include "third_party/blink/renderer/core/html/html_head_element.h" #include "third_party/blink/renderer/core/testing/core_unit_test_helper.h" #include "third_party/blink/renderer/platform/runtime_enabled_features.h" @@ -444,4 +445,30 @@ EXPECT_EQ("x", letter_x.GetLayoutObject()->GetFirstLetterPart()->GetText()); } +// For http://crbug.com/984389 +TEST_P(ParameterizedLayoutTextFragmentTest, SplitTextWithZero) { + // Note: |V8TestingScope| is needed for |Text::splitText()|. + V8TestingScope scope; + + SetBodyInnerHTML( + "<style>div::first-letter {color: red;}</style>" + "<div><b id=sample> x y</b></div>"); + const Element& sample = *GetElementById("sample"); + // Make " " "x y" + To<Text>(sample.firstChild())->splitText(1, ASSERT_NO_EXCEPTION); + UpdateAllLifecyclePhasesForTest(); + + // Make "" " " "x y" + To<Text>(sample.firstChild())->splitText(0, ASSERT_NO_EXCEPTION); + UpdateAllLifecyclePhasesForTest(); + + Text& xy = To<Text>(*sample.lastChild()); + FirstLetterPseudoElement& first_letter_element = + *ToLayoutTextFragment(xy.GetLayoutObject()) + ->GetFirstLetterPseudoElement(); + EXPECT_EQ(first_letter_element.GetLayoutObject(), + xy.GetLayoutObject()->PreviousSibling()) + << "first-letter remaining part should be next to first-letter part"; +} + } // namespace blink
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_resource_filter_primitive.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_resource_filter_primitive.cc index de5aacbe..f697338 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_resource_filter_primitive.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_resource_filter_primitive.cc
@@ -59,8 +59,7 @@ if (!old_style) return; DCHECK(GetElement()); - SVGFilterPrimitiveStandardAttributes& element = - ToSVGFilterPrimitiveStandardAttributes(*GetElement()); + auto& element = To<SVGFilterPrimitiveStandardAttributes>(*GetElement()); const SVGComputedStyle& new_style = StyleRef().SvgStyle(); if (IsSVGFEFloodElement(element) || IsSVGFEDropShadowElement(element)) { CheckForColorChange(element, svg_names::kFloodColorAttr, diff,
diff --git a/third_party/blink/renderer/core/loader/threadable_loader.cc b/third_party/blink/renderer/core/loader/threadable_loader.cc index 71ff8f7f..c77f4ad 100644 --- a/third_party/blink/renderer/core/loader/threadable_loader.cc +++ b/third_party/blink/renderer/core/loader/threadable_loader.cc
@@ -165,6 +165,7 @@ preflight_request->SetHttpMethod(http_names::kOPTIONS); preflight_request->SetHttpHeaderField(http_names::kAccessControlRequestMethod, request.HttpMethod()); + preflight_request->SetMode(network::mojom::RequestMode::kCors); preflight_request->SetPriority(request.Priority()); preflight_request->SetRequestContext(request.GetRequestContext()); preflight_request->SetCredentialsMode(network::mojom::CredentialsMode::kOmit);
diff --git a/third_party/blink/renderer/core/svg/animation/svg_smil_element.cc b/third_party/blink/renderer/core/svg/animation/svg_smil_element.cc index 3c3f9d6..3b9057b 100644 --- a/third_party/blink/renderer/core/svg/animation/svg_smil_element.cc +++ b/third_party/blink/renderer/core/svg/animation/svg_smil_element.cc
@@ -153,12 +153,13 @@ DCHECK(!base_id_.IsEmpty()); DCHECK_EQ(type_, kSyncbase); Element* element = timed_element.GetTreeScope().getElementById(base_id_); - if (!element || !IsSVGSMILElement(*element)) { + auto* svg_smil_element = DynamicTo<SVGSMILElement>(element); + if (!svg_smil_element) { base_element_ = nullptr; return; } - base_element_ = ToSVGSMILElement(element); - ToSVGSMILElement(*element).AddSyncBaseDependent(timed_element); + base_element_ = svg_smil_element; + svg_smil_element->AddSyncBaseDependent(timed_element); } void SVGSMILElement::Condition::DisconnectSyncBase( @@ -166,7 +167,7 @@ DCHECK_EQ(type_, kSyncbase); if (!base_element_) return; - ToSVGSMILElement(*base_element_).RemoveSyncBaseDependent(timed_element); + To<SVGSMILElement>(*base_element_).RemoveSyncBaseDependent(timed_element); base_element_ = nullptr; }
diff --git a/third_party/blink/renderer/core/svg/animation/svg_smil_element.h b/third_party/blink/renderer/core/svg/animation/svg_smil_element.h index 31adf726..6916d016 100644 --- a/third_party/blink/renderer/core/svg/animation/svg_smil_element.h +++ b/third_party/blink/renderer/core/svg/animation/svg_smil_element.h
@@ -309,8 +309,15 @@ element.HasTagName((svg_names::kDiscardTag)); } -DEFINE_SVGELEMENT_TYPE_CASTS_WITH_FUNCTION(SVGSMILElement); +template <> +struct DowncastTraits<SVGSMILElement> { + static bool AllowFrom(const Node& node) { + auto* svg_element = DynamicTo<SVGElement>(node); + return svg_element && IsSVGSMILElement(*svg_element); + } +}; +DEFINE_SVGELEMENT_TYPE_CASTS_WITH_FUNCTION(SVGSMILElement); } // namespace blink #endif // THIRD_PARTY_BLINK_RENDERER_CORE_SVG_ANIMATION_SVG_SMIL_ELEMENT_H_
diff --git a/third_party/blink/renderer/core/svg/graphics/filters/svg_filter_builder.cc b/third_party/blink/renderer/core/svg/graphics/filters/svg_filter_builder.cc index a2080f07..751dc6b 100644 --- a/third_party/blink/renderer/core/svg/graphics/filters/svg_filter_builder.cc +++ b/third_party/blink/renderer/core/svg/graphics/filters/svg_filter_builder.cc
@@ -179,8 +179,7 @@ if (!element->IsFilterEffect()) continue; - SVGFilterPrimitiveStandardAttributes& effect_element = - ToSVGFilterPrimitiveStandardAttributes(*element); + auto& effect_element = To<SVGFilterPrimitiveStandardAttributes>(*element); FilterEffect* effect = effect_element.Build(this, filter); if (!effect) continue;
diff --git a/third_party/blink/renderer/core/svg/svg_a_element.cc b/third_party/blink/renderer/core/svg/svg_a_element.cc index 0a7bb9f2..d3d7015 100644 --- a/third_party/blink/renderer/core/svg/svg_a_element.cc +++ b/third_party/blink/renderer/core/svg/svg_a_element.cc
@@ -120,8 +120,9 @@ if (url[0] == '#') { Element* target_element = GetTreeScope().getElementById(AtomicString(url.Substring(1))); - if (target_element && IsSVGSMILElement(*target_element)) { - ToSVGSMILElement(target_element)->BeginByLinkActivation(); + if (auto* svg_smil_element = + DynamicTo<SVGSMILElement>(target_element)) { + svg_smil_element->BeginByLinkActivation(); event.SetDefaultHandled(); return; }
diff --git a/third_party/blink/renderer/core/svg/svg_animate_element.cc b/third_party/blink/renderer/core/svg/svg_animate_element.cc index 7a916f3..8096b36 100644 --- a/third_party/blink/renderer/core/svg/svg_animate_element.cc +++ b/third_party/blink/renderer/core/svg/svg_animate_element.cc
@@ -339,8 +339,7 @@ DCHECK_EQ(from_property_->GetType(), GetAnimatedPropertyType()); DCHECK(to_property_); - SVGAnimateElement* result_animation_element = - ToSVGAnimateElement(result_element); + auto* result_animation_element = To<SVGAnimateElement>(result_element); DCHECK(result_animation_element->animated_value_); DCHECK_EQ(result_animation_element->GetAnimatedPropertyType(), GetAnimatedPropertyType());
diff --git a/third_party/blink/renderer/core/svg/svg_animate_element.h b/third_party/blink/renderer/core/svg/svg_animate_element.h index 04d0666..094435ae 100644 --- a/third_party/blink/renderer/core/svg/svg_animate_element.h +++ b/third_party/blink/renderer/core/svg/svg_animate_element.h
@@ -137,7 +137,13 @@ element.HasTagName(svg_names::kSetTag); } -DEFINE_SVGELEMENT_TYPE_CASTS_WITH_FUNCTION(SVGAnimateElement); +template <> +struct DowncastTraits<SVGAnimateElement> { + static bool AllowFrom(const Node& node) { + auto* element = DynamicTo<SVGElement>(node); + return element && IsSVGAnimateElement(*element); + } +}; } // namespace blink
diff --git a/third_party/blink/renderer/core/svg/svg_animation_element.cc b/third_party/blink/renderer/core/svg/svg_animation_element.cc index e1b31c52..8b28853 100644 --- a/third_party/blink/renderer/core/svg/svg_animation_element.cc +++ b/third_party/blink/renderer/core/svg/svg_animation_element.cc
@@ -470,9 +470,8 @@ } CalcMode calc_mode = GetCalcMode(); - if (IsSVGAnimateElement(*this)) { - SVGAnimateElement& animate_element = ToSVGAnimateElement(*this); - if (!animate_element.AnimatedPropertyTypeSupportsAddition()) + if (auto* animate_element = DynamicTo<SVGAnimateElement>(this)) { + if (!animate_element->AnimatedPropertyTypeSupportsAddition()) calc_mode = kCalcModeDiscrete; } if (!key_points_.IsEmpty() && calc_mode != kCalcModePaced)
diff --git a/third_party/blink/renderer/core/svg/svg_filter_primitive_standard_attributes.cc b/third_party/blink/renderer/core/svg/svg_filter_primitive_standard_attributes.cc index a0c122aa..9edbeaa 100644 --- a/third_party/blink/renderer/core/svg/svg_filter_primitive_standard_attributes.cc +++ b/third_party/blink/renderer/core/svg/svg_filter_primitive_standard_attributes.cc
@@ -190,12 +190,11 @@ } void InvalidateFilterPrimitiveParent(SVGElement& element) { - auto* svg_parent = DynamicTo<SVGElement>(element.parentElement()); + auto* svg_parent = + DynamicTo<SVGFilterPrimitiveStandardAttributes>(element.parentElement()); if (!svg_parent) return; - if (!IsSVGFilterPrimitiveStandardAttributes(*svg_parent)) - return; - ToSVGFilterPrimitiveStandardAttributes(*svg_parent).Invalidate(); + svg_parent->Invalidate(); } } // namespace blink
diff --git a/third_party/blink/renderer/core/svg/svg_filter_primitive_standard_attributes.h b/third_party/blink/renderer/core/svg/svg_filter_primitive_standard_attributes.h index 2aed48ff..b0271c5 100644 --- a/third_party/blink/renderer/core/svg/svg_filter_primitive_standard_attributes.h +++ b/third_party/blink/renderer/core/svg/svg_filter_primitive_standard_attributes.h
@@ -85,8 +85,13 @@ return element.IsFilterEffect(); } -DEFINE_SVGELEMENT_TYPE_CASTS_WITH_FUNCTION( - SVGFilterPrimitiveStandardAttributes); +template <> +struct DowncastTraits<SVGFilterPrimitiveStandardAttributes> { + static bool AllowFrom(const Node& node) { + auto* element = DynamicTo<SVGElement>(node); + return element && IsSVGFilterPrimitiveStandardAttributes(*element); + } +}; } // namespace blink
diff --git a/third_party/blink/renderer/modules/BUILD.gn b/third_party/blink/renderer/modules/BUILD.gn index 49255bd..ca586dc0 100644 --- a/third_party/blink/renderer/modules/BUILD.gn +++ b/third_party/blink/renderer/modules/BUILD.gn
@@ -350,6 +350,7 @@ "mediastream/mock_mojo_media_stream_dispatcher_host.h", "mediastream/video_track_adapter_unittest.cc", "mediastream/webaudio_media_stream_audio_sink_test.cc", + "mediastream/webmediaplayer_ms_test.cc", "nfc/nfc_proxy_test.cc", "notifications/notification_data_test.cc", "notifications/notification_resources_loader_test.cc",
diff --git a/third_party/blink/renderer/modules/csspaint/css_paint_image_generator_impl.cc b/third_party/blink/renderer/modules/csspaint/css_paint_image_generator_impl.cc index 4b8fe31..976072b5 100644 --- a/third_party/blink/renderer/modules/csspaint/css_paint_image_generator_impl.cc +++ b/third_party/blink/renderer/modules/csspaint/css_paint_image_generator_impl.cc
@@ -54,8 +54,10 @@ scoped_refptr<Image> CSSPaintImageGeneratorImpl::Paint( const ImageResourceObserver& observer, const FloatSize& container_size, - const CSSStyleValueVector* data) { - return paint_worklet_->Paint(name_, observer, container_size, data); + const CSSStyleValueVector* data, + float device_scale_factor) { + return paint_worklet_->Paint(name_, observer, container_size, data, + device_scale_factor); } bool CSSPaintImageGeneratorImpl::HasDocumentDefinition() const {
diff --git a/third_party/blink/renderer/modules/csspaint/css_paint_image_generator_impl.h b/third_party/blink/renderer/modules/csspaint/css_paint_image_generator_impl.h index 6d37117..4d176b4 100644 --- a/third_party/blink/renderer/modules/csspaint/css_paint_image_generator_impl.h +++ b/third_party/blink/renderer/modules/csspaint/css_paint_image_generator_impl.h
@@ -35,7 +35,8 @@ // The |container_size| is without subpixel snapping. scoped_refptr<Image> Paint(const ImageResourceObserver&, const FloatSize& container_size, - const CSSStyleValueVector*) final; + const CSSStyleValueVector*, + float device_scale_factor) final; const Vector<CSSPropertyID>& NativeInvalidationProperties() const final; const Vector<AtomicString>& CustomInvalidationProperties() const final; bool HasAlpha() const final;
diff --git a/third_party/blink/renderer/modules/csspaint/paint_worklet.cc b/third_party/blink/renderer/modules/csspaint/paint_worklet.cc index 336f06de..6c69827 100644 --- a/third_party/blink/renderer/modules/csspaint/paint_worklet.cc +++ b/third_party/blink/renderer/modules/csspaint/paint_worklet.cc
@@ -101,7 +101,8 @@ scoped_refptr<Image> PaintWorklet::Paint(const String& name, const ImageResourceObserver& observer, const FloatSize& container_size, - const CSSStyleValueVector* data) { + const CSSStyleValueVector* data, + float device_scale_factor) { if (!document_definition_map_.Contains(name)) return nullptr; @@ -121,17 +122,6 @@ static_cast<const LayoutObject&>(observer); float zoom = layout_object.StyleRef().EffectiveZoom(); - // TODO(crbug.com/716231): Remove this hack once zoom_for_dsf is enabled on - // all platforms (currently not enabled on Mac). - float device_scale_factor = 1; - if (layout_object.GetFrame() && layout_object.GetFrame()->GetPage()) { - // The value of DeviceScaleFactorDeprecated would be 1 on a platform where - // zoom_for_dsf is enabled, even if we run chrome with - // --force-device-scale-factor with a value that is not 1. - device_scale_factor = - layout_object.GetFrame()->GetPage()->DeviceScaleFactorDeprecated(); - } - StylePropertyMapReadOnly* style_map = MakeGarbageCollected<PrepopulatedComputedStylePropertyMap>( layout_object.GetDocument(), layout_object.StyleRef(),
diff --git a/third_party/blink/renderer/modules/csspaint/paint_worklet.h b/third_party/blink/renderer/modules/csspaint/paint_worklet.h index 717fee2..e6f8d2f 100644 --- a/third_party/blink/renderer/modules/csspaint/paint_worklet.h +++ b/third_party/blink/renderer/modules/csspaint/paint_worklet.h
@@ -42,7 +42,8 @@ scoped_refptr<Image> Paint(const String& name, const ImageResourceObserver&, const FloatSize& container_size, - const CSSStyleValueVector*); + const CSSStyleValueVector*, + float device_scale_factor); int WorkletId() const { return worklet_id_; } void Trace(blink::Visitor*) override;
diff --git a/third_party/blink/renderer/modules/filesystem/file_writer.cc b/third_party/blink/renderer/modules/filesystem/file_writer.cc index c91f83f..d7cd724 100644 --- a/third_party/blink/renderer/modules/filesystem/file_writer.cc +++ b/third_party/blink/renderer/modules/filesystem/file_writer.cc
@@ -43,7 +43,8 @@ namespace blink { static const int kMaxRecursionDepth = 3; -static const double kProgressNotificationIntervalMS = 50; +static const base::TimeDelta kProgressNotificationInterval = + base::TimeDelta::FromMilliseconds(50); static constexpr uint64_t kMaxTruncateLength = std::numeric_limits<uint64_t>::max(); @@ -57,7 +58,6 @@ truncate_length_(kMaxTruncateLength), num_aborts_(0), recursion_depth_(0), - last_progress_notification_time_ms_(0), request_id_(0) {} FileWriter::~FileWriter() { @@ -182,11 +182,11 @@ uint64_t num_aborts = num_aborts_; // We could get an abort in the handler for this event. If we do, it's // already handled the cleanup and signalCompletion call. - double now = CurrentTimeMS(); - if (complete || !last_progress_notification_time_ms_ || - (now - last_progress_notification_time_ms_ > - kProgressNotificationIntervalMS)) { - last_progress_notification_time_ms_ = now; + base::TimeTicks now = base::TimeTicks::Now(); + if (complete || !last_progress_notification_time_.is_null() || + (now - last_progress_notification_time_ > + kProgressNotificationInterval)) { + last_progress_notification_time_ = now; FireEvent(event_type_names::kProgress); }
diff --git a/third_party/blink/renderer/modules/filesystem/file_writer.h b/third_party/blink/renderer/modules/filesystem/file_writer.h index adb3dbc..b0902a7d 100644 --- a/third_party/blink/renderer/modules/filesystem/file_writer.h +++ b/third_party/blink/renderer/modules/filesystem/file_writer.h
@@ -127,7 +127,7 @@ uint64_t truncate_length_; uint64_t num_aborts_; uint8_t recursion_depth_; - double last_progress_notification_time_ms_; + base::TimeTicks last_progress_notification_time_; Member<Blob> blob_being_written_; int request_id_; };
diff --git a/third_party/blink/renderer/modules/mediastream/BUILD.gn b/third_party/blink/renderer/modules/mediastream/BUILD.gn index 20c35e5..10efbbd8 100644 --- a/third_party/blink/renderer/modules/mediastream/BUILD.gn +++ b/third_party/blink/renderer/modules/mediastream/BUILD.gn
@@ -60,6 +60,9 @@ "video_track_adapter_settings.cc", "web_media_stream_utils.cc", "webaudio_media_stream_audio_sink.cc", + "webmediaplayer_ms.cc", + "webmediaplayer_ms_compositor.cc", + "webmediaplayer_ms_compositor.h", ] }
diff --git a/third_party/blink/renderer/modules/mediastream/DEPS b/third_party/blink/renderer/modules/mediastream/DEPS index de4a7a0..dc5c575 100644 --- a/third_party/blink/renderer/modules/mediastream/DEPS +++ b/third_party/blink/renderer/modules/mediastream/DEPS
@@ -12,6 +12,19 @@ "+base/threading/sequenced_task_runner_handle.h", "+base/threading/thread_task_runner_handle.h", + # webmediaplayer_ms{_compositor}.cc includes. + "+base/values.h", + "+cc/layers/surface_layer.h", + "+cc/layers/video_frame_provider_client_impl.h", + "+cc/layers/video_frame_provider.h", + "+cc/layers/video_layer.h", + "+cc/paint/skia_paint_canvas.h", + "+media/filters/video_renderer_algorithm.h", + "+media/renderers/paint_canvas_video_renderer.h", + "+media/video/gpu_memory_buffer_video_frame_pool.h", + "+services/viz/public/cpp/gpu/context_provider_command_buffer.h", + "+skia/ext/platform_canvas.h", + "+base/trace_event/trace_event.h", "+media/audio", "+media/base", @@ -28,6 +41,10 @@ specific_include_rules = { ".*test\.cc" : [ + "+base/containers/circular_deque.h", "+base/run_loop.h", + "+cc/layers/layer.h", + "+media/video/mock_gpu_memory_buffer_video_frame_pool.h", + "+media/video/mock_gpu_video_accelerator_factories.h", ], }
diff --git a/third_party/blink/renderer/modules/mediastream/media_stream.cc b/third_party/blink/renderer/modules/mediastream/media_stream.cc index 375550e..06b849b 100644 --- a/third_party/blink/renderer/modules/mediastream/media_stream.cc +++ b/third_party/blink/renderer/modules/mediastream/media_stream.cc
@@ -32,7 +32,6 @@ #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/heap/heap.h" -#include "third_party/blink/renderer/platform/mediastream/media_stream_center.h" #include "third_party/blink/renderer/platform/mediastream/media_stream_source.h" namespace blink {
diff --git a/third_party/blink/renderer/modules/mediastream/user_media_request.cc b/third_party/blink/renderer/modules/mediastream/user_media_request.cc index 75a3b72..247950f 100644 --- a/third_party/blink/renderer/modules/mediastream/user_media_request.cc +++ b/third_party/blink/renderer/modules/mediastream/user_media_request.cc
@@ -49,7 +49,6 @@ #include "third_party/blink/renderer/modules/mediastream/user_media_controller.h" #include "third_party/blink/renderer/platform/bindings/exception_state.h" #include "third_party/blink/renderer/platform/heap/heap.h" -#include "third_party/blink/renderer/platform/mediastream/media_stream_center.h" #include "third_party/blink/renderer/platform/mediastream/media_stream_descriptor.h" #include "third_party/blink/renderer/platform/runtime_enabled_features.h"
diff --git a/content/renderer/media/stream/webmediaplayer_ms.cc b/third_party/blink/renderer/modules/mediastream/webmediaplayer_ms.cc similarity index 79% rename from content/renderer/media/stream/webmediaplayer_ms.cc rename to third_party/blink/renderer/modules/mediastream/webmediaplayer_ms.cc index dcbf486d..87d52bee 100644 --- a/content/renderer/media/stream/webmediaplayer_ms.cc +++ b/third_party/blink/renderer/modules/mediastream/webmediaplayer_ms.cc
@@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#include "content/renderer/media/stream/webmediaplayer_ms.h" +#include "third_party/blink/public/web/modules/mediastream/webmediaplayer_ms.h" #include <stddef.h> #include <limits> @@ -12,12 +12,9 @@ #include "base/bind.h" #include "base/callback.h" #include "base/threading/thread_task_runner_handle.h" +#include "build/build_config.h" #include "cc/layers/video_frame_provider_client_impl.h" #include "cc/layers/video_layer.h" -#include "content/child/child_process.h" -#include "content/renderer/media/stream/webmediaplayer_ms_compositor.h" -#include "content/renderer/render_frame_impl.h" -#include "content/renderer/render_thread_impl.h" #include "media/base/bind_to_current_loop.h" #include "media/base/media_content_type.h" #include "media/base/media_log.h" @@ -32,6 +29,7 @@ #include "third_party/blink/public/platform/modules/mediastream/web_media_stream_renderer_factory.h" #include "third_party/blink/public/platform/modules/mediastream/web_media_stream_video_renderer.h" #include "third_party/blink/public/platform/modules/webrtc/webrtc_logging.h" +#include "third_party/blink/public/platform/url_conversion.h" #include "third_party/blink/public/platform/web_media_player_client.h" #include "third_party/blink/public/platform/web_media_player_source.h" #include "third_party/blink/public/platform/web_rect.h" @@ -40,6 +38,10 @@ #include "third_party/blink/public/web/modules/media/webmediaplayer_util.h" #include "third_party/blink/public/web/modules/mediastream/media_stream_video_track.h" #include "third_party/blink/public/web/web_local_frame.h" +#include "third_party/blink/renderer/modules/mediastream/media_stream_local_frame_wrapper.h" +#include "third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.h" +#include "third_party/blink/renderer/platform/scheduler/public/post_cross_thread_task.h" +#include "third_party/blink/renderer/platform/wtf/cross_thread_functional.h" namespace { @@ -57,7 +59,23 @@ } // namespace -namespace content { +namespace WTF { + +template <> +struct CrossThreadCopier<viz::SurfaceId> + : public CrossThreadCopierPassThrough<viz::SurfaceId> { + STATIC_ONLY(CrossThreadCopier); +}; + +template <> +struct CrossThreadCopier<media::VideoTransformation> + : public CrossThreadCopierPassThrough<media::VideoTransformation> { + STATIC_ONLY(CrossThreadCopier); +}; + +} // namespace WTF + +namespace blink { #if defined(OS_WIN) // Since we do not have native GMB support in Windows, using GMBs can cause a @@ -76,15 +94,16 @@ // should be destructed on the IO thread. class WebMediaPlayerMS::FrameDeliverer { public: - FrameDeliverer( - const base::WeakPtr<WebMediaPlayerMS>& player, - const blink::WebMediaStreamVideoRenderer::RepaintCB& enqueue_frame_cb, - scoped_refptr<base::SingleThreadTaskRunner> media_task_runner, - scoped_refptr<base::TaskRunner> worker_task_runner, - media::GpuVideoAcceleratorFactories* gpu_factories) + using RepaintCB = + WTF::CrossThreadRepeatingFunction<void(scoped_refptr<media::VideoFrame>)>; + FrameDeliverer(const base::WeakPtr<WebMediaPlayerMS>& player, + RepaintCB enqueue_frame_cb, + scoped_refptr<base::SingleThreadTaskRunner> media_task_runner, + scoped_refptr<base::TaskRunner> worker_task_runner, + media::GpuVideoAcceleratorFactories* gpu_factories) : main_task_runner_(base::ThreadTaskRunnerHandle::Get()), player_(player), - enqueue_frame_cb_(enqueue_frame_cb), + enqueue_frame_cb_(std::move(enqueue_frame_cb)), media_task_runner_(media_task_runner) { DETACH_FROM_THREAD(io_thread_checker_); @@ -144,6 +163,9 @@ // |gpu_memory_buffer_pool_| deletion is going to be posted to // |media_task_runner_|. base::Unretained() usage is fine since // |gpu_memory_buffer_pool_| outlives the task. + // + // TODO(crbug.com/964947): Converting this to PostCrossThreadTask requires + // re-binding a CrossThreadOnceFunction instance. media_task_runner_->PostTask( FROM_HERE, base::BindOnce( @@ -159,9 +181,9 @@ render_frame_suspended_ = render_frame_suspended; } - blink::WebMediaStreamVideoRenderer::RepaintCB GetRepaintCallback() { - return base::Bind(&FrameDeliverer::OnVideoFrame, - weak_factory_.GetWeakPtr()); + RepaintCB GetRepaintCallback() { + return CrossThreadBindRepeating(&FrameDeliverer::OnVideoFrame, + weak_factory_.GetWeakPtr()); } private: @@ -196,12 +218,13 @@ return; // |gpu_memory_buffer_pool_| deletion is going to be posted to - // |media_task_runner_|. base::Unretained() usage is fine since + // |media_task_runner_|. CrossThreadUnretained() usage is fine since // |gpu_memory_buffer_pool_| outlives the task. - media_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&media::GpuMemoryBufferVideoFramePool::Abort, - base::Unretained(gpu_memory_buffer_pool_.get()))); + PostCrossThreadTask( + *media_task_runner_, FROM_HERE, + CrossThreadBindOnce( + &media::GpuMemoryBufferVideoFramePool::Abort, + CrossThreadUnretained(gpu_memory_buffer_pool_.get()))); weak_factory_for_pool_.InvalidateWeakPtrs(); } @@ -209,7 +232,7 @@ const scoped_refptr<base::SingleThreadTaskRunner> main_task_runner_; const base::WeakPtr<WebMediaPlayerMS> player_; - const blink::WebMediaStreamVideoRenderer::RepaintCB enqueue_frame_cb_; + RepaintCB enqueue_frame_cb_; // Pool of GpuMemoryBuffers and resources used to create hardware frames. std::unique_ptr<media::GpuMemoryBufferVideoFramePool> gpu_memory_buffer_pool_; @@ -225,22 +248,22 @@ }; WebMediaPlayerMS::WebMediaPlayerMS( - blink::WebLocalFrame* frame, - blink::WebMediaPlayerClient* client, - blink::WebMediaPlayerDelegate* delegate, + WebLocalFrame* frame, + WebMediaPlayerClient* client, + WebMediaPlayerDelegate* delegate, std::unique_ptr<media::MediaLog> media_log, - std::unique_ptr<blink::WebMediaStreamRendererFactory> factory, + std::unique_ptr<WebMediaStreamRendererFactory> factory, scoped_refptr<base::SingleThreadTaskRunner> main_render_task_runner, scoped_refptr<base::SingleThreadTaskRunner> io_task_runner, scoped_refptr<base::SingleThreadTaskRunner> compositor_task_runner, scoped_refptr<base::SingleThreadTaskRunner> media_task_runner, scoped_refptr<base::TaskRunner> worker_task_runner, media::GpuVideoAcceleratorFactories* gpu_factories, - const blink::WebString& sink_id, + const WebString& sink_id, CreateSurfaceLayerBridgeCB create_bridge_callback, - std::unique_ptr<blink::WebVideoFrameSubmitter> submitter, - blink::WebMediaPlayer::SurfaceLayerMode surface_layer_mode) - : frame_(frame), + std::unique_ptr<WebVideoFrameSubmitter> submitter, + WebMediaPlayer::SurfaceLayerMode surface_layer_mode) + : internal_frame_(std::make_unique<MediaStreamInternalFrameWrapper>(frame)), network_state_(WebMediaPlayer::kNetworkStateEmpty), ready_state_(WebMediaPlayer::kReadyStateHaveNothing), buffered_(static_cast<size_t>(0)), @@ -257,7 +280,7 @@ media_task_runner_(std::move(media_task_runner)), worker_task_runner_(std::move(worker_task_runner)), gpu_factories_(gpu_factories), - initial_audio_output_device_id_(sink_id.Utf8()), + initial_audio_output_device_id_(sink_id), volume_(1.0), volume_multiplier_(1.0), should_play_upon_shown_(false), @@ -284,8 +307,7 @@ // Destruct compositor resources in the proper order. get_client()->SetCcLayer(nullptr); if (video_layer_) { - DCHECK(surface_layer_mode_ != - blink::WebMediaPlayer::SurfaceLayerMode::kAlways); + DCHECK(surface_layer_mode_ != WebMediaPlayer::SurfaceLayerMode::kAlways); video_layer_->StopUsingProvider(); } @@ -308,9 +330,9 @@ delegate_->RemoveObserver(delegate_id_); } -blink::WebMediaPlayer::LoadTiming WebMediaPlayerMS::Load( +WebMediaPlayer::LoadTiming WebMediaPlayerMS::Load( LoadType load_type, - const blink::WebMediaPlayerSource& source, + const WebMediaPlayerSource& source, CorsMode /*cors_mode*/) { DVLOG(1) << __func__; DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); @@ -318,11 +340,11 @@ // TODO(acolwell): Change this to DCHECK_EQ(load_type, LoadTypeMediaStream) // once Blink-side changes land. DCHECK_NE(load_type, kLoadTypeMediaSource); - web_stream_ = blink::GetWebMediaStreamFromWebMediaPlayerSource(source); + web_stream_ = GetWebMediaStreamFromWebMediaPlayerSource(source); if (!web_stream_.IsNull()) web_stream_.AddObserver(this); - compositor_ = new WebMediaPlayerMSCompositor( + compositor_ = base::MakeRefCounted<WebMediaPlayerMSCompositor>( compositor_task_runner_, io_task_runner_, web_stream_, std::move(submitter_), surface_layer_mode_, weak_this_); @@ -334,34 +356,31 @@ frame_deliverer_.reset(new WebMediaPlayerMS::FrameDeliverer( weak_this_, - base::BindRepeating(&WebMediaPlayerMSCompositor::EnqueueFrame, - compositor_), + CrossThreadBindRepeating(&WebMediaPlayerMSCompositor::EnqueueFrame, + compositor_), media_task_runner_, worker_task_runner_, gpu_factories_)); video_frame_provider_ = renderer_factory_->GetVideoRenderer( web_stream_, - frame_deliverer_->GetRepaintCallback(), io_task_runner_, - main_render_task_runner_); + ConvertToBaseCallback(frame_deliverer_->GetRepaintCallback()), + io_task_runner_, main_render_task_runner_); - RenderFrame* const frame = RenderFrame::FromWebFrame(frame_); - - blink::WebLocalFrame* web_frame = nullptr; - GURL url = source.IsURL() ? GURL(source.GetAsURL()) : GURL(); - - if (frame) { + if (internal_frame_->web_frame()) { + WebURL url = source.GetAsURL(); // Report UMA and RAPPOR metrics. - blink::ReportMetrics(load_type, url, *frame_, media_log_.get()); - web_frame = frame->GetWebFrame(); + ReportMetrics(load_type, url, *internal_frame_->web_frame(), + media_log_.get()); } audio_renderer_ = renderer_factory_->GetAudioRenderer( - web_stream_, web_frame, initial_audio_output_device_id_); + web_stream_, internal_frame_->web_frame(), + initial_audio_output_device_id_.Utf8()); if (!audio_renderer_) - blink::WebRtcLogMessage("Warning: Failed to instantiate audio renderer."); + WebRtcLogMessage("Warning: Failed to instantiate audio renderer."); if (!video_frame_provider_ && !audio_renderer_) { SetNetworkState(WebMediaPlayer::kNetworkStateNetworkError); - return blink::WebMediaPlayer::LoadTiming::kImmediate; + return WebMediaPlayer::LoadTiming::kImmediate; } if (audio_renderer_) { @@ -370,8 +389,7 @@ // Store the ID of audio track being played in |current_video_track_id_| if (!web_stream_.IsNull()) { - blink::WebVector<blink::WebMediaStreamTrack> audio_tracks = - web_stream_.AudioTracks(); + WebVector<WebMediaStreamTrack> audio_tracks = web_stream_.AudioTracks(); DCHECK_GT(audio_tracks.size(), 0U); current_audio_track_id_ = audio_tracks[0].Id(); } @@ -382,8 +400,7 @@ // Store the ID of video track being played in |current_video_track_id_| if (!web_stream_.IsNull()) { - blink::WebVector<blink::WebMediaStreamTrack> video_tracks = - web_stream_.VideoTracks(); + WebVector<WebMediaStreamTrack> video_tracks = web_stream_.VideoTracks(); DCHECK_GT(video_tracks.size(), 0U); current_video_track_id_ = video_tracks[0].Id(); } @@ -399,7 +416,7 @@ SetReadyState(WebMediaPlayer::kReadyStateHaveEnoughData); } - return blink::WebMediaPlayer::LoadTiming::kImmediate; + return WebMediaPlayer::LoadTiming::kImmediate; } void WebMediaPlayerMS::OnWebLayerUpdated() {} @@ -427,11 +444,11 @@ client_->OnPictureInPictureStateChange(); } -void WebMediaPlayerMS::TrackAdded(const blink::WebMediaStreamTrack& track) { +void WebMediaPlayerMS::TrackAdded(const WebMediaStreamTrack& track) { Reload(); } -void WebMediaPlayerMS::TrackRemoved(const blink::WebMediaStreamTrack& track) { +void WebMediaPlayerMS::TrackRemoved(const WebMediaStreamTrack& track) { Reload(); } @@ -465,7 +482,7 @@ return base::nullopt; } -base::WeakPtr<blink::WebMediaPlayer> WebMediaPlayerMS::AsWeakPtr() { +base::WeakPtr<WebMediaPlayer> WebMediaPlayerMS::AsWeakPtr() { return weak_this_; } @@ -481,14 +498,13 @@ void WebMediaPlayerMS::ReloadVideo() { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); DCHECK(!web_stream_.IsNull()); - blink::WebVector<blink::WebMediaStreamTrack> video_tracks = - web_stream_.VideoTracks(); + WebVector<WebMediaStreamTrack> video_tracks = web_stream_.VideoTracks(); RendererReloadAction renderer_action = RendererReloadAction::KEEP_RENDERER; if (video_tracks.empty()) { if (video_frame_provider_) renderer_action = RendererReloadAction::REMOVE_RENDERER; - current_video_track_id_ = blink::WebString(); + current_video_track_id_ = WebString(); } else if (video_tracks[0].Id() != current_video_track_id_ && IsPlayableTrack(video_tracks[0])) { renderer_action = RendererReloadAction::NEW_RENDERER; @@ -503,8 +519,8 @@ SetNetworkState(kNetworkStateLoading); video_frame_provider_ = renderer_factory_->GetVideoRenderer( web_stream_, - frame_deliverer_->GetRepaintCallback(), io_task_runner_, - main_render_task_runner_); + ConvertToBaseCallback(frame_deliverer_->GetRepaintCallback()), + io_task_runner_, main_render_task_runner_); DCHECK(video_frame_provider_); video_frame_provider_->Start(); break; @@ -519,25 +535,27 @@ } DCHECK_NE(renderer_action, RendererReloadAction::KEEP_RENDERER); - if (!paused_) - delegate_->DidPlayerSizeChange(delegate_id_, NaturalSize()); + if (!paused_) { + // TODO(crbug.com/964494): Remove this explicit conversion. + WebSize natural_size = NaturalSize(); + gfx::Size gfx_size(natural_size.height, natural_size.width); + delegate_->DidPlayerSizeChange(delegate_id_, gfx_size); + } } void WebMediaPlayerMS::ReloadAudio() { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); DCHECK(!web_stream_.IsNull()); - RenderFrame* const frame = RenderFrame::FromWebFrame(frame_); - if (!frame) + if (!internal_frame_->web_frame()) return; - blink::WebVector<blink::WebMediaStreamTrack> audio_tracks = - web_stream_.AudioTracks(); + WebVector<WebMediaStreamTrack> audio_tracks = web_stream_.AudioTracks(); RendererReloadAction renderer_action = RendererReloadAction::KEEP_RENDERER; if (audio_tracks.empty()) { if (audio_renderer_) renderer_action = RendererReloadAction::REMOVE_RENDERER; - current_audio_track_id_ = blink::WebString(); + current_audio_track_id_ = WebString(); } else if (audio_tracks[0].Id() != current_audio_track_id_ && IsPlayableTrack(audio_tracks[0])) { renderer_action = RendererReloadAction::NEW_RENDERER; @@ -551,7 +569,8 @@ SetNetworkState(WebMediaPlayer::kNetworkStateLoading); audio_renderer_ = renderer_factory_->GetAudioRenderer( - web_stream_, frame->GetWebFrame(), initial_audio_output_device_id_); + web_stream_, internal_frame_->web_frame(), + initial_audio_output_device_id_.Utf8()); // |audio_renderer_| can be null in tests. if (!audio_renderer_) @@ -588,8 +607,12 @@ if (audio_renderer_) audio_renderer_->Play(); - if (HasVideo()) - delegate_->DidPlayerSizeChange(delegate_id_, NaturalSize()); + if (HasVideo()) { + // TODO(crbug.com/964494): Remove this explicit conversion. + WebSize natural_size = NaturalSize(); + gfx::Size gfx_size(natural_size.height, natural_size.width); + delegate_->DidPlayerSizeChange(delegate_id_, gfx_size); + } // |delegate_| expects the notification only if there is at least one track // actually playing. A media stream might have none since tracks can be @@ -656,12 +679,12 @@ } void WebMediaPlayerMS::SetSinkId( - const blink::WebString& sink_id, - blink::WebSetSinkIdCompleteCallback completion_callback) { + const WebString& sink_id, + WebSetSinkIdCompleteCallback completion_callback) { DVLOG(1) << __func__; DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); media::OutputDeviceStatusCB callback = - blink::ConvertToOutputDeviceStatusCB(std::move(completion_callback)); + ConvertToOutputDeviceStatusCB(std::move(completion_callback)); if (audio_renderer_) { audio_renderer_->SwitchOutputDevice(sink_id.Utf8(), std::move(callback)); } else { @@ -675,39 +698,39 @@ bool WebMediaPlayerMS::HasVideo() const { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); - return (video_frame_provider_.get() != nullptr); + return !!video_frame_provider_; } bool WebMediaPlayerMS::HasAudio() const { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); - return (audio_renderer_.get() != nullptr); + return !!audio_renderer_; } -blink::WebSize WebMediaPlayerMS::NaturalSize() const { +WebSize WebMediaPlayerMS::NaturalSize() const { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); if (!video_frame_provider_) - return blink::WebSize(); + return WebSize(); if (video_transformation_.rotation == media::VIDEO_ROTATION_90 || video_transformation_.rotation == media::VIDEO_ROTATION_270) { const gfx::Size& current_size = compositor_->GetCurrentSize(); - return blink::WebSize(current_size.height(), current_size.width()); + return WebSize(current_size.height(), current_size.width()); } - return blink::WebSize(compositor_->GetCurrentSize()); + return WebSize(compositor_->GetCurrentSize()); } -blink::WebSize WebMediaPlayerMS::VisibleRect() const { +WebSize WebMediaPlayerMS::VisibleRect() const { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); scoped_refptr<media::VideoFrame> video_frame = compositor_->GetCurrentFrame(); if (!video_frame) - return blink::WebSize(); + return WebSize(); const gfx::Rect& visible_rect = video_frame->visible_rect(); if (video_transformation_.rotation == media::VIDEO_ROTATION_90 || video_transformation_.rotation == media::VIDEO_ROTATION_270) { - return blink::WebSize(visible_rect.height(), visible_rect.width()); + return WebSize(visible_rect.height(), visible_rect.width()); } - return blink::WebSize(visible_rect.width(), visible_rect.height()); + return WebSize(visible_rect.width(), visible_rect.height()); } bool WebMediaPlayerMS::Paused() const { @@ -735,35 +758,35 @@ return 0.0; } -blink::WebMediaPlayer::NetworkState WebMediaPlayerMS::GetNetworkState() const { +WebMediaPlayer::NetworkState WebMediaPlayerMS::GetNetworkState() const { DVLOG(2) << __func__ << ", state:" << network_state_; DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); return network_state_; } -blink::WebMediaPlayer::ReadyState WebMediaPlayerMS::GetReadyState() const { +WebMediaPlayer::ReadyState WebMediaPlayerMS::GetReadyState() const { DVLOG(1) << __func__ << ", state:" << ready_state_; DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); return ready_state_; } -blink::WebMediaPlayer::SurfaceLayerMode -WebMediaPlayerMS::GetVideoSurfaceLayerMode() const { +WebMediaPlayer::SurfaceLayerMode WebMediaPlayerMS::GetVideoSurfaceLayerMode() + const { return surface_layer_mode_; } -blink::WebString WebMediaPlayerMS::GetErrorMessage() const { - return blink::WebString::FromUTF8(media_log_->GetErrorMessage()); +WebString WebMediaPlayerMS::GetErrorMessage() const { + return WebString::FromUTF8(media_log_->GetErrorMessage()); } -blink::WebTimeRanges WebMediaPlayerMS::Buffered() const { +WebTimeRanges WebMediaPlayerMS::Buffered() const { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); return buffered_; } -blink::WebTimeRanges WebMediaPlayerMS::Seekable() const { +WebTimeRanges WebMediaPlayerMS::Seekable() const { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); - return blink::WebTimeRanges(); + return WebTimeRanges(); } bool WebMediaPlayerMS::DidLoadingProgress() { @@ -772,7 +795,7 @@ } void WebMediaPlayerMS::Paint(cc::PaintCanvas* canvas, - const blink::WebRect& rect, + const WebRect& rect, cc::PaintFlags& flags, int already_uploaded_id, VideoFrameUploadMetadata* out_metadata) { @@ -783,8 +806,7 @@ viz::ContextProvider* provider = nullptr; if (frame && frame->HasTextures()) { - provider = - RenderThreadImpl::current()->SharedMainThreadContextProvider().get(); + provider = Platform::Current()->SharedMainThreadContextProvider(); // GPU Process crashed. if (!provider) return; @@ -805,12 +827,12 @@ unsigned WebMediaPlayerMS::DecodedFrameCount() const { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); - return compositor_->total_frame_count(); + return static_cast<unsigned>(compositor_->total_frame_count()); } unsigned WebMediaPlayerMS::DroppedFrameCount() const { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); - return compositor_->dropped_frame_count(); + return static_cast<unsigned>(compositor_->dropped_frame_count()); } uint64_t WebMediaPlayerMS::AudioDecodedByteCount() const { @@ -835,15 +857,17 @@ // suspended. During undoable tab closures OnHidden() may be called back to // back, so we can't rely on |render_frame_suspended_| being false here. if (frame_deliverer_) { - io_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&FrameDeliverer::SetRenderFrameSuspended, - base::Unretained(frame_deliverer_.get()), true)); + PostCrossThreadTask( + *io_task_runner_, FROM_HERE, + CrossThreadBindOnce(&FrameDeliverer::SetRenderFrameSuspended, + CrossThreadUnretained(frame_deliverer_.get()), + true)); } - compositor_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMSCompositor::SetIsPageVisible, - base::Unretained(compositor_.get()), false)); + PostCrossThreadTask( + *compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMSCompositor::SetIsPageVisible, + CrossThreadUnretained(compositor_.get()), false)); // On Android, substitute the displayed VideoFrame with a copy to avoid holding // onto it unnecessarily. @@ -867,10 +891,11 @@ #endif // defined(OS_ANDROID) if (frame_deliverer_) { - io_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&FrameDeliverer::SetRenderFrameSuspended, - base::Unretained(frame_deliverer_.get()), true)); + PostCrossThreadTask( + *io_task_runner_, FROM_HERE, + CrossThreadBindOnce(&FrameDeliverer::SetRenderFrameSuspended, + CrossThreadUnretained(frame_deliverer_.get()), + true)); } } @@ -878,15 +903,17 @@ DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); if (frame_deliverer_) { - io_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&FrameDeliverer::SetRenderFrameSuspended, - base::Unretained(frame_deliverer_.get()), false)); + PostCrossThreadTask( + *io_task_runner_, FROM_HERE, + CrossThreadBindOnce(&FrameDeliverer::SetRenderFrameSuspended, + CrossThreadUnretained(frame_deliverer_.get()), + false)); } - compositor_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMSCompositor::SetIsPageVisible, - base::Unretained(compositor_.get()), true)); + PostCrossThreadTask( + *compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMSCompositor::SetIsPageVisible, + CrossThreadUnretained(compositor_.get()), true)); // On Android, resume playback on visibility. play() clears // |should_play_upon_shown_|. @@ -948,8 +975,7 @@ if (!video_frame.get() || !video_frame->HasTextures()) return false; - auto* provider = - RenderThreadImpl::current()->SharedMainThreadContextProvider().get(); + auto* provider = Platform::Current()->SharedMainThreadContextProvider(); // GPU Process crashed. if (!provider) return false; @@ -981,8 +1007,7 @@ if (video_frame->HasTextures()) return false; - auto* provider = - RenderThreadImpl::current()->SharedMainThreadContextProvider().get(); + auto* provider = Platform::Current()->SharedMainThreadContextProvider(); // GPU Process crashed. if (!provider) return false; @@ -1017,8 +1042,7 @@ } if (functionID == kTexImage2D) { - auto* provider = - RenderThreadImpl::current()->SharedMainThreadContextProvider().get(); + auto* provider = Platform::Current()->SharedMainThreadContextProvider(); // GPU Process crashed. if (!provider) return false; @@ -1048,11 +1072,12 @@ bridge_->CreateSurfaceLayer(); bridge_->SetContentsOpaque(opaque_); - compositor_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMSCompositor::EnableSubmission, - compositor_, bridge_->GetSurfaceId(), - bridge_->GetLocalSurfaceIdAllocationTime(), - video_transformation_, IsInPictureInPicture())); + PostCrossThreadTask( + *compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMSCompositor::EnableSubmission, + compositor_, bridge_->GetSurfaceId(), + bridge_->GetLocalSurfaceIdAllocationTime(), + video_transformation_, IsInPictureInPicture())); // If the element is already in Picture-in-Picture mode, it means that it // was set in this mode prior to this load, with a different @@ -1077,9 +1102,8 @@ OnRotationChanged(video_rotation); OnOpacityChanged(is_opaque); - if (surface_layer_mode_ == blink::WebMediaPlayer::SurfaceLayerMode::kAlways || - (surface_layer_mode_ == - blink::WebMediaPlayer::SurfaceLayerMode::kOnDemand && + if (surface_layer_mode_ == WebMediaPlayer::SurfaceLayerMode::kAlways || + (surface_layer_mode_ == WebMediaPlayer::SurfaceLayerMode::kOnDemand && client_->DisplayType() == WebMediaPlayer::DisplayType::kPictureInPicture)) { ActivateSurfaceLayerForVideo(); @@ -1162,7 +1186,10 @@ if (HasVideo()) get_client()->SizeChanged(); - delegate_->DidPlayerSizeChange(delegate_id_, NaturalSize()); + // TODO(crbug.com/964494): Remove this explicit conversion. + WebSize natural_size = NaturalSize(); + gfx::Size gfx_size(natural_size.height, natural_size.width); + delegate_->DidPlayerSizeChange(delegate_id_, gfx_size); } void WebMediaPlayerMS::SetGpuMemoryBufferVideoForTesting( @@ -1176,12 +1203,12 @@ if (!bridge_) return; - compositor_task_runner_->PostTask( - FROM_HERE, - base::BindOnce( + PostCrossThreadTask( + *compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce( &WebMediaPlayerMSCompositor::SetForceSubmit, - base::Unretained(compositor_.get()), + CrossThreadUnretained(compositor_.get()), display_type == WebMediaPlayer::DisplayType::kPictureInPicture)); } -} // namespace content +} // namespace blink
diff --git a/content/renderer/media/stream/webmediaplayer_ms_compositor.cc b/third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.cc similarity index 84% rename from content/renderer/media/stream/webmediaplayer_ms_compositor.cc rename to third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.cc index e6f73f6..8e453c8 100644 --- a/content/renderer/media/stream/webmediaplayer_ms_compositor.cc +++ b/third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.cc
@@ -2,24 +2,18 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#include "content/renderer/media/stream/webmediaplayer_ms_compositor.h" +#include "third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.h" #include <stdint.h> #include <string> #include <utility> -#include "base/bind.h" -#include "base/command_line.h" #include "base/hash/hash.h" -#include "base/message_loop/message_loop_current.h" #include "base/single_thread_task_runner.h" #include "base/threading/thread_task_runner_handle.h" #include "base/values.h" #include "cc/paint/skia_paint_canvas.h" -#include "content/renderer/media/stream/webmediaplayer_ms.h" -#include "content/renderer/render_thread_impl.h" #include "media/base/bind_to_current_loop.h" -#include "media/base/media_switches.h" #include "media/base/video_frame.h" #include "media/base/video_util.h" #include "media/filters/video_renderer_algorithm.h" @@ -30,12 +24,25 @@ #include "third_party/blink/public/platform/web_media_stream_source.h" #include "third_party/blink/public/platform/web_media_stream_track.h" #include "third_party/blink/public/platform/web_video_frame_submitter.h" +#include "third_party/blink/public/web/modules/mediastream/webmediaplayer_ms.h" +#include "third_party/blink/renderer/platform/scheduler/public/post_cross_thread_task.h" +#include "third_party/blink/renderer/platform/wtf/cross_thread_functional.h" #include "third_party/libyuv/include/libyuv/convert.h" #include "third_party/libyuv/include/libyuv/planar_functions.h" #include "third_party/libyuv/include/libyuv/video_common.h" #include "third_party/skia/include/core/SkSurface.h" -namespace content { +namespace WTF { + +template <typename T> +struct CrossThreadCopier<base::Optional<T>> + : public CrossThreadCopierPassThrough<base::Optional<T>> { + STATIC_ONLY(CrossThreadCopier); +}; + +} // namespace WTF + +namespace blink { namespace { @@ -54,8 +61,8 @@ media::PIXEL_FORMAT_I420, frame->coded_size(), frame->visible_rect(), frame->natural_size(), frame->timestamp()); - viz::ContextProviderCommandBuffer* const provider = - RenderThreadImpl::current()->SharedMainThreadContextProvider().get(); + auto* const provider = + Platform::Current()->SharedMainThreadContextProvider(); if (!provider) { // Return a black frame (yuv = {0, 0x80, 0x80}). return media::VideoFrame::CreateColorFrame( @@ -132,9 +139,9 @@ scoped_refptr<base::SingleThreadTaskRunner> video_frame_compositor_task_runner, scoped_refptr<base::SingleThreadTaskRunner> io_task_runner, - const blink::WebMediaStream& web_stream, - std::unique_ptr<blink::WebVideoFrameSubmitter> submitter, - blink::WebMediaPlayer::SurfaceLayerMode surface_layer_mode, + const WebMediaStream& web_stream, + std::unique_ptr<WebVideoFrameSubmitter> submitter, + WebMediaPlayer::SurfaceLayerMode surface_layer_mode, const base::WeakPtr<WebMediaPlayerMS>& player) : video_frame_compositor_task_runner_(video_frame_compositor_task_runner), io_task_runner_(io_task_runner), @@ -147,32 +154,33 @@ dropped_frame_count_(0), stopped_(true), render_started_(!stopped_) { - if (surface_layer_mode != blink::WebMediaPlayer::SurfaceLayerMode::kNever) { + if (surface_layer_mode != WebMediaPlayer::SurfaceLayerMode::kNever) { submitter_ = std::move(submitter); - video_frame_compositor_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&WebMediaPlayerMSCompositor::InitializeSubmitter, - weak_ptr_factory_.GetWeakPtr())); - update_submission_state_callback_ = media::BindToLoop( - video_frame_compositor_task_runner_, - base::BindRepeating(&WebMediaPlayerMSCompositor::SetIsSurfaceVisible, + PostCrossThreadTask( + *video_frame_compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMSCompositor::InitializeSubmitter, weak_ptr_factory_.GetWeakPtr())); + update_submission_state_callback_ = + media::BindToLoop(video_frame_compositor_task_runner_, + ConvertToBaseCallback(CrossThreadBindRepeating( + &WebMediaPlayerMSCompositor::SetIsSurfaceVisible, + weak_ptr_factory_.GetWeakPtr()))); } - blink::WebVector<blink::WebMediaStreamTrack> video_tracks; + WebVector<WebMediaStreamTrack> video_tracks; if (!web_stream.IsNull()) video_tracks = web_stream.VideoTracks(); const bool remote_video = video_tracks.size() && video_tracks[0].Source().Remote(); - if (remote_video && !base::CommandLine::ForCurrentProcess()->HasSwitch( - switches::kDisableRTCSmoothnessAlgorithm)) { + if (remote_video && Platform::Current()->RTCSmoothnessAlgorithmEnabled()) { base::AutoLock auto_lock(current_frame_lock_); rendering_frame_buffer_.reset(new media::VideoRendererAlgorithm( - base::Bind(&WebMediaPlayerMSCompositor::MapTimestampsToRenderTimeTicks, - base::Unretained(this)), + ConvertToBaseCallback(CrossThreadBindRepeating( + &WebMediaPlayerMSCompositor::MapTimestampsToRenderTimeTicks, + CrossThreadUnretained(this))), &media_log_)); } @@ -201,9 +209,10 @@ const WebMediaPlayerMSCompositor* compositor) { if (!compositor->video_frame_compositor_task_runner_ ->BelongsToCurrentThread()) { - compositor->video_frame_compositor_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMSCompositorTraits::Destruct, - base::Unretained(compositor))); + PostCrossThreadTask( + *compositor->video_frame_compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMSCompositorTraits::Destruct, + CrossThreadUnretained(compositor))); return; } delete compositor; @@ -391,7 +400,7 @@ bool WebMediaPlayerMSCompositor::HasCurrentFrame() { base::AutoLock auto_lock(current_frame_lock_); - return current_frame_.get() != nullptr; + return !!current_frame_; } scoped_refptr<media::VideoFrame> WebMediaPlayerMSCompositor::GetCurrentFrame() { @@ -423,17 +432,18 @@ base::AutoLock auto_lock(current_frame_lock_); render_started_ = true; } - video_frame_compositor_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&WebMediaPlayerMSCompositor::StartRenderingInternal, - this)); + PostCrossThreadTask( + *video_frame_compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMSCompositor::StartRenderingInternal, + WrapRefCounted(this))); } void WebMediaPlayerMSCompositor::StopRendering() { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); - video_frame_compositor_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&WebMediaPlayerMSCompositor::StopRenderingInternal, this)); + PostCrossThreadTask( + *video_frame_compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMSCompositor::StopRenderingInternal, + WrapRefCounted(this))); } void WebMediaPlayerMSCompositor::ReplaceCurrentFrameWithACopy() { @@ -442,17 +452,18 @@ // passed on IO thread. io_task_runner_->PostTask( FROM_HERE, - media::BindToCurrentLoop(base::Bind( + media::BindToCurrentLoop(WTF::Bind( &WebMediaPlayerMSCompositor::ReplaceCurrentFrameWithACopyInternal, - this))); + WrapRefCounted(this)))); } void WebMediaPlayerMSCompositor::StopUsingProvider() { DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); - video_frame_compositor_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&WebMediaPlayerMSCompositor::StopUsingProviderInternal, - this)); + PostCrossThreadTask( + *video_frame_compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce( + &WebMediaPlayerMSCompositor::StopUsingProviderInternal, + WrapRefCounted(this))); } bool WebMediaPlayerMSCompositor::MapTimestampsToRenderTimeTicks( @@ -504,11 +515,11 @@ void WebMediaPlayerMSCompositor::RenderWithoutAlgorithm( scoped_refptr<media::VideoFrame> frame) { DCHECK(io_task_runner_->BelongsToCurrentThread()); - video_frame_compositor_task_runner_->PostTask( - FROM_HERE, - base::BindOnce( - &WebMediaPlayerMSCompositor::RenderWithoutAlgorithmOnCompositor, this, - std::move(frame))); + PostCrossThreadTask( + *video_frame_compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce( + &WebMediaPlayerMSCompositor::RenderWithoutAlgorithmOnCompositor, + WrapRefCounted(this), std::move(frame))); } void WebMediaPlayerMSCompositor::RenderWithoutAlgorithmOnCompositor( @@ -569,11 +580,12 @@ // Complete the checks after |current_frame_| is accessible to avoid // deadlocks, see https://crbug.com/901744. - video_frame_compositor_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&WebMediaPlayerMSCompositor::CheckForFrameChanges, this, - is_first_frame, has_frame_size_changed, - std::move(new_rotation), std::move(new_opacity))); + PostCrossThreadTask( + *video_frame_compositor_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMSCompositor::CheckForFrameChanges, + WrapRefCounted(this), is_first_frame, + has_frame_size_changed, std::move(new_rotation), + std::move(new_opacity))); } void WebMediaPlayerMSCompositor::CheckForFrameChanges( @@ -584,30 +596,33 @@ DCHECK(video_frame_compositor_task_runner_->BelongsToCurrentThread()); if (is_first_frame) { - main_task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&WebMediaPlayerMS::OnFirstFrameReceived, player_, - *new_frame_rotation, *new_frame_opacity)); + PostCrossThreadTask( + *main_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMS::OnFirstFrameReceived, player_, + *new_frame_rotation, *new_frame_opacity)); return; } if (new_frame_rotation.has_value()) { - main_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMS::OnRotationChanged, player_, - *new_frame_rotation)); + PostCrossThreadTask( + *main_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMS::OnRotationChanged, player_, + *new_frame_rotation)); if (submitter_) submitter_->SetRotation(*new_frame_rotation); } if (new_frame_opacity.has_value()) { - main_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMS::OnOpacityChanged, player_, - *new_frame_opacity)); + PostCrossThreadTask(*main_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMS::OnOpacityChanged, + player_, *new_frame_opacity)); } if (has_frame_size_changed) { - main_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMS::TriggerResize, player_)); + PostCrossThreadTask( + *main_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMS::TriggerResize, player_)); } - main_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMS::ResetCanvasCache, player_)); + PostCrossThreadTask( + *main_task_runner_, FROM_HERE, + CrossThreadBindOnce(&WebMediaPlayerMS::ResetCanvasCache, player_)); } void WebMediaPlayerMSCompositor::StartRenderingInternal() { @@ -676,10 +691,11 @@ if (!rendering_frame_buffer_) { rendering_frame_buffer_.reset(new media::VideoRendererAlgorithm( - base::Bind(&WebMediaPlayerMSCompositor::MapTimestampsToRenderTimeTicks, - base::Unretained(this)), + WTF::BindRepeating( + &WebMediaPlayerMSCompositor::MapTimestampsToRenderTimeTicks, + WTF::Unretained(this)), &media_log_)); } } -} // namespace content +} // namespace blink
diff --git a/content/renderer/media/stream/webmediaplayer_ms_compositor.h b/third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.h similarity index 87% rename from content/renderer/media/stream/webmediaplayer_ms_compositor.h rename to third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.h index 8259036..ba75acf 100644 --- a/content/renderer/media/stream/webmediaplayer_ms_compositor.h +++ b/third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.h
@@ -2,8 +2,8 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef CONTENT_RENDERER_MEDIA_STREAM_WEBMEDIAPLAYER_MS_COMPOSITOR_H_ -#define CONTENT_RENDERER_MEDIA_STREAM_WEBMEDIAPLAYER_MS_COMPOSITOR_H_ +#ifndef THIRD_PARTY_BLINK_RENDERER_MODULES_MEDIASTREAM_WEBMEDIAPLAYER_MS_COMPOSITOR_H_ +#define THIRD_PARTY_BLINK_RENDERER_MODULES_MEDIASTREAM_WEBMEDIAPLAYER_MS_COMPOSITOR_H_ #include <stddef.h> @@ -11,26 +11,21 @@ #include <memory> #include <vector> -#include "base/memory/ref_counted.h" #include "base/memory/weak_ptr.h" #include "base/optional.h" #include "base/synchronization/lock.h" #include "base/threading/thread_checker.h" #include "cc/layers/surface_layer.h" #include "cc/layers/video_frame_provider.h" -#include "content/common/content_export.h" #include "media/base/media_util.h" #include "third_party/blink/public/platform/web_media_player.h" #include "third_party/blink/public/platform/web_video_frame_submitter.h" +#include "third_party/blink/renderer/platform/wtf/thread_safe_ref_counted.h" namespace base { class SingleThreadTaskRunner; } -namespace blink { -class WebMediaStream; -} - namespace gfx { class Size; } @@ -43,8 +38,9 @@ class SurfaceId; } -namespace content { +namespace blink { class WebMediaPlayerMS; +class WebMediaStream; struct WebMediaPlayerMSCompositorTraits; // This class is designed to handle the work load on compositor thread for @@ -56,17 +52,17 @@ // smoothness, if REFERENCE_TIMEs are populated for incoming VideoFrames. // Otherwise, WebMediaPlayerMSCompositor will simply store the most recent // frame, and submit it whenever asked by the compositor. -class CONTENT_EXPORT WebMediaPlayerMSCompositor +class BLINK_MODULES_EXPORT WebMediaPlayerMSCompositor : public cc::VideoFrameProvider, - public base::RefCountedThreadSafe<WebMediaPlayerMSCompositor, - WebMediaPlayerMSCompositorTraits> { + public WTF::ThreadSafeRefCounted<WebMediaPlayerMSCompositor, + WebMediaPlayerMSCompositorTraits> { public: WebMediaPlayerMSCompositor( scoped_refptr<base::SingleThreadTaskRunner> task_runner, scoped_refptr<base::SingleThreadTaskRunner> io_task_runner, - const blink::WebMediaStream& web_stream, - std::unique_ptr<blink::WebVideoFrameSubmitter> submitter, - blink::WebMediaPlayer::SurfaceLayerMode surface_layer_mode, + const WebMediaStream& web_stream, + std::unique_ptr<WebVideoFrameSubmitter> submitter, + WebMediaPlayer::SurfaceLayerMode surface_layer_mode, const base::WeakPtr<WebMediaPlayerMS>& player); // Can be called from any thread. @@ -115,9 +111,8 @@ void StopUsingProvider(); private: - friend class base::RefCountedThreadSafe<WebMediaPlayerMSCompositor, - WebMediaPlayerMSCompositorTraits>; - friend class base::DeleteHelper<WebMediaPlayerMSCompositor>; + friend class WTF::ThreadSafeRefCounted<WebMediaPlayerMSCompositor, + WebMediaPlayerMSCompositorTraits>; friend class WebMediaPlayerMSTest; friend struct WebMediaPlayerMSCompositorTraits; @@ -130,6 +125,9 @@ // Signals the VideoFrameSubmitter to stop submitting frames. void SetIsSurfaceVisible(bool); + // The use of std::vector here is OK because this method is bound into a + // base::OnceCallback instance, and passed to media::VideoRendererAlgorithm + // ctor. bool MapTimestampsToRenderTimeTicks( const std::vector<base::TimeDelta>& timestamps, std::vector<base::TimeTicks>* wall_clock_times); @@ -218,8 +216,9 @@ bool stopped_; bool render_started_; - std::unique_ptr<blink::WebVideoFrameSubmitter> submitter_; + std::unique_ptr<WebVideoFrameSubmitter> submitter_; + // TODO(crbug.com/952716): Replace the use of std::map by WTF::HashMap. std::map<base::TimeDelta, base::TimeTicks> timestamps_to_clock_times_; cc::UpdateSubmissionStateCB update_submission_state_callback_; @@ -234,15 +233,11 @@ }; struct WebMediaPlayerMSCompositorTraits { - private: - friend class base::RefCountedThreadSafe<WebMediaPlayerMSCompositor, - WebMediaPlayerMSCompositorTraits>; - // Ensure destruction occurs on main thread so that "Web" and other resources // are destroyed on the correct thread. static void Destruct(const WebMediaPlayerMSCompositor* player); }; -} // namespace content +} // namespace blink -#endif // CONTENT_RENDERER_MEDIA_STREAM_WEBMEDIAPLAYER_MS_COMPOSITOR_H_ +#endif // THIRD_PARTY_BLINK_RENDERER_MODULES_MEDIASTREAM_WEBMEDIAPLAYER_MS_COMPOSITOR_H_
diff --git a/content/renderer/media/stream/webmediaplayer_ms_unittest.cc b/third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_test.cc similarity index 80% rename from content/renderer/media/stream/webmediaplayer_ms_unittest.cc rename to third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_test.cc index 221dae2..7201b9a 100644 --- a/content/renderer/media/stream/webmediaplayer_ms_unittest.cc +++ b/third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_test.cc
@@ -7,19 +7,15 @@ #include <utility> #include <vector> -#include "base/bind.h" #include "base/bind_helpers.h" #include "base/containers/circular_deque.h" #include "base/run_loop.h" #include "base/single_thread_task_runner.h" #include "base/stl_util.h" #include "base/strings/stringprintf.h" -#include "base/test/scoped_task_environment.h" #include "base/time/time.h" #include "build/build_config.h" #include "cc/layers/layer.h" -#include "content/renderer/media/stream/webmediaplayer_ms.h" -#include "content/renderer/media/stream/webmediaplayer_ms_compositor.h" #include "media/base/media_util.h" #include "media/base/test_helpers.h" #include "media/base/video_frame.h" @@ -31,7 +27,11 @@ #include "third_party/blink/public/platform/web_media_player.h" #include "third_party/blink/public/platform/web_media_player_client.h" #include "third_party/blink/public/platform/web_media_player_source.h" +#include "third_party/blink/public/web/modules/mediastream/webmediaplayer_ms.h" #include "third_party/blink/public/web/web_local_frame.h" +#include "third_party/blink/renderer/modules/mediastream/webmediaplayer_ms_compositor.h" +#include "third_party/blink/renderer/platform/scheduler/public/post_cross_thread_task.h" +#include "third_party/blink/renderer/platform/wtf/cross_thread_functional.h" using ::testing::_; using ::testing::ByRef; @@ -41,7 +41,7 @@ using ::testing::ReturnRef; using ::testing::StrictMock; -namespace content { +namespace blink { enum class FrameType { NORMAL_FRAME = 0, @@ -50,7 +50,7 @@ MIN_TYPE = TEST_BRAKE }; -class MockSurfaceLayerBridge : public blink::WebSurfaceLayerBridge { +class MockSurfaceLayerBridge : public WebSurfaceLayerBridge { public: MockSurfaceLayerBridge() { ON_CALL(*this, GetSurfaceId).WillByDefault(ReturnRef(surface_id_)); @@ -79,7 +79,7 @@ static const int kStandardHeight = 240; class FakeWebMediaPlayerDelegate - : public blink::WebMediaPlayerDelegate, + : public WebMediaPlayerDelegate, public base::SupportsWeakPtr<FakeWebMediaPlayerDelegate> { public: FakeWebMediaPlayerDelegate() {} @@ -150,7 +150,7 @@ void SetIsEffectivelyFullscreen( int delegate_id, - blink::WebFullscreenVideoStatus fullscreen_video_status) override { + WebFullscreenVideoStatus fullscreen_video_status) override { EXPECT_EQ(delegate_id_, delegate_id); } @@ -198,12 +198,12 @@ }; // The class is used mainly to inject VideoFrames into WebMediaPlayerMS. -class MockMediaStreamVideoRenderer : public blink::WebMediaStreamVideoRenderer { +class MockMediaStreamVideoRenderer : public WebMediaStreamVideoRenderer { public: MockMediaStreamVideoRenderer( const scoped_refptr<base::SingleThreadTaskRunner> task_runner, ReusableMessageLoopEvent* message_loop_controller, - const blink::WebMediaStreamVideoRenderer::RepaintCB& repaint_cb) + const WebMediaStreamVideoRenderer::RepaintCB& repaint_cb) : started_(false), standard_size_(kStandardWidth, kStandardHeight), task_runner_(task_runner), @@ -212,7 +212,7 @@ delay_till_next_generated_frame_( base::TimeDelta::FromSecondsD(1.0 / 30.0)) {} - // Implementation of blink::WebMediaStreamVideoRenderer + // Implementation of WebMediaStreamVideoRenderer void Start() override; void Stop() override; void Resume() override; @@ -245,13 +245,13 @@ const scoped_refptr<base::SingleThreadTaskRunner> task_runner_; ReusableMessageLoopEvent* const message_loop_controller_; - const blink::WebMediaStreamVideoRenderer::RepaintCB repaint_cb_; + const WebMediaStreamVideoRenderer::RepaintCB repaint_cb_; base::circular_deque<TestFrame> frames_; base::TimeDelta delay_till_next_generated_frame_; }; -class MockMediaStreamAudioRenderer : public blink::WebMediaStreamAudioRenderer { +class MockMediaStreamAudioRenderer : public WebMediaStreamAudioRenderer { public: MockMediaStreamAudioRenderer() {} @@ -274,9 +274,10 @@ void MockMediaStreamVideoRenderer::Start() { started_ = true; paused_ = false; - task_runner_->PostTask( - FROM_HERE, - base::BindOnce(&MockMediaStreamVideoRenderer::InjectFrame, this)); + PostCrossThreadTask( + *task_runner_, FROM_HERE, + CrossThreadBindOnce(&MockMediaStreamVideoRenderer::InjectFrame, + WrapRefCounted(this))); } void MockMediaStreamVideoRenderer::Stop() { @@ -381,9 +382,10 @@ } } - task_runner_->PostDelayedTask( - FROM_HERE, - base::BindOnce(&MockMediaStreamVideoRenderer::InjectFrame, this), + PostDelayedCrossThreadTask( + *task_runner_, FROM_HERE, + CrossThreadBindOnce(&MockMediaStreamVideoRenderer::InjectFrame, + WrapRefCounted(this)), delay_till_next_generated_frame_); // This will pause the |message_loop_|, and the purpose is to allow the main @@ -394,9 +396,9 @@ message_loop_controller_->GetClosure().Run(); } -class MockWebVideoFrameSubmitter : public blink::WebVideoFrameSubmitter { +class MockWebVideoFrameSubmitter : public WebVideoFrameSubmitter { public: - // blink::WebVideoFrameSubmitter implementation. + // WebVideoFrameSubmitter implementation. MOCK_METHOD0(StopUsingProvider, void()); MOCK_METHOD0(DidReceiveFrame, void()); MOCK_METHOD2(EnableSubmission, void(viz::SurfaceId, base::TimeTicks)); @@ -420,7 +422,7 @@ // The class is used to generate a MockVideoProvider in // WebMediaPlayerMS::load(). -class MockRenderFactory : public blink::WebMediaStreamRendererFactory { +class MockRenderFactory : public WebMediaStreamRendererFactory { public: MockRenderFactory( const scoped_refptr<base::SingleThreadTaskRunner>& task_runner, @@ -428,9 +430,9 @@ : task_runner_(task_runner), message_loop_controller_(message_loop_controller) {} - scoped_refptr<blink::WebMediaStreamVideoRenderer> GetVideoRenderer( - const blink::WebMediaStream& web_stream, - const blink::WebMediaStreamVideoRenderer::RepaintCB& repaint_cb, + scoped_refptr<WebMediaStreamVideoRenderer> GetVideoRenderer( + const WebMediaStream& web_stream, + const WebMediaStreamVideoRenderer::RepaintCB& repaint_cb, scoped_refptr<base::SingleThreadTaskRunner> io_task_runner, scoped_refptr<base::SingleThreadTaskRunner> main_render_task_runner) override; @@ -439,15 +441,14 @@ return static_cast<MockMediaStreamVideoRenderer*>(provider_.get()); } - scoped_refptr<blink::WebMediaStreamAudioRenderer> GetAudioRenderer( - const blink::WebMediaStream& web_stream, - blink::WebLocalFrame* web_frame, + scoped_refptr<WebMediaStreamAudioRenderer> GetAudioRenderer( + const WebMediaStream& web_stream, + WebLocalFrame* web_frame, const std::string& device_id) override { return audio_renderer_; } - void set_audio_renderer( - scoped_refptr<blink::WebMediaStreamAudioRenderer> renderer) { + void set_audio_renderer(scoped_refptr<WebMediaStreamAudioRenderer> renderer) { audio_renderer_ = std::move(renderer); } @@ -460,16 +461,15 @@ private: const scoped_refptr<base::SingleThreadTaskRunner> task_runner_; - scoped_refptr<blink::WebMediaStreamVideoRenderer> provider_; + scoped_refptr<WebMediaStreamVideoRenderer> provider_; ReusableMessageLoopEvent* const message_loop_controller_; bool support_video_renderer_ = true; - scoped_refptr<blink::WebMediaStreamAudioRenderer> audio_renderer_; + scoped_refptr<WebMediaStreamAudioRenderer> audio_renderer_; }; -scoped_refptr<blink::WebMediaStreamVideoRenderer> -MockRenderFactory::GetVideoRenderer( - const blink::WebMediaStream& web_stream, - const blink::WebMediaStreamVideoRenderer::RepaintCB& repaint_cb, +scoped_refptr<WebMediaStreamVideoRenderer> MockRenderFactory::GetVideoRenderer( + const WebMediaStream& web_stream, + const WebMediaStreamVideoRenderer::RepaintCB& repaint_cb, scoped_refptr<base::SingleThreadTaskRunner> io_task_runner, scoped_refptr<base::SingleThreadTaskRunner> main_render_task_runner) { if (!support_video_renderer_) @@ -484,8 +484,8 @@ // This is the main class coordinating the tests. // Basic workflow: // 1. WebMediaPlayerMS::Load will generate and start -// blink::WebMediaStreamVideoRenderer. -// 2. blink::WebMediaStreamVideoRenderer will start pushing frames into +// WebMediaStreamVideoRenderer. +// 2. WebMediaStreamVideoRenderer will start pushing frames into // WebMediaPlayerMS repeatedly. // 3. On WebMediaPlayerMS receiving the first frame, a cc::Layer will be // created. @@ -496,7 +496,7 @@ // WebMediaPlayerMSCompositor::UpdateCurrentFrame, GetCurrentFrame for // rendering repeatedly. // 6. When WebMediaPlayerMS::pause gets called, it should trigger -// blink::WebMediaStreamVideoRenderer::Pause, and then the provider will stop +// WebMediaStreamVideoRenderer::Pause, and then the provider will stop // pushing frames into WebMediaPlayerMS, but instead digesting them; // simultanously, it should call cc::VideoFrameProviderClient::StopRendering, // so cc::VideoFrameProviderClient will stop asking frames from @@ -508,12 +508,12 @@ testing::tuple<bool /* enable_surface_layer_for_video */, bool /* opaque_frame */, bool /* odd_size_frame */>>, - public blink::WebMediaPlayerClient, + public WebMediaPlayerClient, public cc::VideoFrameProvider::Client { public: WebMediaPlayerMSTest() : render_factory_(new MockRenderFactory( - blink::scheduler::GetSingleThreadTaskRunnerForTesting(), + scheduler::GetSingleThreadTaskRunnerForTesting(), &message_loop_controller_)), gpu_factories_(new media::MockGpuVideoAcceleratorFactories(nullptr)), surface_layer_bridge_( @@ -521,7 +521,8 @@ submitter_(std::make_unique<NiceMock<MockWebVideoFrameSubmitter>>()), layer_set_(false), rendering_(false), - background_rendering_(false) { + background_rendering_(false), + weak_factory_(this) { surface_layer_bridge_ptr_ = surface_layer_bridge_.get(); submitter_ptr_ = submitter_.get(); } @@ -542,42 +543,41 @@ void DurationChanged() override {} void SizeChanged() override; void SetCcLayer(cc::Layer* layer) override; - blink::WebMediaPlayer::TrackId AddAudioTrack(const blink::WebString& id, - AudioTrackKind, - const blink::WebString& label, - const blink::WebString& language, - bool enabled) override { - return blink::WebMediaPlayer::TrackId(); + WebMediaPlayer::TrackId AddAudioTrack(const WebString& id, + AudioTrackKind, + const WebString& label, + const WebString& language, + bool enabled) override { + return WebMediaPlayer::TrackId(); } - void RemoveAudioTrack(blink::WebMediaPlayer::TrackId) override {} - blink::WebMediaPlayer::TrackId AddVideoTrack(const blink::WebString& id, - VideoTrackKind, - const blink::WebString& label, - const blink::WebString& language, - bool selected) override { - return blink::WebMediaPlayer::TrackId(); + void RemoveAudioTrack(WebMediaPlayer::TrackId) override {} + WebMediaPlayer::TrackId AddVideoTrack(const WebString& id, + VideoTrackKind, + const WebString& label, + const WebString& language, + bool selected) override { + return WebMediaPlayer::TrackId(); } - void RemoveVideoTrack(blink::WebMediaPlayer::TrackId) override {} - void AddTextTrack(blink::WebInbandTextTrack*) override {} - void RemoveTextTrack(blink::WebInbandTextTrack*) override {} - void MediaSourceOpened(blink::WebMediaSource*) override {} + void RemoveVideoTrack(WebMediaPlayer::TrackId) override {} + void AddTextTrack(WebInbandTextTrack*) override {} + void RemoveTextTrack(WebInbandTextTrack*) override {} + void MediaSourceOpened(WebMediaSource*) override {} void RequestSeek(double) override {} - void RemotePlaybackCompatibilityChanged(const blink::WebURL& url, + void RemotePlaybackCompatibilityChanged(const WebURL& url, bool is_compatible) override {} void OnBecamePersistentVideo(bool) override {} bool WasAlwaysMuted() override { return false; } bool HasSelectedVideoTrack() override { return false; } - blink::WebMediaPlayer::TrackId GetSelectedVideoTrackId() override { - return blink::WebMediaPlayer::TrackId(); + WebMediaPlayer::TrackId GetSelectedVideoTrackId() override { + return WebMediaPlayer::TrackId(); } bool HasNativeControls() override { return false; } bool IsAudioElement() override { return is_audio_element_; } bool IsInAutoPIP() const override { return false; } void ActivateViewportIntersectionMonitoring(bool activate) override {} void MediaRemotingStarted( - const blink::WebString& remote_device_friendly_name) override {} - void MediaRemotingStopped( - blink::WebLocalizedString::Name error_msg) override {} + const WebString& remote_device_friendly_name) override {} + void MediaRemotingStopped(WebLocalizedString::Name error_msg) override {} void RequestPlay() override {} void RequestPause() override {} void RequestMuted(bool muted) override {} @@ -611,20 +611,18 @@ MOCK_METHOD0(DoDidReceiveFrame, void()); MOCK_METHOD1(DoSetCcLayer, void(bool)); - MOCK_METHOD1(DoNetworkStateChanged, - void(blink::WebMediaPlayer::NetworkState)); - MOCK_METHOD1(DoReadyStateChanged, void(blink::WebMediaPlayer::ReadyState)); + MOCK_METHOD1(DoNetworkStateChanged, void(WebMediaPlayer::NetworkState)); + MOCK_METHOD1(DoReadyStateChanged, void(WebMediaPlayer::ReadyState)); MOCK_METHOD1(CheckSizeChanged, void(gfx::Size)); - MOCK_CONST_METHOD0(DisplayType, blink::WebMediaPlayer::DisplayType()); + MOCK_CONST_METHOD0(DisplayType, WebMediaPlayer::DisplayType()); MOCK_CONST_METHOD0(CouldPlayIfEnoughData, bool()); - std::unique_ptr<blink::WebSurfaceLayerBridge> CreateMockSurfaceLayerBridge( - blink::WebSurfaceLayerBridgeObserver*, + std::unique_ptr<WebSurfaceLayerBridge> CreateMockSurfaceLayerBridge( + WebSurfaceLayerBridgeObserver*, cc::UpdateSubmissionStateCB) { return std::move(surface_layer_bridge_); } - base::test::ScopedTaskEnvironment task_environment_; MockRenderFactory* render_factory_; std::unique_ptr<media::MockGpuVideoAcceleratorFactories> gpu_factories_; FakeWebMediaPlayerDelegate delegate_; @@ -648,25 +646,27 @@ bool layer_set_; bool rendering_; bool background_rendering_; + + base::WeakPtrFactory<WebMediaPlayerMSTest> weak_factory_; }; void WebMediaPlayerMSTest::InitializeWebMediaPlayerMS() { enable_surface_layer_for_video_ = testing::get<0>(GetParam()); - blink::WebMediaPlayer::SurfaceLayerMode surface_layer_mode = + WebMediaPlayer::SurfaceLayerMode surface_layer_mode = enable_surface_layer_for_video_ - ? blink::WebMediaPlayer::SurfaceLayerMode::kAlways - : blink::WebMediaPlayer::SurfaceLayerMode::kNever; + ? WebMediaPlayer::SurfaceLayerMode::kAlways + : WebMediaPlayer::SurfaceLayerMode::kNever; player_ = std::make_unique<WebMediaPlayerMS>( nullptr, this, &delegate_, std::make_unique<media::NullMediaLog>(), - std::unique_ptr<blink::WebMediaStreamRendererFactory>(render_factory_), - blink::scheduler::GetSingleThreadTaskRunnerForTesting(), - blink::scheduler::GetSingleThreadTaskRunnerForTesting(), - blink::scheduler::GetSingleThreadTaskRunnerForTesting(), - blink::scheduler::GetSingleThreadTaskRunnerForTesting(), - blink::scheduler::GetSingleThreadTaskRunnerForTesting(), - gpu_factories_.get(), blink::WebString(), - base::BindOnce(&WebMediaPlayerMSTest::CreateMockSurfaceLayerBridge, - base::Unretained(this)), + std::unique_ptr<WebMediaStreamRendererFactory>(render_factory_), + scheduler::GetSingleThreadTaskRunnerForTesting(), + scheduler::GetSingleThreadTaskRunnerForTesting(), + scheduler::GetSingleThreadTaskRunnerForTesting(), + scheduler::GetSingleThreadTaskRunnerForTesting(), + scheduler::GetSingleThreadTaskRunnerForTesting(), gpu_factories_.get(), + WebString(), + WTF::Bind(&WebMediaPlayerMSTest::CreateMockSurfaceLayerBridge, + WTF::Unretained(this)), std::move(submitter_), surface_layer_mode); } @@ -675,13 +675,12 @@ EXPECT_FALSE(!!render_factory_->provider()) << "There should not be a " "FrameProvider yet."; - EXPECT_CALL(*this, DoNetworkStateChanged( - blink::WebMediaPlayer::kNetworkStateLoading)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveNothing)); - player_->Load(blink::WebMediaPlayer::kLoadTypeURL, - blink::WebMediaPlayerSource(), - blink::WebMediaPlayer::kCorsModeUnspecified); + EXPECT_CALL(*this, + DoNetworkStateChanged(WebMediaPlayer::kNetworkStateLoading)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveNothing)); + player_->Load(WebMediaPlayer::kLoadTypeURL, WebMediaPlayerSource(), + WebMediaPlayer::kCorsModeUnspecified); compositor_ = player_->compositor_.get(); EXPECT_TRUE(!!compositor_); compositor_->SetAlgorithmEnabledForTesting(algorithm_enabled); @@ -698,33 +697,33 @@ } void WebMediaPlayerMSTest::NetworkStateChanged() { - blink::WebMediaPlayer::NetworkState state = player_->GetNetworkState(); + WebMediaPlayer::NetworkState state = player_->GetNetworkState(); DoNetworkStateChanged(state); - if (state == blink::WebMediaPlayer::NetworkState::kNetworkStateFormatError || - state == blink::WebMediaPlayer::NetworkState::kNetworkStateDecodeError || - state == blink::WebMediaPlayer::NetworkState::kNetworkStateNetworkError) { + if (state == WebMediaPlayer::NetworkState::kNetworkStateFormatError || + state == WebMediaPlayer::NetworkState::kNetworkStateDecodeError || + state == WebMediaPlayer::NetworkState::kNetworkStateNetworkError) { message_loop_controller_.GetPipelineStatusCB().Run( media::PipelineStatus::PIPELINE_ERROR_NETWORK); } } void WebMediaPlayerMSTest::ReadyStateChanged() { - blink::WebMediaPlayer::ReadyState state = player_->GetReadyState(); + WebMediaPlayer::ReadyState state = player_->GetReadyState(); DoReadyStateChanged(state); - if (state == blink::WebMediaPlayer::ReadyState::kReadyStateHaveMetadata && + if (state == WebMediaPlayer::ReadyState::kReadyStateHaveMetadata && !player_->HasAudio()) { const auto& size = player_->NaturalSize(); EXPECT_GT(size.width, 0); EXPECT_GT(size.height, 0); } - if (state == blink::WebMediaPlayer::ReadyState::kReadyStateHaveEnoughData) + if (state == WebMediaPlayer::ReadyState::kReadyStateHaveEnoughData) player_->Play(); } void WebMediaPlayerMSTest::SetCcLayer(cc::Layer* layer) { // Make sure that the old layer is still alive, see https://crbug.com/705448. if (layer_set_) - EXPECT_TRUE(layer_ != nullptr); + EXPECT_TRUE(layer_); layer_set_ = layer ? true : false; layer_ = layer; @@ -745,9 +744,9 @@ void WebMediaPlayerMSTest::StartRendering() { if (!rendering_) { rendering_ = true; - blink::scheduler::GetSingleThreadTaskRunnerForTesting()->PostTask( - FROM_HERE, base::BindOnce(&WebMediaPlayerMSTest::RenderFrame, - base::Unretained(this))); + scheduler::GetSingleThreadTaskRunnerForTesting()->PostTask( + FROM_HERE, WTF::Bind(&WebMediaPlayerMSTest::RenderFrame, + weak_factory_.GetWeakPtr())); } DoStartRendering(); } @@ -780,10 +779,9 @@ auto frame = compositor_->GetCurrentFrame(); compositor_->PutCurrentFrame(); } - blink::scheduler::GetSingleThreadTaskRunnerForTesting()->PostDelayedTask( + scheduler::GetSingleThreadTaskRunnerForTesting()->PostDelayedTask( FROM_HERE, - base::BindOnce(&WebMediaPlayerMSTest::RenderFrame, - base::Unretained(this)), + WTF::Bind(&WebMediaPlayerMSTest::RenderFrame, weak_factory_.GetWeakPtr()), base::TimeDelta::FromSecondsD(1.0 / 60.0)); } @@ -794,11 +792,11 @@ TEST_P(WebMediaPlayerMSTest, NoDataDuringLoadForVideo) { InitializeWebMediaPlayerMS(); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)) + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)) .Times(0); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)) + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)) .Times(0); LoadAndGetFrameProvider(true); @@ -813,22 +811,21 @@ TEST_P(WebMediaPlayerMSTest, NoWaitForFrameForAudio) { InitializeWebMediaPlayerMS(); is_audio_element_ = true; - scoped_refptr<blink::WebMediaStreamAudioRenderer> audio_renderer( + scoped_refptr<WebMediaStreamAudioRenderer> audio_renderer( new MockMediaStreamAudioRenderer()); render_factory_->set_audio_renderer(audio_renderer); - EXPECT_CALL(*this, DoNetworkStateChanged( - blink::WebMediaPlayer::kNetworkStateLoading)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveNothing)); + EXPECT_CALL(*this, + DoNetworkStateChanged(WebMediaPlayer::kNetworkStateLoading)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveNothing)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); - player_->Load(blink::WebMediaPlayer::kLoadTypeURL, - blink::WebMediaPlayerSource(), - blink::WebMediaPlayer::kCorsModeUnspecified); + player_->Load(WebMediaPlayer::kLoadTypeURL, WebMediaPlayerSource(), + WebMediaPlayer::kCorsModeUnspecified); message_loop_controller_.RunAndWaitForStatus( media::PipelineStatus::PIPELINE_OK); @@ -840,13 +837,13 @@ TEST_P(WebMediaPlayerMSTest, NoWaitForFrameForAudioOnly) { InitializeWebMediaPlayerMS(); render_factory_->set_support_video_renderer(false); - scoped_refptr<blink::WebMediaStreamAudioRenderer> audio_renderer( + scoped_refptr<WebMediaStreamAudioRenderer> audio_renderer( new MockMediaStreamAudioRenderer()); render_factory_->set_audio_renderer(audio_renderer); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); LoadAndGetFrameProvider(true); EXPECT_CALL(*this, DoSetCcLayer(false)); } @@ -871,15 +868,15 @@ EXPECT_CALL(*this, DoSetCcLayer(true)); EXPECT_CALL(*this, DoStartRendering()); } - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); EXPECT_CALL(*this, CheckSizeChanged(gfx::Size(kStandardWidth, kStandardHeight))); message_loop_controller_.RunAndWaitForStatus( media::PipelineStatus::PIPELINE_OK); - const blink::WebSize& natural_size = player_->NaturalSize(); + const WebSize& natural_size = player_->NaturalSize(); EXPECT_EQ(kStandardWidth, natural_size.width); EXPECT_EQ(kStandardHeight, natural_size.height); testing::Mock::VerifyAndClearExpectations(this); @@ -913,10 +910,10 @@ EXPECT_CALL(*this, DoSetCcLayer(true)); EXPECT_CALL(*this, DoStartRendering()); } - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); gfx::Size frame_size = gfx::Size(kStandardWidth - (odd_size_frame ? kOddSizeOffset : 0), kStandardHeight - (odd_size_frame ? kOddSizeOffset : 0)); @@ -964,10 +961,10 @@ EXPECT_CALL(*this, DoSetCcLayer(true)); EXPECT_CALL(*this, DoStartRendering()); } - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); gfx::Size frame_size = gfx::Size(kStandardWidth - (odd_size_frame ? kOddSizeOffset : 0), kStandardHeight - (odd_size_frame ? kOddSizeOffset : 0)); @@ -1029,10 +1026,10 @@ EXPECT_CALL(*this, DoSetCcLayer(true)); EXPECT_CALL(*this, DoStartRendering()); } - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); EXPECT_CALL(*this, CheckSizeChanged(gfx::Size(kStandardWidth, kStandardHeight))); message_loop_controller_.RunAndWaitForStatus( @@ -1041,7 +1038,7 @@ // Make sure we run all non-delayed tasks (E.G. CheckForFrameChanges) before // testing state. base::RunLoop().RunUntilIdle(); - blink::WebSize natural_size = player_->NaturalSize(); + WebSize natural_size = player_->NaturalSize(); // Check that height and width are flipped. EXPECT_EQ(kStandardHeight, natural_size.width); EXPECT_EQ(kStandardWidth, natural_size.height); @@ -1092,10 +1089,10 @@ EXPECT_CALL(*this, DoSetCcLayer(true)); EXPECT_CALL(*this, DoStartRendering()); } - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); EXPECT_CALL(*this, CheckSizeChanged(gfx::Size(kStandardWidth, kStandardHeight))); message_loop_controller_.RunAndWaitForStatus( @@ -1104,7 +1101,7 @@ // Make sure we run all non-delayed tasks before testing state. base::RunLoop().RunUntilIdle(); if (!enable_surface_layer_for_video_) { - ASSERT_TRUE(layer_ != nullptr); + ASSERT_TRUE(layer_); EXPECT_TRUE(layer_->contents_opaque()); } @@ -1167,10 +1164,10 @@ EXPECT_CALL(*this, DoSetCcLayer(true)); EXPECT_CALL(*this, DoStartRendering()); } - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); gfx::Size frame_size = gfx::Size(kStandardWidth, kStandardHeight); EXPECT_CALL(*this, CheckSizeChanged(frame_size)); message_loop_controller_.RunAndWaitForStatus( @@ -1226,10 +1223,10 @@ EXPECT_CALL(*this, DoSetCcLayer(true)); EXPECT_CALL(*this, DoStartRendering()); } - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); EXPECT_CALL(*this, CheckSizeChanged(gfx::Size(kStandardWidth, kStandardHeight))); EXPECT_CALL(*this, CheckSizeChanged( @@ -1266,10 +1263,10 @@ EXPECT_CALL(*this, DoSetCcLayer(true)); EXPECT_CALL(*this, DoStartRendering()); } - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveMetadata)); - EXPECT_CALL(*this, DoReadyStateChanged( - blink::WebMediaPlayer::kReadyStateHaveEnoughData)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveMetadata)); + EXPECT_CALL(*this, + DoReadyStateChanged(WebMediaPlayer::kReadyStateHaveEnoughData)); EXPECT_CALL(*this, CheckSizeChanged(provider->get_standard_size())); // Run all the tasks that will assign current frame in @@ -1278,7 +1275,7 @@ base::RunLoop().RunUntilIdle(); auto frame = compositor_->GetCurrentFrame(); - ASSERT_TRUE(frame != nullptr); + ASSERT_TRUE(frame); testing::Mock::VerifyAndClearExpectations(this); EXPECT_CALL(*this, DoSetCcLayer(false)); @@ -1344,4 +1341,4 @@ ::testing::Combine(::testing::Bool(), ::testing::Bool(), ::testing::Bool())); -} // namespace content +} // namespace blink
diff --git a/third_party/blink/renderer/modules/push_messaging/push_messaging_client.cc b/third_party/blink/renderer/modules/push_messaging/push_messaging_client.cc index b81b5ff..a5a32209 100644 --- a/third_party/blink/renderer/modules/push_messaging/push_messaging_client.cc +++ b/third_party/blink/renderer/modules/push_messaging/push_messaging_client.cc
@@ -89,7 +89,7 @@ DidSubscribe( service_worker_registration, std::move(callbacks), mojom::blink::PushRegistrationStatus::MANIFEST_EMPTY_OR_MISSING, - base::nullopt, nullptr, base::nullopt, base::nullopt); + nullptr /* subscription */); return; } @@ -115,7 +115,7 @@ if (options->application_server_key.IsEmpty()) { DidSubscribe(service_worker_registration, std::move(callbacks), mojom::blink::PushRegistrationStatus::NO_SENDER_ID, - base::nullopt, nullptr, base::nullopt, base::nullopt); + nullptr /* subscription */); return; } @@ -131,10 +131,7 @@ ServiceWorkerRegistration* service_worker_registration, std::unique_ptr<PushSubscriptionCallbacks> callbacks, mojom::blink::PushRegistrationStatus status, - const base::Optional<KURL>& endpoint, - mojom::blink::PushSubscriptionOptionsPtr options, - const base::Optional<WTF::Vector<uint8_t>>& p256dh, - const base::Optional<WTF::Vector<uint8_t>>& auth) { + mojom::blink::PushSubscriptionPtr subscription) { DCHECK(callbacks); if (status == @@ -142,15 +139,10 @@ status == mojom::blink::PushRegistrationStatus:: SUCCESS_NEW_SUBSCRIPTION_FROM_PUSH_SERVICE || status == mojom::blink::PushRegistrationStatus::SUCCESS_FROM_CACHE) { - DCHECK(endpoint); - DCHECK(options); - DCHECK(p256dh); - DCHECK(auth); + DCHECK(subscription); - callbacks->OnSuccess(PushSubscription::Create( - endpoint.value(), options->user_visible_only, - options->application_server_key, p256dh.value(), auth.value(), - service_worker_registration)); + callbacks->OnSuccess(PushSubscription::Create(std::move(subscription), + service_worker_registration)); } else { callbacks->OnError(PushError::CreateException( PushRegistrationStatusToPushErrorType(status),
diff --git a/third_party/blink/renderer/modules/push_messaging/push_messaging_client.h b/third_party/blink/renderer/modules/push_messaging/push_messaging_client.h index 256e217..606d91e 100644 --- a/third_party/blink/renderer/modules/push_messaging/push_messaging_client.h +++ b/third_party/blink/renderer/modules/push_messaging/push_messaging_client.h
@@ -64,10 +64,7 @@ void DidSubscribe(ServiceWorkerRegistration* service_worker_registration, std::unique_ptr<PushSubscriptionCallbacks> callbacks, mojom::blink::PushRegistrationStatus status, - const base::Optional<KURL>& endpoint, - mojom::blink::PushSubscriptionOptionsPtr options, - const base::Optional<WTF::Vector<uint8_t>>& p256dh, - const base::Optional<WTF::Vector<uint8_t>>& auth); + mojom::blink::PushSubscriptionPtr subscription); mojo::Remote<mojom::blink::PushMessaging> push_messaging_manager_;
diff --git a/third_party/blink/renderer/modules/push_messaging/push_provider.cc b/third_party/blink/renderer/modules/push_messaging/push_provider.cc index 4d0b1af..f487a394 100644 --- a/third_party/blink/renderer/modules/push_messaging/push_provider.cc +++ b/third_party/blink/renderer/modules/push_messaging/push_provider.cc
@@ -69,10 +69,7 @@ void PushProvider::DidSubscribe( std::unique_ptr<PushSubscriptionCallbacks> callbacks, mojom::blink::PushRegistrationStatus status, - const base::Optional<KURL>& endpoint, - mojom::blink::PushSubscriptionOptionsPtr options, - const base::Optional<WTF::Vector<uint8_t>>& p256dh, - const base::Optional<WTF::Vector<uint8_t>>& auth) { + mojom::blink::PushSubscriptionPtr subscription) { DCHECK(callbacks); if (status == @@ -80,15 +77,10 @@ status == mojom::blink::PushRegistrationStatus:: SUCCESS_NEW_SUBSCRIPTION_FROM_PUSH_SERVICE || status == mojom::blink::PushRegistrationStatus::SUCCESS_FROM_CACHE) { - DCHECK(endpoint); - DCHECK(options); - DCHECK(p256dh); - DCHECK(auth); + DCHECK(subscription); - callbacks->OnSuccess(PushSubscription::Create( - endpoint.value(), options->user_visible_only, - options->application_server_key, p256dh.value(), auth.value(), - GetSupplementable())); + callbacks->OnSuccess( + PushSubscription::Create(std::move(subscription), GetSupplementable())); } else { callbacks->OnError(PushError::CreateException( PushRegistrationStatusToPushErrorType(status), @@ -134,22 +126,14 @@ void PushProvider::DidGetSubscription( std::unique_ptr<PushSubscriptionCallbacks> callbacks, mojom::blink::PushGetRegistrationStatus status, - const base::Optional<KURL>& endpoint, - mojom::blink::PushSubscriptionOptionsPtr options, - const base::Optional<WTF::Vector<uint8_t>>& p256dh, - const base::Optional<WTF::Vector<uint8_t>>& auth) { + mojom::blink::PushSubscriptionPtr subscription) { DCHECK(callbacks); if (status == mojom::blink::PushGetRegistrationStatus::SUCCESS) { - DCHECK(endpoint); - DCHECK(options); - DCHECK(p256dh); - DCHECK(auth); + DCHECK(subscription); - callbacks->OnSuccess(PushSubscription::Create( - endpoint.value(), options->user_visible_only, - options->application_server_key, p256dh.value(), auth.value(), - GetSupplementable())); + callbacks->OnSuccess( + PushSubscription::Create(std::move(subscription), GetSupplementable())); } else { // We are only expecting an error if we can't find a registration. callbacks->OnSuccess(nullptr);
diff --git a/third_party/blink/renderer/modules/push_messaging/push_provider.h b/third_party/blink/renderer/modules/push_messaging/push_provider.h index 6c10e97e..64b942b 100644 --- a/third_party/blink/renderer/modules/push_messaging/push_provider.h +++ b/third_party/blink/renderer/modules/push_messaging/push_provider.h
@@ -26,7 +26,6 @@ enum class PushRegistrationStatus; } // namespace mojom -class KURL; class PushSubscriptionOptions; class PushProvider final : public GarbageCollectedFinalized<PushProvider>, @@ -54,10 +53,7 @@ void DidSubscribe(std::unique_ptr<PushSubscriptionCallbacks> callbacks, mojom::blink::PushRegistrationStatus status, - const base::Optional<KURL>& endpoint, - mojom::blink::PushSubscriptionOptionsPtr options, - const base::Optional<WTF::Vector<uint8_t>>& p256dh, - const base::Optional<WTF::Vector<uint8_t>>& auth); + mojom::blink::PushSubscriptionPtr subscription); void DidUnsubscribe(std::unique_ptr<PushUnsubscribeCallbacks> callbacks, mojom::blink::PushErrorType error_type, @@ -66,10 +62,7 @@ void DidGetSubscription(std::unique_ptr<PushSubscriptionCallbacks> callbacks, mojom::blink::PushGetRegistrationStatus status, - const base::Optional<KURL>& endpoint, - mojom::blink::PushSubscriptionOptionsPtr options, - const base::Optional<WTF::Vector<uint8_t>>& p256dh, - const base::Optional<WTF::Vector<uint8_t>>& auth); + mojom::blink::PushSubscriptionPtr subscription); mojo::Remote<mojom::blink::PushMessaging> push_messaging_manager_;
diff --git a/third_party/blink/renderer/modules/push_messaging/push_subscription.cc b/third_party/blink/renderer/modules/push_messaging/push_subscription.cc index 41ba9eb..e22e0c0 100644 --- a/third_party/blink/renderer/modules/push_messaging/push_subscription.cc +++ b/third_party/blink/renderer/modules/push_messaging/push_subscription.cc
@@ -49,15 +49,12 @@ // static PushSubscription* PushSubscription::Create( - const KURL& endpoint, - bool user_visible_only, - const WTF::Vector<uint8_t>& application_server_key, - const WTF::Vector<unsigned char>& p256dh, - const WTF::Vector<unsigned char>& auth, + mojom::blink::PushSubscriptionPtr subscription, ServiceWorkerRegistration* service_worker_registration) { return MakeGarbageCollected<PushSubscription>( - endpoint, user_visible_only, application_server_key, p256dh, auth, - service_worker_registration); + subscription->endpoint, subscription->options->user_visible_only, + subscription->options->application_server_key, subscription->p256dh, + subscription->auth, service_worker_registration); } PushSubscription::PushSubscription(
diff --git a/third_party/blink/renderer/modules/push_messaging/push_subscription.h b/third_party/blink/renderer/modules/push_messaging/push_subscription.h index 0910cb2..3c99499 100644 --- a/third_party/blink/renderer/modules/push_messaging/push_subscription.h +++ b/third_party/blink/renderer/modules/push_messaging/push_subscription.h
@@ -8,6 +8,7 @@ #include <memory> #include "base/gtest_prod_util.h" #include "base/memory/scoped_refptr.h" +#include "third_party/blink/public/mojom/push_messaging/push_messaging.mojom-blink.h" #include "third_party/blink/renderer/bindings/core/v8/script_promise.h" #include "third_party/blink/renderer/bindings/core/v8/script_value.h" #include "third_party/blink/renderer/core/dom/dom_time_stamp.h" @@ -29,11 +30,7 @@ public: static PushSubscription* Create( - const KURL& endpoint, - bool user_visible_only, - const WTF::Vector<uint8_t>& application_server_key, - const WTF::Vector<unsigned char>& p256dh, - const WTF::Vector<unsigned char>& auth, + mojom::blink::PushSubscriptionPtr subscription, ServiceWorkerRegistration* service_worker_registration); PushSubscription(const KURL& endpoint,
diff --git a/third_party/blink/renderer/modules/push_messaging/service_worker_global_scope_push.h b/third_party/blink/renderer/modules/push_messaging/service_worker_global_scope_push.h index 63ce901..e1cb3ee 100644 --- a/third_party/blink/renderer/modules/push_messaging/service_worker_global_scope_push.h +++ b/third_party/blink/renderer/modules/push_messaging/service_worker_global_scope_push.h
@@ -12,6 +12,8 @@ class ServiceWorkerGlobalScopePush { public: DEFINE_STATIC_ATTRIBUTE_EVENT_LISTENER(push, kPush) + DEFINE_STATIC_ATTRIBUTE_EVENT_LISTENER(pushsubscriptionchange, + kPushsubscriptionchange) }; } // namespace blink
diff --git a/third_party/blink/renderer/modules/push_messaging/service_worker_global_scope_push.idl b/third_party/blink/renderer/modules/push_messaging/service_worker_global_scope_push.idl index cc7848a..e98c6fe 100644 --- a/third_party/blink/renderer/modules/push_messaging/service_worker_global_scope_push.idl +++ b/third_party/blink/renderer/modules/push_messaging/service_worker_global_scope_push.idl
@@ -7,4 +7,5 @@ RuntimeEnabled=PushMessaging ] partial interface ServiceWorkerGlobalScope { attribute EventHandler onpush; + [RuntimeEnabled=PushMessagingSubscriptionChange] attribute EventHandler onpushsubscriptionchange; };
diff --git a/third_party/blink/renderer/modules/service_worker/service_worker_global_scope.cc b/third_party/blink/renderer/modules/service_worker/service_worker_global_scope.cc index edc74a47..5c527560 100644 --- a/third_party/blink/renderer/modules/service_worker/service_worker_global_scope.cc +++ b/third_party/blink/renderer/modules/service_worker/service_worker_global_scope.cc
@@ -85,6 +85,7 @@ #include "third_party/blink/renderer/modules/payments/payment_request_respond_with_observer.h" #include "third_party/blink/renderer/modules/push_messaging/push_event.h" #include "third_party/blink/renderer/modules/push_messaging/push_message_data.h" +#include "third_party/blink/renderer/modules/push_messaging/push_subscription_change_event.h" #include "third_party/blink/renderer/modules/service_worker/extendable_event.h" #include "third_party/blink/renderer/modules/service_worker/extendable_message_event.h" #include "third_party/blink/renderer/modules/service_worker/fetch_event.h" @@ -1062,6 +1063,20 @@ status); } +void ServiceWorkerGlobalScope::DidHandlePushSubscriptionChangeEvent( + int event_id, + mojom::ServiceWorkerEventStatus status) { + DCHECK(IsContextThread()); + TRACE_EVENT_WITH_FLOW1( + "ServiceWorker", + "ServiceWorkerGlobalScope::DidHandlePushSubscriptionChangeEvent", + TRACE_ID_WITH_SCOPE(kServiceWorkerGlobalScopeTraceScope, + TRACE_ID_LOCAL(event_id)), + TRACE_EVENT_FLAG_FLOW_IN, "status", MojoEnumToString(status)); + RunEventCallback(&push_subscription_change_event_callbacks_, + timeout_timer_.get(), event_id, status); +} + void ServiceWorkerGlobalScope::DidHandleSyncEvent( int event_id, mojom::ServiceWorkerEventStatus status) { @@ -1728,6 +1743,30 @@ DispatchExtendableEvent(event, observer); } +void ServiceWorkerGlobalScope::DispatchPushSubscriptionChangeEvent( + mojom::blink::PushSubscriptionPtr old_subscription, + mojom::blink::PushSubscriptionPtr new_subscription, + DispatchPushSubscriptionChangeEventCallback callback) { + DCHECK(IsContextThread()); + int event_id = timeout_timer_->StartEventWithCustomTimeout( + CreateAbortCallback(&push_subscription_change_event_callbacks_), + base::TimeDelta::FromSeconds(mojom::blink::kPushEventTimeoutSeconds)); + push_subscription_change_event_callbacks_.Set(event_id, std::move(callback)); + TRACE_EVENT_WITH_FLOW0( + "ServiceWorker", + "ServiceWorkerGlobalScope::DispatchPushSubscriptionChangeEvent", + TRACE_ID_WITH_SCOPE(kServiceWorkerGlobalScopeTraceScope, + TRACE_ID_LOCAL(event_id)), + TRACE_EVENT_FLAG_FLOW_OUT); + + WaitUntilObserver* observer = WaitUntilObserver::Create( + this, WaitUntilObserver::kPushSubscriptionChange, event_id); + Event* event = PushSubscriptionChangeEvent::Create( + event_type_names::kPushsubscriptionchange, nullptr /* new_subscription */, + nullptr /* old_subscription */, observer); + DispatchExtendableEvent(event, observer); +} + void ServiceWorkerGlobalScope::DispatchSyncEvent( const String& tag, bool last_chance,
diff --git a/third_party/blink/renderer/modules/service_worker/service_worker_global_scope.h b/third_party/blink/renderer/modules/service_worker/service_worker_global_scope.h index 4fd425c..4ec1ff3 100644 --- a/third_party/blink/renderer/modules/service_worker/service_worker_global_scope.h +++ b/third_party/blink/renderer/modules/service_worker/service_worker_global_scope.h
@@ -250,6 +250,9 @@ void DidHandleNotificationCloseEvent(int event_id, mojom::ServiceWorkerEventStatus); void DidHandlePushEvent(int push_event_id, mojom::ServiceWorkerEventStatus); + void DidHandlePushSubscriptionChangeEvent( + int event_id, + mojom::ServiceWorkerEventStatus status); void DidHandleSyncEvent(int sync_event_id, mojom::ServiceWorkerEventStatus); void DidHandlePeriodicSyncEvent(int event_id, mojom::ServiceWorkerEventStatus status); @@ -394,6 +397,10 @@ DispatchNotificationCloseEventCallback callback) override; void DispatchPushEvent(const String& payload, DispatchPushEventCallback callback) override; + void DispatchPushSubscriptionChangeEvent( + mojom::blink::PushSubscriptionPtr old_subscription, + mojom::blink::PushSubscriptionPtr new_subscription, + DispatchPushSubscriptionChangeEventCallback callback) override; void DispatchSyncEvent(const String& tag, bool last_chance, base::TimeDelta timeout, @@ -481,6 +488,8 @@ HashMap<int, DispatchNotificationCloseEventCallback> notification_close_event_callbacks_; HashMap<int, DispatchPushEventCallback> push_event_callbacks_; + HashMap<int, DispatchPushSubscriptionChangeEventCallback> + push_subscription_change_event_callbacks_; HashMap<int, DispatchFetchEventInternalCallback> fetch_event_callbacks_; HashMap<int, DispatchCookieChangeEventCallback> cookie_change_event_callbacks_;
diff --git a/third_party/blink/renderer/modules/service_worker/wait_until_observer.cc b/third_party/blink/renderer/modules/service_worker/wait_until_observer.cc index c49f421..c1aa32f 100644 --- a/third_party/blink/renderer/modules/service_worker/wait_until_observer.cc +++ b/third_party/blink/renderer/modules/service_worker/wait_until_observer.cc
@@ -294,6 +294,10 @@ case kPush: service_worker_global_scope->DidHandlePushEvent(event_id_, status); break; + case kPushSubscriptionChange: + service_worker_global_scope->DidHandlePushSubscriptionChangeEvent( + event_id_, status); + break; case kSync: service_worker_global_scope->DidHandleSyncEvent(event_id_, status); break;
diff --git a/third_party/blink/renderer/modules/service_worker/wait_until_observer.h b/third_party/blink/renderer/modules/service_worker/wait_until_observer.h index 6a71973a..05f1e11 100644 --- a/third_party/blink/renderer/modules/service_worker/wait_until_observer.h +++ b/third_party/blink/renderer/modules/service_worker/wait_until_observer.h
@@ -40,6 +40,7 @@ kNotificationClose, kPaymentRequest, kPush, + kPushSubscriptionChange, kSync, kPeriodicSync, kBackgroundFetchAbort,
diff --git a/third_party/blink/renderer/modules/wake_lock/wake_lock.cc b/third_party/blink/renderer/modules/wake_lock/wake_lock.cc index 50ee0f4..9120018 100644 --- a/third_party/blink/renderer/modules/wake_lock/wake_lock.cc +++ b/third_party/blink/renderer/modules/wake_lock/wake_lock.cc
@@ -17,15 +17,6 @@ namespace blink { -namespace { - -Document* GetDocument(ScriptState* script_state) { - ExecutionContext* execution_context = ExecutionContext::From(script_state); - return To<Document>(execution_context); -} - -} // namespace - // static ScriptPromise WakeLock::requestPermission(ScriptState* script_state, const String& type) { @@ -38,9 +29,9 @@ // 2.1. Let state be the result of running and waiting for the obtain // permission steps with type. // 2.2. Resolve promise with state. - auto* document = GetDocument(script_state); - WakeLockController::From(*document).RequestPermission(ToWakeLockType(type), - resolver); + auto* document = To<Document>(ExecutionContext::From(script_state)); + WakeLockController::From(document).RequestPermission(ToWakeLockType(type), + resolver); return promise; } @@ -49,36 +40,21 @@ const String& type, WakeLockRequestOptions* options) { // https://w3c.github.io/wake-lock/#request-static-method - // We only support [Exposed=Window] for now. - DCHECK(ExecutionContext::From(script_state)->IsDocument()); - - // 2. Let document be the responsible document of the current settings object. - auto* document = GetDocument(script_state); - - // 3. If the current global object is the DedicatedWorkerGlobalScope object: - // 3.1. If the current global object's owner set is empty, reject promise with - // a "NotAllowedError" DOMException and return promise. - // 3.2. If type is "screen", reject promise with a "NotAllowedError" - // DOMException, and return promise. - - // 4. Otherwise, if the current global object is the Window object: - // 4.1. If the document's browsing context is null, reject promise with a - // "NotAllowedError" DOMException and return promise. - if (!document) { - return ScriptPromise::RejectWithDOMException( - script_state, MakeGarbageCollected<DOMException>( - DOMExceptionCode::kNotAllowedError, - "The document has no associated browsing context")); - } + auto* context = ExecutionContext::From(script_state); + DCHECK(context->IsDocument() || context->IsDedicatedWorkerGlobalScope()); // 2.1. If document is not allowed to use the policy-controlled feature named // "wake-lock", reject promise with a "NotAllowedError" DOMException and // return promise. + // [N.B. Per https://github.com/w3c/webappsec-feature-policy/issues/207 there + // is no official support for workers in the Feature Policy spec, but we can + // perform FP checks in workers in Blink] // 2.2. If the user agent denies the wake lock of this type for document, // reject promise with a "NotAllowedError" DOMException and return // promise. - if (!document->IsFeatureEnabled(mojom::FeaturePolicyFeature::kWakeLock, - ReportOptions::kReportOnFailure)) { + if (!context->GetSecurityContext().IsFeatureEnabled( + mojom::FeaturePolicyFeature::kWakeLock, + ReportOptions::kReportOnFailure)) { return ScriptPromise::RejectWithDOMException( script_state, MakeGarbageCollected<DOMException>( @@ -86,23 +62,51 @@ "Access to WakeLock features is disallowed by feature policy")); } - // 4.2. If document is not fully active, reject promise with a - // "NotAllowedError" DOMException, and return promise. - if (!document->IsActive()) { - return ScriptPromise::RejectWithDOMException( - script_state, - MakeGarbageCollected<DOMException>(DOMExceptionCode::kNotAllowedError, - "The document is not active")); - } - // 4.3. If type is "screen" and the Document of the top-level browsing context - // is hidden, reject promise with a "NotAllowedError" DOMException, and - // return promise. - if (type == "screen" && - !(document->GetPage() && document->GetPage()->IsPageVisible())) { - return ScriptPromise::RejectWithDOMException( - script_state, MakeGarbageCollected<DOMException>( - DOMExceptionCode::kNotAllowedError, - "The requesting page is not visible")); + if (context->IsDedicatedWorkerGlobalScope()) { + // 3. If the current global object is the DedicatedWorkerGlobalScope object: + // 3.1. If the current global object's owner set is empty, reject promise + // with a "NotAllowedError" DOMException and return promise. + // 3.2. If type is "screen", reject promise with a "NotAllowedError" + // DOMException, and return promise. + if (type == "screen") { + return ScriptPromise::RejectWithDOMException( + script_state, MakeGarbageCollected<DOMException>( + DOMExceptionCode::kNotAllowedError, + "Screen locks cannot be requested from workers")); + } + } else if (context->IsDocument()) { + // 2. Let document be the responsible document of the current settings + // object. + auto* document = To<Document>(context); + + // 4. Otherwise, if the current global object is the Window object: + // 4.1. If the document's browsing context is null, reject promise with a + // "NotAllowedError" DOMException and return promise. + if (!document) { + return ScriptPromise::RejectWithDOMException( + script_state, MakeGarbageCollected<DOMException>( + DOMExceptionCode::kNotAllowedError, + "The document has no associated browsing context")); + } + + // 4.2. If document is not fully active, reject promise with a + // "NotAllowedError" DOMException, and return promise. + if (!document->IsActive()) { + return ScriptPromise::RejectWithDOMException( + script_state, + MakeGarbageCollected<DOMException>(DOMExceptionCode::kNotAllowedError, + "The document is not active")); + } + // 4.3. If type is "screen" and the Document of the top-level browsing + // context is hidden, reject promise with a "NotAllowedError" + // DOMException, and return promise. + if (type == "screen" && + !(document->GetPage() && document->GetPage()->IsPageVisible())) { + return ScriptPromise::RejectWithDOMException( + script_state, MakeGarbageCollected<DOMException>( + DOMExceptionCode::kNotAllowedError, + "The requesting page is not visible")); + } } // 5. If options' signal member is present, then run the following steps: @@ -119,7 +123,7 @@ ScriptPromise promise = resolver->Promise(); WakeLockType wake_lock_type = ToWakeLockType(type); - WakeLockController& controller = WakeLockController::From(*document); + WakeLockController& controller = WakeLockController::From(context); // 5.3. Otherwise, add to signal: // 5.3.1. Run release a wake lock with promise and type.
diff --git a/third_party/blink/renderer/modules/wake_lock/wake_lock.idl b/third_party/blink/renderer/modules/wake_lock/wake_lock.idl index d465b52..6fd074a 100644 --- a/third_party/blink/renderer/modules/wake_lock/wake_lock.idl +++ b/third_party/blink/renderer/modules/wake_lock/wake_lock.idl
@@ -10,7 +10,7 @@ // https://w3c.github.io/wake-lock/#the-wakelock-interface [ SecureContext, - Exposed=Window, + Exposed=(DedicatedWorker,Window), RuntimeEnabled=WakeLock ] interface WakeLock { [CallWith=ScriptState, Exposed=Window] static Promise<PermissionState> requestPermission(WakeLockType type);
diff --git a/third_party/blink/renderer/modules/wake_lock/wake_lock_controller.cc b/third_party/blink/renderer/modules/wake_lock/wake_lock_controller.cc index 4f887b0..33c5d0b 100644 --- a/third_party/blink/renderer/modules/wake_lock/wake_lock_controller.cc +++ b/third_party/blink/renderer/modules/wake_lock/wake_lock_controller.cc
@@ -18,7 +18,7 @@ using mojom::blink::PermissionStatus; WakeLockController::WakeLockController(Document& document) - : Supplement<Document>(document), + : Supplement<ExecutionContext>(document), ContextLifecycleObserver(&document), PageVisibilityObserver(document.GetPage()), state_records_{ @@ -27,14 +27,34 @@ MakeGarbageCollected<WakeLockStateRecord>(&document, WakeLockType::kSystem)} {} +WakeLockController::WakeLockController(DedicatedWorkerGlobalScope& worker_scope) + : Supplement<ExecutionContext>(worker_scope), + ContextLifecycleObserver(&worker_scope), + PageVisibilityObserver(nullptr), + state_records_{ + MakeGarbageCollected<WakeLockStateRecord>(&worker_scope, + WakeLockType::kScreen), + MakeGarbageCollected<WakeLockStateRecord>(&worker_scope, + WakeLockType::kSystem)} {} + const char WakeLockController::kSupplementName[] = "WakeLockController"; -WakeLockController& WakeLockController::From(Document& document) { - WakeLockController* controller = - Supplement<Document>::From<WakeLockController>(document); +// static +WakeLockController& WakeLockController::From( + ExecutionContext* execution_context) { + DCHECK(execution_context->IsDocument() || + execution_context->IsDedicatedWorkerGlobalScope()); + auto* controller = + Supplement<ExecutionContext>::From<WakeLockController>(execution_context); if (!controller) { - controller = MakeGarbageCollected<WakeLockController>(document); - ProvideTo(document, controller); + if (execution_context->IsDocument()) { + controller = MakeGarbageCollected<WakeLockController>( + *To<Document>(execution_context)); + } else { + controller = MakeGarbageCollected<WakeLockController>( + *To<DedicatedWorkerGlobalScope>(execution_context)); + } + Supplement<ExecutionContext>::ProvideTo(*execution_context, controller); } return *controller; } @@ -44,7 +64,7 @@ visitor->Trace(state_record); PageVisibilityObserver::Trace(visitor); ContextLifecycleObserver::Trace(visitor); - Supplement<Document>::Trace(visitor); + Supplement<ExecutionContext>::Trace(visitor); } void WakeLockController::RequestWakeLock(WakeLockType type, @@ -192,16 +212,19 @@ mojom::blink::WakeLockType::kSystem, "WakeLockType and mojom::blink::WakeLockType must have identical values"); + auto* local_frame = GetExecutionContext()->IsDocument() + ? To<Document>(GetExecutionContext())->GetFrame() + : nullptr; + GetPermissionService().RequestPermission( CreateWakeLockPermissionDescriptor( static_cast<mojom::blink::WakeLockType>(type)), - LocalFrame::HasTransientUserActivation(GetSupplementable()->GetFrame()), - std::move(callback)); + LocalFrame::HasTransientUserActivation(local_frame), std::move(callback)); } PermissionService& WakeLockController::GetPermissionService() { if (!permission_service_) { - ConnectToPermissionService(GetSupplementable(), + ConnectToPermissionService(GetExecutionContext(), mojo::MakeRequest(&permission_service_)); } return *permission_service_;
diff --git a/third_party/blink/renderer/modules/wake_lock/wake_lock_controller.h b/third_party/blink/renderer/modules/wake_lock/wake_lock_controller.h index 241b7cf..65fb629 100644 --- a/third_party/blink/renderer/modules/wake_lock/wake_lock_controller.h +++ b/third_party/blink/renderer/modules/wake_lock/wake_lock_controller.h
@@ -11,6 +11,7 @@ #include "third_party/blink/renderer/core/dom/document.h" #include "third_party/blink/renderer/core/execution_context/context_lifecycle_observer.h" #include "third_party/blink/renderer/core/page/page_visibility_observer.h" +#include "third_party/blink/renderer/core/workers/dedicated_worker_global_scope.h" #include "third_party/blink/renderer/modules/modules_export.h" #include "third_party/blink/renderer/modules/wake_lock/wake_lock_type.h" #include "third_party/blink/renderer/platform/heap/handle.h" @@ -18,6 +19,7 @@ namespace blink { class AbortSignal; +class ExecutionContext; class ScriptPromiseResolver; class WakeLockStateRecord; @@ -25,7 +27,7 @@ // Document changes appropriately. class MODULES_EXPORT WakeLockController final : public GarbageCollectedFinalized<WakeLockController>, - public Supplement<Document>, + public Supplement<ExecutionContext>, public ContextLifecycleObserver, public PageVisibilityObserver { USING_GARBAGE_COLLECTED_MIXIN(WakeLockController); @@ -34,8 +36,9 @@ static const char kSupplementName[]; explicit WakeLockController(Document&); + explicit WakeLockController(DedicatedWorkerGlobalScope&); - static WakeLockController& From(Document&); + static WakeLockController& From(ExecutionContext*); void Trace(blink::Visitor*) override;
diff --git a/third_party/blink/renderer/modules/wake_lock/wake_lock_controller_test.cc b/third_party/blink/renderer/modules/wake_lock/wake_lock_controller_test.cc index 4e8c086..32d40ff0 100644 --- a/third_party/blink/renderer/modules/wake_lock/wake_lock_controller_test.cc +++ b/third_party/blink/renderer/modules/wake_lock/wake_lock_controller_test.cc
@@ -20,7 +20,7 @@ TEST(WakeLockControllerTest, RequestWakeLockGranted) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kScreen, mojom::blink::PermissionStatus::GRANTED); @@ -46,7 +46,7 @@ TEST(WakeLockControllerTest, RequestWakeLockDenied) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kSystem, mojom::blink::PermissionStatus::DENIED); @@ -80,7 +80,7 @@ TEST(WakeLockControllerTest, RequestWakeLockAbortEarly) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kScreen, mojom::blink::PermissionStatus::GRANTED); @@ -121,7 +121,7 @@ TEST(WakeLockControllerTest, AcquireScreenWakeLock) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); controller.AcquireWakeLock( WakeLockType::kScreen, @@ -136,7 +136,7 @@ TEST(WakeLockControllerTest, AcquireSystemWakeLock) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); controller.AcquireWakeLock( WakeLockType::kSystem, @@ -151,7 +151,7 @@ TEST(WakeLockControllerTest, AcquireMultipleLocks) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); controller.AcquireWakeLock( WakeLockType::kScreen, @@ -177,7 +177,7 @@ TEST(WakeLockControllerTest, ReleaseUnaquiredWakeLockRejectsPromise) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); MockWakeLock& screen_lock = wake_lock_service.get_wake_lock(WakeLockType::kScreen); @@ -200,7 +200,7 @@ TEST(WakeLockControllerTest, ReleaseWakeLock) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kScreen, mojom::blink::PermissionStatus::GRANTED); @@ -229,7 +229,7 @@ TEST(WakeLockControllerTest, AbortSignal) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kScreen, mojom::blink::PermissionStatus::GRANTED); @@ -262,7 +262,7 @@ TEST(WakeLockControllerTest, LossOfDocumentActivity) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); MockWakeLock& screen_lock = wake_lock_service.get_wake_lock(WakeLockType::kScreen); @@ -308,7 +308,7 @@ TEST(WakeLockControllerTest, PageVisibilityHidden) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kScreen, mojom::blink::PermissionStatus::GRANTED); @@ -368,7 +368,7 @@ TEST(WakeLockControllerTest, PageVisibilityHiddenBeforeLockAcquisition) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kScreen, mojom::blink::PermissionStatus::GRANTED); @@ -409,7 +409,7 @@ TEST(WakeLockControllerTest, PageVisibilityAndAbortSignal) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kScreen, mojom::blink::PermissionStatus::GRANTED); @@ -446,7 +446,7 @@ TEST(WakeLockControllerTest, RequestPermissionGranted) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kSystem, mojom::blink::PermissionStatus::GRANTED); @@ -467,7 +467,7 @@ TEST(WakeLockControllerTest, RequestPermissionDenied) { MockWakeLockService wake_lock_service; WakeLockTestingContext context(&wake_lock_service); - auto& controller = WakeLockController::From(*context.GetDocument()); + auto& controller = WakeLockController::From(context.GetDocument()); context.GetPermissionService().SetPermissionResponse( WakeLockType::kSystem, mojom::blink::PermissionStatus::DENIED);
diff --git a/third_party/blink/renderer/modules/wake_lock/wake_lock_state_record.cc b/third_party/blink/renderer/modules/wake_lock/wake_lock_state_record.cc index c5abb165..a431258c 100644 --- a/third_party/blink/renderer/modules/wake_lock/wake_lock_state_record.cc +++ b/third_party/blink/renderer/modules/wake_lock/wake_lock_state_record.cc
@@ -8,15 +8,17 @@ #include "services/service_manager/public/cpp/interface_provider.h" #include "third_party/blink/public/mojom/wake_lock/wake_lock.mojom-blink.h" #include "third_party/blink/renderer/bindings/core/v8/script_promise_resolver.h" -#include "third_party/blink/renderer/core/dom/document.h" #include "third_party/blink/renderer/core/dom/dom_exception.h" +#include "third_party/blink/renderer/core/execution_context/execution_context.h" #include "third_party/blink/renderer/platform/wtf/functional.h" namespace blink { -WakeLockStateRecord::WakeLockStateRecord(Document* document, WakeLockType type) - : wake_lock_type_(ToMojomWakeLockType(type)), document_(document) { - DCHECK_NE(document, nullptr); +WakeLockStateRecord::WakeLockStateRecord(ExecutionContext* execution_context, + WakeLockType type) + : wake_lock_type_(ToMojomWakeLockType(type)), + execution_context_(execution_context) { + DCHECK_NE(execution_context, nullptr); } void WakeLockStateRecord::AcquireWakeLock(ScriptPromiseResolver* resolver) { @@ -35,7 +37,7 @@ // 4.3. Add lockPromise to record.[[WakeLockStateRecord]]. // 5. Return active. if (!wake_lock_) { - auto* interface_provider = document_->GetInterfaceProvider(); + auto* interface_provider = execution_context_->GetInterfaceProvider(); DCHECK(interface_provider); mojom::blink::WakeLockServicePtr wake_lock_service; interface_provider->GetInterface(mojo::MakeRequest(&wake_lock_service)); @@ -96,7 +98,7 @@ } void WakeLockStateRecord::Trace(blink::Visitor* visitor) { - visitor->Trace(document_); + visitor->Trace(execution_context_); visitor->Trace(active_locks_); }
diff --git a/third_party/blink/renderer/modules/wake_lock/wake_lock_state_record.h b/third_party/blink/renderer/modules/wake_lock/wake_lock_state_record.h index bf6c4325..1a653083 100644 --- a/third_party/blink/renderer/modules/wake_lock/wake_lock_state_record.h +++ b/third_party/blink/renderer/modules/wake_lock/wake_lock_state_record.h
@@ -13,7 +13,7 @@ namespace blink { -class Document; +class ExecutionContext; class ScriptPromiseResolver; // https://w3c.github.io/wake-lock/#concepts-and-state-record @@ -21,7 +21,7 @@ class MODULES_EXPORT WakeLockStateRecord : public GarbageCollectedFinalized<WakeLockStateRecord> { public: - WakeLockStateRecord(Document*, WakeLockType); + WakeLockStateRecord(ExecutionContext*, WakeLockType); void AcquireWakeLock(ScriptPromiseResolver*); void ReleaseWakeLock(ScriptPromiseResolver*); @@ -46,8 +46,8 @@ device::mojom::blink::WakeLockPtr wake_lock_; device::mojom::blink::WakeLockType wake_lock_type_; - // Document from which we will connect to |wake_lock_service_|. - Member<Document> document_; + // ExecutionContext from which we will connect to |wake_lock_service_|. + Member<ExecutionContext> execution_context_; FRIEND_TEST_ALL_PREFIXES(WakeLockStateRecordTest, AcquireWakeLock); FRIEND_TEST_ALL_PREFIXES(WakeLockStateRecordTest, ReleaseAllWakeLocks);
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_bind_group.cc b/third_party/blink/renderer/modules/webgpu/gpu_bind_group.cc index 2a870cef..b30a9f81 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_bind_group.cc +++ b/third_party/blink/renderer/modules/webgpu/gpu_bind_group.cc
@@ -23,9 +23,7 @@ GPUBufferBinding* buffer = webgpu_binding->resource().GetAsGPUBufferBinding(); dawn_binding.offset = buffer->offset(); - // UINT64_MAX is used as a special value in Dawn to indicate that it should - // use the whole size of the buffer. - dawn_binding.size = buffer->hasSize() ? buffer->size() : UINT64_MAX; + dawn_binding.size = buffer->hasSize() ? buffer->size() : DAWN_WHOLE_SIZE; dawn_binding.buffer = AsDawnType(buffer->buffer()); } else if (webgpu_binding->resource().IsGPUSampler()) {
diff --git a/third_party/blink/renderer/platform/graphics/canvas_2d_layer_bridge.cc b/third_party/blink/renderer/platform/graphics/canvas_2d_layer_bridge.cc index 204b16d..1612dec 100644 --- a/third_party/blink/renderer/platform/graphics/canvas_2d_layer_bridge.cc +++ b/third_party/blink/renderer/platform/graphics/canvas_2d_layer_bridge.cc
@@ -535,7 +535,11 @@ FinishRasterTimers(gl_interface); } - bool measure_raster_metric = gl_interface && is_deferral_enabled_ && + // Sample one out of every kRasterMetricProbability frames to time + // This measurement only makes sense if deferral is enabled + // If the canvas is accelerated, we also need access to the gl_interface + bool measure_raster_metric = (gl_interface || !IsAccelerated()) && + is_deferral_enabled_ && bernoulli_distribution_(random_generator_); RasterTimer rasterTimer; base::Optional<base::ElapsedTimer> timer;
diff --git a/third_party/blink/renderer/platform/heap/heap.cc b/third_party/blink/renderer/platform/heap/heap.cc index 2a14109..80eb01f 100644 --- a/third_party/blink/renderer/platform/heap/heap.cc +++ b/third_party/blink/renderer/platform/heap/heap.cc
@@ -171,7 +171,7 @@ DCHECK(ephemeron_callbacks_.IsEmpty()); } -void ThreadHeap::DecommitCallbackStacks() { +void ThreadHeap::DecommitCallbackStacks(BlinkGC::StackState stack_state) { marking_worklist_.reset(nullptr); previously_not_fully_constructed_worklist_.reset(nullptr); weak_callback_worklist_.reset(nullptr); @@ -180,14 +180,24 @@ // The fixed point iteration may have found not-fully-constructed objects. // Such objects should have already been found through the stack scan though // and should thus already be marked. + // + // Possible reasons for encountering unmarked objects here: + // - Object is not allocated through MakeGarbageCollected. + // - Type is missing a USING_GARBAGE_COLLECTED_MIXIN annotation which means + // that the GC will always find pointers as in construction. + // - Broken stack (roots) scanning. if (!not_fully_constructed_worklist_->IsGlobalEmpty()) { #if DCHECK_IS_ON() + const bool conservative_gc = + BlinkGC::StackState::kHeapPointersOnStack == stack_state; NotFullyConstructedItem item; while (not_fully_constructed_worklist_->Pop(WorklistTaskId::MainThread, &item)) { HeapObjectHeader* const header = HeapObjectHeader::FromInnerAddress( reinterpret_cast<Address>(const_cast<void*>(item))); - DCHECK(header->IsMarked()); + DCHECK(conservative_gc && header->IsMarked()) + << " conservative: " << (conservative_gc ? "yes" : "no") + << " type: " << header->Name(); } #else not_fully_constructed_worklist_->Clear();
diff --git a/third_party/blink/renderer/platform/heap/heap.h b/third_party/blink/renderer/platform/heap/heap.h index 555b265..872efa0a 100644 --- a/third_party/blink/renderer/platform/heap/heap.h +++ b/third_party/blink/renderer/platform/heap/heap.h
@@ -395,7 +395,7 @@ static int ArenaIndexForObjectSize(size_t); void CommitCallbackStacks(); - void DecommitCallbackStacks(); + void DecommitCallbackStacks(BlinkGC::StackState); void InvokeEphemeronCallbacks(Visitor*);
diff --git a/third_party/blink/renderer/platform/heap/incremental_marking_test.cc b/third_party/blink/renderer/platform/heap/incremental_marking_test.cc index d6903d8..f420ec3 100644 --- a/third_party/blink/renderer/platform/heap/incremental_marking_test.cc +++ b/third_party/blink/renderer/platform/heap/incremental_marking_test.cc
@@ -94,7 +94,9 @@ heap_.CommitCallbackStacks(); } - ~IncrementalMarkingScopeBase() { heap_.DecommitCallbackStacks(); } + ~IncrementalMarkingScopeBase() { + heap_.DecommitCallbackStacks(BlinkGC::StackState::kNoHeapPointersOnStack); + } ThreadHeap& heap() const { return heap_; }
diff --git a/third_party/blink/renderer/platform/heap/thread_state.cc b/third_party/blink/renderer/platform/heap/thread_state.cc index 51c76f8..f6481f0 100644 --- a/third_party/blink/renderer/platform/heap/thread_state.cc +++ b/third_party/blink/renderer/platform/heap/thread_state.cc
@@ -851,9 +851,10 @@ void ThreadState::AtomicPauseMarkPrologue(BlinkGC::StackState stack_state, BlinkGC::MarkingType marking_type, BlinkGC::GCReason reason) { - ThreadHeapStatsCollector::Scope mark_prologue_scope( + ThreadHeapStatsCollector::EnabledScope mark_prologue_scope( Heap().stats_collector(), - ThreadHeapStatsCollector::kAtomicPauseMarkPrologue, "epoch", gc_age_); + ThreadHeapStatsCollector::kAtomicPauseMarkPrologue, "epoch", gc_age_, + "forced", reason == BlinkGC::GCReason::kForcedGCForTesting); EnterAtomicPause(); EnterGCForbiddenScope(); // Compaction needs to be canceled when incremental marking ends with a @@ -1438,25 +1439,29 @@ void ThreadState::AtomicPauseMarkRoots(BlinkGC::StackState stack_state, BlinkGC::MarkingType marking_type, BlinkGC::GCReason reason) { - ThreadHeapStatsCollector::Scope advance_tracing_scope( + ThreadHeapStatsCollector::EnabledScope advance_tracing_scope( Heap().stats_collector(), ThreadHeapStatsCollector::kAtomicPauseMarkRoots, - "epoch", gc_age_); + "epoch", gc_age_, "forced", + current_gc_data_.reason == BlinkGC::GCReason::kForcedGCForTesting); MarkPhaseVisitRoots(); MarkPhaseVisitNotFullyConstructedObjects(); } void ThreadState::AtomicPauseMarkTransitiveClosure() { - ThreadHeapStatsCollector::Scope advance_tracing_scope( + ThreadHeapStatsCollector::EnabledScope advance_tracing_scope( Heap().stats_collector(), ThreadHeapStatsCollector::kAtomicPauseMarkTransitiveClosure, "epoch", - gc_age_); + gc_age_, "forced", + current_gc_data_.reason == BlinkGC::GCReason::kForcedGCForTesting); CHECK(MarkPhaseAdvanceMarking(base::TimeTicks::Max())); } void ThreadState::AtomicPauseMarkEpilogue(BlinkGC::MarkingType marking_type) { - ThreadHeapStatsCollector::Scope stats_scope( + ThreadHeapStatsCollector::EnabledScope stats_scope( Heap().stats_collector(), - ThreadHeapStatsCollector::kAtomicPauseMarkEpilogue, "epoch", gc_age_); + ThreadHeapStatsCollector::kAtomicPauseMarkEpilogue, "epoch", gc_age_, + "forced", + current_gc_data_.reason == BlinkGC::GCReason::kForcedGCForTesting); MarkPhaseEpilogue(marking_type); LeaveAtomicPause(); LeaveGCForbiddenScope(); @@ -1467,7 +1472,9 @@ BlinkGC::SweepingType sweeping_type) { ThreadHeapStatsCollector::EnabledScope stats( Heap().stats_collector(), - ThreadHeapStatsCollector::kAtomicPauseSweepAndCompact, "epoch", gc_age_); + ThreadHeapStatsCollector::kAtomicPauseSweepAndCompact, "epoch", gc_age_, + "forced", + current_gc_data_.reason == BlinkGC::GCReason::kForcedGCForTesting); AtomicPauseScope atomic_pause_scope(this); DCHECK(InAtomicMarkingPause()); @@ -1654,7 +1661,7 @@ VisitWeakPersistents(visitor); Heap().WeakProcessing(visitor); } - Heap().DecommitCallbackStacks(); + Heap().DecommitCallbackStacks(current_gc_data_.stack_state); const size_t marked_bytes = current_gc_data_.visitor->marked_bytes(); current_gc_data_.visitor.reset();
diff --git a/third_party/blink/renderer/platform/heap/thread_state.h b/third_party/blink/renderer/platform/heap/thread_state.h index 9e219498..aed867b 100644 --- a/third_party/blink/renderer/platform/heap/thread_state.h +++ b/third_party/blink/renderer/platform/heap/thread_state.h
@@ -535,8 +535,6 @@ void UpdateIncrementalMarkingStepDuration(); - void EagerSweep(); - void SynchronizeAndFinishConcurrentSweeping(); void InvokePreFinalizers();
diff --git a/third_party/blink/tools/blinkpy/presubmit/audit_non_blink_usage.py b/third_party/blink/tools/blinkpy/presubmit/audit_non_blink_usage.py index 8c3458b..09c359a1 100755 --- a/third_party/blink/tools/blinkpy/presubmit/audit_non_blink_usage.py +++ b/third_party/blink/tools/blinkpy/presubmit/audit_non_blink_usage.py
@@ -657,6 +657,18 @@ 'allowed': [ 'media::.+', 'base::AutoLock', + 'base::Hash', + 'base::Lock', + 'base::TaskRunner', + # TODO(crbug.com/704136): Switch to using frame-based task runners. + 'base::ThreadTaskRunnerHandle', + 'cc::SkiaPaintCanvas', + 'cc::UpdateSubmissionStateCB', + 'cc::VideoFrameProvider', + 'cc::VideoLayer', + 'gpu::gles2::GLES2Interface', + 'libyuv::.+', + 'viz::.+', 'webrtc::AudioTrackInterface', 'webrtc::VideoTrackInterface', 'webrtc::MediaStreamTrackInterface',
diff --git a/third_party/blink/web_tests/TestExpectations b/third_party/blink/web_tests/TestExpectations index 8624008..0dc10262 100644 --- a/third_party/blink/web_tests/TestExpectations +++ b/third_party/blink/web_tests/TestExpectations
@@ -6234,8 +6234,8 @@ crbug.com/974334 [ Mac ] external/wpt/html/cross-origin/null.tentative.html [ Failure ] crbug.com/974334 [ Mac ] external/wpt/html/cross-origin/usecredentials.tentative.html [ Failure ] -# Flaky on Linux -crbug.com/974660 [ Linux ] http/tests/devtools/elements/highlight/highlight-node-vertical-rl.js [ Pass Failure ] +# Flaky on Linux, failing on macOS +crbug.com/984926 [ Linux Mac ] http/tests/devtools/elements/highlight/highlight-node-vertical-rl.js [ Pass Failure ] # Sheriff 2019-06-19 crbug.com/959129 [ Linux ] virtual/threaded/http/tests/devtools/tracing/timeline-script-parse.js [ Pass Failure ] @@ -6314,3 +6314,9 @@ crbug.com/970079 storage/indexeddb/structured-clone.html [ Pass Failure ] crbug.com/970079 virtual/mouseevent_fractional/fast/events/message-port-multi.html [ Pass Failure ] crbug.com/970079 virtual/threaded/external/wpt/animation-worklet/stateful-animator.https.html [ Pass Timeout ] + +# Sheriff 2019-07-17 +crbug.com/982149 [ Win7 ] external/wpt/referrer-policy/unsafe-url/http-rp/cross-origin/http-http/img-tag/no-redirect/generic.http.html [ Pass Timeout ] +crbug.com/982149 [ Win7 ] virtual/blink-cors/external/wpt/referrer-policy/unsafe-url/http-rp/cross-origin/http-http/img-tag/no-redirect/generic.http.html [ Pass Timeout ] +crbug.com/982149 [ Win7 ] virtual/not-omt-sw-fetch/external/wpt/referrer-policy/unsafe-url/http-rp/cross-origin/http-http/img-tag/no-redirect/generic.http.html [ Pass Timeout ] +crbug.com/982149 [ Win7 ] virtual/omt-worker-fetch/external/wpt/referrer-policy/unsafe-url/http-rp/cross-origin/http-http/img-tag/no-redirect/generic.http.html [ Pass Timeout ]
diff --git a/third_party/blink/web_tests/external/WPT_BASE_MANIFEST_6.json b/third_party/blink/web_tests/external/WPT_BASE_MANIFEST_6.json index 7b84d5a..b9bff578 100644 --- a/third_party/blink/web_tests/external/WPT_BASE_MANIFEST_6.json +++ b/third_party/blink/web_tests/external/WPT_BASE_MANIFEST_6.json
@@ -159474,6 +159474,9 @@ "html/semantics/text-level-semantics/the-a-element/resources/a-download-click.html": [ [] ], + "html/semantics/text-level-semantics/the-a-element/resources/a-download-redirect-to-javascript.html": [ + [] + ], "html/semantics/text-level-semantics/the-b-element/b-usage-notref.html": [ [] ], @@ -199760,6 +199763,12 @@ {} ] ], + "css/css-display/parsing/display-computed.html": [ + [ + "css/css-display/parsing/display-computed.html", + {} + ] + ], "css/css-display/parsing/display-invalid.html": [ [ "css/css-display/parsing/display-invalid.html", @@ -243680,6 +243689,12 @@ {} ] ], + "html/semantics/text-level-semantics/the-a-element/a-download-click-redirect-to-javascript.html": [ + [ + "html/semantics/text-level-semantics/the-a-element/a-download-click-redirect-to-javascript.html", + {} + ] + ], "html/semantics/text-level-semantics/the-a-element/a-download-click.html": [ [ "html/semantics/text-level-semantics/the-a-element/a-download-click.html", @@ -347821,6 +347836,10 @@ "bfd072651cb6ec82cca7d9be5b6768afbc39fca0", "testharness" ], + "css/css-display/parsing/display-computed.html": [ + "e0d08a0045866df281a3f97f174c4b318e72f34c", + "testharness" + ], "css/css-display/parsing/display-invalid.html": [ "70516ad4901f684b9d0ecd49a82671172fbc8f14", "testharness" @@ -435529,6 +435548,10 @@ "3c8adc0b97e0d236bf1667226714726d5d931c82", "testharness" ], + "html/semantics/text-level-semantics/the-a-element/a-download-click-redirect-to-javascript.html": [ + "09f63b6f4d3c775d5a351178b2d6dbd1546dbdcb", + "testharness" + ], "html/semantics/text-level-semantics/the-a-element/a-download-click.html": [ "22d329f245275b464fef83aa68f8688b810954dd", "testharness" @@ -435553,6 +435576,10 @@ "7d36c21d1e4ca80f94fe05372f685cf55ba3d776", "support" ], + "html/semantics/text-level-semantics/the-a-element/resources/a-download-redirect-to-javascript.html": [ + "4ff8b61e3be97fc49b842b4b98f53ae4accd9089", + "support" + ], "html/semantics/text-level-semantics/the-b-element/b-usage-notref.html": [ "3d3c46a281f13a8361aeef472a826834d6a0a89b", "support" @@ -439446,7 +439473,7 @@ "support" ], "interfaces/speech-api.idl": [ - "ba86d5065b7a4d941b53e5aabf133fed54b16ff4", + "8a32b457a997e651c8389c0b8da4c756ddf9f571", "support" ], "interfaces/storage.idl": [ @@ -469450,11 +469477,11 @@ "manual" ], "speech-api/historical-expected.txt": [ - "8dd3037396aa064e341bfb2ee93ae16d5026b5d5", + "07d8219a2c97c504780a4a9c9a51ab53d229d479", "support" ], "speech-api/historical.html": [ - "6dd4bd9f9ef0ee1b4856011fce0ddcf951d6052c", + "207d3e016ed1fec05d9a1256f40088c61bb05c83", "testharness" ], "speech-api/idlharness.window-expected.txt": [ @@ -480926,7 +480953,7 @@ "support" ], "webaudio/the-audio-api/the-mediastreamaudiosourcenode-interface/mediastreamaudiosourcenode-routing.html": [ - "b61c318ff0083f170fed58ee4b4a69bca807807a", + "43e5ac8e9bb6dfed192bbdfabdfbbe72f9d998a6", "testharness" ], "webaudio/the-audio-api/the-offlineaudiocontext-interface/ctor-offlineaudiocontext.html": [
diff --git a/third_party/blink/web_tests/external/wpt/cookies/navigated-away.html b/third_party/blink/web_tests/external/wpt/cookies/navigated-away.html new file mode 100644 index 0000000..bd89142 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/cookies/navigated-away.html
@@ -0,0 +1,39 @@ +<!DOCTYPE html> +<head> + <script src="/resources/testharness.js"></script> + <script src="/resources/testharnessreport.js"></script> +</head> +<body> + <iframe id="if" src="about:blank"></iframe> + <script> + var t = async_test("document.cookie behavior on documents without browser context"); + t.add_cleanup(function() { + document.cookie = "nav_away_test=yes;max-age=0"; + }); + + function step2() { + t.step(function() { + // Get from saved doc should fail. + assert_equals(window.iframeDoc.cookie, ""); + + // Try set from saved doc, should do nothing. + window.iframeDoc.cookie = "nav_away_test=second"; + assert_equals(window.iframeDoc.cookie, ""); + assert_not_equals(document.cookie.indexOf("nav_away_test=yes"), -1); + }); + t.done(); + } + + t.step(function() { + document.cookie = "nav_away_test=yes"; + var iframe = document.getElementById("if"); + // Save original document. + window.iframeDoc = iframe.contentDocument; + assert_not_equals(window.iframeDoc.cookie.indexOf("nav_away_test=yes"), -1); + + // Navigate away. + iframe.onload = step2; + iframe.contentWindow.location = "/common/blank.html"; + }) + </script> +</body>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-content-computed.html b/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-content-computed.html new file mode 100644 index 0000000..1fc152c --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-content-computed.html
@@ -0,0 +1,46 @@ +<!DOCTYPE html> +<html> +<head> +<meta charset="utf-8"> +<title>CSS Box Alignment Level 3: getComputedStyle().placeContent</title> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#propdef-place-content"> +<meta name="assert" content="place-content computed value is as specified."> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/css/support/computed-testcommon.js"></script> +</head> +<body> +<div id="target"></div> +<script> +test_computed_value("place-content", "normal normal", "normal"); + +test_computed_value("place-content", "first baseline", "baseline start"); +test_computed_value("place-content", "baseline", "baseline start"); +test_computed_value("place-content", "first baseline start", "baseline start"); +test_computed_value("place-content", "last baseline", "last baseline start"); +test_computed_value("place-content", "first baseline stretch", "baseline stretch"); +test_computed_value("place-content", "last baseline flex-start"); + +test_computed_value("place-content", "baseline stretch"); + +test_computed_value("place-content", "space-between"); +test_computed_value("place-content", "space-around"); +test_computed_value("place-content", "space-evenly"); +test_computed_value("place-content", "stretch"); + +test_computed_value("place-content", "center"); +test_computed_value("place-content", "end"); +test_computed_value("place-content", "flex-start flex-start", "flex-start"); +test_computed_value("place-content", "unsafe end unsafe end", "unsafe end"); +test_computed_value("place-content", "safe flex-start"); + +test_computed_value("place-content", "normal stretch"); +test_computed_value("place-content", "baseline space-around"); +test_computed_value("place-content", "space-evenly unsafe end"); +test_computed_value("place-content", "center normal"); + +test_computed_value("place-content", "normal right"); +test_computed_value("place-content", "baseline unsafe left"); +</script> +</body> +</html>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-items-computed.html b/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-items-computed.html new file mode 100644 index 0000000..24a0fa3 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-items-computed.html
@@ -0,0 +1,52 @@ +<!DOCTYPE html> +<html> +<head> +<meta charset="utf-8"> +<title>CSS Box Alignment Level 3: getComputedStyle().placeItems</title> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#propdef-place-items"> +<meta name="assert" content="place-items computed value is as specified."> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/css/support/computed-testcommon.js"></script> +<style> + #grandparent { + justify-items: legacy center; + } + #parent { + justify-items: legacy; + } +</style> +</head> +<body> +<div id="grandparent"> + <div id="parent"> + <div id="target"></div> + </div> +<script> +test_computed_value("place-items", "normal"); +test_computed_value("place-items", "stretch stretch", "stretch"); + +test_computed_value("place-items", "first baseline", "baseline"); +test_computed_value("place-items", "last baseline last baseline", "last baseline"); + +test_computed_value("place-items", "center"); +test_computed_value("place-items", "end end", "end"); +test_computed_value("place-items", "self-start"); +test_computed_value("place-items", "flex-end"); +test_computed_value("place-items", "unsafe center unsafe center", "unsafe center"); +test_computed_value("place-items", "safe self-end"); + +test_computed_value("place-items", "stretch baseline"); +test_computed_value("place-items", "last baseline center"); +test_computed_value("place-items", "safe self-end normal"); + +test_computed_value("place-items", "normal right"); +test_computed_value("place-items", "baseline unsafe left"); + +// When specified justify-items is legacy, computed value depends on inherited value. +test_computed_value("place-items", "flex-end legacy", "flex-end legacy center"); +test_computed_value("place-items", "stretch legacy left"); +test_computed_value("place-items", "first baseline right legacy", "baseline legacy right"); +</script> +</body> +</html>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-self-computed.html b/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-self-computed.html new file mode 100644 index 0000000..9fa4dbe --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-align/parsing/place-self-computed.html
@@ -0,0 +1,37 @@ +<!DOCTYPE html> +<html> +<head> +<meta charset="utf-8"> +<title>CSS Box Alignment Level 3: getComputedStyle().placeSelf</title> +<link rel="help" href="https://drafts.csswg.org/css-align-3/#propdef-place-self"> +<meta name="assert" content="place-self computed value is as specified."> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/css/support/computed-testcommon.js"></script> +</head> +<body> +<div id="target"></div> +<script> +test_computed_value("place-self", "auto auto", "auto"); +test_computed_value("place-self", "normal"); +test_computed_value("place-self", "stretch"); + +test_computed_value("place-self", "first baseline", "baseline"); +test_computed_value("place-self", "last baseline last baseline", "last baseline"); + +test_computed_value("place-self", "center center", "center"); +test_computed_value("place-self", "start"); +test_computed_value("place-self", "self-start"); +test_computed_value("place-self", "flex-end"); +test_computed_value("place-self", "unsafe center"); +test_computed_value("place-self", "safe self-end safe self-end", "safe self-end"); + +test_computed_value("place-self", "auto last baseline"); +test_computed_value("place-self", "baseline flex-end"); +test_computed_value("place-self", "unsafe center stretch"); + +test_computed_value("place-self", "normal right"); +test_computed_value("place-self", "baseline unsafe left"); +</script> +</body> +</html>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-align/resources/alignment-parsing-utils.js b/third_party/blink/web_tests/external/wpt/css/css-align/resources/alignment-parsing-utils.js index f549bed..2a77b4d7 100644 --- a/third_party/blink/web_tests/external/wpt/css/css-align/resources/alignment-parsing-utils.js +++ b/third_party/blink/web_tests/external/wpt/css/css-align/resources/alignment-parsing-utils.js
@@ -36,6 +36,8 @@ var resolvedValue = getComputedStyle(div).getPropertyValue(shorthand); var expectedResolvedValue = (alignValue + " " + justifyValue).trim(); + if (alignValue === justifyValue) + expectedResolvedValue = alignValue; assert_equals(div.style[shorthand], specifiedValue, shorthandValue + " specified value"); // FIXME: We need https://github.com/w3c/csswg-drafts/issues/1041 to clarify which
diff --git a/third_party/blink/web_tests/external/wpt/css/css-display/parsing/display-computed.html b/third_party/blink/web_tests/external/wpt/css/css-display/parsing/display-computed.html new file mode 100644 index 0000000..e0d08a0 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-display/parsing/display-computed.html
@@ -0,0 +1,98 @@ +<!DOCTYPE html> +<html> +<head> +<meta charset="utf-8"> +<title>CSS Display: getComputedStyle().display</title> +<link rel="help" href="https://drafts.csswg.org/css2/visuren.html#display-prop"> +<link rel="help" href="https://drafts.csswg.org/css-display/#the-display-properties"> +<link rel="help" href="https://drafts.csswg.org/css-grid-1/#grid-containers"> +<link rel="help" href="https://www.w3.org/TR/CSS2/visuren.html#dis-pos-flo"> +<meta name="assert" content="position and float can change display computed value."> +<meta name="assert" content="display computed value is otherwise as specified."> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="/css/support/computed-testcommon.js"></script> +</head> +<body> +<div id="target"></div> +<script> +'use strict'; + +// https://drafts.csswg.org/css-grid-1/#grid-containers +test_computed_value("display", "grid"); +test_computed_value("display", "inline-grid"); + +// https://drafts.csswg.org/css2/visuren.html#display-prop +test_computed_value("display", "inline"); +test_computed_value("display", "block"); +test_computed_value("display", "list-item"); +test_computed_value("display", "inline-block"); +test_computed_value("display", "table"); +test_computed_value("display", "inline-table"); +test_computed_value("display", "table-row-group"); +test_computed_value("display", "table-header-group"); +test_computed_value("display", "table-footer-group"); +test_computed_value("display", "table-row"); +test_computed_value("display", "table-column-group"); +test_computed_value("display", "table-column"); +test_computed_value("display", "table-cell"); +test_computed_value("display", "table-caption"); +test_computed_value("display", "none"); + +// https://drafts.csswg.org/css-flexbox-1/#flex-containers +test_computed_value("display", "flex"); +test_computed_value("display", "inline-flex"); + +test_computed_value("display", "contents"); + +// https://www.w3.org/TR/CSS2/visuren.html#dis-pos-flo +function test_display_affected(property, value) { + const target = document.getElementById('target'); + test(() => { + target.style[property] = value; + target.style.display = 'inline-table'; + assert_equals(getComputedStyle(target).display, 'table', 'inline-table -> block'); + + const displayValues = [ + 'inline', + 'table-row-group', + 'table-column', + 'table-column-group', + 'table-header-group', + 'table-footer-group', + 'table-row', + 'table-cell', + 'table-caption', + 'inline-block' + ]; + + for (let displayValue of displayValues) { + target.style.display = displayValue; + assert_equals(getComputedStyle(target).display, 'block', displayValue + ' -> block'); + } + + target.style.display = 'inline-flex'; + assert_equals(getComputedStyle(target).display, 'flex', 'inline-flex -> flex'); + + target.style.display = 'inline-grid'; + assert_equals(getComputedStyle(target).display, 'grid', 'inline-grid -> grid'); + + // Other values are not affected. + target.style.display = 'list-item'; + assert_equals(getComputedStyle(target).display, 'list-item', 'list-item -> list-item'); + + target.style.display = 'contents'; + assert_equals(getComputedStyle(target).display, 'contents', 'contents -> contents'); + + target.style[property] = ''; + target.style.display = ''; + }, property + ' ' + value + ' affects computed display'); +} + +test_display_affected("position", "absolute"); +test_display_affected("position", "fixed"); +test_display_affected("float", "left"); +test_display_affected("float", "right"); +</script> +</body> +</html>
diff --git a/third_party/blink/web_tests/external/wpt/fetch/sec-metadata/fetch-preflight.tentative.https.sub.html b/third_party/blink/web_tests/external/wpt/fetch/sec-metadata/fetch-preflight.tentative.https.sub.html new file mode 100644 index 0000000..a4e2125 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/fetch/sec-metadata/fetch-preflight.tentative.https.sub.html
@@ -0,0 +1,40 @@ +<!DOCTYPE html> +<script src=/resources/testharness.js></script> +<script src=/resources/testharnessreport.js></script> +<script src=/fetch/sec-metadata/resources/helper.js></script> +<script> + // Site + promise_test(t => { + return fetch("https://{{hosts[][www]}}:{{ports[https][0]}}/fetch/sec-metadata/resources/echo-as-json.py", + { + mode: "cors", + headers: { 'x-test': 'testing' } + }) + .then(r => r.json()) + .then(j => { + assert_header_equals(j, { + "dest": "empty", + "site": "same-site", + "user": "", + "mode": "cors", + }); + }); + }, "Same-site fetch with preflight"); + + promise_test(t => { + return fetch("https://{{hosts[alt][www]}}:{{ports[https][0]}}/fetch/sec-metadata/resources/echo-as-json.py", + { + mode: "cors", + headers: { 'x-test': 'testing' } + }) + .then(r => r.json()) + .then(j => { + assert_header_equals(j, { + "dest": "empty", + "site": "cross-site", + "user": "", + "mode": "cors", + }); + }); + }, "Cross-site fetch with preflight"); +</script>
diff --git a/third_party/blink/web_tests/external/wpt/fetch/sec-metadata/resources/echo-as-json.py b/third_party/blink/web_tests/external/wpt/fetch/sec-metadata/resources/echo-as-json.py index ce5a2d92..7644a85 100644 --- a/third_party/blink/web_tests/external/wpt/fetch/sec-metadata/resources/echo-as-json.py +++ b/third_party/blink/web_tests/external/wpt/fetch/sec-metadata/resources/echo-as-json.py
@@ -7,11 +7,21 @@ if "origin" in request.headers: headers.append(("Access-Control-Allow-Origin", request.headers["origin"])) + body = "" - body = json.dumps({ - "dest": request.headers.get("sec-fetch-dest", ""), - "mode": request.headers.get("sec-fetch-mode", ""), - "site": request.headers.get("sec-fetch-site", ""), - "user": request.headers.get("sec-fetch-user", ""), - }) + # If we're in a preflight, verify that `Sec-Fetch-Mode` is `cors`. + if request.method == 'OPTIONS': + if request.headers.get("sec-fetch-mode") != "cors": + return (403, "Failed"), [], body + + headers.append(("Access-Control-Allow-Methods", "*")) + headers.append(("Access-Control-Allow-Headers", "*")) + else: + body = json.dumps({ + "dest": request.headers.get("sec-fetch-dest", ""), + "mode": request.headers.get("sec-fetch-mode", ""), + "site": request.headers.get("sec-fetch-site", ""), + "user": request.headers.get("sec-fetch-user", ""), + }) + return headers, body
diff --git a/third_party/blink/web_tests/external/wpt/interfaces/speech-api.idl b/third_party/blink/web_tests/external/wpt/interfaces/speech-api.idl index ba86d50..8a32b45 100644 --- a/third_party/blink/web_tests/external/wpt/interfaces/speech-api.idl +++ b/third_party/blink/web_tests/external/wpt/interfaces/speech-api.idl
@@ -11,7 +11,6 @@ attribute boolean continuous; attribute boolean interimResults; attribute unsigned long maxAlternatives; - attribute DOMString serviceURI; // methods to drive the speech interaction void start();
diff --git a/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch-manual.html b/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch.html similarity index 86% rename from third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch-manual.html rename to third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch.html index 592139f..7b713f9 100644 --- a/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch-manual.html +++ b/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch.html
@@ -7,6 +7,9 @@ <link rel="stylesheet" type="text/css" href="../pointerevent_styles.css"> <script src="/resources/testharness.js"></script> <script src="/resources/testharnessreport.js"></script> + <script src="/resources/testdriver.js"></script> + <script src="/resources/testdriver-actions.js"></script> + <script src="/resources/testdriver-vendor.js"></script> <script src="../pointerevent_support.js"></script> <style> #target0 { @@ -83,6 +86,7 @@ function run() { var target0 = document.getElementById("target0"); var btnComplete = document.getElementById("btnComplete"); + var actions_promise; target0.scrollTop = 200; var scrollListenerExecuted = false; @@ -100,9 +104,22 @@ assert_equals(target0.scrollLeft, 0, "scroll x offset should be 0 in the end of the test"); assert_greater_than(target0.scrollTop, 200, "scroll y offset should be greater than 200 in the end of the test"); }); - test_touchaction.done(); + + // Make sure the test finishes after all the input actions are completed. + actions_promise.then( () => { + test_touchaction.done(); + }); updateDescriptionComplete(); }); + + // Inject touch inputs. + actions_promise = touchScrollInTarget(target0, 'up').then(function() { + return touchScrollInTarget(target0, 'right'); + }).then(function() { + return touchScrollInTarget(target0, 'down'); + }).then(function() { + return clickInTarget("touch", btnComplete); + }); } </script> <h1>touch-action: pan-down</h1>
diff --git a/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch-manual.html b/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch.html similarity index 86% rename from third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch-manual.html rename to third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch.html index 7030d5e48..f1becf3 100644 --- a/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch-manual.html +++ b/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch.html
@@ -7,6 +7,9 @@ <link rel="stylesheet" type="text/css" href="../pointerevent_styles.css"> <script src="/resources/testharness.js"></script> <script src="/resources/testharnessreport.js"></script> + <script src="/resources/testdriver.js"></script> + <script src="/resources/testdriver-actions.js"></script> + <script src="/resources/testdriver-vendor.js"></script> <script src="../pointerevent_support.js"></script> <style> #target0 { @@ -83,6 +86,7 @@ function run() { var target0 = document.getElementById("target0"); var btnComplete = document.getElementById("btnComplete"); + var actions_promise; target0.scrollLeft = 200; var scrollListenerExecuted = false; @@ -100,9 +104,22 @@ assert_less_than(target0.scrollLeft, 200, "scroll x offset should be less than 200 in the end of the test"); assert_equals(target0.scrollTop, 0, "scroll y offset should be 0 in the end of the test"); }); - test_touchaction.done(); + + // Make sure the test finishes after all the input actions are completed. + actions_promise.then( () => { + test_touchaction.done(); + }); updateDescriptionComplete(); }); + + // Inject touch inputs. + actions_promise = touchScrollInTarget(target0, 'down').then(function() { + return touchScrollInTarget(target0, 'right'); + }).then(function() { + return touchScrollInTarget(target0, 'left'); + }).then(function() { + return clickInTarget("touch", btnComplete); + }); } </script> <h1>touch-action: pan-left</h1>
diff --git a/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch-manual.html b/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch.html similarity index 86% rename from third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch-manual.html rename to third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch.html index e711236..2c93b550 100644 --- a/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch-manual.html +++ b/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch.html
@@ -7,6 +7,9 @@ <link rel="stylesheet" type="text/css" href="../pointerevent_styles.css"> <script src="/resources/testharness.js"></script> <script src="/resources/testharnessreport.js"></script> + <script src="/resources/testdriver.js"></script> + <script src="/resources/testdriver-actions.js"></script> + <script src="/resources/testdriver-vendor.js"></script> <script src="../pointerevent_support.js"></script> <style> #target0 { @@ -83,6 +86,7 @@ function run() { var target0 = document.getElementById("target0"); var btnComplete = document.getElementById("btnComplete"); + var actions_promise; target0.scrollLeft = 200; var scrollListenerExecuted = false; @@ -100,9 +104,22 @@ assert_greater_than(target0.scrollLeft, 200, "scroll x offset should be greater than 200 in the end of the test"); assert_equals(target0.scrollTop, 0, "scroll y offset should be 0 in the end of the test"); }); - test_touchaction.done(); + + // Make sure the test finishes after all the input actions are completed. + actions_promise.then( () => { + test_touchaction.done(); + }); updateDescriptionComplete(); }); + + // Inject touch inputs. + actions_promise = touchScrollInTarget(target0, 'down').then(function() { + return touchScrollInTarget(target0, 'left'); + }).then(function() { + return touchScrollInTarget(target0, 'right'); + }).then(function() { + return clickInTarget("touch", btnComplete); + }); } </script> <h1>touch-action: pan-right</h1>
diff --git a/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch-manual.html b/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch.html similarity index 86% rename from third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch-manual.html rename to third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch.html index 46ddaa2..30fb3bdf 100644 --- a/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch-manual.html +++ b/third_party/blink/web_tests/external/wpt/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch.html
@@ -7,6 +7,9 @@ <link rel="stylesheet" type="text/css" href="../pointerevent_styles.css"> <script src="/resources/testharness.js"></script> <script src="/resources/testharnessreport.js"></script> + <script src="/resources/testdriver.js"></script> + <script src="/resources/testdriver-actions.js"></script> + <script src="/resources/testdriver-vendor.js"></script> <script src="../pointerevent_support.js"></script> <style> #target0 { @@ -83,6 +86,7 @@ function run() { var target0 = document.getElementById("target0"); var btnComplete = document.getElementById("btnComplete"); + var actions_promise; target0.scrollTop = 200; var scrollListenerExecuted = false; @@ -100,9 +104,22 @@ assert_equals(target0.scrollLeft, 0, "scroll x offset should be 0 in the end of the test"); assert_less_than(target0.scrollTop, 200, "scroll y offset should be less than 200 in the end of the test"); }); - test_touchaction.done(); + + // Make sure the test finishes after all the input actions are completed. + actions_promise.then( () => { + test_touchaction.done(); + }); updateDescriptionComplete(); }); + + // Inject touch inputs. + actions_promise = touchScrollInTarget(target0, 'down').then(function() { + return touchScrollInTarget(target0, 'right'); + }).then(function() { + return touchScrollInTarget(target0, 'up'); + }).then(function() { + return clickInTarget("touch", btnComplete); + }); } </script> <h1>touch-action: pan-up</h1>
diff --git a/third_party/blink/web_tests/external/wpt/pointerevents/pointerevent_support.js b/third_party/blink/web_tests/external/wpt/pointerevents/pointerevent_support.js index 3b37f48..29d48e0 100644 --- a/third_party/blink/web_tests/external/wpt/pointerevents/pointerevent_support.js +++ b/third_party/blink/web_tests/external/wpt/pointerevents/pointerevent_support.js
@@ -272,7 +272,7 @@ throw("scroll direction '" + direction + "' is not expected, direction should be 'down', 'up', 'left' or 'right'"); } return new test_driver.Actions() - .addPointer("pointer1", "touch") + .addPointer("touchPointer1", "touch") .pointerMove(0, 0, {origin: target}) .pointerDown() .pointerMove(x_delta, y_delta, {origin: target})
diff --git a/third_party/blink/web_tests/external/wpt/pointerevents/pointerevent_touch-action-keyboard.html b/third_party/blink/web_tests/external/wpt/pointerevents/pointerevent_touch-action-keyboard.html index fdddd331..aeff7133 100644 --- a/third_party/blink/web_tests/external/wpt/pointerevents/pointerevent_touch-action-keyboard.html +++ b/third_party/blink/web_tests/external/wpt/pointerevents/pointerevent_touch-action-keyboard.html
@@ -121,6 +121,7 @@ // Inject keyboard scroll inputs. actions_promise = new test_driver.Actions() + .addPointer("mousePointer1", "mouse") .pointerMove(0, 0, {origin: target0}) .pointerDown() .pointerUp()
diff --git a/third_party/blink/web_tests/external/wpt/push-api/idlharness.https.any.serviceworker-expected.txt b/third_party/blink/web_tests/external/wpt/push-api/idlharness.https.any.serviceworker-expected.txt deleted file mode 100644 index 572742c..0000000 --- a/third_party/blink/web_tests/external/wpt/push-api/idlharness.https.any.serviceworker-expected.txt +++ /dev/null
@@ -1,84 +0,0 @@ -This is a testharness.js-based test. -Found 80 tests; 78 PASS, 2 FAIL, 0 TIMEOUT, 0 NOTRUN. -PASS idl_test setup -PASS Partial interface ServiceWorkerRegistration: original interface defined -PASS Partial interface ServiceWorkerGlobalScope: original interface defined -PASS Partial interface ServiceWorkerGlobalScope: valid exposure set -PASS PushManager interface: existence and properties of interface object -PASS PushManager interface object length -PASS PushManager interface object name -PASS PushManager interface: existence and properties of interface prototype object -PASS PushManager interface: existence and properties of interface prototype object's "constructor" property -PASS PushManager interface: existence and properties of interface prototype object's @@unscopables property -PASS PushManager interface: attribute supportedContentEncodings -PASS PushManager interface: operation subscribe(PushSubscriptionOptionsInit) -PASS PushManager interface: operation getSubscription() -PASS PushManager interface: operation permissionState(PushSubscriptionOptionsInit) -PASS PushManager must be primary interface of registration.pushManager -PASS Stringification of registration.pushManager -PASS PushManager interface: registration.pushManager must inherit property "supportedContentEncodings" with the proper type -PASS PushManager interface: registration.pushManager must inherit property "subscribe(PushSubscriptionOptionsInit)" with the proper type -PASS PushManager interface: calling subscribe(PushSubscriptionOptionsInit) on registration.pushManager with too few arguments must throw TypeError -PASS PushManager interface: registration.pushManager must inherit property "getSubscription()" with the proper type -PASS PushManager interface: registration.pushManager must inherit property "permissionState(PushSubscriptionOptionsInit)" with the proper type -PASS PushManager interface: calling permissionState(PushSubscriptionOptionsInit) on registration.pushManager with too few arguments must throw TypeError -PASS PushSubscriptionOptions interface: existence and properties of interface object -PASS PushSubscriptionOptions interface object length -PASS PushSubscriptionOptions interface object name -PASS PushSubscriptionOptions interface: existence and properties of interface prototype object -PASS PushSubscriptionOptions interface: existence and properties of interface prototype object's "constructor" property -PASS PushSubscriptionOptions interface: existence and properties of interface prototype object's @@unscopables property -PASS PushSubscriptionOptions interface: attribute userVisibleOnly -PASS PushSubscriptionOptions interface: attribute applicationServerKey -PASS PushSubscription interface: existence and properties of interface object -PASS PushSubscription interface object length -PASS PushSubscription interface object name -PASS PushSubscription interface: existence and properties of interface prototype object -PASS PushSubscription interface: existence and properties of interface prototype object's "constructor" property -PASS PushSubscription interface: existence and properties of interface prototype object's @@unscopables property -PASS PushSubscription interface: attribute endpoint -PASS PushSubscription interface: attribute expirationTime -PASS PushSubscription interface: attribute options -PASS PushSubscription interface: operation getKey(PushEncryptionKeyName) -PASS PushSubscription interface: operation unsubscribe() -PASS PushSubscription interface: operation toJSON() -PASS PushMessageData interface: existence and properties of interface object -PASS PushMessageData interface object length -PASS PushMessageData interface object name -PASS PushMessageData interface: existence and properties of interface prototype object -PASS PushMessageData interface: existence and properties of interface prototype object's "constructor" property -PASS PushMessageData interface: existence and properties of interface prototype object's @@unscopables property -PASS PushMessageData interface: operation arrayBuffer() -PASS PushMessageData interface: operation blob() -PASS PushMessageData interface: operation json() -PASS PushMessageData interface: operation text() -PASS PushEvent interface: existence and properties of interface object -PASS PushEvent interface object length -PASS PushEvent interface object name -PASS PushEvent interface: existence and properties of interface prototype object -PASS PushEvent interface: existence and properties of interface prototype object's "constructor" property -PASS PushEvent interface: existence and properties of interface prototype object's @@unscopables property -PASS PushEvent interface: attribute data -PASS PushEvent must be primary interface of new PushEvent("type") -PASS Stringification of new PushEvent("type") -PASS PushEvent interface: new PushEvent("type") must inherit property "data" with the proper type -PASS PushSubscriptionChangeEvent interface: existence and properties of interface object -PASS PushSubscriptionChangeEvent interface object length -PASS PushSubscriptionChangeEvent interface object name -PASS PushSubscriptionChangeEvent interface: existence and properties of interface prototype object -PASS PushSubscriptionChangeEvent interface: existence and properties of interface prototype object's "constructor" property -PASS PushSubscriptionChangeEvent interface: existence and properties of interface prototype object's @@unscopables property -PASS PushSubscriptionChangeEvent interface: attribute newSubscription -PASS PushSubscriptionChangeEvent interface: attribute oldSubscription -PASS PushSubscriptionChangeEvent must be primary interface of new PushSubscriptionChangeEvent("pushsubscriptionchange") -PASS Stringification of new PushSubscriptionChangeEvent("pushsubscriptionchange") -PASS PushSubscriptionChangeEvent interface: new PushSubscriptionChangeEvent("pushsubscriptionchange") must inherit property "newSubscription" with the proper type -PASS PushSubscriptionChangeEvent interface: new PushSubscriptionChangeEvent("pushsubscriptionchange") must inherit property "oldSubscription" with the proper type -PASS ServiceWorkerRegistration interface: attribute pushManager -PASS ServiceWorkerRegistration interface: registration must inherit property "pushManager" with the proper type -PASS ServiceWorkerGlobalScope interface: attribute onpush -FAIL ServiceWorkerGlobalScope interface: attribute onpushsubscriptionchange assert_own_property: The global object must have a property "onpushsubscriptionchange" expected property "onpushsubscriptionchange" missing -PASS ServiceWorkerGlobalScope interface: self must inherit property "onpush" with the proper type -FAIL ServiceWorkerGlobalScope interface: self must inherit property "onpushsubscriptionchange" with the proper type assert_own_property: expected property "onpushsubscriptionchange" missing -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/external/wpt/speech-api/historical-expected.txt b/third_party/blink/web_tests/external/wpt/speech-api/historical-expected.txt index 8dd3037..07d8219 100644 --- a/third_party/blink/web_tests/external/wpt/speech-api/historical-expected.txt +++ b/third_party/blink/web_tests/external/wpt/speech-api/historical-expected.txt
@@ -6,5 +6,7 @@ FAIL webkitSpeechRecognitionError interface should not exist assert_false: expected false got true FAIL webkitSpeechRecognitionEvent interface should not exist assert_false: expected false got true PASS SpeechRecognition's serviceURI attribute should not exist +PASS SpeechRecognitionEvent's interpretation attribute should not exist +PASS SpeechRecognitionEvent's emma attribute should not exist Harness: the test ran to completion.
diff --git a/third_party/blink/web_tests/external/wpt/speech-api/historical.html b/third_party/blink/web_tests/external/wpt/speech-api/historical.html index 6dd4bd9..207d3e0 100644 --- a/third_party/blink/web_tests/external/wpt/speech-api/historical.html +++ b/third_party/blink/web_tests/external/wpt/speech-api/historical.html
@@ -14,7 +14,7 @@ ].forEach(name => { test(() => { assert_false(name in window); - }, name + " interface should not exist"); + }, `${name} interface should not exist`); }); test(() => { @@ -25,4 +25,18 @@ } assert_false("serviceURI" in SpeechRecognition.prototype); }, "SpeechRecognition's serviceURI attribute should not exist"); + +[ + "interpretation", + "emma", +].forEach(name => { + test(() => { + if (!window.SpeechRecognitionEvent) { + // TODO(foolip): use `t.skip()` after + // https://github.com/web-platform-tests/rfcs/pull/16 is done. + return; + } + assert_false(name in SpeechRecognitionEvent.prototype); + }, `SpeechRecognitionEvent's ${name} attribute should not exist`); +}); </script>
diff --git a/third_party/blink/web_tests/external/wpt/wake-lock/idlharness.https.any.worker-expected.txt b/third_party/blink/web_tests/external/wpt/wake-lock/idlharness.https.any.worker-expected.txt deleted file mode 100644 index 481f78d..0000000 --- a/third_party/blink/web_tests/external/wpt/wake-lock/idlharness.https.any.worker-expected.txt +++ /dev/null
@@ -1,12 +0,0 @@ -This is a testharness.js-based test. -PASS idl_test setup -FAIL WakeLock interface: existence and properties of interface object assert_own_property: self does not have own property "WakeLock" expected property "WakeLock" missing -FAIL WakeLock interface object length assert_own_property: self does not have own property "WakeLock" expected property "WakeLock" missing -FAIL WakeLock interface object name assert_own_property: self does not have own property "WakeLock" expected property "WakeLock" missing -FAIL WakeLock interface: existence and properties of interface prototype object assert_own_property: self does not have own property "WakeLock" expected property "WakeLock" missing -FAIL WakeLock interface: existence and properties of interface prototype object's "constructor" property assert_own_property: self does not have own property "WakeLock" expected property "WakeLock" missing -FAIL WakeLock interface: existence and properties of interface prototype object's @@unscopables property assert_own_property: self does not have own property "WakeLock" expected property "WakeLock" missing -FAIL WakeLock interface: member requestPermission Cannot use 'in' operator to search for 'requestPermission' in undefined -FAIL WakeLock interface: operation request(WakeLockType, WakeLockRequestOptions) assert_own_property: self does not have own property "WakeLock" expected property "WakeLock" missing -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-abortsignal.https.any.worker-expected.txt b/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-abortsignal.https.any.worker-expected.txt deleted file mode 100644 index c75b587..0000000 --- a/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-abortsignal.https.any.worker-expected.txt +++ /dev/null
@@ -1,6 +0,0 @@ -This is a testharness.js-based test. -FAIL 'TypeError' is thrown when the signal option is not an AbortSignal promise_test: Unhandled rejection with value: object "ReferenceError: WakeLock is not defined" -FAIL A WakeLock request with an AbortSignal whose abort flag is set always aborts WakeLock is not defined -FAIL The same AbortSignal can be used to cause multiple wake locks to abort promise_test: Unhandled rejection with value: object "ReferenceError: WakeLock is not defined" -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-screen-type-on-worker.https.worker-expected.txt b/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-screen-type-on-worker.https.worker-expected.txt deleted file mode 100644 index 7019eb3..0000000 --- a/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-screen-type-on-worker.https.worker-expected.txt +++ /dev/null
@@ -1,4 +0,0 @@ -This is a testharness.js-based test. -FAIL Screen wake lock should not be allowed in dedicated worker WakeLock is not defined -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-type.https.any.worker-expected.txt b/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-type.https.any.worker-expected.txt deleted file mode 100644 index 9d738db3..0000000 --- a/third_party/blink/web_tests/external/wpt/wake-lock/wakelock-type.https.any.worker-expected.txt +++ /dev/null
@@ -1,5 +0,0 @@ -This is a testharness.js-based test. -FAIL 'TypeError' is thrown when set an empty wake lock type promise_test: Unhandled rejection with value: object "ReferenceError: WakeLock is not defined" -FAIL 'TypeError' is thrown when set an invalid wake lock type WakeLock is not defined -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/external/wpt/webaudio/the-audio-api/the-mediastreamaudiosourcenode-interface/mediastreamaudiosourcenode-routing.html b/third_party/blink/web_tests/external/wpt/webaudio/the-audio-api/the-mediastreamaudiosourcenode-interface/mediastreamaudiosourcenode-routing.html index b61c318..43e5ac8 100644 --- a/third_party/blink/web_tests/external/wpt/webaudio/the-audio-api/the-mediastreamaudiosourcenode-interface/mediastreamaudiosourcenode-routing.html +++ b/third_party/blink/web_tests/external/wpt/webaudio/the-audio-api/the-mediastreamaudiosourcenode-interface/mediastreamaudiosourcenode-routing.html
@@ -88,18 +88,6 @@ ); checkCount++; } - // Don't assert(false) immediately here if the bin is still higher than - // -40db the analyzer node has a window and it's expecte that it takes some - // time for the volume of this bin to decrease. Similarly, -50 may seem - // quite high but is also a product of windowing. - if (frequencyData[indexToCheckForLowEnergy] < -50) { - assert_true(true, "Correct track routed to the AudioContext."); - } else { - assert_true( - false, - "Other track seem to be routed to the AudioContext?" - ); - } if (checkCount > 5 && checkCount < 20) { twoTrackMediaStream.getAudioTracks().forEach(track => { if (track.id == ids[0]) {
diff --git a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_pointerrawmove-manual-automation.js b/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_pointerrawmove-manual-automation.js deleted file mode 100644 index 6b65722..0000000 --- a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_pointerrawmove-manual-automation.js +++ /dev/null
@@ -1,7 +0,0 @@ -importAutomationScript('/pointerevents/pointerevent_common_input.js'); - -function inject_input() { - return mouseMoveIntoTarget('#target0').then(function() { - return mouseChordedButtonPress('#target0'); - }); -}
diff --git a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch-manual-automation.js b/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch-manual-automation.js deleted file mode 100644 index d45280c..0000000 --- a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-down-css_touch-manual-automation.js +++ /dev/null
@@ -1,11 +0,0 @@ -importAutomationScript('/pointerevents/pointerevent_common_input.js'); - -function inject_input() { - return touchScrollInTarget('#target0', 'up').then(function() { - return touchScrollInTarget('#target0', 'right'); - }).then(function() { - return touchScrollInTarget('#target0', 'down'); - }).then(function() { - btnComplete.click(); - }); -}
diff --git a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch-manual-automation.js b/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch-manual-automation.js deleted file mode 100644 index 76a9cba..0000000 --- a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-left-css_touch-manual-automation.js +++ /dev/null
@@ -1,12 +0,0 @@ -importAutomationScript('/pointerevents/pointerevent_common_input.js'); - -function inject_input() { - return touchScrollInTarget('#target0', 'down').then(function() { - return touchScrollInTarget('#target0', 'right'); - }).then(function() { - return touchScrollInTarget('#target0', 'left'); - }).then(function() { - return touchTapInTarget('#btnComplete'); - }); -} -
diff --git a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch-manual-automation.js b/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch-manual-automation.js deleted file mode 100644 index 4d220a4..0000000 --- a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-right-css_touch-manual-automation.js +++ /dev/null
@@ -1,12 +0,0 @@ -importAutomationScript('/pointerevents/pointerevent_common_input.js'); - -function inject_input() { - return touchScrollInTarget('#target0', 'down').then(function() { - return touchScrollInTarget('#target0', 'left'); - }).then(function() { - return touchScrollInTarget('#target0', 'right'); - }).then(function() { - return touchTapInTarget('#btnComplete'); - }); -} -
diff --git a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch-manual-automation.js b/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch-manual-automation.js deleted file mode 100644 index c3687c6d..0000000 --- a/third_party/blink/web_tests/external/wpt_automation/pointerevents/extension/pointerevent_touch-action-pan-up-css_touch-manual-automation.js +++ /dev/null
@@ -1,11 +0,0 @@ -importAutomationScript('/pointerevents/pointerevent_common_input.js'); - -function inject_input() { - return touchScrollInTarget('#target0', 'down').then(function() { - return touchScrollInTarget('#target0', 'right'); - }).then(function() { - return touchScrollInTarget('#target0', 'up'); - }).then(function() { - btnComplete.click(); - }); -}
diff --git a/third_party/blink/web_tests/fast/alignment/parse-place-content.html b/third_party/blink/web_tests/fast/alignment/parse-place-content.html index dda9f800..af3f0dd 100644 --- a/third_party/blink/web_tests/fast/alignment/parse-place-content.html +++ b/third_party/blink/web_tests/fast/alignment/parse-place-content.html
@@ -101,7 +101,10 @@ element = document.createElement("div"); document.body.appendChild(element); element.style.placeContent = value; - checkValues(element, "placeContent", "place-content", value, alignValue + ' ' + justifyValue) + if (alignValue == justifyValue) + checkValues(element, "placeContent", "place-content", value, alignValue); + else + checkValues(element, "placeContent", "place-content", value, alignValue + ' ' + justifyValue); checkPlaceContentValues(element, value, alignValue, justifyValue) } @@ -116,11 +119,11 @@ { element = document.createElement("div"); document.body.appendChild(element); - checkValues(element, "placeContent", "place-content", "", "normal normal"); + checkValues(element, "placeContent", "place-content", "", "normal"); element.style.placeContent = "center"; checkPlaceContentValues(element, "center", "center", "center"); element.style.placeContent = "initial"; - checkValues(element, "placeContent", "place-content", "initial", "normal normal"); + checkValues(element, "placeContent", "place-content", "initial", "normal"); checkPlaceContentValues(element, "initial", "normal", "normal"); } @@ -136,32 +139,32 @@ test(function() { - checkValues(placeContentNormal, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentNormal, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentNormal, "", "normal", "normal"); }, "Test getting the Computed Value of place-content's longhand properties when setting 'normal' value through CSS."); test(function() { - checkValues(placeContentStart, "placeContent", "place-content", "", "start start"); + checkValues(placeContentStart, "placeContent", "place-content", "", "start"); checkPlaceContentValues(placeContentStart, "", "start", "start"); }, "Test getting the Computed Value of place-content's longhand properties when setting 'start' value through CSS."); test(function() { - checkValues(placeContentFlexStart, "placeContent", "place-content", "", "flex-start flex-start"); + checkValues(placeContentFlexStart, "placeContent", "place-content", "", "flex-start"); checkPlaceContentValues(placeContentFlexStart, "", "flex-start", "flex-start"); }, "Test getting the Computed Value of place-content's longhand properties when setting 'flex-start' value through CSS."); test(function() { - checkValues(placeContentEnd, "placeContent", "place-content", "", "end end"); + checkValues(placeContentEnd, "placeContent", "place-content", "", "end"); checkPlaceContentValues(placeContentEnd, "", "end", "end"); }, "Test getting the Computed Value of place-content's longhand properties when setting 'end' value through CSS."); test(function() { - checkValues(placeContentSpaceBetween, "placeContent", "place-content", "", "space-between space-between"); + checkValues(placeContentSpaceBetween, "placeContent", "place-content", "", "space-between"); checkPlaceContentValues(placeContentSpaceBetween, "", "space-between", "space-between"); }, "Test getting the Computed Value of place-content's longhand properties when setting 'space-between' value through CSS."); test(function() { - checkValues(placeContentStretch, "placeContent", "place-content", "", "stretch stretch"); + checkValues(placeContentStretch, "placeContent", "place-content", "", "stretch"); checkPlaceContentValues(placeContentStretch, "", "stretch", "stretch"); }, "Test getting the Computed Value of place-content's longhand properties when setting 'stretch' value through CSS."); @@ -181,27 +184,27 @@ }, "Test getting the Computed Value of place-content's longhand properties when setting 'baseline start' value through CSS."); test(function() { - checkValues(placeContentAuto, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentAuto, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentAuto, "", "normal", "normal"); }, "Test setting '' as incorrect value through CSS."); test(function() { - checkValues(placeContentAuto, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentAuto, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentAuto, "", "normal", "normal"); }, "Test setting 'auto' as incorrect value through CSS."); test(function() { - checkValues(placeContentNone, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentNone, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentNone, "", "normal", "normal"); }, "Test setting 'none' as incorrect value through CSS."); test(function() { - checkValues(placeContentSafe, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentSafe, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentSafe, "", "normal", "normal"); }, "Test setting 'safe' as incorrect value through CSS."); test(function() { - checkValues(placeContentStartSafe, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentStartSafe, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentStartSafe, "", "normal", "normal"); }, "Test setting 'start safe' as incorrect value through CSS."); @@ -211,17 +214,17 @@ }, "Test setting 'baseline' as 'baseline start'."); test(function() { - checkValues(placeContentBaselineSafe, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentBaselineSafe, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentBaselineSafe, "", "normal", "normal"); }, "Test setting 'baseline safe' as incorrect value through CSS."); test(function() { - checkValues(placeContentStartBaseline, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentStartBaseline, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentStartBaseline, "", "normal", "normal"); }, "Test setting 'start baseline' as incorrect value through CSS."); test(function() { - checkValues(placeContentStartEndLeft, "placeContent", "place-content", "", "normal normal"); + checkValues(placeContentStartEndLeft, "placeContent", "place-content", "", "normal"); checkPlaceContentValues(placeContentStartEndLeft, "", "normal", "normal"); }, "Test setting 'start end left' as incorrect value through CSS.");
diff --git a/third_party/blink/web_tests/fast/alignment/parse-place-items.html b/third_party/blink/web_tests/fast/alignment/parse-place-items.html index 33967a7..8e25eb48 100644 --- a/third_party/blink/web_tests/fast/alignment/parse-place-items.html +++ b/third_party/blink/web_tests/fast/alignment/parse-place-items.html
@@ -108,7 +108,10 @@ element = document.createElement("div"); document.body.appendChild(element); element.style.placeItems = value; - checkValues(element, "placeItems", "place-items", value, alignValue + ' ' + justifyValue) + if (alignValue == justifyValue) + checkValues(element, "placeItems", "place-items", value, alignValue); + else + checkValues(element, "placeItems", "place-items", value, alignValue + ' ' + justifyValue); checkPlaceItemsValues(element, value, alignValue, justifyValue) } @@ -120,47 +123,47 @@ } test(function() { - checkValues(placeItemsNormal, "placeItems", "place-items", "", "normal normal"); + checkValues(placeItemsNormal, "placeItems", "place-items", "", "normal"); checkPlaceItemsValues(placeItemsNormal, "", "normal", "normal"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'normal' value through CSS."); test(function() { - checkValues(placeItemsBaseline, "placeItems", "place-items", "", "baseline baseline"); + checkValues(placeItemsBaseline, "placeItems", "place-items", "", "baseline"); checkPlaceItemsValues(placeItemsBaseline, "", "baseline", "baseline"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'baseline' value through CSS."); test(function() { - checkValues(placeItemsFirstBaseline, "placeItems", "place-items", "", "baseline baseline"); + checkValues(placeItemsFirstBaseline, "placeItems", "place-items", "", "baseline"); checkPlaceItemsValues(placeItemsFirstBaseline, "", "baseline", "baseline"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'first baseline' value through CSS."); test(function() { - checkValues(placeItemsLastBaseline, "placeItems", "place-items", "", "last baseline last baseline"); + checkValues(placeItemsLastBaseline, "placeItems", "place-items", "", "last baseline"); checkPlaceItemsValues(placeItemsLastBaseline, "", "last baseline", "last baseline"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'last baseline' value through CSS."); test(function() { - checkValues(placeItemsStart, "placeItems", "place-items", "", "start start"); + checkValues(placeItemsStart, "placeItems", "place-items", "", "start"); checkPlaceItemsValues(placeItemsStart, "", "start", "start"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'start' value through CSS."); test(function() { - checkValues(placeItemsFlexStart, "placeItems", "place-items", "", "flex-start flex-start"); + checkValues(placeItemsFlexStart, "placeItems", "place-items", "", "flex-start"); checkPlaceItemsValues(placeItemsFlexStart, "", "flex-start", "flex-start"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'flex-start' value through CSS."); test(function() { - checkValues(placeItemsEnd, "placeItems", "place-items", "", "end end"); + checkValues(placeItemsEnd, "placeItems", "place-items", "", "end"); checkPlaceItemsValues(placeItemsEnd, "", "end", "end"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'end' value through CSS."); test(function() { - checkValues(placeItemsSelfStart, "placeItems", "place-items", "", "self-start self-start"); + checkValues(placeItemsSelfStart, "placeItems", "place-items", "", "self-start"); checkPlaceItemsValues(placeItemsSelfStart, "", "self-start", "self-start"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'self-start' value through CSS."); test(function() { - checkValues(placeItemsStretch, "placeItems", "place-items", "", "stretch stretch"); + checkValues(placeItemsStretch, "placeItems", "place-items", "", "stretch"); checkPlaceItemsValues(placeItemsStretch, "", "stretch", "stretch"); }, "Test getting the Computed Value of place-items's longhand properties when setting 'stretch' value through CSS."); @@ -180,37 +183,37 @@ }, "Test getting the Computed Value of place-items's longhand properties when setting 'start baseline' value through CSS."); test(function() { - checkValues(placeItemsAuto, "placeItems", "place-items", "", "normal normal"); + checkValues(placeItemsAuto, "placeItems", "place-items", "", "normal"); checkPlaceItemsValues(placeItemsAuto, "", "normal", "normal"); }, "Test setting 'auto' as incorrect value through CSS."); test(function() { - checkValues(placeItemsCenterAuto, "placeItems", "place-items", "", "normal normal"); + checkValues(placeItemsCenterAuto, "placeItems", "place-items", "", "normal"); checkPlaceItemsValues(placeItemsCenterAuto, "", "normal", "normal"); }, "Test setting 'center auto' as incorrect value through CSS."); test(function() { - checkValues(placeItemsNone, "placeItems", "place-items", "", "normal normal"); + checkValues(placeItemsNone, "placeItems", "place-items", "", "normal"); checkPlaceItemsValues(placeItemsNone, "", "normal", "normal"); }, "Test setting 'none' as incorrect value through CSS."); test(function() { - checkValues(placeItemsSafe, "placeItems", "place-items", "", "normal normal"); + checkValues(placeItemsSafe, "placeItems", "place-items", "", "normal"); checkPlaceItemsValues(placeItemsSafe, "", "normal", "normal"); }, "Test setting 'safe' as incorrect value through CSS."); test(function() { - checkValues(placeItemsStartSafe, "placeItems", "place-items", "", "normal normal"); + checkValues(placeItemsStartSafe, "placeItems", "place-items", "", "normal"); checkPlaceItemsValues(placeItemsStartSafe, "", "normal", "normal"); }, "Test setting 'start safe' as incorrect value through CSS."); test(function() { - checkValues(placeItemsBaselineSafe, "placeItems", "place-items", "", "normal normal"); + checkValues(placeItemsBaselineSafe, "placeItems", "place-items", "", "normal"); checkPlaceItemsValues(placeItemsBaselineSafe, "", "normal", "normal"); }, "Test setting 'baseline safe' as incorrect value through CSS."); test(function() { - checkValues(placeItemsStartEndLeft, "placeItems", "place-items", "", "normal normal"); + checkValues(placeItemsStartEndLeft, "placeItems", "place-items", "", "normal"); checkPlaceItemsValues(placeItemsStartEndLeft, "", "normal", "normal"); }, "Test setting 'start end left' as incorrect value through CSS."); @@ -241,11 +244,11 @@ test(function() { element = document.createElement("div"); document.body.appendChild(element); - checkValues(element, "placeItems", "place-items", "", "normal normal"); + checkValues(element, "placeItems", "place-items", "", "normal"); element.style.placeItems = "center"; checkPlaceItemsValues(element, "center", "center", "center"); element.style.placeItems = "initial"; - checkValues(element, "placeItems", "place-items", "initial", "normal normal"); + checkValues(element, "placeItems", "place-items", "initial", "normal"); checkPlaceItemsValues(element, "initial", "normal", "normal"); }, "Test the 'initial' value of the place-items shorthand and its longhand properties' Computed value");
diff --git a/third_party/blink/web_tests/fast/alignment/parse-place-self.html b/third_party/blink/web_tests/fast/alignment/parse-place-self.html index 4967bdc..0e7dcfb1 100644 --- a/third_party/blink/web_tests/fast/alignment/parse-place-self.html +++ b/third_party/blink/web_tests/fast/alignment/parse-place-self.html
@@ -108,8 +108,11 @@ element = document.createElement("div"); document.body.appendChild(element); element.style.placeSelf = value; - checkValues(element, "placeSelf", "place-self", value, alignValue + ' ' + justifyValue) - checkPlaceSelfValues(element, value, alignValue, justifyValue) + if (alignValue == justifyValue) + checkValues(element, "placeSelf", "place-self", value, alignValue); + else + checkValues(element, "placeSelf", "place-self", value, alignValue + ' ' + justifyValue); + checkPlaceSelfValues(element, value, alignValue, justifyValue); } function checkPlaceSelfValuesBadJS(value) @@ -120,7 +123,7 @@ } test(function() { - checkValues(placeSelfNormal, "placeSelf", "place-self", "", "normal normal"); + checkValues(placeSelfNormal, "placeSelf", "place-self", "", "normal"); checkPlaceSelfValues(placeSelfNormal, "", "normal", "normal"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'normal' value through CSS."); @@ -130,42 +133,42 @@ }, "Test getting the Computed Value of place-self's longhand properties when setting 'center auto' value through CSS."); test(function() { - checkValues(placeSelfBaseline, "placeSelf", "place-self", "", "baseline baseline"); + checkValues(placeSelfBaseline, "placeSelf", "place-self", "", "baseline"); checkPlaceSelfValues(placeSelfBaseline, "", "baseline", "baseline"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'baseline' value through CSS."); test(function() { - checkValues(placeSelfFirstBaseline, "placeSelf", "place-self", "", "baseline baseline"); + checkValues(placeSelfFirstBaseline, "placeSelf", "place-self", "", "baseline"); checkPlaceSelfValues(placeSelfFirstBaseline, "", "baseline", "baseline"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'first baseline' value through CSS."); test(function() { - checkValues(placeSelfLastBaseline, "placeSelf", "place-self", "", "last baseline last baseline"); + checkValues(placeSelfLastBaseline, "placeSelf", "place-self", "", "last baseline"); checkPlaceSelfValues(placeSelfLastBaseline, "", "last baseline", "last baseline"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'last baseline' value through CSS."); test(function() { - checkValues(placeSelfStart, "placeSelf", "place-self", "", "start start"); + checkValues(placeSelfStart, "placeSelf", "place-self", "", "start"); checkPlaceSelfValues(placeSelfStart, "", "start", "start"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'start' value through CSS."); test(function() { - checkValues(placeSelfFlexStart, "placeSelf", "place-self", "", "flex-start flex-start"); + checkValues(placeSelfFlexStart, "placeSelf", "place-self", "", "flex-start"); checkPlaceSelfValues(placeSelfFlexStart, "", "flex-start", "flex-start"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'flex-start' value through CSS."); test(function() { - checkValues(placeSelfEnd, "placeSelf", "place-self", "", "end end"); + checkValues(placeSelfEnd, "placeSelf", "place-self", "", "end"); checkPlaceSelfValues(placeSelfEnd, "", "end", "end"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'end' value through CSS."); test(function() { - checkValues(placeSelfSelfStart, "placeSelf", "place-self", "", "self-start self-start"); + checkValues(placeSelfSelfStart, "placeSelf", "place-self", "", "self-start"); checkPlaceSelfValues(placeSelfSelfStart, "", "self-start", "self-start"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'self-start' value through CSS."); test(function() { - checkValues(placeSelfStretch, "placeSelf", "place-self", "", "stretch stretch"); + checkValues(placeSelfStretch, "placeSelf", "place-self", "", "stretch"); checkPlaceSelfValues(placeSelfStretch, "", "stretch", "stretch"); }, "Test getting the Computed Value of place-self's longhand properties when setting 'stretch' value through CSS."); @@ -185,37 +188,37 @@ }, "Test getting the Computed Value of place-self's longhand properties when setting 'start baseline' value through CSS."); test(function() { - checkValues(placeSelfEmpty, "placeSelf", "place-self", "", "auto auto"); + checkValues(placeSelfEmpty, "placeSelf", "place-self", "", "auto"); checkPlaceSelfValues(placeSelfEmpty, "", "auto", "auto"); }, "Test setting '' as incorrect value through CSS."); test(function() { - checkValues(placeSelfAuto, "placeSelf", "place-self", "", "auto auto"); + checkValues(placeSelfAuto, "placeSelf", "place-self", "", "auto"); checkPlaceSelfValues(placeSelfAuto, "", "auto", "auto"); }, "Test setting 'auto' as incorrect value through CSS."); test(function() { - checkValues(placeSelfNone, "placeSelf", "place-self", "", "auto auto"); + checkValues(placeSelfNone, "placeSelf", "place-self", "", "auto"); checkPlaceSelfValues(placeSelfNone, "", "auto", "auto"); }, "Test setting 'none' as incorrect value through CSS."); test(function() { - checkValues(placeSelfSafe, "placeSelf", "place-self", "", "auto auto"); + checkValues(placeSelfSafe, "placeSelf", "place-self", "", "auto"); checkPlaceSelfValues(placeSelfSafe, "", "auto", "auto"); }, "Test setting 'safe' as incorrect value through CSS."); test(function() { - checkValues(placeSelfStartSafe, "placeSelf", "place-self", "", "auto auto"); + checkValues(placeSelfStartSafe, "placeSelf", "place-self", "", "auto"); checkPlaceSelfValues(placeSelfStartSafe, "", "auto", "auto"); }, "Test setting 'start safe' as incorrect value through CSS."); test(function() { - checkValues(placeSelfBaselineSafe, "placeSelf", "place-self", "", "auto auto"); + checkValues(placeSelfBaselineSafe, "placeSelf", "place-self", "", "auto"); checkPlaceSelfValues(placeSelfBaselineSafe, "", "auto", "auto"); }, "Test setting 'baseline safe' as incorrect value through CSS."); test(function() { - checkValues(placeSelfStartEndLeft, "placeSelf", "place-self", "", "auto auto"); + checkValues(placeSelfStartEndLeft, "placeSelf", "place-self", "", "auto"); checkPlaceSelfValues(placeSelfStartEndLeft, "", "auto", "auto"); }, "Test setting 'start end left' as incorrect value through CSS."); @@ -241,11 +244,11 @@ test(function() { element = document.createElement("div"); document.body.appendChild(element); - checkValues(element, "placeSelf", "place-self", "", "auto auto"); + checkValues(element, "placeSelf", "place-self", "", "auto"); element.style.placeSelf = "center"; checkPlaceSelfValues(element, "center", "center", "center"); element.style.placeSelf = "initial"; - checkValues(element, "placeSelf", "place-self", "initial", "auto auto"); + checkValues(element, "placeSelf", "place-self", "initial", "auto"); checkPlaceSelfValues(element, "initial", "auto", "auto"); }, "Test the 'initial' value of the place-self shorthand and its longhand properties' Computed value");
diff --git a/third_party/blink/web_tests/http/tests/serviceworker/webexposed/global-interface-listing-service-worker-expected.txt b/third_party/blink/web_tests/http/tests/serviceworker/webexposed/global-interface-listing-service-worker-expected.txt index 4dbc026..6e0be3f 100644 --- a/third_party/blink/web_tests/http/tests/serviceworker/webexposed/global-interface-listing-service-worker-expected.txt +++ b/third_party/blink/web_tests/http/tests/serviceworker/webexposed/global-interface-listing-service-worker-expected.txt
@@ -3686,6 +3686,7 @@ getter onpaymentrequest getter onperiodicsync getter onpush + getter onpushsubscriptionchange getter onsync getter registration method fetch @@ -3708,6 +3709,7 @@ setter onpaymentrequest setter onperiodicsync setter onpush + setter onpushsubscriptionchange setter onsync PASS Verify the interface of ServiceWorkerGlobalScope PASS successfullyParsed is true
diff --git a/third_party/blink/web_tests/webexposed/global-interface-listing-dedicated-worker-expected.txt b/third_party/blink/web_tests/webexposed/global-interface-listing-dedicated-worker-expected.txt index b6c8fc2..1a3665a 100644 --- a/third_party/blink/web_tests/webexposed/global-interface-listing-dedicated-worker-expected.txt +++ b/third_party/blink/web_tests/webexposed/global-interface-listing-dedicated-worker-expected.txt
@@ -1445,6 +1445,10 @@ [Worker] getter hasBeenActive [Worker] getter isActive [Worker] method constructor +[Worker] interface WakeLock +[Worker] static method request +[Worker] attribute @@toStringTag +[Worker] method constructor [Worker] interface WebGL2ComputeRenderingContext [Worker] attribute @@toStringTag [Worker] attribute ACTIVE_ATOMIC_COUNTER_BUFFERS
diff --git a/third_party/libvpx/README.chromium b/third_party/libvpx/README.chromium index 4114164..4088419 100644 --- a/third_party/libvpx/README.chromium +++ b/third_party/libvpx/README.chromium
@@ -5,9 +5,9 @@ License File: source/libvpx/LICENSE Security Critical: yes -Date: Monday July 01 2019 +Date: Monday July 15 2019 Branch: master -Commit: cd9f1763c861edfd86d2814e029a34f3ce821e72 +Commit: bb407a27b2e32f89f0e9eeee2bcd0aa9d5cfea3f Description: Contains the sources used to compile libvpx binaries used by Google Chrome and
diff --git a/third_party/libvpx/source/config/vpx_version.h b/third_party/libvpx/source/config/vpx_version.h index f6b1609..225da6e 100644 --- a/third_party/libvpx/source/config/vpx_version.h +++ b/third_party/libvpx/source/config/vpx_version.h
@@ -2,7 +2,7 @@ #define VERSION_MAJOR 1 #define VERSION_MINOR 8 #define VERSION_PATCH 0 -#define VERSION_EXTRA "589-gcd9f1763c8" +#define VERSION_EXTRA "601-gbb407a27b2" #define VERSION_PACKED ((VERSION_MAJOR<<16)|(VERSION_MINOR<<8)|(VERSION_PATCH)) -#define VERSION_STRING_NOSP "v1.8.0-589-gcd9f1763c8" -#define VERSION_STRING " v1.8.0-589-gcd9f1763c8" +#define VERSION_STRING_NOSP "v1.8.0-601-gbb407a27b2" +#define VERSION_STRING " v1.8.0-601-gbb407a27b2"
diff --git a/tools/metrics/histograms/enums.xml b/tools/metrics/histograms/enums.xml index 4704cdc..fbf6488 100644 --- a/tools/metrics/histograms/enums.xml +++ b/tools/metrics/histograms/enums.xml
@@ -52940,6 +52940,25 @@ <int value="8" label="ALREADY_EXISTS"> The shared memory region already exists. </int> + <int value="9" label="ALLOCATE_FILE_REGION_FAILURE"> + Failure to allocate disk space for the file. + </int> + <int value="10" label="FSTAT_FAILURE"> + Failure to fstat the file descriptor. + </int> + <int value="11" label="INODES_MISMATCH"> + Writable and read-only inodes don't match. + </int> + <int value="12" label="GET_SHMEM_TEMP_DIR_FAILURE"> + Failure to get a temporary directory for shared memory. + </int> +</enum> + +<enum name="SharingMessageType"> + <int value="0" label="Unknown"/> + <int value="1" label="Ping"/> + <int value="2" label="Ack"/> + <int value="3" label="ClickToCall"/> </enum> <enum name="ShelfAlignmentValue">
diff --git a/tools/metrics/histograms/histograms.xml b/tools/metrics/histograms/histograms.xml index 5cc81e8..cdd8fc4 100644 --- a/tools/metrics/histograms/histograms.xml +++ b/tools/metrics/histograms/histograms.xml
@@ -23913,7 +23913,7 @@ </histogram> <histogram name="Cryptohome.ChecksumStatus" enum="CryptohomeChecksumStatus" - expires_after="M77"> + expires_after="2021-01-01"> <owner>apronin@chromium.org</owner> <owner>cros-hwsec@chromium.org</owner> <summary> @@ -24257,7 +24257,7 @@ </histogram> <histogram name="Cryptohome.TimeToMountGuestAsync" units="ms" - expires_after="M77"> + expires_after="2021-01-01"> <owner>apronin@chromium.org</owner> <owner>cros-hwsec@chromium.org</owner> <summary> @@ -37070,6 +37070,9 @@ <histogram name="Event.MainThreadEventQueue.FlushQueueNoBeginMainFrame" enum="BooleanHit" expires_after="M77"> + <obsolete> + Expired 2019-07. + </obsolete> <owner>dtapuska@chromium.org</owner> <summary> Whether the Begin Main Frame was not received and the queue generated a @@ -37096,6 +37099,9 @@ <histogram name="Event.PassiveForcedEventDispatchCancelled" enum="PassiveForcedListenerResultType" expires_after="M77"> + <obsolete> + Expired 2019-07. + </obsolete> <owner>dtapuska@chromium.org</owner> <summary> Counts the number of event listener invocations that were forced to be @@ -37132,6 +37138,9 @@ <histogram name="Event.PassiveListeners.ForcedNonBlockingLatencyDueToFling" units="microseconds" expires_after="M77"> + <obsolete> + Expired 2019-07. + </obsolete> <owner>dtapuska@chromium.org</owner> <summary> Time between when a touchstart or first touchmove event per scroll was @@ -119196,7 +119205,7 @@ </histogram> <histogram name="Security.ClientAuth.CertificateSelectionSource" - enum="ClientCertSelectionResult" expires_after="2019-07-30"> + enum="ClientCertSelectionResult" expires_after="2019-10-30"> <owner>jdeblasio@chromium.org</owner> <summary> When TLS client authentication is requested by the server, Chrome must @@ -121481,6 +121490,17 @@ </summary> </histogram> +<histogram name="ServiceWorkerCache.Cache.Browser.Match.Initialized" units="ms" + expires_after="2020-07-15"> + <owner>wanderview@chromium.org</owner> + <owner>chrome-owp-storage@google.com</owner> + <summary> + The time to perform a 'match' operation on a given Cache when that cache is + known to be fully initialized. This includes measurements for hits, misses, + and errors. + </summary> +</histogram> + <histogram name="ServiceWorkerCache.CacheStorage" units="ms"> <owner>dmurph@chromium.org</owner> <summary> @@ -123570,6 +123590,37 @@ </summary> </histogram> +<histogram name="Sharing.ClickToCallAppsToShow" units="apps" + expires_after="2020-02-02"> + <owner>mvanouwerkerk@chromium.org</owner> + <owner>peter@chromium.org</owner> + <summary> + The number of available apps that are about to be shown in a UI for picking + an app to start a phone call with. Desktop only. + </summary> +</histogram> + +<histogram name="Sharing.ClickToCallDevicesToShow" units="devices" + expires_after="2020-02-02"> + <owner>mvanouwerkerk@chromium.org</owner> + <owner>peter@chromium.org</owner> + <summary> + The number of available devices that are about to be shown in a UI for + picking a device to start a phone call on. Desktop only. + </summary> +</histogram> + +<histogram name="Sharing.MessageReceivedType" enum="SharingMessageType" + expires_after="2020-02-02"> + <owner>mvanouwerkerk@chromium.org</owner> + <owner>peter@chromium.org</owner> + <summary> + The type of SharingMessage (aka the PayloadCase). This is logged when a + message is received through FCM by the handler in the Sharing service. All + platforms. + </summary> +</histogram> + <histogram name="ShortcutsProvider.DatabaseSize" expires_after="2018-08-30"> <owner>mpearson@chromium.org</owner> <summary> @@ -148874,7 +148925,7 @@ </histogram> <histogram name="WebRTC.AudioInputSampleRate" enum="AudioSampleRate" - expires_after="M78"> + expires_after="2020-07-17"> <owner>henrika@chromium.org</owner> <summary>Audio input sample rate for WebRTC (in Hz).</summary> </histogram>
diff --git a/tools/perf/core/minidump_unittest.py b/tools/perf/core/minidump_unittest.py index 58fbb53..f6e5e9f 100644 --- a/tools/perf/core/minidump_unittest.py +++ b/tools/perf/core/minidump_unittest.py
@@ -16,7 +16,7 @@ # ChromeOS and Android are currently hard coded to return None for minidump # paths, so disable on those platforms. Windows 7 doesn't find any minidump # paths for some reason. - @decorators.Disabled('chromeos', 'android', 'win7') + @decorators.Disabled('chromeos', 'android', 'win7', 'linux') def testSymbolizeMinidump(self): # Wait for the browser to restart fully before crashing self._LoadPageThenWait('var sam = "car";', 'sam') @@ -90,7 +90,7 @@ @decorators.Isolated # Disabled on Mac 10.12 (Sierra) due to it not getting a stack trace to # symbolize from the second crash. - @decorators.Disabled('chromeos', 'android', 'win7', 'sierra') + @decorators.Disabled('chromeos', 'android', 'win7', 'sierra', 'linux') def testMultipleCrashMinidumps(self): # Wait for the browser to restart fully before crashing self._LoadPageThenWait('var cat = "dog";', 'cat')
diff --git a/tools/traffic_annotation/summary/annotations.xml b/tools/traffic_annotation/summary/annotations.xml index 011c29d4..88ba4233 100644 --- a/tools/traffic_annotation/summary/annotations.xml +++ b/tools/traffic_annotation/summary/annotations.xml
@@ -99,7 +99,6 @@ <item id="external_policy_fetcher" hash_code="9459438" type="0" content_hash_code="64260484" os_list="linux,windows" file_path="components/policy/core/common/cloud/external_policy_data_fetcher.cc"/> <item id="family_info" hash_code="30913825" type="0" content_hash_code="25369370" os_list="linux,windows" file_path="chrome/browser/supervised_user/child_accounts/family_info_fetcher.cc"/> <item id="favicon_loader" hash_code="112189210" type="0" content_hash_code="70773116" os_list="linux,windows" file_path="content/renderer/loader/web_url_loader_impl.cc"/> - <item id="history_ui_favicon_request_handler_get_favicon" hash_code="17562717" type="0" content_hash_code="64054629" os_list="linux,windows" file_path="components/favicon/core/history_ui_favicon_request_handler_impl.cc"/> <item id="feed_image_fetcher" hash_code="87439531" type="0" deprecated="2019-01-04" content_hash_code="26756208" file_path=""/> <item id="gaia_auth_check_connection_info" hash_code="4598626" type="0" content_hash_code="57347000" os_list="linux,windows" file_path="google_apis/gaia/gaia_auth_fetcher.cc"/> <item id="gaia_auth_exchange_cookies" hash_code="134289752" type="0" deprecated="2018-09-11" content_hash_code="66433230" file_path=""/> @@ -130,6 +129,7 @@ <item id="hintsfetcher_gethintsrequest" hash_code="34557599" type="0" content_hash_code="57003380" os_list="linux,windows" file_path="components/optimization_guide/hints_fetcher.cc"/> <item id="history_notice_utils_notice" hash_code="102595701" type="1" second_id="110307337" content_hash_code="130829410" os_list="linux,windows" semantics_fields="2,3,4" policy_fields="4" file_path="components/browsing_data/core/history_notice_utils.cc"/> <item id="history_notice_utils_popup" hash_code="80832574" type="1" second_id="110307337" content_hash_code="30618510" os_list="linux,windows" semantics_fields="2,3,4" policy_fields="4" file_path="components/browsing_data/core/history_notice_utils.cc"/> + <item id="history_ui_favicon_request_handler_get_favicon" hash_code="17562717" type="0" content_hash_code="64054629" os_list="linux,windows" file_path="components/favicon/core/history_ui_favicon_request_handler_impl.cc"/> <item id="http_server_error_response" hash_code="32197336" type="0" content_hash_code="61082230" os_list="linux,windows" file_path="net/server/http_server.cc"/> <item id="https_server_previews_navigation" hash_code="35725390" type="0" content_hash_code="84423109" os_list="linux,windows" file_path="chrome/browser/previews/previews_lite_page_serving_url_loader.cc"/> <item id="icon_cacher" hash_code="103133150" type="0" content_hash_code="116368348" os_list="linux,windows" file_path="components/ntp_tiles/icon_cacher_impl.cc"/> @@ -139,6 +139,7 @@ <item id="interest_feed_send" hash_code="76717919" type="0" content_hash_code="34678180" os_list="linux,windows" file_path="components/feed/core/feed_networking_host.cc"/> <item id="intranet_redirect_detector" hash_code="21785164" type="0" content_hash_code="62025595" os_list="linux,windows" file_path="chrome/browser/intranet_redirect_detector.cc"/> <item id="invalidation_service" hash_code="72354423" type="0" content_hash_code="78425687" os_list="linux,windows" file_path="components/invalidation/impl/gcm_network_channel.cc"/> + <item id="kids_chrome_management_client_classify_url" hash_code="109987793" type="0" content_hash_code="112740597" os_list="linux,windows" file_path="chrome/browser/supervised_user/kids_chrome_management/kids_chrome_management_client.cc"/> <item id="kids_management_url_checker" hash_code="57474321" type="0" content_hash_code="109271547" os_list="linux,windows" file_path="chrome/browser/supervised_user/kids_management_url_checker_client.cc"/> <item id="lib_address_input" hash_code="50816767" type="0" content_hash_code="57977576" os_list="linux,windows" file_path="third_party/libaddressinput/chromium/chrome_metadata_source.cc"/> <item id="logo_service" hash_code="35473769" type="0" content_hash_code="20271299" os_list="linux,windows" file_path="components/search_provider_logos/logo_service_impl.cc"/> @@ -283,6 +284,7 @@ <item id="web_history_expire_between_dates" hash_code="126122632" type="1" second_id="110307337" content_hash_code="34304787" os_list="linux,windows" semantics_fields="2,3,4" policy_fields="4" file_path="components/history/core/browser/history_service.cc"/> <item id="web_history_query" hash_code="17400350" type="1" second_id="110307337" content_hash_code="36075147" os_list="linux,windows" semantics_fields="2,3,4" policy_fields="4" file_path="components/history/core/browser/browsing_history_service.cc"/> <item id="web_history_service" hash_code="110307337" type="2" content_hash_code="16140045" os_list="linux,windows" semantics_fields="1,5" policy_fields="-1,3" file_path="components/history/core/browser/web_history_service.cc"/> + <item id="web_push_message" hash_code="39886742" type="0" content_hash_code="110064650" os_list="linux,windows" file_path="components/gcm_driver/web_push_sender.cc"/> <item id="webrtc_event_log_uploader" hash_code="24186190" type="0" content_hash_code="11005245" os_list="linux,windows" file_path="chrome/browser/media/webrtc/webrtc_event_log_uploader.cc"/> <item id="webrtc_log_upload" hash_code="62443804" type="0" content_hash_code="33661169" os_list="linux,windows" file_path="chrome/browser/media/webrtc/webrtc_log_uploader.cc"/> <item id="webrtc_peer_connection" hash_code="63497370" type="0" content_hash_code="60553259" os_list="linux,windows" file_path="content/renderer/media/webrtc/peer_connection_dependency_factory.cc"/> @@ -293,5 +295,5 @@ <item id="webstore_installer" hash_code="18764319" type="0" content_hash_code="11030110" os_list="linux,windows" file_path="chrome/browser/extensions/webstore_installer.cc"/> <item id="webui_content_scripts_download" hash_code="100545943" type="0" content_hash_code="119898059" os_list="linux,windows" file_path="extensions/browser/guest_view/web_view/web_ui/web_ui_url_fetcher.cc"/> <item id="worker_script_load" hash_code="72087791" type="0" content_hash_code="24889169" os_list="linux,windows" file_path="content/browser/worker_host/worker_script_fetcher.cc"/> - <item id="web_push_message" hash_code="39886742" type="0" content_hash_code="110064650" os_list="linux,windows" file_path="components/gcm_driver/web_push_sender.cc"/> + <item id="xmpp_signal_strategy" hash_code="88906454" type="0" deprecated="2019-07-16" content_hash_code="88958321" file_path=""/> </annotations>
diff --git a/ui/accessibility/ax_node.h b/ui/accessibility/ax_node.h index 73932d9..3ec9c57a 100644 --- a/ui/accessibility/ax_node.h +++ b/ui/accessibility/ax_node.h
@@ -253,7 +253,8 @@ base::string16 GetInheritedString16Attribute( ax::mojom::StringAttribute attribute) const; - // Return a pointer to a string for the language code. + // Return a string representing the language code. + // // This will consider the language declared in the DOM, and may eventually // attempt to automatically detect the language from the text. //
diff --git a/ui/accessibility/platform/ax_platform_node_auralinux.cc b/ui/accessibility/platform/ax_platform_node_auralinux.cc index f9a211e..77a49d7 100644 --- a/ui/accessibility/platform/ax_platform_node_auralinux.cc +++ b/ui/accessibility/platform/ax_platform_node_auralinux.cc
@@ -25,6 +25,7 @@ #include "base/strings/utf_string_conversion_utils.h" #include "base/strings/utf_string_conversions.h" #include "build/build_config.h" +#include "third_party/skia/include/core/SkColor.h" #include "ui/accessibility/ax_action_data.h" #include "ui/accessibility/ax_mode_observer.h" #include "ui/accessibility/ax_node_data.h" @@ -156,6 +157,15 @@ return nullptr; } +// The ATK API often requires pointers to be used as out arguments, while +// allowing for those pointers to be null if the caller is not interested in +// the value. This function is a simpler helper to avoid continually checking +// for null and to help prevent forgetting to check for null. +void SetIntPointerValueIfNotNull(int* pointer, int value) { + if (pointer) + *pointer = value; +} + bool SupportsAtkComponentScrollingInterface() { return dlsym(RTLD_DEFAULT, "atk_component_scroll_to_point"); } @@ -347,6 +357,74 @@ offsets.first != offsets.second; } +void AddTextAttributeToSet(const AtkTextAttribute attribute, + const std::string& value, + AtkAttributeSet** attributes) { + AtkAttribute* new_attribute = + static_cast<AtkAttribute*>(g_malloc(sizeof(AtkAttribute))); + new_attribute->name = g_strdup(atk_text_attribute_get_name(attribute)); + new_attribute->value = g_strdup(value.c_str()); + *attributes = g_slist_prepend(*attributes, new_attribute); +} + +bool HasInvalidAttributeInSet(AtkAttributeSet* attributes) { + const char* underline_attribute = + atk_text_attribute_get_name(ATK_TEXT_ATTR_UNDERLINE); + DCHECK(underline_attribute); + + AtkAttributeSet* current = attributes; + while (current) { + const AtkAttribute* attribute = static_cast<AtkAttribute*>(current->data); + if (!g_strcmp0(attribute->name, underline_attribute) && + !g_strcmp0(attribute->value, "error")) { + return true; + } + current = g_slist_next(current); + } + return false; +} + +bool AttributeSetsEqual(AtkAttributeSet* one, AtkAttributeSet* two) { + AtkAttributeSet* current_one = one; + AtkAttributeSet* current_two = two; + + while (current_one && current_two) { + const AtkAttribute* attribute_one = + static_cast<AtkAttribute*>(current_one->data); + const AtkAttribute* attribute_two = + static_cast<AtkAttribute*>(current_two->data); + + if (g_strcmp0(attribute_one->name, attribute_two->name) || + g_strcmp0(attribute_one->value, attribute_two->value)) { + return false; + } + + current_one = g_slist_next(current_one); + current_two = g_slist_next(current_two); + } + + // The sets are only equal if they have the same length, which means that we + // need to have iterated to the end of both sets. + return !current_one && !current_two; +} + +AtkAttributeSet* CopyAttributeSet(AtkAttributeSet* attributes) { + AtkAttributeSet* copied_attributes = nullptr; + while (attributes) { + const AtkAttribute* attribute = + static_cast<const AtkAttribute*>(attributes->data); + AtkAttribute* new_attribute = + static_cast<AtkAttribute*>(g_malloc(sizeof(AtkAttribute))); + new_attribute->name = g_strdup(attribute->name); + new_attribute->value = g_strdup(attribute->value); + copied_attributes = g_slist_prepend(copied_attributes, new_attribute); + + attributes = g_slist_next(attributes); + } + + return g_slist_reverse(copied_attributes); +} + namespace atk_component { void GetExtents(AtkComponent* atk_component, @@ -811,24 +889,6 @@ return obj->UTF16ToUnicodeOffsetInText(obj->GetHypertext().length()); } -AtkAttributeSet* GetRunAttributes(AtkText* atk_text, - gint offset, - gint* start_offset, - gint* end_offset) { - *start_offset = -1; - *end_offset = -1; - - AtkObject* atk_object = ATK_OBJECT(atk_text); - AXPlatformNodeAuraLinux* obj = AtkObjectToAXPlatformNodeAuraLinux(atk_object); - if (!obj) - return nullptr; - - *start_offset = 0; - *end_offset = GetCharacterCount(atk_text); - - return nullptr; -} - gunichar GetCharacterAtOffset(AtkText* atk_text, int offset) { AtkObject* atk_object = ATK_OBJECT(atk_text); AXPlatformNodeAuraLinux* obj = AtkObjectToAXPlatformNodeAuraLinux(atk_object); @@ -1165,9 +1225,35 @@ out_rectangle->height = rect.height(); } +AtkAttributeSet* GetRunAttributes(AtkText* atk_text, + gint offset, + gint* start_offset, + gint* end_offset) { + SetIntPointerValueIfNotNull(start_offset, -1); + SetIntPointerValueIfNotNull(end_offset, -1); + + if (offset < 0 || offset > GetCharacterCount(atk_text)) + return nullptr; + + AtkObject* atk_object = ATK_OBJECT(atk_text); + AXPlatformNodeAuraLinux* obj = AtkObjectToAXPlatformNodeAuraLinux(atk_object); + if (!obj) + return nullptr; + + return CopyAttributeSet( + obj->GetTextAttributes(offset, start_offset, end_offset)); +} + +AtkAttributeSet* GetDefaultAttributes(AtkText* atk_text) { + AtkObject* atk_object = ATK_OBJECT(atk_text); + AXPlatformNodeAuraLinux* obj = AtkObjectToAXPlatformNodeAuraLinux(atk_object); + if (!obj) + return nullptr; + return CopyAttributeSet(obj->GetDefaultTextAttributes()); +} + void Init(AtkTextIface* iface) { iface->get_text = GetText; - iface->get_run_attributes = GetRunAttributes; iface->get_character_count = GetCharacterCount; iface->get_character_at_offset = GetCharacterAtOffset; iface->get_text_after_offset = GetTextAfterOffset; @@ -1183,6 +1269,9 @@ iface->remove_selection = RemoveSelection; iface->set_selection = SetSelection; + iface->get_run_attributes = GetRunAttributes; + iface->get_default_attributes = GetDefaultAttributes; + #if defined(ATK_210) iface->get_string_at_offset = GetStringAtOffset; #endif @@ -2253,6 +2342,9 @@ return ATK_ROLE_IMAGE; case ax::mojom::Role::kImageMap: return ATK_ROLE_IMAGE_MAP; + case ax::mojom::Role::kInlineTextBox: + // TODO(jdiggs) This should be ATK_ROLE_STATIC. https://crbug.com/984590 + return ATK_ROLE_TEXT; case ax::mojom::Role::kInputTime: return ATK_ROLE_DATE_EDITOR; case ax::mojom::Role::kLabelText: @@ -2271,6 +2363,7 @@ case ax::mojom::Role::kLineBreak: // TODO(Accessibility) Having a separate accessible object for line breaks // is inconsistent with other implementations. http://crbug.com/873144#c1. + // TODO(jdiggs) This should be ATK_ROLE_STATIC. https://crbug.com/984590 return ATK_ROLE_TEXT; case ax::mojom::Role::kLink: return ATK_ROLE_LINK; @@ -2385,6 +2478,7 @@ default: break; } + // TODO(jdiggs) This should be ATK_ROLE_STATIC. https://crbug.com/984590 return ATK_ROLE_TEXT; } case ax::mojom::Role::kStatus: @@ -2410,7 +2504,6 @@ return ATK_ROLE_DESCRIPTION_TERM; case ax::mojom::Role::kTitleBar: return ATK_ROLE_TITLE_BAR; - case ax::mojom::Role::kInlineTextBox: case ax::mojom::Role::kTextField: case ax::mojom::Role::kSearchBox: if (GetData().HasState(ax::mojom::State::kProtected)) @@ -3813,4 +3906,286 @@ #endif // defined(ATK_230) +AtkAttributes AXPlatformNodeAuraLinux::ComputeTextAttributes() const { + AtkAttributeSet* attributes = nullptr; + + int color; + if (GetIntAttribute(ax::mojom::IntAttribute::kBackgroundColor, &color)) { + unsigned int red = SkColorGetR(color); + unsigned int green = SkColorGetG(color); + unsigned int blue = SkColorGetB(color); + std::string color_value = base::NumberToString(red) + ',' + + base::NumberToString(green) + ',' + + base::NumberToString(blue); + AddTextAttributeToSet(ATK_TEXT_ATTR_BG_COLOR, color_value, &attributes); + } + + if (GetIntAttribute(ax::mojom::IntAttribute::kColor, &color)) { + unsigned int red = SkColorGetR(color); + unsigned int green = SkColorGetG(color); + unsigned int blue = SkColorGetB(color); + std::string color_value = base::NumberToString(red) + ',' + + base::NumberToString(green) + ',' + + base::NumberToString(blue); + AddTextAttributeToSet(ATK_TEXT_ATTR_FG_COLOR, color_value, &attributes); + } + + std::string font_family( + GetInheritedStringAttribute(ax::mojom::StringAttribute::kFontFamily)); + // Attribute has no default value. + if (!font_family.empty()) { + AddTextAttributeToSet(ATK_TEXT_ATTR_FAMILY_NAME, font_family, &attributes); + } + + float font_size; + // Attribute has no default value. + if (GetFloatAttribute(ax::mojom::FloatAttribute::kFontSize, &font_size)) { + // The ATK Spec requires the value to be in pt, not in pixels. + // There are 72 points per inch. + // We assume that there are 96 pixels per inch on a standard display. + // TODO(nektar): Figure out the current value of pixels per inch. + float points = font_size * 72.0 / 96.0; + AddTextAttributeToSet(ATK_TEXT_ATTR_SIZE, + base::NumberToString(points) + "pt", &attributes); + } + + // TODO(nektar): Add Blink support for the following attributes: + // text-line-through-mode, text-line-through-width, text-outline:false, + // text-position:baseline, text-shadow:none, text-underline-mode:continuous. + + int32_t text_style = GetIntAttribute(ax::mojom::IntAttribute::kTextStyle); + if (text_style) { + if (GetData().HasTextStyle(ax::mojom::TextStyle::kBold)) { + // TODO(mrobinson): This is based on the weight that CSS uses for "bold," + // but we'd like to support more font weights here. + AddTextAttributeToSet(ATK_TEXT_ATTR_WEIGHT, "700", &attributes); + } + + if (GetData().HasTextStyle(ax::mojom::TextStyle::kItalic)) { + // TODO(mrobinson): We'd also like to support "oblique" here. + AddTextAttributeToSet(ATK_TEXT_ATTR_STYLE, "italic", &attributes); + } + + if (GetData().HasTextStyle(ax::mojom::TextStyle::kLineThrough)) + AddTextAttributeToSet(ATK_TEXT_ATTR_STRIKETHROUGH, "true", &attributes); + + if (GetData().HasTextStyle(ax::mojom::TextStyle::kUnderline)) { + // TODO(mrobinson): Figure out a more specific value. + AddTextAttributeToSet(ATK_TEXT_ATTR_UNDERLINE, "single", &attributes); + } + } + + // Screen readers look at the text attributes to determine if something is + // misspelled, so we need to propagate any spelling attributes from immediate + // parents of text-only objects. AXPlatformNodeBase::GetInvalidValue takes + // care of searching upward to find the appropriate values. + std::string invalid_value = GetInvalidValue(); + if (!invalid_value.empty()) + AddTextAttributeToSet(ATK_TEXT_ATTR_UNDERLINE, "error", &attributes); + + std::string language = GetDelegate()->GetLanguage(); + if (!language.empty()) + AddTextAttributeToSet(ATK_TEXT_ATTR_LANGUAGE, language, &attributes); + + auto text_direction = static_cast<ax::mojom::TextDirection>( + GetIntAttribute(ax::mojom::IntAttribute::kTextDirection)); + switch (text_direction) { + case ax::mojom::TextDirection::kNone: + break; + case ax::mojom::TextDirection::kLtr: + AddTextAttributeToSet(ATK_TEXT_ATTR_LANGUAGE, "ltr", &attributes); + break; + case ax::mojom::TextDirection::kRtl: + AddTextAttributeToSet(ATK_TEXT_ATTR_LANGUAGE, "rtl", &attributes); + break; + case ax::mojom::TextDirection::kTtb: + // Not listed in the ATK docs. + AddTextAttributeToSet(ATK_TEXT_ATTR_LANGUAGE, "ttb", &attributes); + break; + case ax::mojom::TextDirection::kBtt: + // Not listed in the ATK docs. + AddTextAttributeToSet(ATK_TEXT_ATTR_LANGUAGE, "btt", &attributes); + break; + } + + return AtkAttributes(attributes); +} + +void AXPlatformNodeAuraLinux::ComputeStylesIfNeeded() { + if (!offset_to_text_attributes_.empty()) + return; + + default_text_attributes_ = ComputeTextAttributes(); + std::map<int, AtkAttributes> attributes_map; + if (IsLeaf()) { + attributes_map[0] = + AtkAttributes(CopyAttributeSet(default_text_attributes_.get())); + MergeSpellingIntoAtkTextAttributesAtOffset(0 /* start_offset */, + &attributes_map); + offset_to_text_attributes_.swap(attributes_map); + return; + } + + int start_offset = 0; + for (auto child_iterator_ptr = GetDelegate()->ChildrenBegin(); + *child_iterator_ptr != *GetDelegate()->ChildrenEnd(); + ++(*child_iterator_ptr)) { + auto* child = AtkObjectToAXPlatformNodeAuraLinux( + child_iterator_ptr->GetNativeViewAccessible()); + if (!child) + continue; + + AtkAttributes attributes = child->ComputeTextAttributes(); + if (attributes_map.empty()) { + attributes_map[start_offset] = std::move(attributes); + } else { + // Only add the attributes for this child if we are at the start of a new + // style span. + AtkAttributeSet* previous_attributes = + attributes_map.rbegin()->second.get(); + if (!AttributeSetsEqual(attributes.get(), previous_attributes)) + attributes_map[start_offset] = std::move(attributes); + } + + if (child->IsTextOnlyObject()) { + MergeSpellingIntoAtkTextAttributesAtOffset(start_offset, &attributes_map); + start_offset += child->GetHypertext().length(); + } else { + start_offset += 1; + } + } + + offset_to_text_attributes_.swap(attributes_map); +} + +void AXPlatformNodeAuraLinux::MergeSpellingIntoAtkTextAttributesAtOffset( + int offset, + std::map<int, AtkAttributes>* text_attributes) { + DCHECK(text_attributes); + + int hypertext_length = static_cast<int>(GetHypertext().length()); + std::map<int, AtkAttributeSet*> spelling_attributes; + if (IsTextOnlyObject()) { + const std::vector<int32_t>& marker_types = + GetIntListAttribute(ax::mojom::IntListAttribute::kMarkerTypes); + const std::vector<int>& marker_starts = + GetIntListAttribute(ax::mojom::IntListAttribute::kMarkerStarts); + const std::vector<int>& marker_ends = + GetIntListAttribute(ax::mojom::IntListAttribute::kMarkerEnds); + for (size_t i = 0; i < marker_types.size(); ++i) { + bool isSpellingError = + (marker_types[i] & + static_cast<int32_t>(ax::mojom::MarkerType::kSpelling)) != 0; + bool isGrammarError = + (marker_types[i] & + static_cast<int32_t>(ax::mojom::MarkerType::kGrammar)) != 0; + if (!isSpellingError && !isGrammarError) + continue; + + // Add a starting attribute for the error, if one does not already exist. + // We use a default value of an AtkAttributes (unique_ptr of + // AtkAttributeSet*) set to a nullptr. Since AtkAttributeSet is a GSList, + // a nullptr is an empty set. + int marker_start_offset = offset + marker_starts[i]; + auto default_value = std::make_pair(marker_start_offset, nullptr); + auto iterator = text_attributes->insert(default_value).first; + + if (!HasInvalidAttributeInSet(iterator->second.get())) { + // `attributes` is a unique_ptr, but here we want to modify the head of + // the list without having the unique_ptr delete it. We leak the + // pointer to `attribute_set` and then reset the new list value into + // the iterator. + AtkAttributeSet* attribute_set = iterator->second.release(); + AddTextAttributeToSet(ATK_TEXT_ATTR_UNDERLINE, "error", &attribute_set); + if (isSpellingError) { + AddTextAttributeToSet(ATK_TEXT_ATTR_INVALID, "spelling", + &attribute_set); + } + if (isGrammarError) { + AddTextAttributeToSet(ATK_TEXT_ATTR_INVALID, "grammar", + &attribute_set); + } + iterator->second.reset(attribute_set); + } + + // Make sure there is at least an empty attribute set to end the marker. + int marker_end_offset = offset + marker_ends[i]; + DCHECK_LE(marker_end_offset, hypertext_length); + text_attributes->insert(std::make_pair(marker_end_offset, nullptr)); + } + } + + if (IsPlainTextField()) { + AXPlatformNodeDelegate* delegate = GetDelegate(); + DCHECK(delegate); + + int anchor_start_offset = offset; + AXNodeRange range(delegate->CreateTextPositionAt(0), + delegate->CreateTextPositionAt(hypertext_length)); + for (const auto& leaf_text_range : range) { + DCHECK(!leaf_text_range.IsNull()); + DCHECK_EQ(leaf_text_range.anchor()->GetAnchor(), + leaf_text_range.focus()->GetAnchor()) + << "An leaf text range should only span a single object."; + auto* node = static_cast<AXPlatformNodeAuraLinux*>( + delegate->GetFromNodeID(leaf_text_range.anchor()->GetAnchor()->id())); + node->MergeSpellingIntoAtkTextAttributesAtOffset(anchor_start_offset, + text_attributes); + anchor_start_offset += leaf_text_range.GetText().length(); + } + } +} + +int AXPlatformNodeAuraLinux::FindStartOfStyle( + int start_offset, + ui::TextBoundaryDirection direction) { + int text_length = GetHypertext().length(); + DCHECK_GE(start_offset, 0); + DCHECK_LE(start_offset, text_length); + DCHECK(!offset_to_text_attributes_.empty()); + + switch (direction) { + case ui::BACKWARDS_DIRECTION: { + auto iterator = offset_to_text_attributes_.upper_bound(start_offset); + --iterator; + return iterator->first; + } + case ui::FORWARDS_DIRECTION: { + const auto iterator = + offset_to_text_attributes_.upper_bound(start_offset); + if (iterator == offset_to_text_attributes_.end()) + return text_length; + return iterator->first; + } + } + + NOTREACHED(); + return start_offset; +} + +AtkAttributeSet* AXPlatformNodeAuraLinux::GetTextAttributes(int offset, + int* start_offset, + int* end_offset) { + ComputeStylesIfNeeded(); + DCHECK(!offset_to_text_attributes_.empty()); + + int utf16_offset = UnicodeToUTF16OffsetInText(offset); + int style_start = FindStartOfStyle(utf16_offset, ui::BACKWARDS_DIRECTION); + int style_end = FindStartOfStyle(utf16_offset, ui::FORWARDS_DIRECTION); + + auto iterator = offset_to_text_attributes_.find(style_start); + DCHECK(iterator != offset_to_text_attributes_.end()); + + SetIntPointerValueIfNotNull(start_offset, + UTF16ToUnicodeOffsetInText(style_start)); + SetIntPointerValueIfNotNull(end_offset, + UTF16ToUnicodeOffsetInText(style_end)); + return iterator->second.get(); +} + +AtkAttributeSet* AXPlatformNodeAuraLinux::GetDefaultTextAttributes() { + ComputeStylesIfNeeded(); + return default_text_attributes_.get(); +} + } // namespace ui
diff --git a/ui/accessibility/platform/ax_platform_node_auralinux.h b/ui/accessibility/platform/ax_platform_node_auralinux.h index 49b9408..55ad15d 100644 --- a/ui/accessibility/platform/ax_platform_node_auralinux.h +++ b/ui/accessibility/platform/ax_platform_node_auralinux.h
@@ -7,6 +7,8 @@ #include <atk/atk.h> +#include <map> +#include <memory> #include <string> #include <utility> @@ -15,8 +17,20 @@ #include "base/strings/utf_offset_string_conversions.h" #include "base/strings/utf_string_conversions.h" #include "ui/accessibility/ax_export.h" +#include "ui/accessibility/ax_position.h" +#include "ui/accessibility/ax_range.h" #include "ui/accessibility/platform/ax_platform_node_base.h" +// This deleter is used in order to ensure that we properly always free memory +// used by AtkAttributeSet. +struct AtkAttributeSetDeleter { + void operator()(AtkAttributeSet* attributes) { + atk_attribute_set_free(attributes); + } +}; + +using AtkAttributes = std::unique_ptr<AtkAttributeSet, AtkAttributeSetDeleter>; + // Some ATK interfaces require returning a (const gchar*), use // this macro to make it safe to return a pointer to a temporary // string. @@ -168,6 +182,21 @@ void GetSelectionExtents(int* start_offset, int* end_offset); gchar* GetSelectionWithText(int* start_offset, int* end_offset); + // Return the text attributes for this node given an offset. The start + // and end attributes will be assigned to the start_offset and end_offset + // pointers if they are non-null. The return value AtkAttributeSet should + // be freed with atk_attribute_set_free. + AtkAttributeSet* GetTextAttributes(int offset, + int* start_offset, + int* end_offset); + + // Return the default text attributes for this node. The default text + // attributes are the ones that apply to the entire node. Attributes found at + // a given offset can be thought of as overriding the default attribute. + // The return value AtkAttributeSet should be freed with + // atk_attribute_set_free. + AtkAttributeSet* GetDefaultTextAttributes(); + std::string accessible_name_; protected: @@ -183,6 +212,10 @@ PlatformAttributeList* attributes) override; private: + using AXPositionInstance = AXNodePosition::AXPositionInstance; + using AXPositionInstanceType = typename AXPositionInstance::element_type; + using AXNodeRange = AXRange<AXPositionInstanceType>; + enum AtkInterfaces { ATK_ACTION_INTERFACE, ATK_COMPONENT_INTERFACE, @@ -209,6 +242,13 @@ bool IsInLiveRegion(); base::Optional<std::pair<int, int>> GetEmbeddedObjectIndicesForId(int id); + void ComputeStylesIfNeeded(); + void MergeSpellingIntoAtkTextAttributesAtOffset( + int offset, + std::map<int, AtkAttributes>* text_attributes); + AtkAttributes ComputeTextAttributes() const; + int FindStartOfStyle(int start_offset, ui::TextBoundaryDirection direction); + // The AtkStateType for a checkable node can vary depending on the role. AtkStateType GetAtkStateTypeForCheckableNode(); @@ -233,6 +273,13 @@ // and text-caret-moved events. std::pair<int, int> text_selection_ = std::make_pair(-1, -1); + // A map which converts between an offset in the node's hypertext and the + // ATK text attributes at that offset. + std::map<int, AtkAttributes> offset_to_text_attributes_; + + // The default ATK text attributes for this node. + AtkAttributes default_text_attributes_; + DISALLOW_COPY_AND_ASSIGN(AXPlatformNodeAuraLinux); };
diff --git a/ui/accessibility/platform/ax_platform_node_base.cc b/ui/accessibility/platform/ax_platform_node_base.cc index 3695d9e..d7850c96 100644 --- a/ui/accessibility/platform/ax_platform_node_base.cc +++ b/ui/accessibility/platform/ax_platform_node_base.cc
@@ -1330,20 +1330,43 @@ AXPlatformNodeBase* endpoint_object, int endpoint_offset) { // There are three cases: - // 1. Either the selection endpoint is inside this object or is an ancestor - // of of this object. endpoint_offset should be returned. - // 2. The selection endpoint is a pure descendant of this object. The offset - // of the character corresponding to the subtree in which the endpoint is - // located should be returned. + // 1. The selection endpoint is inside this object but not one of its + // descendants, or is in an ancestor of this object. endpoint_offset should be + // returned, possibly adjusted from a child offset to a hypertext offset. + // 2. The selection endpoint is a descendant of this object. The offset of the + // character in this object's hypertext corresponding to the subtree in which + // the endpoint is located should be returned. // 3. The selection endpoint is in a completely different part of the tree. - // Either 0 or text_length should be returned depending on the direction + // Either 0 or hypertext length should be returned depending on the direction // that one needs to travel to find the endpoint. + // + // TODO(nektar): Replace all this logic with the use of AXNodePosition. - // Case 1. + // Case 1. Is the endpoint object equal to this object or an ancestor of this + // object? // // IsDescendantOf includes the case when endpoint_object == this. - if (IsDescendantOf(endpoint_object)) - return endpoint_offset; + if (IsDescendantOf(endpoint_object)) { + if (endpoint_object->IsLeaf()) { + DCHECK_EQ(endpoint_object, this) << "Text objects cannot have children."; + return endpoint_offset; + } else { + DCHECK_GE(endpoint_offset, 0); + DCHECK_LE(endpoint_offset, + endpoint_object->GetDelegate()->GetChildCount()); + + // Adjust the |endpoint_offset| because the selection endpoint is a tree + // position, i.e. it represents a child index and not a text offset. + if (endpoint_offset == endpoint_object->GetDelegate()->GetChildCount()) { + return static_cast<int>(endpoint_object->GetHypertext().size()); + } else { + auto* child = static_cast<AXPlatformNodeBase*>(FromNativeViewAccessible( + endpoint_object->GetDelegate()->ChildAtIndex(endpoint_offset))); + DCHECK(child); + return endpoint_object->GetHypertextOffsetFromChild(child); + } + } + } AXPlatformNodeBase* common_parent = this; int32_t index_in_common_parent = GetDelegate()->GetIndexInParent(); @@ -1358,24 +1381,28 @@ DCHECK_GE(index_in_common_parent, 0); DCHECK(!(common_parent->IsTextOnlyObject())); - // Case 2. + // Case 2. Is the selection endpoint inside a descendant of this object? // - // We already checked in case 1 if our endpoint is inside this object. - // We can safely assume that it is a descendant or in a completely different - // part of the tree. + // We already checked in case 1 if our endpoint object is equal to this + // object. We can safely assume that it is a descendant or in a completely + // different part of the tree. if (common_parent == this) { int32_t hypertext_offset = GetHypertextOffsetFromDescendant(endpoint_object); auto* parent = static_cast<AXPlatformNodeBase*>( FromNativeViewAccessible(endpoint_object->GetParent())); if (parent == this && endpoint_object->IsTextOnlyObject()) { + // Due to a historical design decision, the hypertext of the immediate + // parents of text objects includes all their text. We therefore need to + // adjust the hypertext offset in the parent by adding any text offset. hypertext_offset += endpoint_offset; } return hypertext_offset; } - // Case 3. + // Case 3. Is the selection endpoint in a completely different part of the + // tree? // // We can safely assume that the endpoint is in another part of the tree or // at common parent, and that this object is a descendant of common parent. @@ -1641,4 +1668,45 @@ } return nearest_index; } + +std::string AXPlatformNodeBase::GetInvalidValue() const { + const AXPlatformNodeBase* target = this; + // The aria-invalid=spelling/grammar need to be exposed as text attributes for + // a range matching the visual underline representing the error. + if (static_cast<ax::mojom::InvalidState>( + target->GetIntAttribute(ax::mojom::IntAttribute::kInvalidState)) == + ax::mojom::InvalidState::kNone && + target->IsTextOnlyObject() && target->GetParent()) { + // Text nodes need to reflect the invalid state of their parent object, + // otherwise spelling and grammar errors communicated through aria-invalid + // won't be reflected in text attributes. + target = static_cast<AXPlatformNodeBase*>( + FromNativeViewAccessible(target->GetParent())); + } + + std::string invalid_value(""); + // Note: spelling+grammar errors case is disallowed and not supported. It + // could possibly arise with aria-invalid on the ancestor of a spelling error, + // but this is not currently described in any spec and no real-world use cases + // have been found. + switch (static_cast<ax::mojom::InvalidState>( + target->GetIntAttribute(ax::mojom::IntAttribute::kInvalidState))) { + case ax::mojom::InvalidState::kNone: + case ax::mojom::InvalidState::kFalse: + break; + case ax::mojom::InvalidState::kTrue: + invalid_value = "true"; + break; + case ax::mojom::InvalidState::kOther: { + if (!target->GetStringAttribute( + ax::mojom::StringAttribute::kAriaInvalidValue, &invalid_value)) { + // Set the attribute to "true", since we cannot be more specific. + invalid_value = "true"; + } + break; + } + } + return invalid_value; +} + } // namespace ui
diff --git a/ui/accessibility/platform/ax_platform_node_base.h b/ui/accessibility/platform/ax_platform_node_base.h index e1701479..a5c208d 100644 --- a/ui/accessibility/platform/ax_platform_node_base.h +++ b/ui/accessibility/platform/ax_platform_node_base.h
@@ -406,6 +406,8 @@ base::Optional<int> GetPosInSet() const; base::Optional<int> GetSetSize() const; + std::string GetInvalidValue() const; + AXHypertext hypertext_; private:
diff --git a/ui/accessibility/platform/ax_platform_node_delegate.h b/ui/accessibility/platform/ax_platform_node_delegate.h index 78175c3..7fd210c 100644 --- a/ui/accessibility/platform/ax_platform_node_delegate.h +++ b/ui/accessibility/platform/ax_platform_node_delegate.h
@@ -10,6 +10,7 @@ #include <memory> #include <new> #include <set> +#include <string> #include <utility> #include <vector> @@ -241,6 +242,17 @@ virtual const std::vector<gfx::NativeViewAccessible> GetDescendants() const = 0; + // Return a string representing the language code. + // + // For web content, this will consider the language declared in the DOM, and + // may eventually attempt to automatically detect the language from the text. + // + // This language code will be BCP 47. + // + // Returns empty string if no appropriate language was found or if this node + // uses the default interface language. + virtual std::string GetLanguage() const = 0; + // // Tables. All of these should be called on a node that's a table-like // role, otherwise they return nullopt.
diff --git a/ui/accessibility/platform/ax_platform_node_delegate_base.cc b/ui/accessibility/platform/ax_platform_node_delegate_base.cc index 796a0a0..501ba85 100644 --- a/ui/accessibility/platform/ax_platform_node_delegate_base.cc +++ b/ui/accessibility/platform/ax_platform_node_delegate_base.cc
@@ -476,4 +476,8 @@ return {}; } +std::string AXPlatformNodeDelegateBase::GetLanguage() const { + return std::string(); +} + } // namespace ui
diff --git a/ui/accessibility/platform/ax_platform_node_delegate_base.h b/ui/accessibility/platform/ax_platform_node_delegate_base.h index 6ac6c11..779cf95 100644 --- a/ui/accessibility/platform/ax_platform_node_delegate_base.h +++ b/ui/accessibility/platform/ax_platform_node_delegate_base.h
@@ -10,6 +10,7 @@ #include <stdint.h> #include <set> +#include <string> #include <vector> #include "base/optional.h" @@ -178,6 +179,8 @@ const std::vector<gfx::NativeViewAccessible> GetDescendants() const override; + std::string GetLanguage() const override; + // // Tables. All of these should be called on a node that's a table-like // role, otherwise they return nullopt.
diff --git a/ui/aura/client/aura_constants.cc b/ui/aura/client/aura_constants.cc index f2024e6..5826c67 100644 --- a/ui/aura/client/aura_constants.cc +++ b/ui/aura/client/aura_constants.cc
@@ -12,6 +12,7 @@ DEFINE_EXPORTED_UI_CLASS_PROPERTY_TYPE(AURA_EXPORT, base::UnguessableToken*) DEFINE_EXPORTED_UI_CLASS_PROPERTY_TYPE(AURA_EXPORT, base::string16*) DEFINE_EXPORTED_UI_CLASS_PROPERTY_TYPE(AURA_EXPORT, ui::ModalType) +DEFINE_EXPORTED_UI_CLASS_PROPERTY_TYPE(AURA_EXPORT, ui::ZOrderLevel) DEFINE_EXPORTED_UI_CLASS_PROPERTY_TYPE(AURA_EXPORT, gfx::ImageSkia*) DEFINE_EXPORTED_UI_CLASS_PROPERTY_TYPE(AURA_EXPORT, gfx::NativeViewAccessible) DEFINE_EXPORTED_UI_CLASS_PROPERTY_TYPE(AURA_EXPORT, gfx::Rect*) @@ -39,7 +40,6 @@ kAccessibilityTouchExplorationPassThrough, false) DEFINE_UI_CLASS_PROPERTY_KEY(bool, kActivateOnPointerKey, true) -DEFINE_UI_CLASS_PROPERTY_KEY(bool, kAlwaysOnTopKey, false) DEFINE_UI_CLASS_PROPERTY_KEY(bool, kAnimationsDisabledKey, false) DEFINE_OWNED_UI_CLASS_PROPERTY_KEY(gfx::ImageSkia, kAppIconKey, nullptr) DEFINE_UI_CLASS_PROPERTY_KEY(int, kAppType, 0) @@ -79,6 +79,9 @@ DEFINE_UI_CLASS_PROPERTY_KEY(int, kTopViewInset, 0) DEFINE_OWNED_UI_CLASS_PROPERTY_KEY(gfx::ImageSkia, kWindowIconKey, nullptr) DEFINE_UI_CLASS_PROPERTY_KEY(int, kWindowCornerRadiusKey, -1) +DEFINE_UI_CLASS_PROPERTY_KEY(ui::ZOrderLevel, + kZOrderingKey, + ui::ZOrderLevel::kNormal) } // namespace client } // namespace aura
diff --git a/ui/aura/client/aura_constants.h b/ui/aura/client/aura_constants.h index f99e4f1..0991ada 100644 --- a/ui/aura/client/aura_constants.h +++ b/ui/aura/client/aura_constants.h
@@ -47,9 +47,6 @@ // pointer down event occurs on them. AURA_EXPORT extern const WindowProperty<bool>* const kActivateOnPointerKey; -// A property key to store always-on-top flag. -AURA_EXPORT extern const WindowProperty<bool>* const kAlwaysOnTopKey; - // A property key to store whether animations are disabled for the window. Type // of value is an int. AURA_EXPORT extern const WindowProperty<bool>* const kAnimationsDisabledKey; @@ -168,6 +165,9 @@ // Default is -1, meaning "unspecified". 0 Ensures corners are square. AURA_EXPORT extern const WindowProperty<int>* const kWindowCornerRadiusKey; +// A property key to store the z-ordering. +AURA_EXPORT extern const WindowProperty<ui::ZOrderLevel>* const kZOrderingKey; + // Alphabetical sort. } // namespace client
diff --git a/ui/base/base_window.h b/ui/base/base_window.h index bbb7e28..17192330 100644 --- a/ui/base/base_window.h +++ b/ui/base/base_window.h
@@ -7,7 +7,7 @@ #include "base/compiler_specific.h" #include "build/build_config.h" -#include "ui/base/ui_base_types.h" // WindowShowState +#include "ui/base/ui_base_types.h" #include "ui/gfx/native_widget_types.h" namespace gfx { @@ -88,12 +88,11 @@ // Set |flash| to true to initiate flashing, false to stop flashing. virtual void FlashFrame(bool flash) = 0; - // Returns true if a window is set to be always on top. - virtual bool IsAlwaysOnTop() const = 0; + // Returns the z-order level of the window. + virtual ZOrderLevel GetZOrderLevel() const = 0; - // If set to true, the window will stay on top of other windows which do not - // have this flag enabled. - virtual void SetAlwaysOnTop(bool always_on_top) = 0; + // Sets the z-order level of the window. + virtual void SetZOrderLevel(ZOrderLevel order) = 0; }; } // namespace ui
diff --git a/ui/base/ui_base_types.h b/ui/base/ui_base_types.h index 5309805f..efd565f 100644 --- a/ui/base/ui_base_types.h +++ b/ui/base/ui_base_types.h
@@ -39,6 +39,38 @@ MODAL_TYPE_SYSTEM = 3 // Window is modal to all other windows. }; +// The class of window and its overall z-order. Not all platforms provide this +// level of z-order granularity. For such platforms, which only provide a +// distinction between "normal" and "always on top" windows, any of the values +// here that aren't |kNormal| are treated equally as "always on top". +enum class ZOrderLevel { + // The default level for windows. + kNormal = 0, + + // A "floating" window z-ordered above other normal windows. + // + // Note this is the traditional _desktop_ concept of a "floating window". + // Android has a concept of "freeform window mode" in which apps are presented + // in separate "floating" windows that can be moved and resized by the user. + // That's not what this is. + kFloatingWindow, + + // UI elements are used to annotate positions on the screen, and thus must + // appear above floating windows. + kFloatingUIElement, + + // There have been horrific security decisions that have been made on the web + // platform that are now expected behavior and cannot easily be changed. The + // only way to mitigate problems with these decisions is to inform the user by + // presenting them with a message that they are in a state that they might not + // expect, and this message must be presented in a UI that cannot be + // interfered with or covered up. Thus this level for Security UI that must be + // Z-ordered in front of everything else. Note that this is useful in + // situations where window modality (as in ModalType) cannot or should not be + // used. + kSecuritySurface, +}; + // TODO(varunjain): Remove MENU_SOURCE_NONE (crbug.com/250964) // A Java counterpart will be generated for this enum. // GENERATED_JAVA_ENUM_PACKAGE: org.chromium.ui.base
diff --git a/ui/gfx/linux/native_pixmap_dmabuf.cc b/ui/gfx/linux/native_pixmap_dmabuf.cc index e9f5bd3..f19a959 100644 --- a/ui/gfx/linux/native_pixmap_dmabuf.cc +++ b/ui/gfx/linux/native_pixmap_dmabuf.cc
@@ -56,6 +56,10 @@ return format_; } +size_t NativePixmapDmaBuf::GetNumberOfPlanes() const { + return handle_.planes.size(); +} + gfx::Size NativePixmapDmaBuf::GetBufferSize() const { return size_; }
diff --git a/ui/gfx/linux/native_pixmap_dmabuf.h b/ui/gfx/linux/native_pixmap_dmabuf.h index dbfb919..ca55c9c 100644 --- a/ui/gfx/linux/native_pixmap_dmabuf.h +++ b/ui/gfx/linux/native_pixmap_dmabuf.h
@@ -35,6 +35,7 @@ size_t GetDmaBufPlaneSize(size_t plane) const override; uint64_t GetBufferFormatModifier() const override; gfx::BufferFormat GetBufferFormat() const override; + size_t GetNumberOfPlanes() const override; gfx::Size GetBufferSize() const override; uint32_t GetUniqueId() const override; bool ScheduleOverlayPlane(gfx::AcceleratedWidget widget,
diff --git a/ui/gfx/mac/nswindow_frame_controls.h b/ui/gfx/mac/nswindow_frame_controls.h index 61c6331..d58eecae 100644 --- a/ui/gfx/mac/nswindow_frame_controls.h +++ b/ui/gfx/mac/nswindow_frame_controls.h
@@ -17,16 +17,6 @@ GFX_EXPORT void SetNSWindowCanFullscreen(NSWindow* window, bool allow_fullscreen); -// Returns whether the window is always-on-top. -GFX_EXPORT bool IsNSWindowAlwaysOnTop(NSWindow* window); - -// Sets whether the window is always-on-top. This also sets -// NSWindowCollectionBehaviorManaged because by default always-on-top windows -// are NSWindowCollectionBehaviorTransient which means they will not appear in -// Expose and cannot be moved between workspaces. -GFX_EXPORT void SetNSWindowAlwaysOnTop(NSWindow* window, - bool always_on_top); - // Sets whether the window appears on all workspaces. GFX_EXPORT void SetNSWindowVisibleOnAllWorkspaces(NSWindow* window, bool always_visible);
diff --git a/ui/gfx/mac/nswindow_frame_controls.mm b/ui/gfx/mac/nswindow_frame_controls.mm index fc63d29d..f06af3e 100644 --- a/ui/gfx/mac/nswindow_frame_controls.mm +++ b/ui/gfx/mac/nswindow_frame_controls.mm
@@ -21,13 +21,6 @@ [window setStyleMask:style_mask]; } -// Returns the level for windows that are configured to be always on top. -// This is not a constant because NSFloatingWindowLevel is a macro defined -// as a function call. -NSInteger AlwaysOnTopWindowLevel() { - return NSFloatingWindowLevel; -} - } // namespace namespace gfx { @@ -43,23 +36,6 @@ [window setCollectionBehavior:behavior]; } -bool IsNSWindowAlwaysOnTop(NSWindow* window) { - return [window level] == AlwaysOnTopWindowLevel(); -} - -void SetNSWindowAlwaysOnTop(NSWindow* window, - bool always_on_top) { - [window setLevel:(always_on_top ? AlwaysOnTopWindowLevel() - : NSNormalWindowLevel)]; - // Since always-on-top windows have a higher window level than - // NSNormalWindowLevel, they will default to - // NSWindowCollectionBehaviorTransient. Set the value explicitly here to match - // normal windows. - NSWindowCollectionBehavior behavior = - [window collectionBehavior] | NSWindowCollectionBehaviorManaged; - [window setCollectionBehavior:behavior]; -} - void SetNSWindowVisibleOnAllWorkspaces(NSWindow* window, bool always_visible) { NSWindowCollectionBehavior behavior = [window collectionBehavior]; if (always_visible)
diff --git a/ui/gfx/native_pixmap.h b/ui/gfx/native_pixmap.h index 7cb6717..8fd75d9 100644 --- a/ui/gfx/native_pixmap.h +++ b/ui/gfx/native_pixmap.h
@@ -30,6 +30,8 @@ virtual uint32_t GetDmaBufPitch(size_t plane) const = 0; virtual size_t GetDmaBufOffset(size_t plane) const = 0; virtual size_t GetDmaBufPlaneSize(size_t plane) const = 0; + // Return the number of non-interleaved "color" planes. + virtual size_t GetNumberOfPlanes() const = 0; // The following methods return format, modifier and size of the buffer, // respectively.
diff --git a/ui/gl/gl_image_native_pixmap.cc b/ui/gl/gl_image_native_pixmap.cc index 94b912d..ff64979 100644 --- a/ui/gl/gl_image_native_pixmap.cc +++ b/ui/gl/gl_image_native_pixmap.cc
@@ -178,9 +178,7 @@ bool has_dma_buf_import_modifier = gl::GLSurfaceEGL::HasEGLExtension( "EGL_EXT_image_dma_buf_import_modifiers"); - for (size_t attrs_plane = 0; - attrs_plane < - gfx::NumberOfPlanesForBufferFormat(pixmap->GetBufferFormat()); + for (size_t attrs_plane = 0; attrs_plane < pixmap->GetNumberOfPlanes(); ++attrs_plane) { attrs.push_back(EGL_DMA_BUF_PLANE0_FD_EXT + attrs_plane * 3); @@ -266,13 +264,6 @@ } gfx::BufferFormat format = GetBufferFormatFromFourCCFormat(fourcc); - if (num_planes > 0 && static_cast<size_t>(num_planes) != - gfx::NumberOfPlanesForBufferFormat(format)) { - LOG(ERROR) << "Invalid number of planes: " << num_planes - << " for format: " << gfx::BufferFormatToString(format); - return gfx::NativePixmapHandle(); - } - if (format != format_) { // A driver has returned a format different than what has been requested. // This can happen if RGBX is implemented using RGBA. Otherwise there is
diff --git a/ui/gl/gl_image_native_pixmap_unittest.cc b/ui/gl/gl_image_native_pixmap_unittest.cc index efaddc4..8927c385 100644 --- a/ui/gl/gl_image_native_pixmap_unittest.cc +++ b/ui/gl/gl_image_native_pixmap_unittest.cc
@@ -105,10 +105,6 @@ gfx::NativePixmapHandle native_pixmap_handle = image->ExportHandle(); - size_t num_planes = - gfx::NumberOfPlanesForBufferFormat(this->delegate_.GetBufferFormat()); - EXPECT_EQ(num_planes, native_pixmap_handle.planes.size()); - for (auto& plane : native_pixmap_handle.planes) { EXPECT_TRUE(plane.fd.is_valid()); }
diff --git a/ui/message_center/views/message_popup_view.cc b/ui/message_center/views/message_popup_view.cc index 686fc87..0751647 100644 --- a/ui/message_center/views/message_popup_view.cc +++ b/ui/message_center/views/message_popup_view.cc
@@ -105,7 +105,7 @@ void MessagePopupView::Show() { views::Widget::InitParams params(views::Widget::InitParams::TYPE_POPUP); - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingWindow; #if defined(OS_LINUX) && !defined(OS_CHROMEOS) // Make the widget explicitly activatable as TYPE_POPUP is not activatable by // default but we need focus for the inline reply textarea.
diff --git a/ui/ozone/gl/gl_image_ozone_native_pixmap_unittest.cc b/ui/ozone/gl/gl_image_ozone_native_pixmap_unittest.cc index d78a2fe..17ca2512 100644 --- a/ui/ozone/gl/gl_image_ozone_native_pixmap_unittest.cc +++ b/ui/ozone/gl/gl_image_ozone_native_pixmap_unittest.cc
@@ -44,8 +44,7 @@ bool mapped = client_pixmap->Map(); EXPECT_TRUE(mapped); - for (size_t plane = 0; plane < NumberOfPlanesForBufferFormat(format); - ++plane) { + for (size_t plane = 0; plane < pixmap->GetNumberOfPlanes(); ++plane) { void* data = client_pixmap->GetMemoryAddress(plane); GLImageTestSupport::SetBufferDataToColor( size.width(), size.height(), pixmap->GetDmaBufPitch(plane), plane,
diff --git a/ui/ozone/platform/cast/surface_factory_cast.cc b/ui/ozone/platform/cast/surface_factory_cast.cc index 0d229b3..b31b3b99 100644 --- a/ui/ozone/platform/cast/surface_factory_cast.cc +++ b/ui/ozone/platform/cast/surface_factory_cast.cc
@@ -58,6 +58,7 @@ gfx::BufferFormat GetBufferFormat() const override { return gfx::BufferFormat::BGRA_8888; } + size_t GetNumberOfPlanes() const override { return 1; } gfx::Size GetBufferSize() const override { return gfx::Size(); } uint32_t GetUniqueId() const override { return 0; }
diff --git a/ui/ozone/platform/drm/gpu/gbm_pixmap.cc b/ui/ozone/platform/drm/gpu/gbm_pixmap.cc index c63eb9f..293aee6 100644 --- a/ui/ozone/platform/drm/gpu/gbm_pixmap.cc +++ b/ui/ozone/platform/drm/gpu/gbm_pixmap.cc
@@ -48,6 +48,10 @@ return buffer_->GetPlaneSize(plane); } +size_t GbmPixmap::GetNumberOfPlanes() const { + return buffer_->GetNumPlanes(); +} + uint64_t GbmPixmap::GetBufferFormatModifier() const { return buffer_->GetFormatModifier(); }
diff --git a/ui/ozone/platform/drm/gpu/gbm_pixmap.h b/ui/ozone/platform/drm/gpu/gbm_pixmap.h index 5e00f78..17e1de67 100644 --- a/ui/ozone/platform/drm/gpu/gbm_pixmap.h +++ b/ui/ozone/platform/drm/gpu/gbm_pixmap.h
@@ -30,6 +30,7 @@ uint32_t GetDmaBufPitch(size_t plane) const override; size_t GetDmaBufOffset(size_t plane) const override; size_t GetDmaBufPlaneSize(size_t plane) const override; + size_t GetNumberOfPlanes() const override; uint64_t GetBufferFormatModifier() const override; gfx::BufferFormat GetBufferFormat() const override; gfx::Size GetBufferSize() const override;
diff --git a/ui/ozone/platform/drm/gpu/gbm_surface_factory.cc b/ui/ozone/platform/drm/gpu/gbm_surface_factory.cc index 04c6d02a5..e6f01ae5 100644 --- a/ui/ozone/platform/drm/gpu/gbm_surface_factory.cc +++ b/ui/ozone/platform/drm/gpu/gbm_surface_factory.cc
@@ -5,6 +5,7 @@ #include "ui/ozone/platform/drm/gpu/gbm_surface_factory.h" #include <gbm.h> + #include <memory> #include <utility> @@ -311,13 +312,10 @@ gfx::Size size, gfx::BufferFormat format, gfx::NativePixmapHandle handle) { - size_t num_planes = gfx::NumberOfPlanesForBufferFormat(format); - DCHECK_GE(num_planes, handle.planes.size()); - if (handle.planes.size() != num_planes) { + if (handle.planes.size() > GBM_MAX_PLANES) { return nullptr; } - std::unique_ptr<GbmBuffer> buffer; scoped_refptr<DrmFramebuffer> framebuffer; drm_thread_proxy_->CreateBufferFromHandle(
diff --git a/ui/ozone/platform/headless/headless_surface_factory.cc b/ui/ozone/platform/headless/headless_surface_factory.cc index b982cf5..e2b0ddc 100644 --- a/ui/ozone/platform/headless/headless_surface_factory.cc +++ b/ui/ozone/platform/headless/headless_surface_factory.cc
@@ -15,6 +15,7 @@ #include "build/build_config.h" #include "third_party/skia/include/core/SkCanvas.h" #include "third_party/skia/include/core/SkSurface.h" +#include "ui/gfx/buffer_format_util.h" #include "ui/gfx/codec/png_codec.h" #include "ui/gfx/native_pixmap.h" #include "ui/gfx/skia_util.h" @@ -88,6 +89,9 @@ size_t GetDmaBufPlaneSize(size_t plane) const override { return 0; } uint64_t GetBufferFormatModifier() const override { return 0; } gfx::BufferFormat GetBufferFormat() const override { return format_; } + size_t GetNumberOfPlanes() const override { + return gfx::NumberOfPlanesForBufferFormat(format_); + } gfx::Size GetBufferSize() const override { return gfx::Size(); } uint32_t GetUniqueId() const override { return 0; } bool ScheduleOverlayPlane(gfx::AcceleratedWidget widget,
diff --git a/ui/ozone/platform/scenic/sysmem_buffer_collection.cc b/ui/ozone/platform/scenic/sysmem_buffer_collection.cc index 72fc3f25..4a1aac59 100644 --- a/ui/ozone/platform/scenic/sysmem_buffer_collection.cc +++ b/ui/ozone/platform/scenic/sysmem_buffer_collection.cc
@@ -37,6 +37,10 @@ NOTREACHED(); return 0; } + size_t GetNumberOfPlanes() const override { + NOTREACHED(); + return 0; + } uint64_t GetBufferFormatModifier() const override { NOTREACHED(); return 0;
diff --git a/ui/ozone/platform/wayland/gpu/gbm_pixmap_wayland.cc b/ui/ozone/platform/wayland/gpu/gbm_pixmap_wayland.cc index 7fea3d603..7d0d93b 100644 --- a/ui/ozone/platform/wayland/gpu/gbm_pixmap_wayland.cc +++ b/ui/ozone/platform/wayland/gpu/gbm_pixmap_wayland.cc
@@ -7,6 +7,7 @@ #include <drm_fourcc.h> #include <gbm.h> #include <xf86drmMode.h> + #include <memory> #include "base/files/platform_file.h" @@ -106,6 +107,10 @@ return gbm_bo_->GetPlaneSize(plane); } +size_t GbmPixmapWayland::GetNumberOfPlanes() const { + return gbm_bo_->GetNumPlanes(); +} + uint64_t GbmPixmapWayland::GetBufferFormatModifier() const { return gbm_bo_->GetFormatModifier(); }
diff --git a/ui/ozone/platform/wayland/gpu/gbm_pixmap_wayland.h b/ui/ozone/platform/wayland/gpu/gbm_pixmap_wayland.h index 54829c3..a5214910 100644 --- a/ui/ozone/platform/wayland/gpu/gbm_pixmap_wayland.h +++ b/ui/ozone/platform/wayland/gpu/gbm_pixmap_wayland.h
@@ -35,6 +35,7 @@ uint32_t GetDmaBufPitch(size_t plane) const override; size_t GetDmaBufOffset(size_t plane) const override; size_t GetDmaBufPlaneSize(size_t plane) const override; + size_t GetNumberOfPlanes() const override; uint64_t GetBufferFormatModifier() const override; gfx::BufferFormat GetBufferFormat() const override; gfx::Size GetBufferSize() const override;
diff --git a/ui/views/controls/editable_combobox/editable_combobox.cc b/ui/views/controls/editable_combobox/editable_combobox.cc index 664f90e..baa65319 100644 --- a/ui/views/controls/editable_combobox/editable_combobox.cc +++ b/ui/views/controls/editable_combobox/editable_combobox.cc
@@ -15,6 +15,7 @@ #include "base/strings/string16.h" #include "build/build_config.h" #include "third_party/skia/include/core/SkColor.h" +#include "ui/accessibility/ax_action_data.h" #include "ui/accessibility/ax_node_data.h" #include "ui/base/accelerators/accelerator.h" #include "ui/base/ime/text_input_type.h" @@ -104,7 +105,8 @@ } void GetAccessibleNodeData(ui::AXNodeData* node_data) override { - node_data->role = ax::mojom::Role::kPopUpButton; + node_data->role = ax::mojom::Role::kComboBoxMenuButton; + node_data->SetName(GetAccessibleName()); node_data->SetHasPopup(ax::mojom::HasPopup::kMenu); if (GetEnabled()) node_data->SetDefaultActionVerb(ax::mojom::DefaultActionVerb::kOpen); @@ -275,6 +277,7 @@ event->flags() == event->changed_button_flags()) HandlePressEvent(event->root_location()); } + void OnTouchEvent(ui::TouchEvent* event) override { if (event->type() == ui::ET_TOUCH_PRESSED) HandlePressEvent(event->root_location()); @@ -354,7 +357,6 @@ // SetText does not actually notify the TextfieldController, so we call the // handling code directly. HandleNewContent(text); - ShowDropDownMenu(); } const gfx::FontList& EditableCombobox::GetFontList() const { @@ -367,6 +369,8 @@ void EditableCombobox::SetAccessibleName(const base::string16& name) { textfield_->SetAccessibleName(name); + if (arrow_) + arrow_->SetAccessibleName(name); } void EditableCombobox::SetAssociatedLabel(View* labelling_view) { @@ -408,6 +412,13 @@ textfield_->OnThemeChanged(); } +void EditableCombobox::GetAccessibleNodeData(ui::AXNodeData* node_data) { + node_data->role = ax::mojom::Role::kComboBoxGrouping; + + node_data->SetName(textfield_->accessible_name()); + node_data->SetValue(GetText()); +} + //////////////////////////////////////////////////////////////////////////////// // EditableCombobox, TextfieldController overrides: @@ -417,15 +428,23 @@ ShowDropDownMenu(ui::MENU_SOURCE_KEYBOARD); } +bool EditableCombobox::HandleKeyEvent(Textfield* sender, + const ui::KeyEvent& key_event) { + if (key_event.type() == ui::ET_KEY_PRESSED && + (key_event.key_code() == ui::VKEY_UP || + key_event.key_code() == ui::VKEY_DOWN)) { + ShowDropDownMenu(ui::MENU_SOURCE_KEYBOARD); + return true; + } + return false; +} + bool EditableCombobox::HandleMouseEvent(Textfield* sender, const ui::MouseEvent& mouse_event) { // We show the menu on mouse release instead of mouse press so that the menu // showing up doesn't interrupt a potential text selection operation by the // user. - if (mouse_event.type() == ui::ET_MOUSE_PRESSED) { - mouse_pressed_ = true; - } else if (mouse_event.type() == ui::ET_MOUSE_RELEASED) { - mouse_pressed_ = false; + if (mouse_event.type() == ui::ET_MOUSE_RELEASED) { ShowDropDownMenu(ui::MENU_SOURCE_MOUSE); } return false; @@ -445,14 +464,6 @@ CloseMenu(); } -void EditableCombobox::OnViewFocused(View* observed_view) { - // We only show the menu if the mouse is not currently pressed to avoid - // interrupting a text selection operation. The menu will be shown on mouse - // release inside HandleMouseEvent. - if (!mouse_pressed_) - ShowDropDownMenu(); -} - //////////////////////////////////////////////////////////////////////////////// // EditableCombobox, ButtonListener overrides: @@ -516,7 +527,7 @@ CloseMenu(); return; } - if (!textfield_->HasFocus() || (menu_runner_ && menu_runner_->IsRunning())) + if (menu_runner_ && menu_runner_->IsRunning()) return; // Since we don't capture the mouse, we want to see the events that happen in
diff --git a/ui/views/controls/editable_combobox/editable_combobox.h b/ui/views/controls/editable_combobox/editable_combobox.h index 0386dfb..e3c1166dd 100644 --- a/ui/views/controls/editable_combobox/editable_combobox.h +++ b/ui/views/controls/editable_combobox/editable_combobox.h
@@ -121,17 +121,19 @@ // Overridden from View: void Layout() override; void OnThemeChanged() override; + void GetAccessibleNodeData(ui::AXNodeData* node_data) override; // Overridden from TextfieldController: void ContentsChanged(Textfield* sender, const base::string16& new_contents) override; + bool HandleKeyEvent(Textfield* sender, + const ui::KeyEvent& key_event) override; bool HandleMouseEvent(Textfield* sender, const ui::MouseEvent& mouse_event) override; bool HandleGestureEvent(Textfield* sender, const ui::GestureEvent& gesture_event) override; // Overridden from ViewObserver: - void OnViewFocused(View* observed_view) override; void OnViewBlurred(View* observed_view) override; // Overridden from ButtonListener: @@ -159,10 +161,6 @@ const Type type_; - // True between mouse press and release, used to avoid opening the menu and - // interrupting textfield selection interactions. - bool mouse_pressed_ = false; - // Set while the drop-down is showing. std::unique_ptr<MenuRunner> menu_runner_;
diff --git a/ui/views/controls/editable_combobox/editable_combobox_unittest.cc b/ui/views/controls/editable_combobox/editable_combobox_unittest.cc index 396f86bb..01095a9 100644 --- a/ui/views/controls/editable_combobox/editable_combobox_unittest.cc +++ b/ui/views/controls/editable_combobox/editable_combobox_unittest.cc
@@ -246,16 +246,24 @@ event_generator_->PressKey(key_code, flags); } -TEST_F(EditableComboboxTest, FocusOnTextfieldOpensMenu) { +TEST_F(EditableComboboxTest, FocusOnTextfieldDoesntOpenMenu) { InitEditableCombobox(); EXPECT_FALSE(IsMenuOpen()); combobox_->GetTextfieldForTest()->RequestFocus(); + EXPECT_FALSE(IsMenuOpen()); +} + +TEST_F(EditableComboboxTest, ArrowDownOpensMenu) { + InitEditableCombobox(); + EXPECT_FALSE(IsMenuOpen()); + combobox_->GetTextfieldForTest()->RequestFocus(); + SendKeyEvent(ui::VKEY_DOWN); EXPECT_TRUE(IsMenuOpen()); } TEST_F(EditableComboboxTest, TabMovesToOtherViewAndClosesMenu) { InitEditableCombobox(); - combobox_->GetTextfieldForTest()->RequestFocus(); + ClickArrow(); EXPECT_TRUE(IsMenuOpen()); EXPECT_TRUE(combobox_->GetTextfieldForTest()->HasFocus()); SendKeyEvent(ui::VKEY_TAB); @@ -268,8 +276,9 @@ TEST_F(EditableComboboxTest, ClickOutsideEditableComboboxWithoutLosingFocusClosesMenu) { InitEditableCombobox(); - combobox_->GetTextfieldForTest()->RequestFocus(); + ClickArrow(); EXPECT_TRUE(IsMenuOpen()); + EXPECT_TRUE(combobox_->GetTextfieldForTest()->HasFocus()); const gfx::Point outside_point(combobox_->x() + combobox_->width() + 1, combobox_->y() + 1); @@ -282,7 +291,7 @@ TEST_F(EditableComboboxTest, ClickTextfieldDoesntCloseMenu) { InitEditableCombobox(); - combobox_->GetTextfieldForTest()->RequestFocus(); + ClickArrow(); EXPECT_TRUE(IsMenuOpen()); MenuRunner* menu_runner1 = combobox_->GetMenuRunnerForTest(); @@ -296,7 +305,7 @@ TEST_F(EditableComboboxTest, RemovingControlWhileMenuOpenClosesMenu) { InitEditableCombobox(); - combobox_->GetTextfieldForTest()->RequestFocus(); + ClickArrow(); EXPECT_TRUE(IsMenuOpen()); parent_of_combobox_->RemoveChildView(combobox_); EXPECT_EQ(nullptr, combobox_->GetMenuRunnerForTest()); @@ -304,7 +313,7 @@ TEST_F(EditableComboboxTest, RemovingParentOfControlWhileMenuOpenClosesMenu) { InitEditableCombobox(); - combobox_->GetTextfieldForTest()->RequestFocus(); + ClickArrow(); EXPECT_TRUE(IsMenuOpen()); widget_->GetContentsView()->RemoveChildView(parent_of_combobox_); EXPECT_EQ(nullptr, combobox_->GetMenuRunnerForTest()); @@ -497,8 +506,8 @@ TEST_F(EditableComboboxTest, ClickOnMenuItemSelectsItAndClosesMenu) { InitEditableCombobox(); - combobox_->GetTextfieldForTest()->RequestFocus(); - EXPECT_TRUE(IsMenuOpen()); + ClickArrow(); + ASSERT_TRUE(IsMenuOpen()); ClickMenuItem(/*index=*/0); WaitForMenuClosureAnimation(); @@ -526,7 +535,8 @@ ASCIIToUTF16("bac"), ASCIIToUTF16("bad")}; InitEditableCombobox(items, /*filter_on_edit=*/true); - combobox_->GetTextfieldForTest()->RequestFocus(); + ClickArrow(); + ASSERT_TRUE(IsMenuOpen()); SendKeyEvent(ui::VKEY_DOWN); SendKeyEvent(ui::VKEY_RETURN); @@ -569,7 +579,7 @@ // "bac", the selected item, instead of showing completions of "b", what we // had typed. dummy_focusable_view_->RequestFocus(); - combobox_->GetTextfieldForTest()->RequestFocus(); + ClickArrow(); EXPECT_TRUE(IsMenuOpen()); ASSERT_EQ(2, combobox_->GetItemCountForTest()); }
diff --git a/ui/views/controls/textfield/textfield.h b/ui/views/controls/textfield/textfield.h index b7638eff..0b1d4f3 100644 --- a/ui/views/controls/textfield/textfield.h +++ b/ui/views/controls/textfield/textfield.h
@@ -241,6 +241,7 @@ // Set the accessible name of the text field. If the textfield has a visible // label, use SetAssociatedLabel() instead. void SetAccessibleName(const base::string16& name); + const base::string16& accessible_name() const { return accessible_name_; } // If the accessible name should be the same as the labelling view's text, // use this. It will set the accessible label relationship and copy the
diff --git a/ui/views/corewm/tooltip_aura.cc b/ui/views/corewm/tooltip_aura.cc index 9ff7e6a..2279c53 100644 --- a/ui/views/corewm/tooltip_aura.cc +++ b/ui/views/corewm/tooltip_aura.cc
@@ -58,7 +58,7 @@ params.type = views::Widget::InitParams::TYPE_TOOLTIP; params.context = tooltip_window; DCHECK(params.context); - params.keep_on_top = true; + params.z_order = ui::ZOrderLevel::kFloatingUIElement; params.accept_events = false; params.bounds = bounds; if (CanUseTranslucentTooltipWidget())
diff --git a/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc b/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc index 3031a8d..e7d20b8 100644 --- a/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc +++ b/ui/views/widget/desktop_aura/desktop_native_widget_aura.cc
@@ -86,7 +86,7 @@ const gfx::Rect& bounds, bool full_screen, bool is_menu, - bool root_is_always_on_top) { + ui::ZOrderLevel root_z_order) { // This instance will get deleted when the widget is destroyed. DesktopNativeWidgetTopLevelHandler* top_level_handler = new DesktopNativeWidgetTopLevelHandler; @@ -103,7 +103,7 @@ init_params.activatable = full_screen ? Widget::InitParams::ACTIVATABLE_YES : Widget::InitParams::ACTIVATABLE_NO; - init_params.keep_on_top = root_is_always_on_top; + init_params.z_order = root_z_order; // This widget instance will get deleted when the window is // destroyed. @@ -193,14 +193,14 @@ bool is_menu = window->type() == aura::client::WINDOW_TYPE_MENU; if (is_fullscreen || is_menu) { - bool root_is_always_on_top = false; + ui::ZOrderLevel root_z_order = ui::ZOrderLevel::kNormal; internal::NativeWidgetPrivate* native_widget = DesktopNativeWidgetAura::ForWindow(root_window_); if (native_widget) - root_is_always_on_top = native_widget->IsAlwaysOnTop(); + root_z_order = native_widget->GetZOrderLevel(); return DesktopNativeWidgetTopLevelHandler::CreateParentWindow( - window, bounds, is_fullscreen, is_menu, root_is_always_on_top); + window, bounds, is_fullscreen, is_menu, root_z_order); } return root_window_; } @@ -813,13 +813,15 @@ return content_window_ && desktop_window_tree_host_->IsActive(); } -void DesktopNativeWidgetAura::SetAlwaysOnTop(bool always_on_top) { +void DesktopNativeWidgetAura::SetZOrderLevel(ui::ZOrderLevel order) { if (content_window_) - desktop_window_tree_host_->SetAlwaysOnTop(always_on_top); + desktop_window_tree_host_->SetZOrderLevel(order); } -bool DesktopNativeWidgetAura::IsAlwaysOnTop() const { - return content_window_ && desktop_window_tree_host_->IsAlwaysOnTop(); +ui::ZOrderLevel DesktopNativeWidgetAura::GetZOrderLevel() const { + if (content_window_) + return desktop_window_tree_host_->GetZOrderLevel(); + return ui::ZOrderLevel::kNormal; } void DesktopNativeWidgetAura::SetVisibleOnAllWorkspaces(bool always_visible) {
diff --git a/ui/views/widget/desktop_aura/desktop_native_widget_aura.h b/ui/views/widget/desktop_aura/desktop_native_widget_aura.h index 3acc23d..8b038de 100644 --- a/ui/views/widget/desktop_aura/desktop_native_widget_aura.h +++ b/ui/views/widget/desktop_aura/desktop_native_widget_aura.h
@@ -151,8 +151,8 @@ void Activate() override; void Deactivate() override; bool IsActive() const override; - void SetAlwaysOnTop(bool always_on_top) override; - bool IsAlwaysOnTop() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; + ui::ZOrderLevel GetZOrderLevel() const override; void SetVisibleOnAllWorkspaces(bool always_visible) override; bool IsVisibleOnAllWorkspaces() const override; void Maximize() override;
diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host.h b/ui/views/widget/desktop_aura/desktop_window_tree_host.h index 17f9725..c4fa6859 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host.h +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host.h
@@ -130,8 +130,8 @@ virtual bool HasCapture() const = 0; - virtual void SetAlwaysOnTop(bool always_on_top) = 0; - virtual bool IsAlwaysOnTop() const = 0; + virtual void SetZOrderLevel(ui::ZOrderLevel order) = 0; + virtual ui::ZOrderLevel GetZOrderLevel() const = 0; virtual void SetVisibleOnAllWorkspaces(bool always_visible) = 0; virtual bool IsVisibleOnAllWorkspaces() const = 0;
diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_platform.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_platform.cc index cbd212d..c8021f1 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_platform.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_platform.cc
@@ -345,14 +345,14 @@ return platform_window()->HasCapture(); } -void DesktopWindowTreeHostPlatform::SetAlwaysOnTop(bool always_on_top) { +void DesktopWindowTreeHostPlatform::SetZOrderLevel(ui::ZOrderLevel order) { // TODO: needs PlatformWindow support. NOTIMPLEMENTED_LOG_ONCE(); } -bool DesktopWindowTreeHostPlatform::IsAlwaysOnTop() const { +ui::ZOrderLevel DesktopWindowTreeHostPlatform::GetZOrderLevel() const { // TODO: needs PlatformWindow support. - return false; + return ui::ZOrderLevel::kNormal; } void DesktopWindowTreeHostPlatform::SetVisibleOnAllWorkspaces(
diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_platform.h b/ui/views/widget/desktop_aura/desktop_window_tree_host_platform.h index 02f30ef..8760639 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_platform.h +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_platform.h
@@ -59,8 +59,8 @@ bool IsMaximized() const override; bool IsMinimized() const override; bool HasCapture() const override; - void SetAlwaysOnTop(bool always_on_top) override; - bool IsAlwaysOnTop() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; + ui::ZOrderLevel GetZOrderLevel() const override; void SetVisibleOnAllWorkspaces(bool always_visible) override; bool IsVisibleOnAllWorkspaces() const override; bool SetWindowTitle(const base::string16& title) override;
diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc index eed8b61..7e31a1c1 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc
@@ -133,6 +133,7 @@ remove_standard_frame_ = params.remove_standard_frame; has_non_client_view_ = Widget::RequiresNonClientView(params.type); + z_order_ = params.EffectiveZOrderLevel(); // We don't have an HWND yet, so scale relative to the nearest screen. gfx::Rect pixel_bounds = @@ -367,12 +368,16 @@ return message_handler_->HasCapture(); } -void DesktopWindowTreeHostWin::SetAlwaysOnTop(bool always_on_top) { - message_handler_->SetAlwaysOnTop(always_on_top); +void DesktopWindowTreeHostWin::SetZOrderLevel(ui::ZOrderLevel order) { + z_order_ = order; + // Emulate the multiple window levels provided by other platforms by + // collapsing the z-order enum into kNormal = normal, everything else = always + // on top. + message_handler_->SetAlwaysOnTop(order != ui::ZOrderLevel::kNormal); } -bool DesktopWindowTreeHostWin::IsAlwaysOnTop() const { - return message_handler_->IsAlwaysOnTop(); +ui::ZOrderLevel DesktopWindowTreeHostWin::GetZOrderLevel() const { + return z_order_; } void DesktopWindowTreeHostWin::SetVisibleOnAllWorkspaces(bool always_visible) {
diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h index 8ac960b..335db0db 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h
@@ -95,8 +95,8 @@ bool IsMaximized() const override; bool IsMinimized() const override; bool HasCapture() const override; - void SetAlwaysOnTop(bool always_on_top) override; - bool IsAlwaysOnTop() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; + ui::ZOrderLevel GetZOrderLevel() const override; void SetVisibleOnAllWorkspaces(bool always_visible) override; bool IsVisibleOnAllWorkspaces() const override; bool SetWindowTitle(const base::string16& title) override; @@ -307,6 +307,10 @@ // become activated. bool wants_mouse_events_when_inactive_ = false; + // The z-order level of the window; the window exhibits "always on top" + // behavior if > 0. + ui::ZOrderLevel z_order_ = ui::ZOrderLevel::kNormal; + DISALLOW_COPY_AND_ASSIGN(DesktopWindowTreeHostWin); };
diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_x11.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_x11.cc index b417376..1943ca38 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_x11.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_x11.cc
@@ -130,7 +130,8 @@ config.activatable = params.activatable == Widget::InitParams::ACTIVATABLE_YES; config.force_show_in_taskbar = params.force_show_in_taskbar; - config.keep_on_top = params.keep_on_top; + config.keep_on_top = + params.EffectiveZOrderLevel() != ui::ZOrderLevel::kNormal; config.visible_on_all_workspaces = params.visible_on_all_workspaces; config.remove_standard_frame = params.remove_standard_frame; @@ -666,12 +667,25 @@ return g_current_capture == this; } -void DesktopWindowTreeHostX11::SetAlwaysOnTop(bool always_on_top) { - x11_window_->SetAlwaysOnTop(always_on_top); +void DesktopWindowTreeHostX11::SetZOrderLevel(ui::ZOrderLevel order) { + z_order_ = order; + + // Emulate the multiple window levels provided by other platforms by + // collapsing the z-order enum into kNormal = normal, everything else = always + // on top. + x11_window_->SetAlwaysOnTop(order != ui::ZOrderLevel::kNormal); } -bool DesktopWindowTreeHostX11::IsAlwaysOnTop() const { - return x11_window_->is_always_on_top(); +ui::ZOrderLevel DesktopWindowTreeHostX11::GetZOrderLevel() const { + bool window_always_on_top = x11_window_->is_always_on_top(); + bool level_always_on_top = z_order_ != ui::ZOrderLevel::kNormal; + + if (window_always_on_top == level_always_on_top) + return z_order_; + + // Something external has forced a window to be always-on-top; map it to + // kFloatingWindow as a reasonable equivalent. + return ui::ZOrderLevel::kFloatingWindow; } void DesktopWindowTreeHostX11::SetVisible(bool visible) {
diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_x11.h b/ui/views/widget/desktop_aura/desktop_window_tree_host_x11.h index 3e9f5d0..61a64ce 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_x11.h +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_x11.h
@@ -138,8 +138,8 @@ bool IsMaximized() const override; bool IsMinimized() const override; bool HasCapture() const override; - void SetAlwaysOnTop(bool always_on_top) override; - bool IsAlwaysOnTop() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; + ui::ZOrderLevel GetZOrderLevel() const override; void SetVisibleOnAllWorkspaces(bool always_visible) override; bool IsVisibleOnAllWorkspaces() const override; bool SetWindowTitle(const base::string16& title) override; @@ -291,6 +291,10 @@ // Whether |xwindow_| was requested to be fullscreen via SetFullscreen(). bool is_fullscreen_ = false; + // The z-order level of the window; the window exhibits "always on top" + // behavior if > 0. + ui::ZOrderLevel z_order_ = ui::ZOrderLevel::kNormal; + DesktopDragDropClientAuraX11* drag_drop_client_ = nullptr; std::unique_ptr<ui::EventHandler> x11_non_client_event_filter_;
diff --git a/ui/views/widget/native_widget_aura.cc b/ui/views/widget/native_widget_aura.cc index 6bea4cd..e160cce 100644 --- a/ui/views/widget/native_widget_aura.cc +++ b/ui/views/widget/native_widget_aura.cc
@@ -204,8 +204,8 @@ ->set_parent_controls_visibility(true); } } - // SetAlwaysOnTop before SetParent so that always-on-top container is used. - SetAlwaysOnTop(params.keep_on_top); + // SetZOrderLevel before SetParent so that always-on-top container is used. + SetZOrderLevel(params.EffectiveZOrderLevel()); // Make sure we have a real |window_bounds|. aura::Window* parent_or_context = parent ? parent : context; @@ -610,13 +610,16 @@ return window_ && wm::IsActiveWindow(window_); } -void NativeWidgetAura::SetAlwaysOnTop(bool on_top) { +void NativeWidgetAura::SetZOrderLevel(ui::ZOrderLevel order) { if (window_) - window_->SetProperty(aura::client::kAlwaysOnTopKey, on_top); + window_->SetProperty(aura::client::kZOrderingKey, order); } -bool NativeWidgetAura::IsAlwaysOnTop() const { - return window_ && window_->GetProperty(aura::client::kAlwaysOnTopKey); +ui::ZOrderLevel NativeWidgetAura::GetZOrderLevel() const { + if (window_) + return window_->GetProperty(aura::client::kZOrderingKey); + + return ui::ZOrderLevel::kNormal; } void NativeWidgetAura::SetVisibleOnAllWorkspaces(bool always_visible) {
diff --git a/ui/views/widget/native_widget_aura.h b/ui/views/widget/native_widget_aura.h index deb81b1..8fea00d 100644 --- a/ui/views/widget/native_widget_aura.h +++ b/ui/views/widget/native_widget_aura.h
@@ -116,8 +116,8 @@ void Activate() override; void Deactivate() override; bool IsActive() const override; - void SetAlwaysOnTop(bool always_on_top) override; - bool IsAlwaysOnTop() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; + ui::ZOrderLevel GetZOrderLevel() const override; void SetVisibleOnAllWorkspaces(bool always_visible) override; bool IsVisibleOnAllWorkspaces() const override; void Maximize() override;
diff --git a/ui/views/widget/native_widget_mac.h b/ui/views/widget/native_widget_mac.h index 995b76e4..e64872d3 100644 --- a/ui/views/widget/native_widget_mac.h +++ b/ui/views/widget/native_widget_mac.h
@@ -133,8 +133,8 @@ void Activate() override; void Deactivate() override; bool IsActive() const override; - void SetAlwaysOnTop(bool always_on_top) override; - bool IsAlwaysOnTop() const override; + void SetZOrderLevel(ui::ZOrderLevel order) override; + ui::ZOrderLevel GetZOrderLevel() const override; void SetVisibleOnAllWorkspaces(bool always_visible) override; bool IsVisibleOnAllWorkspaces() const override; void Maximize() override; @@ -233,6 +233,8 @@ // Internal name. std::string name_; + Widget::InitParams::Type type_; + DISALLOW_COPY_AND_ASSIGN(NativeWidgetMac); };
diff --git a/ui/views/widget/native_widget_mac.mm b/ui/views/widget/native_widget_mac.mm index 0c3fbdbf..9043f5b 100644 --- a/ui/views/widget/native_widget_mac.mm +++ b/ui/views/widget/native_widget_mac.mm
@@ -11,6 +11,7 @@ #include "base/bind.h" #include "base/lazy_instance.h" #include "base/mac/scoped_nsobject.h" +#include "base/no_destructor.h" #include "base/strings/sys_string_conversions.h" #include "base/threading/thread_task_runner_handle.h" #include "components/crash/core/common/crash_key.h" @@ -25,7 +26,6 @@ #include "ui/events/gestures/gesture_recognizer_impl_mac.h" #include "ui/gfx/font_list.h" #import "ui/gfx/mac/coordinate_conversion.h" -#import "ui/gfx/mac/nswindow_frame_controls.h" #include "ui/native_theme/native_theme.h" #include "ui/native_theme/native_theme_mac.h" #import "ui/views/cocoa/drag_drop_client_mac.h" @@ -37,6 +37,7 @@ using remote_cocoa::mojom::WindowVisibilityState; namespace views { + namespace { base::LazyInstance<ui::GestureRecognizerImplMac>::Leaky @@ -65,6 +66,42 @@ return NSBorderlessWindowMask; } +CGWindowLevel CGWindowLevelForZOrderLevel(ui::ZOrderLevel level, + Widget::InitParams::Type type) { + switch (level) { + case ui::ZOrderLevel::kNormal: + return kCGNormalWindowLevel; + case ui::ZOrderLevel::kFloatingWindow: + if (type == Widget::InitParams::TYPE_MENU) + return kCGPopUpMenuWindowLevel; + else + return kCGFloatingWindowLevel; + case ui::ZOrderLevel::kFloatingUIElement: + if (type == Widget::InitParams::TYPE_DRAG) + return kCGDraggingWindowLevel; + else + return kCGStatusWindowLevel; + case ui::ZOrderLevel::kSecuritySurface: + return kCGScreenSaverWindowLevel - 1; + } +} + +ui::ZOrderLevel ZOrderLevelForCGWindowLevel(CGWindowLevel level) { + switch (level) { + case kCGNormalWindowLevel: + return ui::ZOrderLevel::kNormal; + case kCGFloatingWindowLevel: + case kCGPopUpMenuWindowLevel: + default: + return ui::ZOrderLevel::kFloatingWindow; + case kCGStatusWindowLevel: + case kCGDraggingWindowLevel: + return ui::ZOrderLevel::kFloatingUIElement; + case kCGScreenSaverWindowLevel - 1: + return ui::ZOrderLevel::kSecuritySurface; + } +} + } // namespace //////////////////////////////////////////////////////////////////////////////// @@ -125,6 +162,7 @@ void NativeWidgetMac::InitNativeWidget(const Widget::InitParams& params) { ownership_ = params.ownership; name_ = params.name; + type_ = params.type; NativeWidgetMacNSWindowHost* parent_host = NativeWidgetMacNSWindowHost::GetFromNativeView(params.parent); @@ -154,10 +192,10 @@ ns_window_host_->InitWindow(params); OnWindowInitialized(); - // Only set always-on-top here if it is true since setting it may affect how - // the window is treated by Expose. - if (params.keep_on_top) - SetAlwaysOnTop(true); + // Only set the z-order here if it is non-default since setting it may affect + // how the window is treated by Expose. + if (params.EffectiveZOrderLevel() != ui::ZOrderLevel::kNormal) + SetZOrderLevel(params.EffectiveZOrderLevel()); delegate_->OnNativeWidgetCreated(); @@ -473,13 +511,21 @@ return ns_window_host_ ? ns_window_host_->IsWindowKey() : false; } -void NativeWidgetMac::SetAlwaysOnTop(bool always_on_top) { - gfx::SetNSWindowAlwaysOnTop(GetNativeWindow().GetNativeNSWindow(), - always_on_top); +void NativeWidgetMac::SetZOrderLevel(ui::ZOrderLevel order) { + NSWindow* window = GetNativeWindow().GetNativeNSWindow(); + [window setLevel:CGWindowLevelForZOrderLevel(order, type_)]; + + // Windows that have a higher window level than NSNormalWindowLevel default to + // NSWindowCollectionBehaviorTransient. Set the value explicitly here to match + // normal windows. + NSWindowCollectionBehavior behavior = + [window collectionBehavior] | NSWindowCollectionBehaviorManaged; + [window setCollectionBehavior:behavior]; } -bool NativeWidgetMac::IsAlwaysOnTop() const { - return gfx::IsNSWindowAlwaysOnTop(GetNativeWindow().GetNativeNSWindow()); +ui::ZOrderLevel NativeWidgetMac::GetZOrderLevel() const { + return ZOrderLevelForCGWindowLevel( + [GetNativeWindow().GetNativeNSWindow() level]); } void NativeWidgetMac::SetVisibleOnAllWorkspaces(bool always_visible) {
diff --git a/ui/views/widget/native_widget_private.h b/ui/views/widget/native_widget_private.h index 14e9825e..84acc003 100644 --- a/ui/views/widget/native_widget_private.h +++ b/ui/views/widget/native_widget_private.h
@@ -187,8 +187,8 @@ virtual void Activate() = 0; virtual void Deactivate() = 0; virtual bool IsActive() const = 0; - virtual void SetAlwaysOnTop(bool always_on_top) = 0; - virtual bool IsAlwaysOnTop() const = 0; + virtual void SetZOrderLevel(ui::ZOrderLevel order) = 0; + virtual ui::ZOrderLevel GetZOrderLevel() const = 0; virtual void SetVisibleOnAllWorkspaces(bool always_visible) = 0; virtual bool IsVisibleOnAllWorkspaces() const = 0; virtual void Maximize() = 0;
diff --git a/ui/views/widget/widget.cc b/ui/views/widget/widget.cc index e9182c3..0cb7527 100644 --- a/ui/views/widget/widget.cc +++ b/ui/views/widget/widget.cc
@@ -149,7 +149,6 @@ opacity(INFER_OPACITY), accept_events(true), activatable(ACTIVATABLE_DEFAULT), - keep_on_top(type == TYPE_MENU || type == TYPE_DRAG), visible_on_all_workspaces(false), ownership(NATIVE_WIDGET_OWNS_WIDGET), mirror_origin_in_rtl(false), @@ -177,6 +176,22 @@ type != InitParams::TYPE_DRAG; } +ui::ZOrderLevel Widget::InitParams::EffectiveZOrderLevel() const { + if (z_order.has_value()) + return z_order.value(); + + switch (type) { + case TYPE_MENU: + return ui::ZOrderLevel::kFloatingWindow; + break; + case TYPE_DRAG: + return ui::ZOrderLevel::kFloatingUIElement; + break; + default: + return ui::ZOrderLevel::kNormal; + } +} + //////////////////////////////////////////////////////////////////////////////// // Widget, public: @@ -682,12 +697,12 @@ return native_widget_->IsActive(); } -void Widget::SetAlwaysOnTop(bool on_top) { - native_widget_->SetAlwaysOnTop(on_top); +void Widget::SetZOrderLevel(ui::ZOrderLevel order) { + native_widget_->SetZOrderLevel(order); } -bool Widget::IsAlwaysOnTop() const { - return native_widget_->IsAlwaysOnTop(); +ui::ZOrderLevel Widget::GetZOrderLevel() const { + return native_widget_->GetZOrderLevel(); } void Widget::SetVisibleOnAllWorkspaces(bool always_visible) {
diff --git a/ui/views/widget/widget.h b/ui/views/widget/widget.h index b0d969c0..83ba608 100644 --- a/ui/views/widget/widget.h +++ b/ui/views/widget/widget.h
@@ -217,6 +217,10 @@ // case where |activatable| is |ACTIVATABLE_DEFAULT|. bool CanActivate() const; + // Returns the z-order level, based on the overriding |z_order| but also + // taking into account special levels due to |type|. + ui::ZOrderLevel EffectiveZOrderLevel() const; + Type type; // If null, a default implementation will be constructed. The default // implementation deletes itself when the Widget closes. @@ -234,7 +238,7 @@ WindowOpacity opacity; bool accept_events; Activatable activatable; - bool keep_on_top; + base::Optional<ui::ZOrderLevel> z_order; bool visible_on_all_workspaces; // See Widget class comment above. Ownership ownership; @@ -536,12 +540,11 @@ // Returns whether the Widget is the currently active window. virtual bool IsActive() const; - // Sets the widget to be on top of all other widgets in the windowing system. - void SetAlwaysOnTop(bool on_top); + // Sets the z-order of the widget. This only applies to top-level widgets. + void SetZOrderLevel(ui::ZOrderLevel order); - // Returns whether the widget has been set to be on top of most other widgets - // in the windowing system. - bool IsAlwaysOnTop() const; + // Gets the z-order of the widget. This only applies to top-level widgets. + ui::ZOrderLevel GetZOrderLevel() const; // Sets the widget to be visible on all work spaces. void SetVisibleOnAllWorkspaces(bool always_visible);
diff --git a/ui/views/widget/widget_hwnd_utils.cc b/ui/views/widget/widget_hwnd_utils.cc index 7d74fdff..9edfa2c 100644 --- a/ui/views/widget/widget_hwnd_utils.cc +++ b/ui/views/widget/widget_hwnd_utils.cc
@@ -45,7 +45,7 @@ DCHECK_NE(Widget::InitParams::ACTIVATABLE_DEFAULT, params.activatable); if (params.activatable == Widget::InitParams::ACTIVATABLE_NO) *ex_style |= WS_EX_NOACTIVATE; - if (params.keep_on_top) + if (params.EffectiveZOrderLevel() != ui::ZOrderLevel::kNormal) *ex_style |= WS_EX_TOPMOST; if (params.mirror_origin_in_rtl) *ex_style |= l10n_util::GetExtendedTooltipStyles();
diff --git a/ui/views/widget/widget_unittest.cc b/ui/views/widget/widget_unittest.cc index de60af6..64a5731a 100644 --- a/ui/views/widget/widget_unittest.cc +++ b/ui/views/widget/widget_unittest.cc
@@ -588,8 +588,8 @@ widget.Activate(); widget.Deactivate(); widget.IsActive(); - widget.SetAlwaysOnTop(true); - widget.IsAlwaysOnTop(); + widget.SetZOrderLevel(ui::ZOrderLevel::kNormal); + widget.GetZOrderLevel(); widget.Maximize(); widget.Minimize(); widget.Restore(); @@ -3692,14 +3692,14 @@ #endif -// Test that SetAlwaysOnTop and IsAlwaysOnTop are consistent. -TEST_F(WidgetTest, AlwaysOnTop) { +// Test that the z-order levels round-trip. +TEST_F(WidgetTest, ZOrderLevel) { WidgetAutoclosePtr widget(CreateTopLevelNativeWidget()); - EXPECT_FALSE(widget->IsAlwaysOnTop()); - widget->SetAlwaysOnTop(true); - EXPECT_TRUE(widget->IsAlwaysOnTop()); - widget->SetAlwaysOnTop(false); - EXPECT_FALSE(widget->IsAlwaysOnTop()); + EXPECT_EQ(ui::ZOrderLevel::kNormal, widget->GetZOrderLevel()); + widget->SetZOrderLevel(ui::ZOrderLevel::kFloatingWindow); + EXPECT_EQ(ui::ZOrderLevel::kFloatingWindow, widget->GetZOrderLevel()); + widget->SetZOrderLevel(ui::ZOrderLevel::kNormal); + EXPECT_EQ(ui::ZOrderLevel::kNormal, widget->GetZOrderLevel()); } namespace {
diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc index f388a37..dba70a0 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc
@@ -763,10 +763,6 @@ return fullscreen_handler_->fullscreen(); } -bool HWNDMessageHandler::IsAlwaysOnTop() const { - return (GetWindowLong(hwnd(), GWL_EXSTYLE) & WS_EX_TOPMOST) != 0; -} - bool HWNDMessageHandler::RunMoveLoop(const gfx::Vector2d& drag_offset, bool hide_on_escape) { ReleaseCapture();
diff --git a/ui/views/win/hwnd_message_handler.h b/ui/views/win/hwnd_message_handler.h index d918f23..83fe042 100644 --- a/ui/views/win/hwnd_message_handler.h +++ b/ui/views/win/hwnd_message_handler.h
@@ -137,7 +137,6 @@ bool IsMinimized() const; bool IsMaximized() const; bool IsFullscreen() const; - bool IsAlwaysOnTop() const; bool RunMoveLoop(const gfx::Vector2d& drag_offset, bool hide_on_escape); void EndMoveLoop();
diff --git a/ui/webui/resources/cr_elements/cr_container_shadow_behavior.js b/ui/webui/resources/cr_elements/cr_container_shadow_behavior.js index 489c3f1..cd5a1c0 100644 --- a/ui/webui/resources/cr_elements/cr_container_shadow_behavior.js +++ b/ui/webui/resources/cr_elements/cr_container_shadow_behavior.js
@@ -67,6 +67,7 @@ // The element holding the drop shadow effect to be shown. const shadow = document.createElement('div'); shadow.id = `cr-container-shadow-${side}`; + shadow.classList.add('cr-container-shadow'); this.dropShadows_.set(side, shadow); this.intersectionProbes_.set(side, document.createElement('div')); });
diff --git a/ui/webui/resources/cr_elements/shared_style_css.html b/ui/webui/resources/cr_elements/shared_style_css.html index 4eed6ee..8e9a990 100644 --- a/ui/webui/resources/cr_elements/shared_style_css.html +++ b/ui/webui/resources/cr_elements/shared_style_css.html
@@ -75,12 +75,21 @@ @apply --cr-actionable; } - /** Styles for elements that implement the CrContainerShadowBehavior */ - #cr-container-shadow-top, - #cr-container-shadow-bottom { - @apply --cr-container-shadow; + .cr-container-shadow { + box-shadow: inset 0 5px 6px -3px rgba(0, 0, 0, .4); + height: var(--cr-container-shadow-height); + left: 0; + margin: 0 0 var(--cr-container-shadow-margin); + opacity: 0; + pointer-events: none; + position: relative; + right: 0; + top: 0; + transition: opacity 500ms; + z-index: 1; } + /** Styles for elements that implement the CrContainerShadowBehavior */ #cr-container-shadow-bottom { margin-bottom: 0; margin-top: var(--cr-container-shadow-margin);
diff --git a/ui/webui/resources/cr_elements/shared_vars_css.html b/ui/webui/resources/cr_elements/shared_vars_css.html index 110a897..3b87af2 100644 --- a/ui/webui/resources/cr_elements/shared_vars_css.html +++ b/ui/webui/resources/cr_elements/shared_vars_css.html
@@ -239,19 +239,6 @@ --cr-container-shadow-height: 6px; --cr-container-shadow-margin: calc(-1 * var(--cr-container-shadow-height)); - --cr-container-shadow: { - box-shadow: inset 0 5px 6px -3px rgba(0, 0, 0, .4); - height: var(--cr-container-shadow-height); - left: 0; - margin: 0 0 var(--cr-container-shadow-margin); - opacity: 0; - pointer-events: none; - position: relative; - right: 0; - top: 0px; - transition: opacity 500ms; - z-index: 1; - } --cr-container-shadow-max-opacity: 1;