如何将数据绑定 XAML 控件呈现到本机 XAML 绘图

发布于 2024-10-17 07:46:37 字数 700 浏览 2 评论 0原文

我有一个像这样的数据绑定 XAML 控件:

<UserControl>
    <TextBlock Text="{Binding Text}" />
</UserControl>

并希望它呈现为这样的“绘图”:

<UserControl>
    <TextBlock Text="Actual text value" />
</UserControl>

有谁知道如何从任意控件中提取绘图?

更新: 这个问题似乎不太清楚。所以我尝试多解释一下。 输入是具有数据绑定的 XAML 控件。现在我想将其转换为纯 XAML,无需任何数据绑定。输出可以写入磁盘并由任何理解 XAML 的应用程序显示,而无需绑定任何内容。

所以解决方案应该看起来像这样:

FrameworkElementinput = (FrameworkElement)XamlReader.Read(inputFile);
input.DataContext = dataObject;
FrameworkElement output = ConvertToNative(input);
XamlWriter.Write(outputFile, output);

我正在寻找“ConvertToNative”的实现

I have a data bound XAML control like this:

<UserControl>
    <TextBlock Text="{Binding Text}" />
</UserControl>

and want it to render as a 'drawing' like this:

<UserControl>
    <TextBlock Text="Actual text value" />
</UserControl>

Does anyone know how to extract the drawing from an arbitrary control?

UPDATE:
This question does not seem to be clear. So I try to explain a bit more.
The input is a XAML control with databinding. Now I want to convert this to plain XAML without any databinding. The output can be written to disk and displayed by any application which understands XAML, without binding to anything.

So the solution should look something like this:

FrameworkElementinput = (FrameworkElement)XamlReader.Read(inputFile);
input.DataContext = dataObject;
FrameworkElement output = ConvertToNative(input);
XamlWriter.Write(outputFile, output);

I'm looking for an implementation of 'ConvertToNative'

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

时常饿 2024-10-24 07:46:37

如果您要对 UserControl 执行此操作,请确保首先删除 x:Class 属性,否则您将收到 XamlParseException

您可以使用 XamlReader.Load 加载 Xaml 文件,并在使用 XamlWriter.Save 保存该文件时,绑定将转换为其实际值。不过,更新绑定似乎存在一些问题,因此我通过订阅 Loaded 事件并将其添加到 UI 中的容器中来解决此问题,然后在事件处理程序中从容器中删除 if ,然后保存它。不过,这可能可以通过更好的方式解决。

private void SomeMethod()
{
    CreateXamlWithBindingValues("UserControl1.xaml", "UserControl1_Saved.xaml");
}
private void CreateXamlWithBindingValues(string sourcePath, string savePath)
{
    StreamReader streamReader = new StreamReader(sourcePath);
    StringReader stringReader = new StringReader(streamReader.ReadToEnd());
    XmlReader xmlReader = XmlReader.Create(stringReader);
    FrameworkElement loadedObject = (FrameworkElement)XamlReader.Load(xmlReader);
    loadedObject.DataContext = UserControlViewModel;

    RoutedEventHandler routedEventHandler = null;
    routedEventHandler = new RoutedEventHandler(delegate
    {
        loadedObject.Loaded -= routedEventHandler;
        grid1.Children.Remove(loadedObject);

        string savedObject = XamlWriter.Save(loadedObject);
        StreamWriter streamWriter = new StreamWriter(savePath);
        streamWriter.Write(savedObject);
        streamWriter.Close();
    });
    loadedObject.Loaded += routedEventHandler;
    grid1.Children.Add(loadedObject);
}

保存前的 Xaml

<UserControl xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             mc:Ignorable="d" 
             d:DesignHeight="300" d:DesignWidth="300">
    <Grid>
        <TextBlock Text="{Binding Text}"/>
    </Grid>
</UserControl>

保存后的 Xaml 如您所见,没有换行符,但文本值是绑定生成的值

<UserControl xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"><Grid><TextBlock Text="Actual Text Value" /></Grid></UserControl>

保存前的 Xaml

<Grid Name="grid1" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
    <Button Content="{Binding MyContent}"/>
</Grid>

保存后的 Xaml

<Grid Name="grid1" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"><Button>Actual Content</Button></Grid>

If you're gonna do this for a UserControls, make sure to remove the x:Class attribute first since you'll get a XamlParseException otherwise.

You can load the Xaml file with XamlReader.Load and when you save it with XamlWriter.Save, the Bindings are translated to their actual value. There seems to be some trouble getting the Bindings to update though so I worked around this by subscribing to the Loaded event and add it to a container in the UI, and in the event handler remove if from the container and then save it. This can probably be worked around in a better way though..

private void SomeMethod()
{
    CreateXamlWithBindingValues("UserControl1.xaml", "UserControl1_Saved.xaml");
}
private void CreateXamlWithBindingValues(string sourcePath, string savePath)
{
    StreamReader streamReader = new StreamReader(sourcePath);
    StringReader stringReader = new StringReader(streamReader.ReadToEnd());
    XmlReader xmlReader = XmlReader.Create(stringReader);
    FrameworkElement loadedObject = (FrameworkElement)XamlReader.Load(xmlReader);
    loadedObject.DataContext = UserControlViewModel;

    RoutedEventHandler routedEventHandler = null;
    routedEventHandler = new RoutedEventHandler(delegate
    {
        loadedObject.Loaded -= routedEventHandler;
        grid1.Children.Remove(loadedObject);

        string savedObject = XamlWriter.Save(loadedObject);
        StreamWriter streamWriter = new StreamWriter(savePath);
        streamWriter.Write(savedObject);
        streamWriter.Close();
    });
    loadedObject.Loaded += routedEventHandler;
    grid1.Children.Add(loadedObject);
}

Xaml before Save

<UserControl xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             mc:Ignorable="d" 
             d:DesignHeight="300" d:DesignWidth="300">
    <Grid>
        <TextBlock Text="{Binding Text}"/>
    </Grid>
</UserControl>

Xaml after Save As you can see, there's no linebreaks but the Text value is the value produced from the binding

<UserControl xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"><Grid><TextBlock Text="Actual Text Value" /></Grid></UserControl>

Xaml before Save

<Grid Name="grid1" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
    <Button Content="{Binding MyContent}"/>
</Grid>

Xaml after Save

<Grid Name="grid1" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"><Button>Actual Content</Button></Grid>
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文