diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/DoricContext.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/DoricContext.java index 54beea8f..638ddb24 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/DoricContext.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/DoricContext.java @@ -1,9 +1,8 @@ package com.github.pengfeizhou.doric; import com.github.pengfeizhou.doric.async.AsyncResult; -import com.github.pengfeizhou.doric.bridge.DoricNativePlugin; -import com.github.pengfeizhou.doric.extension.DoricPluginInfo; -import com.github.pengfeizhou.doric.async.SettableFuture; +import com.github.pengfeizhou.doric.plugin.DoricNativePlugin; +import com.github.pengfeizhou.doric.extension.bridge.DoricPluginInfo; import com.github.pengfeizhou.jscore.JSDecoder; import java.util.HashMap; @@ -27,7 +26,11 @@ public class DoricContext { } public AsyncResult callEntity(String methodName, Object... args) { - return DoricDriver.getInstance().invokeContextMethod(mContextId, methodName, args); + return getDriver().invokeContextEntityMethod(mContextId, methodName, args); + } + + public DoricDriver getDriver() { + return DoricDriver.getInstance(); } @@ -36,8 +39,22 @@ public class DoricContext { } public void teardown() { - DoricDriver.getInstance().destroyContext(mContextId); - mPluginMap.clear(); + DoricDriver.getInstance().destroyContext(mContextId).setCallback(new AsyncResult.Callback() { + @Override + public void onResult(Boolean result) { + + } + + @Override + public void onError(Throwable t) { + + } + + @Override + public void onFinish() { + mPluginMap.clear(); + } + }); } public DoricNativePlugin obtainPlugin(DoricPluginInfo doricPluginInfo) { diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/DoricDriver.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/DoricDriver.java index a314137b..6cc88648 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/DoricDriver.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/DoricDriver.java @@ -1,11 +1,20 @@ package com.github.pengfeizhou.doric; +import android.os.Handler; +import android.os.Looper; + +import com.github.pengfeizhou.doric.async.AsyncCall; import com.github.pengfeizhou.doric.async.AsyncResult; import com.github.pengfeizhou.doric.engine.DoricJSEngine; +import com.github.pengfeizhou.doric.utils.DoricConstant; +import com.github.pengfeizhou.doric.utils.DoricLog; import com.github.pengfeizhou.jscore.JSDecoder; import java.util.Map; +import java.util.concurrent.Callable; import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; import java.util.concurrent.atomic.AtomicInteger; /** @@ -17,9 +26,32 @@ public class DoricDriver { private final DoricJSEngine doricJSEngine; private final AtomicInteger counter = new AtomicInteger(); private final Map doricContextMap = new ConcurrentHashMap<>(); + private final ExecutorService mBridgeExecutor; + private final Handler mUIHandler; + private final Handler mJSHandler; - public AsyncResult invokeContextMethod(final String contextId, final String method, final Object... args) { - return doricJSEngine.invokeContextEntityMethod(contextId, method, args); + public AsyncResult invokeContextEntityMethod(final String contextId, final String method, final Object... args) { + final Object[] nArgs = new Object[args.length + 2]; + nArgs[0] = contextId; + nArgs[1] = method; + if (args.length > 0) { + System.arraycopy(args, 0, nArgs, 2, args.length); + } + return invokeDoricMethod(DoricConstant.DORIC_CONTEXT_INVOKE, nArgs); + } + + public AsyncResult invokeDoricMethod(final String method, final Object... args) { + return AsyncCall.ensureRunInHandler(mJSHandler, new Callable() { + @Override + public JSDecoder call() { + try { + return doricJSEngine.invokeDoricMethod(method, args); + } catch (Exception e) { + DoricLog.e("invokeDoricMethod(%s,...),error is %s", method, e.getLocalizedMessage()); + return new JSDecoder(null); + } + } + }); } private static class Inner { @@ -28,6 +60,21 @@ public class DoricDriver { private DoricDriver() { doricJSEngine = new DoricJSEngine(); + mBridgeExecutor = Executors.newCachedThreadPool(); + mUIHandler = new Handler(Looper.getMainLooper()); + mJSHandler = doricJSEngine.getJSHandler(); + } + + public void runOnJS(Runnable runnable) { + mJSHandler.post(runnable); + } + + public void runOnUI(Runnable runnable) { + mUIHandler.post(runnable); + } + + public void runIndependently(Runnable runnable) { + mBridgeExecutor.execute(runnable); } public static DoricDriver getInstance() { @@ -35,26 +82,37 @@ public class DoricDriver { } DoricContext createContext(final String script, final String source) { - String contextId = String.valueOf(counter.incrementAndGet()); + final String contextId = String.valueOf(counter.incrementAndGet()); DoricContext doricContext = new DoricContext(contextId); - doricJSEngine.prepareContext(contextId, script, source); doricContextMap.put(contextId, doricContext); + AsyncCall.ensureRunInHandler(mJSHandler, new Callable() { + @Override + public Boolean call() { + try { + doricJSEngine.prepareContext(contextId, script, source); + return true; + } catch (Exception e) { + DoricLog.e("createContext %s error is %s", source, e.getLocalizedMessage()); + return false; + } + } + }); + return doricContext; } - void destroyContext(final String contextId) { - doricJSEngine.destroyContext(contextId).setCallback(new AsyncResult.Callback() { + AsyncResult destroyContext(final String contextId) { + return AsyncCall.ensureRunInHandler(mJSHandler, new Callable() { @Override - public void onResult(Boolean result) { - } - - @Override - public void onError(Throwable t) { - } - - @Override - public void onFinish() { - doricContextMap.remove(contextId); + public Boolean call() { + try { + doricJSEngine.destroyContext(contextId); + doricContextMap.remove(contextId); + return true; + } catch (Exception e) { + DoricLog.e("destroyContext %s error is %s", contextId, e.getLocalizedMessage()); + return false; + } } }); } diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/bridge/ModalPlugin.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/bridge/ModalPlugin.java deleted file mode 100644 index 0a0760ea..00000000 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/bridge/ModalPlugin.java +++ /dev/null @@ -1,23 +0,0 @@ -package com.github.pengfeizhou.doric.bridge; - -import com.github.pengfeizhou.doric.DoricContext; -import com.github.pengfeizhou.doric.extension.DoricComponent; -import com.github.pengfeizhou.doric.extension.DoricMethod; - -/** - * @Description: Doric - * @Author: pengfei.zhou - * @CreateDate: 2019-07-18 - */ -@DoricComponent(name = "modal") -public class ModalPlugin extends DoricNativePlugin { - - protected ModalPlugin(DoricContext doricContext) { - super(doricContext); - } - - @DoricMethod(name = "toast") - public void toast() { - - } -} diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/engine/DoricJSEngine.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/engine/DoricJSEngine.java index 7cfbef2b..4f489a5f 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/engine/DoricJSEngine.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/engine/DoricJSEngine.java @@ -7,20 +7,16 @@ import android.os.Message; import android.text.TextUtils; import com.github.pengfeizhou.doric.Doric; -import com.github.pengfeizhou.doric.async.AsyncCall; -import com.github.pengfeizhou.doric.extension.DoricBridgeExtension; -import com.github.pengfeizhou.doric.async.AsyncResult; +import com.github.pengfeizhou.doric.extension.bridge.DoricBridgeExtension; import com.github.pengfeizhou.doric.utils.DoricConstant; import com.github.pengfeizhou.doric.utils.DoricLog; -import com.github.pengfeizhou.doric.async.SettableFuture; -import com.github.pengfeizhou.doric.extension.DoricTimerExtension; +import com.github.pengfeizhou.doric.extension.timer.DoricTimerExtension; import com.github.pengfeizhou.doric.utils.DoricUtils; import com.github.pengfeizhou.jscore.JSDecoder; import com.github.pengfeizhou.jscore.JavaFunction; import com.github.pengfeizhou.jscore.JavaValue; import java.util.ArrayList; -import java.util.concurrent.Callable; /** * @Description: Doric @@ -49,6 +45,10 @@ public class DoricJSEngine implements Handler.Callback, DoricTimerExtension.Time mDoricBridgeExtension = new DoricBridgeExtension(); } + public Handler getJSHandler() { + return mJSHandler; + } + private void initJSExecutor() { mDoricJSE = new DoricJSExecutor(); @@ -157,34 +157,12 @@ public class DoricJSEngine implements Handler.Callback, DoricTimerExtension.Time mDoricJSE.loadJS(script, "Assets://" + assetName); } - public AsyncResult prepareContext(final String contextId, final String script, final String source) { - return AsyncCall.ensureRunInHandler(mJSHandler, new Callable() { - @Override - public Boolean call() throws Exception { - try { - mDoricJSE.loadJS(packageContextScript(contextId, script), "Context://" + source); - return true; - } catch (Exception e) { - DoricLog.e("Prepare Context error:%s", e.getLocalizedMessage()); - return false; - } - } - }); + public void prepareContext(final String contextId, final String script, final String source) { + mDoricJSE.loadJS(packageContextScript(contextId, script), "Context://" + source); } - public AsyncResult destroyContext(final String contextId) { - return AsyncCall.ensureRunInHandler(mJSHandler, new Callable() { - @Override - public Boolean call() throws Exception { - try { - mDoricJSE.loadJS(String.format(DoricConstant.TEMPLATE_CONTEXT_DESTROY, contextId), "_Context://" + contextId); - return true; - } catch (Exception e) { - DoricLog.e("Prepare Context error:%s", e.getLocalizedMessage()); - return false; - } - } - }); + public void destroyContext(final String contextId) { + mDoricJSE.loadJS(String.format(DoricConstant.TEMPLATE_CONTEXT_DESTROY, contextId), "_Context://" + contextId); } private String packageContextScript(String contextId, String content) { @@ -195,7 +173,7 @@ public class DoricJSEngine implements Handler.Callback, DoricTimerExtension.Time return String.format(DoricConstant.TEMPLATE_MODULE, moduleName, content); } - public AsyncResult invokeContextEntityMethod(final String contextId, final String method, final Object... args) { + public JSDecoder invokeContextEntityMethod(final String contextId, final String method, final Object... args) { final Object[] nArgs = new Object[args.length + 2]; nArgs[0] = contextId; nArgs[1] = method; @@ -206,18 +184,13 @@ public class DoricJSEngine implements Handler.Callback, DoricTimerExtension.Time } - public AsyncResult invokeDoricMethod(final String method, final Object... args) { - return AsyncCall.ensureRunInHandler(mJSHandler, new Callable() { - @Override - public JSDecoder call() throws Exception { - ArrayList values = new ArrayList<>(); - for (Object arg : args) { - values.add(DoricUtils.toJavaValue(arg)); - } - return mDoricJSE.invokeMethod(DoricConstant.GLOBAL_DORIC, method, - values.toArray(new JavaValue[values.size()]), true); - } - }); + public JSDecoder invokeDoricMethod(final String method, final Object... args) { + ArrayList values = new ArrayList<>(); + for (Object arg : args) { + values.add(DoricUtils.toJavaValue(arg)); + } + return mDoricJSE.invokeMethod(DoricConstant.GLOBAL_DORIC, method, + values.toArray(new JavaValue[values.size()]), true); } @Override diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricBridgeExtension.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricBridgeExtension.java similarity index 88% rename from Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricBridgeExtension.java rename to Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricBridgeExtension.java index c25cb2bf..a3b6db6b 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricBridgeExtension.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricBridgeExtension.java @@ -1,11 +1,11 @@ -package com.github.pengfeizhou.doric.extension; +package com.github.pengfeizhou.doric.extension.bridge; import android.text.TextUtils; import com.github.pengfeizhou.doric.DoricContext; import com.github.pengfeizhou.doric.DoricDriver; -import com.github.pengfeizhou.doric.bridge.DoricNativePlugin; -import com.github.pengfeizhou.doric.bridge.ModalPlugin; +import com.github.pengfeizhou.doric.plugin.DoricNativePlugin; +import com.github.pengfeizhou.doric.plugin.ModalPlugin; import com.github.pengfeizhou.doric.utils.DoricLog; import com.github.pengfeizhou.jscore.JSDecoder; import com.github.pengfeizhou.jscore.JavaValue; @@ -50,6 +50,7 @@ public class DoricBridgeExtension { DoricLog.e("Cannot find plugin method in class:%s,method:%s", module, methodName); return new JavaValue(false); } + DoricMethod doricMethod = method.getAnnotation(DoricMethod.class); Class[] classes = method.getParameterTypes(); diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricComponent.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricComponent.java similarity index 88% rename from Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricComponent.java rename to Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricComponent.java index 1bbde0c0..b37417dd 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricComponent.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricComponent.java @@ -1,4 +1,4 @@ -package com.github.pengfeizhou.doric.extension; +package com.github.pengfeizhou.doric.extension.bridge; import java.lang.annotation.Documented; import java.lang.annotation.ElementType; diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricMethod.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricMethod.java similarity index 71% rename from Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricMethod.java rename to Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricMethod.java index f32fe1c5..218abe7d 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricMethod.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricMethod.java @@ -1,4 +1,4 @@ -package com.github.pengfeizhou.doric.extension; +package com.github.pengfeizhou.doric.extension.bridge; import java.lang.annotation.Documented; import java.lang.annotation.ElementType; @@ -16,4 +16,12 @@ import java.lang.annotation.Target; @Retention(RetentionPolicy.RUNTIME) public @interface DoricMethod { String name() default ""; + + Mode thread() default Mode.INDEPENDENT; + + enum Mode { + UI, + JS, + INDEPENDENT, + } } diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricPluginInfo.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricPluginInfo.java similarity index 93% rename from Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricPluginInfo.java rename to Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricPluginInfo.java index 6f0cf6c8..890893bd 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricPluginInfo.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricPluginInfo.java @@ -1,9 +1,9 @@ -package com.github.pengfeizhou.doric.extension; +package com.github.pengfeizhou.doric.extension.bridge; import android.text.TextUtils; import com.github.pengfeizhou.doric.DoricContext; -import com.github.pengfeizhou.doric.bridge.DoricNativePlugin; +import com.github.pengfeizhou.doric.plugin.DoricNativePlugin; import com.github.pengfeizhou.doric.utils.DoricLog; import java.lang.reflect.Constructor; @@ -21,7 +21,6 @@ public class DoricPluginInfo { private Constructor pluginConstructor; private Map methodMap = new ConcurrentHashMap<>(); - public boolean stringify = false; private String name; public DoricPluginInfo(Class pluginClass) { diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricPromise.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricPromise.java new file mode 100644 index 00000000..60a1ec2e --- /dev/null +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/bridge/DoricPromise.java @@ -0,0 +1,36 @@ +package com.github.pengfeizhou.doric.extension.bridge; + +import com.github.pengfeizhou.doric.DoricContext; +import com.github.pengfeizhou.doric.utils.DoricConstant; +import com.github.pengfeizhou.jscore.JavaValue; + +/** + * @Description: com.github.pengfeizhou.doric.extension.bridge + * @Author: pengfei.zhou + * @CreateDate: 2019-07-19 + */ +public class DoricPromise { + private final DoricContext context; + private final String callbackId; + + public DoricPromise(DoricContext context, String callbackId) { + this.context = context; + this.callbackId = callbackId; + } + + public void resolve(JavaValue... javaValue) { + context.getDriver().invokeDoricMethod( + DoricConstant.DORIC_BRIDGE_RESOLVE, + context.getContextId(), + callbackId, + javaValue); + } + + public void reject(JavaValue... javaValue) { + context.getDriver().invokeDoricMethod( + DoricConstant.DORIC_BRIDGE_REJECT, + context.getContextId(), + callbackId, + javaValue); + } +} diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricTimerExtension.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/timer/DoricTimerExtension.java similarity index 97% rename from Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricTimerExtension.java rename to Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/timer/DoricTimerExtension.java index 0078df0a..0f169e98 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/DoricTimerExtension.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/extension/timer/DoricTimerExtension.java @@ -1,4 +1,4 @@ -package com.github.pengfeizhou.doric.extension; +package com.github.pengfeizhou.doric.extension.timer; import android.os.Handler; import android.os.Looper; diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/bridge/DoricNativePlugin.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/plugin/DoricNativePlugin.java similarity index 90% rename from Android/doric/src/main/java/com/github/pengfeizhou/doric/bridge/DoricNativePlugin.java rename to Android/doric/src/main/java/com/github/pengfeizhou/doric/plugin/DoricNativePlugin.java index 8344f564..f3bbe602 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/bridge/DoricNativePlugin.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/plugin/DoricNativePlugin.java @@ -1,4 +1,4 @@ -package com.github.pengfeizhou.doric.bridge; +package com.github.pengfeizhou.doric.plugin; import com.github.pengfeizhou.doric.DoricContext; diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/plugin/ModalPlugin.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/plugin/ModalPlugin.java new file mode 100644 index 00000000..63f3e39d --- /dev/null +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/plugin/ModalPlugin.java @@ -0,0 +1,24 @@ +package com.github.pengfeizhou.doric.plugin; + +import com.github.pengfeizhou.doric.DoricContext; +import com.github.pengfeizhou.doric.extension.bridge.DoricComponent; +import com.github.pengfeizhou.doric.extension.bridge.DoricMethod; +import com.github.pengfeizhou.jscore.JSDecoder; + +/** + * @Description: Doric + * @Author: pengfei.zhou + * @CreateDate: 2019-07-18 + */ +@DoricComponent(name = "modal") +public class ModalPlugin extends DoricNativePlugin { + + protected ModalPlugin(DoricContext doricContext) { + super(doricContext); + } + + @DoricMethod(name = "toast", thread = DoricMethod.Mode.UI) + public void toast(JSDecoder decoder) { + + } +} diff --git a/Android/doric/src/main/java/com/github/pengfeizhou/doric/utils/DoricConstant.java b/Android/doric/src/main/java/com/github/pengfeizhou/doric/utils/DoricConstant.java index 1038d921..7a33e835 100644 --- a/Android/doric/src/main/java/com/github/pengfeizhou/doric/utils/DoricConstant.java +++ b/Android/doric/src/main/java/com/github/pengfeizhou/doric/utils/DoricConstant.java @@ -11,7 +11,6 @@ public class DoricConstant { public static final String DORIC_MODULE_LIB = "./index"; - public static final String INJECT_LOG = "nativeLog"; public static final String INJECT_REQUIRE = "nativeRequire"; public static final String INJECT_TIMER_SET = "nativeSetTimer"; @@ -42,4 +41,6 @@ public class DoricConstant { public static final String DORIC_CONTEXT_RELEASE = "jsReleaseContext"; public static final String DORIC_CONTEXT_INVOKE = "jsCallEntityMethod"; public static final String DORIC_TIMER_CALLBACK = "jsCallbackTimer"; + public static final String DORIC_BRIDGE_RESOLVE = "jsCallResolve"; + public static final String DORIC_BRIDGE_REJECT = "jsCallReject"; }