1

我正在开发 UWP 应用程序,但遇到了问题。该应用程序使用带有 Template10 的 MVVM 模式。我创建了一个类似的解决方案来重现我所面临的问题。在该解决方案中,会显示一个订单列表,用户选择一个订单,然后单击“编辑”按钮。然后显示第二个页面并预加载先前选择的订单,在此第二个页面中,用户可以编辑订单。问题出在第二页,绑定到组合框的数据没有显示。也许问题与这个问题有关。在我的例子中,SelectedValue 设置在 ItemsSource 之前。经过调试,我在 OrderEditionPage.g.cs 中达到了这些代码行:

private void Update_ViewModel(global::ComboApp.ViewModels.OrderEditionPageViewModel obj, int phase)
{
    this.bindingsTracking.UpdateChildListeners_ViewModel(obj);
    if (obj != null)
    {
        if ((phase & (NOT_PHASED | DATA_CHANGED | (1 << 0))) != 0)
        {
            this.Update_ViewModel_SelectedOrder(obj.SelectedOrder, phase);
        }
        if ((phase & (NOT_PHASED | (1 << 0))) != 0)
        {
            this.Update_ViewModel_BusinessAssociates(obj.BusinessAssociates, phase);
            this.Update_ViewModel_TransactionTypes(obj.TransactionTypes, phase);
            this.Update_ViewModel_OrderTypes(obj.OrderTypes, phase);
            this.Update_ViewModel_ShowSelectedOrder(obj.ShowSelectedOrder, phase);
        }
    }
}

如果我能实现这行代码最后被执行,我的问题就解决了: this.Update_ViewModel_SelectedOrder(obj.SelectedOrder, phase);

我怎么能做到这一点?Visual Studio 如何确定这些行的顺序?

OrderEditionPage.xaml

<Page
    x:Class="ComboApp.Views.OrderEditionPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:myconverters="using:ComboApp.Converters"
    xmlns:t10converters="using:Template10.Converters"
    mc:Ignorable="d">

    <Page.Resources>
        <t10converters:ChangeTypeConverter x:Key="TypeConverter" />
        <myconverters:DateTimeConverter x:Key="DateTimeConverter" />
    </Page.Resources>

    <ScrollViewer VerticalScrollBarVisibility="Auto">
        <StackPanel
            Padding="15, 5"
            Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
            <TextBox
                Header="Order #"
                Margin="5"
                Width="150"
                HorizontalAlignment="Left"
                Text="{x:Bind ViewModel.SelectedOrder.ExternalId, Mode=TwoWay}" />
            <ComboBox
                Header="Business Associate"
                Margin="5"
                MinWidth="300"
                SelectedValuePath="BusinessAssociateId"
                DisplayMemberPath="Name1"
                ItemsSource="{x:Bind ViewModel.BusinessAssociates}"
                SelectedValue="{x:Bind ViewModel.SelectedOrder.BusinessAssociateId, Mode=TwoWay, Converter={StaticResource TypeConverter}}" />
            <DatePicker
                Header="Delivery Date"
                Margin="5"
                MinWidth="0"
                Width="200"
                Date="{x:Bind ViewModel.SelectedOrder.DeliveryDate, Mode=TwoWay, Converter={StaticResource DateTimeConverter}}" />
            <ComboBox
                Header="Transaction"
                MinWidth="200"
                Margin="5"
                SelectedValuePath="Value"
                DisplayMemberPath="Display"
                ItemsSource="{x:Bind ViewModel.TransactionTypes}"
                SelectedValue="{x:Bind ViewModel.SelectedOrder.TransactionType, Mode=TwoWay}" />
            <TextBox
                Header="Priority"
                Margin="5"
                MaxWidth="150"
                HorizontalAlignment="Left"
                Text="{x:Bind ViewModel.SelectedOrder.Priority}" />
            <ComboBox
                Header="Type"
                Margin="5"
                MinWidth="200"
                SelectedValuePath="Value"
                DisplayMemberPath="Display"
                ItemsSource="{x:Bind ViewModel.OrderTypes}"
                SelectedValue="{x:Bind ViewModel.SelectedOrder.OrderType, Mode=TwoWay}" />
            <TextBox
                Header="Information"
                Margin="5"
                Height="100"
                AcceptsReturn="True"
                TextWrapping="Wrap"
                ScrollViewer.VerticalScrollBarVisibility="Auto"
                Text="{x:Bind ViewModel.SelectedOrder.Information, Mode=TwoWay}" />
            <Button
                Margin="5"
                Content="Show"
                Width="100"
                HorizontalAlignment="Right"
                Command="{x:Bind ViewModel.ShowSelectedOrder}" />
        </StackPanel>
    </ScrollViewer>
</Page>

OrderEditionPage.xaml.cs

using ComboApp.ViewModels;
using Windows.UI.Xaml.Controls;

namespace ComboApp.Views
{
    public sealed partial class OrderEditionPage : Page
    {
        public OrderEditionPageViewModel ViewModel => DataContext as OrderEditionPageViewModel;

        public OrderEditionPage()
        {
            this.InitializeComponent();
        }
    }
}

OrderEditionPageViewModel.cs

using ComboApp.Models;
using ComboApp.Services;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Threading.Tasks;
using Template10.Mvvm;
using Template10.Utils;
using Windows.UI.Xaml.Navigation;

namespace ComboApp.ViewModels
{
    public class OrderEditionPageViewModel
        : ViewModelBase
    {
        private IBusinessAssociateService businessAssociateService;

        private Order selectedOrder;
        public Order SelectedOrder
        {
            get { return selectedOrder; }
            set { Set(ref selectedOrder, value); }
        }

        public ObservableCollection<object> TransactionTypes { get; set; } = new ObservableCollection<object>();
        public ObservableCollection<object> OrderTypes { get; set; } = new ObservableCollection<object>();
        public ObservableCollection<BusinessAssociate> BusinessAssociates { get; set; } = new ObservableCollection<BusinessAssociate>();

        public OrderEditionPageViewModel(IBusinessAssociateService businessAssociateService)
        {
            this.businessAssociateService = businessAssociateService;

            TransactionTypes.Add(new { Value = "I", Display = "Incoming" });
            TransactionTypes.Add(new { Value = "O", Display = "Outgoing" });
            TransactionTypes.Add(new { Value = "T", Display = "Transfer" });

            OrderTypes.Add(new { Value = "M", Display = "Manual" });
            OrderTypes.Add(new { Value = "A", Display = "Automatic" });
            OrderTypes.Add(new { Value = "S", Display = "Semi-automatic" });
        }

        public override async Task OnNavigatedToAsync(object parameter, NavigationMode mode, IDictionary<string, object> state)
        {
            // Loading buiness associates
            var response = await businessAssociateService.GetNextPageAsync();
            if (response.IsSuccessful)
            {
                BusinessAssociates.AddRange(response.Result.Items);
            }

            SelectedOrder = (Order)parameter;
            await base.OnNavigatedToAsync(parameter, mode, state);
        }

        private DelegateCommand showSelectedOrder;
        public DelegateCommand ShowSelectedOrder => showSelectedOrder ?? (showSelectedOrder = new DelegateCommand(async () =>
        {
            await Views.MessageBox.ShowAsync(JsonConvert.SerializeObject(SelectedOrder, Formatting.Indented));
        }));

    }
}
4

1 回答 1

1

有时将 a 设置在其之前是x:Bind一个已知问题,您可以在此处阅读有关它的更多信息。SelectedValueComboBoxItemsSource

作为一种解决方法,您可以使用Bindings代替x:Bind,但请确保在 XAML中ItemsSource绑定之前放置绑定。SelectedValue

或者,您可以尝试Bindings.Update()Page_Loaded第二页的情况下拨打电话。

于 2017-11-16T23:48:22.140 回答