【问题标题】:UserControls/ViewModels don't get loaded when switching tabs切换选项卡时不会加载用户控件/视图模型
【发布时间】:2013-12-08 12:46:40
【问题描述】:

我对 MVVM 和 WPF 非常陌生。我正在尝试构建一个选项卡控件,其中的选项卡页显示为用户控件,但我找不到在选项卡之间切换时用户控件未加载的原因。

public partial class WndMain : Window
{
    public WndMain()
    {
        InitializeComponent();

        var ViewModelWndMain = new ViewModelWndMain();

        this.DataContext = ViewModelWndMain;
    }
}

每个 tabItem 都有自己的 ViewModel:

<Window x:Class="EasyBulking.WndMain"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:ViewModels="clr-namespace:EasyBulking.ViewModels"
    xmlns:Tabs="clr-namespace:EasyBulking.GUI"
    Title="WndMain" Height="350" Width="525">
<Grid>
    <TabControl x:Name="TabsWndMain"
        ItemsSource="{Binding Tabs}"
        SelectedItem="{Binding SelectedTab, Mode=TwoWay}">

        <TabControl.Resources>                
            <DataTemplate DataType="{x:Type ViewModels:ViewModelTabProfile}">
                <Tabs:TabProfile />
            </DataTemplate>
            <DataTemplate DataType="{x:Type ViewModels:ViewModelTabNutrition}">
                <Tabs:TabNutrition />
            </DataTemplate>
            <DataTemplate DataType="{x:Type ViewModels:ViewModelTabTraining}">
                <Tabs:TabTraining />
            </DataTemplate>              
        </TabControl.Resources>

        <TabControl.ItemContainerStyle>
            <Style TargetType="TabItem">
                <Setter Property="Header" Value="{Binding tabName}" />
            </Style>
        </TabControl.ItemContainerStyle>

    </TabControl>
</Grid>

对应的ViewModel:

class ViewModelWndMain : ViewModelBase
{        
    private ObservableCollection<ViewModelTab> tabs = new ObservableCollection<ViewModelTab>();
    private ViewModelTab selectedTab;
    private ResourceManager resourceManager { get; set; }

    public ViewModelWndMain ()
    {
        resourceManager = new ResourceManager("EasyBulking.Properties.Resources", Assembly.GetExecutingAssembly());

        Tabs.Add(new ViewModelTabProfile(resourceManager.GetString("tabProfile")));
        Tabs.Add(new ViewModelTabProfile(resourceManager.GetString("tabNutrition")));
        Tabs.Add(new ViewModelTabProfile(resourceManager.GetString("tabTraining")));

        SelectedTab = Tabs[0];
    }

    public ObservableCollection<ViewModelTab> Tabs
    {
        get
        {
            return tabs;
        }
    }

    public ViewModelTab SelectedTab
    {
        get { return selectedTab;   }
        set { 
            selectedTab = value;
            this.RaisePropertyChangedEvent("SelectedTab");               
        }
    }
}

ProperyChanged 事件触发,但当我切换选项卡时 UI 没有更新。

abstract class ViewModelBase : INotifyPropertyChanged
{

    public event PropertyChangedEventHandler PropertyChanged;

    protected void RaisePropertyChangedEvent(string propertyName)
    {         
        if (PropertyChanged != null)
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }
}

【问题讨论】:

  • 我认为您的 Window XAML 元素缺少 DataContext="{Binding RelativeSource=Self}" 属性...
  • 如果我将此属性 DataContext="{Binding RelativeSource={RelativeSource Self}} 添加到我的选项卡控件中,我的窗口将完全不显示任何内容 - 甚至选项卡标题也不显示。
  • Argh... 抱歉,忽略了显而易见的问题:您正在添加三个“ViewModelTabProfile”类型的对象,而不是单独的其他对象。您的标签可能正在切换,但一遍又一遍地切换到相同的控件。
  • 哦,伙计,我现在感觉很笨,但感谢您的回答!
  • 将您的解决方案发布为答案,而不是将其编辑到问题中。

标签: c# wpf mvvm user-controls tabcontrol


【解决方案1】:

好的,只是以常规答案结束这个问题,我们开始:

添加标签视图模型的代码为所有三个标签页插入相同的对象:

    Tabs.Add(new ViewModelTabProfile(resourceManager.GetString("tabProfile")));
    Tabs.Add(new ViewModelTabProfile(resourceManager.GetString("tabNutrition")));
    Tabs.Add(new ViewModelTabProfile(resourceManager.GetString("tabTraining")));

加载资源的标题文本掩盖了这一事实,并且页面似乎没有交换,而实际上它们再次从一个控件交换到相同类型的控件。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-09-07
    • 1970-01-01
    • 2011-09-25
    • 2015-03-17
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多