1/* 2 * Copyright (c) 2023 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 { Log } from '../../utils/Log' 17import { OhCombinedState } from '../../redux/store' 18import { getStore } from '../../redux/store' 19import { Action } from '../../redux/actions/Action' 20import { EventBus } from '../../worker/eventbus/EventBus' 21import { EventBusManager } from '../../worker/eventbus/EventBusManager' 22import EventLog from '../../utils/EventLog' 23import { CameraService } from '../../camera/CameraService' 24import { Dispatch } from '../../redux/core/redux/types/store' 25import { GlobalContext } from '../../utils/GlobalContext' 26import Want from '@ohos.app.ability.Want' 27 28class StateStruct { 29 thumbnail: Resource = $r('app.media.ic_camera_thumbnail_default_white'); 30} 31 32class UpdateThumbnailStruct { 33 thumbnail: PixelMap | undefined = undefined; 34 resourceUri: string = ''; 35} 36 37class ThumbnailStruct { 38 thumbnail: PixelMap | undefined = undefined; 39} 40 41class StartAbilityParameterStruct { 42 uri: string = ''; 43} 44 45class ThumbnailViewDispatcher { 46 private mDispatch: Dispatch = (data) => data; 47 48 public setDispatch(dispatch: Dispatch) { 49 this.mDispatch = dispatch; 50 } 51} 52 53@Component 54export struct ThumbnailView { 55 private TAG: string = '[ThumbnailView]:' 56 private appEventBus: EventBus = EventBusManager.getInstance().getEventBus() 57 @State thumbnailBorder: BorderOptions = {}; 58 @State state: StateStruct = new StateStruct() 59 @State thumbnail: Resource | PixelMap = $r('app.media.ic_camera_thumbnail_default_white') 60 @State hasThumbnail: boolean = false 61 @State scaleValue: number = 1 62 @State tempOpacity: number = 1 63 private cameraService = CameraService.getInstance() 64 private mAction: ThumbnailViewDispatcher = new ThumbnailViewDispatcher(); 65 66 private async onThumbnailUpdate(data: UpdateThumbnailStruct): Promise<void> { 67 Log.info(`${this.TAG} onThumbnailUpdate data: ${JSON.stringify(data)} E`) 68 this.thumbnail = (data.thumbnail == null ? $r('app.media.ic_camera_thumbnail_default_white') : data.thumbnail) 69 this.hasThumbnail = data.thumbnail != undefined 70 if (this.hasThumbnail) { 71 this.thumbnailBorder = { width: 1, color: Color.White, style: BorderStyle.Solid } 72 } else { 73 this.thumbnailBorder = { width: 0 } 74 } 75 this.scaleValue = 1.5 76 this.tempOpacity = 0.0 77 animateTo({ duration: 100, curve: Curve.Sharp }, () => { 78 this.tempOpacity = 1 79 }) 80 animateTo({ duration: 300, curve: Curve.Sharp }, () => { 81 this.scaleValue = 1 82 }) 83 Log.info(`${this.TAG} onThumbnailUpdate this.state.thumbnail: ${JSON.stringify(this.thumbnail)} X`) 84 } 85 86 private async onThumbnailLoad(data: ThumbnailStruct): Promise<void> { 87 Log.info(`${this.TAG} onThumbnailLoad data: ${JSON.stringify(data)} E`) 88 this.thumbnail = (data.thumbnail == null ? $r('app.media.ic_camera_thumbnail_default_white') : data.thumbnail) 89 this.hasThumbnail = data.thumbnail != undefined 90 if (this.hasThumbnail) { 91 this.thumbnailBorder = { width: 1, color: Color.White, style: BorderStyle.Solid } 92 } else { 93 this.thumbnailBorder = { width: 0 } 94 } 95 this.scaleValue = 1 96 this.tempOpacity = 1 97 Log.info(`${this.TAG} onThumbnailLoad this.state.thumbnail: ${JSON.stringify(this.thumbnail)} X`) 98 } 99 100 aboutToAppear() { 101 Log.info(`${this.TAG} aboutToAppear E`) 102 getStore().subscribe((state: OhCombinedState) => { 103 this.state = { 104 thumbnail: state.CameraInitReducer.thumbnail 105 }; 106 }, (dispatch: Dispatch) => { 107 this.mAction.setDispatch(dispatch); 108 }); 109 this.appEventBus.on(Action.ACTION_UPDATE_THUMBNAIL, (data: UpdateThumbnailStruct) => this.onThumbnailUpdate(data)); 110 this.appEventBus.on(Action.ACTION_LOAD_THUMBNAIL, (data: ThumbnailStruct) => this.onThumbnailLoad(data)); 111 Log.info(`${this.TAG} aboutToAppear X`) 112 } 113 114 aboutToDisappear(): void { 115 Log.info(`${this.TAG} aboutToDisappear E`) 116 this.appEventBus.off(Action.ACTION_UPDATE_THUMBNAIL, (data: UpdateThumbnailStruct) => this.onThumbnailUpdate(data)) 117 this.appEventBus.off(Action.ACTION_LOAD_THUMBNAIL, (data: ThumbnailStruct) => this.onThumbnailLoad(data)); 118 Log.info(`${this.TAG} aboutToDisappear X`) 119 } 120 121 build() { 122 Column() { 123 Stack() { 124 Image(this.thumbnail) 125 .width('100%').aspectRatio(1).borderRadius(22).objectFit(ImageFit.Fill) 126 } 127 .width('100%').height('100%') 128 .enabled(this.hasThumbnail) 129 .onClick(async () => { 130 Log.info(`${this.TAG} launch bundle com.ohos.photos`) 131 EventLog.write(EventLog.CLICK_THUMBNAIL) 132 GlobalContext.get().setObject('keepCameraZoomRatio', true); 133 const recentUri: string = this.cameraService.getRecentFileUri(); 134 Log.info(`${this.TAG} uri === ` + recentUri) 135 const abilityParameter: Record<string, string> = { 'uri': recentUri }; 136 await GlobalContext.get().getCameraAbilityContext().startAbility(this.buildCameraAbilityWant(abilityParameter)) 137 }) 138 } 139 .width(44).aspectRatio(1) 140 .borderRadius(22).border(this.thumbnailBorder) 141 .opacity(this.tempOpacity) 142 .scale({ x: this.scaleValue, y: this.scaleValue }) 143 } 144 145 private buildCameraAbilityWant(parameter: Record<string, string>): Want { 146 let res: Want = { 147 parameters: parameter, 148 action: 'ohos.want.action.viewData', 149 bundleName: 'com.ohos.photos', 150 abilityName: 'com.ohos.photos.MainAbility' 151 }; 152 return res; 153 } 154}