Open MouseAndKeyboard opened 1 month ago
Your RouterViewLayout needs to be static Python wise. It will be up to the JS to report back to the server which slug you are so you can display what you aim to display.
What I'm trying to say, is that the python code only execute once. After that, it is up to the JavaScript side trigger and render what ever has been described.
HTH
Okay, I come from using React. -> What I almost want it some sort of "on-component-mounted" callback. -> Within this callback I want to access the $route.params.slug parameter and pass that to a trigger.
My challenges are:
Fundamentally I want to do something like the code below:
import pyvista as pv
from pyvista.trame.ui import plotter_ui
from trame.widgets import vuetify3, router
from trame.ui.vuetify3 import SinglePageWithDrawerLayout
from trame.ui.router import RouterViewLayout
from trame.app import get_server
server = get_server(client_type='vue3')
state, ctrl = server.state, server.controller
# Initialize the plotter
plotter = pv.Plotter(off_screen=True)
plotter.add_mesh(pv.Sphere(radius=1), color='red', point_size=10)
# Set up the main layout
with SinglePageWithDrawerLayout(server) as layout:
with layout.toolbar:
vuetify3.VBtn("Home", to="/")
with layout.content:
router.RouterView()
# Define the controller function
@ctrl.trigger("on_route_load")
def on_route_load(id, **kwargs):
state.ball_index = id
# Update the plotter when ball_index changes
@state.change('ball_index')
def update_plotter(ball_index=0, **kwargs):
# Clear the plotter
plotter.clear()
# Select the actor based on ball_index
if state.ball_index == '0':
actor = pv.Sphere(radius=1)
elif state.ball_index == '1':
actor = pv.Cone()
elif state.ball_index == '2':
actor = pv.Cylinder()
elif state.ball_index == '3':
actor = pv.Cube()
else:
actor = pv.Sphere(radius=1)
# Add the new actor
plotter.add_mesh(actor, color='red', point_size=10)
# Set up the router view layout
with RouterViewLayout(server, "/:id") as layout:
with vuetify3.VCard():
vuetify3.VCardTitle("Dynamic Shape Viewer")
vuetify3.VCardText("Current Shape Index: {{ $route.params.id }}")
# Include the script to trigger the controller on route change
vuetify3.VCardText(
"""
<script>
export default {
mounted() {
this.$trame.trigger('on_route_load', { id: this.$route.params.id });
},
watch: {
'$route.params.id': function(newVal, oldVal) {
this.$trame.trigger('on_route_load', { id: newVal });
}
}
}
</script>
"""
)
# Initialize the ball_index
state.ball_index = '0'
if __name__ == "__main__":
server.start()
I'm not sure how to actually invoke the trigger and pass the id
parameter in this case.
Here is an example with the client trigger you want.
That is also another good base. But also on the arg side, you can get your hand on the router to extract the :slug
from it. You can trigger a console.log($router)
and figure out the path to get the piece you want using the browser dev tool.
You can also monitor the $router change and trigger a method on the python side from that like below.
client.ClientStateChange(
trigger_on_create=True,
value="$router.currentRoute.value.path",
change=(self.page_changed, "[$event]"),
)
Hello,
I'm developing an application using Trame and have run into a challenge that I hope you can help me with.
I want to define a dynamic route in my application:
Depending on the
:slug
parameter in the route, I aim to conditionally render different 3D visualizations provided by PyVista. My initial approach is to check the value of$route.params.slug
and then display the corresponding PyVista plotter UI.Here's a simplified version of what I'm trying to implement:
My intended workflow is:
When the
RouterViewLayout
component loads or mounts, I want to retrieve the$route.params.slug
value and assign it to a state variable.Updating this state variable should trigger functions decorated with
@state.change
, allowing me to react to the new route parameter.These state change functions would create a new PyVista plotter based on the
slug
value, rendering the appropriate 3D visualization on the page.TL;DR: I need to render different PyVista visualizations based on the dynamic
:slug
route parameter. What would be the best way to access$route.params.slug
within theRouterViewLayout
and trigger the necessary updates in Trame?Any guidance or suggestions would be greatly appreciated!
Thank you.