changeset 43:7d67064f0880

More layers.
author Mikhail Kryshen <mikhail@kryshen.net>
date Mon, 12 Jul 2010 03:52:21 +0400
parents d3e3c43df1cd
children 064b21604f74
files src/kryshen/indyvon/core.clj src/kryshen/indyvon/graph.clj src/kryshen/indyvon/layers.clj
diffstat 3 files changed, 81 insertions(+), 23 deletions(-) [+]
line wrap: on
line diff
--- a/src/kryshen/indyvon/core.clj	Sun Jul 11 06:34:36 2010 +0400
+++ b/src/kryshen/indyvon/core.clj	Mon Jul 12 03:52:21 2010 +0400
@@ -18,10 +18,11 @@
 (def *update*)
 (def *event-dispatcher*)
 
-(defrecord Theme [fore-color back-color border-color font])
+(defrecord Theme [fore-color back-color alt-back-color border-color font])
 
 (defn default-theme []
-  (Theme. Color/BLACK Color/WHITE Color/BLUE (Font. "Sans" Font/PLAIN 12)))
+  (Theme. Color/BLACK Color/LIGHT_GRAY Color/WHITE
+          Color/BLUE (Font. "Sans" Font/PLAIN 12)))
 
 (def *theme* (default-theme))
 
@@ -135,6 +136,21 @@
                           specs)
      (fn [] ~form)))
 
+(defn with-theme* [theme f & args]
+  (apply with-bindings* {#'*theme* (merge *theme* theme)}
+         f args))
+
+(defmacro with-theme [theme & body]
+  `(with-theme* ~theme (fn [] ~@body)))
+
+(defmacro with-color [color & body]
+  `(let [color# (.getColor *graphics*)]
+     (try
+       (.setColor *graphics* ~color)
+       ~@body
+       (finally
+        (.setColor *graphics* color#)))))
+
 (defn- geometry-vec [geometry]
   (if (vector? geometry)
     geometry
--- a/src/kryshen/indyvon/graph.clj	Sun Jul 11 06:34:36 2010 +0400
+++ b/src/kryshen/indyvon/graph.clj	Mon Jul 12 03:52:21 2010 +0400
@@ -62,7 +62,7 @@
                (let [dx (- x @fix-x)
                      dy (- y @fix-y)]
                  (.layoutLocation v (+ vx dx) (+ vy dy))
-                 (.updateBounds layout)
+                 (.invalidateLayout layout)
                  (*update*)
                  (ref-set fix-x x)
                  (ref-set fix-y y)))))))))))
--- a/src/kryshen/indyvon/layers.clj	Sun Jul 11 06:34:36 2010 +0400
+++ b/src/kryshen/indyvon/layers.clj	Mon Jul 12 03:52:21 2010 +0400
@@ -24,6 +24,32 @@
 (defmacro align-y [inner outer align]
   `(align-xy ~inner ~outer ~align :top :center :bottom))
 
+(defmacro decorate-layer [layer & render-tail]
+  `(reify
+    Layer
+    (render! ~@render-tail)
+    (layer-size [t#] (layer-size ~layer))
+    Anchored
+    (anchor [t# xa# ya#] (anchor ~layer xa# ya#))))
+
+(defn padding
+  ([content pad]
+     (padding content pad pad pad pad))
+  ([content top left bottom right]
+     (if (== 0 top left bottom right)
+       content
+       (reify
+        Layer
+        (render! [l]
+           (draw! content
+                  left top
+                  (- (:width *bounds*) left right)
+                  (- (:height *bounds*) top bottom)))
+        (layer-size [l]
+           (let [s (layer-size content)]
+             (Size. (+ (:width s) left right)
+                    (+ (:height s) top bottom))))))))
+
 (defn border
   "Decorate layer with a border."
   ([content]
@@ -31,20 +57,26 @@
   ([content width]
      (border content width 0))
   ([content width gap]
-     (let [offset (+ width gap)]
-       (reify Layer
-        (render! [l]
-           (let [w (:width *bounds*)
-                 h (:height *bounds*)]
-             (.setColor *graphics* (:border-color *theme*))
+     (let [layer (padding content (+ width gap))]
+       (decorate-layer layer [_]
+         (let [w (:width *bounds*)
+               h (:height *bounds*)]
+           (with-color (:border-color *theme*)
              (doseq [i (range 0 width)]
-               (.drawRect *graphics* i i (- w 1 i i) (- h 1 i i)))
-             (draw! content
-                    offset offset (- w offset offset) (- h offset offset))))
-        (layer-size [l]
-           (let [s (layer-size content)]
-             (Size. (+ (:width s) offset offset)
-                    (+ (:height s) offset offset))))))))
+               (.drawRect *graphics* i i (- w 1 i i) (- h 1 i i))))
+           (render! layer))))))
+
+(defn panel
+  "Opaque layer using theme's alt-back-color."
+  ([content]
+     (panel content 0))
+  ([content gap]
+     (let [layer (padding content gap)]
+       (decorate-layer layer [_]
+         (with-color (:alt-back-color *theme*)
+           (.fillRect *graphics* 0 0
+                      (:width *bounds*) (:height *bounds*)))
+         (render! layer)))))
 
 (defn- re-split [^java.util.regex.Pattern re s]
   (seq (.split re s)))
@@ -126,16 +158,26 @@
           (*update*))))
      (layer-size [layer] (layer-size content))))))
 
-(defmacro decorate-layer [layer & render-tail]
-  `(reify
-    Layer
-    (render! ~@render-tail)
-    (layer-size [t#] (layer-size ~layer))
-    Anchored
-    (anchor [t# xa# ya#] (anchor ~layer xa# ya#))))
+;;
+;; Layer context decorators.
+;;
 
 (defmacro handler [layer & handlers]
   `(decorate-layer ~layer [t#]
       (with-handlers t#
         (render! ~layer)
         ~@handlers)))
+
+(defn theme [layer & map-or-keyvals]
+  (let [theme (if (== (count map-or-keyvals) 1)
+                map-or-keyvals
+                (apply array-map map-or-keyvals))]
+    (reify
+     Layer
+     (render! [t]
+        (with-theme* theme render! layer))
+     (layer-size [t]
+        (with-theme* theme layer-size layer))
+     Anchored
+     (anchor [t xa ya]
+        (with-theme* theme anchor layer xa ya)))))