当使用相机插件拍摄新照片时,PhoneGap应用程序崩溃



我正在开发一个移动应用程序与cordova/phonegap,我已经安装了相机插件。我能够打开相机并点击图像,但之后应用程序崩溃。下面是崩溃日志:

    java.lang.RuntimeException: Failure delivering result ResultInfo{who=null, request=34, result=-1, data=null} to activity {com.phonegap.helloworld/com.phonegap.helloworld.CordovaApp}: java.lang.IllegalArgumentException: filename cannot be null
    E/AndroidRuntime(22226):    at android.app.ActivityThread.deliverResults(ActivityThread.java:3510)
    E/AndroidRuntime(22226):    at android.app.ActivityThread.handleSendResult(ActivityThread.java:3553)
    E/AndroidRuntime(22226):    at android.app.ActivityThread.access$1200(ActivityThread.java:165)
    E/AndroidRuntime(22226):    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1374)
    E/AndroidRuntime(22226):    at android.os.Handler.dispatchMessage(Handler.java:99)
    E/AndroidRuntime(22226):    at android.os.Looper.loop(Looper.java:176)
    E/AndroidRuntime(22226):    at android.app.ActivityThread.main(ActivityThread.java:5455)
    E/AndroidRuntime(22226):    at java.lang.reflect.Method.invokeNative(Native Method)
    E/AndroidRuntime(22226):    at java.lang.reflect.Method.invoke(Method.java:525)
    E/AndroidRuntime(22226):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1209)
    E/AndroidRuntime(22226):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1025)
    E/AndroidRuntime(22226):    at dalvik.system.NativeStart.main(Native Method)
    E/AndroidRuntime(22226): Caused by: java.lang.IllegalArgumentException: filename cannot be null
    E/AndroidRuntime(22226):    at android.media.ExifInterface.<init>(ExifInterface.java:121)
    E/AndroidRuntime(22226):    at org.apache.cordova.camera.ExifHelper.createOutFile(ExifHelper.java:66)
    E/AndroidRuntime(22226):    at org.apache.cordova.camera.CameraLauncher.processResultFromCamera(CameraLauncher.java:430)
    E/AndroidRuntime(22226):    at org.apache.cordova.camera.CameraLauncher.onActivityResult(CameraLauncher.java:610)
    E/AndroidRuntime(22226):    at org.apache.cordova.CordovaActivity.onActivityResult(CordovaActivity.java:784)
    E/AndroidRuntime(22226):    at android.app.Activity.dispatchActivityResult(Activity.java:5563)
    E/AndroidRuntime(22226):    at android.app.ActivityThread.deliverResults(ActivityThread.java:3506)
    E/AndroidRuntime(22226):    ... 11 more
我用来打开相机的代码是:
   var pictureSource; // picture source
var destinationType; // sets the format of returned value
document.addEventListener("deviceready", onDeviceReady, false);
function onDeviceReady() {
  // alert("ready-----")
  pictureSource = navigator.camera.PictureSourceType;
  destinationType = navigator.camera.DestinationType;
}
function capturePhoto() {
  alert(navigator.camera);
  navigator.camera.getPicture(onPhotoDataSuccess, onFail, {
    quality: 20,
    destinationType: destinationType.FILE_URI,
    targetWidth: 200,
    targetHeight: 200,
    saveToPhotoAlbum: true,
    sourceType: pictureSource.CAMERA
  });
}
function onPhotoDataSuccess(imageURI) {
  // alert("success--");
  var smallImage = document.getElementById('smallImage');
  smallImage.style.display = 'block';
  smallImage.src = imageURI;
  // smallImage.src = "data:image/jpeg;base64," + imageData;
}
function onFail(message) {
  alert('Failed because: ' + message);
}

这个bug已经在Apache Cordova中被记录了。

帮助! !

尝试用这个(这是我自己的应用程序中的工作代码)替换您的capturePhoto()函数:

function capturePhoto() {
    var options = {
        quality: 75,
        destinationType: Camera.DestinationType.FILE_URI,
        sourceType: Camera.PictureSourceType.CAMERA,
        mediaType: Camera.MediaType.CAMERA,
        encodingType: Camera.EncodingType.JPEG,
        targetWidth: 200,
        targetHeight: 200,
        saveToPhotoAlbum: true
    };
    navigator.camera.getPicture(onPhotoDataSuccess, onFail, options);
}

请更改目的地类型:

destinationType: destinationType.FILE_URI

destinationType: Camera.DestinationType.FILE_URI

如果需要作为base64编码的图像,则将目标类型更改为:

destinationType: Camera.DestinationType.DATA_URL

还要确保您已在清单文件中添加了写入外部存储权限。

插件向ExifInterface传递空指针导致异常,这在旧的插件中没有发生。

尝试应用以下修复程序,也可以报告设备品牌,型号和android版本吗?

https://issues.apache.org/jira/browse/cb - 9446

diff --git a/src/android/ExifHelper.java b/src/android/ExifHelper.java
index 5160a2f..0af0fcd 100644
--- a/src/android/ExifHelper.java
+++ b/src/android/ExifHelper.java
@@ -53,7 +53,11 @@ public class ExifHelper {
  * @throws IOException
  */
 public void createInFile(String filePath) throws IOException {
-        this.inFile = new ExifInterface(filePath);
+        if (filePath != null) {
+            this.inFile = new ExifInterface(filePath);
+        } else {
+            throw new IOException("null pointer passed to createInFile");
+        }
 }
 /**
@@ -63,7 +67,11 @@ public class ExifHelper {
  * @throws IOException
  */
 public void createOutFile(String filePath) throws IOException {
-        this.outFile = new ExifInterface(filePath);
+        if (filePath != null) {
+            this.outFile = new ExifInterface(filePath);
+        } else {
+            throw new IOException("null pointer passed to createOutFile");
+        }
 }
 /**
diff --git a/src/android/FileHelper.java b/src/android/FileHelper.java
index 59f890e..cd4b6ef 100644
--- a/src/android/FileHelper.java
+++ b/src/android/FileHelper.java
@@ -33,6 +33,7 @@ import java.io.FileInputStream;
 import java.io.IOException;
 import java.io.InputStream;
 import java.util.Locale;
+import android.util.Log;
 public class FileHelper {
 private static final String LOG_TAG = "FileUtils";
@@ -54,9 +55,12 @@ public class FileHelper {
 realPath = FileHelper.getRealPathFromURI_BelowAPI11(cordova.getActivity(), uri);
 // SDK >= 11 && SDK < 19
-        else if (Build.VERSION.SDK_INT < 19)
+        else if (Build.VERSION.SDK_INT < 19) {
 realPath = FileHelper.getRealPathFromURI_API11to18(cordova.getActivity(), uri);
-
+            if (realPath == null) {
+                realPath = getRealPathFallback(uri.toString(), cordova);
+            }
+        }
 // SDK > 19 (Android 4.4)
 else
 realPath = FileHelper.getRealPathFromURI_API19(cordova.getActivity(), uri);
@@ -126,6 +130,47 @@ public class FileHelper {
 return result;
 }
+    /**
+     * Returns the real path of the given URI string.
+     * If the given URI string represents a content:// URI, the real path is retrieved from the media store.
+     *
+     * @param uriString the URI string of the audio/image/video
+     * @param cordova the current application context
+     * @return the full path to the file
+     */
+    @SuppressWarnings("deprecation")
+    public static String getRealPathFallback(String uriString, CordovaInterface cordova) {
+        String realPath = null;
+        try {
+            if (uriString.startsWith("content://")) {
+                String[] proj = { _DATA };
+                Cursor cursor = cordova.getActivity().managedQuery(Uri.parse(uriString), proj, null, null, null);
+                int column_index = cursor.getColumnIndexOrThrow(_DATA);
+                cursor.moveToFirst();
+                realPath = cursor.getString(column_index);
+                Log.d(LOG_TAG, "getRealPath managedQuery success uri " + uriString + " realpath " + realPath);
+                if (realPath == null) {
+                    Log.e(LOG_TAG, "getRealPath Could get real path for URI string " + uriString);
+                }
+            } else if (uriString.startsWith("file://")) {
+                realPath = uriString.substring(7);
+                Log.d(LOG_TAG, "getRealPath file:// " + uriString + " realpath " + realPath);
+                if (realPath.startsWith("/android_asset/")) {
+                    Log.e(LOG_TAG, "getRealPath Cannot get real path for URI string " + uriString + " because it is a file:///android_asset/ URI.");
+                    realPath = null;
+                }
+            } else {
+                realPath = uriString;
+            }
+        } catch (Exception e) {
+            Log.d(LOG_TAG, "getRealPath using uristring could not find real path, uriString: " + uriString + " message: " + e.getMessage());
+            realPath = uriString;
+        }
+
+        return realPath;
+    }
+
+
 public static String getRealPathFromURI_BelowAPI11(Context context, Uri contentUri) {
 String[] proj = { MediaStore.Images.Media.DATA };
 String result = null;

最新更新