diff options
author | finnur@chromium.org <finnur@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-10-22 19:53:42 +0000 |
---|---|---|
committer | finnur@chromium.org <finnur@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-10-22 19:53:42 +0000 |
commit | 215a7bea17e6931e0ac743e745ff7c16853f37bf (patch) | |
tree | a8de64127a8a6cfbe64350802f4c24f731a64f34 /chrome/browser/ui | |
parent | 8e94246fae6772fa7488d248d52d6664eb2a98cd (diff) | |
download | chromium_src-215a7bea17e6931e0ac743e745ff7c16853f37bf.zip chromium_src-215a7bea17e6931e0ac743e745ff7c16853f37bf.tar.gz chromium_src-215a7bea17e6931e0ac743e745ff7c16853f37bf.tar.bz2 |
Implement sideload wipeout for Extensions.
BUG=154624
TEST=None
Review URL: https://codereview.chromium.org/11189094
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@163350 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/ui')
-rw-r--r-- | chrome/browser/ui/browser_ui_prefs.cc | 3 | ||||
-rw-r--r-- | chrome/browser/ui/views/extensions/disabled_extensions_view.cc | 293 | ||||
-rw-r--r-- | chrome/browser/ui/views/extensions/disabled_extensions_view.h | 70 | ||||
-rw-r--r-- | chrome/browser/ui/views/toolbar_view.cc | 16 | ||||
-rw-r--r-- | chrome/browser/ui/views/toolbar_view.h | 3 | ||||
-rw-r--r-- | chrome/browser/ui/webui/extensions/extension_settings_handler.cc | 43 |
6 files changed, 422 insertions, 6 deletions
diff --git a/chrome/browser/ui/browser_ui_prefs.cc b/chrome/browser/ui/browser_ui_prefs.cc index ad3005a..a401444 100644 --- a/chrome/browser/ui/browser_ui_prefs.cc +++ b/chrome/browser/ui/browser_ui_prefs.cc @@ -26,6 +26,9 @@ void RegisterBrowserUserPrefs(PrefService* prefs) { prefs->RegisterBooleanPref(prefs::kShowHomeButton, false, PrefService::SYNCABLE_PREF); + prefs->RegisterIntegerPref(prefs::kExtensionsSideloadWipeoutBubbleShown, + 0, + PrefService::SYNCABLE_PREF); #if defined(OS_MACOSX) // This really belongs in platform code, but there's no good place to // initialize it between the time when the AppController is created diff --git a/chrome/browser/ui/views/extensions/disabled_extensions_view.cc b/chrome/browser/ui/views/extensions/disabled_extensions_view.cc new file mode 100644 index 0000000..a5b016e --- /dev/null +++ b/chrome/browser/ui/views/extensions/disabled_extensions_view.cc @@ -0,0 +1,293 @@ +// Copyright (c) 2012 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/extensions/disabled_extensions_view.h" + +#include "base/metrics/histogram.h" +#include "base/string_number_conversions.h" +#include "base/utf_string_conversions.h" +#include "chrome/browser/extensions/extension_service.h" +#include "chrome/browser/extensions/extension_system.h" +#include "chrome/browser/ui/browser.h" +#include "chrome/browser/ui/singleton_tabs.h" +#include "chrome/common/extensions/feature_switch.h" +#include "chrome/common/url_constants.h" +#include "content/public/browser/user_metrics.h" +#include "grit/generated_resources.h" +#include "grit/locale_settings.h" +#include "grit/theme_resources.h" +#include "ui/base/accessibility/accessible_view_state.h" +#include "ui/base/l10n/l10n_util.h" +#include "ui/base/resource/resource_bundle.h" +#include "ui/views/controls/button/text_button.h" +#include "ui/views/controls/label.h" +#include "ui/views/controls/image_view.h" +#include "ui/views/controls/link.h" +#include "ui/views/layout/grid_layout.h" +#include "ui/views/layout/layout_constants.h" +#include "ui/views/widget/widget.h" + +using content::UserMetricsAction; + +namespace { + +// Layout constants. +const int kColumnPadding = 4; +const int kExtensionListPadding = 20; +const int kImagePadding = 7; +const int kLeftColumnPadding = 3; +const int kInsetBottomRight = 13; +const int kInsetTopLeft = 14; +const int kHeadlineMessagePadding = 4; +const int kHeadlineRowPadding = 10; +const int kMessageBubblePadding = 11; + +// How many extensions to show in the bubble (max). +const int kMaxExtensionsToShow = 7; + +} // namespace + +//////////////////////////////////////////////////////////////////////////////// +// DisabledExtensionsView + +// static +bool DisabledExtensionsView::MaybeShow(Browser* browser, + views::View* anchor_view) { +#if !defined(OS_WIN) + // We are targeting registry-installed extensions, which is Windows-specific, + // and extensions marked internal and not from the web store, which are mostly + // problematic on Windows. + return false; +#endif + + if (!extensions::FeatureSwitch::sideload_wipeout()->IsEnabled()) + return false; + + static bool done_showing_ui = false; + if (done_showing_ui) + return false; // Only show the bubble once per launch. + + // Fetch all disabled extensions. + ExtensionService* extension_service = + extensions::ExtensionSystem::Get( + browser->profile())->extension_service(); + scoped_ptr<const ExtensionSet> wiped_out( + extension_service->GetWipedOutExtensions()); + if (wiped_out->size()) { + DisabledExtensionsView* bubble_delegate = + new DisabledExtensionsView( + anchor_view, browser, wiped_out.release()); + views::BubbleDelegateView::CreateBubble(bubble_delegate); + bubble_delegate->StartFade(true); + + done_showing_ui = true; + return true; + } + + return false; +} + +DisabledExtensionsView::DisabledExtensionsView( + views::View* anchor_view, + Browser* browser, + const ExtensionSet* wiped_out) + : BubbleDelegateView(anchor_view, views::BubbleBorder::TOP_RIGHT), + browser_(browser), + wiped_out_(wiped_out), + headline_(NULL), + learn_more_(NULL), + settings_button_(NULL), + dismiss_button_(NULL) { + set_close_on_deactivate(false); + set_move_with_anchor(true); + + UMA_HISTOGRAM_COUNTS_100("DisabledExtension.SideloadWipeoutCount", + wiped_out->size()); +} + +DisabledExtensionsView::~DisabledExtensionsView() { +} + +void DisabledExtensionsView::ButtonPressed(views::Button* sender, + const ui::Event& event) { + if (sender == settings_button_) { + content::RecordAction( + UserMetricsAction("DisabledExtension_SettingsButton")); + browser_->OpenURL( + content::OpenURLParams(GURL(chrome::kChromeUIExtensionsURL), + content::Referrer(), + NEW_FOREGROUND_TAB, + content::PAGE_TRANSITION_LINK, + false)); + + } else if (sender == dismiss_button_) { + content::RecordAction(UserMetricsAction("DisabledExtension_Dismiss")); + // No action required. Close will happen below. + } else { + NOTREACHED(); + } + + GetWidget()->Close(); +} + +void DisabledExtensionsView::LinkClicked( + views::Link* source, int event_flags) { + content::RecordAction(UserMetricsAction("DisabledExtension_LearnMore")); + browser_->OpenURL( + content::OpenURLParams(GURL(chrome::kSideloadWipeoutHelpURL), + content::Referrer(), + NEW_FOREGROUND_TAB, + content::PAGE_TRANSITION_LINK, + false)); + + GetWidget()->Close(); +} + +void DisabledExtensionsView::GetAccessibleState( + ui::AccessibleViewState* state) { + state->role = ui::AccessibilityTypes::ROLE_ALERT; +} + +void DisabledExtensionsView::ViewHierarchyChanged( + bool is_add, View* parent, View* child) { + if (is_add && child == this) { + GetWidget()->NotifyAccessibilityEvent( + this, ui::AccessibilityTypes::EVENT_ALERT, true); + } +} + +void DisabledExtensionsView::Init() { + ui::ResourceBundle& rb = ui::ResourceBundle::GetSharedInstance(); + + views::GridLayout* layout = views::GridLayout::CreatePanel(this); + layout->SetInsets(kInsetTopLeft, kInsetTopLeft, + kInsetBottomRight, kInsetBottomRight); + SetLayoutManager(layout); + + const int headline_column_set_id = 0; + views::ColumnSet* top_columns = layout->AddColumnSet(headline_column_set_id); + top_columns->AddColumn(views::GridLayout::LEADING, views::GridLayout::CENTER, + 0, views::GridLayout::USE_PREF, 0, 0); + top_columns->AddPaddingColumn(0, kImagePadding); + top_columns->AddColumn(views::GridLayout::LEADING, views::GridLayout::CENTER, + 0, views::GridLayout::USE_PREF, 0, 0); + top_columns->AddPaddingColumn(1, 0); + layout->StartRow(0, headline_column_set_id); + + views::ImageView* image = new views::ImageView(); + const gfx::ImageSkia* puzzle_piece = + rb.GetImageSkiaNamed(IDR_EXTENSIONS_PUZZLE_PIECE); + image->SetImage(puzzle_piece); + layout->AddView(image); + int left_padding_column = puzzle_piece->width() + kLeftColumnPadding; + + headline_ = new views::Label(); + headline_->SetFont(rb.GetFont(ui::ResourceBundle::MediumFont)); + headline_->SetText(l10n_util::GetStringUTF16( + IDS_OPTIONS_SIDELOAD_WIPEOUT_BUBBLE_HEADLINE)); + layout->AddView(headline_); + + layout->AddPaddingRow(0, kHeadlineRowPadding); + + const int text_column_set_id = 1; + views::ColumnSet* upper_columns = layout->AddColumnSet(text_column_set_id); + upper_columns->AddPaddingColumn(0, left_padding_column); + upper_columns->AddPaddingColumn(0, kColumnPadding); + upper_columns->AddColumn( + views::GridLayout::LEADING, views::GridLayout::LEADING, + 0, views::GridLayout::USE_PREF, 0, 0); + layout->StartRow(0, text_column_set_id); + + views::Label* message = new views::Label(); + message->SetMultiLine(true); + message->SetHorizontalAlignment(views::Label::ALIGN_LEFT); + message->SetText( + l10n_util::GetStringUTF16(IDS_OPTIONS_SIDELOAD_WIPEOUT_WHAT_HAPPENED)); + message->SizeToFit(views::Widget::GetLocalizedContentsWidth( + IDS_DISABLED_EXTENSIONS_BUBBLE_WIDTH_CHARS)); + layout->AddView(message); + + const int extension_list_column_set_id = 2; + views::ColumnSet* middle_columns = + layout->AddColumnSet(extension_list_column_set_id); + middle_columns->AddPaddingColumn(0, left_padding_column); + middle_columns->AddPaddingColumn(0, kExtensionListPadding); + middle_columns->AddColumn( + views::GridLayout::LEADING, views::GridLayout::CENTER, + 0, views::GridLayout::USE_PREF, 0, 0); + + layout->StartRowWithPadding(0, extension_list_column_set_id, + 0, kHeadlineMessagePadding); + views::Label* extensions = new views::Label(); + extensions->SetMultiLine(true); + extensions->SetHorizontalAlignment(views::Label::ALIGN_LEFT); + extensions->SetFont(extensions->font().DeriveFont(0, gfx::Font::ITALIC)); + + std::vector<string16> extension_list; + int count = 0; + for (ExtensionSet::const_iterator iter = wiped_out_->begin(); + iter != wiped_out_->end() && count < kMaxExtensionsToShow; ++iter) { + const extensions::Extension* extension = *iter; + extension_list.push_back(ASCIIToUTF16("- ") + + UTF8ToUTF16(extension->name())); + count++; + } + + if (count == kMaxExtensionsToShow) { + string16 difference = + base::IntToString16(wiped_out_->size() - kMaxExtensionsToShow); + extension_list.push_back(ASCIIToUTF16("- ") + + l10n_util::GetStringFUTF16(IDS_OPTIONS_SIDELOAD_WIPEOUT_OVERFLOW, + difference)); + } + + extensions->SetText(JoinString(extension_list, ASCIIToUTF16("\n"))); + extensions->SizeToFit(views::Widget::GetLocalizedContentsWidth( + IDS_DISABLED_EXTENSIONS_BUBBLE_WIDTH_CHARS)); + layout->AddView(extensions); + + layout->StartRowWithPadding( + 0, text_column_set_id, 0, kHeadlineMessagePadding); + views::Label* recourse = new views::Label(); + recourse->SetMultiLine(true); + recourse->SetHorizontalAlignment(views::Label::ALIGN_LEFT); + recourse->SetText( + l10n_util::GetStringUTF16(IDS_OPTIONS_SIDELOAD_WIPEOUT_RECOURSE)); + recourse->SizeToFit(views::Widget::GetLocalizedContentsWidth( + IDS_DISABLED_EXTENSIONS_BUBBLE_WIDTH_CHARS)); + layout->AddView(recourse); + + const int action_row_column_set_id = 3; + views::ColumnSet* bottom_columns = + layout->AddColumnSet(action_row_column_set_id); + bottom_columns->AddPaddingColumn(0, left_padding_column); + bottom_columns->AddPaddingColumn(0, kColumnPadding); + bottom_columns->AddColumn(views::GridLayout::LEADING, + views::GridLayout::CENTER, 0, views::GridLayout::USE_PREF, 0, 0); + bottom_columns->AddPaddingColumn(1, views::kRelatedButtonHSpacing); + bottom_columns->AddColumn(views::GridLayout::TRAILING, + views::GridLayout::CENTER, 0, views::GridLayout::USE_PREF, 0, 0); + bottom_columns->AddPaddingColumn(0, views::kRelatedButtonHSpacing); + bottom_columns->AddColumn(views::GridLayout::TRAILING, + views::GridLayout::CENTER, 0, views::GridLayout::USE_PREF, 0, 0); + layout->StartRowWithPadding(0, action_row_column_set_id, + 0, kMessageBubblePadding); + + learn_more_ = new views::Link(l10n_util::GetStringUTF16(IDS_LEARN_MORE)); + learn_more_->set_listener(this); + layout->AddView(learn_more_); + + settings_button_ = new views::NativeTextButton(this, + l10n_util::GetStringUTF16(IDS_OPTIONS_SIDELOAD_WIPEOUT_SETTINGS)); + settings_button_->SetIsDefault(true); + layout->AddView(settings_button_); + dismiss_button_ = new views::NativeTextButton(this, + l10n_util::GetStringUTF16(IDS_OPTIONS_SIDELOAD_WIPEOUT_DISMISS)); + dismiss_button_->SetFont( + dismiss_button_->font().DeriveFont(0, gfx::Font::BOLD)); + layout->AddView(dismiss_button_); + + content::RecordAction( + UserMetricsAction("DisabledExtensionNotificationShown")); +} diff --git a/chrome/browser/ui/views/extensions/disabled_extensions_view.h b/chrome/browser/ui/views/extensions/disabled_extensions_view.h new file mode 100644 index 0000000..6af17bd --- /dev/null +++ b/chrome/browser/ui/views/extensions/disabled_extensions_view.h @@ -0,0 +1,70 @@ +// Copyright (c) 2012 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_EXTENSIONS_DISABLED_EXTENSIONS_VIEW_H_ +#define CHROME_BROWSER_UI_VIEWS_EXTENSIONS_DISABLED_EXTENSIONS_VIEW_H_ + +#include "ui/views/bubble/bubble_delegate.h" +#include "ui/views/controls/button/button.h" +#include "ui/views/controls/link_listener.h" +#include "chrome/common/extensions/extension_set.h" + +class Browser; + +namespace views { +class Label; +class Link; +class NativeTextButton; +} + +// This is the class that implements the UI for the bubble showing which +// extensions have been automatically disabled by the sideload-wipeout +// initiative. +class DisabledExtensionsView : public views::BubbleDelegateView, + public views::ButtonListener, + public views::LinkListener { + public: + DisabledExtensionsView(views::View* anchor_view, + Browser* browser, + const ExtensionSet* wiped_out); + + // Show the Disabled Extension bubble, if needed. Returns true if the bubble + // was shown. + static bool MaybeShow(Browser* browser, views::View* anchor_view); + + protected: + // views::BubbleDelegateView overrides: + virtual void Init() OVERRIDE; + + private: + virtual ~DisabledExtensionsView(); + + // views::ButtonListener implementation. + virtual void ButtonPressed(views::Button* sender, + const ui::Event& event) OVERRIDE; + + // views::LinkListener implementation. + void LinkClicked(views::Link* source, int event_flags) OVERRIDE; + + // views::View implementation. + virtual void GetAccessibleState(ui::AccessibleViewState* state) OVERRIDE; + virtual void ViewHierarchyChanged(bool is_add, + View* parent, + View* child) OVERRIDE; + + Browser* browser_; + + // The set of extensions that have been wiped out by sideload wipeout. + scoped_ptr<const ExtensionSet> wiped_out_; + + // The headline and buttons on the bubble. + views::Label* headline_; + views::Link* learn_more_; + views::NativeTextButton* settings_button_; + views::NativeTextButton* dismiss_button_; + + DISALLOW_COPY_AND_ASSIGN(DisabledExtensionsView); +}; + +#endif // CHROME_BROWSER_UI_VIEWS_EXTENSIONS_DISABLED_EXTENSIONS_VIEW_H_ diff --git a/chrome/browser/ui/views/toolbar_view.cc b/chrome/browser/ui/views/toolbar_view.cc index a558a63..67eae60 100644 --- a/chrome/browser/ui/views/toolbar_view.cc +++ b/chrome/browser/ui/views/toolbar_view.cc @@ -32,6 +32,7 @@ #include "chrome/browser/ui/toolbar/wrench_menu_model.h" #include "chrome/browser/ui/view_ids.h" #include "chrome/browser/ui/views/browser_actions_container.h" +#include "chrome/browser/ui/views/extensions/disabled_extensions_view.h" #include "chrome/browser/ui/views/location_bar/location_bar_container.h" #include "chrome/browser/ui/views/location_bar/page_action_image_view.h" #include "chrome/browser/ui/views/wrench_menu.h" @@ -110,6 +111,9 @@ const int kSearchTopButtonSpacing = 3; const int kSearchTopLocationBarSpacing = 2; const int kSearchToolbarSpacing = 5; +// How often to show the disabled extension (sideload wipeout) bubble. +const int kShowSideloadWipeoutBubbleMax = 3; + gfx::ImageSkia* kPopupBackgroundEdge = NULL; // The omnibox border has some additional shadow, so we use less vertical @@ -294,9 +298,8 @@ void ToolbarView::Init(views::View* location_bar_parent, app_menu_->set_id(VIEW_ID_APP_MENU); // Add any necessary badges to the menu item based on the system state. - if (ShouldShowUpgradeRecommended() || ShouldShowIncompatibilityWarning()) { + if (ShouldShowUpgradeRecommended() || ShouldShowIncompatibilityWarning()) UpdateAppMenuState(); - } LoadImages(); // Always add children in order from left to right, for accessibility. @@ -310,6 +313,10 @@ void ToolbarView::Init(views::View* location_bar_parent, location_bar_->Init(popup_parent_view); show_home_button_.Init(prefs::kShowHomeButton, browser_->profile()->GetPrefs(), this); + sideload_wipeout_bubble_shown_.Init( + prefs::kExtensionsSideloadWipeoutBubbleShown, + browser_->profile()->GetPrefs(), NULL); + browser_actions_->Init(); // Accessibility specific tooltip text. @@ -319,6 +326,11 @@ void ToolbarView::Init(views::View* location_bar_parent, forward_->SetTooltipText( l10n_util::GetStringUTF16(IDS_ACCNAME_TOOLTIP_FORWARD)); } + + int bubble_shown_count = sideload_wipeout_bubble_shown_.GetValue(); + if (bubble_shown_count < kShowSideloadWipeoutBubbleMax && + DisabledExtensionsView::MaybeShow(browser_, app_menu_)) + sideload_wipeout_bubble_shown_.SetValue(++bubble_shown_count); } void ToolbarView::Update(WebContents* tab, bool should_restore_state) { diff --git a/chrome/browser/ui/views/toolbar_view.h b/chrome/browser/ui/views/toolbar_view.h index 7e27ab3..e2912c0 100644 --- a/chrome/browser/ui/views/toolbar_view.h +++ b/chrome/browser/ui/views/toolbar_view.h @@ -238,6 +238,9 @@ class ToolbarView : public views::AccessiblePaneView, // Controls whether or not a home button should be shown on the toolbar. BooleanPrefMember show_home_button_; + // A pref that counts how often the bubble has been shown. + IntegerPrefMember sideload_wipeout_bubble_shown_; + // The display mode used when laying out the toolbar. DisplayMode display_mode_; diff --git a/chrome/browser/ui/webui/extensions/extension_settings_handler.cc b/chrome/browser/ui/webui/extensions/extension_settings_handler.cc index 4daa66d..3d269c5 100644 --- a/chrome/browser/ui/webui/extensions/extension_settings_handler.cc +++ b/chrome/browser/ui/webui/extensions/extension_settings_handler.cc @@ -45,6 +45,7 @@ #include "chrome/common/extensions/extension_constants.h" #include "chrome/common/extensions/extension_icon_set.h" #include "chrome/common/extensions/extension_set.h" +#include "chrome/common/extensions/feature_switch.h" #include "chrome/common/pref_names.h" #include "chrome/common/url_constants.h" #include "content/public/browser/notification_service.h" @@ -145,6 +146,26 @@ DictionaryValue* ExtensionSettingsHandler::CreateExtensionDetailValue( extension_data->SetBoolean("homepageProvided", extension->GetHomepageURL().is_valid()); + string16 automatically_disabled_text; + int disable_reasons = + extension_service_->extension_prefs()->GetDisableReasons(extension->id()); + if ((disable_reasons & Extension::DISABLE_SIDELOAD_WIPEOUT) != 0) { + automatically_disabled_text = l10n_util::GetStringUTF16( + IDS_OPTIONS_SIDELOAD_WIPEOUT_AUTOMATIC_DISABLE); + } + extension_data->SetString("disableReason", automatically_disabled_text); + + string16 location_text; + if (extension->location() == Extension::INTERNAL && + !extension->from_webstore()) { + location_text = l10n_util::GetStringUTF16( + IDS_OPTIONS_SIDELOAD_WIPEOUT_DISABLE_REASON_UNKNOWN); + } else if (extension->location() == Extension::EXTERNAL_REGISTRY) { + location_text = l10n_util::GetStringUTF16( + IDS_OPTIONS_SIDELOAD_WIPEOUT_DISABLE_REASON_3RD_PARTY); + } + extension_data->SetString("locationText", location_text); + // Determine the sort order: Extensions loaded through --load-extensions show // up at the top. Disabled extensions show up at the bottom. if (extension->location() == Extension::LOAD) @@ -284,6 +305,12 @@ void ExtensionSettingsHandler::GetLocalizedValues( l10n_util::GetStringUTF16(IDS_EXTENSIONS_POLICY_CONTROLLED)); localized_strings->SetString("extensionSettingsManagedMode", l10n_util::GetStringUTF16(IDS_EXTENSIONS_LOCKED_MANAGED_MODE)); + localized_strings->SetString("extensionSettingsSideloadWipeout", + l10n_util::GetStringUTF16(IDS_OPTIONS_SIDELOAD_WIPEOUT_BANNER)); + localized_strings->SetString("sideloadWipeoutUrl", + chrome::kSideloadWipeoutHelpURL); + localized_strings->SetString("sideloadWipoutLearnMore", + l10n_util::GetStringUTF16(IDS_LEARN_MORE)); localized_strings->SetString("extensionSettingsShowButton", l10n_util::GetStringUTF16(IDS_EXTENSIONS_SHOW_BUTTON)); localized_strings->SetString("extensionSettingsLoadUnpackedButton", @@ -523,12 +550,20 @@ void ExtensionSettingsHandler::HandleRequestExtensionsData( results.SetBoolean("developerMode", false); } else { results.SetBoolean("managedMode", false); - Profile* profile = Profile::FromWebUI(web_ui()); - bool developer_mode = - profile->GetPrefs()->GetBoolean(prefs::kExtensionsUIDeveloperMode); - results.SetBoolean("developerMode", developer_mode); + Profile* profile = Profile::FromWebUI(web_ui()); + bool developer_mode = + profile->GetPrefs()->GetBoolean(prefs::kExtensionsUIDeveloperMode); + results.SetBoolean("developerMode", developer_mode); } + // Check to see if we have any wiped out extensions. + Profile* profile = Profile::FromWebUI(web_ui()); + ExtensionService* extension_service = + extensions::ExtensionSystem::Get(profile)->extension_service(); + scoped_ptr<const ExtensionSet> wiped_out( + extension_service->GetWipedOutExtensions()); + results.SetBoolean("showDisabledExtensionsWarning", wiped_out->size() > 0); + bool load_unpacked_disabled = extension_service_->extension_prefs()->ExtensionsBlacklistedByDefault(); results.SetBoolean("loadUnpackedDisabled", load_unpacked_disabled); |