I'm currently playing around with using Eto.Forms from F#. One minor annoyance I've run into is that when you define your GUI objects (Forms, Panels, Buttons, etc) in external files (XAML or JSON) and declare event handlers, those event handlers have to have a specific type:
member public this.OnFirstButtonClicked (sender:Object, e:EventArgs) ->
MessageBox.Show(this, "First button was clicked")
|> ignore
member public this.OnSecondButtonClicked (sender:Object, e:EventArgs) ->
MessageBox.Show(this, "Second button was clicked")
|> ignore
The repetition of the type signatures is bothering me. (There's actually a lot of repetition in these two functions, like the calls to MessageBox with barely-varying parameters, but this is just a test project. In a real project, I'd be doing something different for both these buttons.) I'd like to not have to repeat the type signature of each of these functions every time. After reading this page at F Sharp For Fun and Profit, I thought I could do something like this:
type EventHandler = (Object * EventArgs) -> unit
member public this.OnFirstButtonClicked : EventHandler ->
MessageBox.Show(this, "First button was clicked")
|> ignore
member public this.OnSecondButtonClicked : EventHandler ->
MessageBox.Show(this, "Second button was clicked")
|> ignore
However, when I tried this I discovered that on member functions, that syntax actually means "This function returns an EventHandler function". I want to say "This member function is an EventHandler function", and I don't know how to do that.
Update: Since writing the above question, I've learned that I don't actually have to specify the type signatures of the event handler functions' parameters. The following will work:
member public this.OnFirstButtonClicked (sender, e) ->
MessageBox.Show(this, "First button was clicked")
|> ignore
member public this.OnSecondButtonClicked (sender, e) ->
MessageBox.Show(this, "Second button was clicked")
|> ignore
However, my real question isn't "how can I make these event handlers work?" My real question is, "I've learned how to specify the type of a function that isn't a member of a class, but how do I do that for a function that is a member of a class?"
The only difference between standalone function definition and method definition is the
memberkeyword and self-identifier. Other than that, the syntax is the same.Check again the example on F# for fun and profit
It's actually a value binding, not a function binding. The function is defined with a lambda expression
fun a b -> a + band bound to identifier f.To use this kind of definition, you would have to define your event handlers as
Again, it works exactly the same for standalone functions.