yatex

view yatexenv.el @ 583:d4831b3672f8

Add some html5 elements
author HIROSE Yuuji <yuuji@gentei.org>
date Thu, 01 Jul 2021 07:00:05 +0900
parents c0827f80b18e
children
line source
1 ;;; yatexenv.el --- YaTeX environment-specific functions
2 ;;; (c) 1994-2019 by HIROSE Yuuji.[yuuji@yatex.org]
3 ;;; Last modified Sat May 25 14:46:33 2019 on firestorm
4 ;;; $Id$
6 ;;; Code:
7 ;;;
8 ;; Functions for tabular environment
9 ;;;
11 ;; Showing the matching column of tabular environment.
12 (defun YaTeX-array-what-column-internal ()
13 "Return the cons of matching column and its title of array environment.
14 When calling from a program, make sure to be in array/tabular environment."
15 (let ((p (point)) bot beg eot bor eoll (nlptn "\\\\\\\\") (andptn "[^\\]&")
16 (n 0) j
17 (firsterr "This line might be the first row."))
18 (save-excursion
19 (YaTeX-beginning-of-environment)
20 (setq eoll (save-excursion ;end of logical line
21 (YaTeX-goto-corresponding-environment) (point)))
22 (search-forward "{" p) (up-list 1)
23 (search-forward "{" p) (up-list 1)
24 ;;(re-search-forward andptn p)
25 (setq bot (point)) ;beginning of tabular
26 (while (progn (search-forward "&" eoll)
27 (equal (char-after (1- (match-beginning 0))) ?\\ )))
28 (setq beg (1- (point))) ;beg is the point of the first &
29 (or (re-search-forward nlptn eoll t)
30 (error firsterr))
31 (setq eot (point)) ;eot is the point of the first \\
32 (goto-char p)
33 (setq bor (if (re-search-backward nlptn bot 1)
34 (point) ;bor is the beginning of this row.
35 bot))
36 (while (< (1- (point)) p)
37 (if (equal (following-char) ?&)
38 (forward-char 1)
39 (re-search-forward andptn nil 1))
40 (setq n (1+ n))) ;Check current column number
41 (goto-char p)
42 (cond ;Start searching \multicolumn{N}
43 ((> n 1)
44 (re-search-backward andptn) ;Sure to find!
45 (while (re-search-backward "\\\\multicolumn{\\([0-9]+\\)}" bor t)
46 (setq n (+ n (YaTeX-str2int
47 (buffer-substring (match-beginning 1)
48 (match-end 1)))
49 -1)))))
50 (message "%s" n)
51 (goto-char (1- beg))
52 (beginning-of-line)
53 (setq j n)
54 (while (> j 1)
55 (or (re-search-forward andptn p nil)
56 (error "This column exceeds the limit."))
57 (setq j (1- j)))
58 (skip-chars-forward "\\s ")
59 (list n
60 (YaTeX-buffer-substring
61 (progn (skip-chars-forward "\n \t") (point))
62 (progn
63 (re-search-forward (concat andptn "\\|" nlptn) eot)
64 (goto-char (match-beginning 0))
65 (if (looking-at andptn)
66 (forward-char 1))
67 (skip-chars-backward "\\s ")
68 (point)))))))
70 (defun YaTeX-array-what-column ()
71 "Show matching column title of array environment.
72 When calling from a program, make sure to be in array/tabular environment."
73 (apply 'message
74 "This is the column(#%d) of: %s"
75 (YaTeX-array-what-column-internal)))
77 ;;;###autoload
78 (defun YaTeX-what-column ()
79 "Show which kind of column the current position is belonging to."
80 (interactive)
81 (cond
82 ((YaTeX-quick-in-environment-p '("tabular" "tabular*" "array" "array*"))
83 (YaTeX-array-what-column))
84 (t (message "Not in array/tabular environment."))))
86 (defun YaTeX-tabular-parse-format-count-cols (beg end)
87 (goto-char beg)
88 (let (elt (cols 0))
89 (while (< (point) end)
90 (setq elt (following-char))
91 (cond
92 ((string-match (char-to-string elt) "clrX") ;normal indicators.
93 (setq cols (1+ cols))
94 (forward-char 1))
95 ((equal elt ?|) ;vertical
96 (forward-char 1))
97 ((string-match (char-to-string elt) "p@") ;p or @ expression
98 (setq cols (+ (if (eq elt ?p) 1 0) cols))
99 ;;(skip-chars-forward "^{" p)
100 (skip-chars-forward "^{" end)
101 (forward-list 1))
102 ((equal elt ?*) ;*{N}{EXP} -> Repeat EXP N times
103 (skip-chars-forward "^{" end)
104 (setq cols (* (YaTeX-str2int
105 (buffer-substring
106 (1+ (point))
107 (progn (forward-list 1) (1- (point)))))
108 (YaTeX-tabular-parse-format-count-cols
109 (progn (skip-chars-forward "^{" end) (1+ (point)))
110 (progn (forward-list 1) (1- (point)))))))
111 (t (forward-char 1)) ;unknown char
112 ))
113 cols))
115 (defun YaTeX-tabular-parse-format (&optional type)
116 "Parse `tabular' format.
117 Return the list of (No.ofCols PointEndofFormat)"
118 (let ((p (point)) boform eoform (cols 0))
119 (save-excursion
120 (if (null (YaTeX-beginning-of-environment t))
121 (error "Beginning of tabular not found."))
122 (skip-chars-forward "^{")
123 (forward-list 1)
124 (cond
125 ((eq type 'tabular*)
126 (skip-chars-forward "^{")
127 (forward-list 1)))
128 (skip-chars-forward "^{" p)
129 (if (/= (following-char) ?\{) (error "Tabular format not found."))
130 (setq boform (1+ (point))
131 eoform (progn (forward-list 1) (1- (point))))
132 (if (> eoform p) (error "Non-terminated tabular format."))
133 (goto-char boform)
134 (setq cols
135 (cond
136 ((eq type 'alignat)
137 (max
138 1
139 (* 2 (YaTeX-str2int
140 (buffer-substring
141 (point)
142 (progn (up-list -1) (forward-list 1) (1- (point))))))))
143 (t
144 (YaTeX-tabular-parse-format-count-cols (point) eoform))))
145 (list cols (1+ eoform)))))
147 ;; Insert &
148 (defun YaTeX-intelligent-newline-tabular (&optional type)
149 "Parse current tabular format and insert that many `&'s."
150 (let*((p (point)) (format (YaTeX-tabular-parse-format type))
151 (cols (car format)) (beg (car (cdr format)))
152 space hline)
153 (cond
154 ((search-backward "&" beg t)
155 (goto-char p)
156 (setq hline (search-backward "\\hline" beg t))
157 (setq space (if (search-backward "\t&" beg t) "\t" " "))
158 (goto-char p))
159 (t ;;(insert "\\hline\n")
160 (setq space " ")))
161 (goto-char p)
162 (while (> (1- cols) 0)
163 (insert "&" space)
164 (setq cols (1- cols)))
165 (insert "\\\\")
166 (if hline (insert " \\hline"))
167 (goto-char p)
168 (YaTeX-indent-line)))
170 (defun YaTeX-intelligent-newline-tabular* ()
171 "Parse current tabular* format and insert that many `&'s."
172 (YaTeX-intelligent-newline-tabular 'tabular*))
174 (fset 'YaTeX-intelligent-newline-array 'YaTeX-intelligent-newline-tabular)
175 (fset 'YaTeX-intelligent-newline-supertabular 'YaTeX-intelligent-newline-tabular)
176 (fset 'YaTeX-intelligent-newline-longtable 'YaTeX-intelligent-newline-tabular)
177 (fset 'YaTeX-intelligent-newline-tabularx 'YaTeX-intelligent-newline-tabular*)
179 (defun YaTeX-intelligent-newline-align ()
180 "Intelligent newline function for align.
181 Count the number of & in the first align line and insert that many &s."
182 (let*((p (point)) (amps 0))
183 (if (string-match "alignat" env)
184 (setq amps (1- (car (YaTeX-tabular-parse-format 'alignat))))
185 (save-excursion
186 (YaTeX-beginning-of-environment)
187 (catch 'done
188 (while (YaTeX-re-search-active-forward
189 "\\(&\\)\\|\\(\\\\\\\\\\)" YaTeX-comment-prefix p t)
190 (if (match-beginning 1) (setq amps (1+ amps)) (throw 'done t))))))
191 (save-excursion
192 (forward-line -1)
193 (skip-chars-forward " \t")
194 (or (prog1 (looking-at "\\\\begin{") (end-of-line))
195 (save-excursion
196 (skip-chars-backward " \t")
197 (and (= (preceding-char) ?\\) (= (char-after (- (point) 2)) ?\\)))
198 (insert "\\\\")))
199 (save-excursion
200 (while (>= (setq amps (1- amps)) 0)
201 (insert "& ")))
202 (YaTeX-indent-line)))
204 (mapcar
205 (function
206 (lambda (s)
207 (fset (intern (concat "YaTeX-intelligent-newline-"
208 (symbol-name s)))
209 'YaTeX-intelligent-newline-align)))
210 '(align* flalign flalign* matrix pmatrix bmatrix Bmatrix vmatrix Vmatrix
211 cases eqnarray eqnarray* alignat alignat*))
213 ;;;
214 ;; Functions for tabbing environment
215 ;;;
216 (defun YaTeX-intelligent-newline-tabbing ()
217 "Check the number of \\= in the first line and insert that many \\>."
218 (let ((p (point)) begenv tabcount)
219 (save-excursion
220 (YaTeX-beginning-of-environment)
221 (setq begenv (point-end-of-line))
222 (if (YaTeX-search-active-forward "\\\\" YaTeX-comment-prefix p t)
223 (progn
224 (setq tabcount 0)
225 (while (> (point) begenv)
226 (if (search-backward "\\=" begenv 1)
227 (setq tabcount (1+ tabcount)))))))
228 (YaTeX-indent-line)
229 (if tabcount
230 (progn
231 (save-excursion
232 (while (> tabcount 0)
233 (insert "\\>\t")
234 (setq tabcount (1- tabcount))))
235 (forward-char 2))
236 (insert "\\= \\\\")
237 (forward-char -5))))
239 ;;;
240 ;; Functions for itemize/enumerate/list environments
241 ;;;
243 (defun YaTeX-intelligent-newline-itemize ()
244 "Insert '\\item '."
245 (insert "\\item ")
246 (YaTeX-indent-line))
248 (fset 'YaTeX-intelligent-newline-enumerate 'YaTeX-intelligent-newline-itemize)
249 (fset 'YaTeX-intelligent-newline-list 'YaTeX-intelligent-newline-itemize)
251 (defun YaTeX-intelligent-newline-description ()
252 (insert "\\item[] ")
253 (forward-char -2)
254 (YaTeX-indent-line))
256 (defun YaTeX-intelligent-newline-thebibliography ()
257 "Insert '\\bibitem '."
258 (YaTeX-indent-line)
259 (YaTeX-make-section nil nil nil "bibitem")
260 (YaTeX-indent-line))
262 ;;;
263 ;; For document environment
264 ;;;
265 (defun YaTeX-intelligent-newline-document ()
266 "New paragraph by null line or `\\par'."
267 (if (< (count-lines
268 (or (get 'YaTeX-inner-environment 'point)
269 (max 1 (- (point) 17))) ;"\begin{document}\n" == 17
270 (point))
271 2)
272 nil
273 (if (save-excursion (re-search-backward "\\\\par\\>" nil t))
274 (progn
275 (YaTeX-indent-line)
276 (insert "\\par")))
277 (newline))
278 (YaTeX-indent-line))
280 ;;;
281 ;; Intelligent newline
282 ;;;
283 ;;;###autoload
284 (defun YaTeX-intelligent-newline (arg)
285 "Insert newline and environment-specific entry.
286 `\\item' for some itemizing environment,
287 `\\> \\> \\' for tabbing environemnt,
288 `& & \\ \hline' for tabular environment."
289 (interactive "P")
290 (let*(env func)
291 (end-of-line)
292 (setq env (YaTeX-inner-environment))
293 (if arg (setq env (YaTeX-read-environment "For what environment? ")))
294 (setq func (intern-soft (concat "YaTeX-intelligent-newline-" env)))
295 (end-of-line)
296 (newline)
297 (undo-boundary)
298 (if (and env func (fboundp func))
299 (funcall func))))
301 ;;;
302 ;; Environment-specific line indenting functions
303 ;;;
304 ;;;###autoload
305 (defun YaTeX-indent-line-equation ()
306 "Indent a line in equation family."
307 (let ((p (point)) (l-r 0) right-p peol depth (mp YaTeX-environment-indent))
308 (if (save-excursion
309 (beginning-of-line)
310 (skip-chars-forward " \t")
311 (looking-at "\\\\right\\b"))
312 (progn (YaTeX-reindent
313 (save-excursion (YaTeX-goto-corresponding-leftright)
314 (- (current-column) 0))))
315 (save-excursion
316 (forward-line -1)
317 (while (and (not (bobp)) (YaTeX-on-comment-p))
318 (forward-line -1))
319 ;;(beginning-of-line) ;must be unnecessary
320 (skip-chars-forward " \t")
321 (if (eolp) (error "Math-environment can't have a null line!!"))
322 (setq depth (current-column)
323 peol (point-end-of-line))
324 (while (re-search-forward
325 "\\\\\\(\\(left\\)\\|\\(right\\)\\)\\b" peol t)
326 (setq l-r (+ l-r (if (match-beginning 2) 1 -1))))
327 (cond
328 ((progn (beginning-of-line)
329 (re-search-forward "\\\\\\\\\\s *$" (point-end-of-line) t))
330 ;;If previous line has `\\', this indentation is always normal.
331 (setq depth (+ (YaTeX-current-indentation) mp)))
332 ((> l-r 0)
333 (beginning-of-line)
334 (search-forward "\\left" peol nil l-r)
335 (goto-char (1+ (match-beginning 0)))
336 (setq depth (current-column)))
337 ((< l-r 0)
338 (goto-char (match-beginning 0)) ;should be \right
339 (YaTeX-goto-corresponding-leftright)
340 (beginning-of-line)
341 (skip-chars-forward " \t")
342 ;(setq depth (+ (current-column) mp)) ;+mp is good?
343 (setq depth (current-column)))
344 (t ;if \left - \right = 0
345 (cond
346 ((re-search-forward "\\\\\\\\\\s *$" peol t)
347 (setq depth (+ (YaTeX-current-indentation) mp)))
348 ((re-search-forward "\\\\end{" peol t)
349 nil) ;same indentation as previous line's
350 ((re-search-forward "\\\\begin{" peol t)
351 (setq depth (+ depth mp)))
352 (t
353 (or (bobp) (forward-line -1))
354 (cond
355 ((re-search-forward
356 "\\\\\\\\\\s *$\\|\\\\begin{" (point-end-of-line) t)
357 (setq depth (+ depth mp)))
358 )))))
359 (goto-char p))
360 (YaTeX-reindent depth))))
362 ;;;###autoload
363 (defun YaTeX-goto-corresponding-leftright ()
364 "Go to corresponding \left or \right."
365 (let ((YaTeX-struct-begin "\\left%1")
366 (YaTeX-struct-end "\\right%1")
367 (YaTeX-struct-name-regexp "[][(){}\\.|]")
368 (in-leftright-p t))
369 (YaTeX-goto-corresponding-environment t)))
371 ;;;
372 ;; Functions for formatting region being enclosed with environment
373 ;;;
374 ; These functions must take two argument; region-beginning, region-end.
376 (defun YaTeX-enclose-equation (beg end)
377 (goto-char beg)
378 (save-restriction
379 (let (m0 bsl)
380 (narrow-to-region beg end)
381 (while (YaTeX-re-search-active-forward
382 "\\(\\$\\)" YaTeX-comment-prefix nil t)
383 (goto-char (setq m0 (match-beginning 0)))
384 (setq bsl 0)
385 (if (and (not (bobp)) (= (char-after (1- (point))) ?\\ ))
386 (while (progn (forward-char -1) (= (char-after (point)) ?\\ ))
387 (setq bsl (1+ bsl))))
388 (goto-char m0)
389 (if (= 0 (% bsl 2))
390 (delete-char 1)
391 (forward-char 1))))))
393 (fset 'YaTeX-enclose-eqnarray 'YaTeX-enclose-equation)
394 (fset 'YaTeX-enclose-eqnarray* 'YaTeX-enclose-equation)
395 (mapcar (function ;; Add all AMS LaTeX envs
396 (lambda (sym)
397 (fset (intern (concat "YaTeX-enclose-" (car sym)))
398 'YaTeX-enclose-equation)))
399 YaTeX-ams-math-begin-alist)
401 (defun YaTeX-enclose-verbatim (beg end)) ;do nothing when enclose verbatim
402 (fset 'YaTeX-enclose-verbatim* 'YaTeX-enclose-verbatim)
404 (provide 'yatexenv)