Accessing control from datatemplate inside of gridview - c#

I have a ListView that displays a table with various columns. Each cell of a row in the table contains a different type of control; I am trying to allow the user to edit the data in each row by selecting a row and double-clicking it to make the cells editable. So I have been able to get all of them to work with the exception of the column that contains ComboBoxes.
XAML code:
This is the XAML code for the ListView. It has about 7 columns but I am focusing on the column with ComboBoxes as depicted here.
<ListView x:Name="MyListView" IsSynchronizedWithCurrentItem="True" Grid.Row="0" Grid.Column="0" HorizontalAlignment="Center" VerticalAlignment="Center" Margin="0,12,0,0" Height="315" Width="560" ItemsSource="{Binding People}">
<ListView.View>
<GridView>
<!-- More Grid column code here -->
<GridViewColumn Header="Fleet" Width="70">
<GridViewColumn.CellTemplate>
<DataTemplate>
<ComboBox Name="locationCmboBx" ItemsSource="{Binding DataContext.SchoolLocations, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}}, Mode=TwoWay}" Loaded="OnCmboBxLoad" IsEnabled="False" Width="55" HorizontalAlignment="Center"/>
</DataTemplate>
</GridViewColumn.CellTemplate>
</GridViewColumn>
<!-- More Grid column code here -->
</GridView>
</ListView.View>
</ListView>
C# code:
So here in the code-behind I am trying to use the VisualTreeHelper as recommended by others to get access to the locationsCmboBx (ComboBox) nested inside of the DataTemplate, CellTemplate and other XAML headers in the ListView.
// More code before here
ListView listViewItem = (ListView)(MyListView.ItemContainerGenerator.ContainerFromItem(MyListView));
ContentPresenter myContentPresenter = FindVisualChild<ContentPresenter>(listViewItem);
DataTemplate myDataTemplate = myContentPresenter.ContentTemplate;
ComboBox comboBox = (ComboBox)myDataTemplate.FindName("locationsCmboBx", myContentPresenter);
// More code before here
private childItem FindVisualChild<childItem>(DependencyObject obj) where childItem : DependencyObject
{
for (int i = 0; i < VisualTreeHelper.GetChildrenCount(obj); i++)
{
DependencyObject child = VisualTreeHelper.GetChild(obj, i);
if (child != null && child is childItem)
{
return (childItem)child;
}
else
{
childItem childOfChild = FindVisualChild<childItem>(child);
if (childOfChild != null)
{
return childOfChild;
}
}
}
return null;
}
So everything I have works but when I debug through the code and get to the FindName function ComboBox is null. Ultimately, I want to set the IsEnabled property on it and get the SelectedValue from the locationsCmboBx. I believe I am missing something but not sure of what. Any help would be appreciated?

The problem in your code is a typo by combo box's name in XAML locationCmboBx and in code behind is locationsCmboBx.
The code:
ListView listViewItem = (ListView)(MyListView.ItemContainerGenerator.ContainerFromItem(MyListView));
is also wrong. Argument of ContainerFromItem() must be a data item. Returned type is also wrong. It must be ListViewItem
I would recommend you to use a ViewModel + bindings and not a code behind to access the data. So you can avoid such a tipo errors. See also: Detect in XAML broken bindings already at compile time

I found this information:
public static class ListViewHelper
{
public static FrameworkElement GetElementFromCellTemplate(ListView listView, Int32 column, Int32 row, String name)
{
if (row >= listView.Items.Count || row < 0)
{
throw new ArgumentOutOfRangeException('row');
}
GridView gridView = listView.View as GridView;
if (gridView == null) { return null; }
if (column >= gridView.Columns.Count || column < 0)
{
throw new ArgumentOutOfRangeException('column');
}
ListViewItem item = listView.ItemContainerGenerator.ContainerFromItem(listView.Items[row]) as ListViewItem;
if (item != null)
{
GridViewRowPresenter rowPresenter = GetFrameworkElementByName(item);
if (rowPresenter != null)
{
ContentPresenter templatedParent = VisualTreeHelper.GetChild(rowPresenter, column) as ContentPresenter;
DataTemplate dataTemplate = gridView.Columns[column].CellTemplate;
if (dataTemplate != null && templatedParent != null)
{
return dataTemplate.FindName(name, templatedParent) as FrameworkElement;
}
}
}
return null;
}
private static T GetFrameworkElementByName(FrameworkElement referenceElement) where T : FrameworkElement
{
FrameworkElement child = null;
for (Int32 i = 0; i < VisualTreeHelper.GetChildrenCount(referenceElement); i++)
{
child = VisualTreeHelper.GetChild(referenceElement, i) as FrameworkElement;
System.Diagnostics.Debug.WriteLine(child);
if (child != null && child.GetType() == typeof(T))
{
break;
}
else if (child != null)
{
child = GetFrameworkElementByName(child);
if (child != null && child.GetType() == typeof(T))
{
break;
}
}
}
return child as T;
}
}
Source: How do I access the ui element at a row/cell in my GridView?

Related

How to reference Checkbox which is defined in DataTemplate

I have a datagrid as below. I want to reference CheckBox which is named ckbSelectedAll in code behind. WPF does not allow to reference with the name in code behind. Which way should i follow ?
<DataGrid x:Name="deckGrid" ItemsSource="{Binding DeckList}" AutoGenerateColumns="False"
SelectionMode="Single" Margin="10,10,0,0" SelectionUnit="FullRow" CanUserAddRows="False" IsReadOnly="True">
<DataGrid.Columns >
<DataGridTemplateColumn Width="70">
<DataGridTemplateColumn.HeaderTemplate >
<DataTemplate>
<CheckBox x:Name="ckbSelectedAll" IsThreeState="True" Margin="10,0,0,0" Checked="CheckBox_Checked" Unchecked="CheckBox_Checked">
</CheckBox>
</DataTemplate>
</DataGridTemplateColumn.HeaderTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
I answered a similar question regarding accessing buttons from with a DataTemplate of a ListView. Fortunately the process is very much the same. Here, I enumerate each of the DataGrid items from the ItemSource. I randomly uncheck a couple of items that I have stored in a List. I process the items from a Button_Click but doing it from the Window constructor after a call to InitializeComponent() should yield the same results.
List<CheckBox> checkboxes =
new List<CheckBox>();
private void Button_Click(object sender, RoutedEventArgs e)
{
deckGrid.Items
.Cast<dynamic>()
.ToList()
.ForEach(item => {
var checkitem =
(deckGrid
.ItemContainerGenerator
.ContainerFromItem(item));
CheckBox checkbox =
FindVisualChild<CheckBox>
(checkitem);
checkboxes
.Add(checkbox);
});
checkboxes[1]
.IsChecked = false;
checkboxes[3]
.IsChecked = false;
}
private childItem FindVisualChild<childItem>(DependencyObject obj)
where childItem : DependencyObject
{
for (int i = 0;
i < VisualTreeHelper
.GetChildrenCount(obj);
i++)
{
DependencyObject child =
VisualTreeHelper
.GetChild(obj, i);
if (child != null
&& child is childItem)
{
return
(childItem)child;
}
else
{
childItem childOfChild =
FindVisualChild<childItem>
(child);
if (childOfChild != null)
return
childOfChild;
}
}
return null;
}

Recursive search cant find tabitem content (only header) [WPF | C#]

I've been busy experimenting with UWP and WPF. After some getting used to, sometimes stupid, quirks, I decided to make one of my signature... "way overscoped" projects in WPF.
Anyway I'm making an application where I need to bind properties in a static class to UI elements (and when the properties change the UI elements need to change too). I know bindings exist but I've been trying for ages to get the UI to update when the property changes (with INotifyPropertyChanged and the PropertyChanged eventhandler). Eventually, i gave up and decided to make my own binding system(kinda anyway... I've got expansions planned, which is why i want it to be custom).
working of the code:
[Design Time]
Basically, what i have to do is make a property in the VNClient class, add a BindingAttribute(string bindingName) to it and set the Tag of the UI element i want to bind it to to the bindingName. I've got that setup.
[Runtime (only once at startup)]
Now the code will get all properties from the VNClient class with a BindingAttribute and add them to a dictionary as keys, then it will recursively look through the XAML hierarchy and any element with a tag that is also in the dictionary (meaning its bindable) will be added as a value to the dictionary.
[Runtime (every time a property changes)]
An event is fired telling the BindingManager which property changed. It will then get that property name from the dictionary (along with a dependency property but that's not implemented yet) to see which UI elements are bound to that property, then it will change the correct property to the correct value.
Here is the BindingManager:
internal class BindingManager
{
Dictionary<string, List<FrameworkElement>> staticReferenceBindings = new();
public BindingManager()
{
VNClient.PropertyChanged += VNClient_PropertyChanged;
MainWindow.ApplicationLoaded += MainWindow_ApplicationLoaded;
}
private void MainWindow_ApplicationLoaded(object? sender, EventArgs e)
{
foreach (PropertyInfo property in typeof(VNClient).GetProperties())
{
BindingAttribute attr;
if ((attr = (BindingAttribute)property.GetCustomAttribute(typeof(BindingAttribute), false)) != null)
{
staticReferenceBindings.Add(property.Name, null);
}
}
FindBindings(VNClient.MainWindowInstance);
}
private async void VNClient_PropertyChanged(object? sender, (string bindTag, DependencyProperty bindProperty, dynamic value) e)
{
foreach (KeyValuePair<string, List<FrameworkElement>> Binding in staticReferenceBindings)
{
if (Binding.Value == null) continue;
foreach (FrameworkElement element in Binding.Value)
{
DependencyProperty modifiedProperty = e.bindProperty;
//Property conversion for different elements... like background property => fill property
if (Binding is Shape && e.bindProperty == Control.BackgroundProperty) modifiedProperty = Shape.FillProperty;
else if (Binding is Window && e.bindProperty == TextBlock.TextProperty) modifiedProperty = Window.TitleProperty;
if (modifiedProperty != null) element.SetValue(modifiedProperty, e.value);
}
}
}
internal void FindBindings(DependencyObject parent)
{
int childCount = VisualTreeHelper.GetChildrenCount(parent);
for (int i = 0; i < childCount; i++)
{
DependencyObject dpObject = VisualTreeHelper.GetChild(parent, i);
FrameworkElement child = dpObject as FrameworkElement;
if (child != null)
{
string childTag = child.Tag?.ToString();
if (childTag != null && staticReferenceBindings.ContainsKey(childTag))
{
if (staticReferenceBindings[childTag] == null) staticReferenceBindings[childTag] = new List<FrameworkElement>();
staticReferenceBindings[childTag].Add(child);
}
}
FindBindings(dpObject);
}
}
}
Here is an example property:
internal static event EventHandler<(string bindTag, DependencyProperty bindProperty, dynamic value)> PropertyChanged;
private static string _gameName = "*Insert name here :)*";
[BindingAttribute(nameof(GameName))]
public static string GameName
{
get
{
return _gameName;
}
set
{
if (_gameName != value) _gameName = value;
OnPropertyChanged(nameof(GameName), TextBlock.TextProperty, value);
}
}
private static void OnPropertyChanged(string bindTag, DependencyProperty bindProperty, dynamic value) => PropertyChanged?.Invoke(Application.Current, (bindTag, bindProperty, value));
And here is that property bound to a TextBlock:
<TabItem Height="60" Width="250" BorderThickness="1" Background="Transparent" BorderBrush="Black" Foreground="White">
<TabItem.Header>
<Grid HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
<Image HorizontalAlignment="Left" Source="/Res/info_96px.png" Margin="0,0,180,0"/>
<TextBlock Text="About" HorizontalAlignment="Center" VerticalAlignment="Center" TextAlignment="Center" TextTrimming="None" Foreground="#BFFFFFFF"/>
</Grid>
</TabItem.Header>
<StackPanel>
<Image Source="/Res/Logo.png" HorizontalAlignment="Center" VerticalAlignment="Top" Height="150" Width="150"/>
<TextBlock Text="Made with *Insert name here :)*" HorizontalAlignment="Center"/>
<WrapPanel HorizontalAlignment="Center">
<!-- EXAMPLE BINDING --><TextBlock Text="{x:Static local:VNClient.GameName}" Tag="GameName" Margin="0,30,5,0" HorizontalAlignment="Center"/>
<TextBlock Text="was made with *Insert name here :)* version:" Margin="0,30,0,0" HorizontalAlignment="Center"/>
<TextBlock Text="{x:Static local:VNClient.EngineVersion}" Tag="EngineVersion" Margin="5,30,0,0" HorizontalAlignment="Center"/>
</WrapPanel>
</StackPanel>
</TabItem>
(static binding is so i can see the binding in the VS editor)
Okay, so, everything works fine BUT when this XAML element is in a TabItem my recursive search can only find the
<TabItem.Header/>
content NOT the
<TabItem.Content/>
meaning the bindings won't update... which is kinda not good...
If anyone has any idea besides "Just use the normal bindings..." that would be amazing
Thanks in advance :)
(and sorry if this is hard to read i am dyslexic)
EDIT:
I got it working by explicitly specifying, if it's a TabItem start another recursive search through it's content before continuing with it's header (it's a bandaid solution for sure, but I have yet to find bugs or similar problems with other controls like tab items)
[search result before]
Not all bindings found
[search result after]
As far as I can tell, all bindings found
[Modified recursive method in BindingManager]
internal void FindBindings(DependencyObject parent)
{
int childCount = VisualTreeHelper.GetChildrenCount(parent);
for (int i = 0; i < childCount; i++)
{
DependencyObject dpObject = VisualTreeHelper.GetChild(parent, i);
FrameworkElement child = dpObject as FrameworkElement;
if (child != null)
{
string childTag = child.Tag?.ToString();
if (childTag != null && staticReferenceBindings.ContainsKey(childTag))
{
if (staticReferenceBindings[childTag] == null) staticReferenceBindings[childTag] = new List<FrameworkElement>();
staticReferenceBindings[childTag].Add(child);
}
}
//New condition here
if (child is TabItem && ((TabItem)child).Content != null)
{
DependencyObject tabContent = ((TabItem)child).Content as DependencyObject;
FindBindings(tabContent);
}
FindBindings(dpObject);
}
}
if anyone still as anything to add to this or a more universal solution pls don't hesitate to comment.

Check checkboxes in combobox

I have a combobox which has checkbox as its combobox.itemtemplate.
<ComboBox Name="comboBoxTest"
SelectedValuePath="Test"
SelectedItem="{Binding SelectedTest, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
SelectedValue="{Binding SelectedTest, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
ItemsSource="{Binding Test, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
TextBoxBase.TextChanged ="comboBoxTest_TextChanged" Grid.ColumnSpan="2"
TextSearch.TextPath="Model" >
<ComboBox.ItemTemplate>
<DataTemplate>
<CheckBox Name="checkBoxTest"
Content="{Binding Test}"
Click="checkBoxTest_Click"/>
</DataTemplate>
</ComboBox.ItemTemplate>
</ComboBox>
An “--Select All--” item has been add into the result list when the result list is produced.
When user checks on the “All” item, the other checkboxes should be checked as well.
I am using the codes below but it doesn’t work.
if (checkBoxTest.Content.ToString().Equals("--Select All--"))
{
foreach (object item in comboBoxTest.Items)
{
ComboBoxItem comboBoxItem = comboBoxTest.ItemContainerGenerator.ContainerFromItem(item) as ComboBoxItem;
FrameworkElement element = comboBoxItem.ContentTemplate.LoadContent() as FrameworkElement;
CheckBox checkBox = element.FindName("checkBoxTest") as CheckBox;
checkBox.IsChecked = true;
}
}
There are few issues in your code let me first tell you about those issue.
your if condition for identifying the "Select All" checkbox is incorrect. Your need to use Contains() instead of equals()
The checkbox you are fetching is not the correct one within the comboBox Item. If you try to see the checkBox.Content property you will see null as result.
See below code to select all the checkboxes within the comboBox when "Select All" checkbox is checked.
Your Checkbox Click event should be as below.
private void checkBoxTest_Click(object sender, RoutedEventArgs e)
{
CheckBox checkBoxTest = e.Source as CheckBox;
if (checkBoxTest == null)
return;
if (checkBoxTest.Content.ToString().Contains("Select All") && checkBoxTest.IsChecked == true)
{
foreach (object item in comboBoxTest.Items)
{
ComboBoxItem comboBoxItem = comboBoxTest.ItemContainerGenerator.ContainerFromItem(item) as ComboBoxItem;
if (comboBoxItem == null)
{
return;
}
CheckBox checkBox = FindVisualChildByName<CheckBox>(comboBoxItem, "checkBoxTest");
checkBox.IsChecked = true;
}
}
}
I have added a new method to fetch the visual child within any element from the name of the child and its type.
private static T FindVisualChildByName<T>(DependencyObject parent, string name) where T : DependencyObject
{
for (int i = 0; i < VisualTreeHelper.GetChildrenCount(parent); i++)
{
var child = VisualTreeHelper.GetChild(parent, i);
string controlName = child.GetValue(NameProperty) as string;
if (controlName == name)
{
return child as T;
}
T result = FindVisualChildByName<T>(child, name);
if (result != null)
return result;
}
return null;
}
use CompositeCollection inside your ComboBox, check below answers for more information
Combobox and checkbox with "Select All" Checkbox with binding in wpf
How can I insert a "Select All" item at the top of a ComboBox with its ItemsSource set?
Binding/Triggering "Select all"-CheckBox ComboBoxItem in WPF

Get DataGrid Row from ComboBox Event

I have a DataGrid with 2 columns defined in XAML as
<DataGrid x:Name="marketInfodg" Grid.Row="1"
ItemsSource = "{Binding ElementName=This, Path=dataTableTest}"
CanUserAddRows="False">
<DataGrid.Columns>
<DataGridComboBoxColumn Header="Department Id" x:Name="comboboxColumn1"
SelectedValueBinding="{Binding Department Id}" />
<DataGridTemplateColumn x:Name="DataGridTempCol" Header="Selection">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<ComboBox
x: Name = "combo"
SelectedValue = "{Binding Selection, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
ItemsSource = "{Binding comboBoxSelections, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type Window}}}"
DropDownOpened = "combo_DropDownOpened"
DisplayMemberPath = "Key"
IsEditable="True">
</ComboBox>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
The constructor code is
_dataTableTest = new DataTable();
DataColumn dc = new DataColumn();
dc.ReadOnly = false;
dc.DataType = typeof(String);
dc.ColumnName = "Department Id";
_dataTableTest.Columns.Add(dc);
DataColumn dc1 = new DataColumn();
dc1.ReadOnly = false;
dc1.DataType = typeof(KeyValuePair<string, double>);
dc1.ColumnName = "Selection";
_dataTableTest.Columns.Add(dc1);
marketInfodg.ItemsSource = _dataTableTest.DefaultView;
var row = _dataTableTest.NewRow();
row = _dataTableTest.NewRow();
_dataTableTest.Rows.Add(row);
row["Department Id"] = "X567";
row["Selection"] = (KeyValuePair<string, double>)comboBoxSelections[0];
which effectively sets a single row as column "Department Id" = "X567" and a second column is a combobox set to the first item in comboBoxSelections[0]
The combo_DropDownOpened event fires when any Combobox drop down is opened (obviously) and I can set the variable cb based on the sender, using
private void combo_DropDownOpened(object sender, EventArgs e)
{
var cb = ((System.Windows.Controls.ComboBox)sender);
}
How do I also get the associated Row (all columns in the Row) and RowIndex/number of the firing ComboBox in the combo_DropDownOpened event?
ComboBox lies in the visual tree of the DataGrid. If you travel up Visual Tree you will find the DataGridRow on the way to the top to the DataGrid.
You can use the VisualTreeHelper class to walk up to the Visual tree. Generally, you can use this method to find any parent in the Visual tree of your control. Put this method in some Utility class and use whenever you feel like walking up to Visual tree for your control to find any parent -
public static Parent FindParent<Parent>(DependencyObject child)
where Parent : DependencyObject
{
DependencyObject parentObject = child;
//We are not dealing with Visual, so either we need to fnd parent or
//get Visual to get parent from Parent Heirarchy.
while (!((parentObject is System.Windows.Media.Visual)
|| (parentObject is System.Windows.Media.Media3D.Visual3D)))
{
if (parentObject is Parent || parentObject == null)
{
return parentObject as Parent;
}
else
{
parentObject = (parentObject as FrameworkContentElement).Parent;
}
}
//We have not found parent yet , and we have now visual to work with.
parentObject = VisualTreeHelper.GetParent(parentObject);
//check if the parent matches the type we're looking for
if (parentObject is Parent || parentObject == null)
{
return parentObject as Parent;
}
else
{
//use recursion to proceed with next level
return FindParent<Parent>(parentObject);
}
}
Now, in your dropDown event handler you can use the above function to find the DataGridRow like this -
private void combo_DropDownOpened(object sender, EventArgs e)
{
var cb = ((System.Windows.Controls.ComboBox)sender);
DataGridRow dataGridRow = FindParent<DataGridRow>(cb);
int index = dataGridRow.GetIndex();
}

How to put data in WPf Data Grid specific cell

i m using DataGrid in WPF
I want to put some specific string in some specific cell . How can we do this.
I am putting value this way .
//pPredicate is a string variable havign some value
// i m assigning in a particualr cell (3rd col)
if (GetCell(3).Content is TextBlock)
{
((TextBlock)(GetCell(3).Content)).Text = pPredicate;
}
else // TextBox
{
((TextBox)(GetCell(3).Content)).Text = pPredicate;
}
private DataGridCell GetCell(int column)
{
DataGridRow rowContainer = GetRow();
if (rowContainer != null)
{
DataGridCellsPresenter presenter = GetVisualChild<DataGridCellsPresenter>(rowContainer);
// Try to get the cell but it may possibly be virtualized.
DataGridCell cell = (DataGridCell)presenter.ItemContainerGenerator.ContainerFromIndex(column);
if (cell == null)
{
// Now try to bring into view and retreive the cell.
customDataGrid.UCdataGridView.ScrollIntoView(rowContainer, customDataGrid.UCdataGridView.Columns[column]);
cell = (DataGridCell)presenter.ItemContainerGenerator.ContainerFromIndex(column);
}
return cell;
}
return null;
}
private DataGridRow GetRow()
{
DataGridRow row = (DataGridRow)customDataGrid.UCdataGridView.ItemContainerGenerator.ContainerFromIndex(_currentRowIndex);
if (row == null)
{
// May be virtualized, bring into view and try again.
customDataGrid.UCdataGridView.UpdateLayout();
customDataGrid.UCdataGridView.ScrollIntoView(customDataGrid.UCdataGridView.Items[_currentRowIndex]);
row = (DataGridRow)customDataGrid.UCdataGridView.ItemContainerGenerator.ContainerFromIndex(_currentRowIndex);
}
return row;
}
private T GetVisualChild<T>(Visual parent) where T : Visual
{
T child = default(T);
int numVisuals = VisualTreeHelper.GetChildrenCount(parent);
for (int i = 0; i < numVisuals; i++)
{
Visual v = (Visual)VisualTreeHelper.GetChild(parent, i);
child = v as T;
if (child == null)
{
child = GetVisualChild<T>(v);
}
if (child != null)
{
break;
}
}
return child;
}
the problem in top most statmetnts is the row is in edit mode the grid contains textbox while otherwise grid contains textblock. When i m putting value in textblock it does not persisting while putting value in textbox persists.
XAML part of custom DataGrid
<WPFtoolkit:DataGridTextColumn x:Name="dgName" Binding="{Binding Path=Name}" Header="Name" MinWidth="100" Visibility="Collapsed"/>
<WPFtoolkit:DataGridTextColumn x:Name="dgPredicates" Binding="{Binding Path=Predicate}" Header="Predicate" MinWidth="100"
Visibility="Collapsed"/>
<WPFtoolkit:DataGridTemplateColumn Header="Delete" IsReadOnly="True"
Visibility="Collapsed" MaxWidth="80" Width ="*">
<WPFtoolkit:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<Image Source="../images/Delete.png" Height="15" Width="15"/>
</DataTemplate>
</WPFtoolkit:DataGridTemplateColumn.CellTemplate>
</WPFtoolkit:DataGridTemplateColumn>
<WPFtoolkit:DataGridTextColumn Binding="{Binding Path=TreeType}" Header="Tree Type" Width="50"
Visibility="Collapsed"/>
</WPFtoolkit:DataGrid.Columns>
</WPFtoolkit:DataGrid>
If I understand your question correctly then you want the changes that you make to the TextBlock/TextBox to be propagated to the underlying DataTable. This works for a TextBox but not for a TextBlock.
The reason for this is that TextBox.Text binds TwoWay by default but TextBlock.Text binds OneWay. If you want this to work you have to change all your TextBlock bindings to explicitly use TwoWay like
<TextBlock Text="{Binding Path=SomeProperty, Mode=TwoWay}"/>
if you dont want interest xaml , this code maybe work for yor need.
(xx ,yy is row and colonm number)
DataGridCell cell =(YourDgName.Columns[XX].GetCellContent(DgCagrilar.Items[YY])).Parent s DataGridCell;
if (cell.Background == Brushes.Pink)
cell.Background = Brushes.Plum;
else
cell.Background = Brushes.Pink;

Categories

Resources