!16087 UIFirst子线程灭屏下的绘制管控

Merge pull request !16087 from sunqizhen/master
This commit is contained in:
openharmony_ci 2024-10-21 02:31:26 +00:00 committed by Gitee
commit e84f8141e7
No known key found for this signature in database
GPG Key ID: 173E9B9CA92EEF8F
7 changed files with 94 additions and 106 deletions

View File

@ -519,8 +519,8 @@ void RSDisplayRenderNodeDrawable::OnDraw(Drawing::Canvas& canvas)
drawable->GetRenderParams()->SetLayerCreated(false);
}
// if screen power off, skip on draw
if (SkipDisplayIfScreenOff()) {
// if screen power off, skip on draw, needs to draw one more frame.
if (params && RSUniRenderUtil::CheckRenderSkipIfScreenOff(true, params->GetScreenId())) {
return;
}
@ -1628,35 +1628,6 @@ void RSDisplayRenderNodeDrawable::FinishOffscreenRender(const Drawing::SamplingO
curCanvas_ = std::move(canvasBackup_);
}
bool RSDisplayRenderNodeDrawable::SkipDisplayIfScreenOff() const
{
// renderParams_ not null in caller
if (!RSSystemProperties::GetSkipDisplayIfScreenOffEnabled() || !RSSystemProperties::IsPhoneType()) {
return false;
}
auto screenManager = CreateOrGetScreenManager();
if (!screenManager) {
RS_LOGE("RSDisplayRenderNodeDrawable::SkipRenderFrameIfScreenOff, failed to get screen manager!");
return false;
}
// in certain cases such as wireless display, render skipping may be disabled.
ScreenId id = renderParams_->GetScreenId();
auto disableRenderControlScreensCount = screenManager->GetDisableRenderControlScreensCount();
auto isScreenOff = screenManager->IsScreenPowerOff(id);
RS_TRACE_NAME_FMT("RSDisplayRenderNodeDrawable Screen_[%" PRIu64 "] disableRenderControl:[%d], PowerOff:[%d]",
id, disableRenderControlScreensCount, isScreenOff);
if (disableRenderControlScreensCount != 0 || !isScreenOff) {
return false;
}
if (screenManager->GetPowerOffNeedProcessOneFrame()) {
RS_LOGI("RSDisplayRenderNodeDrawable::SkipRenderFrameIfScreenOff screen_%{public}" PRIu64
" power off, one more frame.", id);
screenManager->ResetPowerOffNeedProcessOneFrame();
return false;
}
return true;
}
#ifndef ROSEN_CROSS_PLATFORM
bool RSDisplayRenderNodeDrawable::CreateSurface(sptr<IBufferConsumerListener> listener)
{

View File

@ -154,7 +154,6 @@ private:
void FinishOffscreenRender(const Drawing::SamplingOptions& sampling, float hdrBrightnessRatio = 1.0f);
void PrepareHdrDraw(int32_t offscreenWidth, int32_t offscreenHeight);
void FinishHdrDraw(Drawing::Brush& paint, float hdrBrightnessRatio);
bool SkipDisplayIfScreenOff() const;
int32_t GetSpecialLayerType(RSDisplayRenderParams& params);
void SetDisplayNodeSkipFlag(RSRenderThreadParams& uniParam, bool flag);
void UpdateDisplayDirtyManager(int32_t bufferage, bool useAlignedDirtyRegion = false);

View File

@ -862,6 +862,10 @@ void RSUifirstManager::SortSubThreadNodesPriority()
// post in drawframe sync time
void RSUifirstManager::PostUifistSubTasks()
{
// if screen is power-off, uifirst sub thread can be suspended.
if (RSUniRenderUtil::CheckRenderSkipIfScreenOff()) {
return;
}
PurgePendingPostNodes();
SortSubThreadNodesPriority();
if (sortedSubThreadNodeIds_.size() > 0) {

View File

@ -1959,5 +1959,33 @@ std::optional<Drawing::Matrix> RSUniRenderUtil::GetMatrix(
}
return relativeMat;
}
bool RSUniRenderUtil::CheckRenderSkipIfScreenOff(bool extraFrame, std::optional<ScreenId> screenId)
{
if (!RSSystemProperties::GetSkipDisplayIfScreenOffEnabled() || RSSystemProperties::IsPcType()) {
return false;
}
auto screenManager = CreateOrGetScreenManager();
if (!screenManager) {
RS_LOGE("RSUniRenderUtil::CheckRenderSkipIfScreenOff, failed to get screen manager!");
return false;
}
// in certain cases such as wireless display, render skipping may be disabled.
auto disableRenderControlScreensCount = screenManager->GetDisableRenderControlScreensCount();
auto isScreenOff = screenId.has_value() ?
screenManager->IsScreenPowerOff(screenId.value()) : screenManager->IsAllScreensPowerOff();
RS_TRACE_NAME_FMT("CheckRenderSkipIfScreenOff disableRenderControl:[%d], PowerOff:[%d]",
disableRenderControlScreensCount, isScreenOff);
if (disableRenderControlScreensCount != 0 || !isScreenOff) {
return false;
}
if (extraFrame && screenManager->GetPowerOffNeedProcessOneFrame()) {
RS_LOGI("RSUniRenderUtil::CheckRenderSkipIfScreenOff screen power off, one more frame.");
screenManager->ResetPowerOffNeedProcessOneFrame();
return false;
} else {
return !screenManager->GetPowerOffNeedProcessOneFrame();
}
}
} // namespace Rosen
} // namespace OHOS

View File

@ -148,6 +148,9 @@ public:
}
}
static std::optional<Drawing::Matrix> GetMatrix(std::shared_ptr<RSRenderNode> hwcNode);
// RTthread needs to draw one more frame when screen is turned off. For other threads, use extraframe default value.
static bool CheckRenderSkipIfScreenOff(bool extraFrame = false, std::optional<ScreenId> screenId = std::nullopt);
private:
static RectI SrcRectRotateTransform(RSSurfaceRenderNode& node, GraphicTransformType transformType);
static void AssignMainThreadNode(std::list<std::shared_ptr<RSSurfaceRenderNode>>& mainThreadNodes,

View File

@ -680,80 +680,6 @@ HWTEST_F(RSDisplayRenderNodeDrawableTest, WiredScreenProjectionTest, TestSize.Le
displayDrawable_->WiredScreenProjection(*params, virtualProcesser);
}
/**
* @tc.name: SkipDisplayIfScreenOff
* @tc.desc: Test SkipDisplayIfScreenOff, corner case (node is nullptr), return false
* @tc.type: FUNC
* @tc.require: #I9UNQP
*/
HWTEST_F(RSDisplayRenderNodeDrawableTest, SkipDisplayIfScreenOff001, TestSize.Level1)
{
if (!RSSystemProperties::GetSkipDisplayIfScreenOffEnabled() || !RSSystemProperties::IsPhoneType()) {
return;
}
drawable_->renderNode_.reset();
ASSERT_FALSE(displayDrawable_->SkipDisplayIfScreenOff());
}
/**
* @tc.name: SkipDisplayIfScreenOff
* @tc.desc: Test SkipDisplayIfScreenOff, if power off, return true
* @tc.type: FUNC
* @tc.require: #I9UNQP
*/
HWTEST_F(RSDisplayRenderNodeDrawableTest, SkipDisplayIfScreenOff002, TestSize.Level1)
{
if (!RSSystemProperties::GetSkipDisplayIfScreenOffEnabled() || !RSSystemProperties::IsPhoneType()) {
return;
}
ScreenId screenId = 1;
renderNode_->SetScreenId(screenId);
auto screenManager = CreateOrGetScreenManager();
OHOS::Rosen::impl::RSScreenManager& screenManagerImpl =
static_cast<OHOS::Rosen::impl::RSScreenManager&>(*screenManager);
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_ON;
ASSERT_FALSE(displayDrawable_->SkipDisplayIfScreenOff());
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_OFF;
ASSERT_FALSE(displayDrawable_->SkipDisplayIfScreenOff());
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_SUSPEND;
ASSERT_FALSE(displayDrawable_->SkipDisplayIfScreenOff());
}
/**
* @tc.name: SkipDisplayIfScreenOff
* @tc.desc: Test SkipDisplayIfScreenOff, if power off and render one more frame, return true
* @tc.type: FUNC
* @tc.require: #I9UNQP
*/
HWTEST_F(RSDisplayRenderNodeDrawableTest, SkipDisplayIfScreenOff003, TestSize.Level1)
{
if (!RSSystemProperties::GetSkipDisplayIfScreenOffEnabled() || !RSSystemProperties::IsPhoneType()) {
return;
}
ScreenId screenId = 1;
renderNode_->SetScreenId(screenId);
auto screenManager = CreateOrGetScreenManager();
OHOS::Rosen::impl::RSScreenManager& screenManagerImpl =
static_cast<OHOS::Rosen::impl::RSScreenManager&>(*screenManager);
screenManager->MarkPowerOffNeedProcessOneFrame();
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_OFF;
ASSERT_FALSE(displayDrawable_->SkipDisplayIfScreenOff());
screenManager->MarkPowerOffNeedProcessOneFrame();
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_SUSPEND;
ASSERT_FALSE(displayDrawable_->SkipDisplayIfScreenOff());
screenManager->ResetPowerOffNeedProcessOneFrame();
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_OFF;
ASSERT_FALSE(displayDrawable_->SkipDisplayIfScreenOff());
screenManager->ResetPowerOffNeedProcessOneFrame();
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_SUSPEND;
ASSERT_FALSE(displayDrawable_->SkipDisplayIfScreenOff());
}
/**
* @tc.name: GetSpecialLayerType
* @tc.desc: Test GetSpecialLayerType

View File

@ -2207,4 +2207,61 @@ HWTEST_F(RSUniRenderUtilTest, GetMatrix_006, TestSize.Level2)
assertResult.PostConcat(invertAbsParentMatrix);
ASSERT_EQ(RSUniRenderUtil::GetMatrix(node), assertResult);
}
/**
* @tc.name: CheckRenderSkipIfScreenOff001
* @tc.desc: Test CheckRenderSkipIfScreenOff, no need for extra frame
* @tc.type: FUNC
* @tc.require: #I9UNQP
*/
HWTEST_F(RSUniRenderUtilTest, CheckRenderSkipIfScreenOff001, TestSize.Level1)
{
if (!RSSystemProperties::GetSkipDisplayIfScreenOffEnabled() || RSSystemProperties::IsPcType()) {
return;
}
ScreenId screenId = 1;
auto screenManager = CreateOrGetScreenManager();
OHOS::Rosen::impl::RSScreenManager& screenManagerImpl =
static_cast<OHOS::Rosen::impl::RSScreenManager&>(*screenManager);
screenManagerImpl.powerOffNeedProcessOneFrame_ = false;
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_ON;
EXPECT_FALSE(RSUniRenderUtil::CheckRenderSkipIfScreenOff(false, screenId));
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_ON_ADVANCED;
EXPECT_FALSE(RSUniRenderUtil::CheckRenderSkipIfScreenOff(false, screenId));
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_SUSPEND;
EXPECT_TRUE(RSUniRenderUtil::CheckRenderSkipIfScreenOff(false, screenId));
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_OFF;
EXPECT_TRUE(RSUniRenderUtil::CheckRenderSkipIfScreenOff(false, screenId));
}
/**
* @tc.name: CheckRenderSkipIfScreenOff002
* @tc.desc: Test CheckRenderSkipIfScreenOff, need extra frame
* @tc.type: FUNC
* @tc.require: #I9UNQP
*/
HWTEST_F(RSUniRenderUtilTest, CheckRenderSkipIfScreenOff002, TestSize.Level1)
{
if (!RSSystemProperties::GetSkipDisplayIfScreenOffEnabled() || RSSystemProperties::IsPcType()) {
return;
}
ScreenId screenId = 1;
auto screenManager = CreateOrGetScreenManager();
OHOS::Rosen::impl::RSScreenManager& screenManagerImpl =
static_cast<OHOS::Rosen::impl::RSScreenManager&>(*screenManager);
screenManagerImpl.powerOffNeedProcessOneFrame_ = true;
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_ON;
EXPECT_FALSE(RSUniRenderUtil::CheckRenderSkipIfScreenOff(false, screenId));
screenManagerImpl.powerOffNeedProcessOneFrame_ = true;
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_ON_ADVANCED;
EXPECT_FALSE(RSUniRenderUtil::CheckRenderSkipIfScreenOff(false, screenId));
screenManagerImpl.powerOffNeedProcessOneFrame_ = true;
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_SUSPEND;
EXPECT_FALSE(RSUniRenderUtil::CheckRenderSkipIfScreenOff(false, screenId));
screenManagerImpl.powerOffNeedProcessOneFrame_ = true;
screenManagerImpl.screenPowerStatus_[screenId] = ScreenPowerStatus::POWER_STATUS_OFF;
EXPECT_FALSE(RSUniRenderUtil::CheckRenderSkipIfScreenOff(false, screenId));
}
} // namespace OHOS::Rosen