1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "chrome/browser/three_d_api_observer.h"
7 #include "base/metrics/histogram.h"
8 #include "chrome/browser/infobars/confirm_infobar_delegate.h"
9 #include "chrome/browser/infobars/infobar.h"
10 #include "chrome/browser/infobars/infobar_service.h"
11 #include "chrome/browser/tab_contents/tab_util.h"
12 #include "content/public/browser/gpu_data_manager.h"
13 #include "grit/generated_resources.h"
14 #include "ui/base/l10n/l10n_util.h"
17 // ThreeDAPIInfoBarDelegate ---------------------------------------------------
19 class ThreeDAPIInfoBarDelegate
: public ConfirmInfoBarDelegate
{
21 // Creates a 3D API infobar and delegate and adds the infobar to
23 static void Create(InfoBarService
* infobar_service
,
25 content::ThreeDAPIType requester
);
28 enum DismissalHistogram
{
31 CLOSED_WITHOUT_ACTION
,
35 ThreeDAPIInfoBarDelegate(const GURL
& url
, content::ThreeDAPIType requester
);
36 virtual ~ThreeDAPIInfoBarDelegate();
38 // ConfirmInfoBarDelegate:
39 virtual bool EqualsDelegate(InfoBarDelegate
* delegate
) const OVERRIDE
;
40 virtual ThreeDAPIInfoBarDelegate
* AsThreeDAPIInfoBarDelegate() OVERRIDE
;
41 virtual base::string16
GetMessageText() const OVERRIDE
;
42 virtual base::string16
GetButtonLabel(InfoBarButton button
) const OVERRIDE
;
43 virtual bool Accept() OVERRIDE
;
44 virtual bool Cancel() OVERRIDE
;
45 virtual base::string16
GetLinkText() const OVERRIDE
;
46 virtual bool LinkClicked(WindowOpenDisposition disposition
) OVERRIDE
;
49 content::ThreeDAPIType requester_
;
50 // Basically indicates whether the infobar was displayed at all, or
51 // was a temporary instance thrown away by the InfobarService.
52 mutable bool message_text_queried_
;
55 DISALLOW_COPY_AND_ASSIGN(ThreeDAPIInfoBarDelegate
);
59 void ThreeDAPIInfoBarDelegate::Create(InfoBarService
* infobar_service
,
61 content::ThreeDAPIType requester
) {
63 return; // NULL for apps.
64 infobar_service
->AddInfoBar(ConfirmInfoBarDelegate::CreateInfoBar(
65 scoped_ptr
<ConfirmInfoBarDelegate
>(
66 new ThreeDAPIInfoBarDelegate(url
, requester
))));
69 ThreeDAPIInfoBarDelegate::ThreeDAPIInfoBarDelegate(
71 content::ThreeDAPIType requester
)
72 : ConfirmInfoBarDelegate(),
74 requester_(requester
),
75 message_text_queried_(false),
76 action_taken_(false) {
79 ThreeDAPIInfoBarDelegate::~ThreeDAPIInfoBarDelegate() {
80 if (message_text_queried_
&& !action_taken_
) {
81 UMA_HISTOGRAM_ENUMERATION("GPU.ThreeDAPIInfoBarDismissal",
82 CLOSED_WITHOUT_ACTION
, DISMISSAL_MAX
);
86 bool ThreeDAPIInfoBarDelegate::EqualsDelegate(InfoBarDelegate
* delegate
) const {
87 // For the time being, if a given web page is actually using both
88 // WebGL and Pepper 3D and both APIs are blocked, just leave the
89 // first infobar up. If the user selects "try again", both APIs will
90 // be unblocked and the web page reload will succeed.
91 return (delegate
->AsThreeDAPIInfoBarDelegate() != NULL
);
94 ThreeDAPIInfoBarDelegate
*
95 ThreeDAPIInfoBarDelegate::AsThreeDAPIInfoBarDelegate() {
99 base::string16
ThreeDAPIInfoBarDelegate::GetMessageText() const {
100 message_text_queried_
= true;
102 base::string16 api_name
;
103 switch (requester_
) {
104 case content::THREE_D_API_TYPE_WEBGL
:
105 api_name
= l10n_util::GetStringUTF16(IDS_3D_APIS_WEBGL_NAME
);
107 case content::THREE_D_API_TYPE_PEPPER_3D
:
108 api_name
= l10n_util::GetStringUTF16(IDS_3D_APIS_PEPPER_3D_NAME
);
112 return l10n_util::GetStringFUTF16(IDS_3D_APIS_BLOCKED_TEXT
,
116 base::string16
ThreeDAPIInfoBarDelegate::GetButtonLabel(
117 InfoBarButton button
) const {
118 return l10n_util::GetStringUTF16((button
== BUTTON_OK
) ?
119 IDS_3D_APIS_BLOCKED_OK_BUTTON_LABEL
:
120 IDS_3D_APIS_BLOCKED_TRY_AGAIN_BUTTON_LABEL
);
123 bool ThreeDAPIInfoBarDelegate::Accept() {
124 action_taken_
= true;
125 UMA_HISTOGRAM_ENUMERATION("GPU.ThreeDAPIInfoBarDismissal", IGNORED
,
130 bool ThreeDAPIInfoBarDelegate::Cancel() {
131 action_taken_
= true;
132 UMA_HISTOGRAM_ENUMERATION("GPU.ThreeDAPIInfoBarDismissal", RELOADED
,
134 content::GpuDataManager::GetInstance()->UnblockDomainFrom3DAPIs(url_
);
135 web_contents()->GetController().Reload(true);
139 base::string16
ThreeDAPIInfoBarDelegate::GetLinkText() const {
140 return l10n_util::GetStringUTF16(IDS_LEARN_MORE
);
143 bool ThreeDAPIInfoBarDelegate::LinkClicked(WindowOpenDisposition disposition
) {
144 web_contents()->OpenURL(content::OpenURLParams(
145 GURL("https://support.google.com/chrome/?p=ib_webgl"),
147 (disposition
== CURRENT_TAB
) ? NEW_FOREGROUND_TAB
: disposition
,
148 content::PAGE_TRANSITION_LINK
,
154 // ThreeDAPIObserver ----------------------------------------------------------
156 ThreeDAPIObserver::ThreeDAPIObserver() {
157 content::GpuDataManager::GetInstance()->AddObserver(this);
160 ThreeDAPIObserver::~ThreeDAPIObserver() {
161 content::GpuDataManager::GetInstance()->RemoveObserver(this);
164 void ThreeDAPIObserver::DidBlock3DAPIs(const GURL
& url
,
165 int render_process_id
,
167 content::ThreeDAPIType requester
) {
168 content::WebContents
* web_contents
= tab_util::GetWebContentsByID(
169 render_process_id
, render_view_id
);
172 ThreeDAPIInfoBarDelegate::Create(
173 InfoBarService::FromWebContents(web_contents
), url
, requester
);