1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109
| [MarkupExtensionReturnType(typeof(object))]
public class Reference : MarkupExtension
{
private object _key = null;
#region Constructors
public Reference() { }
public Reference(object key) { _key = key; }
#endregion
#region Key for binding (ATTACHED) (KeyBindingProperty & KeyBindingInfoProperty)
private static DependencyProperty KeyBindingInfoProperty = DependencyProperty.RegisterAttached(
"KeyBindingInfo",
typeof(object),
typeof(Reference),
new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.Inherits));
private static DependencyProperty FirstKeyBindingProperty = DependencyProperty.RegisterAttached(
"FirstKeyBinding",
typeof(object),
typeof(Reference),
new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.Inherits, FirstChange));
private static void FirstChange(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
try
{
DependencyObject _targetObject = d;
DependencyProperty _targetProperty = _targetObject.GetValue(Reference.KeyBindingInfoProperty) as DependencyProperty;
object value = _targetObject.GetValue(Reference.FirstKeyBindingProperty);
// reset binding to reference value
Binding binding = new Binding((string)value);
BindingOperations.SetBinding(_targetObject, Reference.KeyBindingProperty, binding);
}
catch { }
}
private static DependencyProperty KeyBindingProperty = DependencyProperty.RegisterAttached(
"KeyBinding",
typeof(object),
typeof(Reference),
new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.Inherits, Change));
private static void Change(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
try
{
DependencyObject _targetObject = d;
DependencyProperty _targetProperty = _targetObject.GetValue(Reference.KeyBindingInfoProperty) as DependencyProperty;
object value = _targetObject.GetValue(Reference.KeyBindingProperty);
_targetObject.SetValue(_targetProperty, value);
}
catch { }
}
#endregion
public override object ProvideValue(IServiceProvider serviceProvider)
{
DependencyObject _targetObject = null;
DependencyProperty _targetProperty = null;
if (_key is Binding)
{
Binding binding = _key as Binding;
IProvideValueTarget target = serviceProvider.GetService(typeof(IProvideValueTarget)) as IProvideValueTarget;
if (target != null &&
target.TargetObject is DependencyObject &&
target.TargetProperty is DependencyProperty)
{
_targetObject = (DependencyObject)target.TargetObject;
_targetProperty = (DependencyProperty)target.TargetProperty;
}
else
{
return this; // magic
}
// cette ligne doit etre positionné avant le set du binding sinon le binding se realise et on ne retrouve pas _targetProperty
_targetObject.SetValue(Reference.KeyBindingInfoProperty, _targetProperty);
BindingOperations.SetBinding(_targetObject, Reference.FirstKeyBindingProperty, binding);
object value = _targetObject.GetValue(Reference.FirstKeyBindingProperty);
if(value == null)
{
var meta = _targetProperty.GetMetadata(_targetObject);
value = meta.DefaultValue;
}
return value;
}
else
{
try
{
IProvideValueTarget target = serviceProvider.GetService(typeof(IProvideValueTarget)) as IProvideValueTarget;
if (target != null &&
target.TargetObject is DependencyObject &&
target.TargetProperty is DependencyProperty)
{
_targetObject = (DependencyObject)target.TargetObject;
_targetProperty = (DependencyProperty)target.TargetProperty;
}
Binding binding = new Binding((string)_key);
_targetObject.SetValue(Reference.KeyBindingInfoProperty, _targetProperty);
BindingOperations.SetBinding(_targetObject, Reference.KeyBindingProperty, binding);
return _targetObject.GetValue(Reference.KeyBindingProperty);
}
catch { return null; }
}
throw new InvalidOperationException("Inputs cannot be blank");
}
} |