Duplicate Check
Describe the bug
The onInteractionUpdate event of the InteractiveViewer widget returns incorrect data. When the inner content is scaled to its minimum or maximum limit, the scale parameter should return 1, because once the limit is reached the widget actually stops scaling. Instead, the event repeatedly returns a value that is not equal to 1. If we try to determine whether scaling has effectively stopped by checking whether the current scale data equals the previous scale data, this can lead to serious bugs, because it is indeed possible for two consecutive scale values to be equal. As a result, there is no reliable way on the backend to determine whether scaling has truly stopped.
In most use cases of the InteractiveViewer widget, we need to transform coordinates between the viewport and the child widget — for example, in 2D games, infinite canvas scenarios, etc. We require accurate scale data to calculate the real offset of the child space (scaling centered on the mouse pointer causes the child to shift, because the framework’s default scaling is effectively center-based). This bug makes the widget a half-finished component.
My request is that this event return the correct scale data. If possible, please also add the offset delta for each scale operation and scrollbar support, though these are not mandatory.
Code sample
Code
import flet as ft
from typing import cast
@ft.control
class BaseCanvas(ft.GestureDetector):
max_scale: float = 3
scale_step: float = 0.25
min_scale: float = 0.25
def init(self):
self.cumulative_offset_x = self.cumulative_offset_y = 0
self.current_scale = 1
self.window_container_size = ()
self.canvas_size=()
self.scaled_canvas_size = ()
self.scale_offset_x = 0
self.scale_offset_y = 0
self.canvas_container = ft.Container(
bgcolor=ft.Colors.BLUE_100,
content=ft.Stack(
controls=[
self.module_container((50, 50)),
self.module_container((50, 600)),
self.module_container((1000, 50)),
self.module_container((1000, 600)),
],
),
)
self.content = ft.InteractiveViewer(
expand=True,
clip_behavior= ft.ClipBehavior.HARD_EDGE,
content=self.canvas_container,
on_size_change = lambda e: self.get_window_container_size(e),
constrained = False,
on_interaction_update=lambda e: print(e),
)
self.on_hover = self.mouse_hover_event
def module_container(self, pos):
module = ft.Container(
bgcolor=ft.Colors.GREEN,
width=70,
content=ft.Column(
[
ft.Container(width=70, content=ft.Text(f"module {j}"))
for j in range(10)
]
),
)
return ft.GestureDetector(
mouse_cursor=ft.MouseCursor.MOVE,
drag_interval=5,
left=pos[0],
top=pos[1],
content=module,
)
def get_window_container_size(self, e):
self.window_container_size = (e.width, e.height)
if not self.canvas_size or self.canvas_size<self.window_container_size:
self.canvas_size=self.window_container_size
self.canvas_container.width,self.canvas_container.height=self.window_container_size
self.canvas_container=cast(ft.Container,self.canvas_container)
self.canvas_container.update()
print(self.window_container_size)
def mouse_hover_event(self, e: ft.HoverEvent[ft.GestureDetector]) -> None:
"""Handle mouse hover, compute canvas coordinates"""
if e.local_delta is None:
return
if __name__ == "__main__":
def main(page: ft.Page):
canvas = BaseCanvas()
page.add(
ft.Container(expand=True,bgcolor=ft.Colors.AMBER, content=canvas),
)
ft.run(main)
To reproduce
- Run the code
- Scale to the maximum size
- Observe the scale data returned by the on_interaction_update event.
Expected behavior
No response
Screenshots / Videos
Captures
[Upload media here]
Operating System
Windows
Operating system details
11
Flet version
0.85
Regression
No, it isn't
Suggestions
No response
Logs
Logs
Additional details
No response
Duplicate Check
Describe the bug
The onInteractionUpdate event of the InteractiveViewer widget returns incorrect data. When the inner content is scaled to its minimum or maximum limit, the scale parameter should return 1, because once the limit is reached the widget actually stops scaling. Instead, the event repeatedly returns a value that is not equal to 1. If we try to determine whether scaling has effectively stopped by checking whether the current scale data equals the previous scale data, this can lead to serious bugs, because it is indeed possible for two consecutive scale values to be equal. As a result, there is no reliable way on the backend to determine whether scaling has truly stopped.
In most use cases of the InteractiveViewer widget, we need to transform coordinates between the viewport and the child widget — for example, in 2D games, infinite canvas scenarios, etc. We require accurate scale data to calculate the real offset of the child space (scaling centered on the mouse pointer causes the child to shift, because the framework’s default scaling is effectively center-based). This bug makes the widget a half-finished component.
My request is that this event return the correct scale data. If possible, please also add the offset delta for each scale operation and scrollbar support, though these are not mandatory.
Code sample
Code
To reproduce
Expected behavior
No response
Screenshots / Videos
Captures
[Upload media here]
Operating System
Windows
Operating system details
11
Flet version
0.85
Regression
No, it isn't
Suggestions
No response
Logs
Logs
[Paste your logs here]Additional details
No response