Thanks to @shrhdk and his theta4j library, I was able to build a dual-fisheye plug-in in under an hour. This is a simple template for developers to customize and finish a plug-in with the features they want.
Source Code
Complete source code for this simple plug-in available on GitHub.
Pre-compiled apk
There is a pre-compiled apk in the release folder. To test this apk, you will need to have a THETA V in developer mode.
Interval Shooting Modification
If you want to set up interval shooting, you can use this example:
Adjusting Color and Other Photo Options
if you want to adjust options of each picture such as colorTemperature, an example is here:
theta4j tutorials
HTTP Response from Camera
The response branch shows how to get the camera HTTP response from the WebAPI command. It shows how to receive the URI for the last picture taken.
Get and Set Camera Options
The options branch shows to to get and set camera settings. ISO, exposure compensation, capture mode.
Audio and Visual Indicators of Camera Status
The indicators branch shows use of a camera beep and magenta LED to show the start of a multi-picture loop.
Display Last File to Vysor, Getting URL and Path
The response-vysor branch displays the last file taken to the virtual THETA screen using Vysor. It also outputs the URI and the file path for the last file taken.
@codetricity, thanks for building this, it looks really useful. I was not able to take pictures with it yet.
Few notes from my testing:
It seemed like the plug-in would not show up in the list of plug-ins in the RICOH desktop app until after I rebooted the camera after installing the theta4j-fisheye apk with adb. Might be just a glitch on my side, but I noticed it.
Did not have to set permissions using Vysor. Obvious, I guess, since it does not use the camera or storage or other things. But I noticed this, too.
After theta4jfisheye apk is installed and set as the boot plug-in, it switches in to Plug-in Mode, no problem. But when I press the Shutter button, nothing. If I jump out of Plug-in Mode, it takes regular pictures, like it’s supposed to.
I double-checked to make sure it’s properly set as the boot plug-in. It is.
This was the log you sent me. There’s something about a non-protected broadcast that I don’t understand. It appears to work now on your camera.
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:93)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:93)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:126)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:254)
06-12 12:06:01.991 2290 2966 W System.err: at okhttp3.RealCall.execute(RealCall.java:92)
06-12 12:06:01.992 2290 2966 W System.err: at org.theta4j.osc.OSCClient.httpPost(OSCClient.java:419)
06-12 12:06:01.992 2290 2966 W System.err: at org.theta4j.osc.OSCClient.commandExecute(OSCClient.java:189)
06-12 12:06:01.992 2290 2966 W System.err: at org.theta4j.osc.OSCClient.setOptions(OSCClient.java:341)
06-12 12:06:01.992 2290 2966 W System.err: at org.theta4j.osc.OSCClient.setOption(OSCClient.java:326)
06-12 12:06:01.992 2290 2966 W System.err: at org.theta4j.webapi.Theta.setOption(Theta.java:225)
06-12 12:06:01.992 2290 2966 W System.err: at org.codecakes.theta4jfisheye.MainActivity$1.lambda$onKeyDown$0$MainActivity$1(MainActivity.java:32)
06-12 12:06:01.992 2290 2966 W System.err: at org.codecakes.theta4jfisheye.-$$Lambda$MainActivity$1$sO2BKa_sW5VyLC8Q5G_KAgF7vtM.run(lambda)
06-12 12:06:01.992 2290 2966 W System.err: at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:428)
06-12 12:06:01.992 2290 2966 W System.err: at java.util.concurrent.FutureTask.run(FutureTask.java:237)
06-12 12:06:01.993 2290 2966 W System.err: at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133)
06-12 12:06:01.993 2290 2966 W System.err: at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
06-12 12:06:01.993 2290 2966 W System.err: at java.lang.Thread.run(Thread.java:761)
06-12 12:06:02.276 1172 1330 D WindowManager: interceptKeyTq keycode=27 interactive=true keyguardActive=false policyFlags=22000000
06-12 12:06:02.277 1172 1329 D WindowManager: interceptKeyTi keyCode=27 down=false repeatCount=0 keyguardOn=false mHomePressed=false canceled=false
06-12 12:06:02.283 1902 1902 W ContextImpl: Calling a method in the system process without a qualified user: android.app.ContextImpl.sendBroadcast:877 android.content.ContextWrapper.sendBroadcast:421 com.theta360.receptor.view.CameraView.onKeyUp:2329 android.view.KeyEvent.dispatch:2715 android.view.View.dispatchKeyEvent:9960
06-12 12:06:02.285 1172 1830 E ActivityManager: Sending non-protected broadcast com.theta360.plugin.ACTION_KEY_UP from system 1902:com.theta360.receptor/1000 pkg com.theta360.receptor
06-12 12:06:02.285 1172 1830 E ActivityManager: java.lang.Throwable
06-12 12:06:02.285 1172 1830 E ActivityManager: at com.android.server.am.ActivityManagerService.checkBroadcastFromSystem(ActivityManagerService.java:18095)
06-12 12:06:02.285 1172 1830 E ActivityManager: at com.android.server.am.ActivityManagerService.broadcastIntentLocked(ActivityManagerService.java:18576)
06-12 12:06:02.285 1172 1830 E ActivityManager: at com.android.server.am.ActivityManagerService.broadcastIntent(ActivityManagerService.java:18758)
06-12 12:06:02.285 1172 1830 E ActivityManager: at android.app.ActivityManagerNative.onTransact(ActivityManagerNative.java:499)
06-12 12:06:02.285 1172 1830 E ActivityManager: at com.android.server.am.ActivityManagerService.onTransact(ActivityManagerService.java:2869)
06-12 12:06:02.285 1172 1830 E ActivityManager: at android.os.Binder.execTransact(Binder.java:565)
06-12 12:06:02.299 1172 1830 E ActivityManager: Sending non-protected broadcast com.theta360.plugin.ACTION_KEY_UP from system 1902:com.theta360.receptor/1000 pkg com.theta360.receptor
06-12 12:06:02.299 1172 1830 E ActivityManager: java.lang.Throwable
06-12 12:06:02.299 1172 1830 E ActivityManager: at com.android.server.am.ActivityManagerService.checkBroadcastFromSystem(ActivityManagerService.java:18095)
06-12 12:06:02.299 1172 1830 E ActivityManager: at com.android.server.am.ActivityManagerService.broadcastIntentLocked(ActivityManagerService.java:18667)
06-12 12:06:02.299 1172 1830 E ActivityManager: at com.android.server.am.ActivityManagerService.broadcastIntent(ActivityManagerService.java:18758)
06-12 12:06:02.299 1172 1830 E ActivityManager: at android.app.ActivityManagerNative.onTransact(ActivityManagerNative.java:499)
06-12 12:06:02.299 1172 1830 E ActivityManager: at com.android.server.am.ActivityManagerService.onTransact(ActivityManagerService.java:2869)
06-12 12:06:02.299 1172 1830 E ActivityManager: at android.os.Binder.execTransact(Binder.java:565)
06-12 12:06:02.753 577 577 I MSM-irqbalance: Decided to move IRQ5 from CPU3 [P:0] to CPU4 [P:1] (banned)
06-12 12:06:02.754 577 577 I MSM-irqbalance: Decided to move IRQ5 from CPU0 [P:0] to CPU6 [P:1] (banned)
06-12 12:06:02.755 577 577 I MSM-irqbalance: Decided to move IRQ5 from CPU1 [P:0] to CPU5 [P:1] (banned)
06-12 12:06:07.406 1172 1330 D WindowManager: interceptKeyTq keycode=27 interactive=true keyguardActive=false policyFlags=22000000
06-12 12:06:07.406 1172 1329 D PowerManagerService: userActivityNoUpdateLocked: eventTime=833610, event=1, flags=0x0, uid=1000
06-12 12:06:07.407 1172 1329 D WindowManager: interceptKeyTi keyCode=27 down=true repeatCount=0 keyguardOn=false mHomePressed=false canceled=false
06-12 12:06:07.411 1902 1902 W ContextImpl: Calling a method in the system process without a qualified user: android.app.ContextImpl.sendBroadcast:877 android.content.ContextWrapper.sendBroadcast:421 com.theta360.receptor.view.CameraView.onKeyDown:2215 android.view.KeyEvent.dispatch:2691 android.view.View.dispatchKeyEvent:9960
06-12 12:06:07.413 1172 1182 E ActivityManager: Sending non-protected broadcast com.theta360.plugin.ACTION_KEY_DOWN from system 1902:com.theta360.receptor/1000 pkg com.theta360.receptor
06-12 12:06:07.413 1172 1182 E ActivityManager: java.lang.Throwable
06-12 12:06:07.413 1172 1182 E ActivityManager: at com.android.server.am.ActivityManagerService.checkBroadcastFromSystem(ActivityManagerService.java:18095)
It works with the Z1 in DNG mode.
With the Z1 using DNG/RAW images, I can only reduce the time down to 6 seconds. If I try to go lower, it will not take all the images.