android - Cordova-plugin-camera 不适用于 Android 版本 8

标签 android cordova cordova-plugins

我正在使用 cordova-plugin-camera 访问 Android 中的相机。在我将 Target SDK 版本更改为 API 26: Android 8.0 (Oreo) 以便能够上传到现在需要此版本或更高版本的 Google Play 商店之前,一切正常。

我得到的错误是

file:///data/user/0/{mypackage}/cache/Capture.jpg exposed beyond app through ClipData.Item.getUri()

我认为这是由于应用程序从 Android Nougat 访问文件系统的方式发生了变化 - 请参阅 android.os.FileUriExposedException: file:///storage/emulated/0/test.txt exposed beyond app through Intent.getData() .

我已尝试根据 https://github.com/ionic-team/ng-cordova/issues/1381 解决不同版本的 cordova、cordova android 和相机插件的问题。但在每种情况下,一旦我将 TargetSDK 更改为 26,我就会在 Android 8 手机上遇到相同的错误。

我已将以下内容添加到我的 AndroidManifest.xml 文件中

            <provider android:authorities="com.okappy.okappy.provider" android:exported="false" android:grantUriPermissions="true" android:name="android.support.v4.content.FileProvider">
        <meta-data android:name="android.support.FILE_PROVIDER_PATHS" android:resource="@xml/camera_provider_paths" />
    </provider>

我已经检查过我有一个包含以下内容的 camera_provider_paths.xml

    <paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path name="external_files" path="."/>

我还尝试在 cordova/camera/CordovaURI.java 中编辑以下行以强制忽略 fileUri,但没有任何区别

    public Uri getCorrectUri()
{
    /*if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.M)
        return androidUri;
    else
        return fileUri;
    */
    return androidUri;

}

我有以下版本

  • 8.1.2 (cordova-lib@8.1.1)

  • 安卓7.1.2

  • cordova-plugin-camera 4.0.3

  • cordova-plugin-console 1.0.3
  • cordova-plugin-file 6.0.1

我使用的是 Compile SDK 版本 28.0.3、MinumumSDK 版本 21 和 TargetSDK 版本 26。

预先感谢您的帮助

最佳答案

问题出在我们的代码而不是插件 - view issue on github

我们使用了以下代码

function captureImage() {
    navigator.device.capture.captureImage(captureImageSuccess, captureImageError, {limit: 1});
}

function captureImageSuccess(mediaFiles) {
    uploadFile(mediaFiles[0]);
}

function uploadFile(mediaFile,fileType) { //#F333
    var win = function (r) {
}

var options = new FileUploadOptions();
    ImageURL=mediaFile.fullPath;
    options.fileName = (fileType)? mediaFile.name : mediaFile.file; //#F333
    options.mimeType = "multipart/form-data";
    var params = new Object();
    params.fileName = 'AndroidPhoneUpload';
    params.imageType = (fileType)?fileType:'Picture';   //#F333
    var printName = prompt("Add a title","");  //#F644
    if (printName){
        params.printedName = printName;
    }
    window.resolveLocalFileSystemURL(ImageURL, function(fileEntry) {
        fileEntry.file(function(fileObj) {
            params.fileSize = ""+fileObj.size;
        });
    });
    options.params = params;
    var ft = new FileTransfer();
    ft.upload(ImageURL, encodeURI("uploadURL"),win,fail,options);
}

我们用下面的 addImage 函数替换了 captureImage 函数

function setOptions(srcType) {
    var options = {
        quality: 50,
        limit: 1,
        destinationType: Camera.DestinationType.FILE_URI,
        // In this app, dynamically set the picture source, Camera or photo gallery
        sourceType: srcType,
        encodingType: Camera.EncodingType.JPEG,
        mediaType: Camera.MediaType.PICTURE,
        allowEdit: false,
        correctOrientation: true  
    }
    return options;
}

function addImage() {

  var srcType = Camera.PictureSourceType.CAMERA;
  var options = setOptions(srcType);

  navigator.camera.getPicture(function cameraSuccess(imageUri) {
        var options = new FileUploadOptions();
        options.fileKey="file";

        options.fileName="test";
        options.mimeType="multipart/form-data";

        var params = new Object();
        params.fileName = 'AndroidPhoneUpload';
        params.imageType = 'Picture';
        var printName = prompt("Add a title","");
        if (printName){
            params.printedName = printName;
        }
        options.params = params;
        navigator.notification.alert("Your media is being uploaded.", null, "Add media");

        var ft = new FileTransfer();
        ft.upload(imageUri, encodeURI("uploadURL"), win, fail, options);

    }, function captureImageError(error) {
        console.debug("Unable to obtain picture: " + error, "app");
    }, options);
}

为了进一步澄清,我认为问题是因为我们使用相机拍摄图像,然后尝试从存储中上传媒体文件,这导致了新版 Android 的权限问题。

关于android - Cordova-plugin-camera 不适用于 Android 版本 8,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53224086/

相关文章:

java - ABBYY 实时识别(cordova 插件)错误

android - 将 Ionic2 CLI 更新到 Ionic3 后,由于 facebook 插件,Cordova 构建失败

android - NAT 路由器后面的 Android 上的即时消息服务器

java - 如何在选中 ListItem 后修改它的背景?

java - 如何计算当前 View 中是否存在经度/纬度

cordova - 将已安装的 Cordova 插件保存到 config.xml

IOS 项目在 xcode 7.1 上显示错误 "An internal error occurred. Editing functionality may be limited"

ios - 在 native IOS 应用程序中加载多个 Cordova 微应用程序

android - 在android中创建子菜单

android - Titanium 中的 UI 感觉和外观,PhoneGap 与原生相比