1 /* 2 * Copyright (c) 2022-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 16 #ifndef FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_IMAGE_PROVIDER_IMAGE_PROVIDER_H 17 #define FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_IMAGE_PROVIDER_IMAGE_PROVIDER_H 18 19 #include <functional> 20 #include <set> 21 #include <unordered_map> 22 23 #include "base/image/image_defines.h" 24 #include "base/image/pixel_map.h" 25 #include "base/thread/cancelable_callback.h" 26 #include "core/components_ng/image_provider/image_data.h" 27 #include "core/components_ng/image_provider/image_state_manager.h" 28 #include "core/components_ng/pattern/image/image_dfx.h" 29 #include "core/components_ng/render/canvas_image.h" 30 #include "core/image/image_source_info.h" 31 32 namespace OHOS::Ace::NG { 33 34 using DataReadyNotifyTask = std::function<void(const ImageSourceInfo& src)>; 35 using LoadSuccessNotifyTask = std::function<void(const ImageSourceInfo& src)>; 36 using LoadFailNotifyTask = 37 std::function<void(const ImageSourceInfo& src, const std::string& errorMsg, const ImageErrorInfo& errorInfo)>; 38 using OnCompleteInDataReadyNotifyTask = std::function<void(const ImageSourceInfo& src)>; 39 40 struct LoadNotifier { LoadNotifierLoadNotifier41 LoadNotifier(DataReadyNotifyTask&& dataReadyNotifyTask, LoadSuccessNotifyTask&& loadSuccessNotifyTask, 42 LoadFailNotifyTask&& loadFailNotifyTask) 43 : onDataReady_(std::move(dataReadyNotifyTask)), onLoadSuccess_(std::move(loadSuccessNotifyTask)), 44 onLoadFail_(std::move(loadFailNotifyTask)) 45 {} 46 47 DataReadyNotifyTask onDataReady_; 48 LoadSuccessNotifyTask onLoadSuccess_; 49 LoadFailNotifyTask onLoadFail_; 50 OnCompleteInDataReadyNotifyTask onDataReadyComplete_; 51 }; 52 53 struct ImageDecoderOptions { 54 bool forceResize = false; 55 bool sync = false; 56 DynamicRangeMode dynamicMode = DynamicRangeMode::STANDARD; 57 AIImageQuality imageQuality = AIImageQuality::NONE; 58 bool isHdrDecoderNeed = false; 59 PixelFormat photoDecodeFormat = PixelFormat::UNKNOWN; 60 ImageDfxConfig imageDfxConfig; 61 }; 62 63 struct UriDownLoadConfig { 64 ImageSourceInfo src; 65 ImageDfxConfig imageDfxConfig; 66 std::string taskKey; 67 bool sync = false; 68 bool hasProgressCallback = false; 69 }; 70 71 struct ImageLoadResultInfo { 72 ImageErrorInfo errorInfo; 73 size_t fileSize = 0; // size of file in bytes 74 }; 75 76 class ImageObject; 77 78 // load & decode images 79 class ImageProvider : public virtual AceType { 80 DECLARE_ACE_TYPE(ImageProvider, AceType); 81 82 public: 83 /** Fetch image data and create ImageObject from ImageSourceInfo. 84 * 85 * @param src image source info 86 * @param ctxWp ImageLoadingContext that initiates the task, to be stored in the map 87 * @param sync if true, run task synchronously 88 */ 89 static void CreateImageObject( 90 const ImageSourceInfo& src, const WeakPtr<ImageLoadingContext>& ctxWp, bool sync, bool isSceneBoardWindow); 91 92 /** Decode image data and make CanvasImage from ImageObject. 93 * 94 * @param obj imageObject, contains image data 95 * @param targetSize target size of canvasImage 96 * @param forceResize force resize image to target size 97 * @param sync if true, run task synchronously 98 * @param dynamicMode set dynamic range mode of image 99 * @param imageQuality set the image quality enhancement level of image 100 * @return true if MakeCanvasImage was successful 101 */ 102 static void MakeCanvasImage(const RefPtr<ImageObject>& obj, const WeakPtr<ImageLoadingContext>& ctxWp, 103 const SizeF& targetSize, const ImageDecoderOptions& imageDecoderOptions); 104 105 /** Check if data is present in imageObj, if not, reload image data. 106 * 107 * @param imageObj contains image source and image data 108 * @return true if image data is prepared 109 */ 110 static bool PrepareImageData(const RefPtr<ImageObject>& imageObj); 111 112 // Query imageObj from cache, if hit, notify dataReady and returns true 113 static RefPtr<ImageObject> QueryImageObjectFromCache(const ImageSourceInfo& src); 114 115 // cancel a scheduled background task 116 static bool CancelTask(const std::string& key, const WeakPtr<ImageLoadingContext>& ctx); 117 118 static RefPtr<ImageObject> BuildImageObject( 119 const ImageSourceInfo& src, ImageErrorInfo& errorInfo, const RefPtr<ImageData>& data); 120 121 static void CacheImageObject(const RefPtr<ImageObject>& obj); 122 123 static RefPtr<ImageData> QueryDataFromCache(const ImageSourceInfo& src); 124 125 private: 126 /** Check if task is already running and register task in the task map, 127 * making sure the same task runs only once (CreateImageObject with same 128 * [src], MakeCanvasImage with the same [imageObj] and [size]). 129 * 130 * @param key task key, based on [src] +? [size] 131 * @param ctx ImageLoadingContext that initiates the task, to be stored in the amp 132 * @return true if task is new, false if task is already running 133 */ 134 static bool RegisterTask(const std::string& key, const WeakPtr<ImageLoadingContext>& ctx); 135 136 // mark a task as finished, erase from map and retrieve corresponding ctxs 137 static std::set<WeakPtr<ImageLoadingContext>> EndTask(const std::string& key, bool isErase = true); 138 139 static RefPtr<ImageObject> QueryThumbnailCache(const ImageSourceInfo& src); 140 141 // helper function to create image object from ImageSourceInfo 142 static void CreateImageObjHelper(const ImageSourceInfo& src, bool sync = false, bool isSceneBoardWindow = false); 143 144 static void DownLoadSuccessCallback( 145 const RefPtr<ImageObject>& imageObj, const std::string& key, bool sync = false, int32_t containerId = 0); 146 static void DownLoadOnProgressCallback( 147 const std::string& key, bool sync, const uint32_t& dlNow, const uint32_t& dlTotal, int32_t containerId = 0); 148 static void DownLoadImage(const UriDownLoadConfig& downLoadConfig); 149 150 static void MakeCanvasImageHelper(const RefPtr<ImageObject>& obj, const SizeF& targetSize, const std::string& key, 151 const ImageDecoderOptions& imagedecoderOptions); 152 153 // helper functions to end task and callback to LoadingContexts 154 static void SuccessCallback( 155 const RefPtr<CanvasImage>& canvasImage, const std::string& key, bool sync = false, int32_t containerId = 0); 156 static void FailCallback(const std::string& key, const std::string& errorMsg, const ImageErrorInfo& errorInfo, 157 bool sync = false, int32_t containerId = 0); 158 159 struct Task { 160 CancelableCallback<void()> bgTask_; 161 std::set<WeakPtr<ImageLoadingContext>> ctxs_; 162 }; 163 164 static std::timed_mutex taskMtx_; 165 static std::unordered_map<std::string, Task> tasks_; 166 }; 167 168 } // namespace OHOS::Ace::NG 169 170 #endif // FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_IMAGE_PROVIDER_IMAGE_PROVIDER_H 171