From 66a6726306566628da1768bbdf5291bb11a10019 Mon Sep 17 00:00:00 2001 From: Greg Spencer Date: Thu, 9 May 2019 12:25:52 -0700 Subject: [PATCH] Fix benchmark regression in layer.find(Offset) (#32425) This fixes a benchmark regression introduced in #32350. The performance is improved by just reverting the Layer.find routines to use their old definitions, instead of defining them in terms of the findAll lazy iterators. Fixes #32387 --- packages/flutter/lib/src/rendering/layer.dart | 75 ++++++++++++------- 1 file changed, 46 insertions(+), 29 deletions(-) diff --git a/packages/flutter/lib/src/rendering/layer.dart b/packages/flutter/lib/src/rendering/layer.dart index 38a942d0fd6..5ad0e2e7fca 100644 --- a/packages/flutter/lib/src/rendering/layer.dart +++ b/packages/flutter/lib/src/rendering/layer.dart @@ -634,11 +634,15 @@ class ContainerLayer extends Layer { @override S find(Offset regionOffset) { - final Iterable all = findAll(regionOffset); - if (all.isEmpty) { - return null; + Layer current = lastChild; + while (current != null) { + final Object value = current.find(regionOffset); + if (value != null) { + return value; + } + current = current.previousSibling; } - return all.first; + return null; } @override @@ -1263,26 +1267,31 @@ class TransformLayer extends OffsetLayer { return null; // this does not return an engine layer yet. } - @override - S find(Offset regionOffset) { - final Iterable all = findAll(regionOffset); - if (all.isEmpty) { - return null; - } - return all.first; - } - - @override - Iterable findAll(Offset regionOffset) sync* { + Offset _transformOffset(Offset regionOffset) { if (_inverseDirty) { _invertedTransform = Matrix4.tryInvert(transform); _inverseDirty = false; } if (_invertedTransform == null) - return; + return null; final Vector4 vector = Vector4(regionOffset.dx, regionOffset.dy, 0.0, 1.0); final Vector4 result = _invertedTransform.transform(vector); - yield* super.findAll(Offset(result[0], result[1])); + return Offset(result[0], result[1]); + } + + @override + S find(Offset regionOffset) { + final Offset transformedOffset = _transformOffset(regionOffset); + return transformedOffset == null ? null : super.find(transformedOffset); + } + + @override + Iterable findAll(Offset regionOffset) sync* { + final Offset transformedOffset = _transformOffset(regionOffset); + if (transformedOffset == null) { + return; + } + yield* super.findAll(transformedOffset); } @override @@ -1588,11 +1597,9 @@ class PhysicalModelLayer extends ContainerLayer { @override S find(Offset regionOffset) { - final Iterable all = findAll(regionOffset); - if (all.isEmpty) { + if (!clipPath.contains(regionOffset)) return null; - } - return all.first; + return super.find(regionOffset); } @override @@ -1844,11 +1851,11 @@ class FollowerLayer extends ContainerLayer { @override S find(Offset regionOffset) { - final Iterable all = findAll(regionOffset); - if (all.isEmpty) { - return null; + if (link.leader == null) { + return showWhenUnlinked ? super.find(regionOffset - unlinkedOffset) : null; } - return all.first; + final Offset transformedOffset = _transformOffset(regionOffset); + return transformedOffset == null ? null : super.find(transformedOffset); } @override @@ -1856,7 +1863,11 @@ class FollowerLayer extends ContainerLayer { if (link.leader == null) { return showWhenUnlinked ? super.findAll(regionOffset - unlinkedOffset) : []; } - return super.findAll(_transformOffset(regionOffset)); + final Offset transformedOffset = _transformOffset(regionOffset); + if (transformedOffset == null) { + return []; + } + return super.findAll(transformedOffset); } /// The transform that was used during the last composition phase. @@ -2031,11 +2042,17 @@ class AnnotatedRegionLayer extends ContainerLayer { @override S find(Offset regionOffset) { - final Iterable all = findAll(regionOffset); - if (all.isEmpty) { + final S result = super.find(regionOffset); + if (result != null) + return result; + if (size != null && !(offset & size).contains(regionOffset)) return null; + if (T == S) { + final Object untypedResult = value; + final S typedResult = untypedResult; + return typedResult; } - return all.first; + return super.find(regionOffset); } @override