评估`mousemove`上的foo,但仅限于`mousedown`

时间:2014-05-13 23:05:31

标签: clojure clojurescript

如何在鼠标停止并使用core / async移动时评估foo

虽然我试图学习核心/异步背后的概念,但我已经完成了ClojureScript 101 tutorial (但我怀疑这个问题适用于clojure)。

我创建了一个使用以下内容放置鼠标移动事件的通道:

;; helper to get a channel where a dom event type will be put
(defn listen [el type]
  (let [out (chan)]
     (events/listen el type
       (fn [e] (put! out e)))
    out))

;; create a channel for mouse moves, take the values 
;; and pass them to the console 
(let [moves (listen (dom/getElement "canvas") "mousemove")]
  (go (while true
    (foo (<! moves)))))  

这样可以在鼠标移动时评估foo。但是只有在鼠标停止时才能做到这一点?

我的第一个猜测是为mousedownmouseup使用一个原子和两个新通道。然后用鼠标状态更新atom并在go块中对此进行测试。但我怀疑由于使用原子这是错误的;因此问题。

1 个答案:

答案 0 :(得分:2)

回答我自己的问题,这是我最接近的问题。似乎工作。

;; Util for create DOM channels
(defn listen [el type]
  "Takes a DOM element and an event type. Returns a channel for the event"
  ;; out is a new channel
  (let [out (chan (sliding-buffer 1))]
    ;; attach an event listener
    (events/listen el type
      ;; the handler/callback of the listener takes the 
      ;; event and put! in on the channel. We are using 
      ;; put because we are not in a go block
      (fn [e] (put! out e)))
    ;; return the channel
    out))

(def canvas-el (dom/getElement "canvas"))

(def mouse-up   (listen canvas-el "mouseup"))
(def mouse-down (listen canvas-el "mousedown"))
(def mouse-move (listen canvas-el "mousemove"))

(go (while true
      (<! mouse-down)
      (loop []
        (let [[v ch] (alts! [mouse-move mouse-up])]
          (when (= ch mouse-move) 
            (do 
              (.log js/console "move" (.-clientX v) (.-clientY v))
              (recur)))))))