Does anyone have an example of binding a 2 related ComboBoxs to a Selected Item of a DataGrid? I have tried, but I can't seem to get it to work. I am fairly new to MVVM so I am doing something wrong.
I have a datagrid which is binded to a collection in an object named NewClient
in my ViewModel
ClientMarketCodes
.
ClientMarketCodes
has a navigation property named MarketCodeTypes
which has a Market Navigation property. so I want to show in the datagrid the code,MarketCodeTyeName
,MarketName
.
I have Managed to show Markets
and MarketCodeTypes
in DataGrid comboboxes, but I want to do a relation between Markets
and MaketCodeTypes
where user can only select MarketCodeTypes
related to there Market
.
I have added a selected item to Markets
Combobox where on changing it excute filling method of MarketCodeTypes
collection binded to MarketCodeTypes
Combobox but it doesnt work correctly as the filter applys to all rows of MarketCodetypes
Combobox column.
I have something that happens in both combobox for example on changing the Markets
of one row the combobox shows all other markets I choosed one other Market and click the row is not affected and returns back to its original Market.i dont know why this happens.
Heres my ViewModel:
public class MarketsViewModel : ObservableObject, IMarketsViewModel, INavigationAware, IConfirmNavigationRequest, IRegionMemberLifetime
{
#region MarketsViewModel
public MarketsViewModel()
{
//NewClient.ClientMarketCodes[0].MarketCodeType.MarketID
//MarketCodeTypes = new ObservableCollection<MarketCodeType>();
this.GetMarkets();
//this.GetMarketCodeTypes();
this.PropertyChanged += MarketssViewModel_PropertyChanged;
}
private void MarketssViewModel_PropertyChanged(object sender, System.ComponentModel.PropertyChangedEventArgs e)
{
switch (e.PropertyName)
{
case "selectedMarket":
{
if (selectedMarket != null)
{
GetMarketCodeTypes();
}
break;
}
}
}
#endregion
#region --Members--
private ObservableCollection<Market> m_Market;
private ObservableCollection<MarketCodeType> m_MarketCodeType;
private List<MarketCodeType> m_MarketCodeTypes;
public List<MarketCodeType> MarketCodeTypesList
{
get
{
if (m_MarketCodeTypes == null)
{
m_MarketCodeTypes = new List<MarketCodeType>();
}
return m_MarketCodeTypes;
}
set
{
m_MarketCodeTypes = value;
RaisePropertyChanged("MarketCodeTypesList");
RaisePropertyChanged("MarketCodeTypes");
}
}
public ObservableCollection<MarketCodeType> MarketCodeTypes
{
get
{
if (MarketCodeTypesList != null)
return new ObservableCollection<MarketCodeType>(MarketCodeTypesList);
else
return new ObservableCollection<MarketCodeType>();
}
}
#endregion
#region --Properties--
public ObservableCollection<Market> Markets
{
get { return m_Market; }
set
{
m_Market = value;
RaisePropertyChanged("Markets");
}
}
private Market _selectedMarket;
public Market selectedMarket
{
get { return _selectedMarket; }
set
{
if (_selectedMarket != value)
{
_selectedMarket = value;
RaisePropertyChanged("selectedMarket");
RaisePropertyChanged("MarketCodeTypes");
}
}
}
#endregion
private void GetMarkets()
{
try
{
Market[] MarketArr;
using (var client = new ClientServiceProxy())
{
MarketArr = client.GetAllMarkets();
}
if (MarketArr != null)
{
this.Markets = new ObservableCollection<Market>(MarketArr);
}
}
catch (Exception e)
{
MessageBox.Show(e.Message);
}
}
private void GetMarketCodeTypes()
{
try
{
MarketCodeType[] MarketCodeTypeArr;
using (var client = new ClientServiceProxy())
{
MarketCodeTypeArr = client.GetAllMarketCodeTypes().Where(c=>c.MarketID==selectedMarket.marketID).ToArray();
}
if (MarketCodeTypeArr != null)
{
MarketCodeTypesList = MarketCodeTypeArr.ToList();
}
else
{ MarketCodeTypesList = new List<MarketCodeType>(); }
}
catch (Exception e)
{
MessageBox.Show(e.Message);
}
}
}`
Here's My Xaml:
<Grid x:Name="grid2" RenderTransformOrigin="0.5,0.5">
<Custom:C1DataGrid x:Name="c1DataGrid"
AutoGenerateColumns="False"
Height="490"
ItemsSource="{Binding Path=NewClient.ClientMarketCodes,Mode=TwoWay,UpdateSourceTrigger=LostFocus,ValidatesOnDataErrors=True,ValidatesOnExceptions=True}">
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="#FFBEBE00" Offset="0.5"/>
<GradientStop Color="#FFEDED9A" Offset="0.496"/>
</LinearGradientBrush>
</Custom:C1DataGrid.HeaderBackground>
<Custom:C1DataGrid.Columns>
<!--<Custom:DataGridCheckBoxColumn Header="???? ?????"/>-->
<Custom:DataGridTextColumn Header="Code" Binding="{Binding Code,Mode=TwoWay}" IsReadOnly="False" />
<Custom:DataGridTemplateColumn Header="MarketCodeType" >
<Custom:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock Text="{Binding MarketCodeType.NameA}"/>
</DataTemplate>
</Custom:DataGridTemplateColumn.CellTemplate>
<Custom:DataGridTemplateColumn.CellEditingTemplate>
<DataTemplate>
<ComboBox Name="cmbMarketCodeTypes"
ItemsSource="{Binding RelativeSource={RelativeSource FindAncestor,AncestorType=my:MarketsView},Path=DataContext.MarketCodeTypes}"
DisplayMemberPath="NameA"
SelectedValue="{Binding Path=MarketCodeTypeID,Mode=TwoWay,ValidatesOnDataErrors=True}"
/>
</DataTemplate>
</Custom:DataGridTemplateColumn.CellEditingTemplate>
</Custom:DataGridTemplateColumn>
<Custom:DataGridTemplateColumn Header="Markets">
<Custom:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock Text="{Binding MarketCodeType.Market.NameA}"/>
</DataTemplate>
</Custom:DataGridTemplateColumn.CellTemplate>
<Custom:DataGridTemplateColumn.CellEditingTemplate>
<DataTemplate>
<ComboBox Name="cmbMarkets" ItemsSource= "{Binding RelativeSource={RelativeSource FindAncestor,AncestorType=my:MarketsView},Path=DataContext.Markets,Mode=TwoWay}"
DisplayMemberPath="NameA" SelectedValue="{Binding Path=MarketCodeType.Market.MarketID,Mode=TwoWay}"
SelectedValuePath="MarketCodeType.MarketID"
SelectedItem="{Binding RelativeSource={RelativeSource FindAncestor,AncestorType=my:MarketsView},Path=DataContext.selectedMarket,Mode=TwoWay}" />
</DataTemplate>
</Custom:DataGridTemplateColumn.CellEditingTemplate>
</Custom:DataGridTemplateColumn>
</Custom:DataGridTemplateColumn>
</Custom:C1DataGrid.Columns>
</Custom:C1DataGrid>