;;; tex-mode.el --- TeX, LaTeX, and SliTeX mode commands -*- coding: utf-8 -*-
-;; Copyright (C) 1985,86,89,92,94,95,96,97,98,1999,2002,2003
-;; Free Software Foundation, Inc.
+;; Copyright (C) 1985, 1986, 1989, 1992, 1994, 1995, 1996, 1997, 1998, 1999,
+;; 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
;; Maintainer: FSF
;; Keywords: tex
;; You should have received a copy of the GNU General Public License
;; along with GNU Emacs; see the file COPYING. If not, write to the
-;; Free Software Foundation, Inc., 59 Temple Place - Suite 330,
-;; Boston, MA 02111-1307, USA.
+;; Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+;; Boston, MA 02110-1301, USA.
;;; Commentary:
(require 'compile)
(defgroup tex-file nil
- "TeX files and directories"
+ "TeX files and directories."
:prefix "tex-"
:group 'tex)
(defgroup tex-run nil
- "Running external commands from TeX mode"
+ "Running external commands from TeX mode."
:prefix "tex-"
:group 'tex)
(defgroup tex-view nil
- "Viewing and printing TeX files"
+ "Viewing and printing TeX files."
:prefix "tex-"
:group 'tex)
If nil, TeX runs with no options. See the documentation of `tex-command'."
:type 'string
:group 'tex-run
- :version "21.4")
+ :version "22.1")
;;;###autoload
(defcustom tex-start-commands "\\nonstopmode\\input"
"\\nonstopmode\\input")
(string :tag "String at your choice"))
:group 'tex-run
- :version "21.4")
+ :version "22.1")
(defvar latex-standard-block-names
'("abstract" "array" "center" "description"
:group 'tex-view)
;;;###autoload
-(defcustom tex-dvi-view-command '(if (eq window-system 'x) "xdvi" "dvi2tty * | cat -s")
+(defcustom tex-dvi-view-command
+ '(cond
+ ((eq window-system 'x) "xdvi")
+ ((eq window-system 'w32) "yap")
+ (t "dvi2tty * | cat -s"))
"*Command used by \\[tex-view] to display a `.dvi' file.
If it is a string, that specifies the command directly.
If this string contains an asterisk (`*'), that is replaced by the file name;
'("input" "include" "includeonly" "bibliography"
"epsfig" "psfig" "epsf" "nofiles" "usepackage"
"documentstyle" "documentclass" "verbatiminput"
- "includegraphics" "includegraphics*")
+ "includegraphics" "includegraphics*"
+ "url" "nolinkurl")
t))
;; Miscellany.
(slash "\\\\")
;; (arg "\\(?:{\\(\\(?:[^{}\\]+\\|\\\\.\\|{[^}]*}\\)+\\)\\|\\\\[a-z*]+\\)"))
(arg "{\\(\\(?:[^{}\\]+\\|\\\\.\\|{[^}]*}\\)+\\)"))
(list
+ ;; font-lock-syntactic-keywords causes the \ of \end{verbatim} to be
+ ;; highlighted as tex-verbatim-face. Let's undo that.
+ ;; This is ugly and brittle :-( --Stef
+ '("^\\(\\\\\\)end" (1 (get-text-property (match-end 1) 'face) t))
;; display $$ math $$
;; We only mark the match between $$ and $$ because the $$ delimiters
;; themselves have already been marked (along with $..$) by syntactic
1 font-lock-function-name-face))))
"Subdued expressions to highlight in TeX modes.")
+(defun tex-font-lock-append-prop (prop)
+ (unless (memq (get-text-property (match-end 1) 'face)
+ '(font-lock-comment-face tex-verbatim-face))
+ prop))
+
(defconst tex-font-lock-keywords-2
(append tex-font-lock-keywords-1
(eval-when-compile
;;
;; Font environments. It seems a bit dubious to use `bold' etc. faces
;; since we might not be able to display those fonts.
- (list (concat slash bold " *" arg) 2 '(quote bold) 'append)
- (list (concat slash italic " *" arg) 2 '(quote italic) 'append)
+ (list (concat slash bold " *" arg) 2
+ '(tex-font-lock-append-prop 'bold) 'append)
+ (list (concat slash italic " *" arg) 2
+ '(tex-font-lock-append-prop 'italic) 'append)
;; (list (concat slash type arg) 2 '(quote bold-italic) 'append)
;;
;; Old-style bf/em/it/sl. Stop at `\\' and un-escaped `&', for tables.
(list (concat "\\\\\\(em\\|it\\|sl\\)\\>" args)
- 2 '(quote italic) 'append)
+ 2 '(tex-font-lock-append-prop 'italic) 'append)
;; This is separate from the previous one because of cases like
;; {\em foo {\bf bar} bla} where both match.
- (list (concat "\\\\bf\\>" args) 1 '(quote bold) 'append)))))
+ (list (concat "\\\\\\(bf\\(series\\)?\\)\\>" args)
+ 2 '(tex-font-lock-append-prop 'bold) 'append)))))
"Gaudy expressions to highlight in TeX modes.")
(defun tex-font-lock-suscript (pos)
;; degenerate to nasty complexity (because we try to match the
;; closing brace, which forces trying all matching combinations).
(arg "{\\(?:[^{}\\]\\|\\\\.\\|{[^}]*}\\)*"))
- `((,(concat "[_^] *\\([^\n\\{}]\\|" slash general "\\|" arg "}\\)")
+ `((,(concat "[_^] *\\([^\n\\{}#]\\|" slash general "\\|#[0-9]\\|" arg "}\\)")
(1 (tex-font-lock-suscript (match-beginning 0))
append))))))
"Experimental expressions to highlight in TeX modes.")
(defvar tex-font-lock-syntactic-keywords
(let ((verbs (regexp-opt tex-verbatim-environments t)))
`((,(concat "^\\\\begin *{" verbs "}.*\\(\n\\)") 2 "|")
- (,(concat "^\\\\end *{" verbs "}\\(.?\\)") 2
- (unless (<= (match-beginning 0) (point-min))
- (put-text-property (1- (match-beginning 0)) (match-beginning 0)
- 'syntax-table (string-to-syntax "|"))
- "<"))
+ ;; Technically, we'd like to put the "|" property on the \n preceding
+ ;; the \end, but this would have 2 disadvantages:
+ ;; 1 - it's wrong if the verbatim env is empty (the same \n is used to
+ ;; start and end the fenced-string).
+ ;; 2 - font-lock considers the preceding \n as being part of the
+ ;; preceding line, so things gets screwed every time the previous
+ ;; line is re-font-locked on its own.
+ ;; There's a hack in tex-font-lock-keywords-1 to remove the verbatim
+ ;; face from the \ but C-M-f still jumps to the wrong spot :-( --Stef
+ (,(concat "^\\(\\\\\\)end *{" verbs "}\\(.?\\)") (1 "|") (3 "<"))
;; ("^\\(\\\\\\)begin *{comment}" 1 "< b")
;; ("^\\\\end *{comment}.*\\(\n\\)" 1 "> b")
("\\\\verb\\**\\([^a-z@*]\\)" 1 "\""))))
(defface superscript
'((t :height 0.8)) ;; :raise 0.3
- "Face used for superscripts.")
+ "Face used for superscripts."
+ :group 'tex)
(defface subscript
'((t :height 0.8)) ;; :raise -0.3
- "Face used for subscripts.")
+ "Face used for subscripts."
+ :group 'tex)
-(defface tex-math-face
+(defface tex-math
'((t :inherit font-lock-string-face))
- "Face used to highlight TeX math expressions.")
-(defvar tex-math-face 'tex-math-face)
-(defface tex-verbatim-face
+ "Face used to highlight TeX math expressions."
+ :group 'tex)
+;; backward-compatibility alias
+(put 'tex-math-face 'face-alias 'tex-math)
+(defvar tex-math-face 'tex-math)
+
+(defface tex-verbatim
;; '((t :inherit font-lock-string-face))
'((t :family "courier"))
- "Face used to highlight TeX verbatim environments.")
-(defvar tex-verbatim-face 'tex-verbatim-face)
+ "Face used to highlight TeX verbatim environments."
+ :group 'tex)
+;; backward-compatibility alias
+(put 'tex-verbatim-face 'face-alias 'tex-verbatim)
+(defvar tex-verbatim-face 'tex-verbatim)
;; Use string syntax but math face for $...$.
(defun tex-font-lock-syntactic-face-function (state)
(regexp-opt '("documentstyle" "documentclass"
"begin" "subsection" "section"
"part" "chapter" "newcommand"
- "renewcommand") 'words)
+ "renewcommand" "RequirePackage") 'words)
"\\|NeedsTeXFormat{LaTeX")))
- (if (looking-at
- "document\\(style\\|class\\)\\(\\[.*\\]\\)?{slides}")
+ (if (and (looking-at
+ "document\\(style\\|class\\)\\(\\[.*\\]\\)?{slides}")
+ ;; SliTeX is almost never used any more nowadays.
+ (tex-executable-exists-p slitex-run-command))
'slitex-mode
'latex-mode)
'plain-tex-mode))))
(tex-mode-internal)
(tex-guess-mode)))
+;; The following three autoloaded aliases appear to conflict with
+;; AUCTeX. However, even though AUCTeX uses the mixed case variants
+;; for all mode relevant variables and hooks, the invocation function
+;; and setting of `major-mode' themselves need to be lowercase for
+;; AUCTeX to provide a fully functional user-level replacement. So
+;; these aliases should remain as they are, in particular since AUCTeX
+;; users are likely to use them.
+
;;;###autoload
(defalias 'TeX-mode 'tex-mode)
;;;###autoload
'tex-categorize-whitespace)
(set (make-local-variable 'facemenu-add-face-function)
(lambda (face end)
- (let ((face-text (cdr (assq face tex-face-alist))))
- (if face-text
- face-text
- (error "Face %s not configured for %s mode" face mode-name)))))
+ (or (cdr (assq face tex-face-alist))
+ (error "Face %s not configured for %s mode" face mode-name))))
(set (make-local-variable 'facemenu-end-add-face) "}")
(set (make-local-variable 'facemenu-remove-face-function) t)
(set (make-local-variable 'font-lock-defaults)
inserts \" characters."
(interactive "*P")
(if (or arg (memq (char-syntax (preceding-char)) '(?/ ?\\))
- (eq (get-text-property (point) 'face) 'tex-verbatim-face)
+ (eq (get-text-property (point) 'face) tex-verbatim-face)
(save-excursion
(backward-char (length tex-open-quote))
(when (or (looking-at (regexp-quote tex-open-quote))
(delete-char (length tex-open-quote))
t)))
(self-insert-command (prefix-numeric-value arg))
- (insert (if (memq (char-syntax (preceding-char)) '(?\( ?> ?\ ))
+ (insert (if (memq (char-syntax (preceding-char)) '(?\( ?> ?\s))
tex-open-quote tex-close-quote))))
(defun tex-validate-buffer ()
'occur-target tem)))))
(goto-char prev-end))))
(with-current-buffer standard-output
- (if (eq num-matches 0)
- (insert "None!\n"))
- (if (interactive-p)
- (message "%d mismatches found" num-matches))))))
+ (let ((no-matches (zerop num-matches)))
+ (if no-matches
+ (insert "None!\n"))
+ (if (interactive-p)
+ (message (cond (no-matches "No mismatches found")
+ ((= num-matches 1) "1 mismatch found")
+ (t "%d mismatches found"))
+ num-matches)))))))
(defun tex-validate-region (start end)
"Check for mismatched braces or $'s in region.
(forward-sexp 1))
;; Now check that like matches like.
(goto-char start)
- (while (progn (skip-syntax-forward "^(")
- (not (eobp)))
- (let ((match (matching-paren (following-char))))
- (save-excursion
+ (while (re-search-forward "\\s(" nil t)
+ (save-excursion
+ (let ((pos (match-beginning 0)))
+ (goto-char pos)
(forward-sexp 1)
- (or (= (preceding-char) match)
- (error "Mismatched parentheses"))))
- (forward-char 1)))
+ (or (eq (preceding-char) (cdr (syntax-after pos)))
+ (eq (char-after pos) (cdr (syntax-after (1- (point)))))
+ (error "Mismatched parentheses"))))))
(error
(skip-syntax-forward " .>")
(setq failure-point (point)))))
(defvar latex-block-default "enumerate")
(defvar latex-block-args-alist
- '(("array" nil ?\{ (skeleton-read "[options]: ") ?\})
- ("tabular" nil ?\{ (skeleton-read "[options]: ") ?\}))
+ '(("array" nil ?\{ (skeleton-read "Format: ") ?\})
+ ("tabular" nil ?\{ (skeleton-read "Format: ") ?\})
+ ("minipage" nil ?\{ (skeleton-read "Size: ") ?\})
+ ("picture" nil ?\( (skeleton-read "SizeX,SizeY: ") ?\))
+ ;; FIXME: This is right for Prosper, but not for seminar.
+ ;; ("slide" nil ?\{ (skeleton-read "Title: ") ?\})
+ )
"Skeleton element to use for arguments to particular environments.
Every element of the list has the form (NAME . SKEL-ELEM) where NAME is
the name of the environment and SKEL-ELEM is an element to use in
(defvar latex-block-body-alist
'(("enumerate" nil '(latex-insert-item) > _)
("itemize" nil '(latex-insert-item) > _)
- ("table" nil "\\caption{" > - "}" > \n _)
- ("figure" nil > _ \n "\\caption{" > _ "}" >))
+ ("table" nil "\\caption{" > (skeleton-read "Caption: ") "}" > \n
+ '(if (and (boundp 'reftex-mode) reftex-mode) (reftex-label "table"))
+ \n _)
+ ("figure" nil > _ \n "\\caption{" > (skeleton-read "Caption: ") "}" > \n
+ '(if (and (boundp 'reftex-mode) reftex-mode) (reftex-label "table"))))
"Skeleton element to use for the body of particular environments.
Every element of the list has the form (NAME . SKEL-ELEM) where NAME is
the name of the environment and SKEL-ELEM is an element to use in
choice)
\n "\\begin{" str "}"
(cdr (assoc str latex-block-args-alist))
- > \n (or (cdr (assoc str latex-block-body-alist)) '(nil > _)) \n
+ > \n (or (cdr (assoc str latex-block-body-alist)) '(nil > _))
+ (unless (bolp) '\n)
"\\end{" str "}" > \n)
(define-skeleton latex-insert-item
(when (eq (char-after) ?{)
(let ((newpos (point)))
(when (ignore-errors (backward-sexp 1) t)
- (if (looking-at "\\\\end\\>")
+ (if (or (looking-at "\\\\end\\>")
+ ;; In case the \\ ends a verbatim section.
+ (and (looking-at "end\\>") (eq (char-before) ?\\)))
(tex-last-unended-begin)
(goto-char newpos))))))))
;; The utility functions:
(define-derived-mode tex-shell shell-mode "TeX-Shell"
+ (set (make-local-variable 'compilation-parse-errors-function)
+ 'tex-compilation-parse-errors)
(compilation-shell-minor-mode t))
;;;###autoload
(make-comint
"tex-shell"
(or tex-shell-file-name (getenv "ESHELL") shell-file-name)
- nil)
+ nil
+ ;; Specify an interactive shell, to make sure it prompts.
+ "-i")
(let ((proc (get-process "tex-shell")))
(set-process-sentinel proc 'tex-shell-sentinel)
- (process-kill-without-query proc)
+ (set-process-query-on-exit-flag proc nil)
(tex-shell)
(while (zerop (buffer-size))
(sleep-for 1)))))
(concat
(if file
(if star (concat (substring cmd 0 star)
- file (substring cmd (1+ star)))
- (concat cmd " " file))
+ (shell-quote-argument file)
+ (substring cmd (1+ star)))
+ (concat cmd " " (shell-quote-argument file)))
cmd)
(if background "&" ""))))
;; Switch to buffer before checking for subproc output in it.
(defcustom tex-use-reftex t
"If non-nil, use RefTeX's list of files to determine what command to use."
- :type 'boolean)
+ :type 'boolean
+ :group 'tex)
(defvar tex-compile-commands
'(((concat "pdf" tex-command
" " (if (< 0 (length tex-start-commands))
(shell-quote-argument tex-start-commands)) " %f")
t "%r.dvi")
- ("yap %r &" "%r.dvi")
("xdvi %r &" "%r.dvi")
+ ("xpdf %r.pdf &" "%r.pdf")
+ ("gv %r.ps &" "%r.ps")
+ ("yap %r &" "%r.dvi")
("advi %r &" "%r.dvi")
+ ("gv %r.pdf &" "%r.pdf")
("bibtex %r" "%r.aux" "%r.bbl")
("makeindex %r" "%r.idx" "%r.ind")
("texindex %r.??")
("dvipdfm %r" "%r.dvi" "%r.pdf")
("dvipdf %r" "%r.dvi" "%r.pdf")
- ("dvips %r" "%r.dvi" "%r.ps")
+ ("dvips -o %r.ps %r" "%r.dvi" "%r.ps")
("ps2pdf %r.ps" "%r.ps" "%r.pdf")
- ("gv %r.ps &" "%r.ps")
- ("gv %r.pdf &" "%r.pdf")
- ("xpdf %r.pdf &" "%r.pdf")
("lpr %r.ps" "%r.ps"))
"List of commands for `tex-compile'.
Each element should be of the form (FORMAT IN OUT) where
(let* ((file (or tex-main-file
;; Compatibility with AUCTeX.
(with-no-warnings
- (when (and (boundp 'TeX-master) (stringp TeX-master))
- (make-local-variable 'tex-main-file)
- (setq tex-main-file TeX-master)))
+ (when (boundp 'TeX-master)
+ (cond ((stringp TeX-master)
+ (make-local-variable 'tex-main-file)
+ (setq tex-main-file TeX-master))
+ ((and (eq TeX-master t) buffer-file-name)
+ (file-relative-name buffer-file-name)))))
;; Try to guess the main file.
(if (not buffer-file-name)
(error "Buffer is not associated with any file")
(when (file-newer-than-file-p f file)
(setq uptodate nil)))))
uptodate)))
-
+
(autoload 'format-spec "format-spec")
(not (tex-uptodate-p (format-spec out fspec)))))))
(defun tex-compile-default (fspec)
- "Guess a default command given the format-spec FSPEC."
+ "Guess a default command given the `format-spec' FSPEC."
;; TODO: Learn to do latex+dvips!
(let ((cmds nil)
(unchanged-in nil))
(if (tex-command-active-p cmd fspec)
(push cmd cmds)
(push (nth 1 cmd) unchanged-in))))
+ ;; If no command seems to be applicable, arbitrarily pick the first one.
+ (setq cmds (if cmds (nreverse cmds) (list (car tex-compile-commands))))
;; Remove those commands whose input was considered stable for
;; some other command (typically if (t . "%.pdf") is inactive
;; then we're using pdflatex and the fact that the dvi file
(unless (member (nth 1 cmd) unchanged-in)
(push cmd tmp)))
;; Only remove if there's something left.
- (if tmp (setq cmds tmp)))
+ (if tmp (setq cmds (nreverse tmp))))
;; Remove commands whose input is not uptodate either.
(let ((outs (delq nil (mapcar (lambda (x) (nth 2 x)) cmds)))
(tmp nil))
(unless (member (nth 1 cmd) outs)
(push cmd tmp)))
;; Only remove if there's something left.
- (if tmp (setq cmds tmp)))
+ (if tmp (setq cmds (nreverse tmp))))
;; Select which file we're going to operate on (the latest).
(let ((latest (nth 1 (car cmds))))
(dolist (cmd (prog1 (cdr cmds) (setq cmds (list (car cmds)))))
(prog1 (file-name-directory (expand-file-name file))
(setq file (file-name-nondirectory file))))
(root (file-name-sans-extension file))
- (fspec (list (cons ?r (comint-quote-filename root))
- (cons ?f (comint-quote-filename file))))
+ (fspec (list (cons ?r (shell-quote-argument root))
+ (cons ?f (shell-quote-argument file))))
(default (tex-compile-default fspec)))
(list default-directory
(completing-read
(compile-command
(if star
(concat (substring command 0 star)
- (comint-quote-filename file)
+ (shell-quote-argument file)
(substring command (1+ star)))
(concat command " "
tex-start-options
(if (< 0 (length tex-start-commands))
(concat
(shell-quote-argument tex-start-commands) " "))
- (comint-quote-filename file)))))
+ (shell-quote-argument file)))))
(tex-send-tex-command compile-command dir)))
(defun tex-send-tex-command (cmd &optional dir)
default-directory))))
(not dir))
(let (shell-dirtrack-verbose)
- (tex-send-command tex-shell-cd-command dir)))
+ (tex-send-command tex-shell-cd-command
+ (concat "\"" (convert-standard-filename dir) "\""))))
(with-current-buffer (process-buffer (tex-send-command cmd))
- (make-local-variable 'compilation-parse-errors-function)
- (setq compilation-parse-errors-function 'tex-compilation-parse-errors)
(setq compilation-last-buffer (current-buffer))
(compilation-forget-errors)
;; Don't parse previous compilations.
for the error messages."
(require 'thingatpt)
(setq compilation-error-list nil)
- (message "Parsing error messages...")
(let ((default-directory ; Perhaps dir has changed meanwhile.
(file-name-directory (buffer-file-name tex-last-buffer-texed)))
found-desired (num-errors-found 0)
end-of-error (match-end 0)))
(re-search-forward
"^l\\.\\([0-9]+\\) \\(\\.\\.\\.\\)?\\(.*\\)$" nil 'move))
- (let* ((this-error (set-marker (make-marker) begin-of-error))
- (linenum (string-to-int (match-string 1)))
+ (let* ((this-error (copy-marker begin-of-error))
+ (linenum (string-to-number (match-string 1)))
(error-text (regexp-quote (match-string 3)))
(filename
(save-excursion
(or (null last-filename)
(not (string-equal last-filename filename))))
(error-location
- (save-excursion
- (if (equal filename (concat tex-zap-file ".tex"))
- (set-buffer tex-last-buffer-texed)
- (set-buffer (find-file-noselect filename)))
- (if new-file
- (progn (goto-line linenum) (setq last-position nil))
- (goto-char last-position)
- (forward-line (- linenum last-linenum)))
- ;; first try a forward search for the error text,
- ;; then a backward search limited by the last error.
- (let ((starting-point (point)))
- (or (re-search-forward error-text nil t)
- (re-search-backward error-text last-position t)
- (goto-char starting-point)))
- (point-marker))))
+ (with-current-buffer
+ (if (equal filename (concat tex-zap-file ".tex"))
+ tex-last-buffer-texed
+ (find-file-noselect filename))
+ (save-excursion
+ (if new-file
+ (progn (goto-line linenum) (setq last-position nil))
+ (goto-char last-position)
+ (forward-line (- linenum last-linenum)))
+ ;; first try a forward search for the error text,
+ ;; then a backward search limited by the last error.
+ (let ((starting-point (point)))
+ (or (re-search-forward error-text nil t)
+ (re-search-backward error-text last-position t)
+ (goto-char starting-point)))
+ (point-marker)))))
(goto-char this-error)
(if (and compilation-error-list
(or (and find-at-least
compilation-error-list))
(goto-char end-of-error)))))
(set-marker compilation-parsing-end (point))
- (setq compilation-error-list (nreverse compilation-error-list))
- (message "Parsing error messages...done"))
+ (setq compilation-error-list (nreverse compilation-error-list)))
\f
;;; The commands:
(tex-start-shell))
(tex-send-command
(if alt tex-alt-dvi-print-command tex-dvi-print-command)
- (shell-quote-argument
- print-file-name-dvi)
+ print-file-name-dvi
t))))
(defun tex-alt-print ()
(interactive)
(or tex-dvi-view-command
(error "You must set `tex-dvi-view-command'"))
+ ;; Restart the TeX shell if necessary.
+ (or (tex-shell-running)
+ (tex-start-shell))
(let ((tex-dvi-print-command (eval tex-dvi-view-command)))
(tex-print)))
(tex-out-file
(tex-append (file-name-nondirectory (buffer-file-name)) ""))
(file-dir (file-name-directory (buffer-file-name))))
- (tex-send-command tex-shell-cd-command file-dir)
+ (tex-send-command tex-shell-cd-command
+ (concat "\"" (convert-standard-filename file-dir) "\""))
(tex-send-command tex-bibtex-command tex-out-file))
(tex-display-shell))
\f
(defvar tex-indent-basic 2)
(defvar tex-indent-item tex-indent-basic)
(defvar tex-indent-item-re "\\\\\\(bib\\)?item\\>")
+(defvar latex-noindent-environments '("document"))
(defvar tex-latex-indent-syntax-table
(let ((st (make-syntax-table tex-mode-syntax-table)))
(latex-find-indent 'virtual))))
;; Default (maybe an argument)
(let ((pos (point))
- (char (char-after))
;; Outdent \item if necessary.
(indent (if (looking-at tex-indent-item-re) (- tex-indent-item) 0))
up-list-pos)
;; Have to indent relative to the open-paren.
(goto-char up-list-pos)
(if (and (not tex-indent-allhanging)
+ (save-excursion
+ ;; Make sure we're an argument to a macro and
+ ;; that the macro is at the beginning of a line.
+ (condition-case nil
+ (progn
+ (while (eq (char-syntax (char-after)) ?\()
+ (forward-sexp -1))
+ (and (eq (char-syntax (char-after)) ?/)
+ (progn (skip-chars-backward " \t&")
+ (bolp))))
+ (scan-error nil)))
(> pos (progn (latex-down-list)
(forward-comment (point-max))
(point))))
(current-column)
;; We're the first element after a hanging brace.
(goto-char up-list-pos)
- (+ indent tex-indent-basic (latex-find-indent 'virtual))))
+ (+ (if (and (looking-at "\\\\begin *{\\([^\n}]+\\)")
+ (member (match-string 1)
+ latex-noindent-environments))
+ 0 tex-indent-basic)
+ indent (latex-find-indent 'virtual))))
;; We're now at the "beginning" of a line.
((not (and (not virtual) (eq (char-after) ?\\)))
;; Nothing particular here: just keep the same indentation.
(+ indent (current-column)))
;; We're now looking at a macro call.
- ((looking-at tex-indent-item-re)
- ;; Indenting relative to an item, have to re-add the outdenting.
+ ((looking-at tex-indent-item-re)
+ ;; Indenting relative to an item, have to re-add the outdenting.
(+ indent (current-column) tex-indent-item))
(t
(let ((col (current-column)))
- (if (not (eq (char-syntax char) ?\())
+ (if (or (not (eq (char-syntax (or (char-after pos) ?\s)) ?\())
+ ;; Can't be an arg if there's an empty line inbetween.
+ (save-excursion (re-search-forward "^[ \t]*$" pos t)))
;; If the first char was not an open-paren, there's
;; a risk that this is really not an argument to the
;; macro at all.
- (+ indent col)
- (forward-sexp 1)
- (if (< (line-end-position)
- (save-excursion (forward-comment (point-max))
- (point)))
+ (+ indent col)
+ (forward-sexp 1)
+ (if (< (line-end-position)
+ (save-excursion (forward-comment (point-max))
+ (point)))
;; we're indenting the first argument.
(min (current-column) (+ tex-indent-arg col))
(skip-syntax-forward " ")
(provide 'tex-mode)
-;;; arch-tag: c0a680b1-63aa-4547-84b9-4193c29c0080
+;; arch-tag: c0a680b1-63aa-4547-84b9-4193c29c0080
;;; tex-mode.el ends here