so etwas wie INotifyCollectionChanged Feuer auf XML-Datei geändert
-
22-09-2019 - |
Frage
Es ist möglich, INotifyCollectionChanged oder eine andere Schnittstelle wie IObservable implementieren zu dieser Datei geändert zu ermöglichen, um gefilterte Daten aus XML-Datei zu binden? Ich sehe Beispiele mit Eigenschaften oder Sammlung, aber was mit den Dateien ändern?
Ich habe diesen Code zu filtern und zu binden XML-Daten-Listenfeld:
XmlDocument channelsDoc = new XmlDocument();
channelsDoc.Load("RssChannels.xml");
XmlNodeList channelsList = channelsDoc.GetElementsByTagName("channel");
this.RssChannelsListBox.DataContext = channelsList;
Lösung
Versuchen Sie, einen Filesystemwatcher
mit private static void StartMonitoring()
{
//Watch the current directory for changes to the file RssChannels.xml
var fileSystemWatcher = new FileSystemWatcher(@".\","RssChannels.xml");
//What should happen when the file is changed
fileSystemWatcher.Changed += fileSystemWatcher_Changed;
//Start watching
fileSystemWatcher.EnableRaisingEvents = true;
}
static void fileSystemWatcher_Changed(object sender, FileSystemEventArgs e)
{
Debug.WriteLine(e.FullPath + " changed");
}
Andere Tipps
Sie haben INotifyCollectionChanged auf eigene Faust zu implementieren, um für Änderungen Dateisystem zu beobachten verwenden, um die Filesystemwatcher-Klasse in System.IO
Die XmlDocument
wirft bereits NodeChanged
Ereignisse. Wenn Sie eine XmlDataProvider
als Bindungsquelle verwenden, hört es auf NodeChanged
Ereignisse und erfrischt die Bindungen. Es erfrischt auch die Bindungen, wenn Sie seine Document
Eigenschaft ändern. Kombiniert man dies mit dem FileSystemWatcher
und du bist auf dem Weg.
Ein einfaches Beispiel:
<Window x:Class="WpfApplication18.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window1" Height="300" Width="300">
<Window.Resources>
<XmlDataProvider x:Key="Data" XPath="/Data">
<x:XData>
<Data xmlns="">
<Channel>foo</Channel>
<Channel>bar</Channel>
<Channel>baz</Channel>
<Channel>bat</Channel>
</Data>
</x:XData>
</XmlDataProvider>
</Window.Resources>
<StackPanel Margin="50">
<ListBox ItemsSource="{Binding Source={StaticResource Data}, XPath=Channel}" />
<Button Margin="10"
Click="ReloadButton_Click">Reload</Button>
<Button Margin="10"
Click="UpdateButton_Click">Update</Button>
</StackPanel>
</Window>
Die Ereignishandler:
private void ReloadButton_Click(object sender, RoutedEventArgs e)
{
XmlDocument d = new XmlDocument();
d.LoadXml(@"<Data xmlns=''><Channel>foobar</Channel><Channel>quux</Channel></Data>");
XmlDataProvider p = Resources["Data"] as XmlDataProvider;
p.Document = d;
}
private void UpdateButton_Click(object sender, RoutedEventArgs e)
{
XmlDataProvider p = Resources["Data"] as XmlDataProvider;
XmlDocument d = p.Document;
foreach (XmlElement elm in d.SelectNodes("/Data/Channel"))
{
elm.InnerText = "Updated";
}
}