X-Git-Url: https://www.chiark.greenend.org.uk/ucgi/~mdw/git/clg/blobdiff_plain/e3f606ca05d30b62fabf06158ebbcb7501e4ef0d..72d9260f8258b525339c7241da0631ceaf9f3842:/rsvg/rsvg.lisp diff --git a/rsvg/rsvg.lisp b/rsvg/rsvg.lisp index 466e9e5..a6da95c 100644 --- a/rsvg/rsvg.lisp +++ b/rsvg/rsvg.lisp @@ -20,18 +20,16 @@ ;; TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE ;; SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -;; $Id: rsvg.lisp,v 1.4 2006-02-13 20:10:48 espen Exp $ +;; $Id: rsvg.lisp,v 1.9 2008-10-08 18:24:01 espen Exp $ (in-package "RSVG") (eval-when (:compile-toplevel :load-toplevel :execute) - (init-types-in-library - #.(concatenate 'string (pkg-config:pkg-variable "librsvg-2.0" "libdir") - "/librsvg-2.so") :prefix "rsvg_") + (init-types-in-library rsvg "librsvg-2" :prefix "rsvg_") -(define-types-by-introspection "Rsvg" - ("RsvgError" :ignore t))) + (define-types-by-introspection "Rsvg" + ("RsvgError" :ignore t))) (defbinding init () nil) @@ -44,8 +42,8 @@ (defbinding (set-default-dpi "rsvg_set_default_dpi_x_y") (dpi-x &optional (dpi-y (defbinding handle-write () boolean (handle handle) - (data string) - ((length data) int) ; TODO: compute propper length of utf8 string + (data (vector (integer 8))) + ((length data) int) (nil gerror-signal :out)) (defbinding handle-close () boolean @@ -59,7 +57,7 @@ (defbinding (handle-get-pixbuf "rsvg_handle_get_pixbuf_sub") (handle &optional i (defbinding %handle-new-from-data () pointer (data string) - ((length data) int) ; TODO: compute propper length of utf8 string + ((1- (utf8-length data)) int) (nil gerror-signal :out)) (defbinding %handle-new-from-file () pointer @@ -72,6 +70,11 @@ (defmethod allocate-foreign ((handle handle) &key data filename) (data (%handle-new-from-data data)) (t (call-next-method)))) +(defmacro with-handle ((handle &rest args) &body body) + `(let ((,handle (make-instance 'handle ,@args))) + (unwind-protect + (progn ,@body) + (handle-close ,handle)))) ;;; Cairo interface @@ -79,3 +82,22 @@ (defbinding (render-cairo "rsvg_handle_render_cairo_sub") (handle cr &optional i (handle handle) (cr cairo:context) (id (or null string))) + +(defun image-surface-create-from-svg (filename &key width height (format :argb32)id) + (with-handle (handle :filename filename) + (multiple-value-bind (width height) + (cond + ((and width height) (values width height)) + (width + (let ((ratio (/ (handle-height handle) (handle-width handle)))) + (values width (truncate (* width ratio))))) + (height + (let ((ratio (/ (handle-width handle) (handle-height handle)))) + (values (truncate (* height ratio)) height))) + (t (values (handle-width handle) (handle-height handle)))) + (let ((image (make-instance 'cairo:image-surface + :width width :height height :format format))) + (cairo:with-surface (image cr) + (cairo:scale cr (/ width (handle-width handle)) (/ height (handle-height handle))) + (render-cairo handle cr id)) + image))))