diff --git a/tex-buf.el b/tex-buf.el index 510722cb..fa8f1a69 100644 --- a/tex-buf.el +++ b/tex-buf.el @@ -82,7 +82,7 @@ Return non-nil if document needs to be re-TeX'ed." (if (string-equal name "") (setq name (TeX-master-file))) - (TeX-check-files (concat name "." (TeX-output-extension)) + (TeX-check-files (concat name "." (TeX-output-extension)) ;; TODO: This might need changing when TeX-output-dir is set (cons name (TeX-style-list)) TeX-file-extensions)) @@ -826,7 +826,7 @@ omitted) and `TeX-region-file'." ;; comparison. (if (string-equal (expand-file-name name) (expand-file-name (TeX-region-file))) - (TeX-check-files (concat name "." (TeX-output-extension)) + (TeX-check-files (concat name "." (TeX-output-extension)) ;; TODO: This might need changing when TeX-output-dir is set ;; Each original will be checked for all dirs ;; in `TeX-check-path' so this needs to be just ;; a filename without directory. @@ -1093,12 +1093,12 @@ requires special treatment." :group 'TeX-command :type 'boolean) -(defun TeX-run-command (name command file) +(defun TeX-run-command (name command file &optional dir-for-extension) "Create a process for NAME using COMMAND to process FILE. Return the new process." (let ((default TeX-command-default) (buffer (TeX-process-buffer-name file)) - (dir (TeX-master-directory)) + (dir (TeX-master-directory dir-for-extension)) (command-buff (current-buffer))) (TeX-process-check file) ; Check that no process is running (setq-default TeX-command-buffer command-buff) @@ -1232,7 +1232,7 @@ run of `TeX-run-TeX', use (defun TeX-run-BibTeX (name command file) "Create a process for NAME using COMMAND to format FILE with BibTeX." - (let ((process (TeX-run-command name command file))) + (let ((process (TeX-run-command name command file "aux"))) (setq TeX-sentinel-function #'TeX-BibTeX-sentinel) (if TeX-process-asynchronous process @@ -2290,7 +2290,11 @@ The compatibility argument IGNORE is ignored." (cond ((eq extension t) (concat TeX-region "." TeX-default-extension)) (extension - (concat TeX-region "." extension)) + (if (and TeX-output-dir + (when-let (reg (TeX--clean-extensions-regexp t)) + (string-match-p reg (concat "." extension)))) + (concat TeX-output-dir "/" TeX-region "." extension) + (concat TeX-region "." extension))) (t TeX-region)))) diff --git a/tex.el b/tex.el index b2bbbbf7..e90035d1 100644 --- a/tex.el +++ b/tex.el @@ -188,7 +188,7 @@ If nil, none is specified." ;; `TeX-expand-list-builtin' for a description of the % escapes (defcustom TeX-command-list - '(("TeX" "%(PDF)%(tex) %(file-line-error) %`%(extraopts) %S%(PDFout)%(mode)%' %t" + '(("TeX" "%(PDF)%(tex) %(file-line-error) %`%(extraopts) %(output-dir) %S%(PDFout)%(mode)%' %t" TeX-run-TeX nil (plain-tex-mode ams-tex-mode texinfo-mode) :help "Run plain TeX") ("LaTeX" "%`%l%(mode)%' %T" @@ -212,7 +212,7 @@ If nil, none is specified." (plain-tex-mode latex-mode doctex-mode ams-tex-mode texinfo-mode context-mode) :help "Run BibTeX") - ("Biber" "biber %s" TeX-run-Biber nil + ("Biber" "biber %s %(output-dir)" TeX-run-Biber nil (plain-tex-mode latex-mode doctex-mode ams-tex-mode texinfo-mode) :help "Run Biber") ("View" "%V" TeX-run-discard-or-function t t :help "Run Viewer") @@ -399,7 +399,7 @@ The executable `latex' is LaTeX version 2e." (defcustom LaTeX-command-style ;; They have all been combined in LaTeX 2e. - '(("" "%(PDF)%(latex) %(file-line-error) %(extraopts) %S%(PDFout)")) + '(("" "%(PDF)%(latex) %(file-line-error) %(extraopts) %(output-dir) %S%(PDFout)")) "List of style options and LaTeX commands. If the first element (a regular expression) matches the name of one of @@ -566,6 +566,10 @@ string." ("%(cntxcom)" ConTeXt-expand-command) ("%(execopts)" ConTeXt-expand-options) ("%(extraopts)" (lambda () TeX-command-extra-options)) + ("%(output-dir)" (lambda () (if (not TeX-output-dir) "" + (unless (file-exists-p TeX-output-dir) + (make-directory TeX-output-dir)) + (concat "--output-directory=\"" TeX-output-dir "\"")))) ("%S" TeX-source-correlate-expand-options) ("%dS" TeX-source-specials-view-expand-options) ("%cS" TeX-source-specials-view-expand-client) @@ -1237,7 +1241,7 @@ entry in `TeX-view-program-list-builtin'." (get-file-buffer (TeX-region-file t))) (current-buffer)) (pdf-sync-forward-search)) - (let ((pdf (concat file "." (TeX-output-extension)))) + (let ((pdf (TeX-active-master (TeX-output-extension)))) (pop-to-buffer (or (find-buffer-visiting pdf) (find-file-noselect pdf)))))) @@ -1261,7 +1265,7 @@ viewer." (require 'url-util) (let* ((uri (concat "file://" (url-encode-url (expand-file-name - (concat file "." (TeX-output-extension)))))) + (TeX-active-master (TeX-output-extension)))))) (owner (dbus-call-method :session (format "org.%s.%s.Daemon" de app) (format "/org/%s/%s/Daemon" de app) @@ -2279,25 +2283,19 @@ Used as a default in TeX, LaTeX and docTeX mode.") If prefix ARG is non-nil, not only remove intermediate but also output files." (interactive "P") - (let* ((mode-prefix (TeX-mode-prefix)) - (suffixes (append (symbol-value - (intern (concat mode-prefix - "-clean-intermediate-suffixes"))) - (when arg - (symbol-value - (intern (concat mode-prefix - "-clean-output-suffixes")))))) - (master (TeX-active-master)) + (let* (;; Add output extension then remove it, to make sure we get the correct + ;; directory in cases TeX-output-dir is non-nil + (master (file-name-sans-extension (TeX-active-master (TeX-output-extension)))) (master-dir (file-name-directory master)) (regexp (concat "\\(" (regexp-quote (file-name-nondirectory master)) "\\|" (regexp-quote (TeX-region-file nil t)) "\\)" "\\(" - (mapconcat 'identity suffixes "\\|") + (TeX--clean-extensions-regexp arg) "\\)\\'" "\\|" (regexp-quote (TeX-region-file t t)))) - (files (when regexp + (files (when (and regexp (or (not master-dir) (file-exists-p master-dir))) (directory-files (or master-dir ".") nil regexp)))) (if files (when (or (not TeX-clean-confirm) @@ -2310,6 +2308,19 @@ output files." (delete-file (concat master-dir file)))) (message "No files to be deleted")))) +(defun TeX--clean-extensions-regexp (&optional arg) + "Returns a regexp to match extensions that should be cleaned by TeX-clean. +If the optional argument ARG is non-nil then output files are included" + (when-let ((mode-prefix (TeX-mode-prefix)) + (suffixes (append (symbol-value + (intern (concat mode-prefix + "-clean-intermediate-suffixes"))) + (when arg + (symbol-value + (intern (concat mode-prefix + "-clean-output-suffixes"))))))) + (mapconcat 'identity suffixes "\\|"))) + ;;; Master File (defcustom TeX-master t @@ -2403,6 +2414,25 @@ this variable to \"\"." 'path)) (TeX-add-local-master)))))) +(defun TeX-master-output-file (&optional extension) + "Returns an output file based on `TeX-output-dir' in the +master-file, opening it if necessary. if the optional argument +EXTENSION is non-nil it is appended as an extension to the output +file. If EXTENSION is t then (TeX-output-extension) is used." + (interactive) + (if (eq extension t) + (setq extension (TeX-output-extension))) + (let ((file (TeX-master-file t)) name) + (with-current-buffer + (or (find-buffer-visiting file) + (find-file-noselect file)) + (when TeX-output-dir + (setq name (concat TeX-output-dir "/" (TeX-master-file))))) + (if name + (if extension (concat name "." extension) + name) + (TeX-master-file extension)))) + (defun TeX-master-file (&optional extension nondirectory ask) "Set and return the name of the master file for the current document. @@ -2463,7 +2493,11 @@ name of master file if it cannot be determined otherwise." ;; Ask the user (but add it as a local variable). (ask (TeX-master-file-ask))))) - (let ((name (if (stringp TeX-master) + (if (and TeX-output-dir + (when-let (reg (TeX--clean-extensions-regexp t)) + (string-match-p reg (concat "." extension)))) + (TeX-master-output-file extension) + (let ((name (if (stringp TeX-master) TeX-master my-name))) @@ -2481,15 +2515,15 @@ name of master file if it cannot be determined otherwise." (if extension (concat name "." extension) - name)))) + name))))) -(defun TeX-master-directory () +(defun TeX-master-directory (&optional for-extension) "Directory of master file." (file-name-as-directory (abbreviate-file-name (substitute-in-file-name (expand-file-name - (let ((dir (file-name-directory (TeX-master-file)))) + (let ((dir (file-name-directory (TeX-master-file for-extension)))) (if dir (directory-file-name dir) ".")) (and buffer-file-name (file-name-directory buffer-file-name))))))) @@ -2563,6 +2597,16 @@ be relative to that." :group 'TeX-file :type 'string) +(defcustom TeX-output-dir nil + "The directory where the output files will be generated. The + directory cannot start with a `.'. + +If this variable is nil, AUCTeX will assume that the output +directory is the same as the directory of TeX-master." + :group 'TeX-file + :type '(string :format "%v")) +(put 'TeX-output-dir 'safe-local-variable 'stringp-or-null-p) + (defcustom TeX-style-local "style" "*Directory containing hand generated TeX information.