Skip to content

Commit

Permalink
page.go re-worked, EventHandler re-worked
Browse files Browse the repository at this point in the history
  • Loading branch information
FeodorFitsner committed Feb 23, 2024
1 parent 679144d commit d7edea0
Show file tree
Hide file tree
Showing 2 changed files with 40 additions and 66 deletions.
61 changes: 19 additions & 42 deletions sdk/python/packages/flet-core/src/flet_core/event_handler.py
Original file line number Diff line number Diff line change
@@ -1,55 +1,32 @@
import asyncio

from flet_core.utils import is_asyncio
from flet_core.control_event import ControlEvent


class EventHandler:
def __init__(self, result_converter=None) -> None:
self.__handlers = {}
self.__result_converter = result_converter

def get_sync_handler(self):
return self.__sync_handler
self.__handlers = {}

def get_handler(self):
if is_asyncio():
return self.__async_handler
else:
return self.__sync_handler

def __sync_handler(self, e):
for h in self.__handlers.keys():
if self.__result_converter is not None:
r = self.__result_converter(e)
if r is not None:
r.target = e.target
r.name = e.name
r.data = e.data
r.control = e.control
r.page = e.page
h(r)
else:
h(e)

async def __async_handler(self, e):
for h in self.__handlers.keys():
if self.__result_converter is not None:
r = self.__result_converter(e)
if r is not None:
r.target = e.target
r.name = e.name
r.data = e.data
r.control = e.control
r.page = e.page
if asyncio.iscoroutinefunction(h):
await h(r)
else:
h(r)
else:
if asyncio.iscoroutinefunction(h):
await h(e)
async def fn(e: ControlEvent):
for handler in self.__handlers.keys():
ce = e
if self.__result_converter is not None:
ce = self.__result_converter(e)
if ce is not None:
ce.target = e.target
ce.name = e.name
ce.data = e.data
ce.control = e.control
ce.page = e.page

if asyncio.iscoroutinefunction(handler):
await handler(ce)
else:
h(e)
e.page.run_in_thread(handler, ce)

return fn

def subscribe(self, handler):
if handler is not None:
Expand Down
45 changes: 21 additions & 24 deletions sdk/python/packages/flet-core/src/flet_core/page.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
from concurrent.futures import ThreadPoolExecutor
from dataclasses import dataclass
from datetime import datetime, timedelta
from typing import Any, Dict, List, Optional, Tuple, Union, cast
from typing import Any, Awaitable, Callable, Dict, List, Optional, Tuple, Union, cast
from urllib.parse import urlparse
from warnings import warn

Expand Down Expand Up @@ -167,7 +167,7 @@ def convert_route_change_event(e):
self.query() # Update query url (required when manually changed from browser)
return RouteChangeEvent(route=e.data)

self.__on_route_change = EventHandler(convert_route_change_event)
self.__on_route_change: EventHandler = EventHandler(convert_route_change_event)
self._add_event_handler("route_change", self.__on_route_change.get_handler())

def convert_view_pop_event(e):
Expand Down Expand Up @@ -448,13 +448,8 @@ async def on_event_async(self, e: Event):
if handler:
if asyncio.iscoroutinefunction(handler):
await handler(ce)
elif is_pyodide():
handler(ce)
else:
# run in thread pool
self.__loop.call_soon_threadsafe(
self.__loop.run_in_executor, self.__pool, handler, ce
)
self.run_in_thread(handler, ce)

def __on_page_change_event(self, data):
for props in json.loads(data):
Expand All @@ -464,38 +459,40 @@ def __on_page_change_event(self, data):
if name != "i":
self._index[id]._set_attr(name, props[name], dirty=False)

def run_task(self, handler: Callable[..., Awaitable[Any]], *args):
assert asyncio.iscoroutinefunction(handler)
asyncio.run_coroutine_threadsafe(handler(*args), self.__loop)

def run_in_thread(self, handler, *args):
if is_pyodide():
handler(*args)
else:
assert self.__loop
self.__loop.call_soon_threadsafe(
self.__loop.run_in_executor, self.__pool, handler, *args
)

def go(self, route, skip_route_change_event=False, **kwargs):
self.route = route if not kwargs else route + self.query.post(kwargs)

if not skip_route_change_event:
self.__on_route_change.get_sync_handler()(
self.run_task(
self.__on_route_change.get_handler(),
ControlEvent(
target="page",
name="route_change",
data=self.route,
page=self,
control=self,
)
),
)

self.update()
self.query() # Update query url (required when using go)

async def go_async(self, route, skip_route_change_event=False, **kwargs):
self.route = route if not kwargs else route + self.query.post(kwargs)

if not skip_route_change_event:
await self.__on_route_change.get_handler()(
ControlEvent(
target="page",
name="route_change",
data=self.route,
page=self,
control=self,
)
)
await self.update_async()
self.query()
warn("Obsolete. Use page.go() method instead.")
self.go(route, skip_route_change_event, **kwargs)

def get_upload_url(self, file_name: str, expires: int):
r = self._send_command(
Expand Down

0 comments on commit d7edea0

Please sign in to comment.