1 /*
2 * Copyright (c) 2022-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 #include "rs_base_render_engine.h"
16 #include <memory>
17
18 #include "v2_1/cm_color_space.h"
19 #ifdef RS_ENABLE_EGLIMAGE
20 #ifdef USE_M133_SKIA
21 #include "src/gpu/ganesh/gl/GrGLDefines.h"
22 #else
23 #include "src/gpu/gl/GrGLDefines.h"
24 #endif
25 #endif
26
27 #include "common/rs_optional_trace.h"
28 #include "display_engine/rs_luminance_control.h"
29 #ifdef RS_ENABLE_GPU
30 #include "drawable/rs_screen_render_node_drawable.h"
31 #endif
32 #include "memory/rs_tag_tracker.h"
33 #include "metadata_helper.h"
34 #include "pipeline/render_thread/rs_divided_render_util.h"
35 #include "pipeline/rs_uni_render_judgement.h"
36 #include "platform/common/rs_log.h"
37 #include "platform/common/rs_system_properties.h"
38 #if (defined(RS_ENABLE_GPU) && defined(RS_ENABLE_GL))
39 #include "platform/ohos/backend/rs_surface_ohos_gl.h"
40 #include "feature/gpuComposition/rs_image_manager.h"
41 #endif
42 #include "platform/ohos/backend/rs_surface_ohos_raster.h"
43 #ifdef RS_ENABLE_VK
44 #include "platform/ohos/backend/rs_surface_ohos_vulkan.h"
45 #include "platform/ohos/backend/rs_vulkan_context.h"
46 #endif
47 #ifdef USE_VIDEO_PROCESSING_ENGINE
48 #include "render/rs_colorspace_convert.h"
49 #endif
50 #include "render/rs_drawing_filter.h"
51 #include "render/rs_skia_filter.h"
52 #include "feature/hdr/rs_hdr_util.h"
53
54 namespace OHOS {
55 namespace Rosen {
56 constexpr float DEFAULT_DISPLAY_NIT = 500.0f;
57 constexpr float DEGAMMA = 1.0f / 2.2f;
58
CheckAndVerifyDamageRegion(const std::vector<RectI> & rects,const RectI & surfaceRect) const59 std::vector<RectI> RSRenderFrame::CheckAndVerifyDamageRegion(
60 const std::vector<RectI>& rects, const RectI& surfaceRect) const
61 {
62 std::vector<RectI> dstRects;
63 for (const auto& rect : rects) {
64 dstRects.emplace_back(rect.IntersectRect(surfaceRect));
65 }
66 return dstRects;
67 }
68
RSBaseRenderEngine()69 RSBaseRenderEngine::RSBaseRenderEngine()
70 {
71 }
72
~RSBaseRenderEngine()73 RSBaseRenderEngine::~RSBaseRenderEngine() noexcept
74 {
75 }
76
Init()77 void RSBaseRenderEngine::Init()
78 {
79 #if (defined RS_ENABLE_GL) || (defined RS_ENABLE_VK)
80 renderContext_ = std::make_shared<RenderContext>();
81 #ifdef RS_ENABLE_GL
82 if (!RSSystemProperties::IsUseVulkan()) {
83 renderContext_->InitializeEglContext();
84 }
85 #endif
86 if (RSUniRenderJudgement::IsUniRender()) {
87 RS_LOGI("RSRenderEngine::RSRenderEngine set new cacheDir");
88 renderContext_->SetUniRenderMode(true);
89 }
90 #if defined(RS_ENABLE_VK)
91 if (RSSystemProperties::IsUseVulkan()) {
92 skContext_ = RsVulkanContext::GetSingleton().CreateDrawingContext();
93 renderContext_->SetUpGpuContext(skContext_);
94 } else {
95 renderContext_->SetUpGpuContext();
96 }
97 #else
98 renderContext_->SetUpGpuContext();
99 #endif
100 #endif // RS_ENABLE_GL || RS_ENABLE_VK
101 #if (defined(RS_ENABLE_EGLIMAGE) && defined(RS_ENABLE_GPU)) || defined(RS_ENABLE_VK)
102 imageManager_ = RSImageManager::Create(renderContext_);
103 #endif // RS_ENABLE_EGLIMAGE
104 #ifdef USE_VIDEO_PROCESSING_ENGINE
105 colorSpaceConverterDisplay_ = Media::VideoProcessingEngine::ColorSpaceConverterDisplay::Create();
106 #endif
107 }
108
ResetCurrentContext()109 void RSBaseRenderEngine::ResetCurrentContext()
110 {
111 #ifdef RS_ENABLE_GPU
112 if (renderContext_ == nullptr) {
113 RS_LOGE("This render context is nullptr.");
114 return;
115 }
116 #endif
117 #if (defined RS_ENABLE_GL)
118 if (RSSystemProperties::GetGpuApiType() == GpuApiType::OPENGL) {
119 renderContext_->ShareMakeCurrentNoSurface(EGL_NO_CONTEXT);
120 }
121 #endif
122
123 #if defined(RS_ENABLE_VK) // end RS_ENABLE_GL and enter RS_ENABLE_VK
124 if (RSSystemProperties::IsUseVulkan()) {
125 renderContext_->AbandonContext();
126 }
127 #endif // end RS_ENABLE_GL and RS_ENABLE_VK
128 }
129
NeedForceCPU(const std::vector<LayerInfoPtr> & layers)130 bool RSBaseRenderEngine::NeedForceCPU(const std::vector<LayerInfoPtr>& layers)
131 {
132 bool forceCPU = false;
133 for (const auto& layer: layers) {
134 if (layer == nullptr) {
135 continue;
136 }
137
138 auto buffer = layer->GetBuffer();
139 if (buffer == nullptr) {
140 continue;
141 }
142
143 #ifndef RS_ENABLE_EGLIMAGE
144 const auto bufferFormat = buffer->GetFormat();
145 if (bufferFormat == GRAPHIC_PIXEL_FMT_YCRCB_420_SP || bufferFormat == GRAPHIC_PIXEL_FMT_YCBCR_420_SP) {
146 forceCPU = true;
147 break;
148 }
149 #endif
150 }
151
152 return forceCPU;
153 }
154
RequestFrame(const std::shared_ptr<RSSurfaceOhos> & rsSurface,const BufferRequestConfig & config,bool forceCPU,bool useAFBC,const FrameContextConfig & frameContextConfig)155 std::unique_ptr<RSRenderFrame> RSBaseRenderEngine::RequestFrame(
156 const std::shared_ptr<RSSurfaceOhos>& rsSurface,
157 const BufferRequestConfig& config, bool forceCPU, bool useAFBC,
158 const FrameContextConfig& frameContextConfig)
159 {
160 #ifdef RS_ENABLE_VK
161 if (RSSystemProperties::GetGpuApiType() == GpuApiType::VULKAN ||
162 RSSystemProperties::GetGpuApiType() == GpuApiType::DDGR) {
163 skContext_ = RsVulkanContext::GetSingleton().CreateDrawingContext();
164 if (renderContext_ == nullptr) {
165 return nullptr;
166 }
167 renderContext_->SetUpGpuContext(skContext_);
168 }
169 #endif
170 if (rsSurface == nullptr) {
171 RS_LOGE("RSBaseRenderEngine::RequestFrame: surface is null!");
172 return nullptr;
173 }
174 RS_OPTIONAL_TRACE_BEGIN("RSBaseRenderEngine::RequestFrame(RSSurface)");
175 #ifdef RS_ENABLE_VK
176 RSTagTracker tagTracker(skContext_, RSTagTracker::TAGTYPE::TAG_ACQUIRE_SURFACE);
177 #endif
178 rsSurface->SetColorSpace(config.colorGamut);
179 rsSurface->SetSurfacePixelFormat(config.format);
180 if (frameContextConfig.isVirtual) {
181 RS_LOGD("RSBaseRenderEngine::RequestFrame: Mirror Screen Set Timeout to 0.");
182 rsSurface->SetTimeOut(frameContextConfig.timeOut);
183 }
184 auto bufferUsage = config.usage;
185 #if (defined(RS_ENABLE_GL) || defined(RS_ENABLE_VK)) && (defined RS_ENABLE_EGLIMAGE)
186 if (forceCPU) {
187 bufferUsage |= BUFFER_USAGE_CPU_WRITE;
188 }
189 #else
190 bufferUsage |= BUFFER_USAGE_CPU_WRITE;
191 #endif
192 if (frameContextConfig.isProtected) {
193 bufferUsage |= BUFFER_USAGE_PROTECTED;
194 }
195 rsSurface->SetSurfaceBufferUsage(bufferUsage);
196
197 // check if we can use GPU context
198 #ifdef RS_ENABLE_GL
199 if (RSSystemProperties::GetGpuApiType() == GpuApiType::OPENGL &&
200 renderContext_ != nullptr) {
201 rsSurface->SetRenderContext(renderContext_.get());
202 }
203 #endif
204 #ifdef RS_ENABLE_VK
205 if (RSSystemProperties::IsUseVulkan() && skContext_ != nullptr) {
206 std::static_pointer_cast<RSSurfaceOhosVulkan>(rsSurface)->SetSkContext(skContext_);
207 }
208 #endif
209 auto surfaceFrame = rsSurface->RequestFrame(config.width, config.height, 0, useAFBC,
210 frameContextConfig.isProtected);
211 RS_OPTIONAL_TRACE_END();
212 if (surfaceFrame == nullptr) {
213 RS_LOGE("RSBaseRenderEngine::RequestFrame: request SurfaceFrame failed!");
214 return nullptr;
215 }
216 return std::make_unique<RSRenderFrame>(rsSurface, std::move(surfaceFrame));
217 }
218
RequestFrame(const sptr<Surface> & targetSurface,const BufferRequestConfig & config,bool forceCPU,bool useAFBC,const FrameContextConfig & frameContextConfig)219 std::unique_ptr<RSRenderFrame> RSBaseRenderEngine::RequestFrame(const sptr<Surface>& targetSurface,
220 const BufferRequestConfig& config, bool forceCPU, bool useAFBC,
221 const FrameContextConfig& frameContextConfig)
222 {
223 RS_OPTIONAL_TRACE_BEGIN("RSBaseRenderEngine::RequestFrame(targetSurface)");
224 if (targetSurface == nullptr) {
225 RS_LOGE("RSBaseRenderEngine::RequestFrame: surface is null!");
226 RS_OPTIONAL_TRACE_END();
227 return nullptr;
228 }
229
230 std::shared_ptr<RSSurfaceOhos> rsSurface = nullptr;
231 #if (defined RS_ENABLE_GL) && (defined RS_ENABLE_EGLIMAGE)
232 if (RSSystemProperties::GetGpuApiType() == GpuApiType::OPENGL) {
233 if (forceCPU) {
234 rsSurface = std::make_shared<RSSurfaceOhosRaster>(targetSurface);
235 } else {
236 rsSurface = std::make_shared<RSSurfaceOhosGl>(targetSurface);
237 }
238 }
239 #endif
240 #if (defined RS_ENABLE_VK)
241 if (RSSystemProperties::IsUseVulkan()) {
242 rsSurface = std::make_shared<RSSurfaceOhosVulkan>(targetSurface);
243 }
244 #endif
245 if (rsSurface == nullptr) {
246 rsSurface = std::make_shared<RSSurfaceOhosRaster>(targetSurface);
247 }
248 RS_OPTIONAL_TRACE_END();
249 return RequestFrame(rsSurface, config, forceCPU, useAFBC, frameContextConfig);
250 }
251
MakeRSSurface(const sptr<Surface> & targetSurface,bool forceCPU)252 std::shared_ptr<RSSurfaceOhos> RSBaseRenderEngine::MakeRSSurface(const sptr<Surface>& targetSurface, bool forceCPU)
253 {
254 RS_TRACE_FUNC();
255 if (targetSurface == nullptr) {
256 RS_LOGE("RSBaseRenderEngine::MakeRSSurface: surface is null!");
257 RS_OPTIONAL_TRACE_END();
258 return nullptr;
259 }
260
261 std::shared_ptr<RSSurfaceOhos> rsSurface = nullptr;
262 #if (defined RS_ENABLE_GL) && (defined RS_ENABLE_EGLIMAGE)
263 if (RSSystemProperties::GetGpuApiType() == GpuApiType::OPENGL) {
264 if (forceCPU) {
265 rsSurface = std::make_shared<RSSurfaceOhosRaster>(targetSurface);
266 } else {
267 rsSurface = std::make_shared<RSSurfaceOhosGl>(targetSurface);
268 }
269 }
270 #endif
271 #if (defined RS_ENABLE_VK)
272 if (RSSystemProperties::IsUseVulkan()) {
273 rsSurface = std::make_shared<RSSurfaceOhosVulkan>(targetSurface);
274 }
275 #endif
276 if (rsSurface == nullptr) {
277 rsSurface = std::make_shared<RSSurfaceOhosRaster>(targetSurface);
278 }
279 return rsSurface;
280 }
281
SetUiTimeStamp(const std::unique_ptr<RSRenderFrame> & renderFrame,std::shared_ptr<RSSurfaceOhos> surfaceOhos)282 void RSBaseRenderEngine::SetUiTimeStamp(const std::unique_ptr<RSRenderFrame>& renderFrame,
283 std::shared_ptr<RSSurfaceOhos> surfaceOhos)
284 {
285 if (surfaceOhos == nullptr) {
286 RS_LOGE("RSBaseRenderEngine::SetUiTimeStamp: surfaceOhos is null!");
287 return;
288 }
289
290 if (renderFrame == nullptr) {
291 RS_LOGE("RSBaseRenderEngine::SetUiTimeStamp: renderFrame is null!.");
292 return;
293 }
294
295 auto& frame = renderFrame->GetFrame();
296 surfaceOhos->SetUiTimeStamp(frame);
297 }
298
DrawScreenNodeWithParams(RSPaintFilterCanvas & canvas,RSScreenRenderNode & node,BufferDrawParam & params)299 void RSBaseRenderEngine::DrawScreenNodeWithParams(RSPaintFilterCanvas& canvas, RSScreenRenderNode& node,
300 BufferDrawParam& params)
301 {
302 if (params.useCPU) {
303 DrawBuffer(canvas, params);
304 }
305 #ifdef RS_ENABLE_GPU
306 else {
307 auto drawable = node.GetRenderDrawable();
308 if (!drawable) {
309 return;
310 }
311 auto screenDrawable = std::static_pointer_cast<DrawableV2::RSScreenRenderNodeDrawable>(drawable);
312 RegisterDeleteBufferListener(screenDrawable->GetRSSurfaceHandlerOnDraw()->GetConsumer());
313 DrawImage(canvas, params);
314 }
315 #endif
316 }
317
DrawScreenNodeWithParams(RSPaintFilterCanvas & canvas,RSSurfaceHandler & surfaceHandler,BufferDrawParam & drawParam)318 void RSBaseRenderEngine::DrawScreenNodeWithParams(RSPaintFilterCanvas& canvas, RSSurfaceHandler& surfaceHandler,
319 BufferDrawParam& drawParam)
320 {
321 if (drawParam.useCPU) {
322 DrawBuffer(canvas, drawParam);
323 } else {
324 RegisterDeleteBufferListener(surfaceHandler.GetConsumer());
325 DrawImage(canvas, drawParam);
326 }
327 }
328
SetColorFilterMode(ColorFilterMode mode)329 void RSBaseRenderEngine::SetColorFilterMode(ColorFilterMode mode)
330 {
331 std::lock_guard<std::mutex> lock(colorFilterMutex_);
332 uint32_t uMode = static_cast<uint32_t>(mode);
333 uint32_t uInvertMode = static_cast<uint32_t>(ColorFilterMode::INVERT_COLOR_ENABLE_MODE);
334 uint32_t ucolorFilterMode = static_cast<uint32_t>(colorFilterMode_);
335 bool isInvertModeEnabled = ((ucolorFilterMode & uInvertMode) == uInvertMode);
336
337 switch (mode) {
338 case ColorFilterMode::INVERT_COLOR_DISABLE_MODE: {
339 if (colorFilterMode_ != ColorFilterMode::COLOR_FILTER_END) {
340 colorFilterMode_ = static_cast<ColorFilterMode>(ucolorFilterMode & ~uInvertMode);
341 }
342 break;
343 }
344 case ColorFilterMode::INVERT_COLOR_ENABLE_MODE: {
345 if (colorFilterMode_ != ColorFilterMode::COLOR_FILTER_END) {
346 colorFilterMode_ = static_cast<ColorFilterMode>(ucolorFilterMode | uInvertMode);
347 } else {
348 colorFilterMode_ = mode;
349 }
350 break;
351 }
352 case ColorFilterMode::DALTONIZATION_PROTANOMALY_MODE:
353 case ColorFilterMode::DALTONIZATION_DEUTERANOMALY_MODE:
354 case ColorFilterMode::DALTONIZATION_TRITANOMALY_MODE: {
355 if (isInvertModeEnabled) {
356 colorFilterMode_ = static_cast<ColorFilterMode>(uMode | uInvertMode);
357 } else {
358 colorFilterMode_ = mode;
359 }
360 break;
361 }
362 case ColorFilterMode::DALTONIZATION_NORMAL_MODE: {
363 if (isInvertModeEnabled) {
364 colorFilterMode_ = ColorFilterMode::INVERT_COLOR_ENABLE_MODE;
365 } else {
366 colorFilterMode_ = ColorFilterMode::COLOR_FILTER_END;
367 }
368 break;
369 }
370
371 // INVERT_DALTONIZATION_PROTANOMALY_MODE, INVERT_DALTONIZATION_DEUTERANOMALY_MODE
372 // INVERT_DALTONIZATION_TRITANOMALY_MODE and COLOR_FILTER_END can not be set directly
373 case ColorFilterMode::INVERT_DALTONIZATION_PROTANOMALY_MODE: // fall-through
374 case ColorFilterMode::INVERT_DALTONIZATION_DEUTERANOMALY_MODE: // fall-through
375 case ColorFilterMode::INVERT_DALTONIZATION_TRITANOMALY_MODE: // fall-through
376 case ColorFilterMode::COLOR_FILTER_END: // fall-through
377 default: {
378 colorFilterMode_ = ColorFilterMode::COLOR_FILTER_END;
379 break;
380 }
381 }
382 }
383
GetColorFilterMode()384 ColorFilterMode RSBaseRenderEngine::GetColorFilterMode()
385 {
386 std::lock_guard<std::mutex> lock(colorFilterMutex_);
387 return colorFilterMode_;
388 }
389
SetHighContrast(bool enabled)390 void RSBaseRenderEngine::SetHighContrast(bool enabled)
391 {
392 isHighContrastEnabled_ = enabled;
393 }
394
IsHighContrastEnabled()395 bool RSBaseRenderEngine::IsHighContrastEnabled()
396 {
397 return isHighContrastEnabled_;
398 }
399
DrawBuffer(RSPaintFilterCanvas & canvas,BufferDrawParam & params)400 void RSBaseRenderEngine::DrawBuffer(RSPaintFilterCanvas& canvas, BufferDrawParam& params)
401 {
402 RS_TRACE_NAME("RSBaseRenderEngine::DrawBuffer(CPU)");
403 Drawing::Bitmap bitmap;
404 std::vector<uint8_t> newBuffer;
405 if (!RSBaseRenderUtil::ConvertBufferToBitmap(params.buffer, newBuffer, params.targetColorGamut, bitmap,
406 params.metaDatas)) {
407 RS_LOGE("RSDividedRenderUtil::DrawBuffer: create bitmap failed.");
408 return;
409 }
410 Drawing::Image drImage;
411 drImage.BuildFromBitmap(bitmap);
412 canvas.DrawImageRect(drImage, params.srcRect, params.dstRect, Drawing::SamplingOptions(),
413 Drawing::SrcRectConstraint::STRICT_SRC_RECT_CONSTRAINT);
414 }
415
GetCanvasColorSpace(const RSPaintFilterCanvas & canvas)416 std::shared_ptr<Drawing::ColorSpace> RSBaseRenderEngine::GetCanvasColorSpace(const RSPaintFilterCanvas& canvas)
417 {
418 auto surface = canvas.GetSurface();
419 if (surface == nullptr) {
420 return nullptr;
421 }
422
423 return surface->GetImageInfo().GetColorSpace();
424 }
425
426 #ifdef USE_VIDEO_PROCESSING_ENGINE
ConvertDrawingColorSpaceToSpaceInfo(const std::shared_ptr<Drawing::ColorSpace> & colorSpace,HDI::Display::Graphic::Common::V1_0::CM_ColorSpaceInfo & colorSpaceInfo)427 bool RSBaseRenderEngine::ConvertDrawingColorSpaceToSpaceInfo(const std::shared_ptr<Drawing::ColorSpace>& colorSpace,
428 HDI::Display::Graphic::Common::V1_0::CM_ColorSpaceInfo& colorSpaceInfo)
429 {
430 using namespace HDI::Display::Graphic::Common::V1_0;
431 CM_ColorSpaceType colorSpaceType = CM_COLORSPACE_NONE;
432 if (colorSpace == nullptr || colorSpace->Equals(nullptr) || colorSpace->IsSRGB()) {
433 colorSpaceType = CM_SRGB_FULL;
434 } else if (colorSpace->Equals(Drawing::ColorSpace::CreateRGB(
435 Drawing::CMSTransferFuncType::SRGB, Drawing::CMSMatrixType::DCIP3))) {
436 colorSpaceType = CM_P3_FULL;
437 } else if (colorSpace->Equals(Drawing::ColorSpace::CreateRGB(
438 Drawing::CMSTransferFuncType::SRGB, Drawing::CMSMatrixType::ADOBE_RGB))) {
439 colorSpaceType = CM_ADOBERGB_FULL;
440 } else if (colorSpace->Equals(Drawing::ColorSpace::CreateRGB(
441 Drawing::CMSTransferFuncType::SRGB, Drawing::CMSMatrixType::REC2020))) {
442 colorSpaceType = CM_DISPLAY_BT2020_SRGB;
443 } else {
444 RS_LOGD("RSBaseRenderEngine::ConvertDrawingColorSpaceToSpaceInfo color space not supported");
445 return false;
446 }
447
448 GSError ret = MetadataHelper::ConvertColorSpaceTypeToInfo(colorSpaceType, colorSpaceInfo);
449 if (ret != GSERROR_OK) {
450 RS_LOGE("RSBaseRenderEngine::ConvertDrawingColorSpaceToSpaceInfo ConvertColorSpaceTypeToInfo failed with \
451 %{public}u.", ret);
452 return false;
453 }
454
455 return true;
456 }
457
SetColorSpaceConverterDisplayParameter(const BufferDrawParam & params,Media::VideoProcessingEngine::ColorSpaceConverterDisplayParameter & parameter)458 bool RSBaseRenderEngine::SetColorSpaceConverterDisplayParameter(
459 const BufferDrawParam& params, Media::VideoProcessingEngine::ColorSpaceConverterDisplayParameter& parameter)
460 {
461 using namespace HDI::Display::Graphic::Common::V1_0;
462
463 CM_HDR_Metadata_Type hdrMetadataType = CM_METADATA_NONE;
464 GSError ret = MetadataHelper::GetHDRMetadataType(params.buffer, hdrMetadataType);
465 if (ret != GSERROR_OK) {
466 RS_LOGD("RSBaseRenderEngine::ColorSpaceConvertor GetHDRMetadataType failed with %{public}u.", ret);
467 }
468
469 parameter.inputColorSpace.metadataType = hdrMetadataType;
470 parameter.outputColorSpace.metadataType = hdrMetadataType;
471
472 #ifdef USE_VIDEO_PROCESSING_ENGINE
473 RSColorSpaceConvert::Instance().GetHDRStaticMetadata(params.buffer, parameter.staticMetadata, ret);
474 RSColorSpaceConvert::Instance().GetHDRDynamicMetadata(params.buffer, parameter.dynamicMetadata, ret);
475 RSColorSpaceConvert::Instance().GetFOVMetadata(params.buffer, parameter.adaptiveFOVMetadata);
476 #endif
477
478 parameter.width = params.buffer->GetWidth();
479 parameter.height = params.buffer->GetHeight();
480 parameter.tmoNits = params.tmoNits;
481 parameter.currentDisplayNits = params.displayNits;
482 parameter.sdrNits = params.sdrNits;
483 // color temperature
484 parameter.layerLinearMatrix = params.layerLinearMatrix;
485
486 RS_LOGD("RSBaseRenderEngine::ColorSpaceConvertor parameter inPrimaries = %{public}u, inMetadataType = %{public}u, "
487 "outPrimaries = %{public}u, outMetadataType = %{public}u, "
488 "tmoNits = %{public}.2f, currentDisplayNits = %{public}.2f, sdrNits = %{public}.2f",
489 parameter.inputColorSpace.colorSpaceInfo.primaries, parameter.inputColorSpace.metadataType,
490 parameter.outputColorSpace.colorSpaceInfo.primaries, parameter.outputColorSpace.metadataType,
491 parameter.tmoNits, parameter.currentDisplayNits, parameter.sdrNits);
492
493 return true;
494 }
495
ColorSpaceConvertor(std::shared_ptr<Drawing::ShaderEffect> & inputShader,BufferDrawParam & params,Media::VideoProcessingEngine::ColorSpaceConverterDisplayParameter & parameter,const RSPaintFilterCanvas::HDRProperties & hdrProperties)496 void RSBaseRenderEngine::ColorSpaceConvertor(std::shared_ptr<Drawing::ShaderEffect>& inputShader,
497 BufferDrawParam& params, Media::VideoProcessingEngine::ColorSpaceConverterDisplayParameter& parameter,
498 const RSPaintFilterCanvas::HDRProperties& hdrProperties)
499 {
500 RS_OPTIONAL_TRACE_BEGIN("RSBaseRenderEngine::ColorSpaceConvertor");
501
502 if (!SetColorSpaceConverterDisplayParameter(params, parameter)) {
503 RS_OPTIONAL_TRACE_END();
504 return;
505 }
506
507 if(!inputShader) {
508 RS_LOGE("RSBaseRenderEngine::ColorSpaceConvertor inputShader is null");
509 RS_OPTIONAL_TRACE_END();
510 return;
511 }
512 if (params.isHdrRedraw) {
513 parameter.disableHdrFloatHeadRoom = true;
514 } else if (params.isTmoNitsFixed) {
515 parameter.sdrNits = DEFAULT_DISPLAY_NIT;
516 parameter.tmoNits = hdrProperties.screenshotType == RSPaintFilterCanvas::ScreenshotType::HDR_SCREENSHOT ?
517 RSLuminanceConst::DEFAULT_CAPTURE_HDR_NITS : DEFAULT_DISPLAY_NIT;
518 parameter.currentDisplayNits = DEFAULT_DISPLAY_NIT;
519 parameter.layerLinearMatrix = {1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f};
520 } else if (hdrProperties.isHDREnabledVirtualScreen) {
521 parameter.sdrNits = RSLuminanceConst::DEFAULT_CAST_SDR_NITS;
522 parameter.currentDisplayNits = RSLuminanceConst::DEFAULT_CAST_HDR_NITS;
523 parameter.tmoNits = RSLuminanceConst::DEFAULT_CAST_HDR_NITS;
524 parameter.layerLinearMatrix = {1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f};
525 }
526
527 std::shared_ptr<Drawing::ShaderEffect> outputShader;
528 auto convRet = colorSpaceConverterDisplay_->Process(inputShader, outputShader, parameter);
529 if (convRet != Media::VideoProcessingEngine::VPE_ALGO_ERR_OK) {
530 RS_LOGE("RSBaseRenderEngine::ColorSpaceConvertor colorSpaceConverterDisplay failed with %{public}u.", convRet);
531 RS_OPTIONAL_TRACE_END();
532 return;
533 }
534 if (outputShader == nullptr) {
535 RS_LOGE("RSBaseRenderEngine::ColorSpaceConvertor outputShader is nullptr.");
536 RS_OPTIONAL_TRACE_END();
537 return;
538 }
539 params.paint.SetShaderEffect(outputShader);
540 RS_OPTIONAL_TRACE_END();
541 }
542 #endif
543
ConvertColorGamutToDrawingColorSpace(GraphicColorGamut colorGamut)544 std::shared_ptr<Drawing::ColorSpace> RSBaseRenderEngine::ConvertColorGamutToDrawingColorSpace(
545 GraphicColorGamut colorGamut)
546 {
547 std::shared_ptr<Drawing::ColorSpace> colorSpace = nullptr;
548 switch (colorGamut) {
549 case GRAPHIC_COLOR_GAMUT_DISPLAY_P3:
550 case GRAPHIC_COLOR_GAMUT_DCI_P3:
551 colorSpace = Drawing::ColorSpace::CreateRGB(
552 Drawing::CMSTransferFuncType::SRGB, Drawing::CMSMatrixType::DCIP3);
553 break;
554 case GRAPHIC_COLOR_GAMUT_ADOBE_RGB:
555 colorSpace = Drawing::ColorSpace::CreateRGB(
556 Drawing::CMSTransferFuncType::SRGB, Drawing::CMSMatrixType::ADOBE_RGB);
557 break;
558 case GRAPHIC_COLOR_GAMUT_BT2020:
559 colorSpace = Drawing::ColorSpace::CreateRGB(
560 Drawing::CMSTransferFuncType::SRGB, Drawing::CMSMatrixType::REC2020);
561 break;
562 default:
563 colorSpace = Drawing::ColorSpace::CreateSRGB();
564 break;
565 }
566
567 return colorSpace;
568 }
569
ConvertColorSpaceNameToDrawingColorSpace(OHOS::ColorManager::ColorSpaceName colorSpaceName)570 std::shared_ptr<Drawing::ColorSpace> RSBaseRenderEngine::ConvertColorSpaceNameToDrawingColorSpace(
571 OHOS::ColorManager::ColorSpaceName colorSpaceName)
572 {
573 std::shared_ptr<Drawing::ColorSpace> colorSpace = nullptr;
574 switch (colorSpaceName) {
575 case OHOS::ColorManager::ColorSpaceName::DISPLAY_P3:
576 case OHOS::ColorManager::ColorSpaceName::DCI_P3:
577 colorSpace = Drawing::ColorSpace::CreateRGB(
578 Drawing::CMSTransferFuncType::SRGB, Drawing::CMSMatrixType::DCIP3);
579 break;
580 case OHOS::ColorManager::ColorSpaceName::ADOBE_RGB:
581 colorSpace = Drawing::ColorSpace::CreateRGB(
582 Drawing::CMSTransferFuncType::SRGB, Drawing::CMSMatrixType::ADOBE_RGB);
583 break;
584 default:
585 colorSpace = Drawing::ColorSpace::CreateSRGB();
586 break;
587 }
588 return colorSpace;
589 }
590
DumpVkImageInfo(std::string & dumpString)591 void RSBaseRenderEngine::DumpVkImageInfo(std::string &dumpString)
592 {
593 if (imageManager_ != nullptr) {
594 imageManager_->DumpVkImageInfo(dumpString);
595 }
596 }
597
CreateImageFromBuffer(RSPaintFilterCanvas & canvas,BufferDrawParam & params,VideoInfo & videoInfo)598 std::shared_ptr<Drawing::Image> RSBaseRenderEngine::CreateImageFromBuffer(RSPaintFilterCanvas& canvas,
599 BufferDrawParam& params, VideoInfo& videoInfo)
600 {
601 std::shared_ptr<Drawing::AutoCanvasRestore> acr = nullptr;
602 if (params.preRotation) {
603 RS_LOGD_IF(DEBUG_COMPOSER, " - Applying pre-rotation, resetting canvas matrix");
604 acr = std::make_shared<Drawing::AutoCanvasRestore>(canvas, true);
605 canvas.ResetMatrix();
606 }
607
608 std::shared_ptr<Drawing::Image> image;
609 if (!RSBaseRenderUtil::IsBufferValid(params.buffer)) {
610 RS_LOGE("RSBaseRenderEngine::CreateImageFromBuffer invalid buffer!");
611 return nullptr;
612 }
613 RS_LOGD_IF(DEBUG_COMPOSER,
614 " - Buffer info: width=%{public}u, height=%{public}u, format=%{public}d, seqNum=%{public}u",
615 params.buffer->GetWidth(), params.buffer->GetHeight(),
616 params.buffer->GetFormat(), params.buffer->GetSeqNum());
617 videoInfo.drawingColorSpace_ = Drawing::ColorSpace::CreateSRGB();
618 #ifdef USE_VIDEO_PROCESSING_ENGINE
619 videoInfo.parameter_ = {};
620 videoInfo.retGetColorSpaceInfo_ = MetadataHelper::GetColorSpaceInfo(params.buffer,
621 videoInfo.parameter_.inputColorSpace.colorSpaceInfo);
622 if (videoInfo.retGetColorSpaceInfo_ == GSERROR_OK || params.colorFollow) {
623 videoInfo.drawingColorSpace_ = GetCanvasColorSpace(canvas);
624 }
625 #endif
626 #if defined(RS_ENABLE_VK) || defined(RS_ENABLE_GL)
627 if (imageManager_ == nullptr) {
628 RS_LOGE("RSBaseRenderEngine::CreateImageFromBuffer: imageManager is nullptr!");
629 return nullptr;
630 }
631 image = imageManager_->CreateImageFromBuffer(canvas, params, videoInfo.drawingColorSpace_);
632 if (image == nullptr) {
633 RS_LOGE("RSBaseRenderEngine::CreateImageFromBuffer: vk image is nullptr!");
634 return nullptr;
635 }
636 #endif
637 RS_LOGD_IF(DEBUG_COMPOSER,
638 "RSBaseRenderEngine::CreateImageFromBuffer: Image creation successful, size: %{public}d x %{public}d",
639 image->GetWidth(), image->GetHeight());
640 return image;
641 }
642
DrawImage(RSPaintFilterCanvas & canvas,BufferDrawParam & params)643 void RSBaseRenderEngine::DrawImage(RSPaintFilterCanvas& canvas, BufferDrawParam& params)
644 {
645 RS_TRACE_NAME_FMT("RSBaseRenderEngine::DrawImage(GPU) targetColorGamut=%d", params.targetColorGamut);
646
647 RS_LOGD_IF(DEBUG_COMPOSER, "RSBaseRenderEngine::DrawImage: Starting to draw image with gamut:%{public}d, "
648 "src:[%{public}.2f,%{public}.2f,%{public}.2f,%{public}.2f],"
649 "dst:[%{public}.2f,%{public}.2f,%{public}.2f,%{public}.2f], "
650 "useCPU:%{public}d, isMirror:%{public}d, useBilinear:%{public}d",
651 params.targetColorGamut, params.srcRect.GetLeft(), params.srcRect.GetTop(), params.srcRect.GetRight(),
652 params.srcRect.GetBottom(), params.dstRect.GetLeft(), params.dstRect.GetTop(), params.dstRect.GetRight(),
653 params.dstRect.GetBottom(), params.useCPU, params.isMirror, params.useBilinearInterpolation);
654 #ifdef USE_VIDEO_PROCESSING_ENGINE
655 RS_LOGD_IF(DEBUG_COMPOSER, " - Video processing: brightness:%{public}.2f, hasMetadata:%{public}d",
656 params.brightnessRatio, params.hasMetadata);
657 #endif
658
659 RSMainThread::GPUCompositonCacheGuard guard;
660 VideoInfo videoInfo;
661 auto image = CreateImageFromBuffer(canvas, params, videoInfo);
662 if (image == nullptr) {
663 return;
664 }
665
666 Drawing::SamplingOptions samplingOptions;
667 if (!RSSystemProperties::GetUniRenderEnabled()) {
668 samplingOptions = Drawing::SamplingOptions();
669 RS_LOGD_IF(DEBUG_COMPOSER, " - Sampling options: Default sampling options (UniRender not enabled)");
670 } else {
671 if (params.isMirror) {
672 samplingOptions = Drawing::SamplingOptions(Drawing::FilterMode::LINEAR, Drawing::MipmapMode::NEAREST);
673 RS_LOGD_IF(DEBUG_COMPOSER, " - Sampling options: Mirror mode (LINEAR, NEAREST)");
674 } else {
675 bool needBilinear = NeedBilinearInterpolation(params, canvas.GetTotalMatrix());
676 samplingOptions =
677 needBilinear ? Drawing::SamplingOptions(Drawing::FilterMode::LINEAR, Drawing::MipmapMode::NONE) :
678 Drawing::SamplingOptions();
679 RS_LOGD_IF(DEBUG_COMPOSER, " - Sampling options: %{public}s",
680 needBilinear ? "Bilinear interpolation (LINEAR, NONE)" : "Default sampling options");
681 }
682 }
683
684 {
685 // Record canvas transformation matrix information
686 auto matrix = canvas.GetTotalMatrix();
687 RS_LOGD_IF(DEBUG_COMPOSER, " - Canvas transformation matrix:"
688 "[%{public}.2f, %{public}.2f, %{public}.2f, %{public}.2f, %{public}.2f, %{public}.2f]",
689 matrix.Get(Drawing::Matrix::SCALE_X), matrix.Get(Drawing::Matrix::SKEW_X),
690 matrix.Get(Drawing::Matrix::TRANS_X), matrix.Get(Drawing::Matrix::SKEW_Y),
691 matrix.Get(Drawing::Matrix::SCALE_Y), matrix.Get(Drawing::Matrix::TRANS_Y));
692 }
693
694 if (params.targetColorGamut == GRAPHIC_COLOR_GAMUT_SRGB) {
695 RS_LOGD_IF(DEBUG_COMPOSER, " - Using SRGB color gamut for drawing");
696 canvas.AttachBrush(params.paint);
697 canvas.DrawImageRect(*image, params.srcRect, params.dstRect, samplingOptions,
698 Drawing::SrcRectConstraint::FAST_SRC_RECT_CONSTRAINT);
699 canvas.DetachBrush();
700 RS_LOGD_IF(DEBUG_COMPOSER, "RSBaseRenderEngine::DrawImage: SRGB color gamut drawing completed");
701 } else {
702 #ifdef USE_VIDEO_PROCESSING_ENGINE
703
704 if (params.isHeterog) {
705 RS_LOGD("hdr video comin heterog");
706 float hrRatio = std::pow((params.displayNits / params.sdrNits), DEGAMMA);
707 Drawing::Matrix scaleMat;
708 auto imageShader = Drawing::ShaderEffect::CreateImageShader(*image, Drawing::TileMode::CLAMP,
709 Drawing::TileMode::CLAMP, Drawing::SamplingOptions(Drawing::FilterMode::LINEAR), scaleMat);
710
711 RSHdrUtil util;
712 auto shader = util.MakeHdrHeadroomShader(hrRatio, imageShader);
713 if (shader == nullptr) {
714 RS_LOGE("RSHdrUtil::MakeHdrHeadroomShader shader is null");
715 return;
716 }
717 params.paint.SetShaderEffect(shader);
718
719 canvas.AttachBrush(params.paint);
720 canvas.DrawRect(params.dstRect);
721 canvas.DetachBrush();
722 return;
723 }
724
725 // For sdr brightness ratio
726 if (ROSEN_LNE(params.brightnessRatio, DEFAULT_BRIGHTNESS_RATIO) && !params.isHdrRedraw) {
727 RS_LOGD_IF(DEBUG_COMPOSER, " - Applying brightness ratio: %{public}.2f", params.brightnessRatio);
728 Drawing::Filter filter = params.paint.GetFilter();
729 Drawing::ColorMatrix luminanceMatrix;
730 luminanceMatrix.SetScale(params.brightnessRatio, params.brightnessRatio, params.brightnessRatio, 1.0f);
731 auto luminanceColorFilter =
732 std::make_shared<Drawing::ColorFilter>(Drawing::ColorFilter::FilterType::MATRIX, luminanceMatrix);
733 filter.SetColorFilter(luminanceColorFilter);
734 params.paint.SetFilter(filter);
735 }
736
737 if (videoInfo.retGetColorSpaceInfo_ != GSERROR_OK) {
738 RS_LOGD("RSBaseRenderEngine::DrawImage GetColorSpaceInfo failed with %{public}u.",
739 videoInfo.retGetColorSpaceInfo_);
740 DrawImageRect(canvas, image, params, samplingOptions);
741 return;
742 }
743
744 auto& inClrInfo = videoInfo.parameter_.inputColorSpace.colorSpaceInfo;
745 auto& outClrInfo = videoInfo.parameter_.outputColorSpace.colorSpaceInfo;
746 RS_LOGD_IF(DEBUG_COMPOSER, " - Input color space: primaries=%{public}d, transfunc=%{public}d",
747 inClrInfo.primaries, inClrInfo.transfunc);
748 if (!ConvertDrawingColorSpaceToSpaceInfo(videoInfo.drawingColorSpace_, outClrInfo)) {
749 RS_LOGD("RSBaseRenderEngine::DrawImage ConvertDrawingColorSpaceToSpaceInfo failed");
750 DrawImageRect(canvas, image, params, samplingOptions);
751 return;
752 }
753
754 if (params.colorFollow) {
755 // force input and output color spaces to be consistent to avoid color space conversion
756 RS_LOGD("RSBaseRenderEngine::DrawImage force to avoid color space conversion");
757 DrawImageRect(canvas, image, params, samplingOptions);
758 return;
759 }
760
761 if (inClrInfo.primaries == outClrInfo.primaries && inClrInfo.transfunc == outClrInfo.transfunc &&
762 !params.hasMetadata) {
763 RS_LOGD("RSBaseRenderEngine::DrawImage primaries and transfunc equal with no metadata.");
764 DrawImageRect(canvas, image, params, samplingOptions);
765 return;
766 }
767
768 auto& rsLuminance = RSLuminanceControl::Get();
769 // Fix tonemapping: all xxxNits reset to 500, layerLinearMatrix reset to 3x3 Identity matrix
770 params.isTmoNitsFixed = canvas.IsOnMultipleScreen() ||
771 (!canvas.GetHdrOn() &&
772 !params.hasMetadata &&
773 !rsLuminance.IsScreenNoHeadroom(canvas.GetScreenId())) ||
774 !RSSystemProperties::GetHdrVideoEnabled();
775 auto shotType = canvas.GetScreenshotType();
776 if (shotType == RSPaintFilterCanvas::ScreenshotType::HDR_WINDOWSHOT) {
777 params.isTmoNitsFixed = false;
778 }
779 RS_LOGD_IF(DEBUG_COMPOSER, "- Fix tonemapping: %{public}d", params.isTmoNitsFixed);
780
781 Drawing::Matrix matrix;
782 auto srcWidth = params.srcRect.GetWidth();
783 auto srcHeight = params.srcRect.GetHeight();
784 auto sx = params.dstRect.GetWidth() / srcWidth;
785 auto sy = params.dstRect.GetHeight() / srcHeight;
786 auto tx = params.dstRect.GetLeft() - params.srcRect.GetLeft() * sx;
787 auto ty = params.dstRect.GetTop() - params.srcRect.GetTop() * sy;
788 if (ROSEN_EQ(srcWidth, 0.0f) || ROSEN_EQ(srcHeight, 0.0f)) {
789 RS_LOGE("RSBaseRenderEngine::DrawImage image srcRect params invalid.");
790 }
791 matrix.SetScaleTranslate(sx, sy, tx, ty);
792
793 RS_LOGD_IF(DEBUG_COMPOSER, " - Image shader transformation:"
794 "sx=%{public}.2f, sy=%{public}.2f, tx=%{public}.2f, ty=%{public}.2f", sx, sy, tx, ty);
795
796 auto imageShader = Drawing::ShaderEffect::CreateImageShader(
797 *image, Drawing::TileMode::CLAMP, Drawing::TileMode::CLAMP, samplingOptions, matrix);
798 if (imageShader == nullptr) {
799 RS_LOGW("RSBaseRenderEngine::DrawImage imageShader is nullptr.");
800 } else {
801 params.paint.SetShaderEffect(imageShader);
802 ColorSpaceConvertor(imageShader, params, videoInfo.parameter_, canvas.GetHDRProperties());
803 }
804 canvas.AttachBrush(params.paint);
805 canvas.DrawRect(params.dstRect);
806 canvas.DetachBrush();
807 #else
808 DrawImageRect(canvas, image, params, samplingOptions);
809 #endif // USE_VIDEO_PROCESSING_ENGINE
810 }
811 }
812
DrawImageRect(RSPaintFilterCanvas & canvas,std::shared_ptr<Drawing::Image> image,BufferDrawParam & params,Drawing::SamplingOptions & samplingOptions)813 void RSBaseRenderEngine::DrawImageRect(RSPaintFilterCanvas& canvas, std::shared_ptr<Drawing::Image> image,
814 BufferDrawParam& params, Drawing::SamplingOptions& samplingOptions)
815 {
816 RS_LOGD_IF(DEBUG_COMPOSER, "RSBaseRenderEngine::DrawImageRect: rect image src:[%{public}.2f,%{public}.2f,"
817 "%{public}.2f,%{public}.2f], dst:[%{public}.2f,%{public}.2f,%{public}.2f,%{public}.2f]",
818 params.srcRect.GetLeft(), params.srcRect.GetTop(), params.srcRect.GetRight(), params.srcRect.GetBottom(),
819 params.dstRect.GetLeft(), params.dstRect.GetTop(), params.dstRect.GetRight(), params.dstRect.GetBottom());
820 // Record sampling options information
821 RS_LOGD_IF(DEBUG_COMPOSER,
822 " - Sampling filter mode: %{public}d, Sampling mipmap mode: %{public}d",
823 static_cast<int>(samplingOptions.GetFilterMode()), static_cast<int>(samplingOptions.GetMipmapMode()));
824
825 canvas.AttachBrush(params.paint);
826 canvas.DrawImageRect(*image, params.srcRect, params.dstRect, samplingOptions,
827 Drawing::SrcRectConstraint::FAST_SRC_RECT_CONSTRAINT);
828 canvas.DetachBrush();
829 }
830
NeedBilinearInterpolation(const BufferDrawParam & params,const Drawing::Matrix & matrix)831 bool RSBaseRenderEngine::NeedBilinearInterpolation(const BufferDrawParam& params, const Drawing::Matrix& matrix)
832 {
833 if (!params.useBilinearInterpolation) {
834 return false;
835 }
836 if (!ROSEN_EQ(params.dstRect.GetWidth(), params.srcRect.GetWidth()) ||
837 !ROSEN_EQ(params.dstRect.GetHeight(), params.srcRect.GetHeight())) {
838 return true;
839 }
840 auto scaleX = matrix.Get(Drawing::Matrix::SCALE_X);
841 auto scaleY = matrix.Get(Drawing::Matrix::SCALE_Y);
842 auto skewX = matrix.Get(Drawing::Matrix::SKEW_X);
843 auto skewY = matrix.Get(Drawing::Matrix::SKEW_Y);
844 if (ROSEN_EQ(skewX, 0.0f) && ROSEN_EQ(skewY, 0.0f)) {
845 if (!ROSEN_EQ(std::abs(scaleX), 1.0f) || !ROSEN_EQ(std::abs(scaleY), 1.0f)) {
846 // has scale
847 return true;
848 }
849 } else if (ROSEN_EQ(scaleX, 0.0f) && ROSEN_EQ(scaleY, 0.0f)) {
850 if (!ROSEN_EQ(std::abs(skewX), 1.0f) || !ROSEN_EQ(std::abs(skewY), 1.0f)) {
851 // has scale
852 return true;
853 }
854 } else {
855 // skew and/or non 90 degrees rotation
856 return true;
857 }
858 return false;
859 }
860
RegisterDeleteBufferListener(const sptr<IConsumerSurface> & consumer,bool isForUniRedraw)861 void RSBaseRenderEngine::RegisterDeleteBufferListener(const sptr<IConsumerSurface>& consumer, bool isForUniRedraw)
862 {
863 #ifdef RS_ENABLE_VK
864 if (RSSystemProperties::IsUseVulkan()) {
865 auto regUnMapVkImageFunc = [this, isForUniRedraw](int32_t bufferId) {
866 RSMainThread::Instance()->AddToUnmappedCacheSet(bufferId);
867 };
868 if (consumer == nullptr ||
869 (consumer->RegisterDeleteBufferListener(regUnMapVkImageFunc, isForUniRedraw) != GSERROR_OK)) {
870 RS_LOGE("RSBaseRenderEngine::RegisterDeleteBufferListener: failed to register UnMapVkImage callback.");
871 }
872 return;
873 }
874 #endif // #ifdef RS_ENABLE_VK
875
876 #if (defined(RS_ENABLE_EGLIMAGE) && defined(RS_ENABLE_GPU))
877 auto regUnMapEglImageFunc = [this, isForUniRedraw](int32_t bufferId) {
878 RSMainThread::Instance()->AddToUnmappedCacheSet(bufferId);
879 };
880 if (consumer == nullptr ||
881 (consumer->RegisterDeleteBufferListener(regUnMapEglImageFunc, isForUniRedraw) != GSERROR_OK)) {
882 RS_LOGE("RSBaseRenderEngine::RegisterDeleteBufferListener: failed to register UnMapEglImage callback.");
883 }
884 #endif // #ifdef RS_ENABLE_EGLIMAGE
885 }
886
RegisterDeleteBufferListener(RSSurfaceHandler & handler)887 void RSBaseRenderEngine::RegisterDeleteBufferListener(RSSurfaceHandler& handler)
888 {
889 #ifdef RS_ENABLE_VK
890 if (RSSystemProperties::IsUseVulkan()) {
891 auto regUnMapVkImageFunc = [this](int32_t bufferId) {
892 RSMainThread::Instance()->AddToUnmappedCacheSet(bufferId);
893 };
894 handler.RegisterDeleteBufferListener(regUnMapVkImageFunc);
895 return;
896 }
897 #endif // #ifdef RS_ENABLE_VK
898
899 #if (defined(RS_ENABLE_EGLIMAGE) && defined(RS_ENABLE_GPU))
900 auto regUnMapEglImageFunc = [this](int32_t bufferId) {
901 RSMainThread::Instance()->AddToUnmappedCacheSet(bufferId);
902 };
903 handler.RegisterDeleteBufferListener(regUnMapEglImageFunc);
904 #endif // #ifdef RS_ENABLE_EGLIMAGE
905 }
906
ShrinkCachesIfNeeded(bool isForUniRedraw)907 void RSBaseRenderEngine::ShrinkCachesIfNeeded(bool isForUniRedraw)
908 {
909 #if (defined(RS_ENABLE_EGLIMAGE) && defined(RS_ENABLE_GPU))
910 if (imageManager_ != nullptr) {
911 imageManager_->ShrinkCachesIfNeeded(isForUniRedraw);
912 }
913 #endif // RS_ENABLE_EGLIMAGE
914 }
915
ClearCacheSet(const std::set<uint32_t> & unmappedCache)916 void RSBaseRenderEngine::ClearCacheSet(const std::set<uint32_t>& unmappedCache)
917 {
918 if (imageManager_ != nullptr) {
919 for (auto id : unmappedCache) {
920 imageManager_->UnMapImageFromSurfaceBuffer(id);
921 }
922 }
923 }
924 } // namespace Rosen
925 } // namespace OHOS
926