author | Margaret Leibovic <margaret.leibovic@gmail.com> |
Mon, 12 Aug 2013 11:44:46 -0700 | |
changeset 143521 | 2b52431a80543125d1b3c278b5575cb7cf9fddc7 |
parent 143520 | dff6e98eaac0bfd79785f97273f9e9612ab92481 |
child 143522 | 673e9806d6c302d5cda2c784106cb277ac49371a |
push id | 25130 |
push user | lrocha@mozilla.com |
push date | Wed, 21 Aug 2013 09:41:27 +0000 |
treeherder | mozilla-central@b2486721572e [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | wesj, lucasr |
bugs | 899393 |
milestone | 26.0a1 |
first release with | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
last release without | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
--- a/mobile/android/base/BrowserApp.java +++ b/mobile/android/base/BrowserApp.java @@ -11,16 +11,17 @@ import org.mozilla.gecko.db.BrowserDB; import org.mozilla.gecko.gfx.BitmapUtils; import org.mozilla.gecko.gfx.GeckoLayerClient; import org.mozilla.gecko.gfx.ImmutableViewportMetrics; import org.mozilla.gecko.gfx.LayerView; import org.mozilla.gecko.gfx.PanZoomController; import org.mozilla.gecko.health.BrowserHealthReporter; import org.mozilla.gecko.home.BrowserSearch; import org.mozilla.gecko.home.HomePager; +import org.mozilla.gecko.home.HomePager.OnUrlOpenListener; import org.mozilla.gecko.menu.GeckoMenu; import org.mozilla.gecko.util.Clipboard; import org.mozilla.gecko.util.FloatUtils; import org.mozilla.gecko.util.GamepadUtils; import org.mozilla.gecko.util.HardwareUtils; import org.mozilla.gecko.util.ThreadUtils; import org.mozilla.gecko.util.UiAsyncTask; import org.mozilla.gecko.widget.GeckoActionProvider; @@ -79,17 +80,17 @@ import java.util.Vector; abstract public class BrowserApp extends GeckoApp implements TabsPanel.TabsLayoutChangeListener, PropertyAnimator.PropertyAnimationListener, View.OnKeyListener, GeckoLayerClient.OnMetricsChangedListener, BrowserSearch.OnSearchListener, BrowserSearch.OnEditSuggestionListener, HomePager.OnNewTabsListener, - HomePager.OnUrlOpenListener { + OnUrlOpenListener { private static final String LOGTAG = "GeckoBrowserApp"; private static final String PREF_CHROME_DYNAMICTOOLBAR = "browser.chrome.dynamictoolbar"; private static final String ABOUT_HOME = "about:home"; private static final int TABS_ANIMATION_DURATION = 450; @@ -1257,16 +1258,45 @@ abstract public class BrowserApp extends @Override public void onSaveInstanceState(Bundle outState) { super.onSaveInstanceState(outState); mToast.onSaveInstanceState(outState); outState.putBoolean(STATE_DYNAMIC_TOOLBAR_ENABLED, mDynamicToolbarEnabled); outState.putInt(STATE_ABOUT_HOME_TOP_PADDING, mHomePagerContainer.getPaddingTop()); } + /** + * Attempts to switch to an open tab with the given URL. + * + * @return true if we successfully switched to a tab, false otherwise. + */ + private boolean maybeSwitchToTab(String url, EnumSet<OnUrlOpenListener.Flags> flags) { + if (!flags.contains(OnUrlOpenListener.Flags.ALLOW_SWITCH_TO_TAB)) { + return false; + } + + final Tabs tabs = Tabs.getInstance(); + final int tabId = tabs.getTabIdForUrl(url); + if (tabId < 0) { + return false; + } + + // If this tab is already selected, just hide the home pager. + if (tabs.isSelectedTab(tabs.getTab(tabId))) { + hideHomePager(); + } else { + tabs.selectTab(tabId); + } + + hideBrowserSearch(); + mBrowserToolbar.cancelEdit(); + + return true; + } + private void openUrl(String url) { openUrl(url, null, false); } private void openUrl(String url, boolean newTab) { openUrl(url, null, newTab); } @@ -2060,20 +2090,22 @@ abstract public class BrowserApp extends public void onNewTabs(String[] urls) { for (String url : urls) { openUrl(url, true); } } // HomePager.OnUrlOpenListener @Override - public void onUrlOpen(String url) { - openUrl(url); + public void onUrlOpen(String url, EnumSet<OnUrlOpenListener.Flags> flags) { + if (!maybeSwitchToTab(url, flags)) { + openUrl(url); + } } - + // BrowserSearch.OnSearchListener @Override public void onSearch(String engineId, String text) { openUrl(text, engineId); } // BrowserSearch.OnEditSuggestionListener @Override
--- a/mobile/android/base/Tabs.java +++ b/mobile/android/base/Tabs.java @@ -580,29 +580,29 @@ public class Tabs implements GeckoEventL backgroundHandler.postDelayed(mPersistTabsRunnable, PERSIST_TABS_AFTER_MILLISECONDS); } private void registerEventListener(String event) { GeckoAppShell.getEventDispatcher().registerEventListener(event, this); } /** - * Returns true if any of the tabs has the requested url. - * - * @return true if the url is open currently, false otherwise. + * Looks for an open tab with the given URL. + * + * @return id of an open tab with the given URL; -1 if the tab doesn't exist. */ - public boolean hasUrl(String url) { + public int getTabIdForUrl(String url) { for (Tab tab : mOrder) { if (TextUtils.equals(tab.getURL(), url) || TextUtils.equals(ReaderModeUtils.getUrlFromAboutReader(tab.getURL()), url)) { - return true; + return tab.getId(); } } - return false; + return -1; } /** * Loads a tab with the given URL in the currently selected tab. * * @param url URL of page to load, or search term used if searchEngine is given */ public void loadUrl(String url) {
--- a/mobile/android/base/home/BookmarksListView.java +++ b/mobile/android/base/home/BookmarksListView.java @@ -16,16 +16,18 @@ import android.util.AttributeSet; import android.view.MotionEvent; import android.view.View; import android.view.ViewConfiguration; import android.widget.AdapterView; import android.widget.HeaderViewListAdapter; import android.widget.ListAdapter; import android.widget.ListView; +import java.util.EnumSet; + /** * A ListView of bookmarks. */ public class BookmarksListView extends HomeListView implements AdapterView.OnItemClickListener{ public static final String LOGTAG = "GeckoBookmarksListView"; // The last motion event that was intercepted. @@ -129,15 +131,14 @@ public class BookmarksListView extends H if (type == Bookmarks.TYPE_FOLDER) { // If we're clicking on a folder, update adapter to move to that folder final int folderId = cursor.getInt(cursor.getColumnIndexOrThrow(Bookmarks._ID)); final String folderTitle = adapter.getFolderTitle(parent.getContext(), cursor); adapter.moveToChildFolder(folderId, folderTitle); } else { // Otherwise, just open the URL final String url = cursor.getString(cursor.getColumnIndexOrThrow(URLColumns.URL)); - OnUrlOpenListener listener = getOnUrlOpenListener(); - if (listener != null) { - listener.onUrlOpen(url); - } + + // This item is a TwoLinePageRow, so we allow switch-to-tab. + getOnUrlOpenListener().onUrlOpen(url, EnumSet.of(OnUrlOpenListener.Flags.ALLOW_SWITCH_TO_TAB)); } } }
--- a/mobile/android/base/home/BrowserSearch.java +++ b/mobile/android/base/home/BrowserSearch.java @@ -46,16 +46,17 @@ import android.view.animation.Accelerate import android.view.animation.Animation; import android.view.animation.TranslateAnimation; import android.widget.AdapterView; import android.widget.LinearLayout; import android.widget.ListView; import android.widget.TextView; import java.util.ArrayList; +import java.util.EnumSet; import java.util.List; /** * Fragment that displays frecency search results in a ListView. */ public class BrowserSearch extends HomeFragment implements GeckoEventListener { // Logging tag name @@ -225,17 +226,19 @@ public class BrowserSearch extends HomeF mList.setOnItemClickListener(new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { // Account for the search engines position -= getSuggestEngineCount(); final Cursor c = mAdapter.getCursor(position); final String url = c.getString(c.getColumnIndexOrThrow(URLColumns.URL)); - mUrlOpenListener.onUrlOpen(url); + + // This item is a TwoLinePageRow, so we allow switch-to-tab. + mUrlOpenListener.onUrlOpen(url, EnumSet.of(OnUrlOpenListener.Flags.ALLOW_SWITCH_TO_TAB)); } }); final ListSelectionListener listener = new ListSelectionListener(); mList.setOnItemSelectedListener(listener); mList.setOnFocusChangeListener(listener); mList.setOnKeyListener(new View.OnKeyListener() {
--- a/mobile/android/base/home/HomePager.java +++ b/mobile/android/base/home/HomePager.java @@ -35,17 +35,21 @@ public class HomePager extends ViewPager HISTORY, BOOKMARKS, READING_LIST } private EnumMap<Page, Fragment> mPages = new EnumMap<Page, Fragment>(Page.class); public interface OnUrlOpenListener { - public void onUrlOpen(String url); + public enum Flags { + ALLOW_SWITCH_TO_TAB + } + + public void onUrlOpen(String url, EnumSet<Flags> flags); } public interface OnNewTabsListener { public void onNewTabs(String[] urls); } public HomePager(Context context) { this(context, null);
--- a/mobile/android/base/home/MostRecentPage.java +++ b/mobile/android/base/home/MostRecentPage.java @@ -24,16 +24,17 @@ import android.view.View; import android.view.ViewStub; import android.view.ViewGroup; import android.widget.AdapterView; import android.widget.ImageView; import android.widget.ListView; import android.widget.TextView; import java.util.Date; +import java.util.EnumSet; /** * Fragment that displays recent history in a ListView. */ public class MostRecentPage extends HomeFragment { // Logging tag name private static final String LOGTAG = "GeckoMostRecentPage"; @@ -96,17 +97,19 @@ public class MostRecentPage extends Home mList = (ListView) view.findViewById(R.id.list); mList.setOnItemClickListener(new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { position -= mAdapter.getMostRecentSectionsCountBefore(position); final Cursor c = mAdapter.getCursor(position); final String url = c.getString(c.getColumnIndexOrThrow(URLColumns.URL)); - mUrlOpenListener.onUrlOpen(url); + + // This item is a TwoLinePageRow, so we allow switch-to-tab. + mUrlOpenListener.onUrlOpen(url, EnumSet.of(OnUrlOpenListener.Flags.ALLOW_SWITCH_TO_TAB)); } }); registerForContextMenu(mList); } @Override public void onDestroyView() {
--- a/mobile/android/base/home/MostVisitedPage.java +++ b/mobile/android/base/home/MostVisitedPage.java @@ -20,16 +20,18 @@ import android.support.v4.content.Loader import android.support.v4.widget.CursorAdapter; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.AdapterView; import android.widget.ListView; import android.widget.TextView; +import java.util.EnumSet; + /** * Fragment that displays frecency search results in a ListView. */ public class MostVisitedPage extends HomeFragment { // Logging tag name private static final String LOGTAG = "GeckoMostVisitedPage"; // Cursor loader ID for search query @@ -90,17 +92,19 @@ public class MostVisitedPage extends Hom @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { final Cursor c = mAdapter.getCursor(); if (c == null || !c.moveToPosition(position)) { return; } final String url = c.getString(c.getColumnIndexOrThrow(URLColumns.URL)); - mUrlOpenListener.onUrlOpen(url); + + // This item is a TwoLinePageRow, so we allow switch-to-tab. + mUrlOpenListener.onUrlOpen(url, EnumSet.of(OnUrlOpenListener.Flags.ALLOW_SWITCH_TO_TAB)); } }); registerForContextMenu(mList); } @Override public void onDestroyView() {
--- a/mobile/android/base/home/ReadingListPage.java +++ b/mobile/android/base/home/ReadingListPage.java @@ -21,16 +21,18 @@ import android.support.v4.app.LoaderMana import android.support.v4.content.Loader; import android.support.v4.widget.CursorAdapter; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.AdapterView; import android.widget.ListView; +import java.util.EnumSet; + /** * Fragment that displays reading list contents in a ListView. */ public class ReadingListPage extends HomeFragment { // Cursor loader ID for reading list private static final int LOADER_ID_READING_LIST = 0; // Adapter for the list of reading list items @@ -81,17 +83,19 @@ public class ReadingListPage extends Hom public void onItemClick(AdapterView<?> parent, View view, int position, long id) { final Cursor c = mAdapter.getCursor(); if (c == null || !c.moveToPosition(position)) { return; } String url = c.getString(c.getColumnIndexOrThrow(URLColumns.URL)); url = ReaderModeUtils.getAboutReaderForUrl(url, true); - mUrlOpenListener.onUrlOpen(url); + + // This item is a TwoLinePageRow, so we allow switch-to-tab. + mUrlOpenListener.onUrlOpen(url, EnumSet.of(OnUrlOpenListener.Flags.ALLOW_SWITCH_TO_TAB)); } }); registerForContextMenu(mList); } @Override public void onDestroyView() {
--- a/mobile/android/base/home/SearchEngineRow.java +++ b/mobile/android/base/home/SearchEngineRow.java @@ -19,16 +19,18 @@ import android.util.AttributeSet; import android.view.KeyEvent; import android.view.LayoutInflater; import android.view.View; import android.view.animation.AlphaAnimation; import android.widget.ImageView; import android.widget.LinearLayout; import android.widget.TextView; +import java.util.EnumSet; + class SearchEngineRow extends AnimatedHeightLayout { // Duration for fade-in animation private static final int ANIMATION_DURATION = 250; // Inner views private final FlowLayout mSuggestionView; private final FaviconView mIconView; private final LinearLayout mUserEnteredView; @@ -72,17 +74,17 @@ class SearchEngineRow extends AnimatedHe public void onClick(View v) { final String suggestion = getSuggestionTextFromView(v); // If we're not clicking the user-entered view (the first suggestion item) // and the search matches a URL pattern, go to that URL. Otherwise, do a // search for the term. if (v != mUserEnteredView && !StringUtils.isSearchQuery(suggestion, false)) { if (mUrlOpenListener != null) { - mUrlOpenListener.onUrlOpen(suggestion); + mUrlOpenListener.onUrlOpen(suggestion, EnumSet.noneOf(OnUrlOpenListener.Flags.class)); } } else if (mSearchListener != null) { mSearchListener.onSearch(mSearchEngine.name, suggestion); } } }; mLongClickListener = new OnLongClickListener() {
--- a/mobile/android/base/home/TopBookmarksView.java +++ b/mobile/android/base/home/TopBookmarksView.java @@ -19,16 +19,18 @@ import android.util.AttributeSet; import android.view.ContextMenu.ContextMenuInfo; import android.view.View; import android.view.animation.AnimationUtils; import android.view.animation.GridLayoutAnimationController; import android.widget.AbsListView; import android.widget.AdapterView; import android.widget.GridView; +import java.util.EnumSet; + /** * A grid view of top bookmarks and pinned tabs. * Each cell in the grid is a TopBookmarkItemView. */ public class TopBookmarksView extends GridView { private static final String LOGTAG = "GeckoTopBookmarksView"; // Listener for pinning bookmarks. @@ -89,17 +91,17 @@ public class TopBookmarksView extends Gr public void onItemClick(AdapterView<?> parent, View view, int position, long id) { TopBookmarkItemView row = (TopBookmarkItemView) view; String url = row.getUrl(); // If the url is empty, the user can pin a bookmark. // If not, navigate to the page given by the url. if (!TextUtils.isEmpty(url)) { if (mUrlOpenListener != null) { - mUrlOpenListener.onUrlOpen(url); + mUrlOpenListener.onUrlOpen(url, EnumSet.noneOf(OnUrlOpenListener.Flags.class)); } } else { if (mPinBookmarkListener != null) { mPinBookmarkListener.onPinBookmark(position); } } } });
--- a/mobile/android/base/home/TwoLinePageRow.java +++ b/mobile/android/base/home/TwoLinePageRow.java @@ -129,17 +129,18 @@ public class TwoLinePageRow extends Line mPageUrl = url; updateDisplayedUrl(); } /** * Replaces the page URL with "Switch to tab" if there is already a tab open with that URL. */ private void updateDisplayedUrl() { - if (!mShowIcons || !Tabs.getInstance().hasUrl(mPageUrl)) { + int tabId = Tabs.getInstance().getTabIdForUrl(mPageUrl); + if (!mShowIcons || tabId < 0) { setUrl(mPageUrl); setUrlIcon(NO_ICON); } else { setUrl(R.string.switch_to_tab); setUrlIcon(R.drawable.ic_url_bar_tab); } }