Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ScrollView not triggering overscroll effects when content is the same size as scroller #8644

Open
snuq opened this issue Mar 12, 2024 · 0 comments

Comments

@snuq
Copy link
Contributor

snuq commented Mar 12, 2024

Software Versions

  • Python: 3.10.9
  • OS: Windows 10
  • Kivy: 2.2.1
  • Kivy installation method: PIP

Describe the bug
When a ScrollView's content is the same height as itself, overscroll effects are never triggered, even if always_overscroll is set to True.
This blocks some functionality like a nested ScrollView not triggering its parent's scrolling (as normally happens when overscroll is enabled).

Expected behavior
The content should utilize the effect_cls to position itself to some degree, just as it does when content height does not match scrollview height

To Reproduce
This example illustrates the issue: dragging the button up/down does not scroll the outer scrollview, but if the height of the button is set to self.parent.height+1, it will.

from kivy.app import App
from kivy.lang.builder import Builder
KV = """
ScrollView:
    do_scroll_y: True
    BoxLayout:
        orientation: 'vertical'
        size_hint_y: None
        height: 1000
        Widget:
        ScrollView:
            Button:
                text: 'Inner scrollview content'
                size_hint_y: None
                height: self.parent.height
        Widget:
"""

class Test(App):
    def build(self):
        return Builder.load_string(KV)

Test().run()

Proposed Solution
the '_update_effect_y()' and '_update_effect_x()' functions of ScrollView should be updated to better handle this edge case, for instance, a simple addition like setting sh to a small number instead of 0 like:

    def _update_effect_y(self, *args):
        vp = self._viewport
        if not vp or not self.effect_y:
            return
        if self.effect_y.is_manual:
            sh = vp.height - self._effect_y_start_height
        else:
            sh = vp.height - self.height

        if sh < 1 and not (self.always_overscroll and self.do_scroll_y):
            return
        if sh != 0:
            sy = self.effect_y.scroll / sh
            self.scroll_y = -sy
        else:
            self.scroll_y = 1 - self.effect_y.scroll
        self._trigger_update_from_scroll()

resolves the issue and allows for overscroll effects

edit:
changed the proposed solution to not cause a bug where scrolling position was set to the bottom sometimes

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant