我对以下代码有几个问题:
(import
'(java.awt Color Graphics Dimension)
'(java.awt.image BufferedImage)
'(javax.swing JPanel JFrame))
(def width 900)
(def height 600)
(defn render
[g]
(let [img (new BufferedImage width height
(. BufferedImage TYPE_INT_ARGB))
bg (. img (getGraphics))]
(doto bg
(.setColor (. Color white))
(.fillRect 0 0 (. img (getWidth)) (. img (getHeight)))
(.setColor (. Color red))
(.drawOval 200 200 (rand-int 100) (rand-int 50)))
(. g (drawImage img 0 0 nil))
(. bg (dispose))
))
(def panel (doto (proxy [JPanel] []
(paint [g] (render g)))
(.setPreferredSize (new Dimension
width
height))))
(def frame (doto (new JFrame) (.add panel) .pack .show))
(def animator (agent nil))
(defn animation
[x]
(send-off *agent* #'animation)
(. panel (repaint))
(. Thread (sleep 100)))
(send-off animator animation)
Run Code Online (Sandbox Code Playgroud)
#'在发送动画之前使用?send-off动画功能开始工作?它不应该再次开始动画功能,永远不会执行重绘和睡眠方法吗?在编写动画功能时,与原版相比是否有任何不利之处:
(defn animation
[x]
(. panel (repaint))
(. Thread (sleep 100))
(send-off *agent* animation))
Run Code Online (Sandbox Code Playgroud)在动画功能中 - 为什么在发送动画之前使用#'?
展示Clojure的动态性.
表单#'animation是Var,Clojure的可变引用类型之一.该defn宏创建一个无功.为方便起见,调用引用函数的Var与调用函数本身相同.但是,与功能不同,Var可以改变!我们可以#'animation在Clojure REPL 重新定义并立即看到效果.
使用(send-off *agent* #'animation)力Clojure #'animation每次都可以查找Var 的当前值.如果代码已经使用了(send-off *agent* animation),那么Clojure只会查找一次值,并且不能在不停止循环的情况下更改动画功能.