This is the follow up to this Question.
I have to update a ObservableCollection from a different Thread. I tried it with the following Code:
Thread t = new Thread( ()=>
{
while(true)
{
if (ErrorDetection.ErrorDetectionIO.doErrorDetection() == 1)
{
dataLine = ErrorDetection.ErrorDetectionIO.getDataLine();
if (mainWindow != null)
{
ISynchronizeInvoke target = mainWindow; // mainWindow needs to be an WindowsForm?
target.Invoke(
(Action)(() =>
{
mainWindow.setNewDataLine(dataLine);
}
), null);
}
}
}
} );
t.IsBackground = true;
t.Start();
ErrorDetectionIO.doErrorDetection() is in a c++/cli .dll and calls native c Code.
setNewDataLine is on the mainWindow and adds a Line to the Observable Collection.
If its called from a different Thread it causes an exception:
“This type of CollectionView does not support changes to its SourceCollection from a thread different from the Dispatcher thread.”
The Problem is that ISynchronize Invoke does not seem to work with wpf? Threres an compiler error message that mainWindow can´t be converted to ISynchronizeInvoke.
if I use
ISynchronizeInvoke target = mainWindow as ISynchronizeInvoke;
it can be compiled but target is null;
You can just use
mainWindow.Dispatcher.Invokeinstead of trying to cast toISynchronizeInvoke. Dispatcher.Invoke will provide the correct marshaling for WPF.Note that .NET 4.5 adds the ability for WPF to handle this automatically by setting BindingOperations.EnableCollectionSynchronization.