# Is it possible to change label position in a vision template dynamically

**URL:** <https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469>\
**Category:** Ignition\
**Tags:** ignition81, vision\
**Created:** [July 3, 2022, 10:38pm UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469 "2022-07-03T22:38:17Z")\
**Posts on this page:** 9\
**Page:** 1

<div class="post-metadata">

**Author:** ![david.rigby](https://avatars.discourse-cdn.com/v4/letter/d/5f9b8f/32.png) [@david.rigby](https://forum.inductiveautomation.com/u/david.rigby)\
**Post date:** [July 3, 2022, 10:38pm UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/1 "2022-07-03T22:38:17Z")

</div>

Hi All.

What is the best way to position a label in a template?

We have some “standard” valve and motor templates where we would like to position the device name label (top/center/bottom, left/centre/right) - ideally this would be visible in the designer when dropping on a page but not essential.

I have seen use of system.gui.transform to move things around but that isn’t visible in the designer and I need an event to make that work (an event that fires only once on template loading - propertyChange?!).

I have my current (very horrible) solution of having multiple labels and setting visibility of the desired position but that makes the template object in the designer huge. not to mention it “appears” to really lag the page on first load.

Option 3, which is my least favorite, is to not have the label inside the template, meaning I have to add a label whenever I add a template and configure the text. - Since the label text is already part of the UDT parameters it makes more sense to me to be contained.

Anyway, any input greatly appreciated.

Regards  
Dave

---

<div class="post-metadata">

**Author:** ![nminchin](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/nminchin/32/6911_2.png) [@nminchin](https://forum.inductiveautomation.com/u/nminchin)\
**Post date:** [July 4, 2022, 10:31am UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/2 "2022-07-04T10:31:20Z")

</div>

I opted for option 3 since it’s the most flexible. Sometimes the standard four compass positions just don’t suit some instances. I created a device label template with a subset of the params I have in the device templates (ie. deviceParentPath and deviceName) for consistency and so that I can just select both templates and set the props together.

Adding the label into the template also plays havoc with the template bounding box as well as its centre point.

---

<div class="post-metadata">

**Author:** ![jlandwerlen](https://avatars.discourse-cdn.com/v4/letter/j/bc8723/32.png) [@jlandwerlen](https://forum.inductiveautomation.com/u/jlandwerlen)\
**Post date:** [July 4, 2022, 1:11pm UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/3 "2022-07-04T13:11:00Z")

</div>

I would go with option 3 as well. I dealt with a few projects where everything was in a template and it just didn’t work well, as you know you may need to move things around. I would rather make each component a template and then build up what you need. It doesn’t take any longer either, you can make a window that has an example, then simply copy that example and paste where you need it. Then select all components and you can change the tag reference for all at the same time.

Much more flexible and also gives you rapid deployment.

---

<div class="post-metadata">

**Author:** ![pturmel](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/pturmel/32/3295_2.png) [@pturmel](https://forum.inductiveautomation.com/u/pturmel)\
**Post date:** [July 4, 2022, 1:51pm UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/4 "2022-07-04T13:51:01Z")

</div>

> [@david.rigby](#):
>
> system.gui.transform to move things around but that isn’t visible in the designer

You can use the `runScript` expression function to call scripts in the designer even when not in preview mode. Perfect for this sort of adjustment. That is, I would keep it in the template.

I would _ **not** _ use any UDT parameters, though. Always pass a tag path instead of a UDT. Then everything works even if you pass a path that has a folder with the same structure as the original UDT. Or switch among multiple UDTs that can't be modeled by inheritance.

---

<div class="post-metadata">

**Author:** ![david.rigby](https://avatars.discourse-cdn.com/v4/letter/d/5f9b8f/32.png) [@david.rigby](https://forum.inductiveautomation.com/u/david.rigby)\
**Post date:** [July 4, 2022, 11:04pm UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/5 "2022-07-04T23:04:28Z")

</div>

Thanks all for your answers.

My main issue with option 3 is that when my minions are bashing out pages, things like labels get overlooked.

I like Phil’s solution however, its more in line with my thinking, I can replace T/C/B L/C/R with offsetX and offsetY which should give me infinite placement.

Not to derail the topic, but, is there any downside to using the UDT other than flexibility?  
I have started using indirect tags within templates and pop pages (as suggested in other threads by yourself and Nick) to access UDT parameters, so not totally against it.  
We currently only have a single device UDT regardless of how many types of AOIs are in the PLC.  
I also like the fact I can use the drop target to quickly add templates to the pages (which I assume wont work without a few extra mouse clicks when only passing a tag path?!)

Thanks again for you insights.

Regards  
Dave

---

<div class="post-metadata">

**Author:** ![david.rigby](https://avatars.discourse-cdn.com/v4/letter/d/5f9b8f/32.png) [@david.rigby](https://forum.inductiveautomation.com/u/david.rigby)\
**Post date:** [July 6, 2022, 10:35pm UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/6 "2022-07-06T22:35:50Z")

</div>

OK, so I have been bashing my head on this for way too long now.

- I created a new template “Testing” which has 2 parameters “OffsetX” and “OffsetY”
- In the template I added a label “ShortName\_Lbl”
- On the label I created custom properties “OffsetX” and “OffsetY”
- In the binding for “OffsetX” I have the following expression
- 
  - runScript(“system.gui.transform”,0,{Testing.ShortName\_Lbl},{Testing.OffsetX},{Testing.OffsetX}).

but… I’m struggling to get the JComponent reference.

Error message I see is:  
Exception: Error executing expression binding on  
Testing.Testing.ShortName\_Lbl.OffsetX  
caused by ExpressionException: Error executing script for runScript() expression:system.gui.transform  
caused by java.lang.RuntimeException: java.lang.RuntimeException: Component argument not found.

Am I heading in the right direction? or should I be calling a custom method which in turn calls the transform?!

Any pointers greatly appreciated…

Regards  
Dave

---

<div class="post-metadata">

**Author:** ![bmusson](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/bmusson/32/87530_2.png) [@bmusson](https://forum.inductiveautomation.com/u/bmusson)\
**Post date:** [July 6, 2022, 10:48pm UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/7 "2022-07-06T22:48:58Z")

</div>

> [@david.rigby](#):
>
> should I be calling a custom method which in turn calls the transform?!

This.

I’d make a property on the label called `repositionTrigger`, and bind an expression like

```auto
{Testing.OffsetX}+{Testing.OffsetY}+runScript(“self.reposition”)

```

that calls a custom method on the label that repositions itself (and returns a value to make the binding happy). By including both the offsetX and offsetY in the binding, the runScript(“self.reposition”) will be triggered when either value changes.

---

<div class="post-metadata">

**Author:** ![pturmel](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/pturmel/32/3295_2.png) [@pturmel](https://forum.inductiveautomation.com/u/pturmel)\
**Post date:** [July 6, 2022, 11:45pm UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/8 "2022-07-06T23:45:59Z")

</div>

Or switch to my `objectScript`. It can do complete one-liners with passed arguments. `runScript` can only pass arguments to a callable.

---

<div class="post-metadata">

**Author:** ![david.rigby](https://avatars.discourse-cdn.com/v4/letter/d/5f9b8f/32.png) [@david.rigby](https://forum.inductiveautomation.com/u/david.rigby)\
**Post date:** [July 7, 2022, 1:19am UTC](https://forum.inductiveautomation.com/t/is-it-possible-to-change-label-position-in-a-vision-template-dynamically/61469/9 "2022-07-07T01:19:17Z")

</div>

thanks @bmusson.

That worked a treat. That will definitely fix up my (horrible) multi label templates.  
I will need to keep the current large template size however as the label can be placed outside of the template width and height but is not visible (changing the template width and height - doesn't look like I can use transform on self.parent?! and directly referencing self.parent.width and self.parent.height in the MoveMe method doesn't seem to work)

for completeness, the full solution

- Template ("Testing")
- 
  - Add custom parameters OffsetX, OffsetY

- Label ("ShortName")
- 
  - Add custom method ("MoveMe")

> def MoveMe(self):  
> """  
> Arguments:  
> self: A reference to the component instance this method is invoked on. This argument  
> is automatic and should not be specified when invoking this method.  
> """  
> system.gui.transform(self,self.parent.OffsetX,self.parent.OffsetY)

- 
  - Add custom parameter "OffsetChanged"

- 
  - 
    - Expression Bind "OffsetChanged" - {Testing.OffsetX}+{Testing.OffsetY}+runScript("self.MoveMe",0)

Works like a charm.

@pturmel - I will have a play around with objectScript (now I found it in simulation Aids 3rd Party module)

Thanks all.

Regards  
Dave
