textBlock не обновляется (RaisePropertyChanged не работает?) - PullRequest
0 голосов
/ 02 ноября 2019

В моей программе два окна. Содержимое TextBox в MainWindow должно изменить содержимое TextBlock в CalcWindow. Однако TextBlock не изменяется даже после изменения TextBox.

Я добавил RaisePropertyChanged в UISimpleData. Итак, содержимое TextBox корректно изменено. Но это не меняет TextBlock в CalcWindow.

MainWindow.xaml

<Window x:Class="DoubleToTextBlockBinding.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="DataUpdate" Height="220.276" Width="400">

    <Grid Height="190" Margin="0,0,-0.667,0" VerticalAlignment="Top">
        <Label Content="Target Value" HorizontalAlignment="Right" Margin="0,0,112,142" VerticalAlignment="Bottom" Width="78"/>
        <TextBox Margin="0,0,24,142" HorizontalAlignment="Right" VerticalAlignment="Bottom" Height="22" Width="60"
                 Text="{Binding DoubleField, UpdateSourceTrigger=PropertyChanged, ValidatesOnDataErrors=True}">
            <TextBox.Style>
                <Style TargetType="{x:Type TextBox}">
                    <Style.Triggers>
                        <Trigger Property="Validation.HasError" Value="true">
                            <Setter Property="ToolTip" Value="{Binding (Validation.Errors)[0].ErrorContent, 
                                RelativeSource={RelativeSource Self}}"/>
                        </Trigger>
                    </Style.Triggers>
                </Style>
            </TextBox.Style>
        </TextBox>
        <TextBlock Text="{Binding DoubleField}" HorizontalAlignment="Right" VerticalAlignment="Bottom" 
                   Margin="0,0,25,115" Height="22" Width="60"/>
        <Button Name="ConfirmButton" Content="Confirm" Margin="85,0,25.666,58" HorizontalAlignment="Right" VerticalAlignment="Bottom" Click="ConfirmButton_Click"/>
    </Grid>
</Window>

MainWindow.xaml.cs

using DoubleToTextBlockBinding.ViewModels;
using DoubleToTextBlockBinding.Views;
using System.Windows;

namespace DoubleToTextBlockBinding
{
    public partial class MainWindow : Window
    {
        private UISimpleData _uiData = new UISimpleData();

        public MainWindow()
        {
            InitializeComponent();
            DataContext = _uiData;
        }

        private void ConfirmButton_Click(object sender, RoutedEventArgs e)
        {
            new CalcWindow().Show();
        }
    }
}

App.xaml.cs

using System.Windows;

namespace DoubleToTextBlockBinding
{
    public partial class App : Application
    {
        public App()
        {
            System.Windows.FrameworkCompatibilityPreferences
                       .KeepTextBoxDisplaySynchronizedWithTextProperty = false;
        }
    }
}

Просмотров / CalcWindow.xaml

<Window xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:viewModels="clr-namespace:DoubleToTextBlockBinding.ViewModels"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        mc:Ignorable="d"
        x:Class="DoubleToTextBlockBinding.Views.CalcWindow"
        Title="Bound Window" Width="400" Height="212">
    <Grid>
        <TextBlock Text="{Binding DoubleField}" x:Name="textBox"  Width="104"
            Margin="148,84,0,0" HorizontalAlignment="Left" VerticalAlignment="Top">
            <TextBlock.DataContext>
                <viewModels:UISimpleData/>
            </TextBlock.DataContext>
        </TextBlock>
    </Grid>
</Window>

Просмотров/CalcWindow.xaml.cs

using System.Windows;
using DoubleToTextBlockBinding.ViewModels;

namespace DoubleToTextBlockBinding.Views
{
    public partial class CalcWindow : Window
    {
        private UISimpleData _uiData = new UISimpleData();
        public CalcWindow()
        {
            InitializeComponent();
            this.DataContext = _uiData;
        }
    }
}

ViewModels / UISimpleData.cs

using System;
using System.ComponentModel;
using System.Windows;

namespace DoubleToTextBlockBinding.ViewModels
{
    public class UISimpleData : INotifyPropertyChanged, IDataErrorInfo
    {
        private double _doubleField = 2.0;

        public double DoubleField
        {
            get
            {
                return _doubleField;
            }
            set
            {
                if (_doubleField == value)
                    return;

                _doubleField = value;
                RaisePropertyChanged("DoubleField");
            }
        }

        public string this[string propertyName]
        {
            get
            {
                string validationResult = null;
                switch (propertyName)
                {
                    case "DoubleField":
                        {
                            if (DoubleField < 0 || DoubleField > 5)
                                validationResult = "DoubleField is out of range";
                            break;
                        }
                    default:
                        throw new ApplicationException("Unknown Property being validated on UIData");
                }
                return validationResult;
            }
        }

        public string Error { get { return "Not Implemented"; } }

        public event PropertyChangedEventHandler PropertyChanged;

        protected void RaisePropertyChanged(string property)
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(property));
            //MessageBox.Show("Changed to " + DoubleField);
        }
    }
}

Ожидаемое поведение:

  1. Измените содержимое TextBox на «3».

(Вы увидите, что TextBlock в том же окне изменится на «3».)

Нажмите на кнопку «Подтвердить».

Появится новое окно. Проверьте, является ли содержимое TextBlock "3".

(Фактический результат здесь становится «2».)

... Это лучшее, что я могу сделать на данный момент. Пожалуйста, помогите мне. Спасибо.

1 Ответ

1 голос
/ 02 ноября 2019

вы создаете новые экземпляры вашей модели представления в обоих классах. Если вы изменяете что-то в модели представления в MainWindow, вы должны передать эту модель в CalcWindow.

Я предполагаю, что вы должны написать конструктор для CalcWindow следующим образом:

public CalcWindow(UISimpleData yourViewModelFromMainWindow)
{
    InitializeComponent();
    this.DataContext = yourViewModelFromMainWindow;
}

ив MainWindow, в методе ConfirmButton_Click

private void ConfirmButton_Click(object sender, RoutedEventArgs e)
{
    new CalcWindow(this.DataContext as UISimpleData).Show();
}

Я надеюсь, что это полезно. Если это не так, не стесняйтесь спрашивать.

...