Merge branch 'maint'
[org-mode.git] / testing / lisp / test-org-table.el
blob16edb264d4293d0d69e7c69ae1903de534849dc0
1 ;;; test-org-table.el --- tests for org-table.el
3 ;; Copyright (c) David Maus
4 ;; Authors: David Maus, Michael Brand
6 ;; This file is not part of GNU Emacs.
8 ;; This program is free software; you can redistribute it and/or modify
9 ;; it under the terms of the GNU General Public License as published by
10 ;; the Free Software Foundation, either version 3 of the License, or
11 ;; (at your option) any later version.
13 ;; This program is distributed in the hope that it will be useful,
14 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
15 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 ;; GNU General Public License for more details.
18 ;; You should have received a copy of the GNU General Public License
19 ;; along with this program. If not, see <http://www.gnu.org/licenses/>.
21 ;;;; Comments:
23 ;; Template test file for Org tests. Many tests are also a howto
24 ;; example collection as a user documentation, more or less all those
25 ;; using `org-test-table-target-expect'. See also the doc string of
26 ;; `org-test-table-target-expect'.
28 ;;; Code:
30 (require 'org-table) ; `org-table-make-reference'
32 (ert-deftest test-org-table/simple-formula/no-grouping/no-title-row ()
33 "Simple sum without grouping rows, without title row."
34 (org-test-table-target-expect
36 | 2 |
37 | 4 |
38 | 8 |
39 | replace |
42 | 2 |
43 | 4 |
44 | 8 |
45 | 14 |
48 ;; Calc formula
49 "#+TBLFM: @>$1 = vsum(@<..@>>)"
50 ;; Lisp formula
51 "#+TBLFM: @>$1 = '(+ @<..@>>); N"))
53 (ert-deftest test-org-table/simple-formula/no-grouping/with-title-row ()
54 "Simple sum without grouping rows, with title row."
55 (org-test-table-target-expect
57 | foo |
58 |---------|
59 | 2 |
60 | 4 |
61 | 8 |
62 | replace |
65 | foo |
66 |-----|
67 | 2 |
68 | 4 |
69 | 8 |
70 | 14 |
73 ;; Calc formula
74 "#+TBLFM: @>$1 = vsum(@I..@>>)"
75 ;; Lisp formula
76 "#+TBLFM: @>$1 = '(+ @I..@>>); N"))
78 (ert-deftest test-org-table/simple-formula/with-grouping/no-title-row ()
79 "Simple sum with grouping rows, how not to do."
80 ;; The first example has a problem, see the second example in this
81 ;; ert-deftest.
82 (org-test-table-target-expect
84 | 2 |
85 | 4 |
86 | 8 |
87 |---------|
88 | replace |
91 | 2 |
92 | 4 |
93 | 8 |
94 |----|
95 | 14 |
98 ;; Calc formula
99 "#+TBLFM: $1 = vsum(@<..@>>)"
100 ;; Lisp formula
101 "#+TBLFM: $1 = '(+ @<..@>>); N")
103 ;; The problem is that the first three rows with the summands are
104 ;; considered the header and therefore column formulas are not
105 ;; applied on them as shown below. Also export behaves unexpected.
106 ;; See next ert-deftest how to group rows right.
107 (org-test-table-target-expect
109 | 2 | header |
110 | 4 | header |
111 | 8 | header |
112 |---------+---------|
113 | replace | replace |
116 | 2 | header |
117 | 4 | header |
118 | 8 | header |
119 |----+--------|
120 | 14 | 28 |
123 ;; Calc formula
124 "#+TBLFM: @>$1 = vsum(@<..@>>) :: $2 = 2 * $1"
125 ;; Lisp formula
126 "#+TBLFM: @>$1 = '(+ @<..@>>); N :: $2 = '(* 2 $1); N"))
128 (ert-deftest test-org-table/simple-formula/with-grouping/with-title-row ()
129 "Simple sum with grouping rows, how to do it right."
130 ;; Always add a top row with the column names separated by hline to
131 ;; get the desired header when you want to group rows.
132 (org-test-table-target-expect
134 | foo | bar |
135 |---------+---------|
136 | 2 | replace |
137 | 4 | replace |
138 | 8 | replace |
139 |---------+---------|
140 | replace | replace |
143 | foo | bar |
144 |-----+-----|
145 | 2 | 4 |
146 | 4 | 8 |
147 | 8 | 16 |
148 |-----+-----|
149 | 14 | 28 |
152 ;; Calc formula
153 "#+TBLFM: @>$1 = vsum(@I..@>>) :: $2 = 2 * $1"
154 ;; Lisp formula
155 "#+TBLFM: @>$1 = '(+ @I..@>>); N :: $2 = '(* 2 $1); N"))
157 (ert-deftest test-org-table/align ()
158 "Align columns within Org buffer, depends on `org-table-number-regexp'."
159 (org-test-table-target-expect "
160 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
161 | ab | 12 | 12.2 | 2.4e-08 | 2x10^12 | 4.034+-0.02 | 2.7(10) | >3.5 |
162 | ab | ab | ab | ab | ab | ab | ab | ab |
164 (org-test-table-target-expect "
165 | 0 | 0 | 0 | 0 | 0 | 0 |
166 | <-0x0ab.cf | >-36#0vw.yz | nan | uinf | -inf | inf |
167 | ab | ab | ab | ab | ab | ab |
170 (ert-deftest test-org-table/align-buffer-tables ()
171 "Align all tables when updating buffer."
172 (let ((before "
173 | a b |
175 | c d |
177 (after "
178 | a b |
180 | c d |
182 (should (equal (org-test-with-temp-text before
183 (org-table-recalculate-buffer-tables)
184 (buffer-string))
185 after))
186 (should (equal (org-test-with-temp-text before
187 (org-table-iterate-buffer-tables)
188 (buffer-string))
189 after))))
191 (defconst references/target-normal "
192 | 0 | 1 | replace | replace | replace | replace | replace | replace |
193 | z | 1 | replace | replace | replace | replace | replace | replace |
194 | | 1 | replace | replace | replace | replace | replace | replace |
195 | | | replace | replace | replace | replace | replace | replace |
197 "Normal numbers and non-numbers for Lisp and Calc formula.")
199 (defconst references/target-special "
200 | nan | 1 | replace | replace | replace | replace | replace | replace |
201 | uinf | 1 | replace | replace | replace | replace | replace | replace |
202 | -inf | 1 | replace | replace | replace | replace | replace | replace |
203 | inf | 1 | replace | replace | replace | replace | replace | replace |
205 "Special numbers for Calc formula.")
207 (ert-deftest test-org-table/references/mode-string-EL ()
208 "Basic: Assign field reference, sum of field references, sum
209 and len of simple range reference (no row) and complex range
210 reference (with row). Mode string EL."
211 ;; Empty fields are kept during parsing field but lost as list
212 ;; elements within Lisp formula syntactically when used literally
213 ;; and not enclosed with " within fields, see last columns with len.
214 (org-test-table-target-expect
215 references/target-normal
216 ;; All the #ERROR show that for Lisp calculations N has to be used.
218 | 0 | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
219 | z | 1 | z | #ERROR | #ERROR | #ERROR | 2 | 2 |
220 | | 1 | | 1 | 1 | 1 | 1 | 1 |
221 | | | | 0 | 0 | 0 | 0 | 0 |
223 1 (concat
224 "#+TBLFM: $3 = '(identity \"$1\"); EL :: $4 = '(+ $1 $2); EL :: "
225 "$5 = '(+ $1..$2); EL :: $6 = '(+ @0$1..@0$2); EL :: "
226 "$7 = '(length '($1..$2)); EL :: $8 = '(length '(@0$1..@0$2)); EL"))
228 ;; Empty fields are kept during parsing field _and_ as list elements
229 ;; within Lisp formula syntactically even when used literally when
230 ;; enclosed with " within fields, see last columns with len.
231 (org-test-table-target-expect
233 | \"0\" | \"1\" | repl | repl | repl | repl | repl | repl |
234 | \"z\" | \"1\" | repl | repl | repl | repl | repl | repl |
235 | \"\" | \"1\" | repl | repl | repl | repl | repl | repl |
236 | \"\" | \"\" | repl | repl | repl | repl | repl | repl |
239 | \"0\" | \"1\" | \"0\" | 1 | #ERROR | #ERROR | 2 | 2 |
240 | \"z\" | \"1\" | \"z\" | 1 | #ERROR | #ERROR | 2 | 2 |
241 | \"\" | \"1\" | \"\" | 1 | #ERROR | #ERROR | 2 | 2 |
242 | \"\" | \"\" | \"\" | 0 | #ERROR | #ERROR | 2 | 2 |
244 1 (concat
245 "#+TBLFM: $3 = '(concat \"\\\"\" $1 \"\\\"\"); EL :: "
246 "$4 = '(+ (string-to-number $1) (string-to-number $2)); EL :: "
247 "$5 = '(+ $1..$2); EL :: $6 = '(+ @0$1..@0$2); EL :: "
248 "$7 = '(length '($1..$2)); EL :: $8 = '(length '(@0$1..@0$2)); EL")))
250 (ert-deftest test-org-table/references/mode-string-E ()
251 "Basic: Assign field reference, sum of field references, sum
252 and len of simple range reference (no row) and complex range
253 reference (with row). Mode string E."
254 (let ((lisp
255 (concat
256 "#+TBLFM: $3 = '(identity $1); E :: $4 = '(+ $1 $2); E :: "
257 "$5 = '(+ $1..$2); E :: $6 = '(+ @0$1..@0$2); E :: "
258 "$7 = '(length '($1..$2)); E :: $8 = '(length '(@0$1..@0$2)); E"))
259 (calc
260 (concat
261 "#+TBLFM: $3 = $1; E :: $4 = $1 + $2; E :: "
262 "$5 = vsum($1..$2); E :: $6 = vsum(@0$1..@0$2); E :: "
263 "$7 = vlen($1..$2); E :: $8 = vlen(@0$1..@0$2); E")))
264 (org-test-table-target-expect
265 references/target-normal
266 ;; All the #ERROR show that for Lisp calculations N has to be used.
268 | 0 | 1 | 0 | #ERROR | #ERROR | #ERROR | 2 | 2 |
269 | z | 1 | z | #ERROR | #ERROR | #ERROR | 2 | 2 |
270 | | 1 | | #ERROR | #ERROR | #ERROR | 2 | 2 |
271 | | | | #ERROR | #ERROR | #ERROR | 2 | 2 |
273 1 lisp)
274 (org-test-table-target-expect
275 references/target-normal
277 | 0 | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
278 | z | 1 | z | z + 1 | z + 1 | z + 1 | 2 | 2 |
279 | | 1 | nan | nan | nan | nan | 2 | 2 |
280 | | | nan | nan | nan | nan | 2 | 2 |
282 1 calc)
283 (org-test-table-target-expect
284 references/target-special
286 | nan | 1 | nan | nan | nan | nan | 2 | 2 |
287 | uinf | 1 | uinf | uinf | uinf | uinf | 2 | 2 |
288 | -inf | 1 | -inf | -inf | -inf | -inf | 2 | 2 |
289 | inf | 1 | inf | inf | inf | inf | 2 | 2 |
291 1 calc)))
293 (ert-deftest test-org-table/references/mode-string-EN ()
294 "Basic: Assign field reference, sum of field references, sum
295 and len of simple range reference (no row) and complex range
296 reference (with row). Mode string EN."
297 (let ((lisp (concat
298 "#+TBLFM: $3 = '(identity $1); EN :: $4 = '(+ $1 $2); EN :: "
299 "$5 = '(+ $1..$2); EN :: $6 = '(+ @0$1..@0$2); EN :: "
300 "$7 = '(length '($1..$2)); EN :: "
301 "$8 = '(length '(@0$1..@0$2)); EN"))
302 (calc (concat
303 "#+TBLFM: $3 = $1; EN :: $4 = $1 + $2; EN :: "
304 "$5 = vsum($1..$2); EN :: $6 = vsum(@0$1..@0$2); EN :: "
305 "$7 = vlen($1..$2); EN :: $8 = vlen(@0$1..@0$2); EN")))
306 (org-test-table-target-expect
307 references/target-normal
309 | 0 | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
310 | z | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
311 | | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
312 | | | 0 | 0 | 0 | 0 | 2 | 2 |
314 1 lisp calc)
315 (org-test-table-target-expect
316 references/target-special
318 | nan | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
319 | uinf | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
320 | -inf | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
321 | inf | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
323 1 calc)))
325 (ert-deftest test-org-table/references/mode-string-L ()
326 "Basic: Assign field reference, sum of field references, sum
327 and len of simple range reference (no row) and complex range
328 reference (with row). Mode string L."
329 (org-test-table-target-expect
330 references/target-normal
331 ;; All the #ERROR show that for Lisp calculations N has to be used.
333 | 0 | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
334 | z | 1 | z | #ERROR | #ERROR | #ERROR | 2 | 2 |
335 | | 1 | | 1 | 1 | 1 | 1 | 1 |
336 | | | | 0 | 0 | 0 | 0 | 0 |
338 1 (concat
339 "#+TBLFM: $3 = '(identity \"$1\"); L :: $4 = '(+ $1 $2); L :: "
340 "$5 = '(+ $1..$2); L :: $6 = '(+ @0$1..@0$2); L :: "
341 "$7 = '(length '($1..$2)); L :: $8 = '(length '(@0$1..@0$2)); L")))
343 (ert-deftest test-org-table/references/mode-string-none ()
344 "Basic: Assign field reference, sum of field references, sum
345 and len of simple range reference (no row) and complex range
346 reference (with row). No mode string."
347 (let ((lisp (concat
348 "#+TBLFM: $3 = '(identity $1) :: $4 = '(+ $1 $2) :: "
349 "$5 = '(+ $1..$2) :: $6 = '(+ @0$1..@0$2) :: "
350 "$7 = '(length '($1..$2)) :: $8 = '(length '(@0$1..@0$2))"))
351 (calc (concat
352 "#+TBLFM: $3 = $1 :: $4 = $1 + $2 :: "
353 "$5 = vsum($1..$2) :: $6 = vsum(@0$1..@0$2) :: "
354 "$7 = vlen($1..$2) :: $8 = vlen(@0$1..@0$2)")))
355 (org-test-table-target-expect
356 references/target-normal
357 ;; All the #ERROR show that for Lisp calculations N has to be used.
359 | 0 | 1 | 0 | #ERROR | #ERROR | #ERROR | 2 | 2 |
360 | z | 1 | z | #ERROR | #ERROR | #ERROR | 2 | 2 |
361 | | 1 | | #ERROR | #ERROR | #ERROR | 1 | 1 |
362 | | | | #ERROR | 0 | 0 | 0 | 0 |
364 1 lisp)
365 (org-test-table-target-expect
366 references/target-normal
368 | 0 | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
369 | z | 1 | z | z + 1 | z + 1 | z + 1 | 2 | 2 |
370 | | 1 | 0 | 1 | 1 | 1 | 1 | 1 |
371 | | | 0 | 0 | 0 | 0 | 0 | 0 |
373 1 calc)
374 (org-test-table-target-expect
375 references/target-special
377 | nan | 1 | nan | nan | nan | nan | 2 | 2 |
378 | uinf | 1 | uinf | uinf | uinf | uinf | 2 | 2 |
379 | -inf | 1 | -inf | -inf | -inf | -inf | 2 | 2 |
380 | inf | 1 | inf | inf | inf | inf | 2 | 2 |
382 1 calc)))
384 (ert-deftest test-org-table/references/mode-string-N ()
385 "Basic: Assign field reference, sum of field references, sum
386 and len of simple range reference (no row) and complex range
387 reference (with row). Mode string N."
388 (let ((lisp
389 (concat
390 "#+TBLFM: $3 = '(identity $1); N :: $4 = '(+ $1 $2); N :: "
391 "$5 = '(+ $1..$2); N :: $6 = '(+ @0$1..@0$2); N :: "
392 "$7 = '(length '($1..$2)); N :: $8 = '(length '(@0$1..@0$2)); N"))
393 (calc
394 (concat
395 "#+TBLFM: $3 = $1; N :: $4 = $1 + $2; N :: "
396 "$5 = vsum($1..$2); N :: $6 = vsum(@0$1..@0$2); N :: "
397 "$7 = vlen($1..$2); N :: $8 = vlen(@0$1..@0$2); N")))
398 (org-test-table-target-expect
399 references/target-normal
401 | 0 | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
402 | z | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
403 | | 1 | 0 | 1 | 1 | 1 | 1 | 1 |
404 | | | 0 | 0 | 0 | 0 | 0 | 0 |
406 1 lisp calc)
407 (org-test-table-target-expect
408 references/target-special
410 | nan | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
411 | uinf | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
412 | -inf | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
413 | inf | 1 | 0 | 1 | 1 | 1 | 2 | 2 |
415 1 calc)))
417 (ert-deftest test-org-table/lisp-return-value ()
418 "Basic: Return value of Lisp formulas."
419 (org-test-table-target-expect
421 | | nil | (list) | '() |
422 |-------------------------+-------------+--------+-----|
423 | type-of, no L | replace (r) | r | r |
424 | type-of identity, no L | r | r | r |
425 | identity, no L | r | r | r |
426 |-------------------------+-------------+--------+-----|
427 | type-of \"@1\" | r | r | r |
428 | type-of (identity \"@1\") | r | r | r |
429 | identity \"@1\" | r | r | r |
430 |-------------------------+-------------+--------+-----|
431 | type-of @1 | r | r | r |
432 | type-of (identity @1) | r | r | r |
433 | identity @1 | r | r | r |
436 | | nil | (list) | '() |
437 |-------------------------+--------+--------+--------|
438 | type-of, no L | string | string | string |
439 | type-of identity, no L | string | string | string |
440 | identity, no L | nil | (list) | '() |
441 |-------------------------+--------+--------+--------|
442 | type-of \"@1\" | string | string | string |
443 | type-of (identity \"@1\") | string | string | string |
444 | identity \"@1\" | nil | (list) | '() |
445 |-------------------------+--------+--------+--------|
446 | type-of @1 | symbol | symbol | symbol |
447 | type-of (identity @1) | symbol | symbol | symbol |
448 | identity @1 | nil | nil | nil |
450 1 (concat "#+TBLFM: @2$<<..@2$> = '(type-of @1) :: "
451 "@3$<<..@3$> = '(type-of (identity @1)) :: "
452 "@4$<<..@4$> = '(identity @1) :: @5$<<..@>$> = '(@0$1); L")))
454 (ert-deftest test-org-table/compare ()
455 "Basic: Compare field references in Calc."
456 (org-test-table-target-expect
458 | | 0 | z | | nan | uinf | -inf | inf |
459 |------+------+------+------+------+------+------+------|
460 | 0 | repl | repl | repl | repl | repl | repl | repl |
461 | z | repl | repl | repl | repl | repl | repl | repl |
462 | | repl | repl | repl | repl | repl | repl | repl |
463 | nan | repl | repl | repl | repl | repl | repl | repl |
464 | uinf | repl | repl | repl | repl | repl | repl | repl |
465 | -inf | repl | repl | repl | repl | repl | repl | repl |
466 | inf | repl | repl | repl | repl | repl | repl | repl |
469 | | 0 | z | | nan | uinf | -inf | inf |
470 |------+---+---+---+-----+------+------+-----|
471 | 0 | x | | | | | | |
472 | z | | x | | | | | |
473 | | | | x | | | | |
474 | nan | | | | x | | | |
475 | uinf | | | | | x | | |
476 | -inf | | | | | | x | |
477 | inf | | | | | | | x |
480 ;; Compare field reference ($1) with field reference (@1)
481 "#+TBLFM: @<<$<<..@>$> = if(\"$1\" == \"@1\", x, string(\"\")); E"
482 ;; Compare field reference ($1) with absolute term
483 (concat "#+TBLFM: "
484 "$2 = if(\"$1\" == \"(0)\" , x, string(\"\")); E :: "
485 "$3 = if(\"$1\" == \"(z)\" , x, string(\"\")); E :: "
486 "$4 = if(\"$1\" == \"nan\" , x, string(\"\")); E :: "
487 "$5 = if(\"$1\" == \"(nan)\" , x, string(\"\")); E :: "
488 "$6 = if(\"$1\" == \"(uinf)\", x, string(\"\")); E :: "
489 "$7 = if(\"$1\" == \"(-inf)\", x, string(\"\")); E :: "
490 "$8 = if(\"$1\" == \"(inf)\" , x, string(\"\")); E"))
492 ;; Check field reference converted from an empty field: Despite this
493 ;; field reference will not end up in a result, Calc evaluates it.
494 ;; Make sure that also then there is no Calc error.
495 (org-test-table-target-expect
497 | 0 | replace |
498 | z | replace |
499 | | replace |
500 | nan | replace |
503 | 0 | 1 |
504 | z | z + 1 |
505 | | |
506 | nan | nan |
508 1 "#+TBLFM: $2 = if(\"$1\" == \"nan\", string(\"\"), $1 + 1); E"))
510 (ert-deftest test-org-table/empty-field ()
511 "Examples how to deal with empty fields."
512 ;; Test if one field is empty, else do a calculation
513 (org-test-table-target-expect
515 | -1 | replace |
516 | 0 | replace |
517 | | replace |
520 | -1 | 0 |
521 | 0 | 1 |
522 | | |
525 ;; Calc formula
526 "#+TBLFM: $2 = if(\"$1\" == \"nan\", string(\"\"), $1 + 1); E"
527 ;; Lisp formula
528 "#+TBLFM: $2 = '(if (eq \"$1\" \"\") \"\" (1+ $1)); L")
530 ;; Test if several fields are empty, else do a calculation
531 (org-test-table-target-expect
533 | 1 | 2 | replace |
534 | 4 | | replace |
535 | | 8 | replace |
536 | | | replace |
539 | 1 | 2 | 3 |
540 | 4 | | |
541 | | 8 | |
542 | | | |
545 ;; Calc formula
546 (concat "#+TBLFM: $3 = if(\"$1\" == \"nan\" || \"$2\" == \"nan\", "
547 "string(\"\"), $1 + $2); E")
548 ;; Lisp formula
549 (concat "#+TBLFM: $3 = '(if (or (eq \"$1\" \"\") (eq \"$2\" \"\")) "
550 "\"\" (+ $1 $2)); L"))
552 ;; $2: Use $1 + 0.5 if $1 available, else only reformat $2 if $2 available
553 (org-test-table-target-expect
555 | 1.5 | 0 |
556 | 3.5 | |
557 | | 5 |
558 | | |
561 | 1.5 | 2.0 |
562 | 3.5 | 4.0 |
563 | | 5.0 |
564 | | |
567 ;; Calc formula
568 (concat "#+TBLFM: $2 = if(\"$1\" == \"nan\", "
569 "if(\"$2\" == \"nan\", string(\"\"), $2 +.0), $1 + 0.5); E f-1")
570 ;; Lisp formula not implemented yet
573 ;; Empty fields in simple and complex range reference
574 (org-test-table-target-expect
576 | | | | | repl | repl | repl | repl | repl | repl |
577 | | | 5 | 7 | repl | repl | repl | repl | repl | repl |
578 | 1 | 3 | 5 | 7 | repl | repl | repl | repl | repl | repl |
581 | | | | | | | | | 0 | 0 |
582 | | | 5 | 7 | | | 6 | 6 | 3 | 3 |
583 | 1 | 3 | 5 | 7 | 4 | 4 | 4 | 4 | 4 | 4 |
586 ;; Calc formula
587 (concat
588 "#+TBLFM: "
589 "$5 = if(typeof(vmean($1..$4)) == 12, "
590 "string(\"\"), vmean($1..$4)); E :: "
591 "$6 = if(typeof(vmean(@0$1..@0$4)) == 12, "
592 "string(\"\"), vmean(@0$1..@0$4)); E :: "
593 "$7 = if(\"$1..$4\" == \"[]\", string(\"\"), vmean($1..$4)) :: "
594 "$8 = if(\"@0$1..@0$4\" == \"[]\", string(\"\"), vmean(@0$1..@0$4)) :: "
595 "$9 = vmean($1..$4); EN :: "
596 "$10 = vmean(@0$1..@0$4); EN")
597 ;; Lisp formula
598 (concat
599 "#+TBLFM: "
600 "$5 = '(let ((l '($1..$4))) (if (member \"\" l) \"\" "
601 "(/ (apply '+ (mapcar 'string-to-number l)) (length l)))); E :: "
602 "$6 = '(let ((l '(@0$1..@0$4))) (if (member \"\" l) \"\" "
603 "(/ (apply '+ (mapcar 'string-to-number l)) (length l)))); E :: "
604 "$7 = '(let ((l '($1..$4))) "
605 "(if l (/ (apply '+ l) (length l)) \"\")); N :: "
606 "$8 = '(let ((l '(@0$1..@0$4))) "
607 "(if l (/ (apply '+ l) (length l)) \"\")); N :: "
608 "$9 = '(/ (+ $1..$4) (length '($1..$4))); EN :: "
609 "$10 = '(/ (+ @0$1..@0$4) (length '(@0$1..@0$4))); EN")
612 (ert-deftest test-org-table/copy-field ()
613 "Experiments on how to copy one field into another field.
614 See also `test-org-table/remote-reference-access'."
615 (let ((target "
616 | 0 | replace |
617 | a b | replace |
618 | c d | replace |
619 | | replace |
620 | 2012-12 | replace |
621 | [2012-12-31 Mon] | replace |
623 ;; Lisp formula to copy literally
624 (org-test-table-target-expect
625 target
627 | 0 | 0 |
628 | a b | a b |
629 | c d | c d |
630 | | |
631 | 2012-12 | 2012-12 |
632 | [2012-12-31 Mon] | [2012-12-31 Mon] |
634 1 "#+TBLFM: $2 = '(identity $1)")
636 ;; Calc formula to copy quite literally
637 (org-test-table-target-expect
638 target
640 | 0 | 0 |
641 | a b | a b |
642 | c d | c d |
643 | | |
644 | 2012-12 | 2012-12 |
645 | [2012-12-31 Mon] | <2012-12-31 Mon> |
647 1 (concat "#+TBLFM: $2 = if(\"$1\" == \"nan\", "
648 "string(\"\"), string(subvec(\"$1\", 2, vlen(\"$1\")))); E"))
650 ;; Calc formula simple
651 (org-test-table-target-expect
652 target
654 | 0 | 0 |
655 | a b | a b |
656 | c d | c d |
657 | | |
658 | 2012-12 | 2000 |
659 | [2012-12-31 Mon] | <2012-12-31 Mon> |
661 1 "#+TBLFM: $2 = if(\"$1\" == \"nan\", string(\"\"), $1); E")))
663 (ert-deftest test-org-table/sub-total ()
664 "Grouped rows with sub-total.
665 Begin range with \"@II\" to handle multiline header. Convert
666 integer to float with \"+.0\" for sub-total of items c1 and c2.
667 Sum empty fields as value zero but without ignoring them for
668 \"vlen\" with format specifier \"EN\". Format possibly empty
669 results with the Calc formatter \"f-1\" instead of the printf
670 formatter \"%.1f\"."
671 (org-test-table-target-expect
673 |-------+---------+---------|
674 | Item | Item | Sub- |
675 | name | value | total |
676 |-------+---------+---------|
677 | a1 | 4.1 | replace |
678 | a2 | 8.2 | replace |
679 | a3 | | replace |
680 |-------+---------+---------|
681 | b1 | 16.0 | replace |
682 |-------+---------+---------|
683 | c1 | 32 | replace |
684 | c2 | 64 | replace |
685 |-------+---------+---------|
686 | Total | replace | replace |
687 |-------+---------+---------|
690 |-------+-------+-------|
691 | Item | Item | Sub- |
692 | name | value | total |
693 |-------+-------+-------|
694 | a1 | 4.1 | |
695 | a2 | 8.2 | |
696 | a3 | | 12.3 |
697 |-------+-------+-------|
698 | b1 | 16.0 | 16.0 |
699 |-------+-------+-------|
700 | c1 | 32 | |
701 | c2 | 64 | 96.0 |
702 |-------+-------+-------|
703 | Total | 124.3 | |
704 |-------+-------+-------|
706 1 (concat "#+TBLFM: @>$2 = vsum(@II..@>>) ::"
707 "$3 = if(vlen(@0..@+I) == 1, "
708 "vsum(@-I$2..@+I$2) +.0, string(\"\")); EN f-1 :: "
709 "@>$3 = string(\"\")")))
711 (ert-deftest test-org-table/org-lookup-all ()
712 "Use `org-lookup-all' for several GROUP BY as in SQL and for ranking.
713 See also http://orgmode.org/worg/org-tutorials/org-lookups.html ."
714 (let ((data "
715 #+NAME: data
716 | Purchase | Product | Shop | Rating |
717 |----------+---------+------+--------|
718 | a | p1 | s1 | 1 |
719 | b | p1 | s2 | 4 |
720 | c | p2 | s1 | 2 |
721 | d | p3 | s2 | 8 |
724 ;; Product rating and ranking by average purchase from "#+NAME: data"
725 (org-test-table-target-expect
726 (concat data "
727 | Product | Rating | Ranking |
728 |---------+---------+---------|
729 | p1 | replace | replace |
730 | p2 | replace | replace |
731 | p3 | replace | replace |
733 (concat data "
734 | Product | Rating | Ranking |
735 |---------+--------+---------|
736 | p1 | 2.5 | 2 |
737 | p2 | 2.0 | 3 |
738 | p3 | 8.0 | 1 |
740 2 (concat
741 "#+TBLFM: $2 = '(let ((all (org-lookup-all '$1 "
742 "'(remote(data, @I$2..@>$2)) '(remote(data, @I$4..@>$4))))) "
743 "(/ (apply '+ all) (length all) 1.0)); L :: "
744 "$3 = '(+ 1 (length (org-lookup-all $2 '(@I$2..@>$2) nil '<))); N"))
746 ;; Shop rating and ranking by average purchase from "#+NAME: data"
747 (org-test-table-target-expect
748 (concat data "
749 | Shop | Rating | Ranking |
750 |------+---------+---------|
751 | s1 | replace | replace |
752 | s2 | replace | replace |
754 (concat data "
755 | Shop | Rating | Ranking |
756 |------+--------+---------|
757 | s1 | 1.5 | 2 |
758 | s2 | 6.0 | 1 |
760 2 (concat
761 "#+TBLFM: $2 = '(let ((all (org-lookup-all '$1 "
762 "'(remote(data, @I$3..@>$3)) '(remote(data, @I$4..@>$4))))) "
763 "(/ (apply '+ all) (length all) 1.0)); L :: "
764 "$3 = '(+ 1 (length (org-lookup-all $2 '(@I$2..@>$2) nil '<))); N"))))
766 (ert-deftest test-org-table/org-table-make-reference/mode-string-EL ()
767 (fset 'f 'org-table-make-reference)
768 ;; For Lisp formula only
769 (should (equal "0" (f "0" t nil 'literal)))
770 (should (equal "z" (f "z" t nil 'literal)))
771 (should (equal "" (f "" t nil 'literal)))
772 (should (equal "0 1" (f '("0" "1") t nil 'literal)))
773 (should (equal "z 1" (f '("z" "1") t nil 'literal)))
774 (should (equal " 1" (f '("" "1") t nil 'literal)))
775 (should (equal " " (f '("" "" ) t nil 'literal))))
777 (ert-deftest test-org-table/org-table-make-reference/mode-string-E ()
778 (fset 'f 'org-table-make-reference)
779 ;; For Lisp formula
780 (should (equal "\"0\"" (f "0" t nil t)))
781 (should (equal "\"z\"" (f "z" t nil t)))
782 (should (equal "\"\"" (f "" t nil t)))
783 (should (equal "\"0\" \"1\"" (f '("0" "1") t nil t)))
784 (should (equal "\"z\" \"1\"" (f '("z" "1") t nil t)))
785 (should (equal "\"\" \"1\"" (f '("" "1") t nil t)))
786 (should (equal "\"\" \"\"" (f '("" "" ) t nil t)))
787 ;; For Calc formula
788 (should (equal "(0)" (f "0" t nil nil)))
789 (should (equal "(z)" (f "z" t nil nil)))
790 (should (equal "nan" (f "" t nil nil)))
791 (should (equal "[0,1]" (f '("0" "1") t nil nil)))
792 (should (equal "[z,1]" (f '("z" "1") t nil nil)))
793 (should (equal "[nan,1]" (f '("" "1") t nil nil)))
794 (should (equal "[nan,nan]" (f '("" "" ) t nil nil)))
795 ;; For Calc formula, special numbers
796 (should (equal "(nan)" (f "nan" t nil nil)))
797 (should (equal "(uinf)" (f "uinf" t nil nil)))
798 (should (equal "(-inf)" (f "-inf" t nil nil)))
799 (should (equal "(inf)" (f "inf" t nil nil)))
800 (should (equal "[nan,1]" (f '( "nan" "1") t nil nil)))
801 (should (equal "[uinf,1]" (f '("uinf" "1") t nil nil)))
802 (should (equal "[-inf,1]" (f '("-inf" "1") t nil nil)))
803 (should (equal "[inf,1]" (f '( "inf" "1") t nil nil))))
805 (ert-deftest test-org-table/org-table-make-reference/mode-string-EN ()
806 (fset 'f 'org-table-make-reference)
807 ;; For Lisp formula
808 (should (equal "0" (f "0" t t t)))
809 (should (equal "0" (f "z" t t t)))
810 (should (equal "0" (f "" t t t)))
811 (should (equal "0 1" (f '("0" "1") t t t)))
812 (should (equal "0 1" (f '("z" "1") t t t)))
813 (should (equal "0 1" (f '("" "1") t t t)))
814 (should (equal "0 0" (f '("" "" ) t t t)))
815 ;; For Calc formula
816 (should (equal "(0)" (f "0" t t nil)))
817 (should (equal "(0)" (f "z" t t nil)))
818 (should (equal "(0)" (f "" t t nil)))
819 (should (equal "[0,1]" (f '("0" "1") t t nil)))
820 (should (equal "[0,1]" (f '("z" "1") t t nil)))
821 (should (equal "[0,1]" (f '("" "1") t t nil)))
822 (should (equal "[0,0]" (f '("" "" ) t t nil)))
823 ;; For Calc formula, special numbers
824 (should (equal "(0)" (f "nan" t t nil)))
825 (should (equal "(0)" (f "uinf" t t nil)))
826 (should (equal "(0)" (f "-inf" t t nil)))
827 (should (equal "(0)" (f "inf" t t nil)))
828 (should (equal "[0,1]" (f '( "nan" "1") t t nil)))
829 (should (equal "[0,1]" (f '("uinf" "1") t t nil)))
830 (should (equal "[0,1]" (f '("-inf" "1") t t nil)))
831 (should (equal "[0,1]" (f '( "inf" "1") t t nil))))
833 (ert-deftest test-org-table/org-table-make-reference/mode-string-L ()
834 (fset 'f 'org-table-make-reference)
835 ;; For Lisp formula only
836 (should (equal "0" (f "0" nil nil 'literal)))
837 (should (equal "z" (f "z" nil nil 'literal)))
838 (should (equal "" (f "" nil nil 'literal)))
839 (should (equal "0 1" (f '("0" "1") nil nil 'literal)))
840 (should (equal "z 1" (f '("z" "1") nil nil 'literal)))
841 (should (equal "1" (f '("" "1") nil nil 'literal)))
842 (should (equal "" (f '("" "" ) nil nil 'literal))))
844 (ert-deftest test-org-table/org-table-make-reference/mode-string-none ()
845 (fset 'f 'org-table-make-reference)
846 ;; For Lisp formula
847 (should (equal "\"0\"" (f "0" nil nil t)))
848 (should (equal "\"z\"" (f "z" nil nil t)))
849 (should (equal "" (f "" nil nil t)))
850 (should (equal "\"0\" \"1\"" (f '("0" "1") nil nil t)))
851 (should (equal "\"z\" \"1\"" (f '("z" "1") nil nil t)))
852 (should (equal "\"1\"" (f '("" "1") nil nil t)))
853 (should (equal "" (f '("" "" ) nil nil t)))
854 ;; For Calc formula
855 (should (equal "(0)" (f "0" nil nil nil)))
856 (should (equal "(z)" (f "z" nil nil nil)))
857 (should (equal "(0)" (f "" nil nil nil)))
858 (should (equal "[0,1]" (f '("0" "1") nil nil nil)))
859 (should (equal "[z,1]" (f '("z" "1") nil nil nil)))
860 (should (equal "[1]" (f '("" "1") nil nil nil)))
861 (should (equal "[]" (f '("" "" ) nil nil nil)))
862 ;; For Calc formula, special numbers
863 (should (equal "(nan)" (f "nan" nil nil nil)))
864 (should (equal "(uinf)" (f "uinf" nil nil nil)))
865 (should (equal "(-inf)" (f "-inf" nil nil nil)))
866 (should (equal "(inf)" (f "inf" nil nil nil)))
867 (should (equal "[nan,1]" (f '( "nan" "1") nil nil nil)))
868 (should (equal "[uinf,1]" (f '("uinf" "1") nil nil nil)))
869 (should (equal "[-inf,1]" (f '("-inf" "1") nil nil nil)))
870 (should (equal "[inf,1]" (f '( "inf" "1") nil nil nil))))
872 (ert-deftest test-org-table/org-table-make-reference/mode-string-N ()
873 (fset 'f 'org-table-make-reference)
874 ;; For Lisp formula
875 (should (equal "0" (f "0" nil t t)))
876 (should (equal "0" (f "z" nil t t)))
877 (should (equal "" (f "" nil t t)))
878 (should (equal "0 1" (f '("0" "1") nil t t)))
879 (should (equal "0 1" (f '("z" "1") nil t t)))
880 (should (equal "1" (f '("" "1") nil t t)))
881 (should (equal "" (f '("" "" ) nil t t)))
882 ;; For Calc formula
883 (should (equal "(0)" (f "0" nil t nil)))
884 (should (equal "(0)" (f "z" nil t nil)))
885 (should (equal "(0)" (f "" nil t nil)))
886 (should (equal "[0,1]" (f '("0" "1") nil t nil)))
887 (should (equal "[0,1]" (f '("z" "1") nil t nil)))
888 (should (equal "[1]" (f '("" "1") nil t nil)))
889 (should (equal "[]" (f '("" "" ) nil t nil)))
890 ;; For Calc formula, special numbers
891 (should (equal "(0)" (f "nan" nil t nil)))
892 (should (equal "(0)" (f "uinf" nil t nil)))
893 (should (equal "(0)" (f "-inf" nil t nil)))
894 (should (equal "(0)" (f "inf" nil t nil)))
895 (should (equal "[0,1]" (f '( "nan" "1") nil t nil)))
896 (should (equal "[0,1]" (f '("uinf" "1") nil t nil)))
897 (should (equal "[0,1]" (f '("-inf" "1") nil t nil)))
898 (should (equal "[0,1]" (f '( "inf" "1") nil t nil))))
900 (ert-deftest test-org-table/org-table-convert-refs-to-an/1 ()
901 "Simple reference @2$1."
902 (should
903 (string= "A2" (org-table-convert-refs-to-an "@2$1"))))
905 ;; TODO: Test broken
906 ;; (ert-deftest test-org-table/org-table-convert-refs-to-an/2 ()
907 ;; "Self reference @1$1."
908 ;; (should
909 ;; (string= "A1 = $0" (org-table-convert-refs-to-an "@1$1 = $0"))))
911 (ert-deftest test-org-table/org-table-convert-refs-to-an/3 ()
912 "Remote reference."
913 (should
914 (string= "C& = remote(FOO, @@#B&)" (org-table-convert-refs-to-an "$3 = remote(FOO, @@#$2)"))))
916 (ert-deftest test-org-table/org-table-convert-refs-to-rc/1 ()
917 "Simple reference @2$1."
918 (should
919 (string= "@2$1" (org-table-convert-refs-to-rc "A2"))))
921 (ert-deftest test-org-table/org-table-convert-refs-to-rc/2 ()
922 "Self reference $0."
923 (should
924 (string= "@1$1 = $0" (org-table-convert-refs-to-rc "A1 = $0"))))
926 ;; TODO: Test Broken
927 ;; (ert-deftest test-org-table/org-table-convert-refs-to-rc/3 ()
928 ;; "Remote reference."
929 ;; (should
930 ;; (string= "$3 = remote(FOO, @@#$2)" (org-table-convert-refs-to-rc "C& = remote(FOO, @@#B&)"))))
932 (ert-deftest test-org-table/remote-reference-access ()
933 "Access to remote reference.
934 See also `test-org-table/copy-field'."
935 (org-test-table-target-expect
937 #+NAME: table
938 | | x 42 | |
940 | replace | replace |
943 #+NAME: table
944 | | x 42 | |
946 | x 42 | 84 x |
948 1 (concat "#+TBLFM: "
949 ;; Copy text without calculation: Use Lisp formula
950 "$1 = '(identity remote(table, @1$2)) :: "
951 ;; Do a calculation: Use Calc (or Lisp ) formula
952 "$2 = 2 * remote(table, @1$2)")))
954 (ert-deftest test-org-table/remote-reference-indirect ()
955 "Access to remote reference with indirection of name or ID."
956 (let ((source-tables "
957 #+NAME: 2012
958 | amount |
959 |--------|
960 | 1 |
961 | 2 |
962 |--------|
963 | 3 |
964 #+TBLFM: @>$1 = vsum(@I..@II)
966 #+NAME: 2013
967 | amount |
968 |--------|
969 | 4 |
970 | 8 |
971 |--------|
972 | 12 |
973 #+TBLFM: @>$1 = vsum(@I..@II)
976 ;; Read several remote references from same column
977 (org-test-table-target-expect
978 (concat source-tables "
979 #+NAME: summary
980 | year | amount |
981 |-------+---------|
982 | 2012 | replace |
983 | 2013 | replace |
984 |-------+---------|
985 | total | replace |
987 (concat source-tables "
988 #+NAME: summary
989 | year | amount |
990 |-------+--------|
991 | 2012 | 3 |
992 | 2013 | 12 |
993 |-------+--------|
994 | total | 15 |
997 ;; Calc formula
998 "#+TBLFM: @<<$2..@>>$2 = remote($<, @>$1) :: @>$2 = vsum(@I..@II)"
999 ;; Lisp formula
1000 (concat "#+TBLFM: @<<$2..@>>$2 = '(identity remote($<, @>$1)); N :: "
1001 "@>$2 = '(+ @I..@II); N"))
1003 ;; Read several remote references from same row
1004 (org-test-table-target-expect
1005 (concat source-tables "
1006 #+NAME: summary
1007 | year | 2012 | 2013 | total |
1008 |--------+---------+---------+---------|
1009 | amount | replace | replace | replace |
1011 (concat source-tables "
1012 #+NAME: summary
1013 | year | 2012 | 2013 | total |
1014 |--------+------+------+-------|
1015 | amount | 3 | 12 | 15 |
1018 ;; Calc formula
1019 "#+TBLFM: @2$<<..@2$>> = remote(@<, @>$1) :: @2$> = vsum($<<..$>>)"
1020 ;; Lisp formula
1021 (concat "#+TBLFM: @2$<<..@2$>> = '(identity remote(@<, @>$1)); N :: "
1022 "@2$> = '(+ $<<..$>>); N"))))
1024 (ert-deftest test-org-table/org-at-TBLFM-p ()
1025 (org-test-with-temp-text-in-file
1027 | 1 |
1028 | 2 |
1029 #+TBLFM: $2=$1*2
1032 (goto-char (point-min))
1033 (forward-line 2)
1034 (should (equal (org-at-TBLFM-p) nil))
1036 (goto-char (point-min))
1037 (forward-line 3)
1038 (should (equal (org-at-TBLFM-p) t))
1040 (goto-char (point-min))
1041 (forward-line 4)
1042 (should (equal (org-at-TBLFM-p) nil))))
1044 (ert-deftest test-org-table/org-table-TBLFM-begin ()
1045 (org-test-with-temp-text-in-file
1047 | 1 |
1048 | 2 |
1049 #+TBLFM: $2=$1*2
1052 (goto-char (point-min))
1053 (should (equal (org-table-TBLFM-begin)
1054 nil))
1056 (goto-char (point-min))
1057 (forward-line 1)
1058 (should (equal (org-table-TBLFM-begin)
1059 nil))
1061 (goto-char (point-min))
1062 (forward-line 3)
1063 (should (= (org-table-TBLFM-begin)
1064 14))
1066 (goto-char (point-min))
1067 (forward-line 4)
1068 (should (= (org-table-TBLFM-begin)
1069 14))
1073 (ert-deftest test-org-table/org-table-TBLFM-begin-for-multiple-TBLFM-lines ()
1074 "For multiple #+TBLFM lines."
1075 (org-test-with-temp-text-in-file
1077 | 1 |
1078 | 2 |
1079 #+TBLFM: $2=$1*1
1080 #+TBLFM: $2=$1*2
1083 (goto-char (point-min))
1084 (should (equal (org-table-TBLFM-begin)
1085 nil))
1087 (goto-char (point-min))
1088 (forward-line 1)
1089 (should (equal (org-table-TBLFM-begin)
1090 nil))
1092 (goto-char (point-min))
1093 (forward-line 3)
1094 (should (= (org-table-TBLFM-begin)
1095 14))
1097 (goto-char (point-min))
1098 (forward-line 4)
1099 (should (= (org-table-TBLFM-begin)
1100 14))
1102 (goto-char (point-min))
1103 (forward-line 5)
1104 (should (= (org-table-TBLFM-begin)
1105 14))
1109 (ert-deftest test-org-table/org-table-TBLFM-begin-for-pultiple-TBLFM-lines-blocks ()
1110 (org-test-with-temp-text-in-file
1112 | 1 |
1113 | 2 |
1114 #+TBLFM: $2=$1*1
1115 #+TBLFM: $2=$1*2
1117 | 6 |
1118 | 7 |
1119 #+TBLFM: $2=$1*1
1120 #+TBLFM: $2=$1*2
1123 (goto-char (point-min))
1124 (should (equal (org-table-TBLFM-begin)
1125 nil))
1127 (goto-char (point-min))
1128 (forward-line 1)
1129 (should (equal (org-table-TBLFM-begin)
1130 nil))
1132 (goto-char (point-min))
1133 (forward-line 3)
1134 (should (= (org-table-TBLFM-begin)
1135 14))
1137 (goto-char (point-min))
1138 (forward-line 4)
1139 (should (= (org-table-TBLFM-begin)
1140 14))
1142 (goto-char (point-min))
1143 (forward-line 5)
1144 (should (= (org-table-TBLFM-begin)
1145 14))
1147 (goto-char (point-min))
1148 (forward-line 6)
1149 (should (= (org-table-TBLFM-begin)
1150 14))
1152 (goto-char (point-min))
1153 (forward-line 8)
1154 (should (= (org-table-TBLFM-begin)
1155 61))
1157 (goto-char (point-min))
1158 (forward-line 9)
1159 (should (= (org-table-TBLFM-begin)
1160 61))
1162 (goto-char (point-min))
1163 (forward-line 10)
1164 (should (= (org-table-TBLFM-begin)
1165 61))))
1167 (ert-deftest test-org-table/org-table-calc-current-TBLFM ()
1168 (org-test-with-temp-text-in-file
1170 | 1 | |
1171 | 2 | |
1172 #+TBLFM: $2=$1*1
1173 #+TBLFM: $2=$1*2
1174 #+TBLFM: $2=$1*3
1176 (let ((got (progn (goto-char (point-min))
1177 (forward-line 3)
1178 (org-table-calc-current-TBLFM)
1179 (buffer-string)))
1180 (expect "
1181 | 1 | 1 |
1182 | 2 | 2 |
1183 #+TBLFM: $2=$1*1
1184 #+TBLFM: $2=$1*2
1185 #+TBLFM: $2=$1*3
1187 (should (string= got
1188 expect)))
1190 (let ((got (progn (goto-char (point-min))
1191 (forward-line 4)
1192 (org-table-calc-current-TBLFM)
1193 (buffer-string)))
1194 (expect "
1195 | 1 | 2 |
1196 | 2 | 4 |
1197 #+TBLFM: $2=$1*1
1198 #+TBLFM: $2=$1*2
1199 #+TBLFM: $2=$1*3
1201 (should (string= got
1202 expect)))))
1204 (ert-deftest test-org-table/org-table-calc-current-TBLFM-when-stop-because-of-error ()
1205 "org-table-calc-current-TBLFM should preserve the input as it was."
1206 (org-test-with-temp-text-in-file
1208 | 1 | 1 |
1209 | 2 | 2 |
1210 #+TBLFM: $2=$1*1
1211 #+TBLFM: $2=$1*2::$2=$1*2
1212 #+TBLFM: $2=$1*3
1214 (let ((expect "
1215 | 1 | 1 |
1216 | 2 | 2 |
1217 #+TBLFM: $2=$1*1
1218 #+TBLFM: $2=$1*2::$2=$1*2
1219 #+TBLFM: $2=$1*3
1221 (goto-char (point-min))
1222 (forward-line 4)
1223 (should-error (org-table-calc-current-TBLFM))
1224 (setq got (buffer-string))
1225 (message "%s" got)
1226 (should (string= got
1227 expect)))))
1229 ;;; Radio Tables
1231 (ert-deftest test-org-table/to-generic ()
1232 "Test `orgtbl-to-generic' specifications."
1233 ;; Test :hline parameter.
1234 (should
1235 (equal "a\nb"
1236 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1237 '(:hline nil))))
1238 (should
1239 (equal "a\n~\nb"
1240 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1241 '(:hline "~"))))
1242 ;; Test :sep parameter.
1243 (should
1244 (equal "a!b\nc!d"
1245 (orgtbl-to-generic
1246 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1247 '(:sep "!"))))
1248 ;; Test :hsep parameter.
1249 (should
1250 (equal "a!b\nc?d"
1251 (orgtbl-to-generic
1252 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1253 '(:sep "?" :hsep "!"))))
1254 ;; Test :tstart parameter.
1255 (should
1256 (equal "<begin>\na"
1257 (orgtbl-to-generic (org-table-to-lisp "| a |") '(:tstart "<begin>"))))
1258 (should
1259 (equal "<begin>\na"
1260 (orgtbl-to-generic (org-table-to-lisp "| a |")
1261 '(:tstart (lambda () "<begin>")))))
1262 (should
1263 (equal "a"
1264 (orgtbl-to-generic (org-table-to-lisp "| a |")
1265 '(:tstart "<begin>" :splice t))))
1266 ;; Test :tend parameter.
1267 (should
1268 (equal "a\n<end>"
1269 (orgtbl-to-generic (org-table-to-lisp "| a |") '(:tend "<end>"))))
1270 (should
1271 (equal "a\n<end>"
1272 (orgtbl-to-generic (org-table-to-lisp "| a |")
1273 '(:tend (lambda () "<end>")))))
1274 (should
1275 (equal "a"
1276 (orgtbl-to-generic (org-table-to-lisp "| a |")
1277 '(:tend "<end>" :splice t))))
1278 ;; Test :lstart parameter.
1279 (should
1280 (equal "> a"
1281 (orgtbl-to-generic
1282 (org-table-to-lisp "| a |") '(:lstart "> "))))
1283 (should
1284 (equal "> a"
1285 (orgtbl-to-generic (org-table-to-lisp "| a |")
1286 '(:lstart (lambda () "> ")))))
1287 ;; Test :llstart parameter.
1288 (should
1289 (equal "> a\n>> b"
1290 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1291 '(:lstart "> " :llstart ">> "))))
1292 ;; Test :hlstart parameter.
1293 (should
1294 (equal "!> a\n> b"
1295 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1296 '(:lstart "> " :hlstart "!> "))))
1297 ;; Test :hllstart parameter.
1298 (should
1299 (equal "!> a\n!!> b\n> c"
1300 (orgtbl-to-generic (org-table-to-lisp "| a |\n| b |\n|---|\n| c |")
1301 '(:lstart "> " :hlstart "!> " :hllstart "!!> "))))
1302 ;; Test :lend parameter.
1303 (should
1304 (equal "a <"
1305 (orgtbl-to-generic (org-table-to-lisp "| a |") '(:lend " <"))))
1306 ;; Test :llend parameter.
1307 (should
1308 (equal "a <\nb <<"
1309 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1310 '(:lend " <" :llend " <<"))))
1311 ;; Test :hlend parameter.
1312 (should
1313 (equal "a <!\nb <"
1314 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1315 '(:lend " <" :hlend " <!"))))
1316 ;; Test :hllend parameter.
1317 (should
1318 (equal "a <!\nb <!!\nc <"
1319 (orgtbl-to-generic (org-table-to-lisp "| a |\n| b |\n|---|\n| c |")
1320 '(:lend " <" :hlend " <!" :hllend " <!!"))))
1321 ;; Test :lfmt parameter.
1322 (should
1323 (equal "a!b"
1324 (orgtbl-to-generic (org-table-to-lisp "| a | b |")
1325 '(:lfmt "%s!%s"))))
1326 (should
1327 (equal "a+b"
1328 (orgtbl-to-generic
1329 (org-table-to-lisp "| a | b |")
1330 '(:lfmt (lambda (c) (concat (car c) "+" (cadr c)))))))
1331 (should
1332 (equal "a!b"
1333 (orgtbl-to-generic (org-table-to-lisp "| a | b |")
1334 '(:lfmt "%s!%s" :lstart ">" :lend "<" :sep " "))))
1335 ;; Test :llfmt parameter.
1336 (should
1337 (equal "a!b"
1338 (orgtbl-to-generic (org-table-to-lisp "| a | b |")
1339 '(:llfmt "%s!%s"))))
1340 (should
1341 (equal "a!b\nc+d"
1342 (orgtbl-to-generic
1343 (org-table-to-lisp "| a | b |\n| c | d |")
1344 '(:lfmt "%s!%s" :llfmt (lambda (c) (concat (car c) "+" (cadr c)))))))
1345 (should
1346 (equal "a!b"
1347 (orgtbl-to-generic (org-table-to-lisp "| a | b |")
1348 '(:llfmt "%s!%s" :lstart ">" :lend "<" :sep " "))))
1349 ;; Test :hlfmt parameter.
1350 (should
1351 (equal "a!b\ncd"
1352 (orgtbl-to-generic
1353 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1354 '(:hlfmt "%s!%s"))))
1355 (should
1356 (equal "a+b\ncd"
1357 (orgtbl-to-generic
1358 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1359 '(:hlfmt (lambda (c) (concat (car c) "+" (cadr c)))))))
1360 (should
1361 (equal "a!b\n>c d<"
1362 (orgtbl-to-generic
1363 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1364 '(:hlfmt "%s!%s" :lstart ">" :lend "<" :sep " "))))
1365 ;; Test :hllfmt parameter.
1366 (should
1367 (equal "a!b\ncd"
1368 (orgtbl-to-generic
1369 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1370 '(:hllfmt "%s!%s"))))
1371 (should
1372 (equal "a+b\ncd"
1373 (orgtbl-to-generic
1374 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1375 '(:hllfmt (lambda (c) (concat (car c) "+" (cadr c)))))))
1376 (should
1377 (equal "a!b\n>c d<"
1378 (orgtbl-to-generic
1379 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1380 '(:hllfmt "%s!%s" :lstart ">" :lend "<" :sep " "))))
1381 ;; Test :fmt parameter.
1382 (should
1383 (equal ">a<\n>b<"
1384 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1385 '(:fmt ">%s<"))))
1386 (should
1387 (equal ">a<b"
1388 (orgtbl-to-generic (org-table-to-lisp "| a | b |")
1389 '(:fmt (1 ">%s<" 2 (lambda (c) c))))))
1390 (should
1391 (equal "a b"
1392 (orgtbl-to-generic (org-table-to-lisp "| a | b |")
1393 '(:fmt (2 " %s")))))
1394 (should
1395 (equal ">a<"
1396 (orgtbl-to-generic (org-table-to-lisp "| a |")
1397 '(:fmt (lambda (c) (format ">%s<" c))))))
1398 ;; Test :hfmt parameter.
1399 (should
1400 (equal ">a<\nb"
1401 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1402 '(:hfmt ">%s<"))))
1403 (should
1404 (equal ">a<b\ncd"
1405 (orgtbl-to-generic
1406 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1407 '(:hfmt (1 ">%s<" 2 identity)))))
1408 (should
1409 (equal "a b\ncd"
1410 (orgtbl-to-generic
1411 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |")
1412 '(:hfmt (2 " %s")))))
1413 (should
1414 (equal ">a<\nb"
1415 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1416 '(:hfmt (lambda (c) (format ">%s<" c))))))
1417 ;; Test :efmt parameter.
1418 (should
1419 (equal "2x10^3"
1420 (orgtbl-to-generic (org-table-to-lisp "| 2e3 |")
1421 '(:efmt "%sx10^%s"))))
1422 (should
1423 (equal "2x10^3"
1424 (orgtbl-to-generic (org-table-to-lisp "| 2e3 |")
1425 '(:efmt (lambda (m e) (concat m "x10^" e))))))
1426 (should
1427 (equal "2x10^3"
1428 (orgtbl-to-generic (org-table-to-lisp "| 2e3 |")
1429 '(:efmt (1 "%sx10^%s")))))
1430 (should
1431 (equal "2x10^3"
1432 (orgtbl-to-generic
1433 (org-table-to-lisp "| 2e3 |")
1434 '(:efmt (1 (lambda (m e) (format "%sx10^%s" m e)))))))
1435 (should
1436 (equal "2e3"
1437 (orgtbl-to-generic (org-table-to-lisp "| 2e3 |") '(:efmt nil))))
1438 ;; Test :skip parameter.
1439 (should
1440 (equal "cd"
1441 (orgtbl-to-generic
1442 (org-table-to-lisp "| \ | <c> |\n| a | b |\n|---+---|\n| c | d |")
1443 '(:skip 2))))
1444 ;; Test :skipcols parameter.
1445 (should
1446 (equal "a\nc"
1447 (orgtbl-to-generic
1448 (org-table-to-lisp "| a | b |\n| c | d |") '(:skipcols (2)))))
1449 (should
1450 (equal "a\nc"
1451 (orgtbl-to-generic
1452 (org-table-to-lisp
1453 "| / | <c> | <c> |\n| # | a | b |\n|---+---+---|\n| | c | d |")
1454 '(:skipcols (2)))))
1455 ;; Test :raw parameter.
1456 (when (featurep 'ox-latex)
1457 (should
1458 (string-match-p
1459 "/a/"
1460 (orgtbl-to-generic (org-table-to-lisp "| /a/ | b |")
1461 '(:backend latex :raw t)))))
1462 ;; Hooks are ignored.
1463 (should
1464 (equal
1465 "a\nb"
1466 (let* ((fun-list (list (lambda (backend) (search-forward "a") (insert "hook"))))
1467 (org-export-before-parsing-hook fun-list)
1468 (org-export-before-processing-hook fun-list))
1469 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1470 '(:hline nil)))))
1471 ;; User-defined export filters are ignored.
1472 (should
1473 (equal
1474 "a\nb"
1475 (let ((org-export-filter-table-cell-functions (list (lambda (c b i) "filter"))))
1476 (orgtbl-to-generic (org-table-to-lisp "| a |\n|---|\n| b |")
1477 '(:hline nil)))))
1478 ;; Macros, even if unknown, are returned as-is.
1479 (should
1480 (equal "{{{macro}}}"
1481 (orgtbl-to-generic (org-table-to-lisp "| {{{macro}}} |") nil))))
1483 (ert-deftest test-org-table/to-latex ()
1484 "Test `orgtbl-to-latex' specifications."
1485 (should
1486 (equal "\\begin{tabular}{l}\na\\\\\n\\end{tabular}"
1487 (orgtbl-to-latex (org-table-to-lisp "| a |") nil)))
1488 ;; Test :environment parameter.
1489 (should
1490 (equal "\\begin{tabularx}{l}\na\\\\\n\\end{tabularx}"
1491 (orgtbl-to-latex (org-table-to-lisp "| a |")
1492 '(:environment "tabularx"))))
1493 ;; Test :booktabs parameter.
1494 (should
1495 (string-match-p
1496 "\\toprule" (orgtbl-to-latex (org-table-to-lisp "| a |") '(:booktabs t))))
1497 ;; Handle LaTeX snippets.
1498 (should
1499 (equal "\\begin{tabular}{l}\n\\(x\\)\\\\\n\\end{tabular}"
1500 (orgtbl-to-latex (org-table-to-lisp "| $x$ |") nil)))
1501 ;; Test pseudo objects and :raw parameter.
1502 (should
1503 (string-match-p
1504 "\\$x\\$" (orgtbl-to-latex (org-table-to-lisp "| $x$ |") '(:raw t)))))
1506 (ert-deftest test-org-table/to-html ()
1507 "Test `orgtbl-to-html' specifications."
1508 (should
1509 (equal (orgtbl-to-html (org-table-to-lisp "| a |") nil)
1510 "<table border=\"2\" cellspacing=\"0\" cellpadding=\"6\" rules=\"groups\" frame=\"hsides\">
1513 <colgroup>
1514 <col class=\"org-left\" />
1515 </colgroup>
1516 <tbody>
1517 <tr>
1518 <td class=\"org-left\">a</td>
1519 </tr>
1520 </tbody>
1521 </table>"))
1522 ;; Test :attributes parameter.
1523 (should
1524 (string-match-p
1525 "<table>"
1526 (orgtbl-to-html (org-table-to-lisp "| a |") '(:attributes nil))))
1527 (should
1528 (string-match-p
1529 "<table border=\"2\">"
1530 (orgtbl-to-html (org-table-to-lisp "| a |") '(:attributes (:border "2"))))))
1532 (ert-deftest test-org-table/to-texinfo ()
1533 "Test `orgtbl-to-texinfo' specifications."
1534 (should
1535 (equal "@multitable {a}\n@item a\n@end multitable"
1536 (orgtbl-to-texinfo (org-table-to-lisp "| a |") nil)))
1537 ;; Test :columns parameter.
1538 (should
1539 (equal "@multitable @columnfractions .4 .6\n@item a\n@tab b\n@end multitable"
1540 (orgtbl-to-texinfo (org-table-to-lisp "| a | b |")
1541 '(:columns ".4 .6"))))
1542 (should
1543 (equal "@multitable @columnfractions .4 .6\n@item a\n@tab b\n@end multitable"
1544 (orgtbl-to-texinfo (org-table-to-lisp "| a | b |")
1545 '(:columns "@columnfractions .4 .6"))))
1546 (should
1547 (equal "@multitable {xxx} {xx}\n@item a\n@tab b\n@end multitable"
1548 (orgtbl-to-texinfo (org-table-to-lisp "| a | b |")
1549 '(:columns "{xxx} {xx}")))))
1551 (ert-deftest test-org-table/to-orgtbl ()
1552 "Test `orgtbl-to-orgtbl' specifications."
1553 (should
1554 (equal "| a | b |\n|---+---|\n| c | d |"
1555 (orgtbl-to-orgtbl
1556 (org-table-to-lisp "| a | b |\n|---+---|\n| c | d |") nil))))
1558 (ert-deftest test-org-table/to-unicode ()
1559 "Test `orgtbl-to-unicode' specifications."
1560 (should
1561 (equal "━━━\n a \n━━━"
1562 (orgtbl-to-unicode (org-table-to-lisp "| a |") nil)))
1563 ;; Test :narrow parameter.
1564 (should
1565 (equal "━━━━\n => \n━━━━"
1566 (orgtbl-to-unicode (org-table-to-lisp "| <2> |\n| xxx |")
1567 '(:narrow t)))))
1569 (ert-deftest test-org-table/send-region ()
1570 "Test `orgtbl-send-table' specifications."
1571 ;; Error when not at a table.
1572 (should-error
1573 (org-test-with-temp-text "Paragraph"
1574 (orgtbl-send-table)))
1575 ;; Error when destination is missing.
1576 (should-error
1577 (org-test-with-temp-text "#+ORGTBL: SEND\n<point>| a |"
1578 (orgtbl-send-table)))
1579 ;; Error when transformation function is not specified.
1580 (should-error
1581 (org-test-with-temp-text "
1582 # BEGIN RECEIVE ORGTBL table
1583 # END RECEIVE ORGTBL table
1584 #+ORGTBL: SEND table
1585 <point>| a |"
1586 (orgtbl-send-table)))
1587 ;; Standard test.
1588 (should
1589 (equal "| a |\n|---|\n| b |\n"
1590 (org-test-with-temp-text "
1591 # BEGIN RECEIVE ORGTBL table
1592 # END RECEIVE ORGTBL table
1593 #+ORGTBL: SEND table orgtbl-to-orgtbl :hlines nil
1594 <point>| a |\n|---|\n| b |"
1595 (orgtbl-send-table)
1596 (goto-char (point-min))
1597 (buffer-substring-no-properties
1598 (search-forward "# BEGIN RECEIVE ORGTBL table\n")
1599 (progn (search-forward "# END RECEIVE ORGTBL table")
1600 (match-beginning 0))))))
1601 ;; Allow multiple receiver locations.
1602 (should
1603 (org-test-with-temp-text "
1604 # BEGIN RECEIVE ORGTBL table
1605 # END RECEIVE ORGTBL table
1607 #+ORGTBL: SEND table orgtbl-to-orgtbl :hlines nil
1608 <point>| a |
1610 # BEGIN RECEIVE ORGTBL table
1611 # END RECEIVE ORGTBL table"
1612 (orgtbl-send-table)
1613 (goto-char (point-min))
1614 (search-forward "| a |" nil t 3))))
1617 ;;; Sorting
1619 (ert-deftest test-org-table/sort-lines ()
1620 "Test `org-table-sort-lines' specifications."
1621 ;; Sort numerically.
1622 (should
1623 (equal "| 1 | 2 |\n| 2 | 4 |\n| 5 | 3 |\n"
1624 (org-test-with-temp-text "| <point>1 | 2 |\n| 5 | 3 |\n| 2 | 4 |\n"
1625 (org-table-sort-lines nil ?n)
1626 (buffer-string))))
1627 (should
1628 (equal "| 5 | 3 |\n| 2 | 4 |\n| 1 | 2 |\n"
1629 (org-test-with-temp-text "| <point>1 | 2 |\n| 5 | 3 |\n| 2 | 4 |\n"
1630 (org-table-sort-lines nil ?N)
1631 (buffer-string))))
1632 ;; Sort alphabetically.
1633 (should
1634 (equal "| a | x |\n| b | 4 |\n| c | 3 |\n"
1635 (org-test-with-temp-text "| <point>a | x |\n| c | 3 |\n| b | 4 |\n"
1636 (org-table-sort-lines nil ?a)
1637 (buffer-string))))
1638 (should
1639 (equal "| c | 3 |\n| b | 4 |\n| a | x |\n"
1640 (org-test-with-temp-text "| <point>a | x |\n| c | 3 |\n| b | 4 |\n"
1641 (org-table-sort-lines nil ?A)
1642 (buffer-string))))
1643 ;; Sort alphabetically with case.
1644 (should
1645 (equal "| C |\n| a |\n| b |\n"
1646 (org-test-with-temp-text "| <point>a |\n| C |\n| b |\n"
1647 (org-table-sort-lines t ?a)
1648 (buffer-string))))
1649 (should
1650 (equal "| b |\n| a |\n| C |\n"
1651 (org-test-with-temp-text "| <point>a |\n| C |\n| b |\n"
1652 (org-table-sort-lines nil ?A)
1653 (buffer-string))))
1654 ;; Sort by time (timestamps)
1655 (should
1656 (equal
1657 "| <2008-08-08 sat.> |\n| <2012-03-29 thu.> |\n| <2014-03-04 tue.> |\n"
1658 (org-test-with-temp-text
1659 "| <2014-03-04 tue.> |\n| <2008-08-08 sat.> |\n| <2012-03-29 thu.> |\n"
1660 (org-table-sort-lines nil ?t)
1661 (buffer-string))))
1662 (should
1663 (equal
1664 "| <2014-03-04 tue.> |\n| <2012-03-29 thu.> |\n| <2008-08-08 sat.> |\n"
1665 (org-test-with-temp-text
1666 "| <2014-03-04 tue.> |\n| <2008-08-08 sat.> |\n| <2012-03-29 thu.> |\n"
1667 (org-table-sort-lines nil ?T)
1668 (buffer-string))))
1669 ;; Sort by time (HH:MM values)
1670 (should
1671 (equal "| 1:00 |\n| 14:00 |\n| 17:00 |\n"
1672 (org-test-with-temp-text "| 14:00 |\n| 17:00 |\n| 1:00 |\n"
1673 (org-table-sort-lines nil ?t)
1674 (buffer-string))))
1675 (should
1676 (equal "| 17:00 |\n| 14:00 |\n| 1:00 |\n"
1677 (org-test-with-temp-text "| 14:00 |\n| 17:00 |\n| 1:00 |\n"
1678 (org-table-sort-lines nil ?T)
1679 (buffer-string))))
1680 ;; Sort with custom functions.
1681 (should
1682 (equal "| 22 |\n| 15 |\n| 18 |\n"
1683 (org-test-with-temp-text "| 15 |\n| 22 |\n| 18 |\n"
1684 (org-table-sort-lines nil ?f
1685 (lambda (s) (% (string-to-number s) 10))
1686 #'<)
1687 (buffer-string))))
1688 (should
1689 (equal "| 18 |\n| 15 |\n| 22 |\n"
1690 (org-test-with-temp-text "| 15 |\n| 22 |\n| 18 |\n"
1691 (org-table-sort-lines nil ?F
1692 (lambda (s) (% (string-to-number s) 10))
1693 #'<)
1694 (buffer-string))))
1695 ;; Sort according to current column.
1696 (should
1697 (equal "| 1 | 2 |\n| 7 | 3 |\n| 5 | 4 |\n"
1698 (org-test-with-temp-text "| 1 | <point>2 |\n| 5 | 4 |\n| 7 | 3 |\n"
1699 (org-table-sort-lines nil ?n)
1700 (buffer-string))))
1701 ;; Sort between horizontal separators if possible.
1702 (should
1703 (equal
1704 "| 9 | 8 |\n|---+---|\n| 5 | 3 |\n| 7 | 4 |\n|---+---|\n| 1 | 2 |\n"
1705 (org-test-with-temp-text
1706 "| 9 | 8 |\n|---+---|\n| <point>7 | 4 |\n| 5 | 3 |\n|---+---|\n| 1 | 2 |\n"
1707 (org-table-sort-lines nil ?n)
1708 (buffer-string)))))
1711 ;;; Formulas
1713 (ert-deftest test-org-table/eval-formula ()
1714 "Test `org-table-eval-formula' specifications."
1715 ;; Error when not on a table field.
1716 (should-error
1717 (org-test-with-temp-text "Text"
1718 (org-table-eval-formula)))
1719 (should-error
1720 (org-test-with-temp-text "| a |\n|---|<point>"
1721 (org-table-eval-formula)))
1722 (should-error
1723 (org-test-with-temp-text "| a |\n#+TBLFM:<point>"
1724 (org-table-eval-formula)))
1725 ;; Handle @<, @>, $< and $>.
1726 (should
1727 (equal "| 1 |\n| 1 |"
1728 (org-test-with-temp-text "| <point> |\n| 1 |"
1729 (org-table-eval-formula nil "@>" nil nil t)
1730 (buffer-string))))
1731 (should
1732 (equal "| 1 |\n| 1 |"
1733 (org-test-with-temp-text "| 1 |\n| <point> |"
1734 (org-table-eval-formula nil "@<" nil nil t)
1735 (buffer-string))))
1736 (should
1737 (equal "| 1 | 1 |"
1738 (org-test-with-temp-text "| <point> | 1 |"
1739 (org-table-eval-formula nil "$>" nil nil t)
1740 (buffer-string))))
1741 (should
1742 (equal "| 1 | 1 |"
1743 (org-test-with-temp-text "| 1 | <point> |"
1744 (org-table-eval-formula nil "$<" nil nil t)
1745 (buffer-string)))))
1747 (ert-deftest test-org-table/field-formula-outside-table ()
1748 "If `org-table-formula-create-columns' is nil, then a formula
1749 that references an out-of-bounds column should do nothing. If it
1750 is t, then new columns should be added as needed"
1752 (let ((org-table-formula-create-columns nil))
1754 (should-error
1755 (org-test-table-target-expect
1757 | 2 |
1758 | 4 |
1759 | 8 |
1762 | 2 |
1763 | 4 |
1764 | 8 |
1767 "#+TBLFM: @1$2=5")
1768 :type (list 'error 'user-error)))
1770 (let ((org-table-formula-create-columns t))
1772 ;; make sure field formulas work
1773 (org-test-table-target-expect
1775 | 2 |
1776 | 4 |
1777 | 8 |
1780 | 2 | 5 |
1781 | 4 | |
1782 | 8 | |
1785 "#+TBLFM: @1$2=5")
1787 ;; and make sure column formulas work too
1788 (org-test-table-target-expect
1790 | 2 |
1791 | 4 |
1792 | 8 |
1795 | 2 | | 15 |
1796 | 4 | | 15 |
1797 | 8 | | 15 |
1800 "#+TBLFM: $3=15")))
1802 (ert-deftest test-org-table/duration ()
1803 "Test durations in table formulas."
1804 ;; Durations in cells.
1805 (should
1806 (string-match "| 2:12 | 1:47 | 03:59:00 |"
1807 (org-test-with-temp-text "
1808 | 2:12 | 1:47 | |
1809 <point>#+TBLFM: @1$3=$1+$2;T"
1810 (org-table-calc-current-TBLFM)
1811 (buffer-string))))
1812 (should
1813 (string-match "| 3:02:20 | -2:07:00 | 0.92 |"
1814 (org-test-with-temp-text "
1815 | 3:02:20 | -2:07:00 | |
1816 <point>#+TBLFM: @1$3=$1+$2;t"
1817 (org-table-calc-current-TBLFM)
1818 (buffer-string))))
1819 ;; Durations set through properties.
1820 (should
1821 (string-match "| 16:00:00 |"
1822 (org-test-with-temp-text "* H
1823 :PROPERTIES:
1824 :time_constant: 08:00:00
1825 :END:
1828 <point>#+TBLFM: $1=2*$PROP_time_constant;T"
1829 (org-table-calc-current-TBLFM)
1830 (buffer-string))))
1831 (should
1832 (string-match "| 16.00 |"
1833 (org-test-with-temp-text "* H
1834 :PROPERTIES:
1835 :time_constant: 08:00:00
1836 :END:
1839 <point>#+TBLFM: $1=2*$PROP_time_constant;t"
1840 (org-table-calc-current-TBLFM)
1841 (buffer-string)))))
1843 (ert-deftest test-org-table/end-on-hline ()
1844 "Test with a table ending on a hline."
1845 (should
1846 (equal
1847 (org-test-with-temp-text
1849 | 1 | 2 | 3 |
1850 | 4 | 5 | 6 |
1851 | | | |
1852 |---+---+---|
1853 <point>#+TBLFM: @3$2..@3$>=vsum(@1..@2)"
1854 (org-table-calc-current-TBLFM)
1855 (buffer-string))
1857 | 1 | 2 | 3 |
1858 | 4 | 5 | 6 |
1859 | | 7 | 9 |
1860 |---+---+---|
1861 #+TBLFM: @3$2..@3$>=vsum(@1..@2)")))
1863 (ert-deftest test-org-table/named-field ()
1864 "Test formula with a named field."
1865 (should
1866 (string-match-p
1867 "| +| +1 +|"
1868 (org-test-with-temp-text "
1869 | | |
1870 | ^ | name |
1871 <point>#+TBLFM: $name=1"
1872 (org-table-calc-current-TBLFM)
1873 (buffer-string))))
1874 (should
1875 (string-match-p
1876 "| +| +1 +|"
1877 (org-test-with-temp-text "
1878 | _ | name |
1879 | | |
1880 <point>#+TBLFM: $name=1"
1881 (org-table-calc-current-TBLFM)
1882 (buffer-string)))))
1884 (ert-deftest test-org-table/named-column ()
1885 "Test formula with a named field."
1886 (should
1887 (string-match-p
1888 "| +| +1 +| +1 +|"
1889 (org-test-with-temp-text "
1890 | ! | name | |
1891 | | 1 | |
1892 <point>#+TBLFM: @2$3=$name"
1893 (org-table-calc-current-TBLFM)
1894 (buffer-string)))))
1896 (ert-deftest test-org-table/tab-indent ()
1897 "Test named fields with tab indentation."
1898 (should
1899 (string-match-p
1900 "| # | 111 |"
1901 (org-test-with-temp-text
1903 | ! | sum | | a | b | c |
1904 |---+------+------+---+----+-----|
1905 | # | 1011 | 1000 | 1 | 10 | 100 |
1906 <point>#+TBLFM: $2=$a+$b+$c
1908 (org-table-calc-current-TBLFM)
1909 (buffer-string)))))
1911 (ert-deftest test-org-table/first-rc ()
1912 "Test \"$<\" and \"@<\" constructs in formulas."
1913 (should
1914 (string-match-p
1915 "| 1 | 2 |"
1916 (org-test-with-temp-text
1917 "| | 2 |
1918 <point>#+TBLFM: $<=1"
1919 (org-table-calc-current-TBLFM)
1920 (buffer-string))))
1921 (should
1922 (string-match-p
1923 "| 2 |\n| 2 |"
1924 (org-test-with-temp-text
1925 "| 2 |\n| |
1926 <point>#+TBLFM: @2$1=@<"
1927 (org-table-calc-current-TBLFM)
1928 (buffer-string)))))
1930 (ert-deftest test-org-table/last-rc ()
1931 "Test \"$>\" and \"@>\" constructs in formulas."
1932 (should
1933 (string-match-p
1934 "| 2 | 1 |"
1935 (org-test-with-temp-text
1936 "| 2 | |\n<point>#+TBLFM: $>=1"
1937 (org-table-calc-current-TBLFM)
1938 (buffer-string))))
1939 (should
1940 (string-match-p
1941 "| 2 |\n| 2 |"
1942 (org-test-with-temp-text
1943 "| 2 |\n| |\n<point>#+TBLFM: @>$1=@<"
1944 (org-table-calc-current-TBLFM)
1945 (buffer-string)))))
1947 (ert-deftest test-org-table/time-stamps ()
1948 "Test time-stamps handling."
1949 ;; Standard test.
1950 (should
1951 (string-match-p
1952 "| 1 |"
1953 (org-test-with-temp-text
1954 "| <2016-07-07 Sun> | <2016-07-08 Fri> | |\n<point>#+TBLFM: $3=$2-$1"
1955 (org-table-calc-current-TBLFM)
1956 (buffer-string))))
1957 ;; Handle locale specific time-stamps.
1958 (should
1959 (string-match-p
1960 "| 1 |"
1961 (org-test-with-temp-text
1962 "| <2016-07-07 Do> | <2016-07-08 Fr> | |\n<point>#+TBLFM: $3=$2-$1"
1963 (org-table-calc-current-TBLFM)
1964 (buffer-string)))))
1967 (ert-deftest test-org-table/orgtbl-ascii-draw ()
1968 "Test `orgtbl-ascii-draw'."
1969 ;; First value: Make sure that an integer input value is converted to a
1970 ;; float before division. Further values: Show some float input value
1971 ;; ranges corresponding to the same bar width.
1972 (should
1973 (equal
1974 (org-test-with-temp-text
1976 | Value | <l> |
1977 |----------+---------|
1978 | 19 | replace |
1979 |----------+---------|
1980 | -0.50001 | replace |
1981 | -0.49999 | replace |
1982 | 0.49999 | replace |
1983 | 0.50001 | replace |
1984 | 1.49999 | replace |
1985 | 22.50001 | replace |
1986 | 23.49999 | replace |
1987 | 23.50001 | replace |
1988 | 24.49999 | replace |
1989 | 24.50001 | replace |
1990 <point>#+TBLFM: $2 = '(orgtbl-ascii-draw $1 0 24 3 \" 12345678\")"
1991 (org-table-calc-current-TBLFM)
1992 (buffer-string))
1994 | Value | <l> |
1995 |----------+-----------|
1996 | 19 | 883 |
1997 |----------+-----------|
1998 | -0.50001 | too small |
1999 | -0.49999 | |
2000 | 0.49999 | |
2001 | 0.50001 | 1 |
2002 | 1.49999 | 1 |
2003 | 22.50001 | 887 |
2004 | 23.49999 | 887 |
2005 | 23.50001 | 888 |
2006 | 24.49999 | 888 |
2007 | 24.50001 | too large |
2008 #+TBLFM: $2 = '(orgtbl-ascii-draw $1 0 24 3 \" 12345678\")"))
2009 ;; Draw bars with a bullet. The bullet does not count in the parameter
2010 ;; WIDTH of `orgtbl-ascii-draw'.
2011 (should
2012 (equal
2013 (org-test-with-temp-text
2015 | -1 | replace |
2016 | 0 | replace |
2017 | 1 | replace |
2018 | 2 | replace |
2019 | 3 | replace |
2020 | 4 | replace |
2021 <point>#+TBLFM: $2 = '(orgtbl-ascii-draw $1 0 3 3 \"$-\")"
2022 (org-table-calc-current-TBLFM)
2023 (buffer-string))
2025 | -1 | too small |
2026 | 0 | $ |
2027 | 1 | -$ |
2028 | 2 | --$ |
2029 | 3 | ---$ |
2030 | 4 | too large |
2031 #+TBLFM: $2 = '(orgtbl-ascii-draw $1 0 3 3 \"$-\")")))
2033 (ert-deftest test-org-table/single-rowgroup ()
2034 "Test column formula in a table with a single rowgroup."
2035 (should
2036 (equal
2038 |---+---|
2039 | 1 | 0 |
2040 |---+---|
2041 #+TBLFM: $2=$1-1"
2042 (org-test-with-temp-text "
2043 |---+---|
2044 | 1 | |
2045 |---+---|
2046 <point>#+TBLFM: $2=$1-1"
2047 (org-table-calc-current-TBLFM)
2048 (buffer-string))))
2049 (should
2050 (equal
2052 | 1 | 0 |
2053 #+TBLFM: $2=$1-1"
2054 (org-test-with-temp-text "
2055 | 1 | |
2056 <point>#+TBLFM: $2=$1-1"
2057 (org-table-calc-current-TBLFM)
2058 (buffer-string)))))
2061 ;;; Navigation
2063 (ert-deftest test-org-table/next-field ()
2064 "Test `org-table-next-field' specifications."
2065 ;; Regular test.
2066 (should
2067 (equal
2069 (org-test-with-temp-text "| a<point> | b |"
2070 (org-table-next-field)
2071 (org-trim (org-table-get-field)))))
2072 ;; Create new rows as needed.
2073 (should
2074 (equal
2075 "| a |\n| |\n"
2076 (org-test-with-temp-text "| a<point> |"
2077 (org-table-next-field)
2078 (buffer-string))))
2079 ;; Jump over hlines, if `org-table-tab-jumps-over-hlines' is
2080 ;; non-nil.
2081 (should
2082 (equal
2084 (org-test-with-temp-text "| a<point> |\n|---|\n| b |"
2085 (let ((org-table-tab-jumps-over-hlines t)) (org-table-next-field))
2086 (org-trim (org-table-get-field)))))
2087 ;; If `org-table-tab-jumps-over-hlines' is nil, however, create
2088 ;; a new row before the rule.
2089 (should
2090 (equal
2091 "| a |\n| |\n|---|\n| b |"
2092 (org-test-with-temp-text "| a<point> |\n|---|\n| b |"
2093 (let ((org-table-tab-jumps-over-hlines nil)) (org-table-next-field))
2094 (buffer-string)))))
2096 (provide 'test-org-table)
2098 ;;; test-org-table.el ends here