OLD | NEW |
| (Empty) |
1 // Copyright 2015 The Chromium 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. | |
4 | |
5 #include "remoting/client/touch_input_scaler.h" | |
6 | |
7 #include <stdint.h> | |
8 | |
9 #include <cmath> | |
10 | |
11 #include "base/macros.h" | |
12 #include "remoting/protocol/protocol_mock_objects.h" | |
13 #include "remoting/protocol/test_event_matchers.h" | |
14 #include "testing/gmock/include/gmock/gmock.h" | |
15 #include "testing/gtest/include/gtest/gtest.h" | |
16 | |
17 using ::testing::_; | |
18 using ::testing::AllOf; | |
19 using ::testing::PrintToString; | |
20 | |
21 namespace remoting { | |
22 | |
23 using protocol::MockInputStub; | |
24 using protocol::TouchEvent; | |
25 using protocol::TouchEventPoint; | |
26 using protocol::test::EqualsTouchPointCoordinates; | |
27 using protocol::test::EqualsTouchPointRadii; | |
28 | |
29 namespace { | |
30 | |
31 const float kDefaultRadius = 30.0f; | |
32 const float kDefaultXCoord = 1.0f; | |
33 const float kDefaultYCoord = 1.0f; | |
34 | |
35 struct PointInfo { | |
36 PointInfo(float x, float y) | |
37 : PointInfo(x, y, kDefaultRadius, kDefaultRadius) {} | |
38 PointInfo(float x, float y, float radius_x, float radius_y) | |
39 : x(x), y(y), radius_x(radius_x), radius_y(radius_y) {} | |
40 | |
41 float x; | |
42 float y; | |
43 float radius_x; | |
44 float radius_y; | |
45 }; | |
46 | |
47 const PointInfo kDefaultPointInfo = {kDefaultXCoord, | |
48 kDefaultYCoord, | |
49 kDefaultRadius, | |
50 kDefaultRadius}; | |
51 | |
52 } // namespace | |
53 | |
54 class TouchInputScalerTest : public ::testing::Test { | |
55 protected: | |
56 TouchInputScalerTest() : touch_input_scaler_(&mock_stub_) {} | |
57 | |
58 void AddInputCoordinate(const PointInfo& point_info) { | |
59 point_infos_.push_back(point_info); | |
60 } | |
61 | |
62 void AddDefaultTestPoint() { point_infos_.push_back(kDefaultPointInfo); } | |
63 | |
64 void InjectTestTouchEvent() { | |
65 TouchEvent e; | |
66 e.set_event_type(TouchEvent::TOUCH_POINT_MOVE); | |
67 | |
68 uint32_t id = 1; | |
69 for (const PointInfo& point_info : point_infos_) { | |
70 TouchEventPoint* point = e.add_touch_points(); | |
71 point->set_id(id++); | |
72 point->set_x(point_info.x); | |
73 point->set_y(point_info.y); | |
74 point->set_radius_x(point_info.radius_x); | |
75 point->set_radius_y(point_info.radius_y); | |
76 } | |
77 | |
78 touch_input_scaler_.InjectTouchEvent(e); | |
79 } | |
80 | |
81 void SetInputDimensions(int width, int height) { | |
82 touch_input_scaler_.set_input_size(webrtc::DesktopSize(width, height)); | |
83 } | |
84 | |
85 void SetOutputDimensions(int width, int height) { | |
86 touch_input_scaler_.set_output_size(webrtc::DesktopSize(width, height)); | |
87 } | |
88 | |
89 MockInputStub mock_stub_; | |
90 TouchInputScaler touch_input_scaler_; | |
91 | |
92 private: | |
93 std::vector<PointInfo> point_infos_; | |
94 | |
95 DISALLOW_COPY_AND_ASSIGN(TouchInputScalerTest); | |
96 }; | |
97 | |
98 // TouchInputFilter require both input and output dimensions. | |
99 // These test verify that no events are forwarded to the next InputStub if | |
100 // either dimensions are not set or 0. | |
101 TEST_F(TouchInputScalerTest, NoDimensionsSet) { | |
102 AddDefaultTestPoint(); | |
103 EXPECT_CALL(mock_stub_, InjectTouchEvent(_)).Times(0); | |
104 InjectTestTouchEvent(); | |
105 } | |
106 | |
107 TEST_F(TouchInputScalerTest, BothDimensionsZero) { | |
108 SetInputDimensions(0, 0); | |
109 SetOutputDimensions(0, 0); | |
110 AddDefaultTestPoint(); | |
111 EXPECT_CALL(mock_stub_, InjectTouchEvent(_)).Times(0); | |
112 InjectTestTouchEvent(); | |
113 } | |
114 | |
115 TEST_F(TouchInputScalerTest, SetOnlyInputDimensions) { | |
116 SetInputDimensions(50, 60); | |
117 AddDefaultTestPoint(); | |
118 EXPECT_CALL(mock_stub_, InjectTouchEvent(_)).Times(0); | |
119 InjectTestTouchEvent(); | |
120 } | |
121 | |
122 TEST_F(TouchInputScalerTest, SetOnlyOutputDimensions) { | |
123 SetOutputDimensions(50, 60); | |
124 AddDefaultTestPoint(); | |
125 EXPECT_CALL(mock_stub_, InjectTouchEvent(_)).Times(0); | |
126 InjectTestTouchEvent(); | |
127 } | |
128 | |
129 // The x,y coordinate fall in the desktop size. | |
130 TEST_F(TouchInputScalerTest, NoClampingNoScaling) { | |
131 SetInputDimensions(50, 60); | |
132 SetOutputDimensions(50, 60); | |
133 | |
134 AddInputCoordinate({10.0f, 15.0f}); | |
135 TouchEvent expected_out; | |
136 TouchEventPoint* point = expected_out.add_touch_points(); | |
137 point->set_x(10.0f); | |
138 point->set_y(15.0f); | |
139 | |
140 EXPECT_CALL(mock_stub_, | |
141 InjectTouchEvent(EqualsTouchPointCoordinates(expected_out))); | |
142 InjectTestTouchEvent(); | |
143 } | |
144 | |
145 // Make sure clamping works. | |
146 TEST_F(TouchInputScalerTest, ClampingNoScaling) { | |
147 SetInputDimensions(50, 60); | |
148 SetOutputDimensions(50, 60); | |
149 | |
150 // Note that this could happen if touch started in the chromoting window but | |
151 // the finger moved off the windows. | |
152 AddInputCoordinate({-1.0f, 1.0f}); | |
153 TouchEvent expected_out; | |
154 TouchEventPoint* point = expected_out.add_touch_points(); | |
155 point->set_x(0.0f); | |
156 point->set_y(1.0f); | |
157 | |
158 EXPECT_CALL(mock_stub_, | |
159 InjectTouchEvent(EqualsTouchPointCoordinates(expected_out))); | |
160 InjectTestTouchEvent(); | |
161 } | |
162 | |
163 TEST_F(TouchInputScalerTest, ClampingMultiplePointsNoScaling) { | |
164 SetInputDimensions(50, 60); | |
165 SetOutputDimensions(50, 60); | |
166 | |
167 AddInputCoordinate({-1.0f, 1.0f}); // Fall off left. | |
168 TouchEvent expected_out; | |
169 TouchEventPoint* point = expected_out.add_touch_points(); | |
170 point->set_x(0.0f); | |
171 point->set_y(1.0f); | |
172 | |
173 AddInputCoordinate({100.0f, 1.0f}); // Fall off right. | |
174 point = expected_out.add_touch_points(); | |
175 point->set_x(49.0f); | |
176 point->set_y(1.0f); | |
177 | |
178 AddInputCoordinate({20.0f, 15.0f}); // Should not be clamped. | |
179 point = expected_out.add_touch_points(); | |
180 point->set_x(20.0f); | |
181 point->set_y(15.0f); | |
182 | |
183 AddInputCoordinate({3.0f, -1.0f}); // Fall off above. | |
184 point = expected_out.add_touch_points(); | |
185 point->set_x(3.0f); | |
186 point->set_y(0.0f); | |
187 | |
188 AddInputCoordinate({10.0f, 200.0f}); // Fall off below. | |
189 point = expected_out.add_touch_points(); | |
190 point->set_x(10.0f); | |
191 point->set_y(59.0f); | |
192 | |
193 EXPECT_CALL(mock_stub_, | |
194 InjectTouchEvent(EqualsTouchPointCoordinates(expected_out))); | |
195 InjectTestTouchEvent(); | |
196 } | |
197 | |
198 // Verify up-scaling works. All coordinates should fall inside the output | |
199 // dimensions after scaling. | |
200 TEST_F(TouchInputScalerTest, UpScalingNoClamping) { | |
201 SetInputDimensions(20, 20); | |
202 SetOutputDimensions(40, 40); | |
203 | |
204 AddInputCoordinate({1.0f, 1.0f}); | |
205 TouchEvent expected_out; | |
206 TouchEventPoint* point = expected_out.add_touch_points(); | |
207 point->set_x(2.0f); | |
208 point->set_y(2.0f); | |
209 | |
210 AddInputCoordinate({1.2f, 4.2f}); | |
211 point = expected_out.add_touch_points(); | |
212 point->set_x(2.4f); | |
213 point->set_y(8.4f); | |
214 | |
215 EXPECT_CALL(mock_stub_, | |
216 InjectTouchEvent(EqualsTouchPointCoordinates(expected_out))); | |
217 InjectTestTouchEvent(); | |
218 } | |
219 | |
220 // Verify up-scaling works with clamping. | |
221 TEST_F(TouchInputScalerTest, UpScalingWithClamping) { | |
222 SetInputDimensions(20, 20); | |
223 SetOutputDimensions(40, 40); | |
224 | |
225 AddInputCoordinate({25.0f, 25.0f}); | |
226 TouchEvent expected_out; | |
227 TouchEventPoint* point = expected_out.add_touch_points(); | |
228 point->set_x(39.0f); | |
229 point->set_y(39.0f); | |
230 | |
231 EXPECT_CALL(mock_stub_, | |
232 InjectTouchEvent(EqualsTouchPointCoordinates(expected_out))); | |
233 InjectTestTouchEvent(); | |
234 } | |
235 | |
236 // Verify down scaling works. All coordinates should fall inside the output | |
237 // dimensions after scaling. | |
238 TEST_F(TouchInputScalerTest, DownScalingNoClamping) { | |
239 SetInputDimensions(40, 40); | |
240 SetOutputDimensions(20, 20); | |
241 | |
242 AddInputCoordinate({2.0f, 2.0f}); | |
243 TouchEvent expected_out; | |
244 TouchEventPoint* point = expected_out.add_touch_points(); | |
245 point->set_x(1.0f); | |
246 point->set_y(1.0f); | |
247 | |
248 AddInputCoordinate({6.0f, 3.0f}); | |
249 point = expected_out.add_touch_points(); | |
250 point->set_x(3.0); | |
251 point->set_y(1.5f); | |
252 | |
253 EXPECT_CALL(mock_stub_, | |
254 InjectTouchEvent(EqualsTouchPointCoordinates(expected_out))); | |
255 InjectTestTouchEvent(); | |
256 } | |
257 | |
258 // Verify down scaling works with clamping. | |
259 TEST_F(TouchInputScalerTest, DownScalingWithClamping) { | |
260 SetInputDimensions(40, 40); | |
261 SetOutputDimensions(20, 20); | |
262 | |
263 AddInputCoordinate({-20.0f, 10.0f}); | |
264 TouchEvent expected_out; | |
265 TouchEventPoint* point = expected_out.add_touch_points(); | |
266 point->set_x(0.0f); | |
267 point->set_y(5.0f); | |
268 | |
269 AddInputCoordinate({10.0f, -20.0f}); | |
270 point = expected_out.add_touch_points(); | |
271 point->set_x(5.0f); | |
272 point->set_y(0.0f); | |
273 | |
274 AddInputCoordinate({6.0f, 80.0f}); | |
275 point = expected_out.add_touch_points(); | |
276 point->set_x(3.0f); | |
277 point->set_y(19.0f); | |
278 | |
279 AddInputCoordinate({80.0f, 6.0f}); | |
280 point = expected_out.add_touch_points(); | |
281 point->set_x(19.0f); | |
282 point->set_y(3.0f); | |
283 | |
284 EXPECT_CALL(mock_stub_, | |
285 InjectTouchEvent(EqualsTouchPointCoordinates(expected_out))); | |
286 InjectTestTouchEvent(); | |
287 } | |
288 | |
289 // Verify that the radii are up-scaled. | |
290 TEST_F(TouchInputScalerTest, UpScaleRadii) { | |
291 SetInputDimensions(20, 20); | |
292 SetOutputDimensions(40, 40); | |
293 | |
294 AddInputCoordinate({0.0f, 0.0f, 1.0f, 2.0f}); | |
295 TouchEvent expected_out; | |
296 TouchEventPoint* point = expected_out.add_touch_points(); | |
297 point->set_radius_x(2.0f); | |
298 point->set_radius_y(4.0f); | |
299 | |
300 EXPECT_CALL(mock_stub_, | |
301 InjectTouchEvent(EqualsTouchPointRadii(expected_out))); | |
302 InjectTestTouchEvent(); | |
303 } | |
304 | |
305 // Verify that the radii are down-scaled. | |
306 TEST_F(TouchInputScalerTest, DownScaleRadii) { | |
307 SetInputDimensions(20, 20); | |
308 SetOutputDimensions(10, 10); | |
309 | |
310 AddInputCoordinate({0.0f, 0.0f, 5.0f, 4.0f}); | |
311 TouchEvent expected_out; | |
312 TouchEventPoint* point = expected_out.add_touch_points(); | |
313 point->set_radius_x(2.5f); | |
314 point->set_radius_y(2.0f); | |
315 | |
316 EXPECT_CALL(mock_stub_, | |
317 InjectTouchEvent(EqualsTouchPointRadii(expected_out))); | |
318 InjectTestTouchEvent(); | |
319 } | |
320 | |
321 // Verify that up-scaling with clamping works for x,y coordinates and radii all | |
322 // work together. | |
323 TEST_F(TouchInputScalerTest, UpScaleCoordinatesAndRadii) { | |
324 SetInputDimensions(20, 20); | |
325 SetOutputDimensions(40, 40); | |
326 | |
327 AddInputCoordinate({5.0f, 12.0f, 3.0f, 2.0f}); | |
328 TouchEvent expected_out; | |
329 TouchEventPoint* point = expected_out.add_touch_points(); | |
330 point->set_x(10.0f); | |
331 point->set_y(24.0f); | |
332 point->set_radius_x(6.0f); | |
333 point->set_radius_y(4.0f); | |
334 | |
335 // Make sure clamping and scaling all work. | |
336 AddInputCoordinate({22.0f, -1.0f, 8.0f, 3.0f}); | |
337 point = expected_out.add_touch_points(); | |
338 point->set_x(39.0f); | |
339 point->set_y(0.0f); | |
340 point->set_radius_x(16.0f); | |
341 point->set_radius_y(6.0f); | |
342 | |
343 EXPECT_CALL(mock_stub_, | |
344 InjectTouchEvent(AllOf(EqualsTouchPointCoordinates(expected_out), | |
345 EqualsTouchPointRadii(expected_out)))); | |
346 InjectTestTouchEvent(); | |
347 } | |
348 | |
349 // Verify that down-scaling with clamping works for x,y coordinates and radii | |
350 // all work together. | |
351 TEST_F(TouchInputScalerTest, DownScaleCoordinatesAndRadii) { | |
352 SetInputDimensions(60, 60); | |
353 SetOutputDimensions(20, 20); | |
354 | |
355 AddInputCoordinate({50.0f, 24.0f, 10.0f, 9.0f}); | |
356 TouchEvent expected_out; | |
357 TouchEventPoint* point = expected_out.add_touch_points(); | |
358 point->set_x(16.666f); | |
359 point->set_y(8.0f); | |
360 point->set_radius_x(3.333f); | |
361 point->set_radius_y(3.0f); | |
362 | |
363 // Make sure clamping and scaling all work. | |
364 AddInputCoordinate({70.0f, 82.0f, 8.0f, 3.0f}); | |
365 point = expected_out.add_touch_points(); | |
366 point->set_x(19.0f); | |
367 point->set_y(19.0f); | |
368 point->set_radius_x(2.666f); | |
369 point->set_radius_y(1.0f); | |
370 | |
371 EXPECT_CALL(mock_stub_, | |
372 InjectTouchEvent(AllOf(EqualsTouchPointCoordinates(expected_out), | |
373 EqualsTouchPointRadii(expected_out)))); | |
374 InjectTestTouchEvent(); | |
375 } | |
376 | |
377 } // namespace remoting | |
OLD | NEW |