Skip to content

showOnScreen doesn't trigger scroll if item is already fully on screen - #17729

Merged
goderbauer merged 5 commits into
flutter:masterfrom
goderbauer:showOnScreen
May 21, 2018
Merged

goderbauer merged 5 commits into
flutter:masterfrom
goderbauer:showOnScreen

Conversation

@goderbauer

Copy link
Copy Markdown
Member

Fixes #11663.

@gspencergoog

Copy link
Copy Markdown
Contributor

32384589-a60f0e74-c078-11e7-9bc1-e5b5287aea9d

// TODO(goderbauer): Don't scroll if that puts us outside of viewport's bounds.
if ((currentOffset - leadingEdgeOffset).abs() < (currentOffset - trailingEdgeOffset).abs()) {

if (currentOffset > leadingEdgeOffset && currentOffset > trailingEdgeOffset) {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can you assert leadingEdgeOffset <= trailingEdgeOffset?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, but I can guarantee it the other way around: leadingEdgeOffset >= trailingEdgeOffset :)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(really? that's surprising)

in that case, assert that then simplify the expressions

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To get a list item to the leading edge (as opposed to the trailing edge) you have to scroll further, therefore leadingEdgeOffset >= trailingEdgeOffset, no?

Will simplify expression.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In a regular vertically scrolling list, the leading edge is above the trailing edge, so you get it first (lower scroll offset) than the trailing edge (higher scroll offset) unless I'm missing something?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To ensure that we talk about the same thing I have drawn up two diagrams: Both show a long scrollable list (on the left) that scrolls through the viewport window (on the right in yellow).

In the first picture, the list item in question is shown at the leading edge of the viewport. I'd argue that the scrollOffset here is 600, which is called the leadingEdgeOffset in the code.

img-1935

Now, let's move the list item in question to the trailing edge of the viewport. I'd argue that in this picture the scrollOffset is 350, which is called the trailingEdgeOffset in the code.

img-1937

So, now I would argue that 600 > 350. And therefore (even though this is by now means a full mathematically proof), it seems that leadingEdgeOffset >= trailingEdgeOffset holds.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ah, yup, i was missing something. :-)

offset.jumpTo(leadingEdgeOffset);
} else {
} else if (currentOffset < leadingEdgeOffset && currentOffset < trailingEdgeOffset ) {
offset.jumpTo(trailingEdgeOffset);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

any chance we can factor the common code into the base class?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've looked into doing that before and there is no good common ancestor for this...

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

create a common mixin (RenderViewportShowOnScreenMixin) or make a static method on some class (RenderViewportBase.showChildInViewport or some such) and use that.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Mixin doesn't work (or gets awkward because of the super call in the method. I changed it to a static method.

expect(scrollController.offset, kItemHeight / 2);

semantics.dispose();
});

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we should test that this works with negative-scroll-offset children too

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good idea. Added.

@Hixie

Hixie commented May 21, 2018

Copy link
Copy Markdown
Contributor

LGTM

@goderbauer
goderbauer merged commit 7471ff8 into flutter:master May 21, 2018
@goderbauer
goderbauer deleted the showOnScreen branch May 21, 2018 23:33
@goderbauer goderbauer added framework flutter/packages/flutter repository. See also f: labels. a: accessibility Accessibility, e.g. VoiceOver or TalkBack. (aka a11y) f: scrolling Viewports, list views, slivers, etc. labels Feb 22, 2019
@github-actions github-actions Bot locked as resolved and limited conversation to collaborators Aug 7, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

a: accessibility Accessibility, e.g. VoiceOver or TalkBack. (aka a11y) f: scrolling Viewports, list views, slivers, etc. framework flutter/packages/flutter repository. See also f: labels.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

showOnScreen / getOffsetToReveal doesn't take status bar into consideration

4 participants