Bug 1386735 - Add additional preferences to Top Sites settings. r?mcomella draft
authorChenxia Liu <liuche@mozilla.com>
Wed, 30 Aug 2017 20:01:48 -0700
changeset 657724 68268791fb653c2ddab566bf10b5e0a659c2fc2f
parent 657723 76ddcd29a5a45977e2f814ea799dc3bea92aa7af
child 657725 976ef6e156b975aee8d7d70fb9b186d16021ea41
child 657763 de541c75af043bd39dfb57c23a092b58aee4da33
push id77610
push usercliu@mozilla.com
push dateFri, 01 Sep 2017 21:58:48 +0000
reviewersmcomella
bugs1386735
milestone57.0a1
Bug 1386735 - Add additional preferences to Top Sites settings. r?mcomella MozReview-Commit-ID: ADwLLbO41RN
mobile/android/app/src/main/res/layout/preference_topsites_panel_dialog.xml
mobile/android/app/src/main/res/values/attrs.xml
mobile/android/app/src/photon/res/values/dimens.xml
mobile/android/app/src/photon/res/values/styles.xml
mobile/android/base/java/org/mozilla/gecko/activitystream/homepanel/ActivityStreamPanel.java
mobile/android/base/java/org/mozilla/gecko/activitystream/homepanel/StreamRecyclerAdapter.java
mobile/android/base/java/org/mozilla/gecko/preferences/PanelsPreferenceCategory.java
mobile/android/base/java/org/mozilla/gecko/preferences/TopSitesPanelsPreference.java
mobile/android/base/java/org/mozilla/gecko/widget/SwitchPreferenceView.java
mobile/android/base/locales/en-US/android_strings.dtd
mobile/android/base/moz.build
mobile/android/base/strings.xml.in
new file mode 100644
--- /dev/null
+++ b/mobile/android/app/src/main/res/layout/preference_topsites_panel_dialog.xml
@@ -0,0 +1,51 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- This Source Code Form is subject to the terms of the Mozilla Public
+   - License, v. 2.0. If a copy of the MPL was not distributed with this
+   - file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:gecko="http://schemas.android.com/apk/res-auto"
+    android:orientation="vertical"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent">
+
+    <View
+        android:layout_width="match_parent"
+        android:layout_height="1dp"
+        android:background="@color/toolbar_divider_grey"/>
+
+    <TextView
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        style="@style/Gecko.PreferenceCategory"
+        android:text="@string/pref_dialog_activitystream_header_content"/>
+
+    <org.mozilla.gecko.widget.SwitchPreferenceView
+        android:id="@+id/preference_pocket"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        style="@style/Gecko.SwitchPreferenceView"
+        android:paddingBottom="@dimen/dialog_switchpreferenceview_padding"
+        android:text="@string/activity_stream_topstories"
+        gecko:androidPreferenceKey="pref_activitystream_pocket_enabled"
+        gecko:defaultValue="true"/>
+
+    <org.mozilla.gecko.widget.SwitchPreferenceView
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        style="@style/Gecko.SwitchPreferenceView"
+        android:paddingBottom="@dimen/dialog_switchpreferenceview_padding"
+        android:text="@string/pref_dialog_activitystream_recentBookmarks"
+        gecko:androidPreferenceKey="pref_activitystream_recentbookmarks_enabled"
+        gecko:defaultValue="true"/>
+
+    <org.mozilla.gecko.widget.SwitchPreferenceView
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        style="@style/Gecko.SwitchPreferenceView"
+        android:paddingBottom="@dimen/dialog_switchpreferenceview_padding"
+        android:text="@string/pref_dialog_activitystream_visited"
+        gecko:androidPreferenceKey="pref_activitystream_visited_enabled"
+        gecko:defaultValue="true"/>
+
+</LinearLayout>
\ No newline at end of file
--- a/mobile/android/app/src/main/res/values/attrs.xml
+++ b/mobile/android/app/src/main/res/values/attrs.xml
@@ -74,16 +74,21 @@
         <attr name="entryValues" format="string"/>
         <attr name="initialValues" format="string"/>
     </declare-styleable>
 
     <declare-styleable name="MultiPrefMultiChoicePreference">
         <attr name="entryKeys" format="string"/>
     </declare-styleable>
 
+    <declare-styleable name="SwitchPreferenceView">
+        <attr name="androidPreferenceKey" format="string"/>
+        <attr name="defaultValue" format="boolean"/>
+    </declare-styleable>
+
     <declare-styleable name="TabsLayout">
         <attr name="tabs">
             <flag name="tabs_normal" value="0x00" />
             <flag name="tabs_private" value ="0x01" />
         </attr>
     </declare-styleable>
 
     <declare-styleable name="TabCounter">
--- a/mobile/android/app/src/photon/res/values/dimens.xml
+++ b/mobile/android/app/src/photon/res/values/dimens.xml
@@ -253,9 +253,12 @@
 
     <!-- Custom tabs -->
     <dimen name="custom_tab_action_button_size">56dp</dimen>
     <dimen name="custom_tab_action_button_padding">16dp</dimen>
 
     <!-- Full bookmark management -->
     <dimen name="bookmark_folder_first_child_padding">40dp</dimen>
     <dimen name="bookmark_folder_child_padding">16dp</dimen>
+
+    <!-- Dialogs -->
+    <dimen name="dialog_switchpreferenceview_padding">24dp</dimen>
 </resources>
--- a/mobile/android/app/src/photon/res/values/styles.xml
+++ b/mobile/android/app/src/photon/res/values/styles.xml
@@ -77,16 +77,29 @@
         <item name="android:checkMark">?android:attr/listChoiceIndicatorMultiple</item>
         <item name="android:ellipsize">marquee</item>
     </style>
 
     <style name="Widget.Spinner" parent="android:style/Widget.Spinner">
         <item name="android:minWidth">@dimen/doorhanger_input_width</item>
     </style>
 
+    <style name="Gecko.PreferenceCategory" parent="TextAppearance.AppCompat.Body2">
+        <item name="android:textColor">@color/fennec_ui_accent</item>
+        <item name="android:padding">24dp</item>
+    </style>
+
+    <style name="Gecko.SwitchPreferenceView" parent="TextAppearance">
+        <item name="android:textSize">16sp</item>
+        <item name="android:paddingStart">@dimen/dialog_switchpreferenceview_padding</item>
+        <item name="android:paddingLeft">@dimen/dialog_switchpreferenceview_padding</item>
+        <item name="android:paddingEnd">@dimen/dialog_switchpreferenceview_padding</item>
+        <item name="android:paddingRight">@dimen/dialog_switchpreferenceview_padding</item>
+    </style>
+
     <style name="Widget.GeckoMenuListView" parent="Widget.ListView">
         <item name="android:listSelector">@drawable/menu_item_action_bar_bg</item>
         <item name="android:divider">@null</item>
         <item name="android:dividerHeight">0dp</item>
     </style>
 
     <style name="Widget.MenuItemActionBar">
         <item name="android:padding">10dip</item>
--- a/mobile/android/base/java/org/mozilla/gecko/activitystream/homepanel/ActivityStreamPanel.java
+++ b/mobile/android/base/java/org/mozilla/gecko/activitystream/homepanel/ActivityStreamPanel.java
@@ -1,26 +1,28 @@
 /* -*- Mode: Java; c-basic-offset: 4; tab-width: 20; indent-tabs-mode: nil; -*-
  * This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
  package org.mozilla.gecko.activitystream.homepanel;
 
 import android.content.Context;
+import android.content.SharedPreferences;
 import android.content.res.Resources;
 import android.database.Cursor;
 import android.os.Bundle;
 import android.support.v4.app.LoaderManager;
 import android.support.v4.content.ContextCompat;
 import android.support.v4.content.Loader;
 import android.support.v7.widget.LinearLayoutManager;
 import android.support.v7.widget.RecyclerView;
 import android.util.AttributeSet;
 import android.widget.FrameLayout;
 
+import org.mozilla.gecko.GeckoSharedPrefs;
 import org.mozilla.gecko.R;
 import org.mozilla.gecko.activitystream.ActivityStreamTelemetry;
 import org.mozilla.gecko.activitystream.homepanel.model.TopStory;
 import org.mozilla.gecko.activitystream.homepanel.topstories.PocketStoriesLoader;
 import org.mozilla.gecko.db.BrowserDB;
 import org.mozilla.gecko.fxa.FirefoxAccounts;
 import org.mozilla.gecko.home.HomePager;
 import org.mozilla.gecko.activitystream.homepanel.model.Highlight;
@@ -45,27 +47,33 @@ public class ActivityStreamPanel extends
     /**
      * Number of highlights that should be returned (max).
      */
     private static final int HIGHLIGHTS_LIMIT = 10;
 
     public static final int TOP_SITES_COLUMNS = 4;
     public static final int TOP_SITES_ROWS = 2;
 
+    public static final String PREF_POCKET_ENABLED = "pref_activitystream_pocket_enabled";
+    public static final String PREF_VISITED_ENABLED = "pref_activitystream_visited_enabled";
+    public static final String PREF_BOOKMARKS_ENABLED = "pref_activitystream_recentbookmarks_enabled";
+
     private int desiredTileWidth;
     private int tileMargin;
+    private final SharedPreferences sharedPreferences;
 
     public ActivityStreamPanel(Context context, AttributeSet attrs) {
         super(context, attrs);
 
         setBackgroundColor(ContextCompat.getColor(context, R.color.about_page_header_grey));
 
         inflate(context, R.layout.as_content, this);
 
         adapter = new StreamRecyclerAdapter();
+        sharedPreferences = GeckoSharedPrefs.forProfile(context);
 
         final RecyclerView rv = (RecyclerView) findViewById(R.id.activity_stream_main_recyclerview);
 
         rv.setAdapter(adapter);
         rv.setLayoutManager(new LinearLayoutManager(getContext()));
         rv.setHasFixedSize(true);
         // Override item animations to avoid horrible topsites refreshing
         rv.setItemAnimator(new StreamItemAnimator());
@@ -86,18 +94,21 @@ public class ActivityStreamPanel extends
     }
 
     void setOnUrlOpenListeners(HomePager.OnUrlOpenListener onUrlOpenListener, HomePager.OnUrlOpenInBackgroundListener onUrlOpenInBackgroundListener) {
         adapter.setOnUrlOpenListeners(onUrlOpenListener, onUrlOpenInBackgroundListener);
     }
 
     public void load(LoaderManager lm) {
         lm.initLoader(LOADER_ID_TOPSITES, null, new TopSitesCallback());
-        lm.initLoader(LOADER_ID_HIGHLIGHTS, null, new HighlightsCallbacks());
-        if (StreamRecyclerAdapter.POCKET_ENABLED) {
+        if (sharedPreferences.getBoolean(PREF_BOOKMARKS_ENABLED, true) || sharedPreferences.getBoolean(PREF_VISITED_ENABLED, true)) {
+            lm.initLoader(LOADER_ID_HIGHLIGHTS, null, new HighlightsCallbacks());
+        }
+
+        if (sharedPreferences.getBoolean(PREF_POCKET_ENABLED, true)) {
             lm.initLoader(LOADER_ID_POCKET, null, new PocketStoriesCallbacks());
         }
 
     }
 
     public void unload() {
         adapter.swapHighlights(Collections.<Highlight>emptyList());
 
--- a/mobile/android/base/java/org/mozilla/gecko/activitystream/homepanel/StreamRecyclerAdapter.java
+++ b/mobile/android/base/java/org/mozilla/gecko/activitystream/homepanel/StreamRecyclerAdapter.java
@@ -1,26 +1,29 @@
 /* -*- Mode: Java; c-basic-offset: 4; tab-width: 20; indent-tabs-mode: nil; -*-
  * This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 package org.mozilla.gecko.activitystream.homepanel;
 
+import android.content.SharedPreferences;
 import android.database.Cursor;
 import android.support.annotation.NonNull;
 import android.support.v7.widget.RecyclerView;
 import android.util.Log;
 import android.view.LayoutInflater;
 import android.view.View;
 import android.view.ViewGroup;
 
+import org.mozilla.gecko.GeckoSharedPrefs;
 import org.mozilla.gecko.R;
 import org.mozilla.gecko.Telemetry;
 import org.mozilla.gecko.TelemetryContract;
+import org.mozilla.gecko.activitystream.ActivityStream;
 import org.mozilla.gecko.activitystream.ActivityStreamTelemetry;
 import org.mozilla.gecko.activitystream.homepanel.menu.ActivityStreamContextMenu;
 import org.mozilla.gecko.activitystream.homepanel.model.RowModel;
 import org.mozilla.gecko.activitystream.homepanel.model.WebpageRowModel;
 import org.mozilla.gecko.activitystream.homepanel.stream.TopPanelRow;
 import org.mozilla.gecko.activitystream.homepanel.model.TopStory;
 import org.mozilla.gecko.activitystream.homepanel.topstories.PocketStoriesLoader;
 import org.mozilla.gecko.home.HomePager;
@@ -46,19 +49,16 @@ public class StreamRecyclerAdapter exten
         RecyclerViewClickSupport.OnItemLongClickListener, StreamHighlightItemRowContextMenuListener {
 
     private static final String LOGTAG = StringUtils.safeSubstring("Gecko" + StreamRecyclerAdapter.class.getSimpleName(), 0, 23);
 
     private Cursor topSitesCursor;
     private List<RowModel> recyclerViewModel; // List of item types backing this RecyclerView.
     private List<TopStory> topStoriesQueue;
 
-    // TODO: Replace temporary pref placeholder with pref
-    public static final boolean POCKET_ENABLED = false;
-
     private final RowItemType[] FIXED_ROWS = {RowItemType.TOP_PANEL, RowItemType.WELCOME, RowItemType.TOP_STORIES_TITLE, RowItemType.HIGHLIGHTS_TITLE};
     private final int MAX_TOP_STORIES = 3;
 
     private HomePager.OnUrlOpenListener onUrlOpenListener;
     private HomePager.OnUrlOpenInBackgroundListener onUrlOpenInBackgroundListener;
 
     private int tiles;
     private int tilesSize;
@@ -122,25 +122,29 @@ public class StreamRecyclerAdapter exten
 
     @Override
     public StreamViewHolder onCreateViewHolder(ViewGroup parent, final int type) {
         final LayoutInflater inflater = LayoutInflater.from(parent.getContext());
 
         if (type == RowItemType.TOP_PANEL.getViewType()) {
             return new TopPanelRow(inflater.inflate(TopPanelRow.LAYOUT_ID, parent, false), onUrlOpenListener, onUrlOpenInBackgroundListener);
         } else if (type == RowItemType.TOP_STORIES_TITLE.getViewType()) {
-            return new StreamTitleRow(inflater.inflate(StreamTitleRow.LAYOUT_ID, parent, false), R.string.activity_stream_topstories, POCKET_ENABLED);
+            final boolean pocketEnabled = GeckoSharedPrefs.forProfile(parent.getContext()).getBoolean(ActivityStreamPanel.PREF_POCKET_ENABLED, true);
+            return new StreamTitleRow(inflater.inflate(StreamTitleRow.LAYOUT_ID, parent, false), R.string.activity_stream_topstories, pocketEnabled);
         } else if (type == RowItemType.TOP_STORIES_ITEM.getViewType()) {
             return new WebpageItemRow(inflater.inflate(WebpageItemRow.LAYOUT_ID, parent, false), this);
         } else if (type == RowItemType.WELCOME.getViewType()) {
             return new WelcomePanelRow(inflater.inflate(WelcomePanelRow.LAYOUT_ID, parent, false), this);
         } else if (type == RowItemType.HIGHLIGHT_ITEM.getViewType()) {
             return new WebpageItemRow(inflater.inflate(WebpageItemRow.LAYOUT_ID, parent, false), this);
         } else if (type == RowItemType.HIGHLIGHTS_TITLE.getViewType()) {
-            return new StreamTitleRow(inflater.inflate(StreamTitleRow.LAYOUT_ID, parent, false), R.string.activity_stream_highlights, true);
+            final SharedPreferences sharedPreferences = GeckoSharedPrefs.forProfile(parent.getContext());
+            final boolean bookmarksEnabled = sharedPreferences.getBoolean(ActivityStreamPanel.PREF_BOOKMARKS_ENABLED, true);
+            final boolean visitedEnabled = sharedPreferences.getBoolean(ActivityStreamPanel.PREF_VISITED_ENABLED, true);
+            return new StreamTitleRow(inflater.inflate(StreamTitleRow.LAYOUT_ID, parent, false), R.string.activity_stream_highlights, bookmarksEnabled || visitedEnabled);
         } else {
             throw new IllegalStateException("Missing inflation for ViewType " + type);
         }
     }
 
     /**
      * Returns the index of an item within highlights.
      * @param position position in adapter
--- a/mobile/android/base/java/org/mozilla/gecko/preferences/PanelsPreferenceCategory.java
+++ b/mobile/android/base/java/org/mozilla/gecko/preferences/PanelsPreferenceCategory.java
@@ -100,17 +100,22 @@ public class PanelsPreferenceCategory ex
         int index = 0;
         for (PanelConfig panelConfig : configState) {
             final boolean isRemovable = panelConfig.isDynamic();
 
             // Create and add the pref.
             final String panelId = panelConfig.getId();
             final boolean animate = TextUtils.equals(animatePanelId, panelId);
 
-            final PanelsPreference pref = new PanelsPreference(getContext(), PanelsPreferenceCategory.this, isRemovable, index, animate);
+            final PanelsPreference pref;
+            if (TextUtils.equals(panelId, HomeConfig.getIdForBuiltinPanelType(HomeConfig.PanelType.TOP_SITES))) {
+                pref = new TopSitesPanelsPreference(getContext(), PanelsPreferenceCategory.this, isRemovable, index, animate);
+            } else {
+                pref = new PanelsPreference(getContext(), PanelsPreferenceCategory.this, isRemovable, index, animate);
+            }
             pref.setTitle(panelConfig.getTitle());
             pref.setKey(panelConfig.getId());
             // XXX: Pull icon from PanelInfo.
             addPreference(pref);
 
             if (panelConfig.isDisabled()) {
                 pref.setHidden(true);
             }
new file mode 100644
--- /dev/null
+++ b/mobile/android/base/java/org/mozilla/gecko/preferences/TopSitesPanelsPreference.java
@@ -0,0 +1,25 @@
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+package org.mozilla.gecko.preferences;
+
+import android.app.AlertDialog;
+import android.content.Context;
+
+import org.mozilla.gecko.R;
+
+/**
+ * Custom preference that also adds additional options to the dialog of preferences for Top Sites settings.
+ */
+public class TopSitesPanelsPreference extends PanelsPreference {
+
+    TopSitesPanelsPreference(Context context, CustomListCategory parentCategory, boolean isRemovable, int index, boolean animate) {
+        super(context, parentCategory, isRemovable, index, animate);
+    }
+
+    @Override
+    protected void configureDialogBuilder(AlertDialog.Builder builder) {
+        builder.setView(R.layout.preference_topsites_panel_dialog);
+    }
+}
new file mode 100644
--- /dev/null
+++ b/mobile/android/base/java/org/mozilla/gecko/widget/SwitchPreferenceView.java
@@ -0,0 +1,64 @@
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+package org.mozilla.gecko.widget;
+
+import android.content.Context;
+import android.content.SharedPreferences;
+import android.content.res.TypedArray;
+import android.support.annotation.Nullable;
+import android.support.v7.widget.SwitchCompat;
+import android.util.AttributeSet;
+import android.widget.CompoundButton;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import org.mozilla.gecko.GeckoSharedPrefs;
+import org.mozilla.gecko.R;
+
+/**
+ * A toggle that controls a SharedPreference preference, and can be added outside of PreferenceScreen.
+ *
+ * The attribute 'androidPreferenceKey' must be defined when using this layout.
+ */
+public class SwitchPreferenceView extends SwitchCompat {
+
+    public SwitchPreferenceView(Context context) {
+        super(context);
+    }
+
+    public SwitchPreferenceView(Context context, @Nullable AttributeSet attrs) {
+        super(context, attrs);
+        init(context, attrs);
+    }
+
+    public SwitchPreferenceView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
+        super(context, attrs, defStyleAttr);
+        init(context, attrs);
+    }
+
+    private void init(Context context, AttributeSet attrs) {
+        TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.SwitchPreferenceView);
+        final String preferenceKey = a.getString(R.styleable.SwitchPreferenceView_androidPreferenceKey);
+        final boolean defaultValue = a.getBoolean(R.styleable.SwitchPreferenceView_defaultValue, false);
+
+        if (preferenceKey == null ) {
+            throw new IllegalStateException("The 'androidPreferenceKey' attribute must be included in the layout");
+        }
+
+        a.recycle();
+
+        final SharedPreferences sharedPreferences = GeckoSharedPrefs.forProfile(context);
+        final boolean isChecked = sharedPreferences.getBoolean(preferenceKey, defaultValue);
+
+        setChecked(isChecked);
+        setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
+            @Override
+            public void onCheckedChanged(CompoundButton compoundButton, boolean b) {
+                sharedPreferences.edit().putBoolean(preferenceKey, b).apply();
+            }
+        });
+
+    }
+}
--- a/mobile/android/base/locales/en-US/android_strings.dtd
+++ b/mobile/android/base/locales/en-US/android_strings.dtd
@@ -405,16 +405,19 @@
 <!ENTITY pref_default_browser_mozilla_support_tablet "Visit Mozilla Support">
 <!ENTITY pref_about_firefox "About &brandShortName;">
 <!ENTITY pref_vendor_faqs "FAQs">
 <!ENTITY pref_vendor_feedback "Give feedback">
 
 <!ENTITY pref_dialog_set_default "Set as default">
 <!ENTITY pref_dialog_default "Default">
 <!ENTITY pref_dialog_remove "Remove">
+<!ENTITY pref_dialog_activitystream_header_content "Additional content">
+<!ENTITY pref_dialog_activitystream_recentBookmarks "Recent Bookmarks">
+<!ENTITY pref_dialog_activitystream_visited "Visited">
 
 <!ENTITY pref_search_last_toast "You can\'t remove or disable your last search engine.">
 
 <!ENTITY pref_panels_show "Show">
 <!ENTITY pref_panels_hide "Hide">
 <!ENTITY pref_panels_reorder "Change order">
 <!ENTITY pref_panels_move_up "Move up">
 <!ENTITY pref_panels_move_down "Move down">
--- a/mobile/android/base/moz.build
+++ b/mobile/android/base/moz.build
@@ -830,16 +830,17 @@ gbjar.sources += ['java/org/mozilla/geck
     'preferences/MultiPrefMultiChoicePreference.java',
     'preferences/PanelsPreference.java',
     'preferences/PanelsPreferenceCategory.java',
     'preferences/PrivateDataPreference.java',
     'preferences/SearchEnginePreference.java',
     'preferences/SearchPreferenceCategory.java',
     'preferences/SetHomepagePreference.java',
     'preferences/SyncPreference.java',
+    'preferences/TopSitesPanelsPreference.java',
     'PresentationView.java',
     'PrintHelper.java',
     'PrivateTab.java',
     'promotion/AddToHomeScreenPromotion.java',
     'promotion/HomeScreenPrompt.java',
     'promotion/ReaderViewBookmarkPromotion.java',
     'promotion/SimpleHelperUI.java',
     'prompts/ColorPickerInput.java',
@@ -997,16 +998,17 @@ gbjar.sources += ['java/org/mozilla/geck
     'widget/RecyclerViewClickSupport.java',
     'widget/ResizablePathDrawable.java',
     'widget/RoundedCornerLayout.java',
     'widget/SiteLogins.java',
     'widget/SplashScreen.java',
     'widget/SquaredImageView.java',
     'widget/SquaredRelativeLayout.java',
     'widget/SwipeDismissListViewTouchListener.java',
+    'widget/SwitchPreferenceView.java',
     'widget/TabThumbnailWrapper.java',
     'widget/ThumbnailView.java',
     'widget/TouchDelegateWithReset.java',
 ]]
 # The following sources are checked in to version control but
 # generated by a script (java/org/mozilla/gecko/widget/themed/generate_themed_views.py).
 # If you're editing this list, make sure to edit that script.
 gbjar.sources += ['java/org/mozilla/gecko/' + x for x in [
--- a/mobile/android/base/strings.xml.in
+++ b/mobile/android/base/strings.xml.in
@@ -322,16 +322,20 @@
   <string name="pref_vendor_feedback">&pref_vendor_feedback;</string>
   <!-- https://input.mozilla.org/feedback/android/%VERSION%/%CHANNEL%/?utm_source=feedback-settings
        This should be kept in sync with the "app.feedbackURL" pref defined in mobile.js -->
   <string name="feedback_link">https://input.mozilla.org/feedback/android/&formatS1;/&formatS2;/?utm_source=feedback-settings</string>
 
   <string name="pref_dialog_set_default">&pref_dialog_set_default;</string>
   <string name="pref_default">&pref_dialog_default;</string>
   <string name="pref_dialog_remove">&pref_dialog_remove;</string>
+  <string name="pref_dialog_activitystream_header_content">&pref_dialog_activitystream_header_content;</string>
+  <string name="pref_dialog_activitystream_recentBookmarks">&pref_dialog_activitystream_recentBookmarks;</string>
+  <string name="pref_dialog_activitystream_visited">&pref_dialog_activitystream_visited;</string>
+
 
   <string name="pref_search_last_toast">&pref_search_last_toast;</string>
 
   <string name="pref_panels_show">&pref_panels_show;</string>
   <string name="pref_panels_hide">&pref_panels_hide;</string>
   <string name="pref_panels_reorder">&pref_panels_reorder;</string>
   <string name="pref_panels_move_up">&pref_panels_move_up;</string>
   <string name="pref_panels_move_down">&pref_panels_move_down;</string>