C#中的QSON和XAML数据绑定的问题

发布于 2025-02-11 00:30:41 字数 2719 浏览 1 评论 0原文

我正在尝试将构建为C#的PowerShell WPF应用程序转换,但是我遇到了DataContext/Data Binding的问题。

在我的许多搜索中,我访问了以下示例代码,但是当我实现它时,通过IntelliSense显示的属性可以绑定在XAML中,但似乎没有任何实际绑定。我不确定怎么了。我是C#的新手(一些vb.net/powershell背景),所以我可能只是不了解某些东西。

在我的情况下,具有vs 2022和c#的理由代码

using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;

namespace WpfApp1

{
    /// <summary>
    /// Interaction logic for Window7.xaml
    /// </summary>

    public partial class Window7 : Window

    {
        public Window7()
        {
            InitializeComponent();
            string jsonString = @"{
                        'Name' : 'Apple',  
                        'ExpiryDate' : '2018-01-02',
                        'Price' : 3.99
                        }";

            try
            {
                JsonClass jsonClass = JsonConvert.DeserializeObject<JsonClass>(jsonString);
                DataContext = jsonClass;    // I don't understand the point of this line. 
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
        }
    }

    public class JsonClass

    {
        public string Name { get; set; }
        public DateTime ExpiryDate { get; set; }
        public decimal Price { get; set; }
   }
}

XAML参考

<Window x:Class="WpfApp1.Window7"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfApp1"
        mc:Ignorable="d"
        Title="Window7" Height="300" Width="300">

    <Window.DataContext>
        <local:JsonClass/>    # This seems to point to a Class definition, not an actual instance.
    </Window.DataContext>
        
    <Grid>
        <TextBox Text="{Binding Path=Name}"/>
    </Grid>

</Window>

,我的语法略有不同,但不确定很重要。不过,我真的不了解代码中的以下行:

datacontext = jsonClass;

我假设这将窗口的dataContext设置为jsonClass的实例jsonclass nate jsonclass(lowercase json),但XML专门指定课程本身(Capital JsonClass),所以我并不关注实际使用我选择的JSON数据的位置。

    <Window.DataContext>
        <local:JsonClass/>
    </Window.DataContext>

I'm trying to convert a powershell WPF application I built to C#, but I'm running into an issue with the datacontext/data binding.

In my many searches I ran across the following sample code, but when I implemented it, the properties show up via intellisense to bind in the XAML but nothing seems to actually bind. I'm not sure what is wrong. I'm new to C# (some VB.net/Powershell background), so it's likely me just not understanding something.

Deserialization code

using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;

namespace WpfApp1

{
    /// <summary>
    /// Interaction logic for Window7.xaml
    /// </summary>

    public partial class Window7 : Window

    {
        public Window7()
        {
            InitializeComponent();
            string jsonString = @"{
                        'Name' : 'Apple',  
                        'ExpiryDate' : '2018-01-02',
                        'Price' : 3.99
                        }";

            try
            {
                JsonClass jsonClass = JsonConvert.DeserializeObject<JsonClass>(jsonString);
                DataContext = jsonClass;    // I don't understand the point of this line. 
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
        }
    }

    public class JsonClass

    {
        public string Name { get; set; }
        public DateTime ExpiryDate { get; set; }
        public decimal Price { get; set; }
   }
}

XAML reference

<Window x:Class="WpfApp1.Window7"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfApp1"
        mc:Ignorable="d"
        Title="Window7" Height="300" Width="300">

    <Window.DataContext>
        <local:JsonClass/>    # This seems to point to a Class definition, not an actual instance.
    </Window.DataContext>
        
    <Grid>
        <TextBox Text="{Binding Path=Name}"/>
    </Grid>

</Window>

In my case, with VS 2022 and C# I'm my syntax is slightly different but not sure that matters. I'm really not understanding the following line in the code though:

DataContext = jsonClass;

I assume this is setting the window's datacontext to the instance of JsonClass named jsonClass (lowercase json), but the XML specifically specifies the class itself (capital JsonClass) so I'm not following where the json data I deserialized is actually being used.

    <Window.DataContext>
        <local:JsonClass/>
    </Window.DataContext>

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

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

发布评论

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

评论(1

酷炫老祖宗 2025-02-18 00:30:41

我有没有办法在后面的代码之外静态设置/初始化此信息,例如直接在XAML中?

您可以将设计时间 dataContext设置为类似类的实例:

<Window ...
        d:DataContext="{d:DesignInstance local:JsonClass, IsDesignTimeCreatable=True}"
        >

然后,您可以实现此类以返回设计时间值:

public class JsonClass
{
    public string Name { get; set; } = "Apple";
    public DateTime ExpiryDate { get; set; } = new DateTime(2018, 1, 2);
    public decimal Price { get; set; } = 3.99m;
}

但是您不应依靠设计师验证运行时行为。

我完全得到D:DataContext是方式...我只是在问是否可以将运行时和设计时间的DataContext指向同一视图模型实例?

IE IE在XAML中实例化DataContext似乎有效:

<Window.Resources>
    <local:JsonClass x:Key="viewModel" Name="Test" />
</Window.Resources>
<Window.DataContext>
    <StaticResource ResourceKey="viewModel" />
</Window.DataContext>
<Grid>
    <TextBox Text="{Binding Path=Name}"/>
</Grid>

如果您动态地获取属性的值,则可以尝试在代码范围内检验资源并设置其属性。然后,您可能还应实现inotifyPropertychanged接口。

但是我建议您使用d:datacontext使用设计时间上下文,并且不要将代码采用给Visual Studio Designer ...

Is there a way for me to statically set/initialize this information outside of the code behind, e.g. directly in the XAML?

You can set the design time DataContext to an instance of a class like this:

<Window ...
        d:DataContext="{d:DesignInstance local:JsonClass, IsDesignTimeCreatable=True}"
        >

You can then implement this class to return design time values:

public class JsonClass
{
    public string Name { get; set; } = "Apple";
    public DateTime ExpiryDate { get; set; } = new DateTime(2018, 1, 2);
    public decimal Price { get; set; } = 3.99m;
}

But you should not rely on the designer to verify runtime behaviour.

I totally get the d:DataContext is the way...I'm simply asking if it's possible to point the DataContext for both runtime and design time to the same view model instance?

This, i.e. instantiating the DataContext in the XAML seems to work:

<Window.Resources>
    <local:JsonClass x:Key="viewModel" Name="Test" />
</Window.Resources>
<Window.DataContext>
    <StaticResource ResourceKey="viewModel" />
</Window.DataContext>
<Grid>
    <TextBox Text="{Binding Path=Name}"/>
</Grid>

If you get the values of the properties dynamically, you could try to retrive the resource in the code-behind and set the properties of it. Then you should probably also implement the INotifyPropertyChangedinterface.

But I would recommend you to use a design time context using d:DataContext and not adopt your code to the Visual Studio designer...

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文