Force visual tree creation with Prism

296 Views Asked by At

I have a TabControl containing Prism regions. I want to trigger some kind of notification (e.g. flashing the tab header) for certain events, and I want to trigger this notification from the components in the Prism regions.

Once the tab containing such a component was open once, this works nicely using VisualTreeUtil.GetParent() and going up until I find my TabControl and can modify it to indicate the notification.

But the problem is that this doesn't work until the tab is opened by the user because VisualTreeUtil.GetParent() returns null; obviously because Prism doesn't hook up the visual tree until then.

Calling UpdateLayout() on the TabItem containing the region doesn't help. I don't want to open the TabItems programmatically, because this would confuse the user.

Is there anything I can do short of implementing a kind of region registry (which would be rather ugly and harder to maintain)?

If you want to look at code, I wrote a minimal solution to demonstrate the issue. The Print Structure button tries to go up the visual tree from the (initially unrendered invisible) hello TextBlock on the second tab. Before you switch to the tab it prints only the TextBlock, afterwards you get to the root of the visual tree. This is what I want to accomplish without switching to the tab.

2

There are 2 best solutions below

0
On

Hm.. IIRC Prism regions are just a configured ContentControl/ContentPresenter. Once they are ready to work, all the bindings and datamodels should be in place, but the trees are left not created because they are invisible. If so, you should be able to call ApplyTemplate() on them to force it. I do not remember, however, if the Prism assigns the contenttemplates/datacontexts upon init, or upon demand - the latter may cause calling ApplyTemplate useless.

0
On

Adding comment as answer:

This probably isn't exactly the answer you are looking for, but it seems like you're taking a very procedural approach.

Have you considered using an MVVM approach? Each TabItem in the TabControl can have a HeaderTemplate. In the template you can bind to a property in the ViewModel that causes the tab to flash or change appearance