如何将图片选择器返回的File URI转换为Base64字符串
问题原因
- 图片选择器返回的URI多为
content://格式的内容URI,并非本地文件系统的绝对路径,你直接按/拆分得到的路径和文件名不被文件读取API识别,是报错的核心原因。 - 你给回调标记了
async但未使用await处理异步操作,嵌套的.then逻辑容易出现时序错误。 - 未提前申请存储读取权限,安卓13及以上需要
READ_MEDIA_IMAGES权限、低版本安卓需要READ_EXTERNAL_STORAGE权限、iOS需要配置相册访问权限说明,权限缺失会直接导致文件读取失败。 - 路径拆分逻辑未兼容带
file://前缀的URI场景,前缀未移除会导致路径校验不通过。
修复方案
- 先对返回的URI做格式适配:
content://格式的URI先转换为本地绝对路径,带file://前缀的URI先移除前缀再拆分。 - 提前申请所需的存储/相册访问权限,确保权限通过后再执行文件读取操作。
- 统一异步逻辑写法,避免嵌套异常。
下面是基于cordova生态的修复后代码示例,需要先安装cordova-plugin-filepath插件处理content URI转换:
const options: ImagePickerOptions = { maximumImagesCount: 1, width: 1200, height: 1200, quality: 80 }; // 先申请权限,此处省略权限申请代码,可根据你使用的框架调用对应权限API this.imagePicker.getPictures(options).then(async (results) => { const fileUri: string = results[0]; let fullPath: string, fileName: string; try { // 处理content://格式URI if (fileUri.startsWith('content://')) { const nativePath = await this.filePath.resolveNativePath(fileUri); fullPath = nativePath.substring(0, nativePath.lastIndexOf('/') + 1); fileName = nativePath.split('/').pop(); } // 处理file://格式URI else if (fileUri.startsWith('file://')) { const purePath = decodeURIComponent(fileUri.replace('file://', '')); fullPath = purePath.substring(0, purePath.lastIndexOf('/') + 1); fileName = purePath.split('/').pop(); } // 其他情况直接拆分 else { fullPath = fileUri.substring(0, fileUri.lastIndexOf('/') + 1); fileName = fileUri.split('/').pop(); } const base64File = await this.file.readAsDataURL(fullPath, fileName); console.log("here is encoded image ", base64File) } catch (err) { console.log('Error processing file', err); } });
内容的提问来源于stack exchange,提问作者Mobile Development Team
相关产品推荐
相关产品推荐

