private bool VerifyEqual(object knownValue, Type knownType, object itemValue, DynamicValueConverter converter) { object tempValue = knownValue; if (knownType != null && itemValue != null) { Type itemType = itemValue.GetType(); // determine if selectedValue is comparable to itemValue, convert if necessary // using a DefaultValueConverter if (!knownType.IsAssignableFrom(itemType)) { tempValue = converter.Convert(knownValue, itemType); if (tempValue == DependencyProperty.UnsetValue) { // can't convert, keep original value for the following object comparison tempValue = knownValue; } } } return Object.Equals(tempValue, itemValue); }
private object FindItemWithValue(object value) { if (!HasItems) return DependencyProperty.UnsetValue; // use a representative item to determine which kind of binding to use (XML vs. CLR) BindingExpression bindingExpr = PrepareItemValueBinding(Items.GetRepresentativeItem()); if (bindingExpr == null) return DependencyProperty.UnsetValue; // no suitable item found // optimize for case where there is no SelectedValuePath (meaning // that the value of the item is the item itself, or the InnerText // of the item) if (string.IsNullOrEmpty(SelectedValuePath)) { // when there's no SelectedValuePath, the binding's Path // is either empty (CLR) or "/InnerText" (XML) string path = bindingExpr.ParentBinding.Path.Path; Debug.Assert(String.IsNullOrEmpty(path) || path == "/InnerText"); if (string.IsNullOrEmpty(path)) { // CLR - item is its own selected value if (Items.Contains(value)) return value; else return DependencyProperty.UnsetValue; } else { // XML - use the InnerText as the selected value return FindXmlNodeWithInnerText(value); } } Type selectedType = (value != null) ? value.GetType() : null; object selectedValue = value; DynamicValueConverter converter = new DynamicValueConverter(false); foreach (object current in Items) { bindingExpr.Activate(current); object itemValue = bindingExpr.Value; if (VerifyEqual(value, selectedType, itemValue, converter)) { bindingExpr.Deactivate(); return current; } } bindingExpr.Deactivate(); return DependencyProperty.UnsetValue; }