1/* 2 * Copyright (c) 2025-2025 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16import UIExtensionContentSession from '@ohos.app.ability.UIExtensionContentSession'; 17import picker from '@ohos.file.picker'; 18import type { BusinessError } from '@ohos.base'; 19import common from '@ohos.app.ability.common'; 20import commonEventManager from '@ohos.commonEventManager'; 21import photoAccessHelper from '@ohos.file.photoAccessHelper'; 22 23let TAG = '[BT_RECEIVE_PAGE]===>'; 24const BT_NI_GET_URI_EVENT: string = 'ohos.event.notification.BT.GET_URI'; 25 26@Entry 27@Component 28struct btCreateFilePickerPage { 29 30 /** 31 * 文件类型 32 */ 33 private static readonly FILE_TYPE_FILES: string = 'files'; 34 private static readonly FILE_TYPE_IMAGE: string = 'image'; 35 private static readonly FILE_TYPE_VIDEO: string = 'video'; 36 37 private context = getContext(this) as common.UIAbilityContext; 38 private phAccessHelper = photoAccessHelper.getPhotoAccessHelper(getContext(this)); 39 private extension: string = ''; 40 private fileName: string = ''; 41 private fileUri: string = ''; 42 private fileType: string = ''; 43 44 45 aboutToAppear() { 46 console.info(TAG, `aboutToAppear`); 47 this.dealFileReceiveUri(); 48 } 49 50 /** 51 * 处理接收的文件URI生成、发布流程 52 */ 53 private async dealFileReceiveUri() { 54 try { 55 await this.generateFileUri(); 56 this.publishFileUriEvent(); 57 } catch (error) { 58 let err: BusinessError = error as BusinessError; 59 console.error(TAG, `dealFileReceiveUri failed, code is ${err.code}, message is ${err.message}`); 60 } 61 this.context.terminateSelf(); 62 } 63 64 /** 65 * 根据不同的文件类型生成不同的文件路径 66 */ 67 private async generateFileUri() { 68 try { 69 await this.getFileType(); 70 switch (this.fileType) { 71 case btCreateFilePickerPage.FILE_TYPE_FILES: 72 await this.generateFileManagerUri(); 73 break; 74 case btCreateFilePickerPage.FILE_TYPE_IMAGE: 75 await this.generatePhotoUri(photoAccessHelper.PhotoType.IMAGE); 76 break; 77 case btCreateFilePickerPage.FILE_TYPE_VIDEO: 78 await this.generatePhotoUri(photoAccessHelper.PhotoType.VIDEO); 79 break; 80 default: 81 console.error(TAG, `invalid fileType`); 82 break; 83 } 84 } catch (error) { 85 let err: BusinessError = error as BusinessError; 86 console.error(TAG, `generateFileUri failed, code is ${err.code}, message is ${err.message}`); 87 this.context.terminateSelf(); 88 } 89 } 90 91 /** 92 * 发布获取文件路径成功事件 93 */ 94 private publishFileUriEvent() { 95 const options: commonEventManager.CommonEventPublishData = { 96 code: 0, 97 data: 'message', 98 subscriberPermissions: [], 99 isOrdered: false, 100 isSticky: false, 101 parameters: { 'uri': this.fileUri, 'fileType': this.fileType } 102 } 103 commonEventManager.publish(BT_NI_GET_URI_EVENT, options, (err: BusinessError) => { 104 if (err) { 105 console.info(TAG, `get file URI event publish failed, code is ${err.code}, message is ${err.message}`); 106 } else { 107 console.info(TAG, `get file URI event publish success.`); 108 } 109 }); 110 } 111 112 /** 113 * 获取文件后缀名 114 */ 115 private getFileExtension() : string { 116 this.fileName = AppStorage.Get('fileName') as string; 117 AppStorage.Delete('fileName'); 118 if (this.fileName == undefined || this.fileName.length < 1 || 119 !this.fileName.includes('.') || this.fileName.charAt(this.fileName.length - 1) == '.') { 120 console.error(TAG, `undefined fileName`); 121 return ''; 122 } 123 return this.fileName.slice(this.fileName.lastIndexOf('.') + 1).toLowerCase(); 124 } 125 126 /** 127 * 获取文件类型: IMAGE or VIDEO or DOC 128 */ 129 private async getFileType() { 130 try { 131 console.log(TAG, `getFileType start`); 132 this.extension = this.getFileExtension(); 133 let imageList : string[] = 134 await this.phAccessHelper.getSupportedPhotoFormats(photoAccessHelper.PhotoType.IMAGE); 135 if (imageList.includes(this.extension)) { 136 console.log(TAG, `file extension is PhotoType.IMAGE`); 137 this.fileType = btCreateFilePickerPage.FILE_TYPE_IMAGE; 138 return; 139 } 140 let videoList : string[] = 141 await this.phAccessHelper.getSupportedPhotoFormats(photoAccessHelper.PhotoType.VIDEO); 142 if (videoList.includes(this.extension)) { 143 console.log(TAG, `file extension is PhotoType.VIDEO`); 144 this.fileType = btCreateFilePickerPage.FILE_TYPE_VIDEO; 145 } else { 146 this.fileType = btCreateFilePickerPage.FILE_TYPE_FILES; 147 } 148 } catch (error) { 149 let err: BusinessError = error as BusinessError; 150 console.error(TAG, `getFileType failed, code is ${err.code}, message is ${err.message}`); 151 this.context.terminateSelf(); 152 } 153 } 154 155 156 /** 157 * 生成图库文件路径 158 */ 159 private async generatePhotoUri(photoType : photoAccessHelper.PhotoType) { 160 try { 161 console.log(TAG, `createAsset start`); 162 this.fileUri = await this.phAccessHelper.createAsset(photoType, this.extension); 163 } catch (error) { 164 let err: BusinessError = error as BusinessError; 165 console.error(TAG, `createAsset failed, code is ${err.code}, message is ${err.message}`); 166 this.context.terminateSelf(); 167 } 168 } 169 170 171 /** 172 * 生成文件管理文件路径 173 */ 174 private async generateFileManagerUri() { 175 try { 176 let documentSaveOptions = new picker.DocumentSaveOptions(); 177 documentSaveOptions.pickerMode = picker.DocumentPickerMode.DOWNLOAD; 178 const documentPicker = new picker.DocumentViewPicker(); 179 let documentSaveResult: string[] = await documentPicker.save(documentSaveOptions); 180 console.info(TAG, `opp documentViewPicker.save to file succeed` + documentSaveResult.length); 181 if (documentSaveResult.length > 0) { 182 this.fileUri = documentSaveResult[0]; 183 } 184 } catch (error) { 185 let err: BusinessError = error as BusinessError; 186 console.error(TAG, `generateFileManagerUri failed, code is ${err.code}, message is ${err.message}`); 187 this.context.terminateSelf(); 188 } 189 } 190 191 aboutToDisappear() { 192 let session = AppStorage.get<UIExtensionContentSession>('ConfirmSession'); 193 if (session) { 194 console.info(TAG, `session.terminateSelf`); 195 session.terminateSelf(); 196 } 197 } 198 199 onCancel() { 200 console.info(TAG, `onCancel is called`) 201 } 202 203 build() { 204 } 205}