我们正在迁移到Winforms到基于WPF的解决方案。我们有自定义的XML定义,用于在运行时构建windows窗体。
既然XAML是基于XML的,那么我们可以定义一个带有XAML定义的HelloWorldWindow.xml文件吗?它可以在没有CSharp文件后面的任何代码的情况下加载到WPF应用程序中吗?我们将在运行时附加钩子后面的代码。
如何在运行时将代码附加到后台?
发布于 2010-11-02 12:50:53
使用此XAML创建XML文件Tempwin.xml
<UserControl
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Height="300" Width="300" Background="Transparent" >
<Border Background="Black" CornerRadius="10" BorderThickness="4" BorderBrush="RoyalBlue">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
</Grid.RowDefinitions>
<TextBlock Text="Sample Text" Foreground="White" Margin="2"></TextBlock>
<TextBox Grid.Row="1" Margin="5"> </TextBox>
<TextBlock Text="Sample Text 1" Grid.Row="2" Foreground="White" Margin="2"></TextBlock>
<TextBox Grid.Row="3" Margin="5"></TextBox>
<Ellipse Fill="Red" Height="100" Width="100" Grid.Row="4" Margin="0,10,0,0"></Ellipse>
</Grid>
</Border>
使用以下xaml创建示例WPF应用程序
<Window x:Class="WpfApplication12.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window1" Height="600" Width="600">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition/>
</Grid.RowDefinitions>
<Button Height="25" Width="100" Margin="2" Click="Button_Click"> Show Content</Button>
<Grid x:Name="content" Grid.Row="1" Margin="2">
</Grid>
</Grid>
将下面的C#代码粘贴到Button_Click后面的代码中
StreamReader mysr = new StreamReader(@"D:\Tempwin.xml");
FrameworkElement rootObject = XamlReader.Load(mysr.BaseStream) as FrameworkElement;
content.Children.Add(rootObject);
如果要在运行时加载xaml,则不能在XAML文件后面提供任何代码。因此,我在创建xml之前删除了x:Class属性
事件挂钩...
<UserControl
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Height="300" Width="300" Background="Transparent" >
<Border Background="Black" CornerRadius="10" BorderThickness="4" BorderBrush="RoyalBlue">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
</Grid.RowDefinitions>
<TextBlock Text="Sample Text" Foreground="White" Margin="2"></TextBlock>
<TextBox Grid.Row="1" Margin="5"> </TextBox>
<TextBlock Text="Sample Text 1" Grid.Row="2" Foreground="White" Margin="2"></TextBlock>
<TextBox Grid.Row="3" Margin="5"></TextBox>
<Ellipse Fill="Red" Height="100" Width="100" Grid.Row="4" Margin="0,10,0,0"></Ellipse>
<Button Grid.Row="5" Height="25" Content="Event added at Runtime" x:Name="btnTest"></Button>
</Grid>
</Border>
Button ButtoninXAML;
private void Button_Click(object sender, RoutedEventArgs e)
{
StreamReader mysr = new StreamReader(@"D:\Tempwin.xml");
FrameworkElement rootObject = XamlReader.Load(mysr.BaseStream) as FrameworkElement;
ButtoninXAML = LogicalTreeHelper.FindLogicalNode(rootObject, "btnTest") as Button;
ButtoninXAML.Click += new RoutedEventHandler(Button_Click1);
content.Children.Add(rootObject);
}
private void Button_Click1(object sender, RoutedEventArgs e)
{
MessageBox.Show("Added At Runtime");
}
发布于 2010-11-02 12:34:49
您可以像这样动态显示Xaml:
string text = @"<TextBlock Text='test' xmlns='http://schemas.microsoft.com/winfx/2006/xaml/presentation' />";
// Convert to stream
// You can also just stream the xaml from a file, using a FileStream
MemoryStream stream = new MemoryStream(ASCIIEncoding.UTF8.GetBytes(text));
// Convert to object
TextBlock block = (TextBlock)System.Windows.Markup.XamlReader.Load(stream);
//... now you can put that TextBlock somewhere, for example in your main Window
有关更多信息,请参见XamlReader类:http://msdn.microsoft.com/en-us/library/ms613427%28v=VS.95%29.aspx
发布于 2013-05-30 09:40:55
我已经完成了在运行时加载XAML,下面是一个简短的示例
Grid grd = new Grid();
var grdEncoding = new ASCIIEncoding();
var grdBytes = grdEncoding.GetBytes(myXAML);
grd = (Grid)XamlReader.Load(new MemoryStream(grdBytes));
Grid.SetColumn(grd, 0);
Grid.SetRow(grd, 0);
parentGrid.Children.Add(grd);
private String myXAML = @" <Grid xmlns='http://schemas.microsoft.com/winfx/2006/xaml/presentation' Margin='30 10 30 65' VerticalAlignment='Bottom'>" +
"<Label Content='Date: 1-Feb-2013' FontFamily='Arial' FontSize='12' Foreground='#666666' HorizontalAlignment='Left'/>" +
"<Label Content='4' FontFamily='Arial' FontSize='12' Foreground='#666666' HorizontalAlignment='Center'/>" +
"<Label Content='Hello World' FontFamily='Arial' FontSize='12' Foreground='#666666' HorizontalAlignment='Right'/>" +
"</Grid>";
https://stackoverflow.com/questions/4077318
复制