@@ -4,9 +4,12 @@ import 'package:checks/checks.dart';
4
4
import 'package:collection/collection.dart' ;
5
5
import 'package:flutter/foundation.dart' ;
6
6
import 'package:flutter/gestures.dart' ;
7
- import 'package:flutter/rendering.dart' ;
8
- import 'package:flutter/widgets.dart' ;
7
+ // ignore: undefined_hidden_name // anticipates https://github.com/flutter/flutter/pull/164818
8
+ import 'package:flutter/rendering.dart' hide SliverPaintOrder;
9
+ // ignore: undefined_hidden_name // anticipates https://github.com/flutter/flutter/pull/164818
10
+ import 'package:flutter/widgets.dart' hide SliverPaintOrder;
9
11
import 'package:flutter_test/flutter_test.dart' ;
12
+ import 'package:zulip/widgets/scrolling.dart' ;
10
13
import 'package:zulip/widgets/sticky_header.dart' ;
11
14
12
15
void main () {
@@ -230,19 +233,24 @@ void main() {
230
233
});
231
234
232
235
testWidgets ('hit-testing for header overflowing sliver' , (tester) async {
236
+ const centerKey = ValueKey ('center' );
233
237
final controller = ScrollController ();
234
238
await tester.pumpWidget (Directionality (textDirection: TextDirection .ltr,
235
- child: CustomScrollView (
239
+ child: CustomPaintOrderScrollView (
236
240
controller: controller,
241
+ anchor: 0.0 ,
242
+ center: centerKey,
243
+ paintOrder: SliverPaintOrder .firstIsTop,
237
244
slivers: [
238
245
SliverStickyHeaderList (
239
246
headerPlacement: HeaderPlacement .scrollingStart,
240
247
delegate: SliverChildListDelegate (
241
248
List .generate (100 , (i) => StickyHeaderItem (
242
249
allowOverflow: true ,
243
- header: _Header (i, height: 20 ),
244
- child: _Item (i, height: 100 ))))),
250
+ header: _Header (99 - i, height: 20 ),
251
+ child: _Item (99 - i, height: 100 ))))),
245
252
SliverStickyHeaderList (
253
+ key: centerKey,
246
254
headerPlacement: HeaderPlacement .scrollingStart,
247
255
delegate: SliverChildListDelegate (
248
256
List .generate (100 , (i) => StickyHeaderItem (
@@ -251,9 +259,8 @@ void main() {
251
259
child: _Item (100 + i, height: 100 ))))),
252
260
])));
253
261
254
- const topExtent = 100 * 100 ;
255
262
for (double topHeight in [5 , 10 , 15 , 20 ]) {
256
- controller.jumpTo (topExtent - topHeight);
263
+ controller.jumpTo (- topHeight);
257
264
await tester.pump ();
258
265
// The top sliver occupies height [topHeight].
259
266
// Its header overhangs by `20 - topHeight`.
@@ -327,49 +334,34 @@ Future<void> _checkSequence(
327
334
];
328
335
329
336
final double anchor;
330
- bool paintOrderGood;
331
337
if (reverseGrowth) {
332
338
slivers.reverseRange (0 , slivers.length);
333
339
anchor = 1.0 ;
334
- paintOrderGood = switch (sliverConfig) {
335
- _SliverConfig .single => true ,
336
- // The last sliver will paint last.
337
- _SliverConfig .backToBack => headerPlacement == HeaderPlacement .scrollingEnd,
338
- // The last sliver will paint last.
339
- _SliverConfig .followed => headerPlacement == HeaderPlacement .scrollingEnd,
340
- };
341
340
} else {
342
341
anchor = 0.0 ;
343
- paintOrderGood = switch (sliverConfig) {
344
- _SliverConfig .single => true ,
345
- // The last sliver will paint last.
346
- _SliverConfig .backToBack => headerPlacement == HeaderPlacement .scrollingEnd,
347
- // The first sliver will paint last.
348
- _SliverConfig .followed => headerPlacement == HeaderPlacement .scrollingStart,
349
- };
350
342
}
351
343
352
- final skipBecausePaintOrder = allowOverflow && ! paintOrderGood ;
353
- if (skipBecausePaintOrder ) {
354
- // TODO need to control paint order of slivers within viewport in order to
355
- // make some configurations behave properly when headers overflow slivers
356
- markTestSkipped ( 'sliver paint order' );
357
- // Don't return yet; we'll still check layout, and skip specific affected checks below.
344
+ SliverPaintOrder paintOrder = SliverPaintOrder .centerTopFirstBottom ;
345
+ if (! allowOverflow || (sliverConfig == _SliverConfig .single) ) {
346
+ // The paint order doesn't matter.
347
+ } else {
348
+ paintOrder = headerPlacement == HeaderPlacement .scrollingStart
349
+ ? SliverPaintOrder .firstIsTop : SliverPaintOrder .lastIsTop;
358
350
}
359
351
360
-
361
352
final controller = ScrollController ();
362
353
await tester.pumpWidget (Directionality (
363
354
textDirection: textDirection ?? TextDirection .rtl,
364
- child: CustomScrollView (
355
+ child: CustomPaintOrderScrollView (
365
356
controller: controller,
366
357
scrollDirection: axis,
367
358
reverse: reverse,
368
359
anchor: anchor,
369
360
center: center,
361
+ paintOrder: paintOrder,
370
362
slivers: slivers)));
371
363
372
- final overallSize = tester.getSize (find.byType ( CustomScrollView ));
364
+ final overallSize = tester.getSize (find.bySubtype < CustomScrollView >( ));
373
365
final extent = overallSize.onAxis (axis);
374
366
assert (extent % 100 == 0 );
375
367
assert (sliverScrollExtent - extent > 100 );
@@ -418,7 +410,6 @@ Future<void> _checkSequence(
418
410
check (insetExtent (find.byType (_Header ))).equals (expectedHeaderInsetExtent);
419
411
420
412
// Check the header gets hit when it should, and not when it shouldn't.
421
- if (skipBecausePaintOrder) return ;
422
413
await tester.tapAt (headerInset (1 ));
423
414
await tester.tapAt (headerInset (expectedHeaderInsetExtent - 1 ));
424
415
check (_TapLogged .takeTapLog ())..length.equals (2 )
0 commit comments