Commit 2ed8e1f7 authored by Stefan Monnier's avatar Stefan Monnier
Browse files

(comment-search-forward): Make sure we search forward.

(comment-enter-backward): Try and distinguish the non-matching case at
EOB from the non-matching case with a missing comment-end-skip for
a 2-char comment ender.
(comment-choose-indent): New function extracted from comment-indent.
Improve the alignment algorithm.
(comment-indent): Use it.
parent 121f1921
2007-05-08 Stefan Monnier <monnier@iro.umontreal.ca>
 
* newcomment.el (comment-search-forward): Make sure we search forward.
(comment-enter-backward): Try and distinguish the non-matching case at
EOB from the non-matching case with a missing comment-end-skip for
a 2-char comment ender.
(comment-choose-indent): New function extracted from comment-indent.
Improve the alignment algorithm.
(comment-indent): Use it.
* textmodes/sgml-mode.el (sgml-lexical-context): Add handling of
XML style Processing Instructions.
(sgml-parse-tag-backward): Handle XML-style PIs. Also ensure progress.
......@@ -97,10 +97,10 @@ Major modes should set this variable.")
;;;###autoload
(defcustom comment-column 32
"Column to indent right-margin comments to.
Each mode establishes a different default value for this variable; you
Each mode may establish a different default value for this variable; you
can set the value for a particular mode using that mode's hook.
Comments might be indented to a value smaller than this in order
not to go beyond `comment-fill-column'."
Comments might be indented to a different value in order not to go beyond
`comment-fill-column' or in order to align them with surrounding comments."
:type 'integer
:group 'comment)
(make-variable-buffer-local 'comment-column)
......@@ -491,16 +491,24 @@ Point is assumed to be just at the end of a comment."
(goto-char (point-min))
(re-search-forward (concat comment-end-skip "\\'") nil t))
(goto-char (match-beginning 0)))
;; comment-end-skip not found. Maybe we're at EOB which implicitly
;; closes the comment.
((eobp) (skip-syntax-backward " "))
(t
;; else comment-end-skip was not found probably because it was not
;; set right. Since \\s> should catch the single-char case, we'll
;; blindly assume we're at the end of a two-char comment-end.
;; comment-end-skip not found probably because it was not set
;; right. Since \\s> should catch the single-char case, let's
;; check that we're looking at a two-char comment ender.
((not (or (<= (- (point-max) (line-beginning-position)) 1)
(zerop (logand (car (syntax-after (- (point) 1)))
;; Here we take advantage of the fact that
;; the syntax class " " is encoded to 0,
;; so " 4" gives us just the 4 bit.
(car (string-to-syntax " 4"))))
(zerop (logand (car (syntax-after (- (point) 2)))
(car (string-to-syntax " 3"))))))
(backward-char 2)
(skip-chars-backward (string (char-after)))
(skip-syntax-backward " ")))))
(skip-syntax-backward " "))
;; No clue what's going on: maybe we're really not right after the
;; end of a comment. Maybe we're at the "end" because of EOB rather
;; than because of a marker.
(t (skip-syntax-backward " ")))))
;;;;
;;;; Commands
......@@ -516,6 +524,58 @@ Point is assumed to be just at the end of a comment."
(and (> comment-add 0) (looking-at "\\s<\\(\\S<\\|\\'\\)")))
comment-column)))
(defun comment-choose-indent (&optional indent)
"Choose the indentation to use for a right-hand-side comment.
The criteria are (in this order):
- try to keep the comment's text within `comment-fill-column'.
- try to align with surrounding comments.
- prefer INDENT (or `comment-column' if nil).
Point is expected to be at the start of the comment."
(unless indent (setq indent comment-column))
;; Avoid moving comments past the fill-column.
(let ((max (+ (current-column)
(- (or comment-fill-column fill-column)
(save-excursion (end-of-line) (current-column)))))
(other nil)
(min (save-excursion (skip-chars-backward " \t")
(1+ (current-column)))))
;; Fix up the range.
(if (< max min) (setq max min))
;; Don't move past the fill column.
(if (<= max indent) (setq indent max))
;; We can choose anywhere between min..max.
;; Let's try to align to a comment on the previous line.
(save-excursion
(when (and (zerop (forward-line -1))
(setq other (comment-search-forward
(line-end-position) t)))
(goto-char other) (setq other (current-column))))
(if (and other (<= other max) (>= other min))
;; There is a comment and it's in the range: bingo!
other
;; Can't align to a previous comment: let's try to align to comments
;; on the following lines, then. These have not been re-indented yet,
;; so we can't directly align ourselves with them. All we do is to try
;; and choose an indentation point with which they will be able to
;; align themselves.
(save-excursion
(while (and (zerop (forward-line 1))
(setq other (comment-search-forward
(line-end-position) t)))
(goto-char other)
(let ((omax (+ (current-column)
(- (or comment-fill-column fill-column)
(save-excursion (end-of-line) (current-column)))))
(omin (save-excursion (skip-chars-backward " \t")
(1+ (current-column)))))
(if (and (>= omax min) (<= omin max))
(progn (setq min (max omin min))
(setq max (min omax max)))
;; Can't align with this anyway, so exit the loop.
(goto-char (point-max))))))
;; Return the closest point to indent within min..max.
(max min (min max indent)))))
;;;###autoload
(defun comment-indent (&optional continue)
"Indent this line's comment to `comment-column', or insert an empty comment.
......@@ -569,38 +629,9 @@ If CONTINUE is non-nil, use the `comment-continue' markers if any."
(if (not indent)
;; comment-indent-function refuses: delegate to line-indent.
(indent-according-to-mode)
;; If the comment is at the left of code, adjust the indentation.
;; If the comment is at the right of code, adjust the indentation.
(unless (save-excursion (skip-chars-backward " \t") (bolp))
;; Avoid moving comments past the fill-column.
(let ((max (+ (current-column)
(- (or comment-fill-column fill-column)
(save-excursion (end-of-line) (current-column))))))
(if (<= max indent)
(setq indent max) ;Don't move past the fill column.
;; We can choose anywhere between indent..max.
;; Let's try to align to a comment on the previous line.
(let ((other nil)
(min (max indent
(save-excursion (skip-chars-backward " \t")
(1+ (current-column))))))
(save-excursion
(when (and (zerop (forward-line -1))
(setq other (comment-search-forward
(line-end-position) t)))
(goto-char other) (setq other (current-column))))
(if (and other (<= other max) (>= other min))
;; There is a comment and it's in the range: bingo.
(setq indent other)
;; Let's try to align to a comment on the next line, then.
(let ((other nil))
(save-excursion
(when (and (zerop (forward-line 1))
(setq other (comment-search-forward
(line-end-position) t)))
(goto-char other) (setq other (current-column))))
(if (and other (<= other max) (> other min))
;; There is a comment and it's in the range: bingo.
(setq indent other))))))))
(setq indent (comment-choose-indent indent)))
;; Update INDENT to leave at least one space
;; after other nonwhite text on the line.
(save-excursion
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment