Show
Ignore:
Timestamp:
09/18/06 20:48:14 (2 years ago)
Author:
miyoshi
Message:

Sync up with Emacs CVS HEAD.

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • trunk/lisp/allout.el

    r4148 r4166  
    848848  "Length of current buffers' `allout-plain-bullets-string'.") 
    849849(make-variable-buffer-local 'allout-bullets-string-len) 
     850;;;_   = allout-depth-specific-regexp 
     851(defvar allout-depth-specific-regexp "" 
     852  "*Regular expression to match a heading line prefix for a particular depth. 
     853 
     854This expression is used to search for depth-specific topic 
     855headers at depth 2 and greater.  Use `allout-depth-one-regexp' 
     856for to seek topics at depth one. 
     857 
     858This var is set according to the user configuration vars by 
     859`set-allout-regexp'.  It is prepared with format strings for two 
     860decimal numbers, which should each be one less than the depth of the 
     861topic prefix to be matched.") 
     862(make-variable-buffer-local 'allout-depth-specific-regexp) 
     863;;;_   = allout-depth-one-regexp 
     864(defvar allout-depth-one-regexp "" 
     865  "*Regular expression to match a heading line prefix for depth one. 
     866 
     867This var is set according to the user configuration vars by 
     868`set-allout-regexp'.  It is prepared with format strings for two 
     869decimal numbers, which should each be one less than the depth of the 
     870topic prefix to be matched.") 
     871(make-variable-buffer-local 'allout-depth-one-regexp) 
    850872;;;_   = allout-line-boundary-regexp 
    851873(defvar allout-line-boundary-regexp () 
    852874  "`allout-regexp' with outline style beginning-of-line anchor. 
    853875 
    854 This is properly set when `allout-regexp' is produced by 
    855 `set-allout-regexp', so that (match-beginning 2) and (match-end 
    856 2) delimit the prefix.") 
     876This is properly set by `set-allout-regexp'.") 
    857877(make-variable-buffer-local 'allout-line-boundary-regexp) 
    858878;;;_   = allout-bob-regexp 
    859879(defvar allout-bob-regexp () 
    860   "Like `allout-line-boundary-regexp', for headers at beginning of buffer. 
    861 \(match-beginning 2) and \(match-end 2) delimit the prefix.") 
     880  "Like `allout-line-boundary-regexp', for headers at beginning of buffer.") 
    862881(make-variable-buffer-local 'allout-bob-regexp) 
    863882;;;_   = allout-header-subtraction 
     
    870889(make-variable-buffer-local 'allout-plain-bullets-string-len) 
    871890 
    872  
     891;;;_   = allout-doublecheck-at-and-shallower 
     892(defconst allout-doublecheck-at-and-shallower 3 
     893  "Verify apparent topics of this depth and shallower as being non-aberrant. 
     894 
     895Verified with `allout-aberrant-container-p'.  This check's usefulness is 
     896limited to shallow prospects, because the determination of aberrance 
     897depends on the mistaken item being followed by a legitimate item of 
     898excessively greater depth.") 
    873899;;;_   X allout-reset-header-lead (header-lead) 
    874900(defun allout-reset-header-lead (header-lead) 
     
    962988 
    963989Works with respect to `allout-plain-bullets-string' and 
    964 `allout-distinctive-bullets-string'." 
     990`allout-distinctive-bullets-string'. 
     991 
     992Also refresh various data structures that hinge on the regexp." 
    965993 
    966994  (interactive) 
     
    9971025  (setq allout-plain-bullets-string-len (length allout-plain-bullets-string)) 
    9981026  (setq allout-header-subtraction (1- (length allout-header-prefix))) 
    999   ;; Produce the new allout-regexp: 
    1000   (setq allout-regexp (concat "\\(" 
    1001                               (regexp-quote allout-header-prefix) 
    1002                               "[ \t]*[" 
    1003                               allout-bullets-string 
    1004                               "]\\)\\|" 
    1005                               (regexp-quote allout-primary-bullet) 
    1006                               "+\\|\^l")) 
    1007   (setq allout-line-boundary-regexp 
    1008         (concat "\\(\n\\)\\(" allout-regexp "\\)")) 
    1009   (setq allout-bob-regexp 
    1010         (concat "\\(\\`\\)\\(" allout-regexp "\\)")) 
    1011   ) 
     1027 
     1028  (let (new-part old-part) 
     1029    (setq new-part (concat "\\(" 
     1030                           (regexp-quote allout-header-prefix) 
     1031                           "[ \t]*" 
     1032                           ;; already regexp-quoted in a custom way: 
     1033                           "[" allout-bullets-string "]" 
     1034                           "\\)") 
     1035          old-part (concat "\\(" 
     1036                           (regexp-quote allout-primary-bullet) 
     1037                           "\\|" 
     1038                           (regexp-quote allout-header-prefix) 
     1039                           "\\)" 
     1040                           "+" 
     1041                           " ?[^" allout-primary-bullet "]") 
     1042          allout-regexp (concat new-part 
     1043                                "\\|" 
     1044                                old-part 
     1045                                "\\|\^l") 
     1046 
     1047          allout-line-boundary-regexp (concat "\n" new-part 
     1048                                              "\\|" 
     1049                                              "\n" old-part) 
     1050 
     1051          allout-bob-regexp (concat "\\`" new-part 
     1052                                    "\\|" 
     1053                                    "\\`" old-part)) 
     1054 
     1055    (setq allout-depth-specific-regexp 
     1056          (concat "\\(^\\|\\`\\)" 
     1057                  "\\(" 
     1058 
     1059                  ;; new-style spacers-then-bullet string: 
     1060                  "\\(" 
     1061                  (allout-format-quote (regexp-quote allout-header-prefix)) 
     1062                  " \\{%s\\}" 
     1063                  "[" (allout-format-quote allout-bullets-string) "]" 
     1064                  "\\)" 
     1065 
     1066                  ;; old-style all-bullets string, if primary not multi-char: 
     1067                  (if (< 0 allout-header-subtraction) 
     1068                      "" 
     1069                    (concat "\\|\\(" 
     1070                            (allout-format-quote 
     1071                             (regexp-quote allout-primary-bullet)) 
     1072                            (allout-format-quote 
     1073                             (regexp-quote allout-primary-bullet)) 
     1074                            (allout-format-quote 
     1075                             (regexp-quote allout-primary-bullet)) 
     1076                            "\\{%s\\}" 
     1077                            ;; disqualify greater depths: 
     1078                            "[^" 
     1079                            (allout-format-quote allout-primary-bullet) 
     1080                            "]\\)" 
     1081                            )) 
     1082                  "\\)" 
     1083                  )) 
     1084    (setq allout-depth-one-regexp 
     1085          (concat "\\(^\\|\\`\\)" 
     1086                  "\\(" 
     1087 
     1088                  "\\(" 
     1089                  (regexp-quote allout-header-prefix) 
     1090                  ;; disqualify any bullet char following any amount of 
     1091                  ;; intervening whitespace: 
     1092                  " *" 
     1093                  (concat "[^ " allout-bullets-string "]") 
     1094                  "\\)" 
     1095                  (if (< 0 allout-header-subtraction) 
     1096                      ;; Need not support anything like the old 
     1097                      ;; bullet style if the prefix is multi-char. 
     1098                      "" 
     1099                    (concat "\\|" 
     1100                            (regexp-quote allout-primary-bullet) 
     1101                            ;; disqualify deeper primary-bullet sequences: 
     1102                            "[^" allout-primary-bullet "]")) 
     1103                  "\\)" 
     1104                  )))) 
    10121105;;;_  : Key bindings 
    10131106;;;_   = allout-mode-map 
     
    11431236          (error "Pair's name, %S, must be a symbol, not %s" 
    11441237                 name (type-of name))) 
    1145       (setq prior-value (condition-case err 
     1238      (setq prior-value (condition-case nil 
    11461239                            (symbol-value name) 
    11471240                          (void-variable nil))) 
     
    17931886      (remove-hook 'pre-command-hook 'allout-pre-command-business t) 
    17941887      (remove-hook 'post-command-hook 'allout-post-command-business t) 
    1795       (when (featurep 'xemacs) 
    1796         (remove-hook 'before-change-functions 'allout-before-change-handler t)) 
     1888      (remove-hook 'before-change-functions 'allout-before-change-handler t) 
    17971889      (remove-hook 'isearch-mode-end-hook 'allout-isearch-end-handler t) 
    17981890      (remove-hook write-file-hook-var-name 'allout-write-file-hook-handler t) 
     
    18141906      (allout-overlay-preparations)     ; Doesn't hurt to redo this. 
    18151907 
    1816       (allout-infer-header-lead
     1908      (allout-infer-header-lead-and-primary-bullet
    18171909      (allout-infer-body-reindent) 
    18181910 
     
    18551947      (add-hook 'pre-command-hook 'allout-pre-command-business nil t) 
    18561948      (add-hook 'post-command-hook 'allout-post-command-business nil t) 
    1857       (when (featurep 'xemacs) 
    1858         (add-hook 'before-change-functions 'allout-before-change-handler 
    1859                   nil t)) 
     1949      (add-hook 'before-change-functions 'allout-before-change-handler 
     1950                nil t) 
    18601951      (add-hook 'isearch-mode-end-hook 'allout-isearch-end-handler nil t) 
    18611952      (add-hook write-file-hook-var-name 'allout-write-file-hook-handler 
     
    20012092This before-change handler is used only where modification-hooks 
    20022093overlay property is not supported." 
     2094 
     2095  (if (and (allout-mode-p) undo-in-progress (allout-hidden-p)) 
     2096      (allout-show-to-offshoot)) 
     2097 
    20032098  ;; allout-overlay-interior-modification-handler on an overlay handles 
    20042099  ;; this in other emacs, via `allout-exposure-category's 'modification-hooks. 
    20052100  (when (and (featurep 'xemacs) (allout-mode-p)) 
    20062101    ;; process all of the pending overlays: 
    2007     (dolist (overlay (overlays-in beg end)) 
    2008       (if (eq (overlay-get ol 'invisible) 'allout) 
    2009           (allout-overlay-interior-modification-handler 
    2010              overlay nil beg end nil))))) 
     2102    (save-excursion 
     2103      (got-char beg) 
     2104      (let ((overlay (allout-get-invisibility-overlay))) 
     2105        (allout-overlay-interior-modification-handler 
     2106         overlay nil beg end nil))))) 
    20112107;;;_  > allout-isearch-end-handler (&optional overlay) 
    20122108(defun allout-isearch-end-handler (&optional overlay) 
     
    20362132  "Buffer point of the end of the last topic prefix encountered.") 
    20372133(make-variable-buffer-local 'allout-recent-prefix-end) 
     2134;;;_  = allout-recent-depth 
     2135(defvar allout-recent-depth 0 
     2136  "Depth of the last topic prefix encountered.") 
     2137(make-variable-buffer-local 'allout-recent-depth) 
    20382138;;;_  = allout-recent-end-of-subtree 
    20392139(defvar allout-recent-end-of-subtree 0 
    20402140  "Buffer point last returned by `allout-end-of-current-subtree'.") 
    20412141(make-variable-buffer-local 'allout-recent-end-of-subtree) 
    2042 ;;;_  > allout-prefix-data (beg end
    2043 (defmacro allout-prefix-data (beg end
    2044   "Register allout-prefix state data - BEGINNING and END of prefix
     2142;;;_  > allout-prefix-data (
     2143(defsubst allout-prefix-data (
     2144  "Register allout-prefix state data
    20452145 
    20462146For reference by `allout-recent' funcs.  Returns BEGINNING." 
    2047   `(setq allout-recent-prefix-end ,end 
    2048          allout-recent-prefix-beginning ,beg)) 
     2147  (setq allout-recent-prefix-end (or (match-end 1) (match-end 2)) 
     2148        allout-recent-prefix-beginning (or (match-beginning 1) 
     2149                                           (match-beginning 2)) 
     2150        allout-recent-depth (max 1 (- allout-recent-prefix-end 
     2151                                      allout-recent-prefix-beginning 
     2152                                      allout-header-subtraction))) 
     2153  allout-recent-prefix-beginning) 
     2154;;;_  > nullify-allout-prefix-data () 
     2155(defsubst nullify-allout-prefix-data () 
     2156  "Mark allout prefix data as being uninformative." 
     2157  (setq allout-recent-prefix-end (point) 
     2158        allout-recent-prefix-beginning (point) 
     2159        allout-recent-depth 0) 
     2160  allout-recent-prefix-beginning) 
    20492161;;;_  > allout-recent-depth () 
    2050 (defmacro allout-recent-depth () 
     2162(defsubst allout-recent-depth () 
    20512163  "Return depth of last heading encountered by an outline maneuvering function. 
    20522164 
     
    20562168to return the current depth." 
    20572169 
    2058   '(max 1 (- allout-recent-prefix-end 
    2059              allout-recent-prefix-beginning 
    2060              allout-header-subtraction))) 
     2170  allout-recent-depth) 
    20612171;;;_  > allout-recent-prefix () 
    2062 (defmacro allout-recent-prefix () 
     2172(defsubst allout-recent-prefix () 
    20632173  "Like `allout-recent-depth', but returns text of last encountered prefix. 
    20642174 
     
    20662176headings set the variables `allout-recent-prefix-beginning' and 
    20672177`allout-recent-prefix-end' if successful.  This function uses those settings 
    2068 to return the current depth." 
    2069   '(buffer-substring allout-recent-prefix-beginning 
    2070                     allout-recent-prefix-end)) 
     2178to return the current prefix." 
     2179  (buffer-substring-no-properties allout-recent-prefix-beginning 
     2180                                  allout-recent-prefix-end)) 
    20712181;;;_  > allout-recent-bullet () 
    20722182(defmacro allout-recent-bullet () 
     
    20772187`allout-recent-prefix-end' if successful.  This function uses those settings 
    20782188to return the current depth of the most recently matched topic." 
    2079   '(buffer-substring (1- allout-recent-prefix-end) 
    2080                     allout-recent-prefix-end)) 
     2189  '(buffer-substring-no-properties (1- allout-recent-prefix-end) 
     2190                                   allout-recent-prefix-end)) 
    20812191 
    20822192;;;_ #4 Navigation 
     
    20922202    (allout-beginning-of-current-line) 
    20932203    (and (looking-at allout-regexp) 
    2094          (allout-prefix-data (match-beginning 0) (match-end 0))))) 
     2204         (not (allout-aberrant-container-p)) 
     2205         (allout-prefix-data)))) 
    20952206;;;_    > allout-on-heading-p () 
    20962207(defalias 'allout-on-heading-p 'allout-on-current-heading-p) 
     
    21022213                       (looking-at allout-regexp)) 
    21032214       (= (point)(save-excursion (allout-end-of-prefix)(point))))) 
     2215;;;_    > allout-aberrant-container-p () 
     2216(defun allout-aberrant-container-p () 
     2217  "True if topic, or next sibling with children, contains them discontinuously. 
     2218 
     2219Discontinuous means an immediate offspring that is nested more 
     2220than one level deeper than the topic. 
     2221 
     2222If topic has no offspring, then the next sibling with offspring will 
     2223determine whether or not this one is determined to be aberrant. 
     2224 
     2225If true, then the allout-recent-* settings are calibrated on the 
     2226offspring that qaulifies it as aberrant, ie with depth that 
     2227exceeds the topic by more than one." 
     2228 
     2229  ;; This is most clearly understood when considering standard-prefix-leader 
     2230  ;; low-level topics, which can all too easily match text not intended as 
     2231  ;; headers.  For example, any line with a leading '.' or '*' and lacking a 
     2232  ;; following bullet qualifies without this protection.  (A sequence of 
     2233  ;; them can occur naturally, eg a typical textual bullet list.)  We 
     2234  ;; disqualify such low-level sequences when they are followed by a 
     2235  ;; discontinuously contained child, inferring that the sequences are not 
     2236  ;; actually connected with their prospective context. 
     2237 
     2238  (let ((depth (allout-depth)) 
     2239        (start-point (point)) 
     2240        done aberrant) 
     2241    (save-excursion 
     2242      (while (and (not done) 
     2243                  (re-search-forward allout-line-boundary-regexp nil 0)) 
     2244        (allout-prefix-data) 
     2245        (goto-char allout-recent-prefix-beginning) 
     2246        (cond 
     2247         ;; sibling - continue: 
     2248         ((eq allout-recent-depth depth))  
     2249         ;; first offspring is excessive - aberrant: 
     2250         ((> allout-recent-depth (1+ depth)) 
     2251          (setq done t aberrant t)) 
     2252         ;; next non-sibling is lower-depth - not aberrant: 
     2253         (t (setq done t))))) 
     2254    (if aberrant 
     2255        aberrant 
     2256      (goto-char start-point) 
     2257      ;; recalibrate allout-recent-* 
     2258      (allout-depth) 
     2259      nil))) 
    21042260;;;_   : Location attributes 
    21052261;;;_    > allout-depth () 
     
    21142270      (if (and (allout-goto-prefix) 
    21152271               (not (< start-point (point)))) 
    2116           (allout-recent-depth) 
     2272          allout-recent-depth 
    21172273        (progn 
    2118           ;; Oops, no prefix, zero prefix data
    2119           (allout-prefix-data (point)(point)
     2274          ;; Oops, no prefix, nullify it
     2275          (nullify-allout-prefix-data
    21202276          ;; ... and return 0: 
    21212277          0))))) 
     
    21502306      (save-excursion 
    21512307        (allout-back-to-current-heading) 
    2152         (buffer-substring (- allout-recent-prefix-end 1) 
    2153                          allout-recent-prefix-end)) 
     2308        (buffer-substring-no-properties (- allout-recent-prefix-end 1) 
     2309                                        allout-recent-prefix-end)) 
    21542310    ;; Quick and dirty provision, ostensibly for missing bullet: 
    2155     ('args-out-of-range nil)) 
     2311    (args-out-of-range nil)) 
    21562312  ) 
    21572313;;;_    > allout-get-prefix-bullet (prefix) 
     
    21612317  ;; oughtn't be called then, so forget about it... 
    21622318  (if (string-match allout-regexp prefix) 
    2163       (substring prefix (1- (match-end 0)) (match-end 0)))) 
     2319      (substring prefix (1- (match-end 2)) (match-end 2)))) 
    21642320;;;_    > allout-sibling-index (&optional depth) 
    21652321(defun allout-sibling-index (&optional depth) 
     
    21752331          ((or (not depth) (= depth (allout-depth))) 
    21762332           (let ((index 1)) 
    2177              (while (allout-previous-sibling (allout-recent-depth) nil) 
     2333             (while (allout-previous-sibling allout-recent-depth nil) 
    21782334               (setq index (1+ index))) 
    21792335             index)) 
    2180           ((< depth (allout-recent-depth)
     2336          ((< depth allout-recent-depth
    21812337           (allout-ascend-to-depth depth) 
    21822338           (allout-sibling-index)) 
     
    22302386          (not (equal last-command this-command))) 
    22312387      (move-beginning-of-line 1) 
    2232     (let ((beginning-of-body (save-excursion 
    2233                                (allout-beginning-of-current-entry) 
    2234                                (point)))) 
     2388    (allout-depth) 
     2389    (let ((beginning-of-body 
     2390           (save-excursion 
     2391             (while (and (<= allout-recent-depth 
     2392                             allout-doublecheck-at-and-shallower) 
     2393                         (allout-aberrant-container-p) 
     2394                         (allout-previous-visible-heading 1))) 
     2395             (allout-beginning-of-current-entry) 
     2396             (point)))) 
    22352397      (cond ((= (current-column) 0) 
    2236              (allout-beginning-of-current-entry)) 
     2398             (goto-char beginning-of-body)) 
    22372399            ((< (point) beginning-of-body) 
    22382400             (allout-beginning-of-current-line)) 
     
    22422404               (if (< (point) beginning-of-body) 
    22432405                   ;; we were on the headline after its start: 
    2244                    (allout-beginning-of-current-entry))))))) 
     2406                   (goto-char beginning-of-body))))))) 
    22452407;;;_   > allout-end-of-line () 
    22462408(defun allout-end-of-line () 
     
    22622424             (allout-back-to-current-heading) 
    22632425             (allout-show-current-entry) 
     2426             (allout-show-children) 
    22642427             (allout-end-of-entry)) 
    22652428            ((>= (point) end-of-entry) 
     
    22712434  "Move to the heading for the topic \(possibly invisible) after this one. 
    22722435 
    2273 Returns the location of the heading, or nil if none found." 
    2274  
    2275   (if (and (bobp) (not (eobp)) (looking-at allout-regexp)) 
     2436Returns the location of the heading, or nil if none found. 
     2437 
     2438We skip anomolous low-level topics, a la `allout-aberrant-container-p'." 
     2439  (if (looking-at allout-regexp) 
    22762440      (forward-char 1)) 
    22772441 
    2278   (if (re-search-forward allout-line-boundary-regexp nil 0) 
    2279       (allout-prefix-data               ; Got valid location state - set vars: 
    2280        (goto-char (or (match-beginning 2) 
    2281                       allout-recent-prefix-beginning)) 
    2282        (or (match-end 2) allout-recent-prefix-end)))) 
     2442  (when (re-search-forward allout-line-boundary-regexp nil 0) 
     2443    (allout-prefix-data) 
     2444    (and (<= allout-recent-depth allout-doublecheck-at-and-shallower) 
     2445         ;; this will set allout-recent-* on the first non-aberrant topic, 
     2446         ;; whether it's the current one or one that disqualifies it: 
     2447         (allout-aberrant-container-p)) 
     2448    (goto-char allout-recent-prefix-beginning))) 
    22832449;;;_   > allout-this-or-next-heading 
    22842450(defun allout-this-or-next-heading () 
     
    22862452  ;; A throwaway non-macro that is defined after allout-next-heading 
    22872453  ;; and usable by allout-mode. 
    2288   (if (not (allout-goto-prefix)) (allout-next-heading))) 
     2454  (if (not (allout-goto-prefix-doublechecked)) (allout-next-heading))) 
    22892455;;;_   > allout-previous-heading () 
    2290 (defmacro allout-previous-heading () 
     2456(defun allout-previous-heading () 
    22912457  "Move to the prior \(possibly invisible) heading line. 
    22922458 
    2293 Return the location of the beginning of the heading, or nil if not found." 
    2294  
    2295   '(if (bobp) 
    2296        nil 
    2297      (allout-goto-prefix) 
    2298      (if 
    2299          ;; searches are unbounded and return nil if failed: 
    2300          (or (re-search-backward allout-line-boundary-regexp nil 0) 
    2301              (looking-at allout-bob-regexp)) 
    2302          (progn                         ; Got valid location state - set vars: 
    2303            (allout-prefix-data 
    2304             (goto-char (or (match-beginning 2) 
    2305                            allout-recent-prefix-beginning)) 
    2306             (or (match-end 2) allout-recent-prefix-end)))))) 
     2459Return the location of the beginning of the heading, or nil if not found. 
     2460 
     2461We skip anomolous low-level topics, a la `allout-aberrant-container-p'." 
     2462 
     2463  (if (bobp) 
     2464      nil 
     2465    ;; allout-goto-prefix-doublechecked calls us, so we can't use it here. 
     2466    (let ((start-point (point))) 
     2467      (allout-goto-prefix) 
     2468      (when (or (re-search-backward allout-line-boundary-regexp nil 0) 
     2469                (looking-at allout-bob-regexp)) 
     2470        (goto-char (allout-prefix-data)) 
     2471        (if (and (<= allout-recent-depth allout-doublecheck-at-and-shallower) 
     2472                 (allout-aberrant-container-p)) 
     2473            (or (allout-previous-heading) 
     2474                (and (goto-char start-point) 
     2475                     ;; recalibrate allout-recent-*: 
     2476                     (allout-depth) 
     2477                     nil)) 
     2478          (point)))))) 
    23072479;;;_   > allout-get-invisibility-overlay () 
    23082480(defun allout-get-invisibility-overlay () 
     
    23122484    (while (and overlays (not got)) 
    23132485      (if (equal (overlay-get (car overlays) 'invisible) 'allout) 
    2314           (setq got (car overlays)))) 
     2486          (setq got (car overlays)) 
     2487        (pop overlays))) 
    23152488    got)) 
    23162489;;;_   > allout-back-to-visible-text () 
     
    23252498;;; nested lists of the locations of topics within a subtree. 
    23262499;;; 
    2327 ;;; Use of charts enables efficient navigation of subtrees, by 
    2328 ;;; requiring only a single regexp-search based traversal, to scope 
    2329 ;;; out the subtopic locations.  The chart then serves as the basis 
    2330 ;;; for assessment or adjustment of the subtree, without redundant 
    2331 ;;; traversal of the structure. 
     2500;;; Charts enable efficient subtree navigation by providing a reusable basis 
     2501;;; for elaborate, compound assessment and adjustment of a subtree. 
    23322502 
    23332503;;;_   > allout-chart-subtree (&optional levels visible orig-depth prev-depth) 
     
    23492519for their elaborate manipulations. 
    23502520 
    2351 Topics are entered in the chart so the last one is at the car. 
    2352 The entry for each topic consists of an integer indicating the point 
    2353 at the beginning of the topic.  Charts for offspring consists of a 
    2354 list containing, recursively, the charts for the respective subtopics. 
    2355 The chart for a topics' offspring precedes the entry for the topic 
    2356 itself. 
     2521The chart entries for the topics are in reverse order, so the 
     2522last topic is listed first.  The entry for each topic consists of 
     2523an integer indicating the point at the beginning of the topic 
     2524prefix.  Charts for offspring consists of a list containing, 
     2525recursively, the charts for the respective subtopics.  The chart 
     2526for a topics' offspring precedes the entry for the topic itself. 
    23572527 
    23582528The other function parameters are for internal recursion, and should 
     
    23812551    (while (and (not (eobp)) 
    23822552                                        ; Still within original topic? 
    2383                 (< orig-depth (setq curr-depth (allout-recent-depth))) 
     2553                (< orig-depth (setq curr-depth allout-recent-depth)) 
    23842554                (cond ((= prev-depth curr-depth) 
    23852555                       ;; Register this one and move on: 
    2386                        (setq chart (cons (point) chart)) 
     2556                       (setq chart (cons allout-recent-prefix-beginning chart)) 
    23872557                       (if (and levels (<= levels 1)) 
    23882558                           ;; At depth limit - skip sublevels: 
     
    23912561                               ;; next heading at lesser depth: 
    23922562                               (while (and (<= curr-depth 
    2393                                                (allout-recent-depth)
     2563                                               allout-recent-depth
    23942564                                           (if visible 
    23952565                                               (allout-next-visible-heading 1) 
     
    24382608for an explanation of charts." 
    24392609  (save-excursion 
    2440     (if (allout-goto-prefix
    2441        (let ((chart (list (point)))) 
    2442          (while (allout-next-sibling) 
    2443            (setq chart (cons (point) chart))) 
    2444          (if chart (setq chart (nreverse chart))))))) 
     2610    (when (allout-goto-prefix-doublechecked
     2611      (let ((chart (list (point)))) 
     2612        (while (allout-next-sibling) 
     2613          (setq chart (cons (point) chart))) 
     2614        (if chart (setq chart (nreverse chart))))))) 
    24452615;;;_   > allout-chart-to-reveal (chart depth) 
    24462616(defun allout-chart-to-reveal (chart depth) 
     
    25152685      (forward-char 1) 
    25162686      (if (looking-at allout-regexp) 
    2517           (setq done (allout-prefix-data (match-beginning 0) 
    2518                                           (match-end 0))) 
     2687          (setq done (allout-prefix-data)) 
    25192688        (forward-char -1))) 
    25202689    (if (bobp) 
    25212690        (cond ((looking-at allout-regexp) 
    2522                (allout-prefix-data (match-beginning 0)(match-end 0))) 
     2691               (allout-prefix-data)) 
    25232692              ((allout-next-heading)) 
    25242693              (done)) 
    25252694      done))) 
     2695;;;_   > allout-goto-prefix-doublechecked () 
     2696(defun allout-goto-prefix-doublechecked () 
     2697  "Put point at beginning of immediately containing outline topic. 
     2698 
     2699Like `allout-goto-prefix', but shallow topics \(according to `allout-doublecheck-at-and-shallower') are checked and disqualified for child containment discontinuity, according to `allout-aberrant-container-p'." 
     2700  (allout-goto-prefix) 
     2701  (if (and (<= allout-recent-depth allout-doublecheck-at-and-shallower) 
     2702           (allout-aberrant-container-p)) 
     2703      (allout-previous-heading) 
     2704    (point))) 
     2705 
    25262706;;;_   > allout-end-of-prefix () 
    25272707(defun allout-end-of-prefix (&optional ignore-decorations) 
     
    25312711otherwise skip white space between bullet and ensuing text." 
    25322712 
    2533   (if (not (allout-goto-prefix)) 
     2713  (if (not (allout-goto-prefix-doublechecked)) 
    25342714      nil 
    2535     (let ((match-data (match-data))) 
    2536       (goto-char (match-end 0)) 
    2537       (if ignore-decorations 
    2538           t 
    2539         (while (looking-at "[0-9]") (forward-char 1)) 
    2540         (if (and (not (eolp)) (looking-at "\\s-")) (forward-char 1))) 
    2541       (store-match-data match-data)) 
     2715    (goto-char allout-recent-prefix-end) 
     2716    (if ignore-decorations 
     2717        t 
     2718      (while (looking-at "[0-9]") (forward-char 1)) 
     2719      (if (and (not (eolp)) (looking-at "\\s-")) (forward-char 1))) 
    25422720    ;; Reestablish where we are: 
    25432721    (allout-current-depth))) 
     
    25462724  "Return position of current \(visible) topic's bullet." 
    25472725 
    2548  (if (not (allout-current-depth)) 
     2726  (if (not (allout-current-depth)) 
    25492727      nil 
    2550    (1- (match-end 0)))) 
     2728    (1- allout-recent-prefix-end))) 
    25512729;;;_   > allout-back-to-current-heading () 
    25522730(defun allout-back-to-current-heading () 
     
    25632741                        (allout-beginning-of-current-line) 
    25642742                        (if (not (looking-at allout-regexp)) 
    2565                             (re-search-backward (concat 
    2566                                                  "^\\(" allout-regexp "\\)") 
     2743                            (re-search-backward allout-regexp 
    25672744                                                nil 'move))) 
    2568                       (allout-prefix-data (match-beginning 1) 
    2569                                           (match-end 1))))) 
     2745                      (allout-prefix-data)))) 
    25702746      (if (interactive-p) 
    25712747          (allout-end-of-prefix) 
     
    25792755Returns that character position." 
    25802756 
    2581   (if (re-search-forward allout-line-boundary-regexp nil 'move) 
    2582       (prog1 (goto-char (match-beginning 0)) 
    2583              (allout-prefix-data (match-beginning 2)(match-end 2))))) 
     2757  (if (allout-next-heading) 
     2758      (goto-char (1- allout-recent-prefix-beginning)))) 
    25842759;;;_   > allout-end-of-subtree (&optional current include-trailing-blank) 
    25852760(defun allout-end-of-subtree (&optional current include-trailing-blank) 
     
    25972772  (if current 
    25982773      (allout-back-to-current-heading) 
    2599     (allout-goto-prefix)) 
    2600   (let ((level (allout-recent-depth))) 
     2774    (allout-goto-prefix-doublechecked)) 
     2775  (let ((level allout-recent-depth)) 
    26012776    (allout-next-heading) 
    26022777    (while (and (not (eobp)) 
    2603                 (> (allout-recent-depth) level)) 
     2778                (> allout-recent-depth level)) 
    26042779      (allout-next-heading)) 
    26052780    (if (eobp) 
     
    26302805  (let ((start-point (point))) 
    26312806    (move-beginning-of-line 1) 
     2807    (if (< 0 (allout-current-depth)) 
     2808        (goto-char allout-recent-prefix-end) 
     2809      (goto-char (point-min))) 
    26322810    (allout-end-of-prefix) 
    26332811    (if (and (interactive-p) 
     
    26772855  "Ascend to depth DEPTH, returning depth if successful, nil if not." 
    26782856  (if (and (> depth 0)(<= depth (allout-depth))) 
    2679       (let ((last-good (point))) 
    2680         (while (and (< depth (allout-depth)) 
    2681                     (setq last-good (point)) 
    2682                     (allout-beginning-of-level) 
    2683                     (allout-previous-heading))) 
    2684         (if (= (allout-recent-depth) depth) 
    2685             (progn (goto-char allout-recent-prefix-beginning) 
    2686                    depth) 
    2687           (goto-char last-good) 
    2688           nil)) 
    2689     (if (interactive-p) (allout-end-of-prefix)))) 
     2857      (let (last-ascended) 
     2858        (while (and (< depth allout-recent-depth) 
     2859                    (setq last-ascended (allout-ascend)))) 
     2860        (goto-char allout-recent-prefix-beginning) 
     2861        (if (interactive-p) (allout-end-of-prefix)) 
     2862        (and last-ascended allout-recent-depth)))) 
    26902863;;;_   > allout-ascend () 
    26912864(defun allout-ascend () 
     
    26932866  (prog1 
    26942867      (if (allout-beginning-of-level) 
    2695          (allout-previous-heading)) 
     2868          (allout-previous-heading)) 
    26962869    (if (interactive-p) (allout-end-of-prefix)))) 
    26972870;;;_   > allout-descend-to-depth (depth) 
     
    27042877    (while 
    27052878        (and (> (allout-depth) 0) 
    2706              (not (= depth (allout-recent-depth))) ; ... not there yet 
     2879             (not (= depth allout-recent-depth)) ; ... not there yet 
    27072880             (allout-next-heading)     ; ... go further 
    2708              (< start-depth (allout-recent-depth)))) ; ... still in topic 
     2881             (< start-depth allout-recent-depth))) ; ... still in topic 
    27092882    (if (and (> (allout-depth) 0) 
    2710              (= (allout-recent-depth) depth)) 
     2883             (= allout-recent-depth depth)) 
    27112884        depth 
    27122885      (goto-char start-point) 
    27132886      nil)) 
    27142887  ) 
    2715 ;;;_   > allout-up-current-level (arg &optional dont-complain) 
    2716 (defun allout-up-current-level (arg &optional dont-complain) 
    2717   "Move out ARG levels from current visible topic. 
    2718  
    2719 Positions on heading line of containing topic.  Error if unable to 
    2720 ascend that far, or nil if unable to ascend but optional arg 
    2721 DONT-COMPLAIN is non-nil." 
     2888;;;_   > allout-up-current-level (arg) 
     2889(defun allout-up-current-level (arg) 
     2890  "Move out ARG levels from current visible topic." 
    27222891  (interactive "p") 
    2723   (allout-back-to-current-heading) 
    2724   (let ((present-level (allout-recent-depth)) 
    2725         (last-good (point)) 
    2726         failed) 
    2727     ;; Loop for iterating arg: 
    2728     (while (and (> (allout-recent-depth) 1) 
    2729                 (> arg 0) 
    2730                 (not (bobp)) 
    2731                 (not failed)) 
    2732       (setq last-good (point)) 
    2733       ;; Loop for going back over current or greater depth: 
    2734       (while (and (not (< (allout-recent-depth) present-level)) 
    2735                   (or (allout-previous-visible-heading 1) 
    2736                       (not (setq failed present-level))))) 
    2737       (setq present-level (allout-current-depth)) 
    2738       (setq arg (- arg 1))) 
    2739     (if (or failed 
    2740             (> arg 0)) 
    2741         (progn (goto-char last-good) 
    2742                (if (interactive-p) (allout-end-of-prefix)) 
    2743                (if (not dont-complain) 
    2744                    (error "Can't ascend past outermost level") 
    2745                  (if (interactive-p) (allout-end-of-prefix)) 
    2746                  nil)) 
     2892  (let ((start-point (point))) 
     2893    (allout-back-to-current-heading) 
     2894    (if (not (allout-ascend)) 
     2895        (progn (goto-char start-point) 
     2896               (error "Can't ascend past outermost level")) 
    27472897      (if (interactive-p) (allout-end-of-prefix)) 
    27482898      allout-recent-prefix-beginning))) 
     
    27572907Go backward if optional arg BACKWARD is non-nil. 
    27582908 
    2759 Return depth if successful, nil otherwise." 
    2760  
    2761   (if (and backward (bobp)) 
     2909Return the start point of the new topic if successful, nil otherwise." 
     2910 
     2911  (if (if backward (bobp) (eobp)) 
    27622912      nil 
    2763     (let ((start-depth (or depth (allout-depth))) 
     2913    (let ((target-depth (or depth (allout-depth))) 
    27642914          (start-point (point)) 
     2915          (count 0) 
     2916          leaping 
    27652917          last-depth) 
    2766       (while (and (not (if backward (bobp) (eobp))) 
    2767                   (if backward (allout-previous-heading) 
    2768                     (allout-next-heading)) 
    2769                   (> (setq last-depth (allout-recent-depth)) start-depth))) 
    2770       (if (and (not (eobp)) 
    2771                (and (> (or last-depth (allout-depth)) 0) 
    2772                     (= (allout-recent-depth) start-depth))) 
    2773           allout-recent-prefix-beginning 
    2774         (goto-char start-point) 
    2775         (if depth (allout-depth) start-depth) 
    2776         nil)))) 
     2918      (while (and 
     2919              ;; done too few single steps to resort to the leap routine: 
     2920              (not leaping) 
     2921              ;; not at limit: 
     2922              (not (if backward (bobp) (eobp))) 
     2923              ;; still traversable: 
     2924              (if backward (allout-previous-heading) (allout-next-heading)) 
     2925              ;; we're below the target depth 
     2926              (> (setq last-depth allout-recent-depth) target-depth)) 
     2927        (setq count (1+ count)) 
     2928        (if (> count 7)                 ; lists are commonly 7 +- 2, right?-) 
     2929            (setq leaping t))) 
     2930      (cond (leaping 
     2931             (or (allout-next-sibling-leap target-depth backward) 
     2932                 (progn 
     2933                   (goto-char start-point) 
     2934                   (if depth (allout-depth) target-depth) 
     2935                   nil))) 
     2936            ((and (not (eobp)) 
     2937                  (and (> (or last-depth (allout-depth)) 0) 
     2938                       (= allout-recent-depth target-depth))) 
     2939             allout-recent-prefix-beginning) 
     2940            (t 
     2941             (goto-char start-point) 
     2942             (if depth (allout-depth) target-depth) 
     2943             nil))))) 
     2944;;;_   > allout-next-sibling-leap (&optional depth backward) 
     2945(defun allout-next-sibling-leap (&optional depth backward) 
     2946  "Like `allout-next-sibling', but by direct search for topic at depth. 
     2947 
     2948Traverse at optional DEPTH, or current depth if none specified. 
     2949 
     2950Go backward if optional arg BACKWARD is non-nil. 
     2951 
     2952Return the start point of the new topic if successful, nil otherwise. 
     2953 
     2954Costs more than regular `allout-next-sibling' for short traversals: 
     2955 
     2956 - we have to check the prior \(next, if travelling backwards) 
     2957   item to confirm connectivity with the prior topic, and 
     2958 - if confirmed, we have to reestablish the allout-recent-* settings with 
     2959   some extra navigation 
     2960 - if confirmation fails, we have to do more work to recover 
     2961 
     2962It is an increasingly big win when there are many intervening 
     2963offspring before the next sibling, however, so 
     2964`allout-next-sibling' resorts to this if it finds itself in that 
     2965situation." 
     2966 
     2967  (if (if backward (bobp) (eobp)) 
     2968      nil 
     2969    (let* ((start-point (point)) 
     2970           (target-depth (or depth (allout-depth))) 
     2971           (search-whitespace-regexp nil) 
     2972           (depth-biased (- target-depth 2)) 
     2973           (expression (if (<= target-depth 1) 
     2974                           allout-depth-one-regexp 
     2975                         (format allout-depth-specific-regexp 
     2976                                 depth-biased depth-biased))) 
     2977           found 
     2978           done) 
     2979      (while (not done) 
     2980        (setq found (if backward 
     2981                        (re-search-backward expression nil 'to-limit) 
     2982                      (forward-char 1) 
     2983                      (re-search-forward expression nil 'to-limit))) 
     2984        (if (and found (allout-aberrant-container-p)) 
     2985            (setq found nil)) 
     2986        (setq done (or found (if backward (bobp) (eobp))))) 
     2987      (if (not found) 
     2988          (progn (goto-char start-point) 
     2989                 nil) 
     2990        ;; rationale: if any intervening items were at a lower depth, we 
     2991        ;; would now be on the first offspring at the target depth - ie, 
     2992        ;; the preceeding item (per the search direction) must be at a 
     2993        ;; lesser depth.  that's all we need to check. 
     2994        (if backward (allout-next-heading) (allout-previous-heading)) 
     2995        (if (< allout-recent-depth target-depth) 
     2996            ;; return to start and reestablish allout-recent-*: 
     2997            (progn 
     2998              (goto-char start-point) 
     2999              (allout-depth) 
     3000              nil) 
     3001          (goto-char found) 
     3002          ;; locate cursor and set allout-recent-*: 
     3003          (allout-goto-prefix)))))) 
    27773004;;;_   > allout-previous-sibling (&optional depth backward) 
    27783005(defun allout-previous-sibling (&optional depth backward) 
     
    28083035  (let ((depth (allout-depth))) 
    28093036    (while (allout-previous-sibling depth nil)) 
    2810     (prog1 (allout-recent-depth) 
     3037    (prog1 allout-recent-depth 
    28113038      (if (interactive-p) (allout-end-of-prefix))))) 
    28123039;;;_   > allout-next-visible-heading (arg) 
     
    28223049         prev got) 
    28233050 
    2824     (while (> arg 0)                    ; limit condition 
    2825       (while (and (not (if backward (bobp)(eobp))) ; boundary condition 
    2826                   ;; Move, skipping over all those concealed lines: 
    2827                   (prog1 (condition-case nil (or (line-move step) t) 
    2828                            (error nil)) 
    2829                     (allout-beginning-of-current-line)) 
    2830                   (not (setq got (looking-at allout-regexp))))) 
     3051    (while (> arg 0) 
     3052      (while (and 
     3053              ;; Boundary condition: 
     3054              (not (if backward (bobp)(eobp))) 
     3055              ;; Move, skipping over all concealed lines in one fell swoop: 
     3056              (prog1 (condition-case nil (or (line-move step) t) 
     3057                       (error nil)) 
     3058                (allout-beginning-of-current-line)) 
     3059              ;; Deal with apparent header line: 
     3060              (if (not (looking-at allout-regexp)) 
     3061