How to trigger a component script from Perspective page startup

Periodic Component Scripts

I have a way to run a script in a component scope once every x milliseconds, but it's a bit of a hack imo. Just create a custom property on the component you want to run a periodic script from, then create a binding on that property:

The now() expression function takes an update time difference as an argument, so it reevaluates the binding every x milliseconds. Add a script transform, and you've got a script that runs roughly once a minute (I don't think the timing is guaranteed, but it's been pretty close in my experience).

Thoughts

Considering the reply from @cmallonee , now might be a good time to explain what you're trying to do, instead of just asking how to do it. It seems like there are a lot of ways to go about running this update function, and the knowledgeable people in this forum can help you find the best way to go about it.

For example: I just gave you a solution to your periodic component script question, but the answer to your original problem might involve a much simpler solution. Maybe there's a way to trigger a button's action in a startup script, removing the need to replicate the code at all.

yes this worked! this is what i was looking for.
Initially the use case was to fire the button action script when the page refreshes and i had created another thread for it but i was told there thats not possible which i am not sure about
But now i just need the script to fire on a set interval and your solution worked. thanks

1 Like

If you want to do something periodically I would not do it on the view at all,

I would do it in a tag and have that tag hold for example, a dataset. Then your view can reference that tag.

Very important to remember is that anything you do on a view is multiplied by the number of clients and if that includes running scripts int the gateway, you add unnecessary computations.

Nick

1 Like

Hey @rahman.tarek

I know the issue is resolved but one possible way to access the custom parameter's is to use the message handler approach. So in the page start up script, you call the message handler

system.perspective.sendMessage("test-mh", payload = {}, scope = "page")

Now this message handler has the access to the self object, hence access to the custom parameter's.

I highly suspect this Message Handler approach will not work, as the Page Startup script is invoked before the components of the Page have rendered, and therefore they will not yet be listening for any broadcast message. IT's essentially a race condition, and might work for some users but not others; it would depend on the complexity of the View.

1 Like

Hey @cmallonee

yup, that makes more sense

@cmallonee is there another approach to this, I have a parametrized docked view and I want to change some parameters on the docked view depending on the primary view that’s being displayed, I tried the on-startup event of the primary view to send a message to the docked view, but as you mentioned it didn’t work, any work around or solution on this matter?

Instead of parameters, could you bind the relevant values in the Docked Views against self.page.primaryView in some manner?

1 Like

Exactly this.

I suspect most of this thread comes down to "don't push, subscribe".
Not only does it make implementation easier, because it turns out when you shift to subscription, most of what you need is actually built-in, but it also makes maintenance easier, because now you can follow the path "from the leaf to the root": to know where something's data come from, check its properties. No need to try and figure out what the hell is sending data to that particular component, which could very well become a nightmare rather fast.

3 Likes
from com.inductiveautomation.ignition.gateway import IgnitionGateway

PropertyType = IgnitionGateway.get().moduleManager.resolveClass("com.inductiveautomation.perspective.common.api.PropertyType")

pageProps = page.getPropertyTreeOf(PropertyType.props)

for view in page.getViews():
	if pageProps.primaryView in view.id:
		component = view.getChild('/root/Label')
		component.props.text = "cool, but shouldn't have to do this if bindings are set up/working correctly"