Function: org-list-struct-fix-box
org-list-struct-fix-box is a byte-compiled function defined in
org-list.el.gz.
Signature
(org-list-struct-fix-box STRUCT PARENTS PREVS &optional ORDERED)
Documentation
Verify and correct checkboxes in STRUCT.
PARENTS is the alist of parents and PREVS is the alist of
previous items, as returned by, respectively,
org-list-parents-alist and org-list-prevs-alist.
If ORDERED is non-nil, a checkbox can only be checked when every checkbox before it is checked too. If there was an attempt to break this rule, the function will return the blocking item. In all others cases, the return value will be nil.
This function modifies STRUCT.
Source Code
;; Defined in /usr/src/emacs/lisp/org/org-list.el.gz
(defun org-list-struct-fix-box (struct parents prevs &optional ordered)
"Verify and correct checkboxes in STRUCT.
PARENTS is the alist of parents and PREVS is the alist of
previous items, as returned by, respectively,
`org-list-parents-alist' and `org-list-prevs-alist'.
If ORDERED is non-nil, a checkbox can only be checked when every
checkbox before it is checked too. If there was an attempt to
break this rule, the function will return the blocking item. In
all others cases, the return value will be nil.
This function modifies STRUCT."
(let ((all-items (mapcar #'car struct))
(set-parent-box
(lambda (item)
(let* ((box-list
(mapcar (lambda (child)
(org-list-get-checkbox child struct))
(org-list-get-children item struct parents))))
(org-list-set-checkbox
item struct
(cond
((and (member "[ ]" box-list) (member "[X]" box-list)) "[-]")
((member "[-]" box-list) "[-]")
((member "[X]" box-list) "[X]")
((member "[ ]" box-list) "[ ]")
;; Parent has no boxed child: leave box as-is.
(t (org-list-get-checkbox item struct)))))))
parent-list)
;; 1. List all parents with a checkbox.
(mapc
(lambda (e)
(let* ((parent (org-list-get-parent e struct parents))
(parent-box-p (org-list-get-checkbox parent struct)))
(when (and parent-box-p (not (memq parent parent-list)))
(push parent parent-list))))
all-items)
;; 2. Sort those parents by decreasing indentation.
(setq parent-list (sort parent-list
(lambda (e1 e2)
(> (org-list-get-ind e1 struct)
(org-list-get-ind e2 struct)))))
;; 3. For each parent, get all children's checkboxes to determine
;; and set its checkbox accordingly.
(mapc set-parent-box parent-list)
;; 4. If ORDERED is set, see if we need to uncheck some boxes.
(when ordered
(let* ((box-list
(mapcar (lambda (e) (org-list-get-checkbox e struct)) all-items))
(after-unchecked (member "[ ]" box-list)))
;; There are boxes checked after an unchecked one: fix that.
(when (member "[X]" after-unchecked)
(let ((index (- (length struct) (length after-unchecked))))
(dolist (e (nthcdr index all-items))
(when (org-list-get-checkbox e struct)
(org-list-set-checkbox e struct "[ ]")))
;; Verify once again the structure, without ORDERED.
(org-list-struct-fix-box struct parents prevs nil)
;; Return blocking item.
(nth index all-items)))))))