I created a custom column that derives from GridViewBoundColumnBase. The column defines the dependency property SearchType.
I would like to bind this property to the field "ArticleType" while the DataMemberBinding binds to "Article".
<
controlsBaseGridViewColumns:GridViewSearchColumn
UniqueName
=
"Article"
Width
=
"*"
MinWidth
=
"150"
DataMemberBinding
=
"{Binding Article, Mode=TwoWay}"
SortMemberPath
=
"Article.LookupValue"
SearchType
=
"{Binding ArticleType, Converter={StaticResource searchTypeConverter}}"
Header
=
"Artikel"
/>
The binding produces the following runtime error:
System.Windows.Data Error: 40 : BindingExpression path error: 'ArticleType' property not found on 'object' ''OrderItem' (HashCode=19537849)'. BindingExpression:Path=ArticleType; DataItem='OrderItem' (HashCode=19537849); target element is 'GridViewSearchColumn' (HashCode=4419325); target property is 'SearchType' (type 'SearchTypes')
Can you please help me out?
Thanks for your support!
e
5 Answers, 1 is accepted
It seems that the ArticleType property you're trying to bind to does not exist in the OrderItem business object. Is that the case? If so, could you try instead binding the SearchType property to ArticleType?
If this modification does not resolve the issue, could you please provide more details about the exact setup at your end? Specifying the properties of the OrderItem and Article objects would definitely be of help. If possible, please also provide the code behind your GridViewSearchColumn.
Thank you in advance for your cooperation.
Regards,
Dilyan Traykov
Telerik by Progress
Hello Dilyan,
thanks for your response!
In my original post I tried to simplify the error message by replacing the original object names by common names like "orderitem" and I just saw that I made a mistake.
So here is the correct and complete scenario:
I assigned an observable collection of InvoicingInstitutionContractGroupSpecialToolID objects to the itemssource property of the grid. This object contains the properties ArticleType and Article.
The XAML definition of the grid is:
<
telerik:RadGridView
x:Name
=
"gridView"
AutoGenerateColumns
=
"False"
IsFilteringAllowed
=
"False"
>
<
telerik:RadGridView.Columns
>
<
controlsBaseGridViewColumns:GridViewLookupKeyColumn
UniqueName
=
"ArticleType"
Width
=
"130"
MinWidth
=
"100"
DataMemberBinding
=
"{Binding ArticleType, Mode=TwoWay}"
KeyName
=
"ArtikelTyp"
Header
=
"Artikeltyp"
/>
<
controlsBaseGridViewColumns:GridViewSearchColumn
UniqueName
=
"Article"
Width
=
"*"
MinWidth
=
"150"
DataMemberBinding
=
"{Binding Article, Mode=TwoWay}"
SortMemberPath
=
"Article.LookupValue"
SearchType
=
"{Binding ArticleType, Converter={StaticResource searchTypeConverter}}"
Header
=
"Artikel"
/>
</
telerik:RadGridView.Columns
>
<
telerik:RadGridView.SortDescriptors
>
<
telerik:SortDescriptor
Member
=
"Article.LookupValue"
SortDirection
=
"Ascending"
/>
</
telerik:RadGridView.SortDescriptors
>
</
controlsBaseGridView:GridView
>
After assigning the itemssource, I get the following runtime error message:
System.Windows.Data Error: 40 : BindingExpression path error: 'ArticleType' property not found on 'object' ''InvoicingInstitutionMasterData' (HashCode=2569762)'. BindingExpression:Path=ArticleType; DataItem='InvoicingInstitutionMasterData' (HashCode=2569762); target element is 'GridViewSearchColumn' (HashCode=35481661); target property is 'SearchType' (type 'SearchTypes')
The point is, that the datacontext contains the InvoicingInstutitionMasterData object, but this object is irrelevant for the grid. It seems that the binding of the column's ArticleType property doesn't bind to the row item, but to the datacontext. Do I have to define a binding with relative source to address to row item and not the datacontext?
I hope I made it clearer.
Thanks!
I forgot the definition of the GridViewSearchColumn. So here it is:
public
class
GridViewSearchColumn : GridViewBoundColumnBase
{
public
static
readonly
DependencyProperty SearchTypeProperty = DependencyProperty.Register(
"SearchType"
,
typeof
(SearchTypes),
typeof
(GridViewSearchColumn),
new
PropertyMetadata(SearchTypes.Commodity));
public
SearchTypes SearchType
{
get
{
return
(SearchTypes)GetValue(SearchTypeProperty); }
set
{ SetValue(SearchTypeProperty, value); }
}
public
override
System.Windows.FrameworkElement CreateCellEditElement(Telerik.Windows.Controls.GridView.GridViewCell cell,
object
dataItem)
{
var searchBox =
new
SearchBox();
searchBox.Init(
this
.AppContext);
searchBox.SearchType =
this
.SearchType;
searchBox.PreCondition =
this
.PreCondition;
searchBox.IsReadOnly = ((GridView)
this
.Parent).IsReadOnly;
searchBox.SetBinding(SearchBox.SelectedValueProperty,
new
Binding() { Mode = BindingMode.TwoWay, NotifyOnValidationError =
true
, ValidatesOnExceptions =
true
, UpdateSourceTrigger = System.Windows.Data.UpdateSourceTrigger.LostFocus, Path =
new
System.Windows.PropertyPath(
this
.DataMemberBinding.Path.Path) });
return
searchBox;
}
}
Unfortunately, I'm unable to reproduce the issue you've described using just the code you've provided.
However, I believe the following line may be causing the change of the data context:
searchBox.Init(
this
.AppContext);
It would be of help if you could share more information about your SearchBox class and its Init method.
Additionally, could you please have a look at the Create Custom Column Editor article and see whether your implementation differs from the approach described in there in any way?
Regards,
Dilyan Traykov
Telerik by Progress
Hi,
I have the same problem. Did this ever got solved?
I attached an example using the CustomColumn Source Code from the GitHub Examples and the RadColorPickerColumn How To to demonstrate the behavior.
Like David writes:
It seems that the binding of the column's ArticleType property doesn't bind to the row item, but to the datacontext. Do I have to define a binding with relative source to address to row item and not the datacontext?
Maybe you can reproduce the behavior with the attached Example.
regards, marco
Hi Marco,
Thank you very much for the provided project.
If I understand your requirement correctly, you wish to have a separate MainPalette for each item, based on its ColorPreset property.
If that is indeed the case, what I can suggest is to expose a string property for the column, let's say MainPaletteBindingPath, and use this property as follows:
var cellEditElement = new RadColorPicker();
cellEditElement.SetBinding(RadColorPicker.MainPaletteProperty, new Binding(this.MainPaletteBindingPath));
For your convenience, I've demonstrated what I have in mind in the sample project you provided.
Please have a look and let me know if a similar approach would work in your original application.
Thank you Dilyan,
my goal was to use a binding OR direct values with a single DependencyProperty. The Problem was: in a custom column it uses the wrong context (gridView's datacontext instead of the row item's datacontext)
I attach a modified sample to make the "context confusion" more clear.
Maybe the question could be: how can i set the datacontext of the DependencyProperty to the row item?
Hello Marco,
Thank you for the updated project.
The reason for this behavior is that when using a DependencyProperty, the binding is evaluated the moment the control is loaded. In the case of StringAsDependencyProperty="{Binding StringProperty}", the binding will evaluate the DataContext of the RadGridView control, and the string value of "grid datacontext" will be used in the CreateCellElement method. This behavior stems from the nature of the WPF framework and I cannot think of an easy way to overcome it.
As you have noticed, this does not lead to the desired behavior and thus, I would not recommend using a DependencyProperty in this case. Is there a reason you wish to use a DependencyProperty in particular, other than limiting the number of public properties that are exposed by the column?
If that is not the case, my best suggestion would be to go with the approach I proposed in my previous reply and use a string to determine the property of the business objects which should be used for the binding. You can then expose an additional property, let's say FallbackValue, and use this instead of the binding when you wish to set the values directly.
Please let me know if such an approach would work for you.
Thank you for the clarification!
you get it exactly, i tried to get a clean solution with just one property.
I will use an extra property when i want to use "static values".