How to: Fill a DataGrid.DataContext with information from txt files (C#, WPF) - c#

How to: Fill a DataGrid.DataContext with information from txt files (C#, WPF)
I am trying to fill my DataGrid with information I get from some txt files. There is a folder called "CONTACTS" and there are some (5) files in. These files are configurated this way:
Content of John Doe.txt (without list symbols):
John Doe Corp.
Mr.
Doe
John
XAML:
<DataGrid AutoGenerateColumns="False" CanUserResizeRows="False" DockPanel.Dock="Bottom" ItemsSource="{Binding CollectionofDetails}" Name="dataGrid_Content">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding CorporationName}" Header="Firma" />
<DataGridTextColumn Binding="{Binding Prefix}" Header="Anrede" />
<DataGridTextColumn Binding="{Binding FirstName}" Header="Nachname" />
<DataGridTextColumn Binding="{Binding LastName}" Header="Vorname" />
</DataGrid.Columns>
</DataGrid>
C#:
public class Details
{
public string CorporationName { get; set; }
public string Prefix { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
}
public ObservableCollection<Details> _CollectionofDetails = new ObservableCollection<Details>();
public ObservableCollection<Details> CollectionofDetails
{
get { return _CollectionofDetails; }
set { _CollectionofDetails = value; }
}
public void SetItemsToDataContext()
{
foreach (string Datei in Directory.GetFiles(#"C:\Users\schwarz\Desktop\Cusposes_2014-05-20_0827\ISAPO\ISAPO Cusposes\Business Contacts\Contacts", "*.txt"))
{
StreamReader reader = new StreamReader(Datei);
int i = 0;
string line = reader.ReadToEnd().Replace("\n", "");
string[] t = line.Split('\r');
Details d = new Details();
d.CorporationName = t[i];
d.Prefix = t[i + 1];
d.FirstName = t[i + 2];
d.LastName = t[i + 3];
CollectionofDetails.Add(d);
reader.Close();
}
}
Unfortunately, I do have the following problems:
I do not know how to load THE CONTENT of each file (for all files).
I do not know how to fill my DataGrid with this Information.
--> Solution by Dhaval Patel (see below).

You can use the below mentioned code
Your Xaml Code looks like
<DataGrid AutoGenerateColumns="False" CanUserResizeRows="False" DockPanel.Dock="Bottom" ItemsSource="{Binding CollectionofDetails}" Name="dataGrid_Content">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding CorporationName}" Header="Firma" />
<DataGridTextColumn Binding="{Binding Prefix}" Header="Anrede" />
<DataGridTextColumn Binding="{Binding FirstName}" Header="Nachname" />
<DataGridTextColumn Binding="{Binding LastName}" Header="Vorname" />
</DataGrid.Columns>
</DataGrid>
<Button Command="{Binding MyCommand}" Width="100" Margin="346,230,346,-189">RunMyCommand</Button>
Your ViewModel code look like
private ObservableCollection<Details> _CollectionofDetails=new ObservableCollection<Details>();
public ObservableCollection<Details> CollectionofDetails
{
get { return _CollectionofDetails; }
set { _CollectionofDetails = value; RaisePropertyChanged("CollectionofDetails"); }
}
private RelayCommand _MyCommand;
public RelayCommand MyCommand
{
get { return _MyCommand??(_MyCommand=new RelayCommand(Methodcall)); }
set { _MyCommand = value; }
}
void Methodcall()
{
foreach (string Datei in Directory.GetFiles(#"C:\textfile", "*.txt"))
{
StreamReader reader = new StreamReader(Datei);
int i=0;
string line = reader.ReadToEnd().Replace("\n","");
string[] t = line.Split('\r');
Details d = new Details();
d.CorporationName = t[i];
d.Prefix = t[i + 1];
d.FirstName = t[i + 2];
d.LastName = t[i + 3];
CollectionofDetails.Add(d);
reader.Close();
}
}
public class Details
{
public string CorporationName { get; set; }
public string Prefix { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
}
output should look like

This is a problem that you have to break into pieces. I would recommend that you define a class suitable for your data, like
public class Person {
public string FullName {get; set;}
public string FirstName {get; set;}
public string LastName {get; set;}
public string Title {get; set;}
}
and in your viewmodel class you have a variable PersonList of type List<Person>.
Then your have to write a method, something like
private void PopulatePersonData(){
// Here you put all the logic reading the .txt files creating a person for each file
// and adding the person to the PersonList.
}
which you then call in the constructor of the viewmodel.
Finally you bind the ItemsSource of your DataGrid to the PersonList. That should do it.

Maybe you should really read what is in your txt files.
By using for example a Reader :
private void SetItemsToDataContext()
{
foreach (String Datei in Directory.GetFiles(#"C:\Contacts", "*.txt"))
{
String[] linesRead = File.ReadAllLines(Datei);
if (linesRead.Length != 4)
{
continue;
}
Contact contactRead = new Contact();
contactRead.Company = linesRead[0];
contactRead.Gender = linesRead[1];
contactRead.Name = linesRead[2];
contactRead.FirstName = linesRead[3];
dataGrid_Content.Items.Add(contactRead);
}
}
public class Contact
{
public String Company { get; set; }
public String Gender { get; set; }
public String Name { get; set; }
public String FirstName { get; set; }
}

Related

How to add a column to a datagrid for a selected item in WPF?

I have a datagrid which looks like this.
I want for the user to be able to manually enter the date after clicking 'Add Interview DT' for a selected item in the 'Interview Date and time' column.
My code so far for Shortlist.xaml.cs is like this:
List<ShortlistedClient> shlclients = new List<ShortlistedClient>();
public Shortlist()
{
InitializeComponent();
DataContext = shlclients;
shlclients.Add(new ShortlistedClient("Rich", "07515118265", "rich#gmail.com", "Glasgow", "Office", "MSc", "more than 3 years", "Yes", "No"));
shlclients.Add(new ShortlistedClient("Steve", "07515118265", "steve#gmail.com", "Glasgow", "Construction", "High School", "more than 3 years", "Yes", "No"));
shlclients.Add(new ShortlistedClient("Maria", "07485999005", "mb#gmail.com", "Edinburgh", "Office", "MSc", "more than 3 years", "No", "No"));
}
// remove shortlisted client
private void RemoveShClient(object sender, RoutedEventArgs e)
{
if (dgr.Items.Count >= 1)
{
if (dgr.SelectedValue != null)
{
var items = (List<ShortlistedClient>)dgr.ItemsSource;
var item = (ShortlistedClient)dgr.SelectedValue;
dgr.ItemsSource = null;
dgr.Items.Clear();
items.Remove(item);
dgr.ItemsSource = items;
}
}
else
{
System.Windows.Forms.MessageBox.Show("No Clients Found");
}
}
So I need help with writing this method:
// method to fill in data for the date and time column
private void addInterviewDT(object sender, RoutedEventArgs e)
{
ShClient sc = dgr.SelectedItem as ShClient;
if (sc != null)
{
?
}
}
My Client and ShortlistedClient classes are defined as follows:
public partial class Client
{
public string Name { get; set; }
public string Phone { get; set; }
public string Email { get; set; }
public string Location { get; }
public string Worktype { get; }
public string Qualification { get; }
public string Workexp { get; }
public string Drlicence { get; }
public string Crconviction { get; }
public bool IDed { get; private set; }
public Client(string n, string p, string e, string l, string wt, string q, string we, string dl, string cc)
{
Name = n;
Phone = p;
Email = e;
Location = l;
Worktype = wt;
Qualification = q;
Workexp = we;
Drlicence = dl;
Crconviction = cc;
}
}
public class ShortlistedClient : Client
{
public DateTime DT { get; set; }
public bool InterestedinVac { get; private set; }
public List<ShortlistedClient> clients { get; set; } = new List<ShortlistedClient>();
public ShortlistedClient(string n, string p, string e, string l, string wt, string q, string we, string dl, string cc) : base(n, p, e, l, wt, q, we, dl, cc)
{
DT = new DateTime();
InterestedinVac = false;
}
}
And my code for the Shortlist.xaml is this:
<Window x:Class="WpfApp_Employment_Help.Shortlist"
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:WpfApp_Employment_Help"
mc:Ignorable="d"
Title="Shortlist" Height="450" Width="800">
<StackPanel Margin="27,0,0,77">
<DataGrid x:Name="dgr" AutoGenerateColumns="False" ItemsSource="{Binding}" IsSynchronizedWithCurrentItem="True" CanUserAddRows="False" Height="154" Width="760">
<DataGrid.Columns>
<DataGridTextColumn Header="Name" Binding="{Binding Name}" />
<DataGridTextColumn Header="Email" Binding="{Binding Email}" />
<DataGridTextColumn Header="Phone" Binding="{Binding Phone}"/>
<DataGridTextColumn Header="Location" Binding="{Binding Location}"/>
<DataGridTextColumn Header="Worktype" Binding="{Binding Worktype}"/>
<DataGridTextColumn Header="Qualification" Binding="{Binding Qualification}"/>
<DataGridTextColumn Header="Workexp" Binding="{Binding Worktype}"/>
<DataGridTextColumn Header="Driving licence" Binding="{Binding Drlicence}"/>
<DataGridTextColumn Header="Criminal conviction" Binding="{Binding Crconviction}"/>
<DataGridTextColumn Header="Interview Date and time" Binding="{Binding DT}"/>
</DataGrid.Columns>
</DataGrid>
<Button Content="Add Interview DT" Width="128" FontWeight="Bold" Height="28"/>
<TextBox TextWrapping="Wrap" Text="TextBox" Width="120" Height="46"/>
<Button x:Name="BtnRemoveShlClient" Content="Remove Shortlisted Client" FontWeight="Bold" Height="33" Width="221" Click="RemoveShClient"/>
</StackPanel>
</Window>
Additionally, how can I show my Interview date and time column values as empty instead of '1/1/0001 12:00:00 AM'?
thank you, I'm new to C# and wpf.
First of all ShortlistedClient must implement INotifyPropertyChanged for you to be able to dynamically set one of its properties and have the UI updated automatically:
public class ShortlistedClient : Client, INotifyPropertyChanged
{
private DateTime _dt;
public DateTime DT
{
get { return _dt; }
set { _dt = value; NotifyPropertyChanged(); }
}
public bool InterestedinVac { get; private set; }
public List<ShortlistedClient> clients { get; set; } = new List<ShortlistedClient>();
public ShortlistedClient(string n, string p, string e, string l, string wt, string q, string we, string dl, string cc) : base(n, p, e, l, wt, q, we, dl, cc)
{
DT = new DateTime();
InterestedinVac = false;
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged([CallerMemberName] string propertyName = "")
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}
You can then parse the value of the TextBox and try to set the property:
private void addInterviewDT(object sender, RoutedEventArgs e)
{
ShortlistedClient sc = dgr.SelectedItem as ShortlistedClient;
if (sc != null && DateTime.TryParse(textBox.Text, out DateTime value))
{
sc.DT = value;
}
}
textBox is the name of the TextBox control:
<TextBox x:Name="textBox" TextWrapping="Wrap" Text="TextBox" Width="120" Height="46"/>
additionally, how can I show my Interview date and time column values as empty instead of '1/1/0001 12:00:00 AM'?
Change the type of the DT property to Nullable<DateTime>.

How can I set a selection in a DataGridComboBoxColumn?

How can I set a DataGridComboBoxColumn item selection programmatically?
I want to populate my list with data, and the comboboxitem should set the selected item from the list.
But I dont find any way to achieve that.
In this example the selection should be "Forward"
XAML:
<DataGrid ItemsSource="{Binding }" x:Name="dgSFD" AlternatingRowBackground="BlanchedAlmond" SelectionChanged="dgSFD_SelectionChanged" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Path=sID}" Header="Step ID"/>
<DataGridComboBoxColumn x:Name="cbServo" Header="Servo" SelectedItemBinding="{Binding Servo, Mode =TwoWay}" SelectedValuePath="sFunctionName ,Mode=TwoWay" DisplayMemberPath="sFunctionName"/>
</DataGrid>
Class
public class Step
{
public string sID { get; set; }
public Servo serServo { get; set; }
}
public class Servo
{
public string sFunction { get; set; }
public string sServo { get; set; }
}
C#
public static List<Step> listStep { get; set; }
public static List<Servo> listServo { get; set; }
public MainWindow()
{
InitializeComponent();
}
public void loadList()
{
dgSFD.ItemsSource = listStep;
cbServo.ItemsSource = listServo;
}
public void testfill()
{
Servo newServo = new Servo();
newServo.sFunctionName = "Forward";
newServo.sServo = "Left";
listServo.Add(newServo);
Step newStep = new Step();
newStep.serServo = newServo;
newStep.sID = "1";
listStep.Add(newStep);
}
Bind the SelectedItemBinding property to the serServo property of the Step object:
<DataGridComboBoxColumn x:Name="cbServo" Header="Servo" SelectedItemBinding="{Binding serServo, Mode=TwoWay}" DisplayMemberPath="sFunction"/>

Datagrid image TemplateColumn source binding wpf

i'm using a Datagrid to display users information, every thing is working fine for text columns ,except the column I want to display user image,
here is the Datagrid in xaml
<DataGrid Name="UserListDataGrid" Margin="10,50,10,10"
AutoGenerateColumns="False"
EnableRowVirtualization="False"
ItemsSource="{Binding convUsrList}"
CellStyle="{StaticResource Body_Content_DataGrid_Centering}"
RowDetailsVisibilityMode="VisibleWhenSelected"
CanUserSortColumns="False"
CanUserAddRows="False"
CanUserResizeRows="False"
CanUserReorderColumns="False"
IsReadOnly="True"
Width="900"
Opacity="0"
Foreground="Black"
GridLinesVisibility="None"
HeadersVisibility="All"
HorizontalContentAlignment="Center"
Background="Gray"
BorderBrush="Transparent"
ScrollViewer.HorizontalScrollBarVisibility="Auto" >
<DataGrid.Columns>
<DataGridTemplateColumn >
<DataGridTemplateColumn.CellTemplate >
<DataTemplate>
<Image Source="{Binding PhotoSource}" Width="60" Height="60" />
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
<DataGridTemplateColumn.HeaderTemplate>
<DataTemplate>
<TextBlock Text="{Binding DataContext[10],RelativeSource={RelativeSource AncestorType=DataGrid}}" Width="60"/>
</DataTemplate>
</DataGridTemplateColumn.HeaderTemplate>
</DataGridTemplateColumn>
<DataGridTextColumn Binding="{Binding FirstName}" >
<DataGridTextColumn.HeaderTemplate>
<DataTemplate>
<TextBlock Text="{Binding DataContext[4],RelativeSource={RelativeSource AncestorType=DataGrid}}" Width="60"/>
</DataTemplate>
</DataGridTextColumn.HeaderTemplate>
</DataGridTextColumn>....
I get the user photo from my DB in base64 string format, convert to BitmapImage using this function
public static BitmapImage getImage(string image)
{
byte[] b = Convert.FromBase64String(image);
MemoryStream mst = new MemoryStream(b, 0, b.Length);
BitmapImage bmp = new BitmapImage();
bmp.BeginInit();
bmp.CacheOption = BitmapCacheOption.OnLoad;
bmp.StreamSource = mst;
bmp.EndInit();
return bmp;
}
and finally create a list of user (which is a class presenting user information such as firstname (string) //lastname(string)// ...//PhotoSource (BitmapImage) ) and feed it to data grid as follows
UserListDataGrid.ItemsSource = convUsrList;
as I said everything is showing on the Datagrid except user image would you please help me ?
this is the user class:
public class User
{
public int Id { get; set; }
public string UserName { get; set; }
public string Password { get; set; }
public bool IsActive { get; set; }
public int UserTypeId { get; set; }
public int ShopId { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
public string PhoneNumber { get; set; }
public string CellNumber { get; set; }
public string Address { get; set; }
public string Email { get; set; }
public bool Gender { get; set; }
public string Photo { get; set; }
public string SecurityAnswer { get; set; }
public int SecurityQuestionId { get; set; }
public long LastSecurityCheck { get; set; }
public DateTime? DeletedAt { get; set; }
public DateTime? ExpireDate { get; set; }
}
public class UserDatagrid:User
{
public BitmapImage PhotoSource;
}
and here is how convUsrList is declared:
public void loadUserTable()
{
UserManagement um = new UserManagement(db);
List<User> userlist = um.getUserlist(um.GetUsers());
if (db.IsRTL)
UserListDataGrid.FlowDirection = FlowDirection.RightToLeft;
else
UserListDataGrid.FlowDirection = FlowDirection.LeftToRight;
string s = "";
dataBase.AppNotifyDic.TryGetValue("userTbl", out s);
string[] contbl = s.Split('-');
UserListDataGrid.DataContext = new List<string>() { contbl[0], contbl[1], contbl[2], contbl[3], contbl[4], contbl[5], contbl[6], contbl[7], contbl[8], contbl[9], contbl[10], contbl[11], contbl[12], contbl[13], contbl[14], contbl[15], contbl[16] };
List<UserDatagrid> convUsrList = new List<UserDatagrid>();
for (int i=0;i<userlist.Count;i++)
{
convUsrList.Add(tools.convertUserForDataGrid(userlist[i]));
}
UserListDataGrid.ItemsSource = convUsrList;
}
and the convertUserForDataGrid is as follow:
public static UserDatagrid convertUserForDataGrid(User origUser)
{
UserDatagrid convUser = new UserDatagrid();
convUser.Id = origUser.Id;
convUser.UserName = origUser.UserName;
convUser.Password = origUser.Password;
convUser.IsActive = origUser.IsActive;
convUser.UserTypeId = origUser.UserTypeId;
convUser.ShopId = origUser.ShopId;
convUser.FirstName = origUser.FirstName;
convUser.LastName = origUser.LastName;
convUser.PhoneNumber = origUser.PhoneNumber;
convUser.CellNumber = origUser.CellNumber;
convUser.Address = origUser.Address;
convUser.Email = origUser.Email;
convUser.Gender = origUser.Gender;
convUser.Photo = origUser.Photo;
convUser.SecurityAnswer = origUser.SecurityAnswer;
convUser.SecurityQuestionId = origUser.SecurityQuestionId;
convUser.LastSecurityCheck = origUser.LastSecurityCheck;
convUser.DeletedAt = origUser.DeletedAt;
convUser.ExpireDate = origUser.ExpireDate;
convUser.PhotoSource = (string.IsNullOrEmpty(origUser.Photo)) ? (convUser.Gender)? setImagesource("male.png"): setImagesource("Female.png") : getImage(origUser.Photo);
return convUser;
}
Because binding system uses Reflection to find the
Property in DataContext(i.e your VM)
Hope this will help.
credits:link1

WPF Binding to property list not updating

Help. I've been searching with google and stackoverflow searchbar for a week and didn't found my answers.
So I have a class named Student and the properties is string Name, string Address, DoB DateofBirth, and List Score. And a ViewModel class for the Student class.
public partial class StudentWindow : Window
{
public class DoB
{
public int Day { get; set; }
public int Month { get; set; }
public int Year { get; set; }
public DoB(int day, int month, int year)
{
Day = day;
Month = month;
Year = year;
}
public override string ToString()
{
return Day + "/" + Month + "/" + Year;
}
}
public class Student
{
public string Name { get; set; }
public string Address { get; set; }
public DoB DateOfBirth { get; set; }
public List<int> Score { get; set; }
}
public class ViewModel : INotifyPropertyChanged
{
private Student entry;
public event PropertyChangedEventHandler PropertyChanged;
public void Notify(string Property)
{
PropertyChanged(this, new PropertyChangedEventArgs(Property));
}
public string Name
{
get { return entry.Name; }
set { entry.Name = value; Notify("Name"); }
}
public string Address
{
get { return entry.Address; }
set { entry.Address = value; Notify("Address"); }
}
public string DateOfBirth
{
get { return entry.DateOfBirth.ToString(); }
set
{
var p = value.Split('/');
int d = 1, m = 1, y = 1;
bool pass = int.TryParse(p[0], out d) && int.TryParse(p[1], out m) && int.TryParse(p[2], out y);
if (pass)
{
entry.DateOfBirth = new DoB(d, m, y);
Notify("DateOfBirth");
}
else
throw new InvalidCastException();
}
}
public List<string> Score
{
get { return entry.Score.Select(sc => "" + sc).ToList(); }
set { entry.Score = value.Select(va => int.Parse(va)).ToList(); Notify("Score"); }
}
public ViewModel(Student entry)
{
this.entry = entry;
}
}
public ObservableCollection<ViewModel> entry { get; set; }
public StudentWindow()
{
InitializeComponent();
entry = new ObservableCollection<ViewModel>();
entry.Add(new ViewModel(new Student() { Name = "First People", Address = "Earth", DateOfBirth = new DoB(13, 11, 1996), Score = new List<int>(new int[] { 100, 90, 100, 90 }) }));
entry.Add(new ViewModel(new Student() { Name = "Second People", Address = "Moon", DateOfBirth = new DoB(13, 11, 1995), Score = new List<int>(new int[] { 90, 80, 100, 100 }) }));
DataContext = this;
}
}
And the XAML is
<Grid>
<DataGrid x:Name="dataGridStudent" ItemsSource="{Binding entry}" HorizontalAlignment="Left" Margin="10,10,0,0" VerticalAlignment="Top" Height="210" Width="572"/>
<DataGrid x:Name="dataGridStudentScore" ItemsSource="{Binding ElementName=dataGrid, Path=SelectedItem.Score}" HorizontalAlignment="Left" Margin="10,242,0,0" VerticalAlignment="Top" Height="218" Width="572" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Path=., Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" />
</DataGrid.Columns>
</DataGrid>
</Grid>
Everything works fine for dataGridStudent.
But dataGridStudentScore is only displaying the values and unable to edit the value. I have to set the Binding Path=. , otherwise the Path or Xpath exception will thrown.
Please help with any solutions you have. I'm newbie here, please do tell if something is wrong with my approach. Thanks in advance.
Ignoring the confusing understanding on the MVVM architecture.
The reason student score not editable is that you try to bind a value type variable to DataGridTextColumn. I'm not sure about the background implementation of DependencyProperty binding but I would imagine there is no reference to bind to in order to perform the update as it's just a value type variable.
I'm not an expect in wpf too but I would implement that same thing in the following.
public class ViewModelBase : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
[NotifyPropertyChangedInvocator]
protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null) handler(this, new PropertyChangedEventArgs(propertyName));
}
}
public class Score : ViewModelBase
{
public int Value { get; set; }
}
public class Student : ViewModelBase
{
public string Name { get; private set; }
public string Address { get; private set; }
public DateTime Dob { get; private set; }
public ObservableCollection<Score> Scores { get; set; }
public Student(string name, string address, DateTime dob)
{
Name = name;
Address = address;
Dob = dob;
Scores = new ObservableCollection<Score>();
}
}
public class StudentViewModel : ViewModelBase
{
public ObservableCollection<Student> Students { get; private set; }
public StudentViewModel()
{
Students = new ObservableCollection<Student>
{
new Student("Student A", "A Address", DateTime.Now)
{
Scores = new ObservableCollection<Score>
{
new Score { Value = 80 },
new Score { Value = 85 },
new Score { Value = 90 },
}
},
new Student("Student B", "B Address", DateTime.Now)
{
Scores = new ObservableCollection<Score>
{
new Score { Value = 70 },
new Score { Value = 75 },
new Score { Value = 60 },
}
}
};
}
private Student _selectedStudent;
public Student SelectedStudent
{
get { return _selectedStudent; }
set
{
_selectedStudent = value;
OnPropertyChanged("SelectedStudentScores");
}
}
public ObservableCollection<Score> SelectedStudentScores
{
get
{
if (_selectedStudent == null) return null;
return _selectedStudent.Scores;
}
}
public Score SelectedScore { get; set; }
}
<Window x:Class="StudentScoreWpfProj.MainWindow"
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:studentScoreWpfProj="clr-namespace:StudentScoreWpfProj"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance Type=studentScoreWpfProj:StudentViewModel,IsDesignTimeCreatable=True}"
Title="MainWindow" Height="350" Width="525">
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<DataGrid ItemsSource="{Binding Students}" AutoGenerateColumns="False"
SelectedItem="{Binding SelectedStudent}">
<DataGrid.Columns>
<DataGridTextColumn Header="Name" Binding="{Binding Name, Mode=OneWay}" />
<DataGridTextColumn Header="Address" Binding="{Binding Address, Mode=OneWay}" />
<DataGridTextColumn Header="Birth" Binding="{Binding Dob, Mode=OneWay, StringFormat={}{0:MM/dd/yyyy}}" />
</DataGrid.Columns>
</DataGrid>
<DataGrid Grid.Row="1" ItemsSource="{Binding SelectedStudentScores}"
SelectedItem="{Binding SelectedScore}">
</DataGrid>
</Grid>
public partial class MainWindow
{
public MainWindow()
{
InitializeComponent();
DataContext = new StudentViewModel();
}
}

Different values for different comboboxes in Datagrid

Bear with me, as I'm new to WPF.I have a datagrid which contains comboboxes.
<DataGrid x:Name="dgData" AutoGenerateColumns="False" Margin="131,93,13,101" Grid.Column="1" SelectionChanged="dgData_SelectionChanged">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Subject}" Header="Subject" Width="100"/>
<DataGridComboBoxColumn Header="Subject" x:Name="comboboxColumn1"/>
</DataGrid.Columns>
</DataGrid>
And I use the following code to load different itemsources depending on which combobox is clicked on by the user:
private void dgData_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
if (dgData.SelectedIndex == 0)
{
comboboxColumn1.ItemsSource = resolution;
} else if (dgData.SelectedIndex == 1)
{
comboboxColumn1.ItemsSource = codec;
}
}
How I bind dgData:
List<TicketInfo> ticketsList = new List<TicketInfo>
{
new TicketInfo{ Subject="File", Status="Open"},
new TicketInfo{ Subject="Resolution", Status="Assigned"},
};
dgData.ItemsSource = ticketsList;
public class TicketInfo
{
public string Subject { get; set; }
public string Status { get; set; }
}
Now I also need to retrieve the value of the combobox once the user chooses the value. Is there a more elegant way to load different items in different comboboxes and retrieving the value?
Thanks!
You don't show how you bind dgData.
public class TicketInfo
{
public string Subject { get; set; }
public string Status { get; set; }
public List<string> SubjectSubList { get; set; }
}
Bind the second column to SubjectSubList
When you build List ticketsList just put resolution in the first SubjectSubList and codec in the second.

Categories

Resources