Without diving too much into your code, I don't see why you can't just have a channel that communicates bound changes which you save via om.core/set-state!.
David On Mon, Jan 13, 2014 at 4:14 PM, David Pidcock <[email protected]> wrote: > > Let me add that, profiling this in Chrome has shown a steady growth of > the number of ManyToManyChannel objects when I do a lot of resizing, but > Garbage collection does clean them up nicely. > > On Monday, January 13, 2014 1:10:15 PM UTC-8, David Pidcock wrote: > > I've been playing around with Om recently, and started down a rabbithole > towards a drag-drop implementation. > > > > In my (toy) application, I have a couple of lists of items which I want > to drag between. Before stumbling on Om and React, I was using a > goog.fx.DragListGroup, and listening to the events. But binding data back > to sub-components of the app was starting to look onerous. > > > > Om to the rescue! > > > > The lists are in app-state and mutations on them cascade nicely to the > sub-components. Great. > > > > So my first thought was to try to integrate DragListGroup somehow (after > all - that code is already written). Unfortunately, React doesn't like DOM > manipulation outside it's lifecycle (it's possible, but much harder to do > in idiomatic Om). > > > > Fortunately, David Nolen threw a sortable example together. > > > > Building on that example, I now have my "master app" component creating > some core.async channels, which it then passes down to sub-components. > These components can register for drag-events within their visible bounds. > > > > So here's my problem : when the bounds of a component change (i.e. it > get's re-sized), the existing channel still only delivers events to the old > bounds. > > > > I 'solved' this by untapping the old channel, creating a new channel > with a filter for the new bounds and listening to it. > > > > This seems .. unwieldy. > > > > ; state is either current or previous state , depending on whether this > > ; is called from did-update or did-mount. > > > > (defn listen-bounds [owner state opts ref-node] > > (when-let [container (om/get-node owner ref-node)] > > (let [ dims (-> container gstyle/getSize gsize->vec) > > disperser (disperser opts) > > drag-chan (:drag-target-chan state) > > new-bounds (bounds container) > > track-fn (fn [evt] (om/set-state! owner :last-evt evt)) > > ] > > (if (= (:bounds state) new-bounds) > > (do > > (if (nil? drag-chan) > > (create-listener disperser new-bounds track-fn) > > drag-chan) > > ) > > (do > > (when-not (nil? drag-chan) > > (untap disperser drag-chan) > > (close! drag-chan)) > > > > (om/set-state! owner :bounds new-bounds) > > (let [new-drag-chan (create-listener disperser new-bounds > track-fn)] > > (om/set-state! owner :drag-target-chan new-drag-chan) > > new-drag-chan) > > ))))) > > > > > > > > (defn directed-event-chan [bounds] > > (filter> > > (bound-filter bounds) > > (chan))) > > > > (defn create-listener [disperser bounds f] > > (let [drag-target-chan (directed-event-chan bounds)] > > (tap disperser drag-target-chan) > > (go (while > > (when-let [event (<! drag-target-chan)] > > (f event) > > event > > ))) > > drag-target-chan > > )) > > > > > > So two questions : > > 1. I couldn't tell if untapping a channel also effectively closes it. > Is (close! ..) necessary here? > > 2. Is there some way to avoid this churn? Would using an atom in > (directed-event-chan [@bounds] get me a dynamic filter? > > > > > > As an aside : A lot of the core-async tutorials use (go (while true ... > > I haven't gotten into the implementation, but if all channels in a go > loop are closed, is that code still taking up memory somewhere? > > > > I erred on the safe side (perhaps at the expense of readability) by using > > (go (while (when-let ... ) and returning the value of the last read > from the channel. When the channel returns nil upon close, this is > guaranteed to exit. > > -- > 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. > -- 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.
