简体   繁体   English

从一个视图切换到另一个视图时,如何保持用户控件的 Textbox Text 属性的值?

[英]How do I persist the value of the Textbox Text property of a user control when switching from one view to another?

Learning C#, specifically WPF, and the MVVM framework.学习 C#,特别是 WPF,以及 MVVM 框架。 I'm creating a basic project that presents a MainWindow with a contentcontrol binding.我正在创建一个基本项目,它提供一个带有 contentcontrol 绑定的 MainWindow。 Straightforward.直截了当。

I have 2 views, each with a textbox.我有 2 个视图,每个视图都有一个文本框。 I have 2 buttons on the MainWindow, each allow me to toggle between views.我在 MainWindow 上有 2 个按钮,每个按钮都允许我在视图之间切换。 However, when I enter data in a textbox, switch views, and come back, the data is gone.但是,当我在文本框中输入数据、切换视图并返回时,数据就消失了。 How can I persist that data to be consumed later?我怎样才能持久化这些数据以供以后使用?

Relevant code:相关代码:

MainWindow.xaml主窗口.xaml

<Window x:Class="TestDataRetention.MainWindow"
        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:TestDataRetention"
        xmlns:views="clr-namespace:TestDataRetention.Views"
        xmlns:viewmodels="clr-namespace:TestDataRetention.ViewModels"
        mc:Ignorable="d"
        Title="MainWindow" Height="450" Width="800">
    <Window.Resources>
        <DataTemplate DataType="{x:Type viewmodels:View1ViewModel}">
            <views:View1View DataContext="{Binding}"/>
        </DataTemplate>
        <DataTemplate DataType="{x:Type viewmodels:View2ViewModel}">
            <views:View2View DataContext="{Binding}"/>
        </DataTemplate>
    </Window.Resources>
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition/>
            <RowDefinition Height="60"/>
        </Grid.RowDefinitions>
        <StackPanel Orientation="Horizontal" Grid.Row="1" HorizontalAlignment="Right">
            <Button x:Name="View1Button" Margin="10" Width="80" Content="View1" Click="View1Button_Click"/>
            <Button x:Name="View2Button" Margin="10" Width="80" Content="View2" Click="View2Button_Click"/>
        </StackPanel>
        <ContentControl x:Name="Content" Grid.Row="0" Content="{Binding}"/>
    </Grid>
</Window>

MainWindow.xaml.cs主窗口.xaml.cs

using System.Windows;
using TestDataRetention.ViewModels;

namespace TestDataRetention
{
    
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
        }

        private void View1Button_Click(object sender, RoutedEventArgs e)
        {
            DataContext = new View1ViewModel();
        }

        private void View2Button_Click(object sender, RoutedEventArgs e)
        {
            DataContext = new View2ViewModel();
        }
    }
}

View1View.xaml View1View.xaml

<UserControl x:Class="TestDataRetention.Views.View1View"
             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" 
             xmlns:local="clr-namespace:TestDataRetention.Views"
             xmlns:vm="clr-namespace:TestDataRetention.ViewModels"
             mc:Ignorable="d" 
             FontSize="24"
             d:DesignHeight="450" d:DesignWidth="800">
    <UserControl.DataContext>
        <vm:View1ViewModel/>
    </UserControl.DataContext>
    <Grid Background="AliceBlue">
        <StackPanel>
            <Label HorizontalAlignment="Center" Content="Enter View1 Stuff"/>
            <TextBox x:Name="View1TextBox" Width="400" Height="50" Text="{Binding View1Words}" />
        </StackPanel>
    </Grid>
</UserControl>

View1View.xaml.cs View1View.xaml.cs

using System.Windows.Controls;
using TestDataRetention.ViewModels;

namespace TestDataRetention.Views
{
    public partial class View1View : UserControl
    {
        public View1View()
        {
            InitializeComponent();

            this.DataContext = new View1ViewModel();
        }
    }
}

View2 is obviously the same as View1 but with corresponding variables. View2 显然与 View1 相同,但具有相应的变量。

While there might also be a way to just have wpf cache it for you, you can just as easily save it properly and then have the input available at will.虽然也可能有一种方法让 wpf 为您缓存它,但您可以轻松地正确保存它,然后随意使用输入。

Look here for two methods on how to:在此处查看有关如何执行以下操作的两种方法:

How to save user inputed value in TextBox? 如何在 TextBox 中保存用户输入的值? (WPF, XAML) (WPF,XAML)

At quick glance, you create new ViewModel each time your button is clicked, this will always create new ViewModel for your DataContext not using the original one.快速浏览一下,每次单击按钮时都会创建new的 ViewModel,这将始终为您的DataContext创建新的 ViewModel,而不是使用原始的 ViewModel。

Also this snippet from your code will create new ViewModel for your Control's DataContext regardless of the one the parent control has:此外,您的代码中的此代码段将为您的控件的 DataContext 创建new的 ViewModel,而不管父控件具有什么:

<UserControl.DataContext>
    <vm:View1ViewModel/>
</UserControl.DataContext>

And I am not sure how you use your DataTemplate here:而且我不确定您如何在这里使用DataTemplate

<DataTemplate DataType="{x:Type viewmodels:View1ViewModel}">
    <views:View1View DataContext="{Binding}"/>
</DataTemplate>
<DataTemplate DataType="{x:Type viewmodels:View2ViewModel}">
    <views:View2View DataContext="{Binding}"/>
</DataTemplate>

But generally, as a guidance for you to model your MVVM project, always keep in mind that XAML code is translated to C# while compiling.但一般来说,作为 model MVVM 项目的指导,请始终记住 XAML 代码在编译时会转换为 C#。 So when writing something like <vm:View1ViewModel/> you actually do new View1ViewModel() .因此,在编写<vm:View1ViewModel/>类的内容时,您实际上是在执行new View1ViewModel()

So for you to use the DataContext your control inherited from its parent, you just use <UserControl DataContext="{binding}" for your UserControl.因此,要使用从其父级继承的控件的 DataContext,您只需将<UserControl DataContext="{binding}"用于您的 UserControl。

And for your button click, you have to keep a pointer for your previously created ViewModel and assign it to the DataContext when needed, I suggest you to create these ViewModels only when needed to minimize memory consumption in large applications, like:对于您的按钮单击,您必须为先前创建的 ViewModel 保留一个指针,并在需要时将其分配给 DataContext,我建议您仅在需要时创建这些 ViewModel,以最大限度地减少大型应用程序中的 memory 消耗,例如:

private View1ViewModel m_View1VM = null;
private void View1Button_Click(object sender, RoutedEventArgs e)
{
    if (m_View1VM is null)
        m_View1VM = new View1ViewModel();
    this.DataContext = m_View1VM;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何将文本从一个文本框添加到另一个文本框? - How do I prepend text from one textbox to another? 如何从一个用户控件导航到另一个 - How do I navigate from one user control to another 如何在用户控件中公开 TextBox 文本属性 - How to expose TextBox Text Property in a User Control 如何从一个用户控件到另一个用户控件获取文本框信息 - How to get Textbox information from one user control to another 我如何将值从用户控件传递到另一个用户控件 - How do i pass value from User Control to another User Control 如何通过单击另一个用户控件中的按钮来在用户控件的文本框中显示一些文本? - How can I show some text on a textbox in a user control by clicking a button in another user control? 如何在设计时将复杂的属性值从一个用户控件复制到另一个用户控件? - How to copy a complex property value from one user control to another as design time? 获取值以在同一视图中从一种形式持久化到另一种形式 - Getting a value to persist from one form to another in the same view 我如何才能将一个控件中的文本框的值获取到另一个控件中 - How can i get a value of textbox located in one control into another control 在切换到其他控件之前,如何在用户控件上保存数据? - How do I save the data on a user control before switching to a different one?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM