-
Reflex does not have some |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment 3 replies
-
How to Get Viewport in JSThe viewport dimensions can be accessed in javascript via the How to Get Viewport in ReflexUsing a custom react hook, we can register a reflex state Custom Reflex ComponentEdit: updated to work with Reflex 0.6.7+
Define def _on_resize_signature(width: rx.Var[int], height: rx.Var[int]) -> tuple[rx.Var[int], rx.Var[int]]:
return width, height
class ResizeWatcher(rx.Fragment):
"""
A component that watches the window size and updates the state.
The only event trigger in `on_resize` which is called once when the component mounts
and again each time the viewport dimensions change.
"""
on_resize: rx.EventHandler[_on_resize_signature]
def _exclude_props(self) -> list[str]:
return ["on_resize"] Defining def add_imports(self) -> dict[str, str]:
return {"react": "useEffect"}
def add_hooks(self) -> list[str]:
"""Register backend on_resize as a handler for the browser window resize event."""
return [
"""
useEffect(() => {
function handleResize() {
%s(window.innerWidth, window.innerHeight);
}
// Fire initial resize event when the component mounts.
handleResize();
// Add the event listener with cleanup.
window.addEventListener("resize", handleResize);
return () => window.removeEventListener("resize", handleResize);
}, []);""" % (
self.event_triggers["on_resize"]
)
] This is a critical line Define Event Handler and StateFirst define some attributes that we will render in the frontend. class State(rx.State):
viewport_width: int = 0
viewport_height: int = 0
device: str = "undetermined" Then define the event handler that will be called when the def set_viewport(self, width: int, height: int) -> None:
self.viewport_width = width
self.viewport_height = height
self.device = device_guess(width) Putting it all togetherDemo 📼Screen.Recording.2024-01-25.at.9.25.54.PM.movimport reflex as rx
def device_guess(width: int) -> str:
if width < 520:
return "phone"
elif width < 768:
return "phone-landscape"
elif width < 1024:
return "tablet"
elif width < 1280:
return "tablet-landscape"
elif width < 1640:
return "laptop"
else:
return "desktop"
class State(rx.State):
viewport_width: int = 0
viewport_height: int = 0
device: str = "undetermined"
def set_viewport(self, width: int, height: int) -> None:
self.viewport_width = width
self.viewport_height = height
self.device = device_guess(width)
def _on_resize_signature(width: rx.Var[int], height: rx.Var[int]) -> tuple[rx.Var[int], rx.Var[int]]:
return width, height
class ResizeWatcher(rx.Fragment):
"""
A component that watches the window size and updates the state.
The only event trigger in `on_resize` which is called once when the component mounts
and again each time the viewport dimensions change.
"""
on_resize: rx.EventHandler[_on_resize_signature]
def _exclude_props(self) -> list[str]:
return ["on_resize"]
def add_imports(self) -> dict[str, str]:
return {"react": "useEffect"}
def add_hooks(self) -> list[str]:
"""Register backend on_resize as a handler for the browser window resize event."""
return [
"""
useEffect(() => {
function handleResize() {
%s(window.innerWidth, window.innerHeight);
}
// Fire initial resize event when the component mounts.
handleResize();
// Add the event listener with cleanup.
window.addEventListener("resize", handleResize);
return () => window.removeEventListener("resize", handleResize);
}, []);""" % (
self.event_triggers["on_resize"]
)
]
def index() -> rx.Component:
return rx.vstack(
ResizeWatcher.create(on_resize=State.set_viewport),
rx.heading("Viewport Resize Watcher Demo"),
rx.heading(f"[{State.viewport_width}, {State.viewport_height}]"),
rx.heading(f"Device: {State.device}"),
align="center",
font_size="2em",
padding_top="10%",
)
app = rx.App()
app.add_page(index) |
Beta Was this translation helpful? Give feedback.
How to Get Viewport in JS
The viewport dimensions can be accessed in javascript via the
window.innerWidth
andwindow.innerHeight
attributes. When the viewport size changes, the browser fires theresize
event on thewindow
.How to Get Viewport in Reflex
Using a custom react hook, we can register a reflex state
EventHandler
as thewindow.onresize
event handler and get the latest viewport dimensions whenever they change.Custom Reflex Component
Edit: updated to work with Reflex 0.6.7+
ResizeWatcher
will extendrx.Fragment
, which does not render anything in the DOM.Define
on_resize
as an EventHandler with the required function signature so that it can be linked to an event handler in the sta…