Pivot Viewer Template Refresh - silverlight

I have a Silverlight 5 app with a PivotViewer in it. This is binding with the data source correctly, but I need to force a rebind on the templates without replacing the data source and re-setting the entire control. The results are.... interesting.
We are using a ValueConverter to determine what color a tile should be, and this value converter can be adjusted depending on an external selection. At this point the INotifyPropertyChange of all the records are fired and a rebind occurs, but only on the currently visible template. This leads to tiles changing colors when zooming in and out as the other views have no been refreshed.
Can anyone tell me if it is possible to implement this in such a way that it would affect all levels of zoom? And is it possible to trigger a rebind without firing the INotifyPropertyChange?
Thanks

After considerable investigation, I came across this issue in the microsoft bug tracker:
http://connect.microsoft.com/VisualStudio/feedback/details/768779/silverlight-forum-issue-with-changing-items-background-color-for-sl5-pivotviewer
The description:
Create a simple data class that implements INotifyPropertyChanged, change all the items' color every 5 secs, but some items have different background color with different zoom levels. This issue was reported from Silverlight forum: http://forums.silverlight.net/p/262082/654612.aspx/1?Re+PivotViewer+SL5+Dynamic+Collection+to+change+item+background+color
So I guess that explains what the problem was. Just waiting for a fix now.

Related

WPF : The toggle button in my GridViewToggleRowDetailsColumn get visible when scrolling horizontally

I have a radgridview with a GridViewToggleRowDetailsColumn and I can set the visibility of the GridViewToggleButton the way I want through the RowLoaded event for each row. It was working fine until I need to scroll horizontally. When the GridViewToggleRowDetailsColumn get out of the screen and I scroll back to it, the GridViewToggleButton are now all visible.
I tried to find any event triggered by this without success. Even the IsVisibleChanged event attached to the GridViewToggleButton seems to be triggered only on the visible one.
Does anyone faced the same issue or have any idea of what could produce this behavior ?
Edit: Found the answer. It was a virtualization issue. Adding EnableColumnVirtualization="False" in the gridview properties solved it.
https://docs.telerik.com/devtools/wpf/controls/radgridview/features/ui-virtualization
After a few minutes of research, it appears that telerik WPF GridView uses virtualization to improve performace. This means that the state of what is in the screen is retained and as things leave your viewing area they are destroyed. This frees up memory space significantly, however can have some side effects as you are experiencing.
You can set EnableColumnVirtualization=false however Telerik has provided a help article that will likely answer your question more directly while not sacrificing the performance provided by the virtualizations. A link is below and following through the steps, it looks fairly straightforward.
https://docs.telerik.com/devtools/wpf/controls/radgridview/style-selectors/cell-style-selector
The recommended approach for customizing this behavior, and not turning off the virtualization, is to use a custom column. Try inheriting from GridViewToggleRowDetailsColumn and override CreateCellElement. It is the callback for creating the visual element in the cell, which is called, more or less, at the same time as RowLoaded. Then return null for those rows that you don't want to have a button for.

How to debug problems in XAML/WPF controls?

I'm trying to build a maintenance form in WPF, using Telerik's WPF controls. The idea is to have a grid and a form that are bound to the same collection. Changes to the grid should be immediately reflected in the form, and vice versa. An online example using Telerik's Silverlight controls is here.
My specific problem is that when I enter a new record (by clicking on the "Add" icon in the upper-right of the DataForm), the record is added to both the grid and to the form's collection, but it seems to break the synchronization. The new row in the grid stays highlighted, like the grid thinks it's not done being edited, and while changes to the current record in the form are reflected in the grid, changes to the current record in the grid are no longer being reflected in the form.
But my real problem is more general than that. WPF controls, like Telerik's, are heavily dependent on binding, and in having what they bind to support specific behaviors. In this case, the underlying record needs to support INotifyIEditableObject, so that when the user hits the Cancel button on the form, the EditCancel method on the record can be called. Which is then responsible for setting its properties back to what they had been, and then raising a NotifyPropertyChanged event, so that controls that are informed that they have been so set.
When I didn't have EditCancel working right, I would hit cancel on the form and the values in the grid would not be changed. My guess as to what is going on with the inserts is that something in either my collection or by records doesn't support whatever it is that makes this work. The grid doesn't know that the form has finished editing the record because either my record or the collection hasn't told it.
And here's the real question: how can I find out what these third-party controls are expecting? Telerik's RadGrid can be bound to pretty much anything that can be IEnumerated. But all this neat enhanced functionality depends upon being bound to collections that are very much more specific. I don't get errors, when I bind to a collection that lacks facilities that are needed for certain functions to work, I just get a control that doesn't work.
How can I tell, when working with someone else's control, for which I do not have source code, what functionality it requires, in the objects it binds to?
Your best bet would be to browse Telerik's documentation or ask on their support forums
If that doesn't work, I like to use Snoop for debugging WPF's Visual Tree and Reflector for looking through compiled libraries

Silverlight Binding in Pivot Control

I have a design question : In a pivot view (three "pages"), I have a lot of bindings. Well, about 12 items in each pivot view (TextBox, Map...).
I realized that these binding were slowing a lot the load of my view. But the binding on the first "page" of my pivot is the only one that needs to be loaded. I can put a progress indicator and load in a thread or something my other data (in fact, the binded data will be set only after an HTTPWebRequest).
How can I tell that to my application ? Like "onLoadPageX: bind items"
Thanks a lot, I don't know if i'm clear
You should be able to add a RoutedEventHandler for the Loaded event of each PivotItem. This event is fired when a particular PivotItem page is loaded; there is also a corresponding Unloaded event for when the page unloads, in case you need to free any resources.
Your question is quite vague but there are lots of options around showing a loading state, defering binding and having lots of controls in a pivot:
If you need to do anything that may take time then do it off the UI thread.
If you're doing something which takes time then you should show an indication to the user that something is happening. This could be a message or animation, depending on the likley time period and the rest of the application.
If your content is highly dependent upon data loaded from the web, be sure to have appropriate timeouts on failing to load the data. Also have useful messages if there is no data connection available.
If your UI is highly dependent on details loaded externally you could look at adding the controls to the UI once you know what you need to display.
If the UI will always have the same controls but different content in them, you could consider data-binding to objects which have placeholder content which is updated when the relevant information is downloaded from the web service.
If you have lots of items in your pivot you should consider defereing the loading of individual items so that you don't load them before they are needed. Only load the data on the items next to the one displayed. This way they appear preloaded to the user but ease the impact on the system.

WPF Undo Redo Property System to highlight in red color if value has changed

I have a following requirement for a very complex UI. (Complex here means there are lot of controls in the form [approximately 100]). I am using MVVM (if my problem requires it to slightly go away from MVVM I am ok with it)
My question is for Editable ComboBox and TextBox. But I would say I like to hear a common algorithm which will fit all controls.
Requirement 1 : The user edits the content and goes to next control, the color of the control/text should become red.
Requirement 2 : When the user comes back to the previously edited control and enters the value which was initially present, the color of the control/text should become back to black.
I know the requirement is tough and I have been breaking my head to design a generic algorithm using which I can store the previous value and call a function to change the color of control.
To just give you all an idea, --> I tried storing 2 properties for every TextBox like Default_Text and Text. But since the number of properties are huge, the memory footprint is very huge. Also maintaining so many properties is very tough.
--> I tried adding a Dictionary to every ViewModel to store what values have got changed. But here the problem I faced was giving unique keys to all the controls in my application, which is not very helpful
--> I had even thought and tried about subclassing controls like TextBox, ComboBox and overriding some methods to suit my requirement, but sadly I failed miserabley when I started adding validations and all.
So here I am stuck with designing a generic WPF property system/algorithm to handle all undo redo functionality, changing styles of controls,etc!!!
It will be really great if you experts can guide me in right direction and also help me in developing such an algorithm/system. A sample illustration will be nice though!!!
I found an answer to the above problem. I used attached behavior for this. More details on this link Function call from XAML from StackOverFlow.
When I databind, I store the initial value of the DataBound variable in the Tag property by using Binding=OneWay. Then I have written a attached behaviour for LostFocus event. Whenever the user enters a control and then goes to other control, it fires LostFocus event and calls my attached behaviour. In this, I check whether the value is equal to the value in Tag. If it is same, I display in black else I display in red.
Attached Behaviour rocks in WPF. I can achieve anything from that cleanly without code cluttering!!!!
Another alternative is to use some "dirty" tracking in your models (or viewmodels) and bind to a properties isdirty (and convert it to a color).

Dynamic animations, Commands and separation of concerns

Scenario: I have a (numeric) textbox, a button, and a label. When the button is clicked I'd like the label to "animate" to the numeric value in the textbox (like a spinning dial)
Given:
a) that animations in storyboards cannot have databindings (because they are not FrameworkElements)
b) the lack of triggers in Silverlight
What is the best, and with least coupling of the view model to the view's storyboard, way to update the target animation value and start the animation when the button is clicked?
Note: The scenario is conceptual, so don't concentrate on the specifics of 'animating' numbers or anything
If your goal is strictly to reduce the code-behind in the view I think that an attached behaviour on the Label would work for this. The attached behaviour on the label would expose the number to be animated to and when this number changes an animation (in code) would be run to animate from the old value to the new value.
One drawback is that your animation is now in code, unless you store a templated (just has fake values to start with) version of it in a resource file somewhere where you can load it as needed and replace the templated values.
This article from Josh Smith seems to be the authority on Attached Behaviours;
http://joshsmithonwpf.wordpress.com/2008/08/30/introduction-to-attached-behaviors/
I recently had to solve a similar problem in an MVVM application. My problem was that I needed to animate a container's height from zero to auto. Since Auto is a dynamic value I recognized that the animation (or storyboard) would need to be built (or manipulated) on demand. The solution that I put in place involved using view code-behind to update and fire the animation.
This isn't the most MVVM-friendly approach; however, animations in WPF can be tricky in XAML. Since this solution is really just a workaround for a XAML limitation it seems okay to tie the code directly to the view. Likewise, if the views were mocked then there would be no framework elements to animate, so it really wouldn't make sense to place this code on the VM side.
Does anybody have a better approach?

Resources