Closed Bug 1962355 Opened 1 year ago Closed 3 months ago

Synthesizing wheel (and maybe touch) scroll limits values for deltaX and deltaY to the scollable element's viewport

Categories

(Remote Protocol :: Agent, defect, P3)

defect

Tracking

(firefox149 fixed)

RESOLVED FIXED
149 Branch
Tracking Status
firefox149 --- fixed

People

(Reporter: whimboo, Assigned: hiro)

References

(Blocks 1 open bug)

Details

(Whiteboard: [webdriver:m19][webdriver:external][webdriver:relnote])

Attachments

(2 files, 1 obsolete file)

While working on async (widget) wheel events, I noticed that Firefox internally caps the deltaX and deltaY values (at least for wheel scrolling) to the size of the scrollable element's visible viewport.

In contrast, Chrome does not apply such a cap and allows a single scroll action with large delta values. The following test demonstrates the difference:

def test_scroll_more_than_a_page(session, test_actions_scroll_page, wheel_chain):
    frame = session.find.css("#iframe", all=False)
    session.switch_frame(frame)

    target = session.find.css("div", all=False)
    wheel_chain.scroll(0, 0, 5, 3000, origin=target).perform()

    session.switch_frame(None)

    def wait_for_events(_):
        return len(get_events(session)) > 0

    Poll(session, timeout=0.5, interval=0.01,
         message='No wheel events found').until(wait_for_events)

    events = get_events(session)
    assert len(events) == 1
    assert events[0]["type"] == "wheel"
    assert events[0]["deltaX"] == 5
    assert events[0]["deltaY"] == 3000
    assert events[0]["deltaZ"] == 0
    assert events[0]["target"] == "iframeContent"

    # Allow some time for scrollTop to be updated
    import time
    time.sleep(1)

    session.switch_frame(frame)
    root = session.find.css(":root", all=False)
    assert root.property('scrollTop') == 3000

This test tries to scroll a div inside an iframe vertically by 3000px using a single wheel event. While the event emitted in Firefox shows a deltaY of 3000, the resulting scrollTop of the root element only reaches 77px, due to most of the iframe being outside the visible viewport.

Running the same test in Chrome passes as expected: the scroll action is performed in full, and only one wheel event is emitted.

As Botond pointed out, this capping behavior is intentional in both the APZ and the legacy event synthesizing code. One proposed solution is to internally emit multiple wheel events to cover the requested scroll distance. However, doing so would likely result in more events than other browsers emit in the same situation, potentially leading to cross-browser compatibility issues.

A workaround for now would be to use the duration argument of the scroll action which will divide the full distance into smaller parts and execute once per animation frame. But this also results in multiple wheel events.

Would I be right to say that, since the DOM event codepath observes this limit as well, this is a pre-existing issue and thus not a regression from or a blocker for the project to switch to using widget events?

If we wanted to change this, that would be possible, but it would require a bit of plumbing, as we'd need to plumb the information that a given event is coming from WebDriver, to the places where these checks are implemented, so we can follow different rules for them.

Before doing that, I wonder if it would make sense to raise this as a spec issue first: if the intention is to simulate input events provided by a user, it would make sense to make those events "realistic", i.e. similar to what a real hardware device would produce. Such events would not run into this limit because e.g. a touchpad is going to generate many events with small deltas over the course of a touchpad swipe, rather than a single event with a large delta.

Whiteboard: [webdriver:triage]

(In reply to Botond Ballo [:botond] from comment #1)

Would I be right to say that, since the DOM event codepath observes this limit as well, this is a pre-existing issue and thus not a regression from or a blocker for the project to switch to using widget events?

I would say so, yes.

Before doing that, I wonder if it would make sense to raise this as a spec issue first: if the intention is to simulate input events provided by a user, it would make sense to make those events "realistic", i.e. similar to what a real hardware device would produce. Such events would not run into this limit because e.g. a touchpad is going to generate many events with small deltas over the course of a touchpad swipe, rather than a single event with a large delta.

We will discuss it in our internal triage meeting today.

The severity field is not set for this bug.
:whimboo, could you have a look please?

For more information, please visit BugBot documentation.

Flags: needinfo?(hskupin)
Flags: needinfo?(hskupin)
Whiteboard: [webdriver:triage]
Severity: -- → S3
Flags: needinfo?(hskupin)
Priority: -- → P3
Blocks: 2013447

Henrik, I am unsure whether you've been aware of a mention to you in https://phabricator.services.mozilla.com/D281119#9753177 (which is for bug 2013447), so I am setting NI to you here. Botond and I wonder the conclusion of the discussion in comment 2. Thanks!

Hm, this is strange. I've taken a look at our internal notes but I cannot find comments about this bug and I also only removed the triage flag on 26th of May last year. I cannot remember what we discussed but the fact that Chrome doesn't cap the maximum value for the scrolling we should follow that behavior. Note that in the WebDriver specification we do not mention that automation should limit the deltaX and deltaY values.

Also when the perform action command is called for wheel scrolling and a duration > 0 is given we are going to automatically split the scroll into x-number of scroll events (per 16ms). Maybe there are cases that we won't be able to mimic as what a real device is capable to do?

Flags: needinfo?(hskupin)
Assignee: nobody → hikezoe.birchill
Status: NEW → ASSIGNED
Pushed by hikezoe.birchill@mozilla.com: https://github.com/mozilla-firefox/firefox/commit/d828cf5e65df https://hg.mozilla.org/integration/autoland/rev/d5db9df094ce Add a pref to allow scroll amount larger than a page on a single wheel event. r=botond https://github.com/mozilla-firefox/firefox/commit/22f81a3280a1 https://hg.mozilla.org/integration/autoland/rev/5a30cbc9e9f7 Set mousewheel.allow_scrolling_more_than_one_page for web-platform tests. r=whimboo
Status: ASSIGNED → RESOLVED
Closed: 3 months ago
Resolution: --- → FIXED
Target Milestone: --- → 149 Branch
Blocks: 2014665
Whiteboard: [webdriver:m19][webdriver:external]
Duplicate of this bug: 2011658
Whiteboard: [webdriver:m19][webdriver:external] → [webdriver:m19][webdriver:external][webdriver:relnote]

Comment on attachment 9569230 [details]
Bug 1962355 - Reset recommended prefs on xpcom-shutdown. r=whimboo

Revision D293842 was moved to bug 2028422. Setting attachment 9569230 [details] to obsolete.

Attachment #9569230 - Attachment is obsolete: true
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: