OSDN Git Service

Ricoh Theta対応。 Theta S に対応できた。
authorMRSa <mrsa@myad.jp>
Sat, 18 Jan 2020 03:48:13 +0000 (12:48 +0900)
committerMRSa <mrsa@myad.jp>
Sat, 18 Jan 2020 03:48:13 +0000 (12:48 +0900)
app/src/main/java/net/osdn/gokigen/pkremote/camera/utils/SimpleHttpClient.java
app/src/main/java/net/osdn/gokigen/pkremote/camera/vendor/theta/wrapper/ThetaInterfaceProvider.java
app/src/main/java/net/osdn/gokigen/pkremote/camera/vendor/theta/wrapper/playback/ThetaCameraContent.java [new file with mode: 0644]
app/src/main/java/net/osdn/gokigen/pkremote/camera/vendor/theta/wrapper/playback/ThetaPlaybackControl.java
app/src/main/java/net/osdn/gokigen/pkremote/preference/IPreferencePropertyAccessor.java
app/src/main/java/net/osdn/gokigen/pkremote/preference/theta/ThetaPreferenceFragment.java
app/src/main/res/values-ja/strings.xml
app/src/main/res/values/strings.xml
app/src/main/res/xml/preferences_theta.xml

index b2c8d40..7b1c078 100644 (file)
@@ -16,6 +16,7 @@ import java.util.List;
 import java.util.Map;
 
 import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
 
 /**
  *
@@ -132,7 +133,24 @@ public class SimpleHttpClient
      */
     public static void httpGetBytes(String url, Map<String, String> setProperty, int timeoutMs, @NonNull IReceivedMessageCallback callback)
     {
+        httpCommandBytes(url, "GET", null, setProperty, null, timeoutMs, callback);
+    }
+
+    /**
+     *
+     *
+     *
+     */
+    public static void httpPostBytes(String url, String postData, Map<String, String> setProperty, int timeoutMs, @NonNull IReceivedMessageCallback callback)
+    {
+        httpCommandBytes(url, "POST", postData, setProperty, null, timeoutMs, callback);
+    }
+
+    private static void httpCommandBytes(@NonNull String url, @NonNull String requestMethod, @Nullable String postData, @Nullable Map<String, String> setProperty, @Nullable String contentType, int timeoutMs, @NonNull IReceivedMessageCallback callback)
+    {
         HttpURLConnection httpConn = null;
+        OutputStream outputStream = null;
+        OutputStreamWriter writer = null;
         InputStream inputStream = null;
         int timeout = timeoutMs;
         if (timeoutMs < 0)
@@ -140,12 +158,12 @@ public class SimpleHttpClient
             timeout = DEFAULT_TIMEOUT;
         }
 
-        //  HTTP GETメソッドで要求を投げる
+        //  HTTP メソッドで要求を送出
         try
         {
             final URL urlObj = new URL(url);
             httpConn = (HttpURLConnection) urlObj.openConnection();
-            httpConn.setRequestMethod("GET");
+            httpConn.setRequestMethod(requestMethod);
             if (setProperty != null)
             {
                 for (String key : setProperty.keySet())
@@ -154,9 +172,29 @@ public class SimpleHttpClient
                     httpConn.setRequestProperty(key, value);
                 }
             }
+            if (contentType != null)
+            {
+                httpConn.setRequestProperty("Content-Type", contentType);
+            }
             httpConn.setConnectTimeout(timeout);
             httpConn.setReadTimeout(timeout);
-            httpConn.connect();
+            if (postData == null)
+            {
+                httpConn.connect();
+            }
+            else
+            {
+                httpConn.setDoInput(true);
+                httpConn.setDoOutput(true);
+                outputStream = httpConn.getOutputStream();
+                writer = new OutputStreamWriter(outputStream, "UTF-8");
+                writer.write(postData);
+                writer.flush();
+                writer.close();
+                writer = null;
+                outputStream.close();
+                outputStream = null;
+            }
 
             int responseCode = httpConn.getResponseCode();
             if (responseCode == HttpURLConnection.HTTP_OK)
@@ -165,7 +203,7 @@ public class SimpleHttpClient
             }
             if (inputStream == null)
             {
-                Log.w(TAG, "httpGet: Response Code Error: " + responseCode + ": " + url);
+                Log.w(TAG, " http " + requestMethod + " Response Code Error: " + responseCode + ": " + url);
                 callback.onErrorOccurred(new NullPointerException());
                 callback.onCompleted();
                 return;
@@ -173,7 +211,7 @@ public class SimpleHttpClient
         }
         catch (Exception e)
         {
-            Log.w(TAG, "httpGet: " + url + "  " + e.getMessage());
+            Log.w(TAG, "http " + requestMethod + " " + url + "  " + e.getMessage());
             e.printStackTrace();
             if (httpConn != null)
             {
@@ -183,6 +221,31 @@ public class SimpleHttpClient
             callback.onCompleted();
             return;
         }
+        finally
+        {
+            try
+            {
+                if (writer != null)
+                {
+                    writer.close();
+                }
+            }
+            catch (Exception e)
+            {
+                e.printStackTrace();
+            }
+            try
+            {
+                if (outputStream != null)
+                {
+                    outputStream.close();
+                }
+            }
+            catch (IOException e)
+            {
+                e.printStackTrace();
+            }
+        }
 
         // 応答を確認する
         try
@@ -256,6 +319,7 @@ public class SimpleHttpClient
         callback.onCompleted();
     }
 
+
     public static String getValue(List<String> valueList)
     {
         // 応答ヘッダの値切り出し用...
@@ -276,15 +340,32 @@ public class SimpleHttpClient
         return (values.toString());
     }
 
+    public static Bitmap httpGetBitmap(String url, Map<String, String> setProperty, int timeoutMs)
+    {
+        return (httpCommandBitmap(url, "GET", null, setProperty, null, timeoutMs));
+    }
+
     /**
      *
      *
      *
      */
-    public static Bitmap httpGetBitmap(String url, Map<String, String> setProperty, int timeoutMs)
+    public static Bitmap httpPostBitmap(String url, String postData, int timeoutMs)
+    {
+        return (httpCommandBitmap(url, "POST", postData, null, null, timeoutMs));
+    }
+
+    /**
+     *
+     *
+     *
+     */
+    private static Bitmap httpCommandBitmap(@NonNull String url, @NonNull String requestMethod, @Nullable String postData, @Nullable Map<String, String> setProperty, @Nullable String contentType, int timeoutMs)
     {
         HttpURLConnection httpConn = null;
         InputStream inputStream = null;
+        OutputStream outputStream = null;
+        OutputStreamWriter writer = null;
         Bitmap bmp = null;
 
         int timeout = timeoutMs;
@@ -293,12 +374,12 @@ public class SimpleHttpClient
             timeout = DEFAULT_TIMEOUT;
         }
 
-        //  HTTP GETメソッドで要求を投げる
+        //  HTTP メソッドで要求を送出
         try
         {
             final URL urlObj = new URL(url);
             httpConn = (HttpURLConnection) urlObj.openConnection();
-            httpConn.setRequestMethod("GET");
+            httpConn.setRequestMethod(requestMethod);
             if (setProperty != null)
             {
                 for (String key : setProperty.keySet())
@@ -307,9 +388,30 @@ public class SimpleHttpClient
                     httpConn.setRequestProperty(key, value);
                 }
             }
+            if (contentType != null)
+            {
+                httpConn.setRequestProperty("Content-Type", contentType);
+            }
             httpConn.setConnectTimeout(timeout);
             httpConn.setReadTimeout(timeout);
-            httpConn.connect();
+
+            if (postData == null)
+            {
+                httpConn.connect();
+            }
+            else
+            {
+                httpConn.setDoInput(true);
+                httpConn.setDoOutput(true);
+                outputStream = httpConn.getOutputStream();
+                writer = new OutputStreamWriter(outputStream, "UTF-8");
+                writer.write(postData);
+                writer.flush();
+                writer.close();
+                writer = null;
+                outputStream.close();
+                outputStream = null;
+            }
 
             int responseCode = httpConn.getResponseCode();
             if (responseCode == HttpURLConnection.HTTP_OK)
@@ -322,14 +424,14 @@ public class SimpleHttpClient
             }
             if (inputStream == null)
             {
-                Log.w(TAG, "httpGet: Response Code Error: " + responseCode + ": " + url);
+                Log.w(TAG, "http: (" + requestMethod + ") Response Code Error: " + responseCode + ": " + url);
                 return (null);
             }
             inputStream.close();
         }
         catch (Exception e)
         {
-            Log.w(TAG, "httpGet: " + url + "  " + e.getMessage());
+            Log.w(TAG, "http: (" + requestMethod + ") " + url + "  " + e.getMessage());
             e.printStackTrace();
             if (httpConn != null)
             {
@@ -337,6 +439,31 @@ public class SimpleHttpClient
             }
             return (null);
         }
+        finally
+        {
+            try
+            {
+                if (writer != null)
+                {
+                    writer.close();
+                }
+            }
+            catch (Exception e)
+            {
+                e.printStackTrace();
+            }
+            try
+            {
+                if (outputStream != null)
+                {
+                    outputStream.close();
+                }
+            }
+            catch (IOException e)
+            {
+                e.printStackTrace();
+            }
+        }
         return (bmp);
     }
 
@@ -350,7 +477,6 @@ public class SimpleHttpClient
         return (httpCommand(url, "POST", postData, null, null, timeoutMs));
     }
 
-
     /**
      *
      *
index 53796d8..7d6e123 100644 (file)
@@ -70,7 +70,7 @@ public class ThetaInterfaceProvider implements IThetaInterfaceProvider, IDisplay
         //this.provider = provider;
         thetaConnection = new ThetaConnection(context, provider);
         buttonControl = new ThetaButtonControl();
-        playbackControl = new ThetaPlaybackControl(context, communicationTimeoutMs);
+        playbackControl = new ThetaPlaybackControl(context, communicationTimeoutMs, 65000);
         hardwareStatus = new ThetaHardwareStatus();
         runMode = new ThetaRunMode();
     }
diff --git a/app/src/main/java/net/osdn/gokigen/pkremote/camera/vendor/theta/wrapper/playback/ThetaCameraContent.java b/app/src/main/java/net/osdn/gokigen/pkremote/camera/vendor/theta/wrapper/playback/ThetaCameraContent.java
new file mode 100644 (file)
index 0000000..8f95ce9
--- /dev/null
@@ -0,0 +1,171 @@
+package net.osdn.gokigen.pkremote.camera.vendor.theta.wrapper.playback;
+
+import android.util.Log;
+
+import net.osdn.gokigen.pkremote.camera.interfaces.playback.ICameraContent;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+import java.util.Locale;
+
+public class ThetaCameraContent implements ICameraContent
+{
+    private final String TAG = toString();
+
+    private final String path;
+    private final String name;
+    private final String url;
+    private final String size;
+    private final String date;
+
+    ThetaCameraContent(String name, String path, String url, String size, String date)
+    {
+        this.path = path;
+        this.name = name;
+        this.url = url;
+        this.size = size;
+        this.date = date;
+        // Log.v(TAG, " [" + " " + "] " + name + " " + path + " (" + size + ") " + date + " " + url);
+    }
+
+    @Override
+    public String getCameraId()
+    {
+        return ("");
+    }
+
+    @Override
+    public String getCardId()
+    {
+        return ("");
+    }
+
+    @Override
+    public String getContentPath()
+    {
+        if (url == null)
+        {
+            return (getContentPathFromPath());
+        }
+        return (getContentPathFromUrl());
+    }
+
+    private String getContentPathFromPath()
+    {
+        // データ内容 : "100RICOH/R0010015.JPG"
+        try
+        {
+            int index = path.indexOf("/");
+            return (path.substring(0, index));
+        }
+        catch (Exception e)
+        {
+            e.printStackTrace();
+        }
+        return (path);
+    }
+
+    private String getContentPathFromUrl()
+    {
+        // データ内容 : "http://192.168.1.1/files/abcde/100RICOH/R0010032.JPG"
+        try
+        {
+            int index = url.indexOf("/");
+            return (url.substring(0, index));
+        }
+        catch (Exception e)
+        {
+            e.printStackTrace();
+        }
+        return (url);
+    }
+
+    @Override
+    public String getContentName()
+    {
+        return (name);
+    }
+
+    @Override
+    public String getOriginalName()
+    {
+        return (name);
+    }
+
+    @Override
+    public boolean isRaw()
+    {
+        try
+        {
+            String target = name.toLowerCase();
+            return ((target.endsWith("dng")));
+        }
+        catch (Exception e)
+        {
+            e.printStackTrace();
+        }
+        return (false);
+    }
+
+    @Override
+    public boolean isMovie()
+    {
+        try
+        {
+            String target = name.toLowerCase();
+            return ((target.endsWith("mov")) || (target.endsWith("mp4")));
+        }
+        catch (Exception e)
+        {
+            e.printStackTrace();
+        }
+        return (false);
+    }
+
+    @Override
+    public boolean isDateValid()
+    {
+        return (true);
+    }
+
+    @Override
+    public boolean isContentNameValid()
+    {
+        return (true);
+    }
+
+    @Override
+    public Date getCapturedDate()
+    {
+        try
+        {
+            try {
+                SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy:MM:dd hh:mm:ss", Locale.ENGLISH);
+                return (dateFormat.parse(date));
+            } catch (Exception eee) {
+                try {
+                    SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy:MM:dd hh:mm:ssZ", Locale.ENGLISH);
+                    return (dateFormat.parse(date));
+                } catch (Exception ee) {
+                    try {
+                        SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy:MM:dd hh:mm:ssX", Locale.ENGLISH);
+                        return (dateFormat.parse(date));
+                    } catch (Exception e) {
+                        e.printStackTrace();
+                    }
+                }
+            }
+        }
+        catch (Throwable t)
+        {
+            t.printStackTrace();
+        }
+        return (new Date());
+    }
+
+    @Override
+    public void setCapturedDate(Date date)
+    {
+        Log.v(TAG, " setCapturedDate() " + date.toString() + " (name : " + name + " , size: " + size + ")");
+    }
+}
index 32c1fe0..1ab312a 100644 (file)
@@ -1,9 +1,14 @@
 package net.osdn.gokigen.pkremote.camera.vendor.theta.wrapper.playback;
 
 import android.app.Activity;
+import android.content.SharedPreferences;
+import android.graphics.Bitmap;
+import android.util.Log;
 
 import androidx.annotation.NonNull;
+import androidx.preference.PreferenceManager;
 
+import net.osdn.gokigen.pkremote.camera.interfaces.playback.ICameraContent;
 import net.osdn.gokigen.pkremote.camera.interfaces.playback.ICameraContentListCallback;
 import net.osdn.gokigen.pkremote.camera.interfaces.playback.ICameraFileInfo;
 import net.osdn.gokigen.pkremote.camera.interfaces.playback.IContentInfoCallback;
@@ -11,62 +16,308 @@ import net.osdn.gokigen.pkremote.camera.interfaces.playback.IDownloadContentCall
 import net.osdn.gokigen.pkremote.camera.interfaces.playback.IDownloadContentListCallback;
 import net.osdn.gokigen.pkremote.camera.interfaces.playback.IDownloadThumbnailImageCallback;
 import net.osdn.gokigen.pkremote.camera.interfaces.playback.IPlaybackControl;
+import net.osdn.gokigen.pkremote.camera.playback.ProgressEvent;
+import net.osdn.gokigen.pkremote.camera.utils.SimpleHttpClient;
+import net.osdn.gokigen.pkremote.preference.IPreferencePropertyAccessor;
+
+import org.json.JSONArray;
+import org.json.JSONObject;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
 
 public class ThetaPlaybackControl implements IPlaybackControl
 {
-    public ThetaPlaybackControl(@NonNull Activity activity, int timeoutMs)
+    private final String TAG = toString();
+    private static final int DEFAULT_TIMEOUT = 3000;
+    private static final int DEFAULT_MAX_COUNT = 300;
+    private final int timeoutValue;
+    private final int maxCount;
+    private final boolean useThetaV21;
+
+    private List<ICameraContent> cameraContentList;
+
+    public ThetaPlaybackControl(@NonNull Activity activity, int timeoutMs, int maxCount)
     {
+        this.timeoutValue  = (timeoutMs < DEFAULT_TIMEOUT) ? DEFAULT_TIMEOUT : timeoutMs;
+        this.maxCount  = (maxCount < DEFAULT_MAX_COUNT) ? DEFAULT_MAX_COUNT : maxCount;
+        SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(activity);
+        useThetaV21 = preferences.getBoolean(IPreferencePropertyAccessor.USE_OSC_THETA_V21, false);
+        cameraContentList = new ArrayList<>();
 
     }
 
 
     @Override
     public String getRawFileSuffix() {
-        return null;
+        return ".DNG";
     }
 
     @Override
-    public void downloadContentList(IDownloadContentListCallback callback) {
-
+    public void downloadContentList(IDownloadContentListCallback callback)
+    {
+        Log.v(TAG, " downloadContentList()");
     }
 
     @Override
-    public void getContentInfo(String path, String name, IContentInfoCallback callback) {
+    public void getContentInfo(String path, String name, IContentInfoCallback callback)
+    {
+        Log.v(TAG, " getContentInfo() : " + path + " / " + name);
 
     }
 
     @Override
-    public void updateCameraFileInfo(ICameraFileInfo info) {
+    public void updateCameraFileInfo(ICameraFileInfo info)
+    {
+        Log.v(TAG, " updateCameraFileInfo() : " + info.getFilename());
+    }
 
+    @Override
+    public void downloadContentScreennail(String path, IDownloadThumbnailImageCallback callback)
+    {
+        downloadContentThumbnail(path, callback);
     }
 
     @Override
-    public void downloadContentScreennail(String path, IDownloadThumbnailImageCallback callback) {
+    public void downloadContentThumbnail(String path, IDownloadThumbnailImageCallback callback)
+    {
+        if (useThetaV21) {
+            downloadContentThumbnailV21(path, callback);
+        } else {
+            downloadContentThumbnailV2(path, callback);
+        }
+    }
+
+    private void downloadContentThumbnailV2(String path, IDownloadThumbnailImageCallback callback)
+    {
+        //  POST /osc/commands/execute
+        //  {"name":"camera.getImage","parameters":{"_type":"thumb","fileUri":"100RICOH/R0010093.JPG"}}
+        Log.v(TAG, "downloadContentThumbnail() : " + path);
+        try
+        {
+            String url = "http://192.168.1.1/osc/commands/execute";
+            String postData = "{\"name\":\"camera.getImage\",\"parameters\":{\"_type\":\"thumb\",\"fileUri\":\"" + path + "\"}}";
+            Log.v(TAG, " postData : " + postData);
 
+            Bitmap bmp = SimpleHttpClient.httpPostBitmap(url, postData, timeoutValue);
+            HashMap<String, Object> map = new HashMap<>();
+            map.put("Orientation", 0);
+            callback.onCompleted(bmp, map);
+        }
+        catch (Throwable e)
+        {
+            e.printStackTrace();
+            callback.onErrorOccurred(new NullPointerException());
+        }
     }
 
-    @Override
-    public void downloadContentThumbnail(String path, IDownloadThumbnailImageCallback callback) {
+    private void downloadContentThumbnailV21(String path, IDownloadThumbnailImageCallback callback)
+    {
+        //  POST /osc/commands/execute
+        //  {"name":"camera.getImage","parameters":{"_type":"thumb","fileUri":"100RICOH/R0010093.JPG"}}
+        Log.v(TAG, "downloadContentThumbnail() : " + path);
+        try
+        {
+            String url = "http://192.168.1.1/osc/commands/execute";
+            String postData = "{\"name\":\"camera.getImage\",\"parameters\":{\"_type\":\"thumb\",\"fileUri\":\"" + path + "\"}}";
+            Log.v(TAG, " postData : " + postData);
 
+            Bitmap bmp = SimpleHttpClient.httpPostBitmap(url, postData, timeoutValue);
+            HashMap<String, Object> map = new HashMap<>();
+            map.put("Orientation", 0);
+            callback.onCompleted(bmp, map);
+        }
+        catch (Throwable e)
+        {
+            e.printStackTrace();
+            callback.onErrorOccurred(new NullPointerException());
+        }
     }
 
     @Override
-    public void downloadContent(String path, boolean isSmallSize, IDownloadContentCallback callback) {
+    public void downloadContent(String path, boolean isSmallSize, IDownloadContentCallback callback)
+    {
+        try
+        {
+            if (useThetaV21) {
+                downloadContentImplV21(path, isSmallSize, callback);
+            } else {
+                downloadContentImpl(path, isSmallSize, callback);
+            }
+        }
+        catch (Exception e)
+        {
+            e.printStackTrace();
+        }
+    }
+
+    private void downloadContentImplV21(String path, boolean isSmallSize, final IDownloadContentCallback callback)
+    {
+        downloadContentImpl(path, isSmallSize, callback);
+    }
+
+    private void downloadContentImpl(String path, boolean isSmallSize, final IDownloadContentCallback callback)
+    {
+        Log.v(TAG, "downloadContent() : " + path + " (small :" + isSmallSize + ")");
+        String urlToGet = "http://192.168.1.1/osc/commands/execute";
+        String postData = "{\"name\":\"camera.getImage\",\"parameters\":{\"_type\":\"full\",\"fileUri\":\"" + path + "\"}}";
+        try
+        {
+            SimpleHttpClient.httpPostBytes(urlToGet, postData, null, timeoutValue, new SimpleHttpClient.IReceivedMessageCallback() {
+                @Override
+                public void onCompleted() {
+                    callback.onCompleted();
+                }
+
+                @Override
+                public void onErrorOccurred(Exception e) {
+                    callback.onErrorOccurred(e);
+                }
 
+                @Override
+                public void onReceive(int readBytes, int length, int size, byte[] data) {
+                    float percent = (length == 0) ? 0.0f : ((float) readBytes / (float) length);
+                    //Log.v(TAG, " onReceive : " + readBytes + " " + length + " " + size);
+                    ProgressEvent event = new ProgressEvent(percent, null);
+                    callback.onProgress(data, size, event);
+                }
+            });
+        }
+        catch (Throwable e)
+        {
+            e.printStackTrace();
+        }
     }
 
-    @Override
-    public void getCameraContentList(ICameraContentListCallback callback) {
 
+    @Override
+    public void getCameraContentList(ICameraContentListCallback callback)
+    {
+        try
+        {
+            if (useThetaV21) {
+                getCameraContentListImplV21(callback);
+            } else {
+                getCameraContentListImpl(callback);
+            }
+        }
+        catch (Exception e)
+        {
+            e.printStackTrace();
+        }
     }
 
     @Override
-    public void showPictureStarted() {
+    public void showPictureStarted()
+    {
 
     }
 
     @Override
-    public void showPictureFinished() {
+    public void showPictureFinished()
+    {
+
+    }
+
+
+    private void getCameraContentListImpl(ICameraContentListCallback callback)
+    {
+        String imageListurl = "http://192.168.1.1/osc/commands/execute";
+        String contentList;
+        try
+        {
+            String paramStr = "{\"name\":\"camera._listAll\",\"parameters\":{\"detail\":false,\"entryCount\":" + maxCount + ",\"sort\":\"newest\"}}";
+
+            contentList = SimpleHttpClient.httpPost(imageListurl, paramStr, timeoutValue);
+            if (contentList == null)
+            {
+                // ぬるぽ発行
+                callback.onErrorOccurred(new NullPointerException());
+                cameraContentList.clear();
+                return;
+            }
+        }
+        catch (Exception e)
+        {
+            // 例外をそのまま転送
+            callback.onErrorOccurred(e);
+            //cameraContentList.clear();
+            return;
+        }
+        try
+        {
+            Log.v(TAG, "PHOTO LIST RECV: [" + contentList.length() + "] ");
+            JSONObject resultsObject = new JSONObject(contentList).getJSONObject("results");
+            JSONArray entriesArray = resultsObject.getJSONArray("entries");
+            int size = entriesArray.length();
+            cameraContentList.clear();
+            for (int index = 0; index < size; index++)
+            {
+                JSONObject object = entriesArray.getJSONObject(index);
+                String fileName = object.getString("name");
+                String fileUri = object.getString("uri");
+                String fileSize = object.getString("size");
+                String fileDateTime = object.getString("dateTime");
+
+                cameraContentList.add(new ThetaCameraContent(fileName, fileUri, null, fileSize, fileDateTime));
+                Log.v(TAG, " [" + (index + 1) + "] " + fileName + " " + fileUri + " " + fileSize + " " + fileDateTime + " ");
+            }
+        }
+        catch (Exception e)
+        {
+            e.printStackTrace();
+        }
+        callback.onCompleted(cameraContentList);
+    }
+
+    private void getCameraContentListImplV21(ICameraContentListCallback callback)
+    {
+        String imageListurl = "http://192.168.1.1/osc/commands/execute";
+        String contentList;
+        try
+        {
+            String paramStr = "{\"name\":\"camera.listFiles\",\"parameters\":{\"fileType\":\"all\",\"entryCount:\"" +  maxCount + ",\"maxThumbSize\":0,\"_detail\":false}}";
+            contentList = SimpleHttpClient.httpPost(imageListurl, paramStr, timeoutValue);
+            if (contentList == null)
+            {
+                // ぬるぽ発行
+                callback.onErrorOccurred(new NullPointerException());
+                cameraContentList.clear();
+                return;
+            }
+        }
+        catch (Exception e)
+        {
+            // 例外をそのまま転送
+            callback.onErrorOccurred(e);
+            //cameraContentList.clear();
+            return;
+        }
+        try
+        {
+            // Log.v(TAG, "PHOTO LIST RECV: [" + contentList.length() + "] " + contentList);
+            JSONObject resultsObject = new JSONObject(contentList).getJSONObject("results");
+            JSONArray entriesArray = resultsObject.getJSONArray("entries");
+            int size = entriesArray.length();
+            cameraContentList.clear();
+            for (int index = 0; index < size; index++)
+            {
+                JSONObject object = entriesArray.getJSONObject(index);
+                String fileName = object.getString("name");
+                String fileUri = object.getString("fileUrl");
+                String fileSize = object.getString("size");
+                String fileDateTime = object.getString("dateTime");
 
+                cameraContentList.add(new ThetaCameraContent(fileName, null, fileUri, fileSize, fileDateTime));
+                // Log.v(TAG, " [" + (index + 1) + "] " + fileName + " " + fileUri + " " + fileSize + " " + fileDateTime + " ");
+            }
+        }
+        catch (Exception e)
+        {
+            e.printStackTrace();
+            cameraContentList.clear();
+        }
+        callback.onCompleted(cameraContentList);
     }
 }
index 551256e..610d1c2 100644 (file)
@@ -117,6 +117,8 @@ public interface IPreferencePropertyAccessor
 
     String HTTP_COMMAND_SEND_DIALOG = "send_command_dialog";
 
+    String USE_OSC_THETA_V21 = "use_osc_theta_v21";
+
     /*
     //String GR2_DISPLAY_MODE = "gr2_display_mode";
     //String GR2_DISPLAY_MODE_DEFAULT_VALUE = "0";
index fceaa02..e859c1a 100644 (file)
@@ -131,6 +131,12 @@ public class ThetaPreferenceFragment  extends PreferenceFragmentCompat implement
             if (!items.containsKey(IPreferencePropertyAccessor.CONNECTION_METHOD)) {
                 editor.putString(IPreferencePropertyAccessor.CONNECTION_METHOD, IPreferencePropertyAccessor.CONNECTION_METHOD_DEFAULT_VALUE);
             }
+            if (!items.containsKey(IPreferencePropertyAccessor.RICOH_GET_PICS_LIST_TIMEOUT)) {
+                editor.putString(IPreferencePropertyAccessor.RICOH_GET_PICS_LIST_TIMEOUT, IPreferencePropertyAccessor.RICOH_GET_PICS_LIST_TIMEOUT_DEFAULT_VALUE);
+            }
+            if (!items.containsKey(IPreferencePropertyAccessor.USE_OSC_THETA_V21)) {
+                editor.putBoolean(IPreferencePropertyAccessor.USE_OSC_THETA_V21, false);
+            }
             editor.apply();
         }
         catch (Exception e)
@@ -162,6 +168,11 @@ public class ThetaPreferenceFragment  extends PreferenceFragmentCompat implement
                     Log.v(TAG, " " + key + " , " + value);
                     break;
 
+                case IPreferencePropertyAccessor.USE_OSC_THETA_V21:
+                    value = preferences.getBoolean(key, false);
+                    Log.v(TAG, " " + key + " , " + value);
+                    break;
+
                 default:
                     String strValue = preferences.getString(key, "");
                     setListPreference(key, key, strValue);
@@ -184,20 +195,22 @@ public class ThetaPreferenceFragment  extends PreferenceFragmentCompat implement
             addPreferencesFromResource(R.xml.preferences_theta);
 
             ListPreference connectionMethod = findPreference(IPreferencePropertyAccessor.CONNECTION_METHOD);
-            connectionMethod.setOnPreferenceChangeListener(new Preference.OnPreferenceChangeListener() {
-                @Override
-                public boolean onPreferenceChange(Preference preference, Object newValue) {
-                    preference.setSummary(newValue + " ");
-                    return (true);
-                }
-            });
-            connectionMethod.setSummary(connectionMethod.getValue() + " ");
+            if (connectionMethod != null)
+            {
+                connectionMethod.setOnPreferenceChangeListener(new Preference.OnPreferenceChangeListener() {
+                    @Override
+                    public boolean onPreferenceChange(Preference preference, Object newValue) {
+                        preference.setSummary(newValue + " ");
+                        return (true);
+                    }
+                });
+                connectionMethod.setSummary(connectionMethod.getValue() + " ");
+            }
 
-            findPreference(EXIT_APPLICATION).setOnPreferenceClickListener(powerOffController);
-            findPreference(DEBUG_INFO).setOnPreferenceClickListener(logCatViewer);
-            findPreference(WIFI_SETTINGS).setOnPreferenceClickListener(this);
-            findPreference(HTTP_COMMAND_SEND_DIALOG).setOnPreferenceClickListener(this);
-            //findPreference("panasonic_api_list").setOnPreferenceClickListener(cameraApiListViewer);
+            setOnPreferenceClickListener(EXIT_APPLICATION, powerOffController);
+            setOnPreferenceClickListener(DEBUG_INFO, logCatViewer);
+            setOnPreferenceClickListener(WIFI_SETTINGS, this);
+            setOnPreferenceClickListener(HTTP_COMMAND_SEND_DIALOG, this);
         }
         catch (Exception e)
         {
@@ -205,6 +218,15 @@ public class ThetaPreferenceFragment  extends PreferenceFragmentCompat implement
         }
     }
 
+    private void setOnPreferenceClickListener(String key, Preference.OnPreferenceClickListener listener)
+    {
+        Preference preference = findPreference(key);
+        if (preference != null)
+        {
+            preference.setOnPreferenceClickListener(listener);
+        }
+    }
+
     /**
      *
      *
@@ -223,9 +245,7 @@ public class ThetaPreferenceFragment  extends PreferenceFragmentCompat implement
         {
             e.printStackTrace();
         }
-
         Log.v(TAG, "onResume() End");
-
     }
 
     /**
@@ -318,6 +338,7 @@ public class ThetaPreferenceFragment  extends PreferenceFragmentCompat implement
                         // Preferenceの画面に反映させる
                         setBooleanPreference(IPreferencePropertyAccessor.AUTO_CONNECT_TO_CAMERA, IPreferencePropertyAccessor.AUTO_CONNECT_TO_CAMERA, defaultValue);
                         setBooleanPreference(IPreferencePropertyAccessor.CAPTURE_BOTH_CAMERA_AND_LIVE_VIEW, IPreferencePropertyAccessor.CAPTURE_BOTH_CAMERA_AND_LIVE_VIEW, defaultValue);
+                        setBooleanPreference(IPreferencePropertyAccessor.USE_OSC_THETA_V21, IPreferencePropertyAccessor.USE_OSC_THETA_V21, false);
                     }
                     catch (Exception e)
                     {
index 4b9dd82..d9716b7 100644 (file)
     <string name="http_dialog_parameter_hint">(parameter)</string>
     <string name="http_method_string">GET</string>
 
+    <string name="pref_use_osc_theta_v21">THETA Web API v2.1の使用</string>
+    <string name="pref_summary_use_osc_theta_v21"> </string>
+
 </resources>
index 10e8b18..a3c2d23 100644 (file)
     <string name="http_dialog_parameter_hint">(parameter)</string>
     <string name="http_method_string">GET</string>
 
+    <string name="pref_use_osc_theta_v21">Use THETA Web API v2.1</string>
+    <string name="pref_summary_use_osc_theta_v21"> </string>
+
 </resources>
index 2f8c022..ab89cbf 100644 (file)
     <PreferenceCategory
         android:title="@string/pref_cat_camera">
 
+        <CheckBoxPreference
+            android:key="use_osc_theta_v21"
+            android:title="@string/pref_use_osc_theta_v21"
+            android:summary="@string/pref_summary_use_osc_theta_v21"/>
+
         <PreferenceScreen
             android:key="send_command_dialog"
             android:title="@string/pref_show_send_dialog"
             android:summary="@string/pref_summary_show_send_dialog" />
 
-<!--
+        <EditTextPreference
+            android:key="ricoh_get_pics_list_timeout"
+            android:title="@string/pref_ricoh_get_pics_list_timeout"
+            android:defaultValue="10"
+            android:inputType="number"
+            android:summary="@string/pref_summary_ricoh_get_pics_list_timeout" />
+
+        <!--
         <CheckBoxPreference
             android:key="capture_both_camera_and_live_view"
             android:title="@string/pref_capture_both_camera_and_live_view" />