【问题标题】:UWP Community Toolkit MasterDetailsView not binding as expectedUWP 社区工具包 MasterDetailsView 未按预期绑定
【发布时间】:2020-03-05 16:57:05
【问题描述】:

我一直在尝试从 UWP 社区工具包中实现 MasterDetailsView,但收效甚微。我用我自己的类镜像了 SampleApp 源代码,但无法获得我用来在主窗格或详细信息窗格中显示的列表。最后,我尝试在 VS 中创建一个新项目,并完全复制 SampleApp 中列出的源代码,使用与 Sample App 相同的 Email 类。尽管完美地复制了所有内容,但我得到了相同的结果。

我注意到 VS 的输出窗口中有几个绑定错误(如下所示),这表明这是一个绑定问题,但据我所知,我遵循了在其他应用程序上使用的正常绑定格式以及其他控件。

错误示例:

Error: BindingExpression path error: 'Emails' property not found on 'MasterDetailsTest.MainPage'. BindingExpression: Path='Emails' DataItem='MasterDetailsTest.MainPage'; target element is 'Microsoft.Toolkit.Uwp.UI.Controls.MasterDetailsView' (Name='null'); target property is 'ItemsSource' (type 'Object')

在 StackOverflow 上至少还有一个与此相同问题的其他问题(我想我已经看到了更多),但没有接受的答案,并且没有一个不接受的答案为我解决了这个问题。我还尝试检查 github 上的 Toolkit Sample App 源代码,看看 SampleApp 中是否缺少列出的源代码,但所有内容都相同。

我在下面粘贴我的源代码,有人可以帮忙确定这是怎么回事吗?

上一个问题(没有接受的答案)

Master-Details view in UWP Community Toolkit

MainPage.xaml:

<Page
    x:Class="MasterDetailsTest.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:MasterDetailsTest"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:controls="using:Microsoft.Toolkit.Uwp.UI.Controls"
    mc:Ignorable="d"
    Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
    <controls:MasterDetailsView BackButtonBehavior="Automatic" ItemsSource="{Binding Emails}" NoSelectionContent="Select an item to view" CompactModeThresholdWidth="720">
        <controls:MasterDetailsView.ItemTemplate>
            <DataTemplate>
                <StackPanel Margin="8,0">
                    <TextBlock Text="{Binding From}" Style="{ThemeResource SubtitleTextBlockStyle}" />
                    <TextBlock Text="{Binding Subject}" Style="{ThemeResource BodyTextBlockStyle}" Foreground="{ThemeResource Brush-Blue-01}" MaxLines="1" />
                    <TextBlock Text="{Binding Body}" Style="{ThemeResource BodyTextBlockStyle}" Opacity="0.6" MaxLines="1" />
                </StackPanel>
            </DataTemplate>
        </controls:MasterDetailsView.ItemTemplate>
        <controls:MasterDetailsView.DetailsTemplate>
            <DataTemplate>
                <RelativePanel Margin="24">
                    <controls:ImageEx x:Name="FromEllipse" Source="{Binding Thumbnail}" Width="50" Height="50" CornerRadius="999" />
                    <TextBlock Text="{Binding From}" Style="{ThemeResource SubtitleTextBlockStyle}" RelativePanel.RightOf="FromEllipse" Margin="12,-6,0,0" />
                    <TextBlock x:Name="SubjectLine" Text="{Binding Subject}" Style="{ThemeResource BodyTextBlockStyle}" RelativePanel.Below="FromEllipse" Margin="0,12,0,0" />
                    <TextBlock x:Name="Body" Text="{Binding Body}" Style="{ThemeResource BodyTextBlockStyle}" TextWrapping="Wrap" RelativePanel.Below="SubjectLine" Margin="0,12,0,0" />
                </RelativePanel>
            </DataTemplate>
        </controls:MasterDetailsView.DetailsTemplate>
        <controls:MasterDetailsView.NoSelectionContentTemplate>
            <DataTemplate>
                <StackPanel HorizontalAlignment="Center" VerticalAlignment="Center">
                    <SymbolIcon Symbol="Mail" RenderTransformOrigin="0.5,0.5">
                        <SymbolIcon.RenderTransform>
                            <CompositeTransform ScaleX="2" ScaleY="2" />
                        </SymbolIcon.RenderTransform>
                    </SymbolIcon>
                    <TextBlock Text="{Binding}" FontSize="24" Margin="0,12" />
                </StackPanel>
            </DataTemplate>
        </controls:MasterDetailsView.NoSelectionContentTemplate>
        <controls:MasterDetailsView.MasterCommandBar>
            <CommandBar>
                <AppBarButton Icon="Back" Label="Back" />
                <AppBarButton Icon="Forward" Label="Forward" />
                <CommandBar.Content>
                    <TextBlock Margin="12,14">
                            <Run Text="{Binding Emails.Count}" />
                            <Run Text="Items" />
                    </TextBlock>
                </CommandBar.Content>
            </CommandBar>
        </controls:MasterDetailsView.MasterCommandBar>
        <controls:MasterDetailsView.DetailsCommandBar>
            <CommandBar>
                <AppBarButton Icon="MailReply" Label="Reply" />
                <AppBarButton Icon="MailReplyAll" Label="Reply All" />
                <AppBarButton Icon="MailForward" Label="Forward" />
            </CommandBar>
        </controls:MasterDetailsView.DetailsCommandBar>
    </controls:MasterDetailsView>
</Page>

MainPage.xaml.cs:

using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices.WindowsRuntime;
using Windows.Foundation;
using Windows.Foundation.Collections;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Controls.Primitives;
using Windows.UI.Xaml.Data;
using Windows.UI.Xaml.Input;
using Windows.UI.Xaml.Media;
using Windows.UI.Xaml.Navigation;

namespace MasterDetailsTest
{
    public sealed partial class MainPage : Page
    {
        List<Email> Emails = new List<Email>
        {            
            new Email {From = "Steve Johnson", Subject = "Lunch Tomorrow", Body = "Are you available for lunch tomorrow? A client would like to discuss a project with you." },
            new Email { From = "Becky Davidson", Subject = "Kids game", Body = "Don't forget the kids have their soccer game this Friday. We have to supply end of game snacks." },
            new Email { From = "OneDrive", Subject = "Check out your event recap", Body = "Your new album.\r\nYou uploaded some photos to yuor OneDrive and automatically created an album for you." },
            new Email { From = "Twitter", Subject = "Follow randomPerson, APersonYouMightKnow", Body = "Here are some people we think you might like to follow:\r\n.@randomPerson\r\nAPersonYouMightKnow" },
        };

        public MainPage()
        {
            this.InitializeComponent();
            DataContext = this;
        }
    }
}

Email.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace MasterDetailsTest
{
    public class Email
    {
        public string From { get; set; }
        public string Subject { get; set; }
        public string Body { get; set; }
        public Uri Thumbnail { get; set; }
    }    
}

【问题讨论】:

    标签: c# xaml uwp binding windows-community-toolkit


    【解决方案1】:

    这不是绑定问题,而是渲染问题。

    在渲染过程中,由于缺少一些关键内容而无法渲染。但是因为我们使用的是Binding关键字而不是x:Bind,所以在运行时遇到渲染错误不会报错,而是中止渲染Email项,所以我们会看到一个空白。

    缺少的内容如下:

    1. 刷机:Brush-Blue-01
    2. 类字段:Thumbnail

    Brush-Blue-01出现在MasterDetailsView.ItemTemplate中,如果你没有定义这个画笔那么你需要替换或者删除它。

    Thumbnail出现在MasterDetailsView.DetailsTemplate中,应该是Email类中的一个属性,如果没有定义,也会导致异常。所以可以考虑删除引用该属性的控件,或者完善Email类的定义。

    【讨论】:

    • 我在发布之前确实添加了这两个,抱歉我忘记了它们不是 SampleApp 中代码的一部分。我刚刚编辑了问题以显示我正在使用的电子邮件类,其中包含缩略图,并且我将 Brush-Blue-01 添加到 App.xaml 中(不想发布那么多代码)。我也只是在删除这些后再次尝试运行它,并得到了相同的结果。还有什么可能导致这种情况的吗?
    • 您好,请将MasterDetailsView.ItemsSource的绑定关键字改为x:Bind,可以在编译时绑定。
    • 其实我只是想在这里发帖,我才弄明白的。需要使用x:Bind 而不是Binding,但也需要在&lt;DataTemplate&gt; 上使用x:DataType。我之前尝试过,但我只是意识到,当我这样做时,我只在第一部分(ItemsTemplate)上尝试过,而不是在第二部分(DetailTemplate
    • 一般情况下,对于预定义的集合,使用x:Bind对程序查找绑定对象更有帮助,所以可以修改代码帮助自己使用
    【解决方案2】:

    通过与 Richard Zhang(在 cmets 上方)的讨论,我发现了这个问题的全部问题。这个问题实际上有两个组成部分,都相互关联。

    1. 社区工具包 SampleApp 使用 {Binding} 而不是 {x:Bind},这需要在代码文件和 XAML 中设置 ItemsSource
    2. 此外,XAML 中的DataTemplate 还需要设置{x:DataType}

    注意:要使{x:Bind} 正常工作,ItemsSource(在本例中为List&lt;Email&gt;)必须是全局成员;它必须在类中声明,但在任何函数之外。它可以在函数中定义/操作,但初始声明需要在类级别(我通常将它们作为类中的第一件事,紧跟在左括号之后)。

    在发布问题之前,我已经分别尝试了这些方法,但没有同时尝试。一旦我进行了这两项更改(以及DataTemplate 部分),一切都按预期进行。

    为了将来参考,正确的 XAML 代码粘贴在下面:

    <controls:MasterDetailsView BackButtonBehavior="Automatic" ItemsSource="{x:Bind inbox}" NoSelectionContent="Select an item to view" CompactModeThresholdWidth="720">
        <controls:MasterDetailsView.ItemTemplate>
            <DataTemplate x:DataType="local:Email">
                <StackPanel Margin="8,0">
                    <TextBlock Text="{x:Bind From}" Style="{ThemeResource SubtitleTextBlockStyle}" />
                    <TextBlock Text="{x:Bind Subject}" Style="{ThemeResource BodyTextBlockStyle}" Foreground="{ThemeResource Brush-Blue-01}" MaxLines="1" />
                    <TextBlock Text="{x:Bind Body}" Style="{ThemeResource BodyTextBlockStyle}" Opacity="0.6" MaxLines="1" />
                </StackPanel>
            </DataTemplate>
        </controls:MasterDetailsView.ItemTemplate>
        <controls:MasterDetailsView.DetailsTemplate>
            <DataTemplate x:DataType="local:Email">
                <RelativePanel Margin="24">
                    <controls:ImageEx x:Name="FromEllipse" Source="{x:Bind Thumbnail}" Width="50" Height="50" CornerRadius="999" />
                    <TextBlock Text="{x:Bind From}" Style="{ThemeResource SubtitleTextBlockStyle}" RelativePanel.RightOf="FromEllipse" Margin="12,-6,0,0" />
                    <TextBlock x:Name="SubjectLine" Text="{x:Bind Subject}" Style="{ThemeResource BodyTextBlockStyle}" RelativePanel.Below="FromEllipse" Margin="0,12,0,0" />
                    <TextBlock x:Name="Body" Text="{x:Bind Body}" Style="{ThemeResource BodyTextBlockStyle}" TextWrapping="Wrap" RelativePanel.Below="SubjectLine" Margin="0,12,0,0" />
                </RelativePanel>
            </DataTemplate>
        </controls:MasterDetailsView.DetailsTemplate>
    

    【讨论】:

      猜你喜欢
      • 2017-09-12
      • 1970-01-01
      • 2023-03-11
      • 2019-05-26
      • 2020-03-20
      • 1970-01-01
      • 2020-03-10
      • 2019-11-09
      • 2018-02-25
      相关资源
      最近更新 更多