:qt and :qt-impl packages to prevent collision with :cl symbols and fix object with non smoke parent.
Annotate for file src/variant.lisp
2009-06-11 tobias 1 (in-package :cl-smoke.qt-impl)
2010-01-10 tobias 2
2009-06-11 tobias 3 (defmethod print-object ((variant qt:variant) stream)
2010-01-10 tobias 4 "Print the type and value of the variant."
08:52:49 ' 5 (if (or (not (slot-boundp variant 'pointer))
' 6 (null-pointer-p (pointer variant)))
' 7 (call-next-method)
' 8 (print-unreadable-object (variant stream :type t :identity t)
' 9 (format stream "~A~@[ ~S~]"
' 10 (cxx:type-name variant)
2009-06-11 tobias 11 (handler-case (qt:from-variant variant)
2010-01-10 tobias 12 (error () nil))))))
08:52:49 ' 13
2009-06-11 tobias 14 (defun qt:make-variant (&optional (value nil value-p))
2010-01-10 tobias 15 "Returns a new VARIANT containing a C++ version of VALUE
08:52:49 ' 16 or an empty variant when VALUE is not specified."
' 17 (if value-p
2009-06-11 tobias 18 (make-instance 'qt:variant :args (list value))
14:59:48 ' 19 (make-instance 'qt:variant)))
2010-01-10 tobias 20
2009-06-11 tobias 21 (defun qt:make-char (character)
2010-01-10 tobias 22 "Returns a char for a lisp CHARACTER."
08:52:49 ' 23 (let ((octets (babel:string-to-octets (string character))))
' 24 (case (length octets)
2009-06-11 tobias 25 (1 (make-instance 'qt:char :args (list (aref octets 0))))
14:59:48 ' 26 (2 (make-instance 'qt:char :args (list (aref octets 0)
2009-07-22 tobias 27 (aref octets 1))))
2010-01-10 tobias 28 (t (error "qt:char requires the character ~A to be encoded
08:52:49 ' 29 in one or two octets, but it is using ~A."
' 30 character (length octets))))))
' 31
' 32 (defun surrogate-p (char)
' 33 (or (cxx:is-high-surrogate char)
' 34 (cxx:is-low-surrogate char)))
' 35
2009-06-11 tobias 36 (defun qt:from-char (char)
2009-07-22 tobias 37 "Returns the lisp character represented by CHAR."
2010-01-10 tobias 38 (assert (not (surrogate-p char))
08:52:49 ' 39 (char)
' 40 "The char ~A is part of a surrogate.")
' 41 (char
' 42 (babel:octets-to-string (make-array 2 :element-type '(unsigned-byte 8)
' 43 :initial-contents
' 44 (list
' 45 (char-code (cxx:cell char))
' 46 (char-code (cxx:row char)))))
' 47 0))
' 48
2009-06-11 tobias 49 (defmethod print-object ((char qt:char) stream)
2010-01-10 tobias 50 (if (or (null-pointer-p (pointer char))
08:52:49 ' 51 (surrogate-p char))
' 52 (call-next-method)
' 53 (print-unreadable-object (char stream :type t)
2009-06-11 tobias 54 (princ (qt:from-char char) stream))))
2010-01-10 tobias 55
08:52:49 ' 56
2009-07-22 tobias 57 ;; FIXME include in MAKE-VARIANT?
2009-06-11 tobias 58 (defun qt:make-lisp-variant (value)
2010-01-10 tobias 59 "Returns a new VARIANT that wraps VALUE.
08:52:49 ' 60
2009-07-22 tobias 61 The variant contains the actual Lisp object
2010-01-10 tobias 62 and not its C++ value like in MAKE-VARIANT."
08:52:49 ' 63 (let ((object (make-cxx-lisp-object value)))
' 64 (unwind-protect
2009-06-11 tobias 65 (make-instance 'qt:variant :args (list *cxx-lisp-object-metatype*
14:59:48 ' 66 object))
2010-01-10 tobias 67 (free-cxx-lisp-object object))))
08:52:49 ' 68
' 69 (defcfun qt-smoke-lisp-object-value :pointer
' 70 (variant :pointer))
' 71
2009-06-11 tobias 72 (defun qt:variant-boundp (variant)
2010-01-10 tobias 73 "Returns true when VARIANT is valid (has a value) and false otherwise."
08:52:49 ' 74 (cxx:is-valid variant))
' 75
' 76 (defmacro variant-conversions ((variant) &body types)
' 77 `(ecase (cxx:user-type ,variant)
' 78
' 79 ,@(loop for type in types collect
' 80 (if (symbolp type)
2009-06-11 tobias 81 `(,(value (symbol-value
14:59:48 ' 82 (let ((*package* (find-package :cl-smoke.qt)))
' 83 (alexandria:symbolicate 'variant.+ type '+))))
2010-01-10 tobias 84 (,(intern (format nil "TO-~A" type) :cxx) ,variant))
08:52:49 ' 85 type))))
' 86
2009-06-11 tobias 87 (defun qt:from-variant (variant)
2010-01-10 tobias 88 "Returns the value of VARIANT."
08:52:49 ' 89 (variant-conversions (variant)
2009-06-11 tobias 90 (#.(value qt:variant.+invalid+)
2010-01-10 tobias 91 (cerror "Return (VALUES)" "Type of variant ~A is invalid." variant)
08:52:49 ' 92 (values))
' 93 bit-array bool byte-array
' 94 char
' 95 date date-time double
' 96 int
' 97 line line-f list locale long-long
' 98 point point-f
' 99 rect rect-f reg-exp
' 100 size size-f string string-list
' 101 time
' 102 uint
' 103 ulong-long
' 104 url
' 105 (#.*cxx-lisp-object-metatype*
' 106 (let* ((lisp-object (qt-smoke-lisp-object-value (smoke::pointer variant)))
' 107 (value))
' 108 (setf value (translate-cxx-lisp-object lisp-object))
' 109 (free-cxx-lisp-object lisp-object)
' 110 value))))
' 111
2009-06-11 tobias 112 (defmethod qt:value ((variant qt:variant))
2010-01-10 tobias 113 "Returns the value of VARIANT."
2009-06-11 tobias 114 (qt:from-variant variant))
2010-01-10 tobias 115
2009-06-11 tobias 116 (defmethod (setf qt:value) (new-value (variant qt:variant))
14:59:48 ' 117 (cxx:operator= variant (qt:make-variant new-value))
2010-01-10 tobias 118 new-value)