Flutter Engine Uber Docs
Docs for the entire Flutter Engine repo.
 
Loading...
Searching...
No Matches
cursor_handler_unittests.cc
Go to the documentation of this file.
1// Copyright 2013 The Flutter Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
5
6#include <memory>
7#include <vector>
8
20#include "gmock/gmock.h"
21#include "gtest/gtest.h"
22
23namespace flutter {
24namespace testing {
25
26namespace {
27using ::testing::_;
28using ::testing::IsNull;
29using ::testing::NotNull;
30using ::testing::Return;
31
32static constexpr char kChannelName[] = "flutter/mousecursor";
33
34static constexpr char kActivateSystemCursorMethod[] = "activateSystemCursor";
35static constexpr char kCreateCustomCursorMethod[] =
36 "createCustomCursor/windows";
37static constexpr char kSetCustomCursorMethod[] = "setCustomCursor/windows";
38static constexpr char kDeleteCustomCursorMethod[] =
39 "deleteCustomCursor/windows";
40
41void SimulateCursorMessage(TestBinaryMessenger* messenger,
42 const std::string& method_name,
43 std::unique_ptr<EncodableValue> arguments,
44 MethodResult<EncodableValue>* result_handler) {
45 MethodCall<> call(method_name, std::move(arguments));
46
48
49 EXPECT_TRUE(messenger->SimulateEngineMessage(
50 kChannelName, message->data(), message->size(),
51 [&result_handler](const uint8_t* reply, size_t reply_size) {
52 StandardMethodCodec::GetInstance().DecodeAndProcessResponseEnvelope(
53 reply, reply_size, result_handler);
54 }));
55}
56
57} // namespace
58
60 public:
61 CursorHandlerTest() = default;
62 virtual ~CursorHandlerTest() = default;
63
64 protected:
65 FlutterWindowsEngine* engine() { return engine_.get(); }
66 FlutterWindowsView* view() { return view_.get(); }
67 MockWindowBindingHandler* window() { return window_; }
68 MockWindowsProcTable* proc_table() { return windows_proc_table_.get(); }
69
72
73 engine_ = builder.Build();
74 }
75
77 windows_proc_table_ = std::make_shared<MockWindowsProcTable>();
78
80 builder.SetWindowsProcTable(windows_proc_table_);
81
82 auto window = std::make_unique<MockWindowBindingHandler>();
83 EXPECT_CALL(*window.get(), SetView).Times(1);
84 EXPECT_CALL(*window.get(), GetWindowHandle).WillRepeatedly(Return(nullptr));
85
86 window_ = window.get();
87 engine_ = builder.Build();
88 view_ =
89 engine_->CreateView(std::move(window),
90 /*is_sized_to_content=*/false, BoxConstraints());
91 }
92
93 private:
94 std::unique_ptr<FlutterWindowsEngine> engine_;
95 std::unique_ptr<FlutterWindowsView> view_;
97 std::shared_ptr<MockWindowsProcTable> windows_proc_table_;
98
100};
101
102TEST_F(CursorHandlerTest, ActivateSystemCursor) {
103 UseEngineWithView();
104
105 TestBinaryMessenger messenger;
106 CursorHandler cursor_handler(&messenger, engine());
107
108 EXPECT_CALL(*proc_table(), LoadCursor(IsNull(), IDC_HAND)).Times(1);
109 EXPECT_CALL(*proc_table(), SetCursor).Times(1);
110
111 bool success = false;
112 MethodResultFunctions<> result_handler(
113 [&success](const EncodableValue* result) {
114 success = true;
115 EXPECT_EQ(result, nullptr);
116 },
117 nullptr, nullptr);
118
119 SimulateCursorMessage(&messenger, kActivateSystemCursorMethod,
120 std::make_unique<EncodableValue>(EncodableMap{
121 {EncodableValue("device"), EncodableValue(0)},
122 {EncodableValue("kind"), EncodableValue("click")},
123 }),
124 &result_handler);
125
126 EXPECT_TRUE(success);
127}
128
129TEST_F(CursorHandlerTest, CreateCustomCursor) {
130 UseEngineWithView();
131
132 TestBinaryMessenger messenger;
133 CursorHandler cursor_handler(&messenger, engine());
134
135 // Create a 4x4 raw BGRA test cursor buffer.
136 std::vector<uint8_t> buffer(4 * 4 * 4, 0);
137
138 bool success = false;
139 MethodResultFunctions<> result_handler(
140 [&success](const EncodableValue* result) {
141 success = true;
142 EXPECT_EQ(std::get<std::string>(*result), "hello");
143 },
144 nullptr, nullptr);
145
146 SimulateCursorMessage(&messenger, kCreateCustomCursorMethod,
147 std::make_unique<EncodableValue>(EncodableMap{
148 {EncodableValue("name"), EncodableValue("hello")},
150 {EncodableValue("width"), EncodableValue(4)},
151 {EncodableValue("height"), EncodableValue(4)},
152 {EncodableValue("hotX"), EncodableValue(0.0)},
153 {EncodableValue("hotY"), EncodableValue(0.0)},
154 }),
155 &result_handler);
156
157 EXPECT_TRUE(success);
158}
159
160TEST_F(CursorHandlerTest, SetCustomCursor) {
161 UseEngineWithView();
162
163 TestBinaryMessenger messenger;
164 CursorHandler cursor_handler(&messenger, engine());
165
166 // Create a 4x4 raw BGRA test cursor buffer.
167 std::vector<uint8_t> buffer(4 * 4 * 4, 0);
168
169 bool success = false;
170 MethodResultFunctions<> create_result_handler(nullptr, nullptr, nullptr);
171 MethodResultFunctions<> set_result_handler(
172 [&success](const EncodableValue* result) {
173 success = true;
174 EXPECT_EQ(result, nullptr);
175 },
176 nullptr, nullptr);
177
178 EXPECT_CALL(*proc_table(), LoadCursor).Times(0);
179 EXPECT_CALL(*proc_table(), SetCursor(NotNull())).Times(1);
180
181 SimulateCursorMessage(&messenger, kCreateCustomCursorMethod,
182 std::make_unique<EncodableValue>(EncodableMap{
183 {EncodableValue("name"), EncodableValue("hello")},
185 {EncodableValue("width"), EncodableValue(4)},
186 {EncodableValue("height"), EncodableValue(4)},
187 {EncodableValue("hotX"), EncodableValue(0.0)},
188 {EncodableValue("hotY"), EncodableValue(0.0)},
189 }),
190 &create_result_handler);
191
192 SimulateCursorMessage(&messenger, kSetCustomCursorMethod,
193 std::make_unique<EncodableValue>(EncodableMap{
194 {EncodableValue("name"), EncodableValue("hello")},
195 }),
196 &set_result_handler);
197
198 EXPECT_TRUE(success);
199}
200
201TEST_F(CursorHandlerTest, SetNonexistentCustomCursor) {
202 UseEngineWithView();
203
204 TestBinaryMessenger messenger;
205 CursorHandler cursor_handler(&messenger, engine());
206
207 bool error = false;
208 MethodResultFunctions<> result_handler(
209 nullptr,
210 [&error](const std::string& error_code, const std::string& error_message,
211 const EncodableValue* value) {
212 error = true;
213 EXPECT_EQ(
214 error_message,
215 "The custom cursor identified by the argument key cannot be found");
216 },
217 nullptr);
218
219 EXPECT_CALL(*proc_table(), LoadCursor).Times(0);
220 EXPECT_CALL(*proc_table(), SetCursor).Times(0);
221
222 SimulateCursorMessage(&messenger, kSetCustomCursorMethod,
223 std::make_unique<EncodableValue>(EncodableMap{
224 {EncodableValue("name"), EncodableValue("hello")},
225 }),
226 &result_handler);
227
228 EXPECT_TRUE(error);
229}
230
231TEST_F(CursorHandlerTest, DeleteCustomCursor) {
232 UseEngineWithView();
233
234 TestBinaryMessenger messenger;
235 CursorHandler cursor_handler(&messenger, engine());
236
237 // Create a 4x4 raw BGRA test cursor buffer.
238 std::vector<uint8_t> buffer(4 * 4 * 4, 0);
239
240 bool success = false;
241 MethodResultFunctions<> create_result_handler(nullptr, nullptr, nullptr);
242 MethodResultFunctions<> delete_result_handler(
243 [&success](const EncodableValue* result) {
244 success = true;
245 EXPECT_EQ(result, nullptr);
246 },
247 nullptr, nullptr);
248
249 SimulateCursorMessage(&messenger, kCreateCustomCursorMethod,
250 std::make_unique<EncodableValue>(EncodableMap{
251 {EncodableValue("name"), EncodableValue("hello")},
253 {EncodableValue("width"), EncodableValue(4)},
254 {EncodableValue("height"), EncodableValue(4)},
255 {EncodableValue("hotX"), EncodableValue(0.0)},
256 {EncodableValue("hotY"), EncodableValue(0.0)},
257 }),
258 &create_result_handler);
259
260 SimulateCursorMessage(&messenger, kDeleteCustomCursorMethod,
261 std::make_unique<EncodableValue>(EncodableMap{
262 {EncodableValue("name"), EncodableValue("hello")},
263 }),
264 &delete_result_handler);
265
266 EXPECT_TRUE(success);
267}
268
269TEST_F(CursorHandlerTest, DeleteNonexistentCustomCursor) {
270 UseEngineWithView();
271
272 TestBinaryMessenger messenger;
273 CursorHandler cursor_handler(&messenger, engine());
274
275 bool success = false;
276 MethodResultFunctions<> result_handler(
277 [&success](const EncodableValue* result) {
278 success = true;
279 EXPECT_EQ(result, nullptr);
280 },
281 nullptr, nullptr);
282
283 SimulateCursorMessage(&messenger, kDeleteCustomCursorMethod,
284 std::make_unique<EncodableValue>(EncodableMap{
285 {EncodableValue("name"), EncodableValue("fake")},
286 }),
287 &result_handler);
288
289 EXPECT_TRUE(success);
290}
291
292} // namespace testing
293} // namespace flutter
static NSString *const kChannelName
static NSString *const kActivateSystemCursorMethod
std::unique_ptr< std::vector< uint8_t > > EncodeMethodCall(const MethodCall< T > &method_call) const
static const StandardMethodCodec & GetInstance(const StandardCodecSerializer *serializer=nullptr)
Mock for the |WindowsProcTable| base class.
WindowsTestContext & GetContext()
static constexpr char kDeleteCustomCursorMethod[]
static constexpr char kCreateCustomCursorMethod[]
static constexpr char kSetCustomCursorMethod[]
int32_t value
FlutterEngine engine
Definition main.cc:84
const char * message
const uint8_t uint32_t uint32_t GError ** error
#define FML_DISALLOW_COPY_AND_ASSIGN(TypeName)
Definition macros.h:27
TEST_F(DisplayListTest, Defaults)
std::map< EncodableValue, EncodableValue > EncodableMap
DEF_SWITCHES_START aot vmservice shared library Name of the *so containing AOT compiled Dart assets for launching the service isolate vm snapshot The VM snapshot data that will be memory mapped as read only SnapshotAssetPath must be present isolate snapshot The isolate snapshot data that will be memory mapped as read only SnapshotAssetPath must be present cache dir Path to the cache directory This is different from the persistent_cache_path in embedder which is used for Skia shader cache icu native lib Path to the library file that exports the ICU data vm service The hostname IP address on which the Dart VM Service should be served If not defaults to or::depending on whether ipv6 is specified disable vm Disable the Dart VM Service The Dart VM Service is never available in release mode Bind to the IPv6 localhost address for the Dart VM Service Ignored if vm service host is set profile Make the profiler discard new samples once the profiler sample buffer is full When this flag is not the profiler sample buffer is used as a ring buffer
Definition switch_defs.h:98