Skip to content

feature: Add on-demand getters/methods for scroll position (offset) and max_scroll_extent in ListView #6575

@Iaw4tch

Description

@Iaw4tch

Duplicate Check

Describe the requested feature

Currently, if I need to know current scroll position (pixels) or its max value (max_scroll_extent) of ListView, the only way to do this is to track on_scroll: there's where a huge problem rises.

If I want to get these variables for the first time, i need a user to trigger the event or do it programmatically with scroll_to method. Moreover even with that you need to listen to this event all the time, save needed to the local variables and constantly synchronize them. It complicates the logic and loads the app with intermediate events.

Suggest a solution

The solution is quite simple: make an asynchronous getter/method of ListView that returns scroll offset or max extent.

Screenshots

No response

Additional details

I am creating a custom class InertiaListView (a wrapper of GestureDetector), which allows to drag ListView up and down with inertia on_pan_end.

class InertiaListView(ft.GestureDetector):
    def __init__(
        self,
        controls: list[ft.Control],
        smoothness_time: float = 0.00001,
        inertia_duration: float = 1,
        stop_velocity: float = 30,
        expand: bool | int | None = None,
        alignment: ft.Alignment | None = None,
    ):
        ...
        self._list_view = ft.ListView(
            spacing=10,
            scroll=ft.ScrollMode.AUTO,
            on_scroll=self._on_scroll,
            animate_offset=ft.Animation(duration=0),
            controls=controls,
        )


        super().__init__(
            expand=expand,
            on_pan_start=self._on_pan_start,
            on_pan_update=self._on_pan_update,
            on_pan_end=self._on_pan_end,
            content=ft.Container(
                expand=True,
                alignment=alignment,
                content=self._list_view,
            ),
        )

        self._max_offset: float = 0.01
        self._current_offset: float = 0

    def _on_scroll(self, e: ft.OnScrollEvent):
        if self._max_offset != e.max_scroll_extent:
            self._max_offset = e.max_scroll_extent if e.max_scroll_extent != 0 else 0.01

        self._current_offset = e.pixels

I need self._current_offset for the safety in the mismatch of my variable, and the true one.

self._max_offset is used to track the bounds of the offset:

def _clamp_offset(self, offset: float):
    if not 0 <= offset <= self._max_offset:
        self._velocity = 0

    return max(0.0, min(offset, self._max_offset))

My code would become cleaner if there was an option to asynchronously get the these ListView properties.

Metadata

Metadata

Assignees

No one assigned

    Labels

    feature requestSuggestion/Request for additional feature

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions