diff options
author | The Android Open Source Project <initial-contribution@android.com> | 2009-03-13 13:04:24 -0700 |
---|---|---|
committer | The Android Open Source Project <initial-contribution@android.com> | 2009-03-13 13:04:24 -0700 |
commit | f59ec877363eaf43118677f249008eddc7a9ce11 (patch) | |
tree | 1ad656054b6207bff725c939613fdb08a27079f9 /src/com | |
parent | cb9a0bbc3a00a044fbfdabda920d3be80b0747f0 (diff) | |
download | packages_apps_Browser-f59ec877363eaf43118677f249008eddc7a9ce11.zip packages_apps_Browser-f59ec877363eaf43118677f249008eddc7a9ce11.tar.gz packages_apps_Browser-f59ec877363eaf43118677f249008eddc7a9ce11.tar.bz2 |
auto import from //branches/cupcake_rel/...@138607
Diffstat (limited to 'src/com')
-rw-r--r-- | src/com/android/browser/BrowserActivity.java | 67 | ||||
-rw-r--r-- | src/com/android/browser/BrowserBookmarksPage.java | 9 | ||||
-rw-r--r-- | src/com/android/browser/ImageAdapter.java | 15 | ||||
-rw-r--r-- | src/com/android/browser/TabControl.java | 150 |
4 files changed, 186 insertions, 55 deletions
diff --git a/src/com/android/browser/BrowserActivity.java b/src/com/android/browser/BrowserActivity.java index fc80fcd..bd6fdc6 100644 --- a/src/com/android/browser/BrowserActivity.java +++ b/src/com/android/browser/BrowserActivity.java @@ -686,9 +686,11 @@ public class BrowserActivity extends Activity // If the intent is ACTION_VIEW and data is not null, the Browser is // invoked to view the content by another application. In this case, // the tab will be close when exit. + String url = getUrlFromIntent(intent); final TabControl.Tab t = mTabControl.createNewTab( Intent.ACTION_VIEW.equals(intent.getAction()) && - intent.getData() != null); + intent.getData() != null, + intent.getStringExtra(Browser.EXTRA_APPLICATION_ID), url); mTabControl.setCurrentTab(t); // This is one of the only places we call attachTabToContentView // without animating from the tab picker. @@ -710,7 +712,6 @@ public class BrowserActivity extends Activity } copyPlugins(true); - String url = getUrlFromIntent(intent); if (url == null || url.length() == 0) { if (mSettings.isLoginInitialized()) { webView.loadUrl(mSettings.getHomePage()); @@ -778,11 +779,44 @@ public class BrowserActivity extends Activity } if (Intent.ACTION_VIEW.equals(action) && (flags & Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT) != 0) { + final String appId = + intent.getStringExtra(Browser.EXTRA_APPLICATION_ID); + final TabControl.Tab appTab = mTabControl.getTabFromId(appId); + if (appTab != null) { + Log.i(LOGTAG, "Reusing tab for " + appId); + // Dismiss the subwindow if applicable. + dismissSubWindow(appTab); + // Since we might kill the WebView, remove it from the + // content view first. + removeTabFromContentView(appTab); + // Recreate the main WebView after destroying the old one. + // If the WebView has the same original url and is on that + // page, it can be reused. + boolean needsLoad = + mTabControl.recreateWebView(appTab, url); + if (current != appTab) { + showTab(appTab, needsLoad ? url : null); + } else { + if (mTabOverview != null && mAnimationCount == 0) { + sendAnimateFromOverview(appTab, false, + needsLoad ? url : null, TAB_OVERVIEW_DELAY, + null); + } else { + // If the tab was the current tab, we have to attach + // it to the view system again. + attachTabToContentView(appTab); + if (needsLoad) { + appTab.getWebView().loadUrl(url); + } + } + } + return; + } // if FLAG_ACTIVITY_BROUGHT_TO_FRONT flag is on, the url will be // opened in a new tab unless we have reached MAX_TABS. Then the // url will be opened in the current tab. If a new tab is // created, it will have "true" for exit on close. - openTabAndShow(url, null, true); + openTabAndShow(url, null, true, appId); } else { if ("about:debug".equals(url)) { mSettings.toggleDebugSettings(); @@ -1329,7 +1363,7 @@ public class BrowserActivity extends Activity case R.id.windows_menu_id: if (mTabControl.getTabCount() == 1) { - openTabAndShow(mSettings.getHomePage(), null, false); + openTabAndShow(mSettings.getHomePage(), null, false, null); } else { tabPicker(true, mTabControl.getCurrentIndex(), false); } @@ -1808,6 +1842,10 @@ public class BrowserActivity extends Activity // Called by TabControl when a tab is requesting focus /* package */ void showTab(TabControl.Tab t) { + showTab(t, null); + } + + private void showTab(TabControl.Tab t, String url) { // Disallow focus change during a tab animation. if (mAnimationCount > 0) { return; @@ -1819,7 +1857,7 @@ public class BrowserActivity extends Activity delay = TAB_ANIMATION_DURATION + TAB_OVERVIEW_DELAY; tabPicker(false, mTabControl.getTabIndex(t), false); } - sendAnimateFromOverview(t, false, null, delay, null); + sendAnimateFromOverview(t, false, url, delay, null); } // This method does a ton of stuff. It will attempt to create a new tab @@ -1831,7 +1869,7 @@ public class BrowserActivity extends Activity // method is called from TabListener.onClick(), the method will animate // away from the tab overview. private void openTabAndShow(String url, final Message msg, - boolean closeOnExit) { + boolean closeOnExit, String appId) { final boolean newTab = mTabControl.getTabCount() != TabControl.MAX_TABS; final TabControl.Tab currentTab = mTabControl.getCurrentTab(); if (newTab) { @@ -1859,8 +1897,9 @@ public class BrowserActivity extends Activity } // Animate from the Tab overview after any animations have // finished. - sendAnimateFromOverview(mTabControl.createNewTab(closeOnExit), - true, url, delay, msg); + sendAnimateFromOverview( + mTabControl.createNewTab(closeOnExit, appId, url), true, + url, delay, msg); } } else if (url != null) { // We should not have a msg here. @@ -2093,12 +2132,12 @@ public class BrowserActivity extends Activity private void openTab(String url) { if (mSettings.openInBackground()) { - TabControl.Tab t = mTabControl.createNewTab(false); + TabControl.Tab t = mTabControl.createNewTab(); if (t != null) { t.getWebView().loadUrl(url); } } else { - openTabAndShow(url, null, false); + openTabAndShow(url, null, false, null); } } @@ -2512,7 +2551,7 @@ public class BrowserActivity extends Activity // the method relies on the value being 0 to start the next // animation. mAnimationCount--; - openTabAndShow((String) msg.obj, null, false); + openTabAndShow((String) msg.obj, null, false, null); break; case FOCUS_NODE_HREF: @@ -3130,7 +3169,7 @@ public class BrowserActivity extends Activity // openTabAndShow will dispatch the message after creating the // new WebView. This will prevent another request from coming // in during the animation. - openTabAndShow(null, msg, false); + openTabAndShow(null, msg, false, null); parent.addChildTab(mTabControl.getCurrentTab()); WebView.WebViewTransport transport = (WebView.WebViewTransport) msg.obj; @@ -4052,7 +4091,7 @@ public class BrowserActivity extends Activity // If the user removes the last tab, act like the New Tab item // was clicked on. if (mTabControl.getTabCount() == 0) { - current = mTabControl.createNewTab(false); + current = mTabControl.createNewTab(); sendAnimateFromOverview(current, true, mSettings.getHomePage(), TAB_OVERVIEW_DELAY, null); } else { @@ -4092,7 +4131,7 @@ public class BrowserActivity extends Activity // NEW_TAB means that the "New Tab" cell was clicked on. if (index == ImageGrid.NEW_TAB) { - openTabAndShow(mSettings.getHomePage(), null, false); + openTabAndShow(mSettings.getHomePage(), null, false, null); } else { sendAnimateFromOverview(mTabControl.getTab(index), false, null, 0, null); diff --git a/src/com/android/browser/BrowserBookmarksPage.java b/src/com/android/browser/BrowserBookmarksPage.java index 7708e8b..a7d45f9 100644 --- a/src/com/android/browser/BrowserBookmarksPage.java +++ b/src/com/android/browser/BrowserBookmarksPage.java @@ -212,8 +212,13 @@ public class BrowserBookmarksPage extends Activity implements private Intent createShortcutIntent(String url, String title) { final Intent i = new Intent(); - i.putExtra(Intent.EXTRA_SHORTCUT_INTENT, new Intent(Intent.ACTION_VIEW, - Uri.parse(url))); + final Intent shortcutIntent = new Intent(Intent.ACTION_VIEW, + Uri.parse(url)); + long urlHash = url.hashCode(); + long uniqueId = (urlHash << 32) | shortcutIntent.hashCode(); + shortcutIntent.putExtra(Browser.EXTRA_APPLICATION_ID, + Long.toString(uniqueId)); + i.putExtra(Intent.EXTRA_SHORTCUT_INTENT, shortcutIntent); i.putExtra(Intent.EXTRA_SHORTCUT_NAME, title); i.putExtra(Intent.EXTRA_SHORTCUT_ICON_RESOURCE, Intent.ShortcutIconResource.fromContext(BrowserBookmarksPage.this, diff --git a/src/com/android/browser/ImageAdapter.java b/src/com/android/browser/ImageAdapter.java index b4c1209..e957143 100644 --- a/src/com/android/browser/ImageAdapter.java +++ b/src/com/android/browser/ImageAdapter.java @@ -231,20 +231,7 @@ public class ImageAdapter implements ListAdapter { if (l == null) { return; } - DialogInterface.OnClickListener confirm = - new DialogInterface.OnClickListener() { - public void onClick(DialogInterface dialog, - int whichButton) { - l.remove(position); - } - }; - new AlertDialog.Builder(mContext) - .setTitle(R.string.close) - .setIcon(android.R.drawable.ic_dialog_alert) - .setMessage(R.string.close_window) - .setPositiveButton(R.string.ok, confirm) - .setNegativeButton(R.string.cancel, null) - .show(); + l.remove(position); } /* (non-Javadoc) diff --git a/src/com/android/browser/TabControl.java b/src/com/android/browser/TabControl.java index 57e55c4..d58ee22 100644 --- a/src/com/android/browser/TabControl.java +++ b/src/com/android/browser/TabControl.java @@ -174,11 +174,19 @@ class TabControl { private Vector<Tab> mChildTabs; private Boolean mCloseOnExit; + // Application identifier used to find tabs that another application + // wants to reuse. + private String mAppId; + // Keep the original url around to avoid killing the old WebView if the + // url has not changed. + private String mOriginalUrl; // Construct a new tab - private Tab(WebView w, boolean closeOnExit) { + private Tab(WebView w, boolean closeOnExit, String appId, String url) { mMainView = w; mCloseOnExit = closeOnExit; + mAppId = appId; + mOriginalUrl = url; } /** @@ -403,25 +411,19 @@ class TabControl { } /** - * Create a new tab and display the new tab immediately. + * Create a new tab. * @return The newly createTab or null if we have reached the maximum * number of open tabs. */ - Tab createNewTab(boolean closeOnExit) { + Tab createNewTab(boolean closeOnExit, String appId, String url) { int size = mTabs.size(); // Return false if we have maxed out on tabs if (MAX_TABS == size) { return null; } - // Create a new WebView - WebView w = new WebView(mActivity); - w.setMapTrackballToArrowKeys(false); // use trackball directly - // Add this WebView to the settings observer list and update the - // settings - final BrowserSettings s = BrowserSettings.getInstance(); - s.addObserver(w.getSettings()).update(s, null); + final WebView w = createNewWebView(); // Create a new tab and add it to the tab list - Tab t = new Tab(w, closeOnExit); + Tab t = new Tab(w, closeOnExit, appId, url); mTabs.add(t); // Initially put the tab in the background. putTabInBackground(t); @@ -429,6 +431,14 @@ class TabControl { } /** + * Create a new tab with default values for closeOnExit(false), + * appId(null), and url(null). + */ + Tab createNewTab() { + return createNewTab(false, null, null); + } + + /** * Remove the tab from the list. If the tab is the current tab shown, the * last created tab will be shown. * @param t The tab to be removed. @@ -536,6 +546,8 @@ class TabControl { private static final String CURRTITLE = "currentTitle"; private static final String CLOSEONEXIT = "closeonexit"; private static final String PARENTTAB = "parentTab"; + private static final String APPID = "appid"; + private static final String ORIGINALURL = "originalUrl"; /** * Save the state of all the Tabs. @@ -569,7 +581,7 @@ class TabControl { final int currentTab = inState.getInt(CURRTAB, -1); for (int i = 0; i < numTabs; i++) { if (i == currentTab) { - Tab t = createNewTab(false); + Tab t = createNewTab(); // Me must set the current tab before restoring the state // so that all the client classes are set. setCurrentTab(t); @@ -581,11 +593,15 @@ class TabControl { } else { // Create a new tab and don't restore the state yet, add it // to the tab list - Tab t = new Tab(null, false); + Tab t = new Tab(null, false, null, null); t.mSavedState = inState.getBundle(WEBVIEW + i); if (t.mSavedState != null) { t.mUrl = t.mSavedState.getString(CURRURL); t.mTitle = t.mSavedState.getString(CURRTITLE); + // Need to maintain the app id and original url so we + // can possibly reuse this tab. + t.mAppId = t.mSavedState.getString(APPID); + t.mOriginalUrl = t.mSavedState.getString(ORIGINALURL); } mTabs.add(t); mTabQueue.add(t); @@ -727,13 +743,92 @@ class TabControl { } /** + * Return the tab with the matching application id. + * @param id The application identifier. + */ + Tab getTabFromId(String id) { + if (id == null) { + return null; + } + final int size = getTabCount(); + for (int i = 0; i < size; i++) { + final Tab t = getTab(i); + if (id.equals(t.mAppId)) { + return t; + } + } + return null; + } + + /** + * Recreate the main WebView of the given tab. Returns true if the WebView + * was deleted. + */ + boolean recreateWebView(Tab t, String url) { + final WebView w = t.mMainView; + if (w != null) { + if (url != null && url.equals(t.mOriginalUrl)) { + // The original url matches the current url. Just go back to the + // first history item so we can load it faster than if we + // rebuilt the WebView. + final WebBackForwardList list = w.copyBackForwardList(); + if (list != null) { + w.goBackOrForward(-list.getCurrentIndex()); + w.clearHistory(); // maintains the current page. + return false; + } + } + // Remove the settings object from the global settings and destroy + // the WebView. + BrowserSettings.getInstance().deleteObserver( + t.mMainView.getSettings()); + t.mMainView.destroy(); + } + // Create a new WebView. If this tab is the current tab, we need to put + // back all the clients so force it to be the current tab. + t.mMainView = createNewWebView(); + if (getCurrentTab() == t) { + setCurrentTab(t, true); + } + // Clear the saved state except for the app id and close-on-exit + // values. + t.mSavedState = null; + t.mUrl = null; + t.mTitle = null; + // Save the new url in order to avoid deleting the WebView. + t.mOriginalUrl = url; + return true; + } + + /** + * Creates a new WebView and registers it with the global settings. + */ + private WebView createNewWebView() { + // Create a new WebView + WebView w = new WebView(mActivity); + w.setMapTrackballToArrowKeys(false); // use trackball directly + // Add this WebView to the settings observer list and update the + // settings + final BrowserSettings s = BrowserSettings.getInstance(); + s.addObserver(w.getSettings()).update(s, null); + return w; + } + + /** * Put the current tab in the background and set newTab as the current tab. * @param newTab The new tab. If newTab is null, the current tab is not * set. */ boolean setCurrentTab(Tab newTab) { + return setCurrentTab(newTab, false); + } + + /** + * If force is true, this method skips the check for newTab == current. + */ + private boolean setCurrentTab(Tab newTab, boolean force) { Tab current = getTab(mCurrentTab); - if (current == newTab) { + if (current == newTab && !force) { return true; } if (current != null) { @@ -761,13 +856,7 @@ class TabControl { boolean needRestore = (mainView == null); if (needRestore) { // Same work as in createNewTab() except don't do new Tab() - newTab.mMainView = mainView = new WebView(mActivity); - mainView.setMapTrackballToArrowKeys(false); // use t-ball directly - - // Add this WebView to the settings observer list and update the - // settings - final BrowserSettings s = BrowserSettings.getInstance(); - s.addObserver(mainView.getSettings()).update(s, null); + newTab.mMainView = mainView = createNewWebView(); } mainView.setWebViewClient(mActivity.getWebViewClient()); mainView.setWebChromeClient(mActivity.getWebChromeClient()); @@ -900,6 +989,12 @@ class TabControl { b.putString(CURRTITLE, t.mTitle); } b.putBoolean(CLOSEONEXIT, t.mCloseOnExit); + if (t.mAppId != null) { + b.putString(APPID, t.mAppId); + } + if (t.mOriginalUrl != null) { + b.putString(ORIGINALURL, t.mOriginalUrl); + } // Remember the parent tab so the relationship can be restored. if (t.mParentTab != null) { @@ -920,6 +1015,15 @@ class TabControl { if (b == null) { return false; } + // Restore the internal state even if the WebView fails to restore. + // This will maintain the app id, original url and close-on-exit values. + t.mSavedState = null; + t.mUrl = null; + t.mTitle = null; + t.mCloseOnExit = b.getBoolean(CLOSEONEXIT); + t.mAppId = b.getString(APPID); + t.mOriginalUrl = b.getString(ORIGINALURL); + final WebView w = t.mMainView; final WebBackForwardList list = w.restoreState(b); if (list == null) { @@ -930,10 +1034,6 @@ class TabControl { w.restorePicture(b, f); f.delete(); } - t.mSavedState = null; - t.mUrl = null; - t.mTitle = null; - t.mCloseOnExit = b.getBoolean(CLOSEONEXIT); return true; } } |