1010#include " flutter/shell/platform/common/client_wrapper/include/flutter/standard_message_codec.h"
1111#include " flutter/shell/platform/common/client_wrapper/include/flutter/standard_method_codec.h"
1212#include " flutter/shell/platform/windows/flutter_windows_view.h"
13+ #include " flutter/shell/platform/windows/testing/flutter_windows_engine_builder.h"
1314#include " flutter/shell/platform/windows/testing/mock_window_binding_handler.h"
1415#include " flutter/shell/platform/windows/testing/test_binary_messenger.h"
16+ #include " flutter/shell/platform/windows/testing/windows_test.h"
1517#include " gmock/gmock.h"
1618#include " gtest/gtest.h"
1719
@@ -50,12 +52,46 @@ void SimulateCursorMessage(TestBinaryMessenger* messenger,
5052
5153} // namespace
5254
53- TEST (CursorHandlerTest, ActivateSystemCursor) {
55+ class CursorHandlerTest : public WindowsTest {
56+ protected:
57+ FlutterWindowsEngine* engine () { return engine_.get (); }
58+ FlutterWindowsView* view () { return view_.get (); }
59+ MockWindowBindingHandler* window () { return window_; }
60+
61+ void use_headless_engine () {
62+ FlutterWindowsEngineBuilder builder{GetContext ()};
63+
64+ engine_ = builder.Build ();
65+ }
66+
67+ void use_engine_with_view () {
68+ FlutterWindowsEngineBuilder builder{GetContext ()};
69+
70+ auto window = std::make_unique<MockWindowBindingHandler>();
71+
72+ window_ = window.get ();
73+ EXPECT_CALL (*window_, SetView).Times (1 );
74+ EXPECT_CALL (*window_, GetRenderTarget).WillOnce (Return (nullptr ));
75+
76+ engine_ = builder.Build ();
77+ view_ = std::make_unique<FlutterWindowsView>(std::move (window));
78+
79+ engine_->SetView (view_.get ());
80+ }
81+
82+ private:
83+ std::unique_ptr<FlutterWindowsEngine> engine_;
84+ std::unique_ptr<FlutterWindowsView> view_;
85+ MockWindowBindingHandler* window_;
86+ };
87+
88+ TEST_F (CursorHandlerTest, ActivateSystemCursor) {
89+ use_engine_with_view ();
90+
5491 TestBinaryMessenger messenger;
55- MockWindowBindingHandler window;
56- CursorHandler cursor_handler (&messenger, &window);
92+ CursorHandler cursor_handler (&messenger, engine ());
5793
58- EXPECT_CALL (window, UpdateFlutterCursor (" click" )).Times (1 );
94+ EXPECT_CALL (* window () , UpdateFlutterCursor (" click" )).Times (1 );
5995
6096 bool success = false ;
6197 MethodResultFunctions<> result_handler (
@@ -75,10 +111,38 @@ TEST(CursorHandlerTest, ActivateSystemCursor) {
75111 EXPECT_TRUE (success);
76112}
77113
78- TEST (CursorHandlerTest, CreateCustomCursor) {
114+ TEST_F (CursorHandlerTest, ActivateSystemCursorRequiresView) {
115+ use_headless_engine ();
116+
79117 TestBinaryMessenger messenger;
80- MockWindowBindingHandler window;
81- CursorHandler cursor_handler (&messenger, &window);
118+ CursorHandler cursor_handler (&messenger, engine ());
119+
120+ bool error = false ;
121+ MethodResultFunctions<> result_handler (
122+ nullptr ,
123+ [&error](const std::string& error_code, const std::string& error_message,
124+ const EncodableValue* value) {
125+ error = true ;
126+ EXPECT_EQ (error_message,
127+ " Cursor is not available in Windows headless mode" );
128+ },
129+ nullptr );
130+
131+ SimulateCursorMessage (&messenger, kActivateSystemCursorMethod ,
132+ std::make_unique<EncodableValue>(EncodableMap{
133+ {EncodableValue (" device" ), EncodableValue (0 )},
134+ {EncodableValue (" kind" ), EncodableValue (" click" )},
135+ }),
136+ &result_handler);
137+
138+ EXPECT_TRUE (error);
139+ }
140+
141+ TEST_F (CursorHandlerTest, CreateCustomCursor) {
142+ use_engine_with_view ();
143+
144+ TestBinaryMessenger messenger;
145+ CursorHandler cursor_handler (&messenger, engine ());
82146
83147 // Create a 4x4 raw BGRA test cursor buffer.
84148 std::vector<uint8_t > buffer (4 * 4 * 4 , 0 );
@@ -105,10 +169,11 @@ TEST(CursorHandlerTest, CreateCustomCursor) {
105169 EXPECT_TRUE (success);
106170}
107171
108- TEST (CursorHandlerTest, SetCustomCursor) {
172+ TEST_F (CursorHandlerTest, SetCustomCursor) {
173+ use_engine_with_view ();
174+
109175 TestBinaryMessenger messenger;
110- MockWindowBindingHandler window;
111- CursorHandler cursor_handler (&messenger, &window);
176+ CursorHandler cursor_handler (&messenger, engine ());
112177
113178 // Create a 4x4 raw BGRA test cursor buffer.
114179 std::vector<uint8_t > buffer (4 * 4 * 4 , 0 );
@@ -122,7 +187,7 @@ TEST(CursorHandlerTest, SetCustomCursor) {
122187 },
123188 nullptr , nullptr );
124189
125- EXPECT_CALL (window, SetFlutterCursor (/* cursor=*/ NotNull ())).Times (1 );
190+ EXPECT_CALL (* window () , SetFlutterCursor (/* cursor=*/ NotNull ())).Times (1 );
126191
127192 SimulateCursorMessage (&messenger, kCreateCustomCursorMethod ,
128193 std::make_unique<EncodableValue>(EncodableMap{
@@ -144,10 +209,52 @@ TEST(CursorHandlerTest, SetCustomCursor) {
144209 EXPECT_TRUE (success);
145210}
146211
147- TEST (CursorHandlerTest, SetNonexistentCustomCursor) {
212+ TEST_F (CursorHandlerTest, SetCustomCursorRequiresView) {
213+ use_headless_engine ();
214+
148215 TestBinaryMessenger messenger;
149- MockWindowBindingHandler window;
150- CursorHandler cursor_handler (&messenger, &window);
216+ CursorHandler cursor_handler (&messenger, engine ());
217+
218+ // Create a 4x4 raw BGRA test cursor buffer.
219+ std::vector<uint8_t > buffer (4 * 4 * 4 , 0 );
220+
221+ bool error = false ;
222+ MethodResultFunctions<> create_result_handler (nullptr , nullptr , nullptr );
223+ MethodResultFunctions<> set_result_handler (
224+ nullptr ,
225+ [&error](const std::string& error_code, const std::string& error_message,
226+ const EncodableValue* value) {
227+ error = true ;
228+ EXPECT_EQ (error_message,
229+ " Cursor is not available in Windows headless mode" );
230+ },
231+ nullptr );
232+
233+ SimulateCursorMessage (&messenger, kCreateCustomCursorMethod ,
234+ std::make_unique<EncodableValue>(EncodableMap{
235+ {EncodableValue (" name" ), EncodableValue (" hello" )},
236+ {EncodableValue (" buffer" ), EncodableValue (buffer)},
237+ {EncodableValue (" width" ), EncodableValue (4 )},
238+ {EncodableValue (" height" ), EncodableValue (4 )},
239+ {EncodableValue (" hotX" ), EncodableValue (0.0 )},
240+ {EncodableValue (" hotY" ), EncodableValue (0.0 )},
241+ }),
242+ &create_result_handler);
243+
244+ SimulateCursorMessage (&messenger, kSetCustomCursorMethod ,
245+ std::make_unique<EncodableValue>(EncodableMap{
246+ {EncodableValue (" name" ), EncodableValue (" hello" )},
247+ }),
248+ &set_result_handler);
249+
250+ EXPECT_TRUE (error);
251+ }
252+
253+ TEST_F (CursorHandlerTest, SetNonexistentCustomCursor) {
254+ use_engine_with_view ();
255+
256+ TestBinaryMessenger messenger;
257+ CursorHandler cursor_handler (&messenger, engine ());
151258
152259 bool error = false ;
153260 MethodResultFunctions<> result_handler (
@@ -161,7 +268,7 @@ TEST(CursorHandlerTest, SetNonexistentCustomCursor) {
161268 },
162269 nullptr );
163270
164- EXPECT_CALL (window, SetFlutterCursor).Times (0 );
271+ EXPECT_CALL (* window () , SetFlutterCursor).Times (0 );
165272
166273 SimulateCursorMessage (&messenger, kSetCustomCursorMethod ,
167274 std::make_unique<EncodableValue>(EncodableMap{
@@ -172,10 +279,11 @@ TEST(CursorHandlerTest, SetNonexistentCustomCursor) {
172279 EXPECT_TRUE (error);
173280}
174281
175- TEST (CursorHandlerTest, DeleteCustomCursor) {
282+ TEST_F (CursorHandlerTest, DeleteCustomCursor) {
283+ use_engine_with_view ();
284+
176285 TestBinaryMessenger messenger;
177- MockWindowBindingHandler window;
178- CursorHandler cursor_handler (&messenger, &window);
286+ CursorHandler cursor_handler (&messenger, engine ());
179287
180288 // Create a 4x4 raw BGRA test cursor buffer.
181289 std::vector<uint8_t > buffer (4 * 4 * 4 , 0 );
@@ -209,10 +317,11 @@ TEST(CursorHandlerTest, DeleteCustomCursor) {
209317 EXPECT_TRUE (success);
210318}
211319
212- TEST (CursorHandlerTest, DeleteNonexistentCustomCursor) {
320+ TEST_F (CursorHandlerTest, DeleteNonexistentCustomCursor) {
321+ use_engine_with_view ();
322+
213323 TestBinaryMessenger messenger;
214- MockWindowBindingHandler handler;
215- CursorHandler cursor_handler (&messenger, &handler);
324+ CursorHandler cursor_handler (&messenger, engine ());
216325
217326 bool success = false ;
218327 MethodResultFunctions<> result_handler (
0 commit comments