In Tag, you are not it I mistakenly said you need an IValueConverter so that the xaml parser could convert the string "Divide" into the enum value Operator.Divide. (I must've been too busy trying to find a clever Parthian Shot.)
IValueConverters are used by the binding engine, and are assigned via binding markup extensions.
The OperationConverter code that I provided was not used by the xaml parser. Instead, the parser was automatically turning the string into the corresponding enum value.
So my sample code worked quite by accident, because I happened to use an enum to define my operations. What happens when I use objects instead of enums?
To find out, lets change the Operator class, and remove the enum:
public class Operator
{
public static Operator GetOperator(DependencyObject obj)
{
return (Operator)obj.GetValue(OperationProperty);
}
public static void SetOperator(DependencyObject obj, Operator value)
{
obj.SetValue(OperationProperty, value);
}
public static readonly DependencyProperty OperationProperty =
DependencyProperty.RegisterAttached("Operator",
typeof(Operator), typeof(Operator), null);
}
public class NotAnOperator : Operator { }
public class PlusOperator : Operator { }
public class MinusOperator : Operator { }
public class TimesOperator : Operator { }
public class DivideOperator : Operator { }
public class EqualsOperator : Operator { }
then update Page.xaml:
<Button Grid.Column="3" Grid.Row="2" Content="/"
Style="{StaticResource calcButtonStyle}"
local:Operator.Operator="Divide" Click="ClickOperator" />
When I run the code, I get this nasty exception:
Wow! Catastrophic!
I am missing a converter, but not a value converter. What I need is a TypeConverter. Lets replace the OperationConverter code with OperatorConverter:
public class OperatorConverter : TypeConverter
{
public override object ConvertFrom(object value)
{
System.Diagnostics.Debug.WriteLine(
"Converting '{0}' to an Operator", value.ToString());
Operator returnValue = new NotAnOperator();
if (value.GetType().Equals(typeof(System.String)))
{
switch ((string)value)
{
case "Minus":
returnValue = new MinusOperator();
break;
case "Plus":
returnValue = new PlusOperator();
break;
case "Times":
returnValue = new TimesOperator();
break;
case "Divide":
returnValue = new DivideOperator();
break;
case "Equals":
returnValue = new EqualsOperator();
break;
}
}
return returnValue;
}
}
and add a TypeConverter attribute to the Operator class:
[TypeConverter(typeof(OperatorConverter))]
public class Operator
This time, when I run, the conversion code does get called.
Published May 19, 2008