In this program, I’m able to add one tab at a time by clicking the “Add Course” button. Ideally, the header of the tab should be the course name I entered and the text in the textbox , which is on the tab, should display the course name.
However, it’s not functioning correctly. When I tried to add more than 1 tabs, each time it gives me this error message:
System.Windows.Data Error: 40 : BindingExpression path error: 'Text' property not found on 'object' ''MyHomeworkViewModel' (HashCode=33010577)'. BindingExpression:Path=Text; DataItem='MyHomeworkViewModel' (HashCode=33010577); target element is 'TextBox' (Name=''); target property is 'Text' (type 'String')
Also, it seems to “override” other tab’s text (just text, not header). For example, if I add a tab with header “a”, the text of that is also “a”. Then if I add “B”, both textboxes on two tabs become “B”. However, if I print out the Text property of each tab (MyHomeworkModel in this case), they are “a” and “B”, respectively.
I have been debugging this whole day but no luck. Any help would be appreciated!
My View (DataContext set to MyHomeworkViewModel):
<Window x:Class="MyHomework__MVVM_.MyHomeworkView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="My Homework" Height="450" Width="800" ResizeMode="CanMinimize">
<Grid Margin="0,0,10,10">
<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>
<Button Content="Add Course" HorizontalAlignment="Left" VerticalAlignment="Top" Width="105" Margin="10,351,0,0" Height="50" Command="{Binding AddCourseCommand}"/>
<Button Content="Drop Course" HorizontalAlignment="Left" VerticalAlignment="Top" Width="76" Margin="138,379,0,0" Height="22" Command="{Binding DropCourseCommand, UpdateSourceTrigger=PropertyChanged}"/>
<Button Content="Save HW" HorizontalAlignment="Left" VerticalAlignment="Top" Width="105" Margin="669,351,0,0" Height="50"/>
</Grid>
</Window>
My Model:
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));
}
}
}
}
My ViewModel:
using MyHomework;
using System;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Windows.Input;
namespace MyHomework__MVVM_
{
class MyHomeworkViewModel : INotifyPropertyChanged
{
private ObservableCollection<MyHomeworkModel> allTabs;
private MyHomeworkModel selectedTab;
private MyHomeworkView mainWindow;
public event PropertyChangedEventHandler PropertyChanged;
public MyHomeworkViewModel(MyHomeworkView mainWindow)
{
allTabs = new ObservableCollection<MyHomeworkModel>();
this.mainWindow = mainWindow;
AddCourseCommand = new AddCourseCommand(this);
DropCourseCommand = new DropCourseCommand(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 ICommand DropCourseCommand
{
get;
private set;
}
public void AddNewTab()
{
NewCourseName ncn = new NewCourseName();
ncn.Owner = mainWindow;
ncn.ShowDialog();
if (ncn.courseName != null)
{
MyHomeworkModel newTab = new MyHomeworkModel();
newTab.Header = ncn.courseName;
newTab.Text = ncn.courseName;
AllTabs.Add(newTab);
SelectedTab = newTab;
}
foreach (MyHomeworkModel item in AllTabs)
{
Console.WriteLine(item.Text);
}
}
public bool CanDrop()
{
return SelectedTab != null;
}
public void RemoveTab()
{
DropCourseConfirmation dcc = new DropCourseConfirmation();
dcc.Owner = mainWindow;
dcc.ShowDialog();
if (dcc.drop == true)
{
int index = AllTabs.IndexOf(SelectedTab);
AllTabs.Remove(SelectedTab);
if (AllTabs.Count > 0)
{
if (index == 0)
{
SelectedTab = AllTabs[0];
}
else
{
SelectedTab = AllTabs[--index];
}
}
else
{
SelectedTab = null;
}
}
}
private void OnPropertyChanged(string propertyName)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
}
}
Please let me know if you need more codes to help me.
Change your
for this: