diff options
author | Nicolas Goaziou <n.goaziou@gmail.com> | 2010-12-29 18:24:50 +0100 |
---|---|---|
committer | Nicolas Goaziou <n.goaziou@gmail.com> | 2011-02-18 12:45:08 +0100 |
commit | 148deffd4e9573a4f6539ba04e0945f770739611 (patch) | |
tree | bccc90501cc006caa7035f4d78700f1980af1cf6 | |
parent | 9230df2e0de0b4082ad2fc4bf820c74ca86a8fed (diff) | |
download | org-mode-148deffd4e9573a4f6539ba04e0945f770739611.tar.gz |
org-list: move error messages in interactive indent/outdent functions
* list/org-list.el (org-list-indent-item-generic): remove error
messages happening before process. This belongs to interactive
functions.
(org-indent-item,org-indent-item-tree,
org-outdent-item,org-outdent-item-tree): ensure point or region is
correct before computing list structure. Return an error message
otherwise.
-rw-r--r-- | lisp/org-list.el | 185 |
1 files changed, 99 insertions, 86 deletions
diff --git a/lisp/org-list.el b/lisp/org-list.el index 4ab70a9..6cea2cd 100644 --- a/lisp/org-list.el +++ b/lisp/org-list.el @@ -660,84 +660,76 @@ Return t if successful." (beginning-of-line) (let* ((regionp (org-region-active-p)) (rbeg (and regionp (region-beginning))) - (rend (and regionp (region-end)))) - (cond - ((and regionp - (goto-char rbeg) - (not (org-search-forward-unenclosed org-item-beginning-re rend t))) - (error "No item in region")) - ((not (org-at-item-p)) - (error "Not at an item")) - (t - (let* ((top (org-list-get-top-point struct)) - (parents (org-list-struct-parent-alist struct)) - (prevs (org-list-struct-prev-alist struct)) - ;; Are we going to move the whole list? - (specialp (and (cdr (assq 'indent org-list-automatic-rules)) - (not no-subtree) - (= top (point))))) - ;; Determine begin and end points of zone to indent. If moving - ;; more than one item, save them for subsequent moves. - (unless (and (memq last-command '(org-shiftmetaright org-shiftmetaleft)) - (memq this-command '(org-shiftmetaright org-shiftmetaleft))) - (if regionp - (progn - (set-marker org-last-indent-begin-marker rbeg) - (set-marker org-last-indent-end-marker rend)) - (set-marker org-last-indent-begin-marker (point)) - (set-marker org-last-indent-end-marker - (cond - (specialp (org-list-get-bottom-point struct)) - (no-subtree (1+ (point))) - (t (org-list-get-item-end (point) struct)))))) - (let* ((beg (marker-position org-last-indent-begin-marker)) - (end (marker-position org-last-indent-end-marker))) - (cond - ;; Special case: moving top-item with indent rule - (specialp - (let* ((level-skip (org-level-increment)) - (offset (if (< arg 0) (- level-skip) level-skip)) - (top-ind (org-list-get-ind beg struct)) - (old-struct (mapcar (lambda (e) (copy-alist e)) struct))) - (if (< (+ top-ind offset) 0) - (error "Cannot outdent beyond margin") - ;; Change bullet if necessary - (when (and (= (+ top-ind offset) 0) - (string-match "*" - (org-list-get-bullet beg struct))) - (org-list-set-bullet beg struct - (org-list-bullet-string "-"))) - ;; Shift every item by OFFSET and fix bullets. Then - ;; apply changes to buffer. - (mapc (lambda (e) - (let ((ind (org-list-get-ind (car e) struct))) - (org-list-set-ind (car e) struct (+ ind offset)))) - struct) - (org-list-struct-fix-bul struct prevs) - (org-list-struct-apply-struct struct old-struct)))) - ;; Forbidden move: - ((and (< arg 0) - ;; If only one item is moved, it mustn't have a child - (or (and no-subtree - (not regionp) - (org-list-has-child-p beg struct)) - ;; If a subtree or region is moved, the last item - ;; of the subtree mustn't have a child - (let ((last-item (caar - (reverse - (org-remove-if - (lambda (e) (>= (car e) end)) - struct))))) - (org-list-has-child-p last-item struct)))) - (error "Cannot outdent an item without its children")) - ;; Normal shifting - (t - (let* ((new-parents - (if (< arg 0) - (org-list-struct-outdent beg end struct parents) - (org-list-struct-indent beg end struct parents prevs)))) - (org-list-struct-fix-struct struct new-parents)) - (org-update-checkbox-count-maybe))))))))) + (rend (and regionp (region-end))) + (top (org-list-get-top-point struct)) + (parents (org-list-struct-parent-alist struct)) + (prevs (org-list-struct-prev-alist struct)) + ;; Are we going to move the whole list? + (specialp (and (cdr (assq 'indent org-list-automatic-rules)) + (not no-subtree) + (= top (point))))) + ;; Determine begin and end points of zone to indent. If moving + ;; more than one item, save them for subsequent moves. + (unless (and (memq last-command '(org-shiftmetaright org-shiftmetaleft)) + (memq this-command '(org-shiftmetaright org-shiftmetaleft))) + (if regionp + (progn + (set-marker org-last-indent-begin-marker rbeg) + (set-marker org-last-indent-end-marker rend)) + (set-marker org-last-indent-begin-marker (point)) + (set-marker org-last-indent-end-marker + (cond + (specialp (org-list-get-bottom-point struct)) + (no-subtree (1+ (point))) + (t (org-list-get-item-end (point) struct)))))) + (let* ((beg (marker-position org-last-indent-begin-marker)) + (end (marker-position org-last-indent-end-marker))) + (cond + ;; Special case: moving top-item with indent rule + (specialp + (let* ((level-skip (org-level-increment)) + (offset (if (< arg 0) (- level-skip) level-skip)) + (top-ind (org-list-get-ind beg struct)) + (old-struct (mapcar (lambda (e) (copy-alist e)) struct))) + (if (< (+ top-ind offset) 0) + (error "Cannot outdent beyond margin") + ;; Change bullet if necessary + (when (and (= (+ top-ind offset) 0) + (string-match "*" + (org-list-get-bullet beg struct))) + (org-list-set-bullet beg struct + (org-list-bullet-string "-"))) + ;; Shift every item by OFFSET and fix bullets. Then + ;; apply changes to buffer. + (mapc (lambda (e) + (let ((ind (org-list-get-ind (car e) struct))) + (org-list-set-ind (car e) struct (+ ind offset)))) + struct) + (org-list-struct-fix-bul struct prevs) + (org-list-struct-apply-struct struct old-struct)))) + ;; Forbidden move: + ((and (< arg 0) + ;; If only one item is moved, it mustn't have a child + (or (and no-subtree + (not regionp) + (org-list-has-child-p beg struct)) + ;; If a subtree or region is moved, the last item + ;; of the subtree mustn't have a child + (let ((last-item (caar + (reverse + (org-remove-if + (lambda (e) (>= (car e) end)) + struct))))) + (org-list-has-child-p last-item struct)))) + (error "Cannot outdent an item without its children")) + ;; Normal shifting + (t + (let* ((new-parents + (if (< arg 0) + (org-list-struct-outdent beg end struct parents) + (org-list-struct-indent beg end struct parents prevs)))) + (org-list-struct-fix-struct struct new-parents)) + (org-update-checkbox-count-maybe)))))) t) ;;; Predicates @@ -1793,29 +1785,50 @@ Initial position of cursor is restored after the changes." "Outdent a local list item, but not its children. If a region is active, all items inside will be moved." (interactive) - (let ((struct (org-list-struct))) - (org-list-indent-item-generic -1 t struct))) + (if (org-at-item-p) + (let ((struct (org-list-struct))) + (org-list-indent-item-generic -1 t struct)) + (error "Not at an item"))) (defun org-indent-item () "Indent a local list item, but not its children. If a region is active, all items inside will be moved." (interactive) - (let ((struct (org-list-struct))) - (org-list-indent-item-generic 1 t struct))) + (if (org-at-item-p) + (let ((struct (org-list-struct))) + (org-list-indent-item-generic 1 t struct)) + (error "Not at an item"))) (defun org-outdent-item-tree () "Outdent a local list item including its children. If a region is active, all items inside will be moved." (interactive) - (let ((struct (org-list-struct))) - (org-list-indent-item-generic -1 nil struct))) + (let ((regionp (org-region-active-p))) + (cond + ((or (org-at-item-p) + (and (org-region-active-p) + (goto-char (region-beginning)) + (org-at-item-p))) + (let ((struct (org-list-struct))) + (org-list-indent-item-generic -1 nil struct))) + (regionp (error "Region not starting at an item")) + (t (error "Not at an item"))))) (defun org-indent-item-tree () "Indent a local list item including its children. If a region is active, all items inside will be moved." (interactive) - (let ((struct (org-list-struct))) - (org-list-indent-item-generic 1 nil struct))) + (interactive) + (let ((regionp (org-region-active-p))) + (cond + ((or (org-at-item-p) + (and (org-region-active-p) + (goto-char (region-beginning)) + (org-at-item-p))) + (let ((struct (org-list-struct))) + (org-list-indent-item-generic 1 nil struct))) + (regionp (error "Region not starting at an item")) + (t (error "Not at an item"))))) (defvar org-tab-ind-state) (defun org-cycle-item-indentation () |