view src/indyvon/core.clj @ 2:0f2a98f71a9c

Beginnings of event dispatching code.
author Mikhail Kryshen <mikhail@kryshen.net>
date Mon, 07 Jun 2010 21:13:05 +0400
parents a93cfcf60f27
children 6bc931b1b755
line source
1 (ns indyvon.core
2 (:import (java.awt Dimension Point Component Graphics2D AWTEvent)))
4 (def ^{:private true} *rx* 0)
5 (def ^{:private true} *ry* 0)
7 (def *graphics*)
9 (def *width*)
10 (def *height*)
12 (def *lag*)
14 (def *update-fn*)
16 (defprotocol Layer
17 (render! [this])
18 (size [this])
19 (anchor [this]))
21 (defmacro reify-layer [& fns]
22 (let [method-map {'size [['_] [0 0]]
23 'anchor [['_] [0 0]]}
24 method-map (loop [fns fns
25 mm method-map]
26 (if-let [form (first fns)]
27 (recur (next fns)
28 (conj mm [(first form) (next form)]))
29 mm))
30 methods (for [m method-map]
31 (cons (first m) (second m)))]
32 `(reify Layer ~@methods)))
34 (defn- make-graphics [g x y w h clip]
35 (if clip
36 (.create g x y w h)
37 (doto (.create g)
38 (.translate x y))))
40 (defn render-layer!
41 "Render layer in a new graphics context."
42 ([layer]
43 (render-layer! layer 0 0 *width* *height*))
44 ([layer x y]
45 (render-layer! layer x y true))
46 ([layer x y clip]
47 (let [s (size layer)]
48 (render-layer! layer x y (.width s) (.height s) clip)))
49 ([layer x y w h]
50 (render-layer! layer x y w h true))
51 ([layer x y w h clip]
52 (binding [*graphics* (make-graphics *graphics* x y w h clip)
53 *rx* (+ *rx* x)
54 *ry* (+ *ry* y)
55 *width* w
56 *height* h]
57 (render! layer))))
59 ;;
60 ;; Event handling
61 ;;
63 (defprotocol EventDispatcher
64 (register [this layer])
65 (commit [this])
66 (dispatch [this event]))
68 (defrecord LayerContext [layer rx ry width height update-fn])
70 (defn make-event-dispatcher []
71 (let [contexts-r (ref [])
72 contexts-d (ref [])]
73 (reify
74 EventDispatcher
75 (register [this layer]
76 (dosync
77 (alter contexts-r conj
78 (LayerContext. layer *rx* *ry*
79 *width* *height*
80 *update-fn*))))
81 (commit [this]
82 (dosync (ref-set contexts-d @contexts-r)
83 (ref-set contexts-r [])))
84 (dispatch [this event]
85 ;; TODO
86 ))))
88 ;;
89 ;; Connection to AWT.
90 ;;
92 (defn- make-update-fn [component]
93 (fn [] (.repaint component)))
95 ;; (defn make-component [layer]
96 ;; (proxy [Component] []
97 ;; (update [g] (.paint this g))
98 ;; (paint [g]
99 ;; (let [insets (.getInsets this)
100 ;; top (.top insets)
101 ;; left (.left insets)
102 ;; bottom (.bottom insets)
103 ;; right (.right insets)
104 ;; size (.getSize this)
105 ;; width (- (.width size) left right)
106 ;; height (- (.height size) top bottom)]
107 ;; (binding [*graphics* g
108 ;; *update-fn* (make-update-fn this)]
109 ;; (render-layer! layer top left width height false))))
110 ;; (getPreferredSize []
111 ;; (size layer))))
113 (defn make-component [layer]
114 (proxy [Component] []
115 (update [g] (.paint this g))
116 (paint [g]
117 (let [size (.getSize this)
118 width (.width size)
119 height (.height size)]
120 (binding [*graphics* g
121 *update-fn* (make-update-fn this)]
122 (render-layer! layer 0 0 width height false))))
123 (getPreferredSize []
124 (let [s (size layer)]
125 (Dimension. (s 0) (s 1))))))
127 (comment
128 (do
129 (def frame (java.awt.Frame. "Test"))
130 (def layer
131 (reify-layer
132 (render! [this]
133 (.fillRect *graphics* 10 10 40 40))
134 (size [this] [100 100])))
135 (doto frame
136 (.addWindowListener
137 (proxy [java.awt.event.WindowAdapter] []
138 (windowClosing [event] (.dispose frame))))
139 (.add (make-component layer))
140 (.pack)
141 (.setVisible true))
142 )