diff --git a/mobile/android/base/Tabs.java b/mobile/android/base/Tabs.java index 478befbce4c..501315687a9 100644 --- a/mobile/android/base/Tabs.java +++ b/mobile/android/base/Tabs.java @@ -21,6 +21,7 @@ import java.util.ArrayList; import java.util.HashMap; import java.util.Iterator; import java.util.concurrent.CopyOnWriteArrayList; +import java.util.concurrent.atomic.AtomicInteger; public class Tabs implements GeckoEventListener { private static final String LOGTAG = "GeckoTabs"; @@ -41,6 +42,8 @@ public class Tabs implements GeckoEventListener { private static final int SCORE_INCREMENT_TAB_SELECTED = 10; private static final int SCORE_THRESHOLD = 30; + private static AtomicInteger sTabId = new AtomicInteger(0); + private GeckoApp mActivity; private Tabs() { @@ -68,17 +71,7 @@ public class Tabs implements GeckoEventListener { return mTabs.size(); } - private Tab addTab(JSONObject params) throws JSONException { - int id = params.getInt("tabID"); - if (mTabs.containsKey(id)) - return mTabs.get(id); - - // null strings return "null" (http://code.google.com/p/android/issues/detail?id=13830) - String url = params.isNull("uri") ? null : params.getString("uri"); - Boolean external = params.getBoolean("external"); - int parentId = params.getInt("parentId"); - String title = params.getString("title"); - + private Tab addTab(int id, String url, boolean external, int parentId, String title) { final Tab tab = new Tab(id, url, external, parentId, title); mTabs.put(id, tab); mOrder.add(tab); @@ -245,7 +238,20 @@ public class Tabs implements GeckoEventListener { } } else if (event.equals("Tab:Added")) { Log.i(LOGTAG, "Received message from Gecko: " + SystemClock.uptimeMillis() + " - Tab:Added"); - Tab tab = addTab(message); + + int id = message.getInt("tabID"); + Tab tab = null; + + if (mTabs.containsKey(id)) { + tab = mTabs.get(id); + } else { + tab = addTab(id, + message.isNull("uri") ? null : message.getString("uri"), + message.getBoolean("external"), + message.getInt("parentId"), + message.getString("title")); + } + if (message.getBoolean("selected")) selectTab(tab.getId()); if (message.getBoolean("delayLoad")) @@ -446,18 +452,30 @@ public class Tabs implements GeckoEventListener { */ public void loadUrl(String url, String searchEngine, int parentId, int flags) { JSONObject args = new JSONObject(); + int tabId = -1; + try { args.put("url", url); args.put("engine", searchEngine); args.put("parentId", parentId); args.put("userEntered", (flags & LOADURL_USER_ENTERED) != 0); args.put("newTab", (flags & LOADURL_NEW_TAB) != 0); + + if ((flags & LOADURL_NEW_TAB) != 0) { + tabId = getNextTabId(); + args.put("tabID", tabId); + addTab(tabId, null, false, parentId, url); + } } catch (Exception e) { Log.e(LOGTAG, "error building JSON arguments"); } Log.d(LOGTAG, "Sending message to Gecko: " + SystemClock.uptimeMillis() + " - Tab:Load"); GeckoAppShell.sendEventToGecko(GeckoEvent.createBroadcastEvent("Tab:Load", args.toString())); + + if (tabId != -1) { + selectTab(tabId); + } } /** @@ -480,4 +498,13 @@ public class Tabs implements GeckoEventListener { loadUrl(url, null, getSelectedTab().getId(), LOADURL_NEW_TAB); } + + /** + * Gets the next tab ID. + * + * This method is invoked via JNI. + */ + public static int getNextTabId() { + return sTabId.getAndIncrement(); + } } diff --git a/mobile/android/chrome/content/browser.js b/mobile/android/chrome/content/browser.js index 6aa914cf067..5e2d5a4eb4d 100644 --- a/mobile/android/chrome/content/browser.js +++ b/mobile/android/chrome/content/browser.js @@ -13,6 +13,7 @@ Cu.import("resource://gre/modules/XPCOMUtils.jsm"); Cu.import("resource://gre/modules/Services.jsm"); Cu.import("resource://gre/modules/AddonManager.jsm"); Cu.import("resource://gre/modules/FileUtils.jsm"); +Cu.import("resource://gre/modules/JNI.jsm"); #ifdef ACCESSIBILITY Cu.import("resource://gre/modules/accessibility/AccessFu.jsm"); @@ -1082,7 +1083,8 @@ var BrowserApp = { let params = { selected: true, parentId: ("parentId" in data) ? data.parentId : -1, - flags: flags + flags: flags, + tabID: data.tabID }; let url = data.url; @@ -2232,8 +2234,6 @@ nsBrowserAccess.prototype = { }; -let gTabIDFactory = 0; - // track the last known screen size so that new tabs // get created with the right size rather than being 1x1 let gScreenWidth = 1; @@ -2289,7 +2289,16 @@ Tab.prototype = { } catch (e) {} if (!aParams.zombifying) { - this.id = ++gTabIDFactory; + if ("tabID" in aParams) { + this.id = aParams.tabID; + } else { + let jni = new JNI(); + let cls = jni.findClass("org.mozilla.gecko.Tabs"); + let method = jni.getStaticMethodID(cls, "getNextTabId", "()I"); + this.id = jni.callStaticIntMethod(cls, method); + jni.close(); + } + this.desktopMode = ("desktopMode" in aParams) ? aParams.desktopMode : false; let message = { @@ -6632,7 +6641,6 @@ var WebappsUI = { get iconSize() { let iconSize = 64; try { - Cu.import("resource://gre/modules/JNI.jsm"); let jni = new JNI(); let cls = jni.findClass("org.mozilla.gecko.GeckoAppShell"); let method = jni.getStaticMethodID(cls, "getPreferredIconSize", "()I");