WPF - ObservableCollection PropertyChanged event? - wpf

I have an object which has a property of type ObservableCollection<bool>. It is bound to a list of checkboxes on a form using TwoWay bindings. I would like to add a PropertyChanged notification to this so that if certain values are selected, some other ones get automatically deselected. Is there a way to do this?
The ObservableCollection.PropertyChanged event doesn't get triggered when a value in the collection gets changed and I'm using the MVVM design pattern.

You would need to use your own class that implements the INotifyPropertyChanged interface. You won't be able to use bool, but you can have a single property in your class that is that bool that you want.

Related

How DataGrid is notified when item in the collection is changed?

I have two DataGrids bound to the same ObservableCollection property in my ViewModel.
When I edit an existing row in one DataGrid another gets updated after row is commited.
But how it works? The NotifyCollectionChanged event is not raised on the underlying ObservableCollection. I have checked it by subscribing to the event.
In this case, you are modifying the properties of the item (entity) of the collection, not the collection itself.
Therefore, the CollectionChanged event is not raised.
To update properties in an entity, INotifyPropertyChanged must be implemented in it.
But if the change of properties happens ONLY through bindings, then even this is not necessary.
Bindings use PropertyDescriptor and other types of reflection in their work.
This allows bindings to "know" that a property has been changed by another binding.
If you speak Russian, read my article: https://www.cyberforum.ru/wpf-silverlight/thread2650880.html

List<> collection does not update the View in MVVM

I used the List<Person> collection as the ItemsSource for the DataGrid control.
But it did not update the View if i remove the item from the List collection. I was struggling for a long time for the solution.
Then Instead of the List<Person> collection in my ViewModel. I changed this into ObservableCollection<Person> collection. Now it updates the view when ever there is a change in the collection.
I am not sure why it updates only for ObservableCollection<Person> ? Anyone ?
Well its in the name. A simple List doesn't tell the ui to update, in other words "the view can't observe the list". There is no weird magic behind Databinding. WPF and DataBinding needs the Data model to tell them "this is new" or "this is changed", you propably already saw INotifyPropertyChanged, INotifyCollectionChanged is the same but for collections, and the List<> doesn't implement it, ObservableCollection does.
Because List does not implement INotifyCollectionChanged
Because the update of a databinding is not a kind of magic, there are several requirements to make databinding working correctly. If you have a single property to bind on this property must be either a dependency property or its parent class must implement the INotifyPropertyChanged interface to notify the wpf binding system about changes of the property value.
For a collection there is a simelar mechanism: it must implement INotifyPropertyChanged to inform the wpf binding system about removed/moved/added items.
See here for more details: http://msdn.microsoft.com/en-us/library/system.collections.specialized.inotifycollectionchanged.aspx
ObservableCollection<T> fires change events every time you change the items in the collection. List<T> doesn't. That's the reason.
DataBinding is lazy. If you don't tell your view that something has changed, it won't bother updating. Under the hoods, WPF DataBinding registers for change notifications, so that your ViewModel can tell the view when it has changed. It does this with interfaces like INotifyPropertyChanged and INotifyCollectionChanged.
ObservableCollection<T> implements the interface INotifyCollectionChanged. This interface defines the event CollectionChanged, which your View basically attaches its own event handler to. That handler will update the view when the event is raised by the collection.

INotifyPropertyChanged or INotifyCollectionChanged with DataTable?

Hi i am having some troube with DataTables. So What i need is to detect whenever i change any cell in the DataGrid of the DataTable that is binded.
How to do it? With INotifyPropertyChanged or with INotifyCollectionChanged?
Note: I am trying with INotifyPropertyChanged but it only detects when i set some value in the DataTable, and never when i change any value of any cell in the DataGrid, i already have tried OneWay and TwoWay but nothing happens.
Thanks in advance!
The datagrid would be bound to a list of objects. If you want the grid to update when individual object properties change, than each contained object must implement the INotifyPropertyChanged interface.
The INotifyCollectionChanged is an interface that the collection should implement, and are for notifications of addition and removal events.
See the section "How to implement collections" on this page.
Here's a way to approach your problem:
Create a new class that exposes the properties currently held in each DataRow. On this class implement INotifyPropertyChanged.
Instead of a DataTable, use an ObservableCollection<T> or your new class.
ObservableCollection already implements INotifyCollectionChanged, so this saves you the effort of implementing it yourself.
if you set the itemssource of your datagrid to a datatable then wpf create a IBindingListView wich is bound to the datagrid.
what you can do now is edit,add and delete items to your datatable via datagrid. if you wanna know when a cell in your datatable is changed you can subscribe to DataTable.ColumnChanged event.
why do you want do know when a cell is changed?
The answer to the title of your question is : Neither. Actually you do not need to bind a DataTable to a DataGrid. You bind a DataView. "The ADO.NET DataView implements the IBindingList interface, which provides change notifications that the binding engine listens for."(Binding Sources Overview)
One answer to your question is :
You modify the datagrid cell with a TextBox (usually). Do this with a new textbox inheriting from TextBox and override the OnGotFocus and OnLostFocus methods of it.

WPF MVVM: Notifying the View of a change to an element within an ObservableCollection?

Calling OnPropertyChanged for an ObservableCollection only works when there has been some change to the properties of the collection, not the objects it contains (add, remove, clear, etc).
Is there any way to notify the View that there has been a change to an item within the collection?
The objects it contains have to implement INotifyPropertyChanged as well. In your setter you trigger the event, and WPF will pick up on this and read in the new value as long as you are using two-way bindings or read-only bindings.

Can we update a source that is not DepencyProperty or not INotifyPropertyChanged compliant

I have a business object that comes from the core of the application. That object does not inherit from INotifyPropertyChanged. It contains some property that my XAML code bind to it.
I only want to update the properties not the UI dynamically (OneWayToSource style).
By example, if I change the text of a text box, the source item does not get updated.
It is a limitation of silverlight that if the object does not implement INotifyPropertyChanged or use DepencyProperties that the source of the binding cannot be updated?
The source property does not need to be a dependency property nor does the class that exposes it need to implement INotifyPropertyChanged.
If you have the binding on the TextBox set to use the TwoWay mode editing the text box should update the bound property even if it is a plain "vanila" property. Note by default the focus has to leave the TextBox in order for the binding to update.
If your business object has a set method on the property you want to update, then the value should be updated, provided the value you enter doesn't trigger an exception.
Not implementing INotifyPropertyChanged hinders just visual feedback.

Resources