I am new to WPF, so I thought this was simple. I have a form with a listbox and a button. In the click handler for the button I do something iteratively that generates strings, which I want to put in the listbox as I get them. The xaml for the list box is like
<ListBox Height="87" Margin="12,0,12,10" Name="lbxProgress" VerticalAlignment="Bottom">
<ListBox.BindingGroup>
<BindingGroup Name="{x:Null}" NotifyOnValidationError="False" />
</ListBox.BindingGroup>
</ListBox>
and the click handler is like
private void btn_Click(object sender, RoutedEventArgs e)
{
List<String> lstrFiles= new List<String>(System.IO.Directory.GetFiles ("C:\\temp", "*.tmp");
foreach(string strFile in lstrFiles)
lbxProgress.Items.Add(strFile);
}
Pretty straightforward. Since my real operation is lengthy, I want the listbox to update as I do each one – how do I get the box to dynamically update on each addition?
Create an
ObservableCollection<string>and set your ListBox.ItemsSource to that collection. Because the collection is observable, the ListBox will update as its contents change.However, if your real operation is blocking the UI thread, this may prevent WPF from updating the UI until the operation completes (because the WPF data binding infrastructure doesn’t get a chance to run). So you may need to run your lengthy operation on a background thread. In this case, you will not be able to update the ObservableCollection from the background thread due to WPF cross-threading restrictions (you can update properties, but not collections). To get around this, use Dispatcher.BeginInvoke() to update the collection on the UI thread while continuing your operation on the background thread.