Converting my existing code into using the Elm architecture

I’ve been having a good conversation about Iced pros/cons in this thread and so decided to try converting one of my side projects into using Iced instead of FLTK.rs. And, of course, got confused right from the get-go. Don’t get me wrong – I think learning how to use the Elm architecture is going to improve my programming skills, so I’m not complaining. I’m just having trouble getting started. Here’s my question:

In all or most of my various projects I try to keep main.rs fairly simple and divide up my lib.rs file into several modules. Each module has it’s own set of structs that, at least in my mind, correspond to Iced’s State segment of the State-Message-View-Update (SMVU) architecture. So, how do I fit my existing code into the SMVU framework? This is really, really important for when (if) I decide to convert my main project (1000’s of lines) over into Iced. Thoughts anyone?

You could take a look at GitHub - airstrike/iced_receipts: An iced example showcasing clean screen management, unified event handling, and keyboard-navigable forms for an example on how you structure your app, breaking things up into multiple pieces

1 Like

Thanks for the shoutout to iced_receipts!

I’d also say that the very first concept @jtreagan should take a look at is how we use .map() to compose views (Elements, really) and Tasks.

Make sure to read the official pocket guide too, particularly the “Scaling Applications” section:

Thanks for your replies. I did take a look at @airstrike ‘s iced_receipts and have been looking through the documentation on docs.rs. I find I’m still confused and am wondering if the documentation’s statement that “iced is easy to learn for advanced Rust programmers” simply doesn’t apply to me. I certainly am not an “advanced” Rust programmer and that is probably why, when I look at examples like iced_receipts or the examples in the repository, I still am struggling to see Elm’s SMVU structure working in the code. I’ve never been good at learning by looking at examples and that weakness is likely in play now. I’m wondering if I should take @hecrj’s advice in the documentation and “wait patiently until the book is finished.” (Note: I really like what Hector has done in the book so far and am looking forward to seeing it finished.)

That said I would like to give it one more try. So, in an attempt to simplify the problem as much as possible, I attempted to create a single window that did nothing and contained nothing. That might be too basic and I didn’t succeed. My AI kept messing up, too, so I gave up on that tactic. So, instead of that tactic I pulled up my just-for-fun side project of creating a solitaire game. If I can convert that project over to Iced then I will have made some progress. The simplest task is to create and display a single card using an *.svg image file. (Keep in mind that I’m currently using FLTK.rs.)

Here’s the struct I use for a basic card:

#[derive(Debug, Clone)]
pub struct Card {
    pub front: SvgImage,
    pub back_svg: SvgImage,
    pub back_png: PngImage,
    pub value: String,
    pub suit: String,
    pub color: String,
}

The types SvgImage & PngImage come from FLTK and, of course, I will need to find equivalents in Iced. Anyway, am I correct in saying that this struct should be considered my State in the SMVU architecture?

It is. You’re looking for iced::widget::{image, svg}::Handle. You’ll also want to enable the svg and image feature flags.

Just so you know, it’s okay if you don’t want to baby me along on this. I’ll be fine waiting for a better tutorial to come out.

Anyway, I found this example in iced::widget::image but I’m not sure how to implement it. Want to show me how?

use iced::widget::image;

enum Message {
    // ...
}

fn view(state: &State) -> Element<'_, Message> {
    image("ferris.png").into()
}

Check out the pokedex example. I suggest cloning iced locally and running cargo run -p example -r

It may be years before that tutorial exists, so we’re be happy to help in the meantime.

And since you mentioned AI, I suggest feeding your AI a few examples from the repo to ground its answers. Either feed it manually or tell Claude Code/Codex etc to peruse the examples and stick to the API they demonstrate