我有一段使用 ScriptEngineManager 和 ScriptEngine 类在Java中执行JavaScript代码的代码。但是它能够在Java SE中正常工作,但在Android环境下无法正常工作 - SDK显示缺少类的错误。是否可能在Android中执行JS代码?谢谢。
我有一段使用 ScriptEngineManager 和 ScriptEngine 类在Java中执行JavaScript代码的代码。但是它能够在Java SE中正常工作,但在Android环境下无法正常工作 - SDK显示缺少类的错误。是否可能在Android中执行JS代码?谢谢。
AndroidJSCore 是一个非常好的库。这里还有另一个我写的用于评估 JavaScript 的小型库:
https://github.com/evgenyneu/js-evaluator-for-android
jsEvaluator.evaluate("function hello(){ return 'Hello world!'; } hello();", new JsCallback() {
@Override
public void onResult(final String result) {
// get result here (optional)
}
});
它在幕后创建一个WebView。适用于Android 3及以上版本。
findViewById()
函数在活动中使用。但是要使用JavaScript,您可以创建一个包含JavaScript代码的HTML文件。下面的示例可能会有所帮助。Webview browser=(Webview) findViewById(R.main.browser); //if you gave the id as browser
browser.getSettings().setJavaScriptEnabled(true); //Yes you have to do it
browser.loadUrl("file:///android_asset/JsPage.html"); //If you put the HTML file in asset folder of android
请记住,JS代码将在WebView中运行而不是本地环境中运行,因此您可能会在模拟器中遇到延迟或FPS缓慢的情况。但是,在实际手机上使用时,代码可能会快速运行,这取决于手机的速度。
http://divineprogrammer.blogspot.com/2009/11/javascript-rhino-on-android.html 可以作为起点。ScriptEngine是一个Java工具,但Android并没有JVM,而是DalvikVM,两者不尽相同但有相似之处。
原始回答:AndroidJSCore是Webkit的JavaScriptCore C库的Android Java JNI封装。它受到iOS 7中原生包含的Objective-C JavaScriptCore框架的启发。在应用程序中本地使用JavaScript而无需使用注入到庞大、缓慢、受安全限制的WebView中的JavaScript是非常有用的,这对于许多类型的应用程序(如游戏或支持插件的平台)非常有用。然而,它的使用受到人为限制,因为该框架仅受到iOS的支持。大多数开发者希望使用能够跨越主要移动操作系统的技术。AndroidJSCore旨在支持此要求。
例如,您可以共享Java对象并进行异步调用:
public interface IAsyncObj {
public void callMeMaybe(Integer ms, JSValue callback) throws JSException;
}
public class AsyncObj extends JSObject implements IAsyncObj {
public AsyncObj(JSContext ctx) throws JSException { super(ctx,IAsyncObj.class); }
@Override
public void callMeMaybe(Integer ms, JSValue callback) throws JSException {
new CallMeLater(ms).execute(callback.toObject());
}
private class CallMeLater extends AsyncTask<JSObject, Void, JSObject> {
public CallMeLater(Integer ms) {
this.ms = ms;
}
private final Integer ms;
@Override
protected JSObject doInBackground(JSObject... params) {
try {
Thread.sleep(ms);
} catch (InterruptedException e) {
Thread.interrupted();
}
return params[0];
}
@Override
protected void onPostExecute(JSObject callback) {
JSValue args [] = { new JSValue(context,
"This is a delayed message from Java!") };
try {
callback.callAsFunction(null, args);
} catch (JSException e) {
System.out.println(e);
}
}
}
}
public void run() throws JSException {
AsyncObj async = new AsyncObj(context);
context.property("async",async);
context.evaluateScript(
"log('Please call me back in 5 seconds');\n" +
"async.callMeMaybe(5000, function(msg) {\n" +
" alert(msg);\n" +
" log('Whoomp. There it is.');\n" +
"});\n" +
"log('async.callMeMaybe() has returned, but wait for it ...');\n"
);
}
compile 'com.eclipsesource.j2v8:j2v8_android:3.0.5@aar'
它有相当简单的API,但我除了maven repository中的javadoc之外,在网上没有找到任何文档。他们博客上的文章也很有用。
这篇文章中的代码示例:
public static void main(String[] args) {
V8 runtime = V8.createV8Runtime();
int result = runtime.executeIntegerScript(""
+ "var hello = 'hello, ';\n"
+ "var world = 'world!';\n"
+ "hello.concat(world).length;\n");
System.out.println(result);
runtime.release();
}
import com.eclipsesource.v8.V8;
- ybdesireObject[] params = new Object[] { "javaScriptParam" };
// Every Rhino VM begins with the enter()
// This Context is not Android's Context
Context rhino = Context.enter();
// Turn off optimization to make Rhino Android compatible
rhino.setOptimizationLevel(-1);
try {
Scriptable scope = rhino.initStandardObjects();
// Note the forth argument is 1, which means the JavaScript source has
// been compressed to only one line using something like YUI
rhino.evaluateString(scope, javaScriptCode, "JavaScript", 1, null);
// Get the functionName defined in JavaScriptCode
Object obj = scope.get(functionNameInJavaScriptCode, scope);
if (obj instanceof Function) {
Function jsFunction = (Function) obj;
// Call the function with params
Object jsResult = jsFunction.call(rhino, scope, scope, params);
// Parse the jsResult object to a String
String result = Context.toString(jsResult);
}
} finally {
Context.exit();
}
data:text/html, <html contenteditable>
<title>
记事本 </title>
<script>
alert('Abhasker Alert Test on Mobile'); </script>
</html>