为什么这些标签似乎共享相同的文本框?

时间:2013-01-18 16:05:15

标签: c#

我在xaml中定义了我的UI,下面是我的代码:

<TabControl HorizontalAlignment="Left" Height="330" VerticalAlignment="Top" Width="764" Margin="10,10,0,0" ItemsSource="{Binding AllTabs}" SelectedItem="{Binding SelectedTab}">
        <TabControl.ItemContainerStyle>
            <Style TargetType="TabItem">
                <Setter Property="Header" Value="{Binding Header}"/>
                <Setter Property="Content">
                    <Setter.Value>
                        <Grid>
                            <TextBox Text="{Binding Text}" FontSize="16" AcceptsReturn="True" HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
                            </TextBox>
                        </Grid>
                    </Setter.Value>
                </Setter>
                <Setter Property="FontSize" Value="20"/>
            </Style>
        </TabControl.ItemContainerStyle>
    </TabControl>

当我运行我的程序时。我可以添加许多选项卡没有问题。标题不同但每当我在其中一个标签中更改文本框的内容时,其他标签中的所有文本框都会更改为相同的内容(好像它们都共享相同的文本框,或绑定到同一个源,这很奇怪) 。

我是否在定义UI时出错了?请帮助我,并提前感谢。

这是我的模型,非常简单:

using System;
using System.Collections.ObjectModel;
using System.ComponentModel;

namespace MyHomework__MVVM_
{
    class MyHomeworkModel : INotifyPropertyChanged
    {
        private string header, text;
        public event PropertyChangedEventHandler PropertyChanged;

        public string Header
        {
            get
            {
                return header;
            }
            set
            {
                header = value;
                OnPropertyChanged("Header");
            }
        }

        public string Text
        {
            get
            {
                return text;
            }
            set
            {
                text = value;
                OnPropertyChanged("Text");
            }
        }

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

我的viewmodel,仍然非常简单:

using MyHomework;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Windows.Input;

namespace MyHomework__MVVM_
{
    class MyHomeworkViewModel : INotifyPropertyChanged
    {
        private ObservableCollection<MyHomeworkModel> allTabs;
        private MyHomeworkModel selectedTab;
        public event PropertyChangedEventHandler PropertyChanged;

        public MyHomeworkViewModel()
        {
            allTabs = new ObservableCollection<MyHomeworkModel>();
            selectedTab = new MyHomeworkModel();
            AddCourseCommand = new AddCourseCommand(this);
        }

        public ObservableCollection<MyHomeworkModel> AllTabs
        {
            get
            {
                return allTabs;
            }
            set
            {
                allTabs = value;
                OnPropertyChanged("AllTabs");
            }
        }

        public MyHomeworkModel SelectedTab
        {
            get
            {
                return selectedTab;
            }
            set
            {
                selectedTab = value;
                OnPropertyChanged("SelectedTab");
            }
        }

        public ICommand AddCourseCommand
        {
            get;
            private set;
        }

        public void AddNewTab()
        {
            NewCourseName ncn = new NewCourseName();
            ncn.ShowDialog();
            if (ncn.courseName != null)
            {
                MyHomeworkModel newTab = new MyHomeworkModel();
                newTab.Header = ncn.courseName;
                newTab.Text = ncn.courseName;
                AllTabs.Add(newTab);
                SelectedTab = newTab;
            }
        }

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

编辑: 刚刚注意到我收到了这条消息:

System.Windows.Data Error: 40 : BindingExpression path error: 'Text' property not found on 'object' ''MyHomeworkViewModel' (HashCode=31265986)'. BindingExpression:Path=Text; DataItem='MyHomeworkViewModel' (HashCode=31265986); target element is 'TextBox' (Name=''); target property is 'Text' (type 'String')

我想我知道为什么抱怨。我的Text属性是MyHomeworkModel而不是MyHomeworkViewModel ...但是为什么我可以将标题绑定到MyHomeworkModel中的Header属性?

我的AddCourseCommand类:

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

namespace MyHomework__MVVM_
{
    class AddCourseCommand : ICommand
    {
        private MyHomeworkViewModel viewModel;

        public AddCourseCommand(MyHomeworkViewModel viewModel)
        {
            this.viewModel = viewModel;
        }

        public event EventHandler CanExecuteChanged
        {
            add
            {
                CommandManager.RequerySuggested += value;
            }
            remove
            {
                CommandManager.RequerySuggested -= value;
            }
        }

        public bool CanExecute(object parameter)
        {
            return true;
        }

        public void Execute(object parameter)
        {
            viewModel.AddNewTab();
        }
    }
}

1 个答案:

答案 0 :(得分:0)

看起来像你的模型工具

ObservableCollection<MyHomeworkModel>.

删除此Base类,它应该可以工作。

修改

您需要改变:

       AddCourseCommand = new AddCourseCommand(this);

下载DelegateCommand

       AddCourseCommand = new DelegateCommand(AddNewTab);

修改

您可以从UI中剪切ViewModel。您将实例复制到您的命令,然后调用该复制添加。这是错误的并且属性你的错误。我真的建议你使用DelegateCommand这可能会修复它。

你的猜测:

  

我想我知道为什么抱怨。我的Text属性是MyHomeworkModel而不是MyHomeworkViewModel ...但是为什么我可以将标题绑定到MyHomeworkModel中的Header属性?

您的媒体资源位于MyHomeworkModel而非MyHomeworkViewModel,您绑定到包含MyHomeworkModel的列表是正确的。现在,您要添加Binding将在最低级别设置的新项目。在这种情况下,您MyHomeworkModel而不是MyHomeworkViewModel