My feeling is that your app-state atom should contain everything that would be 
saved into a document if your user did a File->Save in a conventional desktop 
application. Given that, it wouldn't seem appropriate to put things like 
channels or flags for tracking mouse/hover state and that sort of thing into 
the app-state atom. I feel that that sort of thing should live in component 
local state.
I agree that things get a bit trickier in the case you outlined with the 
'current-cat' example. You can pass multiple cursors to a component 
(https://github.com/swannodette/om/wiki/Cursors), so the cat-viewer component 
could rely on two cursors: one cursor to the list of kitties, and another to 
the :cat-viewer-widget entry which would allow it to transact! directly on the 
app state and set the current cat itself.

An alternative approach is to have the cat-viewer-widget just pass an event on 
a channel when someone selects a cat. A parent component would then be 
responsible for pulling this event off the channel and transacting! on the app 
state to set the current cat.

In my project, I have the exact same situation, except I'm displaying and 
selecting colors instead of cats 
(https://github.com/jackschaedler/goya/blob/master/src/cljs/goya/appstate.cljs 
See :palette and :paint-color). I've decided to go with the second option, 
creating a parent component which has a cursor to basically the entire 
application state (which is less than ideal), and this component builds a child 
component whose job is to render the list of colors and pass any 
clicks/selections on those colors to the parent component via an async channel:

https://github.com/jackschaedler/goya/blob/master/src/cljs/goya/components/palette.cljs#L18

The parent component is then responsible for transacting! on the app-state - 
It's acting sort of like a controller for all child components, waiting for 
children to send events or requests over the channels it created in its 
component local state.

As for the 'should you transact! or let someone else do it for you' question, I 
think that just needs to be worked out on a case by case basis. I've mixed and 
matched a bit, and I don't see any benefit to letting another component 
transact! on your behalf if you can do it via your own cursor 
(https://github.com/jackschaedler/goya/blob/master/src/cljs/goya/components/canvastools.cljs#L26)

Those are my very un-informed two cents coming from a complete beginner :) 
Hopefully that's somehow helpful!




On Friday, May 2, 2014 7:32:40 AM UTC+2, Elliot Block wrote:
> There seems to be a few types of shared state in an Om system:
> 
> 1. "model"-ish data, e.g. if your app's about cats, a list of cats.
> 2. "view"-ish data, like whether a given UI panel is shown or hidden
> 3. coordination-ish data, like async channels so that components can talk to 
> each other, e.g. to show or hide panels, to switch the cat being displayed.
> 
> Which one or more of these is supposed to go in the global app-state atom?
> 
> Suppose that you put both model and view state in the app-state atom:
> 
> (def app-state
>   (atom {:cats {"Fluffy" {:age 7}
>                 "Scratchy" {:age 5}}
>          :cat-viewer-widget {:current-cat "Fluffy"}}))
> 
> How do you provide a cursor to the cat viewer widget without giving it a 
> completely global cursor, or without hopelessly intermixing the model and 
> view data?
> 
> Alternatively, suppose that only the "model" data lives in `app-state` atom.  
> Presumably then the view state is component-local, but then that just implies 
> you need a globally addressable async channel to talk to it.  Where does one 
> put the async channels so that other components can talk to them?  Options 
> include:
> 
> - Include channels in `app-state` atom
> - :shared global component state
> - Some other var in scope in the namespace
> 
> (This also raises the question of, when you should prefer to om/transact! 
> directly vs. use a channel to ask some other process to transact! for you?  
> But I'll leave that one for now.)
> 
> Haven't been able to find a write-up on this in the past few days.  Any 
> guidance greatly appreciated.  Thank you!
> 
> - Elliot

-- 
Note that posts from new members are moderated - please be patient with your 
first post.
--- 
You received this message because you are subscribed to the Google Groups 
"ClojureScript" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
Visit this group at http://groups.google.com/group/clojurescript.

Reply via email to