Proposed "on_xxx_if" functionality

Maybe I’m missing something with iced, but I keep running into the following paradigm:

let my_button_disabled = Button::new("Foo");

let my_button = match self.state {
       SomeStateType::Running => my_button_disabled,
       SomeStateType::Ready => my_button_disabled.on_input(Message::SomeMessage)
}

return row![my_button]

This allows me to conditionally enable or disable certain elements depending on whether the application is in a certain state. In my case, I have a desktop application where you configure a request in the GUI, and then when the request is running, all of the input elements are disabled until the request is completed or cancelled.

I feel like this is extremely cumbersome. What if there were a conditional one-line for on_xxx where it only assigns the handler if some condition is true, i.e:

    let my_button = Button::new("Foo").on_input_if(
        self.state ==  SomeStateType::Ready,
        Message::SomeMessage);

This succinctly encapsulates all of that logic in a single line. If the condition is true, enable the button with that message. If the condition is false, don’t register the message, and thus disable the interactable element.

Does anyone have any thoughts on this?

I was just informed by a buddy of mine that this isn’t valid syntax due to the way the enums work. But we could just as easily make it a conditional input that is valid

I think this is a problem that comes up not only with Iced but any library that uses this pattern where you create an object.and().configure().it().like().this(). I don’t know the exact name of this pattern… is it builder? factory? Their descriptions on Wikipedia don’t really match with what I describe.

Your proposal, though, isn’t general enough and I think it would cause more trouble than relief. What if I want to bind different messages to the event depending on some condition? Your solution only considers binding a message or no message, so it already falls short.

I would just try to take advantage of Rust’s syntax to express what you want more succinctly. I do it like this:

let mut my_button = Button::new("Foo");

if self.state == SomeStateType::Ready {
    my_button = my_button.on_input(Message::SomeMessage);
}

return row![my_button];