X-Git-Url: http://repo.macrolet.net/gitweb/?a=blobdiff_plain;f=glib%2Fgobject.foreign-closures.lisp;h=0b30da8228060dd4a11506b756856c2b75495f9b;hb=ddaa0292b675c0336e20dfcca1ce3c7dcfc8ccee;hp=bed6d45f1093c4ffa4bc5a555638f89b87ff7c11;hpb=0d03b82a77743d2ea5ef69bea08735fa12857d92;p=cl-gtk2.git diff --git a/glib/gobject.foreign-closures.lisp b/glib/gobject.foreign-closures.lisp index bed6d45..0b30da8 100644 --- a/glib/gobject.foreign-closures.lisp +++ b/glib/gobject.foreign-closures.lisp @@ -1,14 +1,15 @@ (in-package :gobject) -(defcstruct lisp-closure - (parent-instance g-closure) - (function-id :pointer)) - (defcallback lisp-closure-finalize :void ((data :pointer) (closure (:pointer lisp-closure))) (declare (ignore data)) (finalize-lisp-closure closure)) +(defun call-with-restarts (fn args) + (restart-case + (apply fn args) + (return-from-g-closure (&optional v) :report "Return value from closure" v))) + (defcallback lisp-closure-marshal :void ((closure (:pointer lisp-closure)) (return-value (:pointer g-value)) (count-of-args :uint) @@ -17,13 +18,13 @@ (marshal-data :pointer)) (declare (ignore invocation-hint marshal-data)) (let* ((args (parse-closure-arguments count-of-args args)) - (function-id (foreign-slot-value closure 'lisp-closure 'function-id)) + (function-id (foreign-slot-value closure 'lisp-closure :function-id)) (return-type (and (not (null-pointer-p return-value)) (gvalue-type return-value))) (fn (get-stable-pointer-value function-id)) - (fn-result (apply fn args))) + (fn-result (call-with-restarts fn args))) (when return-type - (set-g-value return-value fn-result return-type)))) + (set-g-value return-value fn-result return-type :g-value-init nil)))) (defun parse-closure-arguments (count-of-args args) (loop @@ -32,20 +33,30 @@ (defun create-closure (fn) (let ((function-id (allocate-stable-pointer fn)) - (closure (g-closure-new-simple (foreign-type-size 'lisp-closure) - (null-pointer)))) - (setf (foreign-slot-value closure 'lisp-closure 'function-id) function-id) + (closure (g-closure-new-simple (foreign-type-size 'lisp-closure) (null-pointer)))) + (setf (foreign-slot-value closure 'lisp-closure :function-id) function-id) (g-closure-add-finalize-notifier closure (null-pointer) (callback lisp-closure-finalize)) (g-closure-set-marshal closure (callback lisp-closure-marshal)) closure)) (defun g-signal-connect (object signal handler &key after) + "Deprecated alias for @fun{connect-signal}" + (connect-signal object signal handler :after after)) + +(defun connect-signal (object signal handler &key after) + "Connects the function to a signal for a particular object. +If @code{after} is true, then the function will be called after the default handler of the signal. + +@arg[object]{an instance of @class{gobject}} +@arg[signal]{a string; names the signal} +@arg[handler]{a function; handles the signal. Number (and type) of arguments and return value type depends on the signal} +@arg[after]{a boolean}" (g-signal-connect-closure (ensure-object-pointer object) signal (create-closure handler) after)) (defun finalize-lisp-closure (closure) - (let ((function-id (foreign-slot-value closure 'lisp-closure 'function-id))) + (let ((function-id (foreign-slot-value closure 'lisp-closure :function-id))) (free-stable-pointer function-id))) \ No newline at end of file