1 /*
2  * Copyright (c) 2024 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 #include "rs_graphic_test.h"
17 #include "rs_graphic_test_director.h"
18 #include "rs_graphic_test_utils.h"
19 #include "rs_parameter_parse.h"
20 #include "ui/rs_root_node.h"
21 #include "ui/rs_surface_node.h"
22 
23 #include <chrono>
24 #include <filesystem>
25 #include <iostream>
26 #include <thread>
27 
28 namespace OHOS {
29 namespace Rosen {
30 namespace {
31 constexpr uint32_t SURFACE_COLOR = 0xffffffff;
32 
ShouldRunCurrentTest()33 bool ShouldRunCurrentTest()
34 {
35     const ::testing::TestInfo* const testInfo =
36         ::testing::UnitTest::GetInstance()->current_test_info();
37     const auto& extInfo = ::OHOS::Rosen::TestDefManager::Instance().GetTestInfo(
38         testInfo->test_case_name(), testInfo->name());
39     const auto& params = RSParameterParse::Instance();
40     if (!extInfo) {
41         LOGE("RSGraphicTest no testinfo %{public}s-%{public}s",
42             testInfo->test_case_name(), testInfo->name());
43         return false;
44     }
45     if (!params.filterTestTypes.empty() && params.filterTestTypes.count(extInfo->testType) == 0) {
46         return false;
47     }
48 
49     if (params.runTestMode != RSGraphicTestMode::ALL && extInfo->testMode != params.runTestMode) {
50         return false;
51     }
52 
53     return true;
54 }
55 }
56 
57 uint32_t RSGraphicTest::imageWriteId_ = 0;
58 
SetUpTestCase()59 void RSGraphicTest::SetUpTestCase()
60 {
61     imageWriteId_ = 0;
62 }
63 
TearDownTestCase()64 void RSGraphicTest::TearDownTestCase()
65 {
66     return;
67 }
68 
SetUp()69 void RSGraphicTest::SetUp()
70 {
71     shouldRunTest_ = ShouldRunCurrentTest();
72     if (!shouldRunTest_) {
73         GTEST_SKIP();
74         return;
75     }
76 
77     RSSurfaceNodeConfig config;
78     config.SurfaceNodeName = "TestSurface";
79     auto testSurface = RSSurfaceNode::Create(config, false);
80 
81     testSurface->SetBounds({0, 0, GetScreenSize()[0], GetScreenSize()[1]});
82     testSurface->SetFrame({0, 0, GetScreenSize()[0], GetScreenSize()[1]});
83     testSurface->SetBackgroundColor(SURFACE_COLOR);
84     GetRootNode()->SetTestSurface(testSurface);
85 
86     BeforeEach();
87 }
88 
TearDown()89 void RSGraphicTest::TearDown()
90 {
91     if (!shouldRunTest_) {
92         return;
93     }
94 
95     RSGraphicTestDirector::Instance().FlushMessage();
96     WaitTimeout(RSParameterParse::Instance().testCaseWaitTime);
97 
98     const ::testing::TestInfo* const testInfo =
99         ::testing::UnitTest::GetInstance()->current_test_info();
100     const auto& extInfo = ::OHOS::Rosen::TestDefManager::Instance().GetTestInfo(
101         testInfo->test_case_name(), testInfo->name());
102     bool isManualTest = false;
103     if (extInfo) {
104         isManualTest = (extInfo->testMode == RSGraphicTestMode::MANUAL);
105     } else {
106         LOGE("RSGraphicTest no testinfo %{public}s-%{public}s", testInfo->test_case_name(), testInfo->name());
107     }
108 
109     if (isManualTest) {
110         WaitTimeout(RSParameterParse::Instance().manualTestWaitTime);
111     } else {
112         auto pixelMap = RSGraphicTestDirector::Instance().TakeScreenCaptureAndWait(
113             RSParameterParse::Instance().surfaceCaptureWaitTime);
114         if (pixelMap) {
115             std::string filename = GetImageSavePath(extInfo->filePath);
116             filename += testInfo->test_case_name() + std::string("_");
117             filename += testInfo->name() + std::string(".png");
118             if (std::filesystem::exists(filename)) {
119                 LOGW("RSGraphicTest file exists %{public}s", filename.c_str());
120             }
121             if (!WriteToPngWithPixelMap(filename, *pixelMap)) {
122                 LOGE("RSGraphicTest::TearDown write image failed %{public}s-%{public}s",
123                     testInfo->test_case_name(), testInfo->name());
124             }
125             std::cout << "png write to " << filename << std::endl;
126         }
127     }
128 
129     AfterEach();
130     WaitTimeout(RSParameterParse::Instance().testCaseWaitTime);
131 
132     GetRootNode()->ResetTestSurface();
133     RSGraphicTestDirector::Instance().FlushMessage();
134     WaitTimeout(RSParameterParse::Instance().testCaseWaitTime);
135 
136     ++imageWriteId_;
137 }
138 
RegisterNode(std::shared_ptr<RSNode> node)139 void RSGraphicTest::RegisterNode(std::shared_ptr<RSNode> node)
140 {
141     nodes_.push_back(node);
142 }
143 
GetRootNode() const144 std::shared_ptr<RSGraphicRootNode> RSGraphicTest::GetRootNode() const
145 {
146     return RSGraphicTestDirector::Instance().GetRootNode();
147 }
148 
GetScreenSize() const149 Vector2f RSGraphicTest::GetScreenSize() const
150 {
151     return RSGraphicTestDirector::Instance().GetScreenSize();
152 }
153 
SetSurfaceBounds(const Vector4f & bounds)154 void RSGraphicTest::SetSurfaceBounds(const Vector4f& bounds)
155 {
156     RSGraphicTestDirector::Instance().SetSurfaceBounds(bounds);
157 }
158 
SetSurfaceColor(const RSColor & color)159 void RSGraphicTest::SetSurfaceColor(const RSColor& color)
160 {
161     RSGraphicTestDirector::Instance().SetSurfaceColor(color);
162 }
163 
GetImageSavePath(const std::string path)164 std::string RSGraphicTest::GetImageSavePath(const std::string path)
165 {
166     std::string imagePath = "/data/local/";
167     size_t posCnt = path.rfind("/") + 1;
168     std::string subPath = path.substr(0, posCnt);
169     imagePath.append(subPath);
170 
171     namespace fs = std::filesystem;
172     if (!fs::exists(imagePath)) {
173         if (!fs::create_directories(imagePath)) {
174             LOGE("RSGraphicTestDirector create dir failed");
175         }
176     } else {
177         if (!fs::is_directory(imagePath)) {
178             LOGE("RSGraphicTestDirector path is not dir");
179         }
180     }
181 
182     return imagePath;
183 }
184 
185 } // namespace Rosen
186 } // namespace OHOS