You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cordova.apache.org by ag...@apache.org on 2014/12/10 21:42:13 UTC

android commit: CB-3679 Move splashscreen logic into splashscreen plugin

Repository: cordova-android
Updated Branches:
  refs/heads/master f953e6adb -> 27f1181d5


CB-3679 Move splashscreen logic into splashscreen plugin

Tried as hard as possible for this not to be a breaking change (all
symbols were preserved). Planning to remove delegating symbols in 4.0.x
though.

Also for backwards compatability - a copy of the plugin is bundled. It
will likewise be removed in 4.0.x


Project: http://git-wip-us.apache.org/repos/asf/cordova-android/repo
Commit: http://git-wip-us.apache.org/repos/asf/cordova-android/commit/27f1181d
Tree: http://git-wip-us.apache.org/repos/asf/cordova-android/tree/27f1181d
Diff: http://git-wip-us.apache.org/repos/asf/cordova-android/diff/27f1181d

Branch: refs/heads/master
Commit: 27f1181d53a6feca77f5bb645892f7d357a6f35a
Parents: f953e6a
Author: Andrew Grieve <ag...@chromium.org>
Authored: Mon Nov 17 23:46:39 2014 -0800
Committer: Andrew Grieve <ag...@chromium.org>
Committed: Wed Dec 10 15:40:03 2014 -0500

----------------------------------------------------------------------
 .../src/org/apache/cordova/CordovaActivity.java | 198 +++------------
 .../src/org/apache/cordova/CordovaWebView.java  |  11 +-
 .../apache/cordova/SplashScreenInternal.java    | 252 +++++++++++++++++++
 3 files changed, 296 insertions(+), 165 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cordova-android/blob/27f1181d/framework/src/org/apache/cordova/CordovaActivity.java
----------------------------------------------------------------------
diff --git a/framework/src/org/apache/cordova/CordovaActivity.java b/framework/src/org/apache/cordova/CordovaActivity.java
index 816b12b..b61fa98 100755
--- a/framework/src/org/apache/cordova/CordovaActivity.java
+++ b/framework/src/org/apache/cordova/CordovaActivity.java
@@ -24,17 +24,13 @@ import java.util.Locale;
 import java.util.concurrent.ExecutorService;
 import java.util.concurrent.Executors;
 
-import org.apache.cordova.CordovaInterface;
-import org.apache.cordova.CordovaPlugin;
-import org.apache.cordova.LOG;
+import org.json.JSONArray;
 import org.json.JSONException;
 import org.json.JSONObject;
 
 import android.annotation.SuppressLint;
 import android.app.Activity;
 import android.app.AlertDialog;
-import android.app.Dialog;
-import android.app.ProgressDialog;
 import android.content.Context;
 import android.content.DialogInterface;
 import android.content.Intent;
@@ -42,7 +38,6 @@ import android.graphics.Color;
 import android.media.AudioManager;
 import android.net.Uri;
 import android.os.Bundle;
-import android.os.Handler;
 import android.util.Log;
 import android.view.Display;
 import android.view.KeyEvent;
@@ -100,7 +95,6 @@ public class CordovaActivity extends Activity implements CordovaInterface {
     @Deprecated // Will be removed. Use findViewById() to retrieve views.
     protected LinearLayout root;
 
-    protected ProgressDialog spinnerDialog = null;
     private final ExecutorService threadPool = Executors.newCachedThreadPool();
 
     private static int ACTIVITY_STARTING = 0;
@@ -117,9 +111,10 @@ public class CordovaActivity extends Activity implements CordovaInterface {
      */
 
     // Draw a splash screen using an image located in the drawable resource directory.
-    // This is not the same as calling super.loadSplashscreen(url)
+    @Deprecated // Use "SplashScreen" preference instead.
     protected int splashscreen = 0;
-    protected int splashscreenTime = 3000;
+    @Deprecated // Use "SplashScreenDelay" preference instead.
+    protected int splashscreenTime = -1;
 
     // LoadUrl timeout value in msec (default of 20 sec)
     protected int loadUrlTimeoutValue = 20000;
@@ -267,9 +262,6 @@ public class CordovaActivity extends Activity implements CordovaInterface {
                 ViewGroup.LayoutParams.MATCH_PARENT,
                 1.0F));
 
-        // Add web view but make it invisible while loading URL
-        appView.setVisibility(View.INVISIBLE);
-        
         // need to remove appView from any existing parent before invoking root.addView(appView)
         ViewParent parent = appView.getParent();
         if ((parent != null) && (parent != root)) {
@@ -334,6 +326,13 @@ public class CordovaActivity extends Activity implements CordovaInterface {
     public void init(CordovaWebView webView, CordovaWebViewClient webViewClient, CordovaChromeClient webChromeClient) {
         LOG.d(TAG, "CordovaActivity.init()");
 
+        if (splashscreenTime >= 0) {
+            preferences.set("SplashScreenDelay", splashscreenTime);
+        }
+        if (splashscreen != 0) {
+            preferences.set("SplashDrawableId", splashscreen);
+        }
+
         appView = webView != null ? webView : makeWebView();
         if (appView.pluginManager == null) {
             appView.init(this, webViewClient != null ? webViewClient : makeWebViewClient(appView),
@@ -361,36 +360,10 @@ public class CordovaActivity extends Activity implements CordovaInterface {
         if (appView == null) {
             init();
         }
-        this.splashscreenTime = preferences.getInteger("SplashScreenDelay", this.splashscreenTime);
-        String splash = preferences.getString("SplashScreen", null);
-        if(this.splashscreenTime > 0 && splash != null)
-        {
-            this.splashscreen = getResources().getIdentifier(splash, "drawable", getClass().getPackage().getName());;
-            if(this.splashscreen != 0)
-            {
-                this.showSplashScreen(this.splashscreenTime);
-            }
-        }
-        
         // If keepRunning
         this.keepRunning = preferences.getBoolean("KeepRunning", true);
 
-        //Check if the view is attached to anything
-        if(appView.getParent() != null)
-        {
-            // Then load the spinner
-            this.loadSpinner();
-        }
-        //Load the correct splashscreen
-        
-        if(this.splashscreen != 0)
-        {
-            this.appView.loadUrl(url, this.splashscreenTime);
-        }
-        else
-        {
-            this.appView.loadUrl(url);
-        }
+        appView.loadUrlIntoView(url, true);
     }
 
     /**
@@ -400,44 +373,12 @@ public class CordovaActivity extends Activity implements CordovaInterface {
      * @param url
      * @param time              The number of ms to wait before loading webview
      */
+    @Deprecated // Use loadUrl(String url) instead.
     public void loadUrl(final String url, int time) {
 
         this.splashscreenTime = time;
         this.loadUrl(url);
     }
-    
-    /*
-     * Load the spinner
-     */
-    void loadSpinner() {
-
-        // If loadingDialog property, then show the App loading dialog for first page of app
-        String loading = null;
-        if ((this.appView == null) || !this.appView.canGoBack()) {
-            loading = preferences.getString("LoadingDialog", null);
-        }
-        else {
-            loading = preferences.getString("LoadingPageDialog", null);
-        }
-        if (loading != null) {
-
-            String title = "";
-            String message = "Loading Application...";
-
-            if (loading.length() > 0) {
-                int comma = loading.indexOf(',');
-                if (comma > 0) {
-                    title = loading.substring(0, comma);
-                    message = loading.substring(comma + 1);
-                }
-                else {
-                    title = "";
-                    message = loading;
-                }
-            }
-            this.spinnerStart(title, message);
-        }
-    }
 
     @Deprecated
     public void cancelLoadUrl() {
@@ -588,9 +529,6 @@ public class CordovaActivity extends Activity implements CordovaInterface {
         {
             this.appView.handlePause(this.keepRunning);
         }
-
-        // hide the splash screen to avoid leaking a window
-        this.removeSplashScreen();
     }
 
     /**
@@ -645,9 +583,6 @@ public class CordovaActivity extends Activity implements CordovaInterface {
         LOG.d(TAG, "CordovaActivity.onDestroy()");
         super.onDestroy();
 
-        // hide the splash screen to avoid leaking a window
-        this.removeSplashScreen();
-
         if (this.appView != null) {
             appView.handleDestroy();
         }
@@ -697,28 +632,20 @@ public class CordovaActivity extends Activity implements CordovaInterface {
      * @param title         Title of the dialog
      * @param message       The message of the dialog
      */
+    @Deprecated // Call this directly on SplashScreen plugin instead.
     public void spinnerStart(final String title, final String message) {
-        if (this.spinnerDialog != null) {
-            this.spinnerDialog.dismiss();
-            this.spinnerDialog = null;
-        }
-        final CordovaActivity me = this;
-        this.spinnerDialog = ProgressDialog.show(CordovaActivity.this, title, message, true, true,
-                new DialogInterface.OnCancelListener() {
-                    public void onCancel(DialogInterface dialog) {
-                        me.spinnerDialog = null;
-                    }
-                });
+        JSONArray args = new JSONArray();
+        args.put(title);
+        args.put(message);
+        doSplashScreenAction("spinnerStart", args);
     }
 
     /**
      * Stop spinner - Must be called from UI thread
      */
+    @Deprecated // Call this directly on SplashScreen plugin instead.
     public void spinnerStop() {
-        if (this.spinnerDialog != null && this.spinnerDialog.isShowing()) {
-            this.spinnerDialog.dismiss();
-            this.spinnerDialog = null;
-        }
+        doSplashScreenAction("spinnerStop", null);
     }
 
     /**
@@ -810,8 +737,6 @@ public class CordovaActivity extends Activity implements CordovaInterface {
             // Load URL on UI thread
             me.runOnUiThread(new Runnable() {
                 public void run() {
-                    // Stop "app loading" spinner if showing
-                    me.spinnerStop();
                     me.appView.showWebPage(errorUrl, false, true, null);
                 }
             });
@@ -915,62 +840,34 @@ public class CordovaActivity extends Activity implements CordovaInterface {
         }
     }
 
-    protected Dialog splashDialog;
+    private void doSplashScreenAction(String action, JSONArray args) {
+        CordovaPlugin p = appView.pluginManager.getPlugin("org.apache.cordova.splashscreeninternal");
+        if (p != null) {
+            args = args == null ? new JSONArray() : args;
+            try {
+                p.execute(action, args, null);
+            } catch (JSONException e) {
+                e.printStackTrace();
+            }
+        }
+    }
 
     /**
      * Removes the Dialog that displays the splash screen
      */
+    @Deprecated
     public void removeSplashScreen() {
-        if (splashDialog != null && splashDialog.isShowing()) {
-            splashDialog.dismiss();
-            splashDialog = null;
-        }
+        doSplashScreenAction("hide", null);
     }
 
     /**
      * Shows the splash screen over the full Activity
      */
     @SuppressWarnings("deprecation")
+    @Deprecated
     protected void showSplashScreen(final int time) {
-        final CordovaActivity that = this;
-
-        Runnable runnable = new Runnable() {
-            public void run() {
-                // Get reference to display
-                Display display = getWindowManager().getDefaultDisplay();
-
-                // Create the layout for the dialog
-                LinearLayout root = new LinearLayout(that.getActivity());
-                root.setMinimumHeight(display.getHeight());
-                root.setMinimumWidth(display.getWidth());
-                root.setOrientation(LinearLayout.VERTICAL);
-                root.setBackgroundColor(preferences.getInteger("backgroundColor", Color.BLACK));
-                root.setLayoutParams(new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
-                        ViewGroup.LayoutParams.MATCH_PARENT, 0.0F));
-                root.setBackgroundResource(that.splashscreen);
-                
-                // Create and show the dialog
-                splashDialog = new Dialog(that, android.R.style.Theme_Translucent_NoTitleBar);
-                // check to see if the splash screen should be full screen
-                if ((getWindow().getAttributes().flags & WindowManager.LayoutParams.FLAG_FULLSCREEN)
-                        == WindowManager.LayoutParams.FLAG_FULLSCREEN) {
-                    splashDialog.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
-                            WindowManager.LayoutParams.FLAG_FULLSCREEN);
-                }
-                splashDialog.setContentView(root);
-                splashDialog.setCancelable(false);
-                splashDialog.show();
-
-                // Set Runnable to remove splash screen just in case
-                final Handler handler = new Handler();
-                handler.postDelayed(new Runnable() {
-                    public void run() {
-                        removeSplashScreen();
-                    }
-                }, time);
-            }
-        };
-        this.runOnUiThread(runnable);
+        preferences.set("SplashScreenDelay", time);
+        doSplashScreenAction("show", null);
     }
 
     @Override
@@ -1015,28 +912,7 @@ public class CordovaActivity extends Activity implements CordovaInterface {
             LOG.d(TAG, "onMessage(" + id + "," + data + ")");
         }
 
-        if ("splashscreen".equals(id)) {
-            if ("hide".equals(data.toString())) {
-                this.removeSplashScreen();
-            }
-            else {
-                // If the splash dialog is showing don't try to show it again
-                if (this.splashDialog == null || !this.splashDialog.isShowing()) {
-                    String splashResource = preferences.getString("SplashScreen", null);
-                    if (splashResource != null) {
-                        splashscreen = getResources().getIdentifier(splashResource, "drawable", getClass().getPackage().getName());
-                    }
-                    this.showSplashScreen(this.splashscreenTime);
-                }
-            }
-        }
-        else if ("spinner".equals(id)) {
-            if ("stop".equals(data.toString())) {
-                this.spinnerStop();
-                this.appView.setVisibility(View.VISIBLE);
-            }
-        }
-        else if ("onReceivedError".equals(id)) {
+        if ("onReceivedError".equals(id)) {
             JSONObject d = (JSONObject) data;
             try {
                 this.onReceivedError(d.getInt("errorCode"), d.getString("description"), d.getString("url"));

http://git-wip-us.apache.org/repos/asf/cordova-android/blob/27f1181d/framework/src/org/apache/cordova/CordovaWebView.java
----------------------------------------------------------------------
diff --git a/framework/src/org/apache/cordova/CordovaWebView.java b/framework/src/org/apache/cordova/CordovaWebView.java
index 62a641b..feec5a9 100755
--- a/framework/src/org/apache/cordova/CordovaWebView.java
+++ b/framework/src/org/apache/cordova/CordovaWebView.java
@@ -156,6 +156,9 @@ public class CordovaWebView extends WebView {
         resourceApi = new CordovaResourceApi(this.getContext(), pluginManager);
 
         pluginManager.addService("App", "org.apache.cordova.App");
+        // This will be removed in 4.0.x in favour of the plugin not being bundled.
+        pluginManager.addService(new PluginEntry("SplashScreenInternal", "org.apache.cordova.SplashScreenInternal", true));
+        pluginManager.init();
         initWebViewSettings();
         exposeJsInterface();
     }
@@ -383,8 +386,11 @@ public class CordovaWebView extends WebView {
         initIfNecessary();
 
         if (recreatePlugins) {
+            // Don't re-initialize on first load.
+            if (loadedUrl != null) {
+                this.pluginManager.init();
+            }
             this.loadedUrl = url;
-            this.pluginManager.init();
         }
 
         // Create a timeout timer for loadUrl
@@ -462,9 +468,6 @@ public class CordovaWebView extends WebView {
         else {
 
             LOG.d(TAG, "loadUrlIntoView(%s, %d)", url, time);
-
-            // Send message to show splashscreen now if desired
-            this.postMessage("splashscreen", "show");
         }
 
         // Load url

http://git-wip-us.apache.org/repos/asf/cordova-android/blob/27f1181d/framework/src/org/apache/cordova/SplashScreenInternal.java
----------------------------------------------------------------------
diff --git a/framework/src/org/apache/cordova/SplashScreenInternal.java b/framework/src/org/apache/cordova/SplashScreenInternal.java
new file mode 100644
index 0000000..605fce7
--- /dev/null
+++ b/framework/src/org/apache/cordova/SplashScreenInternal.java
@@ -0,0 +1,252 @@
+/*
+       Licensed to the Apache Software Foundation (ASF) under one
+       or more contributor license agreements.  See the NOTICE file
+       distributed with this work for additional information
+       regarding copyright ownership.  The ASF licenses this file
+       to you under the Apache License, Version 2.0 (the
+       "License"); you may not use this file except in compliance
+       with the License.  You may obtain a copy of the License at
+
+         http://www.apache.org/licenses/LICENSE-2.0
+
+       Unless required by applicable law or agreed to in writing,
+       software distributed under the License is distributed on an
+       "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+       KIND, either express or implied.  See the License for the
+       specific language governing permissions and limitations
+       under the License.
+*/
+
+package org.apache.cordova;
+
+import android.app.Dialog;
+import android.app.ProgressDialog;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.graphics.Color;
+import android.os.Handler;
+import android.view.Display;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.WindowManager;
+import android.widget.LinearLayout;
+
+import org.json.JSONArray;
+import org.json.JSONException;
+
+// This file is a copy of SplashScreen.java from cordova-plugin-splashscreen, and is required only
+// for pre-4.0 Cordova as a transition path to it being extracted into the plugin.
+public class SplashScreenInternal extends CordovaPlugin {
+    private static final String LOG_TAG = "SplashScreenInternal";
+    private static Dialog splashDialog;
+    private static ProgressDialog spinnerDialog;
+    private static boolean firstShow = true;
+
+    @Override
+    protected void pluginInitialize() {
+        if (!firstShow) {
+            return;
+        }
+        // Make WebView invisible while loading URL
+        webView.setVisibility(View.INVISIBLE);
+        int drawableId = preferences.getInteger("SplashDrawableId", 0);
+        if (drawableId == 0) {
+            String splashResource = preferences.getString("SplashScreen", null);
+            if (splashResource != null) {
+                drawableId = cordova.getActivity().getResources().getIdentifier(splashResource, "drawable", cordova.getActivity().getClass().getPackage().getName());
+                preferences.set("SplashDrawableId", drawableId);
+            }
+        }
+
+        firstShow = false;
+        loadSpinner();
+        showSplashScreen();
+    }
+
+    @Override
+    public void onPause(boolean multitasking) {
+        // hide the splash screen to avoid leaking a window
+        this.removeSplashScreen();
+    }
+
+    @Override
+    public void onDestroy() {
+        // hide the splash screen to avoid leaking a window
+        this.removeSplashScreen();
+        firstShow = true;
+    }
+
+    @Override
+    public boolean execute(String action, JSONArray args, CallbackContext callbackContext) throws JSONException {
+        if (action.equals("hide")) {
+            cordova.getActivity().runOnUiThread(new Runnable() {
+                public void run() {
+                    webView.postMessage("splashscreen", "hide");
+                }
+            });
+        } else if (action.equals("show")) {
+            cordova.getActivity().runOnUiThread(new Runnable() {
+                public void run() {
+                    webView.postMessage("splashscreen", "show");
+                }
+            });
+        } else if (action.equals("spinnerStart")) {
+            final String title = args.getString(0);
+            final String message = args.getString(1);
+            cordova.getActivity().runOnUiThread(new Runnable() {
+                public void run() {
+                    spinnerStart(title, message);
+                }
+            });
+        } else {
+            return false;
+        }
+
+        callbackContext.success();
+        return true;
+    }
+
+    @Override
+    public Object onMessage(String id, Object data) {
+        if ("splashscreen".equals(id)) {
+            if ("hide".equals(data.toString())) {
+                this.removeSplashScreen();
+            } else {
+                this.showSplashScreen();
+            }
+        } else if ("spinner".equals(id)) {
+            if ("stop".equals(data.toString())) {
+                this.spinnerStop();
+                webView.setVisibility(View.VISIBLE);
+            }
+        } else if ("onReceivedError".equals(id)) {
+            spinnerStop();
+        }
+        return null;
+    }
+
+    private void removeSplashScreen() {
+        cordova.getActivity().runOnUiThread(new Runnable() {
+            public void run() {
+                if (splashDialog != null && splashDialog.isShowing()) {
+                    splashDialog.dismiss();
+                    splashDialog = null;
+                }
+            }
+        });
+    }
+
+    /**
+     * Shows the splash screen over the full Activity
+     */
+    @SuppressWarnings("deprecation")
+    private void showSplashScreen() {
+        final int splashscreenTime = preferences.getInteger("SplashScreenDelay", 3000);
+        final int drawableId = preferences.getInteger("SplashDrawableId", 0);
+
+        // If the splash dialog is showing don't try to show it again
+        if (this.splashDialog != null && splashDialog.isShowing()) {
+            return;
+        }
+        if (drawableId == 0 || splashscreenTime <= 0) {
+            return;
+        }
+
+        cordova.getActivity().runOnUiThread(new Runnable() {
+            public void run() {
+                // Get reference to display
+                Display display = cordova.getActivity().getWindowManager().getDefaultDisplay();
+                Context context = webView.getContext();
+
+                // Create the layout for the dialog
+                LinearLayout root = new LinearLayout(context);
+                root.setMinimumHeight(display.getHeight());
+                root.setMinimumWidth(display.getWidth());
+                root.setOrientation(LinearLayout.VERTICAL);
+
+                // TODO: Use the background color of the webview's parent instead of using the
+                // preference.
+                root.setBackgroundColor(preferences.getInteger("backgroundColor", Color.BLACK));
+                root.setLayoutParams(new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
+                        ViewGroup.LayoutParams.MATCH_PARENT, 0.0F));
+                root.setBackgroundResource(drawableId);
+
+                // Create and show the dialog
+                splashDialog = new Dialog(context, android.R.style.Theme_Translucent_NoTitleBar);
+                // check to see if the splash screen should be full screen
+                if ((cordova.getActivity().getWindow().getAttributes().flags & WindowManager.LayoutParams.FLAG_FULLSCREEN)
+                        == WindowManager.LayoutParams.FLAG_FULLSCREEN) {
+                    splashDialog.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
+                            WindowManager.LayoutParams.FLAG_FULLSCREEN);
+                }
+                splashDialog.setContentView(root);
+                splashDialog.setCancelable(false);
+                splashDialog.show();
+
+                // Set Runnable to remove splash screen just in case
+                final Handler handler = new Handler();
+                handler.postDelayed(new Runnable() {
+                    public void run() {
+                        removeSplashScreen();
+                    }
+                }, splashscreenTime);
+            }
+        });
+    }
+
+    /*
+     * Load the spinner
+     */
+    private void loadSpinner() {
+        // If loadingDialog property, then show the App loading dialog for first page of app
+        String loading = null;
+        if (webView.canGoBack()) {
+            loading = preferences.getString("LoadingDialog", null);
+        }
+        else {
+            loading = preferences.getString("LoadingPageDialog", null);
+        }
+        if (loading != null) {
+            String title = "";
+            String message = "Loading Application...";
+
+            if (loading.length() > 0) {
+                int comma = loading.indexOf(',');
+                if (comma > 0) {
+                    title = loading.substring(0, comma);
+                    message = loading.substring(comma + 1);
+                }
+                else {
+                    title = "";
+                    message = loading;
+                }
+            }
+            spinnerStart(title, message);
+        }
+    }
+
+    private void spinnerStart(final String title, final String message) {
+        cordova.getActivity().runOnUiThread(new Runnable() {
+            public void run() {
+                spinnerStop();
+                spinnerDialog = ProgressDialog.show(webView.getContext(), title, message, true, true,
+                        new DialogInterface.OnCancelListener() {
+                            public void onCancel(DialogInterface dialog) {
+                                spinnerDialog = null;
+                            }
+                        });
+            }
+        });
+    }
+
+    private void spinnerStop() {
+        cordova.getActivity().runOnUiThread(new Runnable() {
+            public void run() {
+                if (spinnerDialog != null && spinnerDialog.isShowing()) {
+                    spinnerDialog.dismiss();
+                    spinnerDialog = null;
+                }
+            }
+        });
+    }
+}


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@cordova.apache.org
For additional commands, e-mail: commits-help@cordova.apache.org