OLD | NEW |
---|---|
(Empty) | |
1 // Copyright 2017 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 "hit_test_aggregator.h" | |
6 #include "cc/surfaces/frame_sink_id.h" | |
7 #include "cc/surfaces/local_surface_id.h" | |
8 #include "cc/surfaces/surface_id.h" | |
9 #include "testing/gtest/include/gtest/gtest.h" | |
10 | |
11 namespace viz { | |
12 namespace hit_test { | |
13 namespace test { | |
14 | |
15 namespace { | |
16 | |
17 constexpr cc::FrameSinkId kDisplayFrameSink(2, 0); | |
18 | |
19 cc::SurfaceId MakeSurfaceId(const cc::FrameSinkId& frame_sink_id, | |
20 uint32_t local_id) { | |
21 return cc::SurfaceId( | |
22 frame_sink_id, | |
23 cc::LocalSurfaceId(local_id, base::UnguessableToken::Deserialize(0, 1u))); | |
24 } | |
25 | |
26 } // namespace | |
27 | |
28 using namespace hit_test::mojom; | |
29 | |
30 class HitTestAggregatorTest : public testing::Test { | |
31 public: | |
32 HitTestAggregatorTest() {} | |
33 ~HitTestAggregatorTest() override {} | |
34 | |
35 // testing::Test: | |
36 void SetUp() override {} | |
37 void TearDown() override { Reset(); } | |
38 | |
39 HitTestAggregator aggregator_; | |
40 | |
41 int count() { | |
42 DisplayHitTestRegion* start = | |
43 (DisplayHitTestRegion*)aggregator_.read_buffer_.get(); | |
44 DisplayHitTestRegion* end = start; | |
45 while (end->child_count != kEndOfList) { | |
varkha
2017/06/28 19:20:38
nit: no {}
gklassen
2017/06/29 11:56:26
Done.
| |
46 end++; | |
47 } | |
48 int count = end - start; | |
49 return count; | |
50 } | |
51 | |
52 int GetPendingCount() { return aggregator_.pending_.size(); } | |
53 int GetActiveCount() { return aggregator_.active_.size(); } | |
54 | |
55 void CallOnSurfaceWillDraw(cc::SurfaceId surface_id) { | |
56 aggregator_.OnSurfaceWillDraw(surface_id); | |
57 } | |
58 | |
59 void Reset() { | |
60 DisplayHitTestRegion* regions = | |
61 (DisplayHitTestRegion*)aggregator_.write_buffer_.get(); | |
62 regions[0].child_count = kEndOfList; | |
63 | |
64 regions = (DisplayHitTestRegion*)aggregator_.read_buffer_.get(); | |
65 regions[0].child_count = kEndOfList; | |
66 | |
67 aggregator_.pending_.clear(); | |
68 aggregator_.active_.clear(); | |
69 } | |
70 | |
71 int GetDisplayHitTestRegionListSize() { return aggregator_.read_size_; } | |
72 | |
73 DisplayHitTestRegion* GetRegions() { | |
74 return (DisplayHitTestRegion*)aggregator_.read_buffer_.get(); | |
75 } | |
76 | |
77 // Creates a hit test data element with 8 children recursively to | |
78 // the specified depth. SurfaceIds are generated in sequential order and | |
79 // the method returns the next unused id ( also matches the count ). | |
80 int CreateAndSubmitHitTestRegionListWith8Children(int id, int depth) { | |
81 cc::SurfaceId surface_id = MakeSurfaceId(kDisplayFrameSink, id); | |
82 id++; | |
83 | |
84 auto hit_test_region_list = HitTestRegionList::New(); | |
85 hit_test_region_list->surface_id = surface_id; | |
86 hit_test_region_list->flags = kHitTestMine; | |
87 hit_test_region_list->bounds.SetRect(0, 0, 1024, 768); | |
88 | |
89 for (int i = 0; i < 8; i++) { | |
90 auto hit_test_region = HitTestRegion::New(); | |
91 hit_test_region->rect.SetRect(100, 100, 100, 100); | |
92 | |
93 if (depth > 0) { | |
94 hit_test_region->flags = kHitTestChildSurface; | |
95 hit_test_region->surface_id = MakeSurfaceId(kDisplayFrameSink, id); | |
96 id = CreateAndSubmitHitTestRegionListWith8Children(id, depth - 1); | |
97 } else { | |
98 hit_test_region->flags = kHitTestMine; | |
99 } | |
100 hit_test_region_list->regions.push_back(std::move(hit_test_region)); | |
101 } | |
102 | |
103 aggregator_.SubmitHitTestRegionList(std::move(hit_test_region_list)); | |
104 return id; | |
105 } | |
106 }; | |
107 | |
108 // TODO(gklassen): Add tests for 3D use cases as suggested by and with | |
109 // input from rjkroege. | |
110 | |
111 // One surface. | |
112 // | |
113 // +----------+ | |
114 // | | | |
115 // | | | |
116 // | | | |
117 // +----------+ | |
118 // | |
119 TEST_F(HitTestAggregatorTest, OneSurface) { | |
120 EXPECT_EQ(count(), 0); | |
121 | |
122 cc::SurfaceId display_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
123 | |
124 auto hit_test_region_list = HitTestRegionList::New(); | |
125 hit_test_region_list->surface_id = display_surface_id; | |
126 hit_test_region_list->flags = kHitTestMine; | |
127 hit_test_region_list->bounds.SetRect(0, 0, 1024, 768); | |
128 | |
129 aggregator_.SubmitHitTestRegionList(std::move(hit_test_region_list)); | |
130 EXPECT_EQ(count(), 0); | |
131 | |
132 EXPECT_EQ(GetPendingCount(), 1); | |
133 EXPECT_EQ(GetActiveCount(), 0); | |
134 | |
135 CallOnSurfaceWillDraw(display_surface_id); | |
136 | |
137 EXPECT_EQ(GetPendingCount(), 0); | |
138 EXPECT_EQ(GetActiveCount(), 1); | |
139 | |
140 aggregator_.Aggregate(display_surface_id); | |
141 aggregator_.Swap(); | |
142 | |
143 // Expect 1 entry routing all events to the one surface ( display root ). | |
varkha
2017/06/28 19:20:38
nit: spacing
gklassen
2017/06/29 11:56:26
Done.
| |
144 EXPECT_EQ(count(), 1); | |
145 | |
146 DisplayHitTestRegion* regions = GetRegions(); | |
147 | |
148 DisplayHitTestRegion* region = nullptr; | |
149 | |
150 region = ®ions[0]; | |
151 EXPECT_EQ(region->flags, kHitTestMine); | |
152 EXPECT_EQ(region->frame_sink_id, display_surface_id.frame_sink_id()); | |
153 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 1024, 768)); | |
154 EXPECT_EQ(region->child_count, 0); | |
155 } | |
156 | |
157 // One opaque embedder with two regions. | |
158 // | |
159 // +e-------------+ | |
160 // | +r1-+ +r2--+ | | |
161 // | | | | | | | |
162 // | | | | | | | |
163 // | +---+ +----+ | | |
164 // +--------------+ | |
165 // | |
166 TEST_F(HitTestAggregatorTest, OneEmbedderTwoRegions) { | |
167 EXPECT_EQ(count(), 0); | |
168 | |
169 cc::SurfaceId e_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
170 | |
171 auto e_hit_test_data = HitTestRegionList::New(); | |
172 e_hit_test_data->surface_id = e_surface_id; | |
173 e_hit_test_data->flags = kHitTestMine; | |
174 e_hit_test_data->bounds.SetRect(0, 0, 1024, 768); | |
175 | |
176 auto e_hit_test_region_r1 = HitTestRegion::New(); | |
177 e_hit_test_region_r1->flags = kHitTestMine; | |
178 e_hit_test_region_r1->rect.SetRect(100, 100, 200, 400); | |
179 | |
180 auto e_hit_test_region_r2 = HitTestRegion::New(); | |
181 e_hit_test_region_r2->flags = kHitTestMine; | |
182 e_hit_test_region_r2->rect.SetRect(400, 100, 300, 400); | |
183 | |
184 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_r1)); | |
185 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_r2)); | |
186 | |
187 // Submit HitTestRegionList. | |
188 | |
189 EXPECT_EQ(GetPendingCount(), 0); | |
190 | |
191 aggregator_.SubmitHitTestRegionList(std::move(e_hit_test_data)); | |
192 EXPECT_EQ(GetPendingCount(), 1); | |
193 | |
194 // Add Surfaces to DisplayFrame in unexpected order. | |
195 | |
196 EXPECT_EQ(count(), 0); | |
197 EXPECT_EQ(GetActiveCount(), 0); | |
198 | |
199 CallOnSurfaceWillDraw(e_surface_id); | |
200 EXPECT_EQ(GetActiveCount(), 1); | |
201 | |
202 // Aggregate and swap. | |
203 | |
204 aggregator_.Aggregate(e_surface_id); | |
205 EXPECT_EQ(count(), 0); | |
206 | |
207 aggregator_.Swap(); | |
208 EXPECT_EQ(count(), 3); | |
209 | |
210 DisplayHitTestRegion* regions = GetRegions(); | |
211 | |
212 DisplayHitTestRegion* region = nullptr; | |
213 | |
214 region = ®ions[0]; | |
215 EXPECT_EQ(region->flags, kHitTestMine); | |
216 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
217 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 1024, 768)); | |
218 EXPECT_EQ(region->child_count, 2); | |
219 | |
220 region = ®ions[1]; | |
221 EXPECT_EQ(region->flags, kHitTestMine); | |
222 EXPECT_EQ(region->rect, gfx::Rect(100, 100, 200, 400)); | |
223 EXPECT_EQ(region->child_count, 0); | |
224 | |
225 region = ®ions[2]; | |
226 EXPECT_EQ(region->flags, kHitTestMine); | |
227 EXPECT_EQ(region->rect, gfx::Rect(400, 100, 300, 400)); | |
228 EXPECT_EQ(region->child_count, 0); | |
229 } | |
230 | |
231 // One embedder with two children. | |
232 // | |
233 // +e-------------+ | |
234 // | +c1-+ +c2--+ | | |
235 // | | | | | | | |
236 // | | | | | | | |
237 // | +---+ +----+ | | |
238 // +--------------+ | |
239 // | |
240 | |
241 TEST_F(HitTestAggregatorTest, OneEmbedderTwoChildren) { | |
242 EXPECT_EQ(count(), 0); | |
243 | |
244 cc::SurfaceId e_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
245 cc::SurfaceId c1_surface_id = MakeSurfaceId(kDisplayFrameSink, 2); | |
246 cc::SurfaceId c2_surface_id = MakeSurfaceId(kDisplayFrameSink, 3); | |
247 | |
248 auto e_hit_test_data = HitTestRegionList::New(); | |
249 e_hit_test_data->surface_id = e_surface_id; | |
250 e_hit_test_data->flags = kHitTestMine; | |
251 e_hit_test_data->bounds.SetRect(0, 0, 1024, 768); | |
252 | |
253 auto e_hit_test_region_c1 = HitTestRegion::New(); | |
254 e_hit_test_region_c1->flags = kHitTestChildSurface; | |
255 e_hit_test_region_c1->surface_id = c1_surface_id; | |
256 e_hit_test_region_c1->rect.SetRect(100, 100, 200, 300); | |
257 | |
258 auto e_hit_test_region_c2 = HitTestRegion::New(); | |
259 e_hit_test_region_c2->flags = kHitTestChildSurface; | |
260 e_hit_test_region_c2->surface_id = c2_surface_id; | |
261 e_hit_test_region_c2->rect.SetRect(400, 100, 400, 300); | |
262 | |
263 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_c1)); | |
264 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_c2)); | |
265 | |
266 auto c1_hit_test_data = HitTestRegionList::New(); | |
267 c1_hit_test_data->surface_id = c1_surface_id; | |
268 | |
269 auto c2_hit_test_data = HitTestRegionList::New(); | |
270 c2_hit_test_data->surface_id = c2_surface_id; | |
271 | |
272 // Submit in unexpected order. | |
273 | |
274 EXPECT_EQ(GetPendingCount(), 0); | |
275 | |
276 aggregator_.SubmitHitTestRegionList(std::move(c1_hit_test_data)); | |
277 EXPECT_EQ(GetPendingCount(), 1); | |
278 | |
279 aggregator_.SubmitHitTestRegionList(std::move(e_hit_test_data)); | |
280 EXPECT_EQ(GetPendingCount(), 2); | |
281 | |
282 aggregator_.SubmitHitTestRegionList(std::move(c2_hit_test_data)); | |
283 EXPECT_EQ(GetPendingCount(), 3); | |
284 | |
285 // Surfaces added to DisplayFrame in unexpected order. | |
286 | |
287 EXPECT_EQ(count(), 0); | |
288 | |
289 EXPECT_EQ(GetActiveCount(), 0); | |
290 | |
291 CallOnSurfaceWillDraw(c2_surface_id); | |
292 EXPECT_EQ(GetActiveCount(), 1); | |
293 | |
294 CallOnSurfaceWillDraw(c1_surface_id); | |
295 EXPECT_EQ(GetActiveCount(), 2); | |
296 | |
297 CallOnSurfaceWillDraw(e_surface_id); | |
298 EXPECT_EQ(GetActiveCount(), 3); | |
299 | |
300 // Aggregate and swap. | |
301 | |
302 aggregator_.Aggregate(e_surface_id); | |
303 EXPECT_EQ(count(), 0); | |
304 | |
305 aggregator_.Swap(); | |
306 | |
307 EXPECT_EQ(count(), 3); | |
308 | |
309 DisplayHitTestRegion* regions = GetRegions(); | |
310 | |
311 DisplayHitTestRegion* region = nullptr; | |
312 | |
313 region = ®ions[0]; | |
314 EXPECT_EQ(region->flags, kHitTestMine); | |
315 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
316 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 1024, 768)); | |
317 EXPECT_EQ(region->child_count, 2); | |
318 | |
319 region = ®ions[1]; | |
320 EXPECT_EQ(region->flags, kHitTestChildSurface); | |
321 EXPECT_EQ(region->frame_sink_id, c1_surface_id.frame_sink_id()); | |
322 EXPECT_EQ(region->rect, gfx::Rect(100, 100, 200, 300)); | |
323 EXPECT_EQ(region->child_count, 0); | |
324 | |
325 region = ®ions[2]; | |
326 EXPECT_EQ(region->flags, kHitTestChildSurface); | |
327 EXPECT_EQ(region->frame_sink_id, c2_surface_id.frame_sink_id()); | |
328 EXPECT_EQ(region->rect, gfx::Rect(400, 100, 400, 300)); | |
329 EXPECT_EQ(region->child_count, 0); | |
330 } | |
331 | |
332 // Occluded child frame ( OOPIF ). | |
333 // | |
334 // +e-----------+ | |
335 // | +c--+ | | |
336 // | | +div-+ | | |
337 // | | | | | | |
338 // | | +----+ | | |
339 // | +---+ | | |
340 // +------------+ | |
341 // | |
342 | |
343 TEST_F(HitTestAggregatorTest, OccludedChildFrame) { | |
344 EXPECT_EQ(count(), 0); | |
345 | |
346 cc::SurfaceId e_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
347 cc::SurfaceId c_surface_id = MakeSurfaceId(kDisplayFrameSink, 2); | |
348 | |
349 auto e_hit_test_data = HitTestRegionList::New(); | |
350 e_hit_test_data->surface_id = e_surface_id; | |
351 e_hit_test_data->flags = kHitTestMine; | |
352 e_hit_test_data->bounds.SetRect(0, 0, 1024, 768); | |
353 | |
354 auto e_hit_test_region_div = HitTestRegion::New(); | |
355 e_hit_test_region_div->flags = kHitTestMine; | |
356 e_hit_test_region_div->surface_id = e_surface_id; | |
357 e_hit_test_region_div->rect.SetRect(200, 200, 300, 200); | |
358 | |
359 auto e_hit_test_region_c = HitTestRegion::New(); | |
360 e_hit_test_region_c->flags = kHitTestChildSurface; | |
361 e_hit_test_region_c->surface_id = c_surface_id; | |
362 e_hit_test_region_c->rect.SetRect(100, 100, 200, 500); | |
363 | |
364 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_div)); | |
365 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_c)); | |
366 | |
367 auto c_hit_test_data = HitTestRegionList::New(); | |
368 c_hit_test_data->surface_id = c_surface_id; | |
369 c_hit_test_data->flags = kHitTestMine; | |
370 c_hit_test_data->bounds.SetRect(0, 0, 200, 500); | |
371 | |
372 // Submit in unexpected order. | |
373 | |
374 EXPECT_EQ(GetPendingCount(), 0); | |
375 | |
376 aggregator_.SubmitHitTestRegionList(std::move(c_hit_test_data)); | |
377 EXPECT_EQ(GetPendingCount(), 1); | |
378 | |
379 aggregator_.SubmitHitTestRegionList(std::move(e_hit_test_data)); | |
380 EXPECT_EQ(GetPendingCount(), 2); | |
381 | |
382 // Surfaces added to DisplayFrame in unexpected order. | |
383 | |
384 EXPECT_EQ(count(), 0); | |
385 | |
386 EXPECT_EQ(GetActiveCount(), 0); | |
387 | |
388 CallOnSurfaceWillDraw(e_surface_id); | |
389 EXPECT_EQ(GetActiveCount(), 1); | |
390 | |
391 CallOnSurfaceWillDraw(c_surface_id); | |
392 EXPECT_EQ(GetActiveCount(), 2); | |
393 | |
394 // Aggregate and swap. | |
395 | |
396 aggregator_.Aggregate(e_surface_id); | |
397 EXPECT_EQ(count(), 0); | |
398 | |
399 aggregator_.Swap(); | |
400 | |
401 EXPECT_EQ(count(), 3); | |
402 | |
403 DisplayHitTestRegion* regions = GetRegions(); | |
404 | |
405 DisplayHitTestRegion* region = nullptr; | |
406 | |
407 region = ®ions[0]; | |
408 EXPECT_EQ(region->flags, kHitTestMine); | |
409 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
410 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 1024, 768)); | |
411 EXPECT_EQ(region->child_count, 2); | |
412 | |
413 region = ®ions[1]; | |
414 EXPECT_EQ(region->flags, kHitTestMine); | |
415 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
416 EXPECT_EQ(region->rect, gfx::Rect(200, 200, 300, 200)); | |
417 EXPECT_EQ(region->child_count, 0); | |
418 | |
419 region = ®ions[2]; | |
420 EXPECT_EQ(region->flags, kHitTestChildSurface | kHitTestMine); | |
421 EXPECT_EQ(region->frame_sink_id, c_surface_id.frame_sink_id()); | |
422 EXPECT_EQ(region->rect, gfx::Rect(100, 100, 200, 500)); | |
423 EXPECT_EQ(region->child_count, 0); | |
424 } | |
425 | |
426 // Foreground child frame ( OOPIF ). | |
427 // Same as the previous test except the child is foreground. | |
428 // | |
429 // +e-----------+ | |
430 // | +c--+ | | |
431 // | | |div-+ | | |
432 // | | | | | | |
433 // | | |----+ | | |
434 // | +---+ | | |
435 // +------------+ | |
436 // | |
437 | |
438 TEST_F(HitTestAggregatorTest, ForegroundChildFrame) { | |
439 EXPECT_EQ(count(), 0); | |
440 | |
441 cc::SurfaceId e_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
442 cc::SurfaceId c_surface_id = MakeSurfaceId(kDisplayFrameSink, 2); | |
443 | |
444 auto e_hit_test_data = HitTestRegionList::New(); | |
445 e_hit_test_data->surface_id = e_surface_id; | |
446 e_hit_test_data->flags = kHitTestMine; | |
447 e_hit_test_data->bounds.SetRect(0, 0, 1024, 768); | |
448 | |
449 auto e_hit_test_region_div = HitTestRegion::New(); | |
450 e_hit_test_region_div->flags = kHitTestMine; | |
451 e_hit_test_region_div->surface_id = e_surface_id; | |
452 e_hit_test_region_div->rect.SetRect(200, 200, 300, 200); | |
453 | |
454 auto e_hit_test_region_c = HitTestRegion::New(); | |
455 e_hit_test_region_c->flags = kHitTestChildSurface; | |
456 e_hit_test_region_c->surface_id = c_surface_id; | |
457 e_hit_test_region_c->rect.SetRect(100, 100, 200, 500); | |
458 | |
459 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_c)); | |
460 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_div)); | |
461 | |
462 auto c_hit_test_data = HitTestRegionList::New(); | |
463 c_hit_test_data->surface_id = c_surface_id; | |
464 c_hit_test_data->flags = kHitTestMine; | |
465 c_hit_test_data->bounds.SetRect(0, 0, 200, 500); | |
466 | |
467 // Submit in unexpected order. | |
468 | |
469 EXPECT_EQ(GetPendingCount(), 0); | |
470 | |
471 aggregator_.SubmitHitTestRegionList(std::move(c_hit_test_data)); | |
472 EXPECT_EQ(GetPendingCount(), 1); | |
473 | |
474 aggregator_.SubmitHitTestRegionList(std::move(e_hit_test_data)); | |
475 EXPECT_EQ(GetPendingCount(), 2); | |
476 | |
477 // Surfaces added to DisplayFrame in unexpected order. | |
478 | |
479 EXPECT_EQ(count(), 0); | |
480 | |
481 EXPECT_EQ(GetActiveCount(), 0); | |
482 | |
483 CallOnSurfaceWillDraw(e_surface_id); | |
484 EXPECT_EQ(GetActiveCount(), 1); | |
485 | |
486 CallOnSurfaceWillDraw(c_surface_id); | |
487 EXPECT_EQ(GetActiveCount(), 2); | |
488 | |
489 // Aggregate and swap. | |
490 | |
491 aggregator_.Aggregate(e_surface_id); | |
492 EXPECT_EQ(count(), 0); | |
493 | |
494 aggregator_.Swap(); | |
495 | |
496 EXPECT_EQ(count(), 3); | |
497 | |
498 DisplayHitTestRegion* regions = GetRegions(); | |
499 | |
500 DisplayHitTestRegion* region = nullptr; | |
501 | |
502 region = ®ions[0]; | |
503 EXPECT_EQ(region->flags, kHitTestMine); | |
504 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
505 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 1024, 768)); | |
506 EXPECT_EQ(region->child_count, 2); | |
507 | |
508 region = ®ions[1]; | |
509 EXPECT_EQ(region->flags, kHitTestChildSurface | kHitTestMine); | |
510 EXPECT_EQ(region->frame_sink_id, c_surface_id.frame_sink_id()); | |
511 EXPECT_EQ(region->rect, gfx::Rect(100, 100, 200, 500)); | |
512 EXPECT_EQ(region->child_count, 0); | |
513 | |
514 region = ®ions[2]; | |
515 EXPECT_EQ(region->flags, kHitTestMine); | |
516 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
517 EXPECT_EQ(region->rect, gfx::Rect(200, 200, 300, 200)); | |
518 EXPECT_EQ(region->child_count, 0); | |
519 } | |
520 | |
521 // One embedder with a clipped child with a tab and transparent background. | |
522 // | |
523 // +e-------------+ | |
524 // | +c---------| Point maps to | |
525 // | 1 |+a--+ | ----- ------- | |
526 // | || 2 | 3 | 1 e | |
527 // | |+b--------| 2 a | |
528 // | || | 3 e ( transparent area in c ) | |
529 // | || 4 | 4 b | |
530 // +--------------+ | |
531 // | |
532 | |
533 TEST_F(HitTestAggregatorTest, ClippedChildWithTabAndTransparentBackground) { | |
534 EXPECT_EQ(count(), 0); | |
535 | |
536 cc::SurfaceId e_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
537 cc::SurfaceId c_surface_id = MakeSurfaceId(kDisplayFrameSink, 2); | |
538 cc::SurfaceId a_surface_id = MakeSurfaceId(kDisplayFrameSink, 3); | |
539 cc::SurfaceId b_surface_id = MakeSurfaceId(kDisplayFrameSink, 4); | |
540 | |
541 auto e_hit_test_data = HitTestRegionList::New(); | |
542 e_hit_test_data->surface_id = e_surface_id; | |
543 e_hit_test_data->flags = kHitTestMine; | |
544 e_hit_test_data->bounds.SetRect(0, 0, 1024, 768); | |
545 | |
546 auto e_hit_test_region_c = HitTestRegion::New(); | |
547 e_hit_test_region_c->flags = kHitTestChildSurface; | |
548 e_hit_test_region_c->surface_id = c_surface_id; | |
549 e_hit_test_region_c->rect.SetRect(200, 100, 1600, 800); | |
550 e_hit_test_region_c->transform.Translate(200, 100); | |
551 | |
552 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_c)); | |
553 | |
554 auto c_hit_test_data = HitTestRegionList::New(); | |
555 c_hit_test_data->surface_id = c_surface_id; | |
556 c_hit_test_data->flags = kHitTestIgnore; | |
557 c_hit_test_data->bounds.SetRect(0, 0, 1600, 800); | |
558 | |
559 auto c_hit_test_region_a = HitTestRegion::New(); | |
560 c_hit_test_region_a->flags = kHitTestChildSurface; | |
561 c_hit_test_region_a->surface_id = a_surface_id; | |
562 c_hit_test_region_a->rect.SetRect(0, 0, 200, 100); | |
563 | |
564 auto c_hit_test_region_b = HitTestRegion::New(); | |
565 c_hit_test_region_b->flags = kHitTestChildSurface; | |
566 c_hit_test_region_b->surface_id = b_surface_id; | |
567 c_hit_test_region_b->rect.SetRect(0, 100, 800, 600); | |
568 | |
569 c_hit_test_data->regions.push_back(std::move(c_hit_test_region_a)); | |
570 c_hit_test_data->regions.push_back(std::move(c_hit_test_region_b)); | |
571 | |
572 auto a_hit_test_data = HitTestRegionList::New(); | |
573 a_hit_test_data->surface_id = a_surface_id; | |
574 a_hit_test_data->flags = kHitTestMine; | |
575 a_hit_test_data->bounds.SetRect(0, 0, 200, 100); | |
576 | |
577 auto b_hit_test_data = HitTestRegionList::New(); | |
578 b_hit_test_data->surface_id = b_surface_id; | |
579 b_hit_test_data->flags = kHitTestMine; | |
580 b_hit_test_data->bounds.SetRect(0, 100, 800, 600); | |
581 | |
582 // Submit in unexpected order. | |
583 | |
584 EXPECT_EQ(GetPendingCount(), 0); | |
585 | |
586 aggregator_.SubmitHitTestRegionList(std::move(c_hit_test_data)); | |
587 EXPECT_EQ(GetPendingCount(), 1); | |
588 | |
589 aggregator_.SubmitHitTestRegionList(std::move(a_hit_test_data)); | |
590 EXPECT_EQ(GetPendingCount(), 2); | |
591 | |
592 aggregator_.SubmitHitTestRegionList(std::move(b_hit_test_data)); | |
593 EXPECT_EQ(GetPendingCount(), 3); | |
594 | |
595 aggregator_.SubmitHitTestRegionList(std::move(e_hit_test_data)); | |
596 EXPECT_EQ(GetPendingCount(), 4); | |
597 | |
598 // Surfaces added to DisplayFrame in unexpected order. | |
599 | |
600 EXPECT_EQ(count(), 0); | |
601 | |
602 EXPECT_EQ(GetActiveCount(), 0); | |
603 | |
604 CallOnSurfaceWillDraw(c_surface_id); | |
605 EXPECT_EQ(GetActiveCount(), 1); | |
606 | |
607 CallOnSurfaceWillDraw(e_surface_id); | |
608 EXPECT_EQ(GetActiveCount(), 2); | |
609 | |
610 CallOnSurfaceWillDraw(b_surface_id); | |
611 EXPECT_EQ(GetActiveCount(), 3); | |
612 | |
613 CallOnSurfaceWillDraw(a_surface_id); | |
614 EXPECT_EQ(GetActiveCount(), 4); | |
615 | |
616 // Aggregate and swap. | |
617 | |
618 aggregator_.Aggregate(e_surface_id); | |
619 EXPECT_EQ(count(), 0); | |
620 | |
621 aggregator_.Swap(); | |
622 | |
623 EXPECT_EQ(count(), 4); | |
624 | |
625 DisplayHitTestRegion* regions = GetRegions(); | |
626 | |
627 DisplayHitTestRegion* region = nullptr; | |
628 | |
629 region = ®ions[0]; | |
630 EXPECT_EQ(region->flags, kHitTestMine); | |
631 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
632 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 1024, 768)); | |
633 EXPECT_EQ(region->child_count, 3); | |
634 | |
635 region = ®ions[1]; | |
636 EXPECT_EQ(region->flags, kHitTestChildSurface | kHitTestIgnore); | |
637 EXPECT_EQ(region->frame_sink_id, c_surface_id.frame_sink_id()); | |
638 EXPECT_EQ(region->rect, gfx::Rect(200, 100, 1600, 800)); | |
639 EXPECT_EQ(region->child_count, 2); | |
640 | |
641 gfx::Point point(300, 300); | |
642 region->transform.TransformPointReverse(&point); | |
643 EXPECT_TRUE(point == gfx::Point(100, 200)); | |
644 | |
645 region = ®ions[2]; | |
646 EXPECT_EQ(region->flags, kHitTestChildSurface | kHitTestMine); | |
647 EXPECT_EQ(region->frame_sink_id, a_surface_id.frame_sink_id()); | |
648 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 200, 100)); | |
649 EXPECT_EQ(region->child_count, 0); | |
650 | |
651 region = ®ions[3]; | |
652 EXPECT_EQ(region->flags, kHitTestChildSurface | kHitTestMine); | |
653 EXPECT_EQ(region->frame_sink_id, b_surface_id.frame_sink_id()); | |
654 EXPECT_EQ(region->rect, gfx::Rect(0, 100, 800, 600)); | |
655 EXPECT_EQ(region->child_count, 0); | |
656 } | |
657 | |
658 // Three children deep. | |
659 // | |
660 // +e------------+ | |
661 // | +c1-------+ | | |
662 // | | +c2---+ | | | |
663 // | | | +c3-| | | | |
664 // | | | | | | | | |
665 // | | | +---| | | | |
666 // | | +-----+ | | | |
667 // | +---------+ | | |
668 // +-------------+ | |
669 // | |
670 | |
671 TEST_F(HitTestAggregatorTest, ThreeChildrenDeep) { | |
672 EXPECT_EQ(count(), 0); | |
673 | |
674 cc::SurfaceId e_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
675 cc::SurfaceId c1_surface_id = MakeSurfaceId(kDisplayFrameSink, 2); | |
676 cc::SurfaceId c2_surface_id = MakeSurfaceId(kDisplayFrameSink, 3); | |
677 cc::SurfaceId c3_surface_id = MakeSurfaceId(kDisplayFrameSink, 4); | |
678 | |
679 auto e_hit_test_data = HitTestRegionList::New(); | |
680 e_hit_test_data->surface_id = e_surface_id; | |
681 e_hit_test_data->flags = kHitTestMine; | |
682 e_hit_test_data->bounds.SetRect(0, 0, 1024, 768); | |
683 | |
684 auto e_hit_test_region_c1 = HitTestRegion::New(); | |
685 e_hit_test_region_c1->flags = kHitTestChildSurface; | |
686 e_hit_test_region_c1->surface_id = c1_surface_id; | |
687 e_hit_test_region_c1->rect.SetRect(100, 100, 700, 700); | |
688 | |
689 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_c1)); | |
690 | |
691 auto c1_hit_test_data = HitTestRegionList::New(); | |
692 c1_hit_test_data->surface_id = c1_surface_id; | |
693 c1_hit_test_data->flags = kHitTestMine; | |
694 c1_hit_test_data->bounds.SetRect(0, 0, 600, 600); | |
695 | |
696 auto c1_hit_test_region_c2 = HitTestRegion::New(); | |
697 c1_hit_test_region_c2->flags = kHitTestChildSurface; | |
698 c1_hit_test_region_c2->surface_id = c2_surface_id; | |
699 c1_hit_test_region_c2->rect.SetRect(100, 100, 500, 500); | |
700 | |
701 c1_hit_test_data->regions.push_back(std::move(c1_hit_test_region_c2)); | |
702 | |
703 auto c2_hit_test_data = HitTestRegionList::New(); | |
704 c2_hit_test_data->surface_id = c2_surface_id; | |
705 c2_hit_test_data->flags = kHitTestMine; | |
706 c2_hit_test_data->bounds.SetRect(0, 0, 400, 400); | |
707 | |
708 auto c2_hit_test_region_c3 = HitTestRegion::New(); | |
709 c2_hit_test_region_c3->flags = kHitTestChildSurface; | |
710 c2_hit_test_region_c3->surface_id = c3_surface_id; | |
711 c2_hit_test_region_c3->rect.SetRect(100, 100, 300, 300); | |
712 | |
713 c2_hit_test_data->regions.push_back(std::move(c2_hit_test_region_c3)); | |
714 | |
715 auto c3_hit_test_data = HitTestRegionList::New(); | |
716 c3_hit_test_data->surface_id = c3_surface_id; | |
717 c3_hit_test_data->flags = kHitTestMine; | |
718 c3_hit_test_data->bounds.SetRect(0, 0, 200, 200); | |
719 | |
720 // Submit in unexpected order. | |
721 | |
722 EXPECT_EQ(GetPendingCount(), 0); | |
723 | |
724 aggregator_.SubmitHitTestRegionList(std::move(c1_hit_test_data)); | |
725 EXPECT_EQ(GetPendingCount(), 1); | |
726 | |
727 aggregator_.SubmitHitTestRegionList(std::move(c3_hit_test_data)); | |
728 EXPECT_EQ(GetPendingCount(), 2); | |
729 | |
730 aggregator_.SubmitHitTestRegionList(std::move(e_hit_test_data)); | |
731 EXPECT_EQ(GetPendingCount(), 3); | |
732 | |
733 aggregator_.SubmitHitTestRegionList(std::move(c2_hit_test_data)); | |
734 EXPECT_EQ(GetPendingCount(), 4); | |
735 | |
736 // Surfaces added to DisplayFrame in unexpected order. | |
737 | |
738 EXPECT_EQ(count(), 0); | |
739 | |
740 EXPECT_EQ(GetActiveCount(), 0); | |
741 | |
742 CallOnSurfaceWillDraw(c2_surface_id); | |
743 EXPECT_EQ(GetActiveCount(), 1); | |
744 | |
745 CallOnSurfaceWillDraw(c1_surface_id); | |
746 EXPECT_EQ(GetActiveCount(), 2); | |
747 | |
748 CallOnSurfaceWillDraw(e_surface_id); | |
749 EXPECT_EQ(GetActiveCount(), 3); | |
750 | |
751 CallOnSurfaceWillDraw(c3_surface_id); | |
752 EXPECT_EQ(GetActiveCount(), 4); | |
753 | |
754 // Aggregate and swap. | |
755 | |
756 aggregator_.Aggregate(e_surface_id); | |
757 EXPECT_EQ(count(), 0); | |
758 | |
759 aggregator_.Swap(); | |
760 | |
761 EXPECT_EQ(count(), 4); | |
762 | |
763 DisplayHitTestRegion* regions = GetRegions(); | |
764 | |
765 DisplayHitTestRegion* region = nullptr; | |
766 | |
767 region = ®ions[0]; | |
768 EXPECT_EQ(region->flags, kHitTestMine); | |
769 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
770 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 1024, 768)); | |
771 EXPECT_EQ(region->child_count, 3); | |
772 | |
773 region = ®ions[1]; | |
774 EXPECT_EQ(region->flags, kHitTestChildSurface | kHitTestMine); | |
775 EXPECT_EQ(region->frame_sink_id, c1_surface_id.frame_sink_id()); | |
776 EXPECT_EQ(region->rect, gfx::Rect(100, 100, 700, 700)); | |
777 EXPECT_EQ(region->child_count, 2); | |
778 | |
779 region = ®ions[2]; | |
780 EXPECT_EQ(region->flags, kHitTestChildSurface | kHitTestMine); | |
781 EXPECT_EQ(region->frame_sink_id, c2_surface_id.frame_sink_id()); | |
782 EXPECT_EQ(region->rect, gfx::Rect(100, 100, 500, 500)); | |
783 EXPECT_EQ(region->child_count, 1); | |
784 | |
785 region = ®ions[3]; | |
786 EXPECT_EQ(region->flags, kHitTestChildSurface | kHitTestMine); | |
787 EXPECT_EQ(region->frame_sink_id, c3_surface_id.frame_sink_id()); | |
788 EXPECT_EQ(region->rect, gfx::Rect(100, 100, 300, 300)); | |
789 EXPECT_EQ(region->child_count, 0); | |
790 } | |
791 | |
792 // Missing / late child. | |
793 // | |
794 // +e-----------+ | |
795 // | +c--+ | | |
796 // | | |div-+ | | |
797 // | | | | | | |
798 // | | |----+ | | |
799 // | +---+ | | |
800 // +------------+ | |
801 // | |
802 | |
803 TEST_F(HitTestAggregatorTest, MissingChildFrame) { | |
804 EXPECT_EQ(count(), 0); | |
805 | |
806 cc::SurfaceId e_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
807 cc::SurfaceId c_surface_id = MakeSurfaceId(kDisplayFrameSink, 2); | |
808 | |
809 auto e_hit_test_data = HitTestRegionList::New(); | |
810 e_hit_test_data->surface_id = e_surface_id; | |
811 e_hit_test_data->flags = kHitTestMine; | |
812 e_hit_test_data->bounds.SetRect(0, 0, 1024, 768); | |
813 | |
814 auto e_hit_test_region_div = HitTestRegion::New(); | |
815 e_hit_test_region_div->flags = kHitTestMine; | |
816 e_hit_test_region_div->surface_id = e_surface_id; | |
817 e_hit_test_region_div->rect.SetRect(200, 200, 300, 200); | |
818 | |
819 auto e_hit_test_region_c = HitTestRegion::New(); | |
820 e_hit_test_region_c->flags = kHitTestChildSurface; | |
821 e_hit_test_region_c->surface_id = c_surface_id; | |
822 e_hit_test_region_c->rect.SetRect(100, 100, 200, 500); | |
823 | |
824 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_c)); | |
825 e_hit_test_data->regions.push_back(std::move(e_hit_test_region_div)); | |
826 | |
827 auto c_hit_test_data = HitTestRegionList::New(); | |
828 c_hit_test_data->surface_id = c_surface_id; | |
829 c_hit_test_data->flags = kHitTestMine; | |
830 c_hit_test_data->bounds.SetRect(0, 0, 200, 500); | |
831 | |
832 // Submit in unexpected order, but not the child. | |
833 | |
834 EXPECT_EQ(GetPendingCount(), 0); | |
835 | |
836 aggregator_.SubmitHitTestRegionList(std::move(e_hit_test_data)); | |
837 EXPECT_EQ(GetPendingCount(), 1); | |
838 | |
839 // Surfaces added to DisplayFrame in unexpected order. | |
840 | |
841 EXPECT_EQ(count(), 0); | |
842 | |
843 EXPECT_EQ(GetActiveCount(), 0); | |
844 | |
845 CallOnSurfaceWillDraw(e_surface_id); | |
846 EXPECT_EQ(GetActiveCount(), 1); | |
847 | |
848 // Aggregate and swap. | |
849 | |
850 aggregator_.Aggregate(e_surface_id); | |
851 EXPECT_EQ(count(), 0); | |
852 | |
853 aggregator_.Swap(); | |
854 | |
855 EXPECT_EQ(count(), 2); | |
856 | |
857 DisplayHitTestRegion* regions = GetRegions(); | |
858 | |
859 DisplayHitTestRegion* region = nullptr; | |
860 | |
861 region = ®ions[0]; | |
862 EXPECT_EQ(region->flags, kHitTestMine); | |
863 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
864 EXPECT_EQ(region->rect, gfx::Rect(0, 0, 1024, 768)); | |
865 EXPECT_EQ(region->child_count, 1); | |
866 | |
867 // Child would exist here but it was not included in the Display Frame. | |
868 | |
869 region = ®ions[1]; | |
870 EXPECT_EQ(region->flags, kHitTestMine); | |
871 EXPECT_EQ(region->frame_sink_id, e_surface_id.frame_sink_id()); | |
872 EXPECT_EQ(region->rect, gfx::Rect(200, 200, 300, 200)); | |
873 EXPECT_EQ(region->child_count, 0); | |
874 } | |
875 | |
876 // Exceed limits to ensure that bounds and resize work. | |
877 // | |
878 // A tree of embedders each with 8 children and 4 levels deep = 4096 regions. | |
879 // This will exceed initial allocation and force a resize. | |
880 // | |
881 // +e--------------------------------------------------------+ | |
882 // | +c1----------++c2----------++c3----------++c4----------+| | |
883 // | | +c1--------|| +c1--------|| +c1--------|| +c1--------|| | |
884 // | | | +c1-++c2-|| | +c1-++c2-|| | +c1-++c2-|| | +c1-++c2-|| | |
885 // | | | | || || | | || || | | || || | | || || | |
886 // | | | +---++---|| | +---++---|| | +---++---|| | +---++---|| | |
887 // | +------------++------------++------------++------------+| | |
888 // | +c5----------++c6----------++c7----------++c8----------+| | |
889 // | | +c1--------|| +c1--------|| +c1--------|| +c1--------|| | |
890 // | | | +c1-++c2-|| | +c1-++c2-|| | +c1-++c2-|| | +c1-++c2-|| | |
891 // | | | | || || | | || || | | || || | | || || | |
892 // | | | +---++---|| | +---++---|| | +---++---|| | +---++---|| | |
893 // | +------------++------------++------------++------------+| | |
894 // +---------------------------------------------------------+ | |
895 // | |
896 | |
897 TEST_F(HitTestAggregatorTest, ExceedLimits) { | |
898 EXPECT_EQ(count(), 0); | |
899 | |
900 EXPECT_LT(GetDisplayHitTestRegionListSize(), 4096); | |
901 | |
902 cc::SurfaceId display_surface_id = MakeSurfaceId(kDisplayFrameSink, 1); | |
903 | |
904 int next_surface_id = CreateAndSubmitHitTestRegionListWith8Children(1, 3); | |
905 int surface_count = next_surface_id - 1; | |
906 | |
907 EXPECT_EQ(GetPendingCount(), surface_count); | |
908 | |
909 // Mark Surfaces as added to DisplayFrame in unexpected order. | |
910 | |
911 EXPECT_EQ(count(), 0); | |
912 EXPECT_EQ(GetActiveCount(), 0); | |
913 | |
914 for (int i = 1; i <= surface_count; i++) { | |
915 cc::SurfaceId surface_id = MakeSurfaceId(kDisplayFrameSink, i); | |
916 CallOnSurfaceWillDraw(surface_id); | |
917 } | |
918 | |
919 EXPECT_EQ(GetActiveCount(), surface_count); | |
920 | |
921 // Aggregate and swap. | |
922 aggregator_.Aggregate(display_surface_id); | |
923 EXPECT_EQ(count(), 0); | |
924 | |
925 aggregator_.Swap(); | |
926 | |
927 // Expect 4680 regions: | |
928 // 8 children 4 levels deep 8*8*8*8 is 4096 | |
929 // 1 region for each embedder/surface + 584 | |
930 // 1 root + 1 | |
931 // ----- | |
932 // 4681. | |
933 EXPECT_EQ(count(), 4681); | |
934 | |
935 EXPECT_GE(GetDisplayHitTestRegionListSize(), 4681); | |
936 } | |
937 | |
938 } // namespace test | |
939 } // namespace hit_test | |
940 } // namespace viz | |
OLD | NEW |