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 16 #ifndef DRAW_CMD_LIST_H 17 #define DRAW_CMD_LIST_H 18 19 #include "draw/canvas.h" 20 #include "recording/cmd_list.h" 21 22 namespace OHOS { 23 namespace Rosen { 24 namespace Drawing { 25 class DrawOpItem; 26 class DRAWING_API DrawCmdList : public CmdList { 27 public: 28 /** 29 * @brief there are two mode for DrawCmdList to add new op 30 * @param IMMEDIATE add op to continouns buffer immediately, overload will benefit from this 31 * @param DEFERRED add op to vector and then add to contiguous buffer if needed 32 * @detail playback can get all op from continouns buffer in IMMEDIATE mode or vector int DEFERRED mode 33 */ 34 enum class UnmarshalMode { 35 IMMEDIATE, 36 DEFERRED 37 }; 38 39 /** 40 * @brief Creates a DrawCmdList with contiguous buffers. 41 * @param data A contiguous buffers. 42 * @param isCopy Whether to copy data or not. 43 * @detail Called only by Unmarshalling-Thread, the default mode is DEFERRED since all DrawOp store in vector 44 */ 45 static std::shared_ptr<DrawCmdList> CreateFromData(const CmdListData& data, bool isCopy = false); 46 47 /** 48 * @brief Creates a DrawCmdList 49 */ 50 DrawCmdList(UnmarshalMode mode = UnmarshalMode::IMMEDIATE); 51 DrawCmdList(int32_t width, int32_t height, UnmarshalMode mode = UnmarshalMode::IMMEDIATE); 52 53 /** 54 * @brief Destroy a DrawCmdList 55 */ 56 ~DrawCmdList() override; 57 58 /** 59 * @brief Gets cmd list type. 60 * @return Returns DRAW_CMD_LIST 61 */ GetType()62 uint32_t GetType() const override 63 { 64 return Type::DRAW_CMD_LIST; 65 } 66 67 /** 68 * @brief Add DrawOpItem to DrawCmdList, only can be used in IMMEDIATE mode 69 * @param T The name of DrawOpItem class 70 * @param Args Constructs arguments to the DrawOpItem 71 * @return true if add success, false if not in IMMEDIATE mode or create op in contiguous buffer failed 72 */ 73 template<typename T, typename... Args> AddDrawOp(Args &&...args)74 bool AddDrawOp(Args&&... args) 75 { 76 if (mode_ != UnmarshalMode::IMMEDIATE) { 77 return false; 78 } 79 std::lock_guard<std::recursive_mutex> lock(mutex_); 80 T* op = opAllocator_.Allocate<T>(std::forward<Args>(args)...); 81 if (op == nullptr) { 82 return false; 83 } 84 85 uint32_t offset = opAllocator_.AddrToOffset(op); 86 if (lastOpItemOffset_.has_value()) { 87 #ifdef CROSS_PLATFORM 88 auto* lastOpItem = static_cast<OpItem*>( 89 opAllocator_.OffsetToAddr(lastOpItemOffset_.__get(), sizeof(OpItem))); 90 #else 91 auto* lastOpItem = static_cast<OpItem*>( 92 opAllocator_.OffsetToAddr(lastOpItemOffset_.value(), sizeof(OpItem))); 93 #endif 94 if (lastOpItem != nullptr) { 95 lastOpItem->SetNextOpItemOffset(offset); 96 } 97 } 98 lastOpItemOffset_.emplace(offset); 99 opCnt_++; 100 return true; 101 } 102 103 /** 104 * @brief Add DrawOpItem to DrawCmdList, only can be used in DEFERRED mode 105 * @param drawOpItem A real DrawOpItem instance 106 * @return true if add success, false if not in DEFERRED mode 107 */ 108 bool AddDrawOp(std::shared_ptr<DrawOpItem>&& drawOpItem); 109 110 /** 111 * @brief Clear DrawOpItem in contiguous buffer, draw op vector, and other resource associated with draw op 112 */ 113 void ClearOp(); 114 115 /** 116 * @brief Get op vector size 117 */ 118 size_t GetOpItemSize() const; 119 120 /** 121 * @brief for each op in vector, combine there desc together 122 */ 123 std::string GetOpsWithDesc() const; 124 125 /** 126 * @brief Marshalling Draw Ops Param from vector to contiguous buffers. 127 */ 128 void MarshallingDrawOps(); 129 130 /** 131 * @brief Unmarshalling Draw Ops from contiguous buffers to vector 132 * it is only called by Unmarshalling-Thread, the mode should be set to DEFERRED when create. 133 */ 134 void UnmarshallingDrawOps(uint32_t* opItemCount = nullptr); 135 136 /** 137 * @brief Draw cmd is empty or not. 138 */ 139 bool IsEmpty() const; 140 141 /** 142 * @brief Calls the corresponding operations of all opitems in DrawCmdList to the canvas. 143 * @param canvas Implements the playback action of the DrawCmdList in the Canvas. 144 * @param rect Rect used to playback, may be nullptr. 145 */ 146 void Playback(Canvas& canvas, const Rect* rect = nullptr); 147 148 /** 149 * @brief Gets the width of the DrawCmdList. 150 */ 151 int32_t GetWidth() const; 152 153 /** 154 * @brief Gets the height of the DrawCmdList. 155 */ 156 int32_t GetHeight() const; 157 158 /** 159 * @brief Sets the width of the DrawCmdList. 160 */ 161 void SetWidth(int32_t width); 162 163 /** 164 * @brief Sets the height of the DrawCmdList. 165 */ 166 void SetHeight(int32_t height); 167 168 /** 169 * @brief Convert Textblob Op to Image Op, it is different for difference mode 170 * IMMEDIATE: the Image Op will add to the end of buffer, and the mapped offset will be recorded in 171 * replacedOpListForBuffer. 172 * DEFERRED: the image Op will replace the Textblob op in vector, and the index-op_ptr will be recorded 173 * in replacedOpListForVector. 174 */ 175 void GenerateCache(Canvas* canvas = nullptr, const Rect* rect = nullptr); 176 177 bool GetIsCache() const; 178 179 void SetIsCache(bool isCached); 180 181 bool GetCachedHighContrast() const; 182 183 void SetCachedHighContrast(bool cachedHighContrast); 184 185 std::vector<std::pair<size_t, size_t>> GetReplacedOpList(); 186 187 void SetReplacedOpList(std::vector<std::pair<size_t, size_t>> replacedOpList); 188 189 void UpdateNodeIdToPicture(NodeId nodeId); 190 191 size_t CountTextBlobNum(); 192 193 void Dump(std::string& out); 194 195 void Purge(); 196 197 void SetIsNeedUnmarshalOnDestruct(bool isNeedUnmarshalOnDestruct); 198 private: 199 void ClearCache(); 200 void GenerateCacheByVector(Canvas* canvas, const Rect* rect); 201 void GenerateCacheByBuffer(Canvas* canvas, const Rect* rect); 202 203 void PlaybackToDrawCmdList(std::shared_ptr<DrawCmdList> drawCmdList); 204 void PlaybackByVector(Canvas& canvas, const Rect* rect = nullptr); 205 void PlaybackByBuffer(Canvas& canvas, const Rect* rect = nullptr); 206 void CaculatePerformanceOpType(); 207 208 int32_t width_; 209 int32_t height_; 210 const UnmarshalMode mode_; 211 const size_t offset_ = 2 * sizeof(int32_t); // 2 is width and height.Offset of first OpItem is behind the w and h 212 std::vector<std::shared_ptr<DrawOpItem>> drawOpItems_; 213 214 size_t lastOpGenSize_ = 0; 215 std::vector<std::pair<size_t, size_t>> replacedOpListForBuffer_; 216 std::vector<std::pair<int, std::shared_ptr<DrawOpItem>>> replacedOpListForVector_; 217 bool isCached_ = false; 218 bool cachedHighContrast_ = false; 219 uint32_t performanceCaculateOpType_ = 0; 220 bool isNeedUnmarshalOnDestruct_ = false; 221 }; 222 223 using DrawCmdListPtr = std::shared_ptr<DrawCmdList>; 224 } // namespace Drawing 225 } // namespace Rosen 226 } // namespace OHOS 227 228 #endif // DRAW_CMD_LIST_H 229