1 /*
2 * Copyright (c) 2021-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 RENDER_SERVICE_CLIENT_CORE_RENDER_RS_IMAGE_H
17 #define RENDER_SERVICE_CLIENT_CORE_RENDER_RS_IMAGE_H
18
19 #include "draw/canvas.h"
20 #include "effect/color_filter.h"
21 #include "image/image.h"
22 #include "render/rs_image_base.h"
23
24 namespace OHOS {
25 namespace Media {
26 class PixelMap;
27 }
28 namespace Rosen {
29 namespace Drawing {
30 struct AdaptiveImageInfo {
31 int32_t fitNum = 0;
32 int32_t repeatNum = 0;
33 Point radius[4];
34 double scale = 0.0;
35 uint32_t uniqueId = 0;
36 int32_t width = 0;
37 int32_t height = 0;
38 uint32_t dynamicRangeMode = 0;
39 int32_t rotateDegree = 0;
40 Rect frameRect;
41 Drawing::Matrix fitMatrix = Drawing::Matrix();
42 };
43 }
44
45 class RsImageInfo final {
46 public:
RsImageInfo(int fitNum,int repeatNum,const Drawing::Point * radius,double scale,uint32_t id,int w,int h)47 RsImageInfo(int fitNum, int repeatNum, const Drawing::Point* radius, double scale, uint32_t id, int w, int h)
48 : fitNum_(fitNum), repeatNum_(repeatNum), radius_(radius), scale_(scale),
49 uniqueId_(id), width_(w), height_(h) {};
~RsImageInfo()50 ~RsImageInfo() {}
51 int fitNum_ = 0;
52 int repeatNum_ = 0;
53 const Drawing::Point* radius_;
54 double scale_ = 0.0;
55 uint32_t uniqueId_ = 0;
56 int width_ = 0;
57 int height_ = 0;
58 };
59
60 enum class ImageRepeat {
61 NO_REPEAT = 0,
62 REPEAT_X,
63 REPEAT_Y,
64 REPEAT,
65 };
66
67 enum class ImageFit {
68 FILL,
69 CONTAIN,
70 COVER,
71 FIT_WIDTH,
72 FIT_HEIGHT,
73 NONE,
74 SCALE_DOWN,
75 TOP_LEFT,
76 TOP,
77 TOP_RIGHT,
78 LEFT,
79 CENTER,
80 RIGHT,
81 BOTTOM_LEFT,
82 BOTTOM,
83 BOTTOM_RIGHT,
84 COVER_TOP_LEFT,
85 MATRIX,
86 };
87
88 class RSB_EXPORT RSImage : public RSImageBase {
89 public:
90 RSImage() = default;
91 ~RSImage();
92
93 bool IsEqual(const RSImage& other) const;
94 void CanvasDrawImage(Drawing::Canvas& canvas, const Drawing::Rect& rect,
95 const Drawing::SamplingOptions& samplingOptions, bool isBackground = false);
96 void SetImageFit(int fitNum);
97 void SetImageRepeat(int repeatNum);
98 void SetImageRotateDegree(int32_t degree);
99 void SetRadius(const std::vector<Drawing::Point>& radius);
100 void SetScale(double scale);
SetInnerRect(const std::optional<Drawing::RectI> & innerRect)101 void SetInnerRect(const std::optional<Drawing::RectI>& innerRect) { innerRect_ = innerRect;}
102
103 void SetCompressData(const std::shared_ptr<Drawing::Data> data, uint32_t id, int width, int height);
104 void SetCompressData(const std::shared_ptr<Drawing::Data> compressData);
105
106 bool HDRConvert(const Drawing::SamplingOptions& sampling, Drawing::Canvas& canvas);
107 void SetPaint(Drawing::Paint paint);
108 void SetDynamicRangeMode(uint32_t dynamicRangeMode);
109
110 void SetNodeId(NodeId nodeId);
111
112 void ApplyImageFit();
113 ImageFit GetImageFit();
114 Drawing::AdaptiveImageInfo GetAdaptiveImageInfoWithCustomizedFrameRect(const Drawing::Rect& frameRect) const;
115 RectF GetDstRect();
116 void SetFrameRect(RectF frameRect);
117 void SetFitMatrix(const Drawing::Matrix& matrix);
118 Drawing::Matrix GetFitMatrix() const;
119 #ifdef ROSEN_OHOS
120 bool Marshalling(Parcel& parcel) const override;
121 [[nodiscard]] static RSImage* Unmarshalling(Parcel& parcel);
122 #endif
dump(std::string & desc,int depth)123 void dump(std::string &desc, int depth) const
124 {
125 std::string split(depth, '\t');
126 desc += split + "RSImage:{";
127 desc += split + "\timageFit_: " + std::to_string(static_cast<int>(imageFit_)) + "\n";
128 desc += split + "\timageRepeat_: " + std::to_string(static_cast<int>(imageRepeat_)) + "\n";
129 int radiusSize = 4;
130 for (int i = 0; i < radiusSize; i++) {
131 desc += split + "\tPointF:{ \n";
132 desc += split + "\t\t x_: " + std::to_string(radius_[i].GetX()) + "\n";
133 desc += split + "\t\t y_: " + std::to_string(radius_[i].GetY()) + "\n";
134 desc += split + "\t}\n";
135 }
136 desc += split + frameRect_.ToString();
137 desc += split + "\tscale_: " + std::to_string(scale_) + "\n";
138 desc += split + "}\n";
139 }
140
141 private:
142 bool HasRadius() const;
143 void ApplyCanvasClip(Drawing::Canvas& canvas);
144 void UploadGpu(Drawing::Canvas& canvas);
145 std::pair<float, float> CalculateByDegree(const Drawing::Rect& rect);
146 void DrawImageWithRotateDegree(
147 Drawing::Canvas& canvas, const Drawing::Rect& rect, const Drawing::SamplingOptions& samplingOptions);
148 void DrawImageRepeatRect(const Drawing::SamplingOptions& samplingOptions, Drawing::Canvas& canvas);
149 void CalcRepeatBounds(int& minX, int& maxX, int& minY, int& maxY);
150 void DrawImageOnCanvas(
151 const Drawing::SamplingOptions& samplingOptions, Drawing::Canvas& canvas, const bool hdrImageDraw);
152 void DrawImageWithFirMatrixRotateOnCanvas(
153 const Drawing::SamplingOptions& samplingOptions, Drawing::Canvas& canvas) const;
154 #ifdef ROSEN_OHOS
155 static bool UnmarshalIdSizeAndNodeId(Parcel& parcel, uint64_t& uniqueId, int& width, int& height, NodeId& nodeId);
156 static bool UnmarshalImageProperties(Parcel& parcel, int& fitNum, int& repeatNum,
157 std::vector<Drawing::Point>& radius, double& scale, int32_t& degree,
158 bool& hasFitMatrix, Drawing::Matrix& fitMatrix);
159 static void ProcessImageAfterCreation(RSImage* rsImage, const uint64_t uniqueId, const bool useSkImage,
160 const std::shared_ptr<Media::PixelMap>& pixelMap);
161 #endif
162 std::shared_ptr<Drawing::Data> compressData_;
163 ImageFit imageFit_ = ImageFit::COVER;
164 ImageRepeat imageRepeat_ = ImageRepeat::NO_REPEAT;
165 std::vector<Drawing::Point> radius_ = std::vector<Drawing::Point>(4);
166 std::optional<Drawing::RectI> innerRect_ = std::nullopt;
167 bool hasRadius_ = false;
168 RectF frameRect_;
169 double scale_ = 1.0;
170 NodeId nodeId_ = 0;
171 int32_t rotateDegree_;
172 Drawing::Paint paint_;
173 uint32_t dynamicRangeMode_ = 0;
174 std::optional<Drawing::Matrix> fitMatrix_ = std::nullopt;
175 bool isFitMatrixValid_ = false;
176 };
177
178 template<>
ROSEN_EQ(const std::shared_ptr<RSImage> & x,const std::shared_ptr<RSImage> & y)179 inline bool ROSEN_EQ(const std::shared_ptr<RSImage>& x, const std::shared_ptr<RSImage>& y)
180 {
181 if (x == y) {
182 return true;
183 }
184 return (x && y) ? x->IsEqual(*y) : false;
185 }
186 } // namespace Rosen
187 } // namespace OHOS
188 #endif // RENDER_SERVICE_CLIENT_CORE_RENDER_RS_IMAGE_H
189