EQL5/examples/M-modules/quick/table-view/source-model.lisp

59 lines
2.1 KiB
Common Lisp

;;; source model for table view
(provide :source-model)
(defvar *books* (make-array 0 :fill-pointer t :adjustable t))
(defvar *book-model* nil)
(defmacro define-roles (start &rest roles)
(let ((n start))
`(progn
,@(mapcar (lambda (role) `(defconstant ,role ,(incf n))) roles))))
(define-roles #.|Qt.UserRole|
+title-role+
+author-role+)
(defstruct book
title
author)
(defvar *empty-model-index* (qnew "QModelIndex"))
(defun add-book (title author)
(|beginInsertRows| *book-model* *empty-model-index*
(|rowCount| *book-model*) (|rowCount| *book-model*))
(vector-push-extend (make-book :title title :author author)
*books*)
(|endInsertRows| *book-model*))
(defun variant (value)
(cond ((stringp value)
(qvariant-from-value value "QString"))))
(defvar *empty-variant* (qnew "QVariant"))
(defconstant +filter-role+ |Qt.DisplayRole|) ; see QSortFilterProxyModel
(defun make-book-model ()
(setf *book-model* (qnew "QAbstractListModel"))
(qoverride *book-model* "rowCount(QModelIndex)"
(lambda (index) (length *books*)))
(qoverride *book-model* "data(QModelIndex,int)" ; QOVERRIDE return value is GC'd
(lambda (index role)
(let* ((row (|row| index))
(data (when (< -1 row (length *books*))
(let ((book (aref *books* row)))
(case role
(#.+filter-role+ ; provide string for search
(variant (x:join (list (book-title book) (book-author book)) " ")))
(#.+title-role+
(variant (book-title book)))
(#.+author-role+
(variant (book-author book))))))))
(or data
*empty-variant*))))
(qoverride *book-model* "roleNames()"
(lambda ()
(list (cons +title-role+ "title")
(cons +author-role+ "author")))))