UMG Widget blueprint with bindable exposed properties?

Is it possible to support binding to an “expose on spawn” property defined in a UMG widget blueprint?

Example usage:
We have some generic skinned widgets in order to re-use style. For example, we have a simple widget that includes a styled button with a text label. We have an “expose on spawn” property to define the text label. We’d like to make that text bindable in other widgets that use this button widget as a component. Is that possible? Is there a better way to accomplish what we’re trying to do here?

Thanks!
Lauren

Have you tried:

  • Make a Text variable
  • Set Editable and Expose on Spawn to True
  • On your button/label (in the Designer tab) bind the Text property to the Text variable
  • Now when you create the widget in a BP, you will see that property exposed.

Does this help?

Hi Zak!

Yup, I have done all of that. Now I want that exposed property to be bindable in other widgets that use my styled button as a component widget. Currently I can set it manually, but it would be nice to use the binding functionality, as we plan to use this kind of thing in many places.

Here is the Label inside my reusable, styled button widget:
![alt text][https://udn.unrealengine.com/storage/attachments/98402-labelwithinbuttonbp.png]

Here is a usage of that button. I’d like “Label Text” to be bindable.
![alt text][https://udn.unrealengine.com/storage/attachments/98403-buttonusage.png]

Okay, I think I see.

For performance reasons, you probably don’t want to use a bind unless you want to update the label on every frame. This seems like something you only want changed once (the moment you spawn the button).

So, I would take this approach:

In your Login Button (UserWidget) unbind LabelText. Make the TextBlock itself a variable so you can access it and set its Text property. In the Event Graph, make a really simple CustomEvent/Function kinda like this one:

66280-setlabel.png

In this example I didn’t do anything fancy to LabelText. It’s just a text variable, neither Editable nor Exposed.

Next, in your other fancy widget that is utilizing your Login Button (which is a variable), do something like this on Construct.

66291-spawnwidget.png

As you can infer, the Text at this stage is Editable and Exposed on Spawn.

Now, finally, when you actually spawn this new fancy widget, you’ll see this and can use it as you’d expect:

And when spawned, whatever you fed into the exposed variable pin will be the new label.

66293-hadokenresult.png

Best of all, it only has to fire this chain of sequences once, as opposed to every frame, which it would if using traditional binds.

Hope this helps!

Hi Ben,
Yes, it’s fine to post this on the public community site.

Zak,
Thanks for posting this! I haven’t had a change to run through it yet. We’ll post back to let you know how it goes. :slight_smile:

This is a valuable answer Zak, I have a follow-up though.

I agree in Lauren’s case that binding was unnecessary, but what is your recommendation in situations where binding is appropriate? For example, the same basic setup but with a custom Widget Blueprint Class “EntertainingProgressBarContainer” that contains a ProgressBar as well as some custom animations (e.g. support for “shudder” or “blink” animations)?

Even when EntertainingProgressBarContainer’s inner ProgressBar (theBar) has “Is Variable” checked, and “Editable” is checked on theBar in the Graph view, I’m not seeing any ProgressBar-related editable fields in the Details tab when selecting any of my placed instances of EntertainingProgressBarContainer in a WidgetBlueprint.

Ideally I’d like for instances of EntertainingProgressBarContainer to expose the inner ProgressBar fields (Percent, Bar Fill Type, etc) to anyone who places them, the most convenient would be to able to, at my HUD level, bind those values to variables only available at the HUD level. If it’s not possible to get these fields to show up in the Details tab, is it possible to use the Blueprint Graph (either in EntertainingProgressBarContainer or HUD) to perform the binding manually when constructed?

If not, what’s the general strategy or best practice for this type of design, where you want one or more pieces of a complex WidgetBlueprint to “bubble up” and be exposed to consumers of the Blueprint for binding/manipulating?

Situation where binding is appropriate:

A UI element that MUST update every frame. An attitude indicator on a cockpit comes readily to mind. Most other things can be more event driven. Like an ammo counter only changes when you fire, reload, or pick up ammo.

For exposing sub properties:

I would create a function on EntertainingProgressBar that you could call that updates its internal progress bar by an input value. Then, in your uber UI, you simply get a reference to the EntertainingProgressBar, call that function, and pass in the new value. The function does the rest of the work.

Does that make sense?

Certainly it makes sense, although I’m still curious what the general solution would be for the cockpit attitude indicator example you provided. Is binding just not an option for the type of use case I’m working on?

The function to manually set the values is a straightforward solution, but I was hoping that I could build objects that exposed their inner controls to users so adding an EntertainingProgressBar would have the same convenience and Details Pane usage pattern as a regular one.

Apologies; let me clarify. :slight_smile:

Binding is certainly an option. It’s just something we’d generally advise against in any case where the data could be more event-driven. It’s just a performance consideration; binds get very expensive very quickly, as they have to query their required data on every single tick. If you don’t need data to update that quickly, it’s wiser not to do that.

An attitude indicator (esp. an analog one like you’d see on a traditional non-electronic cockpit) is going to need to update every frame as you fly the plane around, bank, pitch, etc. It’s possible that you could put it on a timer and calculate it slower than every frame (and if so, great; better performance!) but if you knew you needed it to look absolutely smooth, it’s possible you would need to bind the data and get those frame-by-frame updates.

As for exposing native properties of sub-widgets (i.e. your ProgressBar example) no, I’m afraid right now that’s not supported. Not in the way you’re asking. We recommend driving that through functions internal to the sub-widget, or by sending out via something like an Event Dispatcher.