Link Search Menu Expand Document

Store

In fritz2, Stores are used to handle your app’s state. It heavily depends on Kotlin’s Flow - if you are not familiar with this concept, please take a look at Flows first.

Let’s assume the state of your app is a simple String. Creating a Store to manage that state is quite easy:

val s = storeOf("initial value")

Every Store offers a Flow named data which can be bound as part of your html:

render {
    p {
        s.data.bind()
    }
}.mount("target")

By calling s.data.bind() a MountPoint is created and collects your model values. This means a DOM-element is created (in this example it’s a simple TextNode) and bound to your data so that it will change whenever your Store’s state updates. This is called precise data binding.

You can of course use every intermediate action like map,filter, etc., on the data-flow as on every other Flow:

render {
    p {
        s.data.map { "you have entered ${it.length} characters so far." }.bind()
    }
}.mount("target")

To combine data from two or more stores you can use the combine method:

val firstName = object : RootStore<String>("Foo") {}
val lastName = object : RootStore<String>("Bar") {}

render {
    p {
        firstName.data.combine(lastName.data) { firstName, lastName ->
            "Your full name is: $firstName $lastName"
        }.bind()
    }
}.mount("target")

Of course, you can also use a RootStore<T> with a complex model which contains all data that you need in one place. Therefore, take a look at Nested Structures.

You can also bind a Flow to an attribute:

input {
    value = store.data
}

In this case, only the attribute value will change when the model in your store changes. fritz2 offers pre-defined properties (at each Tag) for every HTML5-attribute.

But how can you change the model-data in a store? Let’s have a look at State Management.


Table of contents


Distributed by an MIT license.