1 ;;; Copyright (c) 2007 Zachary Beane, All Rights Reserved
3 ;;; Redistribution and use in source and binary forms, with or without
4 ;;; modification, are permitted provided that the following conditions
7 ;;; * Redistributions of source code must retain the above copyright
8 ;;; notice, this list of conditions and the following disclaimer.
10 ;;; * Redistributions in binary form must reproduce the above
11 ;;; copyright notice, this list of conditions and the following
12 ;;; disclaimer in the documentation and/or other materials
13 ;;; provided with the distribution.
15 ;;; THIS SOFTWARE IS PROVIDED BY THE AUTHOR 'AS IS' AND ANY EXPRESSED
16 ;;; OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
17 ;;; WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18 ;;; ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
19 ;;; DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20 ;;; DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
21 ;;; GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
22 ;;; INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
23 ;;; WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
24 ;;; NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 ;;; SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 ;;; $Id: graphics-state.lisp,v 1.15 2007/10/01 02:24:44 xach Exp $
31 (defconstant +png-channels
+ 4)
32 (defconstant +png-color-type
+ :truecolor-alpha
)
33 (defvar *default-character-spacing
* 1.0d0
)
35 (defclass graphics-state
()
52 :initarg
:stroke-color
53 :accessor stroke-color
)
59 :accessor dash-vector
)
68 :accessor fill-source
)
77 :accessor blend-style
)
79 :initarg
:transform-matrix
80 :accessor transform-matrix
)
82 :initarg
:clipping-path
83 :accessor clipping-path
)
85 :initarg
:after-paint-fun
86 :accessor after-paint-fun
)
88 :initarg
:font-loaders
89 :accessor font-loaders
)
94 :initarg
:character-spacing
95 :accessor character-spacing
))
99 :stroke-color
(make-instance 'rgba-color
)
103 :fill-color
(make-instance 'rgba-color
)
108 :transform-matrix
(scaling-matrix 1.0 -
1.0)
109 :after-paint-fun
(constantly nil
)
110 :font-loaders
(make-hash-table :test
'equal
)
112 :character-spacing
*default-character-spacing
*))
114 (defgeneric image-data
(state)
116 (zpng:image-data
(image state
))))
118 (defgeneric transform-function
(state)
119 (:documentation
"Return a function that takes x, y coordinates
120 and returns them transformed by STATE's current transformation
121 matrix as multiple values.")
123 (make-transform-function (transform-matrix state
))))
126 (defgeneric call-after-painting
(state fun
)
128 "Call FUN after painting, and reset the post-painting fun to a no-op.")
130 (setf (after-paint-fun state
)
133 (setf (after-paint-fun state
) (constantly nil
))))))
135 (defgeneric after-painting
(state)
136 (:documentation
"Invoke the post-painting function.")
138 (funcall (after-paint-fun state
))))
141 (defgeneric apply-matrix
(state matrix
)
142 (:documentation
"Replace the current transform matrix of STATE
143 with the result of premultiplying it with MATRIX.")
144 (:method
(state matrix
)
145 (let ((old (transform-matrix state
)))
146 (setf (transform-matrix state
) (mult matrix old
)))))
148 (defgeneric clear-paths
(state)
149 (:documentation
"Clear out any paths in STATE.")
151 (setf (paths state
) nil
153 (after-paint-fun state
) (constantly nil
))))
155 (defmethod (setf paths
) :after
(new-value (state graphics-state
))
156 (setf (path state
) (first new-value
)))
158 (defun state-image (state width height
)
159 "Set the backing image of the graphics state to an image of the
160 specified dimensions."
162 (make-instance 'zpng
:png
165 :color-type
+png-color-type
+)
167 (height state
) height
168 (clipping-path state
) (make-clipping-path width height
))
169 (apply-matrix state
(translation-matrix 0 (- height
))))
172 (defun find-font-loader (state file
)
173 (let* ((cache (font-loaders state
))
174 (key (namestring (truename file
))))
175 (or (gethash key cache
)
176 (setf (gethash key cache
) (zpb-ttf:open-font-loader file
)))))
178 (defgeneric close-font-loaders
(state)
179 (:documentation
"Close any font loaders that were obtained with GET-FONT.")
181 (maphash (lambda (filename loader
)
182 (declare (ignore filename
))
183 (ignore-errors (zpb-ttf:close-font-loader loader
)))
184 (font-loaders state
))))
186 (defgeneric clear-state
(state)
187 (:documentation
"Clean up any state in STATE.")
188 (:method
((state graphics-state
))
189 (close-font-loaders state
)))
191 (defun clear-fill-source (state)
192 (setf (fill-source state
) nil
))
194 (defmethod copy ((state graphics-state
))
195 (make-instance 'graphics-state
198 :height
(height state
)
201 :stroke-color
(copy (stroke-color state
))
202 :line-width
(line-width state
)
203 :dash-vector
(copy-seq (dash-vector state
))
204 :dash-phase
(dash-phase state
)
205 :fill-color
(copy (fill-color state
))
206 :fill-source
(fill-source state
)
207 :join-style
(join-style state
)
208 :cap-style
(cap-style state
)
209 :transform-matrix
(copy-seq (transform-matrix state
))
210 :clipping-path
(copy (clipping-path state
))
211 :after-paint-fun
(after-paint-fun state
)
212 :font-loaders
(font-loaders state
)
214 :character-spacing
(character-spacing state
)))