I am trying to convert a C# Dependency Property that limits the maximum length of text entered into a ComboBox to F#. The program is a MVVM program that uses F# for the model and viewmodel, and C# for the view. the working C# code is this:
public class myComboBoxProperties
{
public static int GetMaxLength(DependencyObject obj)
{
return (int)obj.GetValue(MaxLengthProperty);
}
public static void SetMaxLength(DependencyObject obj, int value)
{
obj.SetValue(MaxLengthProperty, value);
}
// Using a DependencyProperty as the backing store for MaxLength. This enables animation, styling, binding, etc...
public static readonly DependencyProperty MaxLengthProperty =
DependencyProperty.RegisterAttached("MaxLength",
typeof(int),
typeof(myComboBoxProperties),
new UIPropertyMetadata(OnMaxLengthChanged));
private static void OnMaxLengthChanged(DependencyObject obj, DependencyPropertyChangedEventArgs args)
{
if (obj is ComboBox)
{
ComboBox comboBox = (ComboBox)obj;
comboBox.Loaded += (sender, e) =>
{
TextBox textBox = comboBox.Template.FindName("PART_EditableTextBox", comboBox) as TextBox;
if (textBox != null)
{
textBox.SetValue(TextBox.MaxLengthProperty, args.NewValue);
}
};
}
}
}
The F# code is this:
type myComboBoxProperties() =
static let OnMaxLengthChanged (myobj1 : DependencyObject, args : DependencyPropertyChangedEventArgs) =
let comboBox = myobj1 :?> ComboBox
comboBox.Loaded.Subscribe (fun _ ->
let textBox : TextBox = comboBox.Template.FindName("PART_EditableTextBox", comboBox) :?> TextBox
match textBox with
| null -> ()
|_ -> textBox.SetValue(TextBox.MaxLengthProperty, args.NewValue))
static let MaxLengthProperty = DependencyProperty.RegisterAttached("MaxLength", typeof<int>, typeof<myComboBoxProperties>, new UIPropertyMetadata(OnMaxLengthChanged))
static member GetMaxLength (myobj : DependencyObject) = myobj.GetValue(MaxLengthProperty) :?> int
static member SetMaxLength (myobj : DependencyObject, value : int) = myobj.SetValue(MaxLengthProperty, value)
The problem I am having is that the XAML error I get is:
Default value type does not match type of property
MaxLength
What am I doing wrong?
A dependency property can reference a value through data binding. Data binding works through a specific markup extension syntax in XAML, or the Binding object in code. With data binding, determination of the final property value is deferred until run time, at which time the value is obtained from a data source.
A dependency property represents or supports a specific feature of the programming model for defining a Windows Runtime app with XAML for UI and C#, Microsoft Visual Basic or Visual C++ component extensions (C++/CX) for code. These features include: Data binding. Styles. Storyboarded animations.
A dependency property provides functionality that extends the functionality of a property as opposed to a property that is backed by a field. Often, each such functionality represents or supports a specific feature of the overall WPF set of features.
You could try this
open System.Windows
open System.Windows.Controls
type MyComboBoxProperties() =
static let OnMaxLengthChanged (myobj1 : DependencyObject) (args : DependencyPropertyChangedEventArgs) =
let comboBox = myobj1 :?> ComboBox
comboBox.Loaded.Add (
fun _ ->
let textBox : TextBox = comboBox.Template.FindName("PART_EditableTextBox", comboBox) :?> TextBox
match textBox with
| null -> ()
|_ -> textBox.SetValue(TextBox.MaxLengthProperty, args.NewValue)
)
static let MaxLengthProperty =
DependencyProperty.RegisterAttached(
"MaxLength",
typeof<int>,
typeof<MyComboBoxProperties>,
UIPropertyMetadata(0, PropertyChangedCallback OnMaxLengthChanged)
)
static member GetMaxLength (myobj : DependencyObject) = myobj.GetValue(MaxLengthProperty) :?> int
static member SetMaxLength (myobj : DependencyObject, value : int) = myobj.SetValue(MaxLengthProperty, value)
The key difference to your code is this UIPropertyMetadata(0, PropertyChangedCallback OnMaxLengthChanged)
that converts OnMaxLengthChanged
into a PropertyChangedCallback
.
But it feels odd to me that you subscribe to the .Loaded
even each time the max value you change. I suspect you only like to subscribe the first time?
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With