XamlReader/XamlWriterでXAMLを読み書き
XamlReaderクラスとXamlWriterクラスを使うことで、簡単にXAMLの読み書きができます。
ということで、さっそく使い方。
XamlWriterでWPFのコントロールとかをXAMLとして出力
XamlWriterにオブジェクトを渡すと、XAML形式のテキストを取得できます。
とりあえず、PageにGridを追加。Gridを2×2に分割してButtonを追加したものを用意し、このPageをXamlWriterで出力してみました。
サンプルコード
var page = new Page(); var grid = new Grid(); grid.ColumnDefinitions.Add(new ColumnDefinition()); grid.ColumnDefinitions.Add(new ColumnDefinition()); grid.RowDefinitions.Add(new RowDefinition()); grid.RowDefinitions.Add(new RowDefinition()); var button = new Button() { Content = "test" }; Grid.SetColumn(button, 1); Grid.SetRow(button, 1); grid.Children.Add(button); page.Content = grid; // XAMLで書き出し var text = XamlWriter.Save(page); File.WriteAllText(@"C:\temp\test.xaml", text);
出力結果
<Page xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"><Grid><Grid.ColumnDefinitions><ColumnDefinition /><ColumnDefinition /></Grid.ColumnDefinitions><Grid.RowDefinitions><RowDefinition /><RowDefinition /></Grid.RowDefinitions><Button Grid.Column="1" Grid.Row="1">test</Button></Grid></Page>
しかし、これで出力されるXAMLは、改行を含まず1行になっていて、
ファイルなどに書き出して読むには、読みにくい形となっています。
どうせテキストに落とすなら、読みやすい形にしたい。
XAMLファイルをフォーマットして出力
以下のサイトを参考に、XAMLのフォーマットをしてみました。
http://stackoverflow.com/questions/1123718/format-xml-string-to-print-friendly-xml-string
XAMLはXML形式のテキストなので、XDocumentを使ってXMLとして読み取ってから文字列に変換してます。
自分で下手に文字列をパースしてXAMLの整形をするよりも、こっちの方が信頼できそう。
XAMLを整形してから書き出し
private void Button_Click(object sender, RoutedEventArgs e) { var page = new Page(); var grid = new Grid(); grid.ColumnDefinitions.Add(new ColumnDefinition()); grid.ColumnDefinitions.Add(new ColumnDefinition()); grid.RowDefinitions.Add(new RowDefinition()); grid.RowDefinitions.Add(new RowDefinition()); var button = new Button() { Content = "test" }; Grid.SetColumn(button, 1); Grid.SetRow(button, 1); grid.Children.Add(button); page.Content = grid; // XAMLで書き出し var text = XamlWriter.Save(page); text = FormatXml(text); File.WriteAllText(@"C:\temp\test.xaml", text); } string FormatXml(String Xml) { try { XDocument doc = XDocument.Parse(Xml); return doc.ToString(); } catch (Exception) { return Xml; } }
出力結果
<Page xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"> <Grid> <Grid.ColumnDefinitions> <ColumnDefinition /> <ColumnDefinition /> </Grid.ColumnDefinitions> <Grid.RowDefinitions> <RowDefinition /> <RowDefinition /> </Grid.RowDefinitions> <Button Grid.Column="1" Grid.Row="1">test</Button> </Grid> </Page>
XamlReaderで読み込み
XamlWriterでの出力と同じように、XamlReaderを使うとXAMLファイルの読み込みができます。
前述のXamlWriterで出力したファイルを、XamlReaderで読み込んでみました。
読み込んだ結果のPageインスタンスを、ウィンドウに用意したFrameに設定して表示しています。
XAMLの読み込みテスト
private void Button_Click(object sender, RoutedEventArgs e) { var page = new Page(); var grid = new Grid(); grid.ColumnDefinitions.Add(new ColumnDefinition()); grid.ColumnDefinitions.Add(new ColumnDefinition()); grid.RowDefinitions.Add(new RowDefinition()); grid.RowDefinitions.Add(new RowDefinition()); var button = new Button() { Content = "test" }; Grid.SetColumn(button, 1); Grid.SetRow(button, 1); grid.Children.Add(button); page.Content = grid; // XAMLで書き出し var text = XamlWriter.Save(page); text = FormatXml(text); File.WriteAllText(@"C:\temp\test.xaml", text); // XAMLから読み込み Page readPage; using (var stream = File.Open(@"C:\temp\test.xaml", FileMode.Open)) { readPage = XamlReader.Load(stream) as Page; } frame.Content = readPage; } string FormatXml(String Xml) { try { XDocument doc = XDocument.Parse(Xml); return doc.ToString(); } catch (Exception) { return Xml; } }
XamlWriter/XamlReaderで任意のオブジェクトのシリアライズ
XamlWriter/XamlReaderでは、WPFなどで用いるコントロールだけでなく、任意のCLRオブジェクトの書き出し/読み込みもできます。
サンプルコード
public class SampleData { public string Name { get; set; } public int Age { get; set; } public double Data { get; set; } } class Program { static void Main(string[] args) { var data = new SampleData() { Name = "hoge", Age = 20, Data = 0.5 }; // XAML形式で書き出し var text = XamlWriter.Save(data); text = FormatXml(text); System.IO.File.WriteAllText(@"C:\temp\test.xaml", text); SampleData readData; using (var stream = File.Open(@"C:\temp\test.xaml", FileMode.Open)) { readData = XamlReader.Load(stream) as SampleData; } Console.WriteLine(readData.Name); Console.WriteLine(readData.Age); Console.WriteLine(readData.Data); } static string FormatXml(String Xml) { try { XDocument doc = XDocument.Parse(Xml); return doc.ToString(); } catch (Exception) { return Xml; } } }
出力結果
hoge 20 0.5 続行するには何かキーを押してください . . .