Note that there are some explanatory texts on larger screens.

plurals
  1. POEmbedding Rhino on Android Problems
    primarykey
    data
    text
    <p>When trying to add an object to the JS environment using Rhino 1.7 r2 on Android 2.2 I always get a NullPointerException. I have boiled the class down to the bare minimum to get this exception, and I can't figure out why. Here's the code that always produces the exception:</p> <pre><code>public class StartActivity extends Activity { /** Rhino context object */ private Context mCX; /** Rhino script scope object */ private Scriptable mScope; /** Called when the activity is first created. */ @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Create our context and turn off compilation mCX = Context.enter(); mCX.setOptimizationLevel( -1 ); // Initialize the scope mScope = mCX.initStandardObjects(); Object insertObj; // This line always throws the exception. insertObj = Context.javaToJS( this, mScope ); // We never get here ScriptableObject.putProperty( mScope, "platform", insertObj ); setContentView(R.layout.main); } } </code></pre> <p>Changing the troublesome line to some else like <code>insertObj = Context.javaToJS( null, mScope );</code> or really anything but <code>this</code> and the problem doesn't occur. </p> <p>Here is the stacktrace:</p> <pre><code>E/AndroidRuntime( 308): FATAL EXCEPTION: main E/AndroidRuntime( 308): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.me/com.me.StartActivity}: java.lang.NullPointerException E/AndroidRuntime( 308): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2663) E/AndroidRuntime( 308): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2679) E/AndroidRuntime( 308): at android.app.ActivityThread.access$2300(ActivityThread.java:125) E/AndroidRuntime( 308): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2033) E/AndroidRuntime( 308): at android.os.Handler.dispatchMessage(Handler.java:99) E/AndroidRuntime( 308): at android.os.Looper.loop(Looper.java:123) E/AndroidRuntime( 308): at android.app.ActivityThread.main(ActivityThread.java:4627) E/AndroidRuntime( 308): at java.lang.reflect.Method.invokeNative(Native Method) E/AndroidRuntime( 308): at java.lang.reflect.Method.invoke(Method.java:521) E/AndroidRuntime( 308): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:868) E/AndroidRuntime( 308): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:626) E/AndroidRuntime( 308): at dalvik.system.NativeStart.main(Native Method) E/AndroidRuntime( 308): Caused by: java.lang.NullPointerException E/AndroidRuntime( 308): at org.mozilla.javascript.net.sf.retrotranslator.runtime.impl.MethodDescriptor.getInstance(MethodDescriptor.java:137) E/AndroidRuntime( 308): at org.mozilla.javascript.net.sf.retrotranslator.runtime.java.lang.reflect._Constructor.isVarArgs(_Constructor.java:83) E/AndroidRuntime( 308): at org.mozilla.javascript.jdk15.VMBridge_jdk15.isVarArgs(VMBridge_jdk15.java:66) E/AndroidRuntime( 308): at org.mozilla.javascript.MemberBox.init(MemberBox.java:86) E/AndroidRuntime( 308): at org.mozilla.javascript.MemberBox.&lt;init&gt;(MemberBox.java:72) E/AndroidRuntime( 308): at org.mozilla.javascript.JavaMembers.reflect(JavaMembers.java:667) E/AndroidRuntime( 308): at org.mozilla.javascript.JavaMembers.&lt;init&gt;(JavaMembers.java:76) E/AndroidRuntime( 308): at org.mozilla.javascript.JavaMembers.lookupClass(JavaMembers.java:838) E/AndroidRuntime( 308): at org.mozilla.javascript.NativeJavaObject.initMembers(NativeJavaObject.java:90) E/AndroidRuntime( 308): at org.mozilla.javascript.NativeJavaObject.&lt;init&gt;(NativeJavaObject.java:80) E/AndroidRuntime( 308): at org.mozilla.javascript.NativeJavaObject.&lt;init&gt;(NativeJavaObject.java:70) E/AndroidRuntime( 308): at org.mozilla.javascript.WrapFactory.wrapAsJavaObject(WrapFactory.java:149) E/AndroidRuntime( 308): at org.mozilla.javascript.WrapFactory.wrap(WrapFactory.java:105) E/AndroidRuntime( 308): at org.mozilla.javascript.Context.javaToJS(Context.java:1698) E/AndroidRuntime( 308): at com.me.android.StartActivity.onCreate(StartActivity.java:34) E/AndroidRuntime( 308): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1047) E/AndroidRuntime( 308): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2627) E/AndroidRuntime( 308): ... 11 more </code></pre> <p>Any insight as to why this is happening would be greatly appreciated.</p> <p><strong>[EDIT]</strong> After some serious googling and head smashing I discovered the <code>ScriptableObject.defineClass</code> method and tried using that instead, following the examples in the Rhino documentation, however now I get a RuntimeException "ReferenceError: 'DeviceInterface' is not defined." I know this is possible, as Rhino is what the <a href="http://code.google.com/p/android-scripting/" rel="nofollow">ASE</a> uses for its JavaScript support.</p> <p>Here is the new code which throws the RuntimeException:</p> <pre><code>public class StartActivity extends Activity { /** Rhino context object */ private Context mCX; /** Rhino script scope object */ private Scriptable mScope; /** Called when the activity is first created. */ @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Create our context and turn off compilation mCX = Context.enter(); mCX.setOptimizationLevel( -1 ); // Initialize the scope mScope = mCX.initStandardObjects(); try{ ScriptableObject.defineClass( mScope, DeviceInterface.class ); } catch( Exception e ) { Log.e("StartActivity", e.toString()); } // This is the line that throws the exception mCX.evaluateString(mScope, "var p = new DeviceInterface();", "", 1, null); setContentView(R.layout.main); } } </code></pre> <p>And the DeviceInterface class:</p> <pre><code>public class DeviceInterface extends ScriptableObject { static private final long serialVersionUID = 1L; static public void init ( Scriptable scope ) { Log.i( "JSInterface", "Init called" ); } public DeviceInterface() { logger( "Created new JSInterface Object" ); } @Override public String getClassName() { return "DeviceInterface"; } public void jsFunction_logger( String message ) { logger( message ); } private void logger( String message ) { if( message.contains("[alrt]") ) Log.e( "JSInterface", message ); else if( message.contains("[info]") ) Log.i( "JSInterface", message ); else Log.d( "JSInterface", message ); } } </code></pre>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload