Move new export framework files into core
[org-mode.git] / lisp / ox-beamer.el
blobe9697f4050f4ad9ddb6a1d3b6b30f423e52f1928
1 ;;; ox-beamer.el --- Beamer Back-End for Org Export Engine
3 ;; Copyright (C) 2007-2013 Free Software Foundation, Inc.
5 ;; Author: Carsten Dominik <carsten.dominik AT gmail DOT com>
6 ;; Nicolas Goaziou <n.goaziou AT gmail DOT com>
7 ;; Keywords: org, wp, tex
9 ;; GNU Emacs is free software: you can redistribute it and/or modify
10 ;; it under the terms of the GNU General Public License as published by
11 ;; the Free Software Foundation, either version 3 of the License, or
12 ;; (at your option) any later version.
14 ;; GNU Emacs is distributed in the hope that it will be useful,
15 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
16 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 ;; GNU General Public License for more details.
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>.
22 ;;; Commentary:
24 ;; This library implements both a Beamer back-end, derived from the
25 ;; LaTeX one and a minor mode easing structure edition of the
26 ;; document.
28 ;; Depending on the desired output format, three commands are provided
29 ;; for export: `org-beamer-export-as-latex' (temporary buffer),
30 ;; `org-beamer-export-to-latex' ("tex" file) and
31 ;; `org-beamer-export-to-pdf' ("pdf" file).
33 ;; This back-end supports every buffer keyword, attribute and options
34 ;; items (see `org-latex-options-alist') already supported by `latex'
35 ;; back-end. As such, it is suggested to add an entry in
36 ;; `org-latex-classes' variable which is appropriate for Beamer
37 ;; export.
39 ;; On top of this, the `beamer' back-end also introduces the following
40 ;; keywords: "BEAMER_THEME", "BEAMER_COLOR_THEME",
41 ;; "BEAMER_FONT_THEME", "BEAMER_INNER_THEME" and "BEAMER_OUTER_THEME".
42 ;; All accept options in square brackets.
44 ;; Moreover, headlines now fall into three categories: sectioning
45 ;; elements, frames and blocks.
47 ;; - Like `latex' back-end sectioning elements are still set through
48 ;; `org-latex-classes' variable.
50 ;; - Headlines become frames when their level is equal to
51 ;; `org-beamer-frame-level' (or "H" value in the OPTIONS line).
52 ;; Though, if an headline in the current tree has a "BEAMER_env"
53 ;; (see below) property set to either "frame" or "fullframe", its
54 ;; level overrides the variable. A "fullframe" is a frame with an
55 ;; empty (ignored) title.
57 ;; - All frames' children become block environments. Special block
58 ;; types can be enforced by setting headline's "BEAMER_env" property
59 ;; to an appropriate value (see `org-beamer-environments-default'
60 ;; for supported value and `org-beamer-environments-extra' for
61 ;; adding more).
63 ;; - As a special case, if the "BEAMER_env" property is set to either
64 ;; "appendix", "note", "noteNH" or "againframe", the headline will
65 ;; become, respectively, an appendix, a note (within frame or
66 ;; between frame, depending on its level), a note with its title
67 ;; ignored or an againframe command. In the latter case,
68 ;; a "BEAMER_ref" property is mandatory in order to refer to the
69 ;; frame being resumed, and contents are ignored.
71 ;; Also, an headline with an "ignoreheading" value will have its
72 ;; contents only inserted in the output. This special value is
73 ;; useful to have data between frames, or to properly close
74 ;; a "column" environment.
76 ;; Along with "BEAMER_env", headlines also support "BEAMER_act" and
77 ;; "BEAMER_opt" properties. The former is translated as an
78 ;; overlay/action specification (or a default overlay specification
79 ;; when enclosed within square brackets) whereas the latter specifies
80 ;; options for the current frame ("fragile" option is added
81 ;; automatically, though).
83 ;; Every plain list has support for `:environment', `:overlay' and
84 ;; `:options' attributes (through ATTR_BEAMER affiliated keyword).
85 ;; The first one allows to use a different environment, the second
86 ;; sets overlay specifications and the last one inserts optional
87 ;; arguments in current list environment.
89 ;; Eventually, an export snippet with a value enclosed within angular
90 ;; brackets put at the beginning of an element or object whose type is
91 ;; among `bold', `item', `link', `radio-target' and `target' will
92 ;; control its overlay specifications.
94 ;; On the minor mode side, `org-beamer-select-environment' (bound by
95 ;; default to "C-c C-b") and `org-beamer-insert-options-template' are
96 ;; the two entry points.
98 ;;; Code:
100 (require 'ox-latex)
104 ;;; User-Configurable Variables
106 (defgroup org-export-beamer nil
107 "Options specific for using the beamer class in LaTeX export."
108 :tag "Org Beamer"
109 :group 'org-export
110 :version "24.2")
112 (defcustom org-beamer-frame-level 1
113 "The level at which headlines become frames.
115 Headlines at a lower level will be translated into a sectioning
116 structure. At a higher level, they will be translated into
117 blocks.
119 If an headline with a \"BEAMER_env\" property set to \"frame\" is
120 found within a tree, its level locally overrides this number.
122 This variable has no effect on headlines with the \"BEAMER_env\"
123 property set to either \"ignoreheading\", \"appendix\", or
124 \"note\", which will respectively, be invisible, become an
125 appendix or a note.
127 This integer is relative to the minimal level of an headline
128 within the parse tree, defined as 1."
129 :group 'org-export-beamer
130 :type 'integer)
132 (defcustom org-beamer-frame-default-options ""
133 "Default options string to use for frames.
134 For example, it could be set to \"allowframebreaks\"."
135 :group 'org-export-beamer
136 :type '(string :tag "[options]"))
138 (defcustom org-beamer-column-view-format
139 "%45ITEM %10BEAMER_env(Env) %10BEAMER_act(Act) %4BEAMER_col(Col) %8BEAMER_opt(Opt)"
140 "Column view format that should be used to fill the template."
141 :group 'org-export-beamer
142 :type '(choice
143 (const :tag "Do not insert Beamer column view format" nil)
144 (string :tag "Beamer column view format")))
146 (defcustom org-beamer-theme "default"
147 "Default theme used in Beamer presentations."
148 :group 'org-export-beamer
149 :type '(choice
150 (const :tag "Do not insert a Beamer theme" nil)
151 (string :tag "Beamer theme")))
153 (defcustom org-beamer-environments-extra nil
154 "Environments triggered by tags in Beamer export.
155 Each entry has 4 elements:
157 name Name of the environment
158 key Selection key for `org-beamer-select-environment'
159 open The opening template for the environment, with the following escapes
160 %a the action/overlay specification
161 %A the default action/overlay specification
162 %o the options argument of the template
163 %h the headline text
164 %H if there is headline text, that text in {} braces
165 %U if there is headline text, that text in [] brackets
166 close The closing string of the environment."
167 :group 'org-export-beamer
168 :type '(repeat
169 (list
170 (string :tag "Environment")
171 (string :tag "Selection key")
172 (string :tag "Begin")
173 (string :tag "End"))))
175 (defcustom org-beamer-outline-frame-title "Outline"
176 "Default title of a frame containing an outline."
177 :group 'org-export-beamer
178 :type '(string :tag "Outline frame title"))
180 (defcustom org-beamer-outline-frame-options ""
181 "Outline frame options appended after \\begin{frame}.
182 You might want to put e.g. \"allowframebreaks=0.9\" here."
183 :group 'org-export-beamer
184 :type '(string :tag "Outline frame options"))
188 ;;; Internal Variables
190 (defconst org-beamer-column-widths
191 "0.1 0.2 0.3 0.4 0.5 0.6 0.7 0.8 0.9 0.0 :ETC"
192 "The column widths that should be installed as allowed property values.")
194 (defconst org-beamer-environments-special
195 '(("againframe" "A")
196 ("appendix" "x")
197 ("column" "c")
198 ("columns" "C")
199 ("frame" "f")
200 ("fullframe" "F")
201 ("ignoreheading" "i")
202 ("note" "n")
203 ("noteNH" "N"))
204 "Alist of environments treated in a special way by the back-end.
205 Keys are environment names, as strings, values are bindings used
206 in `org-beamer-select-environment'. Environments listed here,
207 along with their binding, are hard coded and cannot be modified
208 through `org-beamer-environments-extra' variable.")
210 (defconst org-beamer-environments-default
211 '(("block" "b" "\\begin{block}%a{%h}" "\\end{block}")
212 ("alertblock" "a" "\\begin{alertblock}%a{%h}" "\\end{alertblock}")
213 ("verse" "v" "\\begin{verse}%a %% %h" "\\end{verse}")
214 ("quotation" "q" "\\begin{quotation}%a %% %h" "\\end{quotation}")
215 ("quote" "Q" "\\begin{quote}%a %% %h" "\\end{quote}")
216 ("structureenv" "s" "\\begin{structureenv}%a %% %h" "\\end{structureenv}")
217 ("theorem" "t" "\\begin{theorem}%a%U" "\\end{theorem}")
218 ("definition" "d" "\\begin{definition}%a%U" "\\end{definition}")
219 ("example" "e" "\\begin{example}%a%U" "\\end{example}")
220 ("exampleblock" "E" "\\begin{exampleblock}%a{%h}" "\\end{exampleblock}")
221 ("proof" "p" "\\begin{proof}%a%U" "\\end{proof}")
222 ("beamercolorbox" "o" "\\begin{beamercolorbox}%o{%h}" "\\end{beamercolorbox}"))
223 "Environments triggered by properties in Beamer export.
224 These are the defaults - for user definitions, see
225 `org-beamer-environments-extra'.")
227 (defconst org-beamer-verbatim-elements
228 '(code example-block fixed-width inline-src-block src-block verbatim)
229 "List of element or object types producing verbatim text.
230 This is used internally to determine when a frame should have the
231 \"fragile\" option.")
235 ;;; Internal functions
237 (defun org-beamer--normalize-argument (argument type)
238 "Return ARGUMENT string with proper boundaries.
240 TYPE is a symbol among the following:
241 `action' Return ARGUMENT within angular brackets.
242 `defaction' Return ARGUMENT within both square and angular brackets.
243 `option' Return ARGUMENT within square brackets."
244 (if (not (string-match "\\S-" argument)) ""
245 (case type
246 (action (if (string-match "\\`<.*>\\'" argument) argument
247 (format "<%s>" argument)))
248 (defaction (cond
249 ((string-match "\\`\\[<.*>\\]\\'" argument) argument)
250 ((string-match "\\`<.*>\\'" argument)
251 (format "[%s]" argument))
252 ((string-match "\\`\\[\\(.*\\)\\]\\'" argument)
253 (format "[<%s>]" (match-string 1 argument)))
254 (t (format "[<%s>]" argument))))
255 (option (if (string-match "\\`\\[.*\\]\\'" argument) argument
256 (format "[%s]" argument)))
257 (otherwise argument))))
259 (defun org-beamer--element-has-overlay-p (element)
260 "Non-nil when ELEMENT has an overlay specified.
261 An element has an overlay specification when it starts with an
262 `beamer' export-snippet whose value is between angular brackets.
263 Return overlay specification, as a string, or nil."
264 (let ((first-object (car (org-element-contents element))))
265 (when (eq (org-element-type first-object) 'export-snippet)
266 (let ((value (org-element-property :value first-object)))
267 (and (string-match "\\`<.*>\\'" value) value)))))
271 ;;; Define Back-End
273 (org-export-define-derived-backend beamer latex
274 :export-block "BEAMER"
275 :menu-entry
276 (?l 1
277 ((?B "As TEX buffer (Beamer)" org-beamer-export-as-latex)
278 (?b "As TEX file (Beamer)" org-beamer-export-to-latex)
279 (?P "As PDF file (Beamer)" org-beamer-export-to-pdf)
280 (?O "As PDF file and open (Beamer)"
281 (lambda (a s v b)
282 (if a (org-beamer-export-to-pdf t s v b)
283 (org-open-file (org-beamer-export-to-pdf nil s v b)))))))
284 :options-alist
285 ((:beamer-theme "BEAMER_THEME" nil org-beamer-theme)
286 (:beamer-color-theme "BEAMER_COLOR_THEME" nil nil t)
287 (:beamer-font-theme "BEAMER_FONT_THEME" nil nil t)
288 (:beamer-inner-theme "BEAMER_INNER_THEME" nil nil t)
289 (:beamer-outer-theme "BEAMER_OUTER_THEME" nil nil t)
290 (:headline-levels nil "H" org-beamer-frame-level))
291 :translate-alist ((bold . org-beamer-bold)
292 (export-block . org-beamer-export-block)
293 (export-snippet . org-beamer-export-snippet)
294 (headline . org-beamer-headline)
295 (item . org-beamer-item)
296 (keyword . org-beamer-keyword)
297 (link . org-beamer-link)
298 (plain-list . org-beamer-plain-list)
299 (radio-target . org-beamer-radio-target)
300 (target . org-beamer-target)
301 (template . org-beamer-template)))
305 ;;; Transcode Functions
307 ;;;; Bold
309 (defun org-beamer-bold (bold contents info)
310 "Transcode BLOCK object into Beamer code.
311 CONTENTS is the text being bold. INFO is a plist used as
312 a communication channel."
313 (format "\\alert%s{%s}"
314 (or (org-beamer--element-has-overlay-p bold) "")
315 contents))
318 ;;;; Export Block
320 (defun org-beamer-export-block (export-block contents info)
321 "Transcode an EXPORT-BLOCK element into Beamer code.
322 CONTENTS is nil. INFO is a plist used as a communication
323 channel."
324 (when (member (org-element-property :type export-block) '("BEAMER" "LATEX"))
325 (org-remove-indentation (org-element-property :value export-block))))
328 ;;;; Export Snippet
330 (defun org-beamer-export-snippet (export-snippet contents info)
331 "Transcode an EXPORT-SNIPPET object into Beamer code.
332 CONTENTS is nil. INFO is a plist used as a communication
333 channel."
334 (let ((backend (org-export-snippet-backend export-snippet))
335 (value (org-element-property :value export-snippet)))
336 ;; Only "latex" and "beamer" snippets are retained.
337 (cond ((eq backend 'latex) value)
338 ;; Ignore "beamer" snippets specifying overlays.
339 ((and (eq backend 'beamer)
340 (or (org-export-get-previous-element export-snippet info)
341 (not (string-match "\\`<.*>\\'" value))))
342 value))))
345 ;;;; Headline
347 ;; The main function to translate an headline is
348 ;; `org-beamer-headline'.
350 ;; Depending on the level at which an headline is considered as
351 ;; a frame (given by `org-beamer--frame-level'), the headline is
352 ;; either a section (`org-beamer--format-section'), a frame
353 ;; (`org-beamer--format-frame') or a block
354 ;; (`org-beamer--format-block').
356 ;; `org-beamer-headline' also takes care of special environments
357 ;; like "ignoreheading", "note", "noteNH", "appendix" and
358 ;; "againframe".
360 (defun org-beamer--get-label (headline info)
361 "Return label for HEADLINE, as a string.
363 INFO is a plist used as a communication channel.
365 The value is either the label specified in \"BEAMER_opt\"
366 property, or a fallback value built from headline's number. This
367 function assumes HEADLINE will be treated as a frame."
368 (let ((opt (org-element-property :beamer-opt headline)))
369 (if (and (org-string-nw-p opt)
370 (string-match "\\(?:^\\|,\\)label=\\(.*?\\)\\(?:$\\|,\\)" opt))
371 (match-string 1 opt)
372 (format "sec-%s"
373 (mapconcat 'number-to-string
374 (org-export-get-headline-number headline info)
375 "-")))))
377 (defun org-beamer--frame-level (headline info)
378 "Return frame level in subtree containing HEADLINE.
379 INFO is a plist used as a communication channel."
381 ;; 1. Look for "frame" environment in parents, starting from the
382 ;; farthest.
383 (catch 'exit
384 (mapc (lambda (parent)
385 (let ((env (org-element-property :beamer-env parent)))
386 (when (and env (member (downcase env) '("frame" "fullframe")))
387 (throw 'exit (org-export-get-relative-level parent info)))))
388 (nreverse (org-export-get-genealogy headline)))
389 nil)
390 ;; 2. Look for "frame" environment in HEADLINE.
391 (let ((env (org-element-property :beamer-env headline)))
392 (and env (member (downcase env) '("frame" "fullframe"))
393 (org-export-get-relative-level headline info)))
394 ;; 3. Look for "frame" environment in sub-tree.
395 (org-element-map headline 'headline
396 (lambda (hl)
397 (let ((env (org-element-property :beamer-env hl)))
398 (when (and env (member (downcase env) '("frame" "fullframe")))
399 (org-export-get-relative-level hl info))))
400 info 'first-match)
401 ;; 4. No "frame" environment in tree: use default value.
402 (plist-get info :headline-levels)))
404 (defun org-beamer--format-section (headline contents info)
405 "Format HEADLINE as a sectioning part.
406 CONTENTS holds the contents of the headline. INFO is a plist
407 used as a communication channel."
408 ;; Use `latex' back-end output, inserting overlay specifications
409 ;; if possible.
410 (let ((latex-headline (org-export-with-backend 'latex headline contents info))
411 (mode-specs (org-element-property :beamer-act headline)))
412 (if (and mode-specs
413 (string-match "\\`\\\\\\(.*?\\)\\(?:\\*\\|\\[.*\\]\\)?{"
414 latex-headline))
415 (replace-match (concat (match-string 1 latex-headline)
416 (format "<%s>" mode-specs))
417 nil nil latex-headline 1)
418 latex-headline)))
420 (defun org-beamer--format-frame (headline contents info)
421 "Format HEADLINE as a frame.
422 CONTENTS holds the contents of the headline. INFO is a plist
423 used as a communication channel."
424 (let ((fragilep
425 ;; FRAGILEP is non-nil when HEADLINE contains an element
426 ;; among `org-beamer-verbatim-elements'.
427 (org-element-map headline org-beamer-verbatim-elements 'identity
428 info 'first-match)))
429 (concat "\\begin{frame}"
430 ;; Overlay specification, if any. When surrounded by
431 ;; square brackets, consider it as a default
432 ;; specification.
433 (let ((action (org-element-property :beamer-act headline)))
434 (cond
435 ((not action) "")
436 ((string-match "\\`\\[.*\\]\\'" action )
437 (org-beamer--normalize-argument action 'defaction))
438 (t (org-beamer--normalize-argument action 'action))))
439 ;; Options, if any.
440 (let* ((beamer-opt (org-element-property :beamer-opt headline))
441 (options
442 ;; Collect options from default value and headline's
443 ;; properties. Also add a label for links.
444 (append
445 (org-split-string org-beamer-frame-default-options ",")
446 (and beamer-opt
447 (org-split-string
448 ;; Remove square brackets if user provided
449 ;; them.
450 (and (string-match "^\\[?\\(.*\\)\\]?$" beamer-opt)
451 (match-string 1 beamer-opt))
452 ","))
453 ;; Provide an automatic label for the frame
454 ;; unless the user specified one.
455 (unless (and beamer-opt
456 (string-match "\\(^\\|,\\)label=" beamer-opt))
457 (list
458 (format "label=%s"
459 (org-beamer--get-label headline info)))))))
460 ;; Change options list into a string.
461 (org-beamer--normalize-argument
462 (mapconcat
463 'identity
464 (if (or (not fragilep) (member "fragile" options)) options
465 (cons "fragile" options))
466 ",")
467 'option))
468 ;; Title.
469 (let ((env (org-element-property :beamer-env headline)))
470 (format "{%s}"
471 (if (and env (equal (downcase env) "fullframe")) ""
472 (org-export-data
473 (org-element-property :title headline) info))))
474 "\n"
475 ;; The following workaround is required in fragile frames
476 ;; as Beamer will append "\par" to the beginning of the
477 ;; contents. So we need to make sure the command is
478 ;; separated from the contents by at least one space. If
479 ;; it isn't, it will create "\parfirst-word" command and
480 ;; remove the first word from the contents in the PDF
481 ;; output.
482 (if (not fragilep) contents
483 (replace-regexp-in-string "\\`\n*" "\\& " contents))
484 "\\end{frame}")))
486 (defun org-beamer--format-block (headline contents info)
487 "Format HEADLINE as a block.
488 CONTENTS holds the contents of the headline. INFO is a plist
489 used as a communication channel."
490 (let* ((column-width (org-element-property :beamer-col headline))
491 ;; ENVIRONMENT defaults to "block" if none is specified and
492 ;; there is no column specification. If there is a column
493 ;; specified but still no explicit environment, ENVIRONMENT
494 ;; is "column".
495 (environment (let ((env (org-element-property :beamer-env headline)))
496 (cond
497 ;; "block" is the fallback environment.
498 ((and (not env) (not column-width)) "block")
499 ;; "column" only.
500 ((not env) "column")
501 ;; Use specified environment.
502 (t (downcase env)))))
503 (env-format (unless (member environment '("column" "columns"))
504 (assoc environment
505 (append org-beamer-environments-special
506 org-beamer-environments-extra
507 org-beamer-environments-default))))
508 (title (org-export-data (org-element-property :title headline) info))
509 (options (let ((options (org-element-property :beamer-opt headline)))
510 (if (not options) ""
511 (org-beamer--normalize-argument options 'option))))
512 ;; Start a "columns" environment when explicitly requested or
513 ;; when there is no previous headline or the previous
514 ;; headline do not have a BEAMER_column property.
515 (parent-env (org-element-property
516 :beamer-env (org-export-get-parent-headline headline)))
517 (start-columns-p
518 (or (equal environment "columns")
519 (and column-width
520 (not (and parent-env
521 (equal (downcase parent-env) "columns")))
522 (or (org-export-first-sibling-p headline info)
523 (not (org-element-property
524 :beamer-col
525 (org-export-get-previous-element
526 headline info)))))))
527 ;; End the "columns" environment when explicitly requested or
528 ;; when there is no next headline or the next headline do not
529 ;; have a BEAMER_column property.
530 (end-columns-p
531 (or (equal environment "columns")
532 (and column-width
533 (not (and parent-env
534 (equal (downcase parent-env) "columns")))
535 (or (org-export-last-sibling-p headline info)
536 (not (org-element-property
537 :beamer-col
538 (org-export-get-next-element headline info))))))))
539 (concat
540 (when start-columns-p
541 ;; Column can accept options only when the environment is
542 ;; explicitly defined.
543 (if (not (equal environment "columns")) "\\begin{columns}\n"
544 (format "\\begin{columns}%s\n" options)))
545 (when column-width
546 (format "\\begin{column}%s{%s}\n"
547 ;; One can specify placement for column only when
548 ;; HEADLINE stands for a column on its own.
549 (if (equal environment "column") options "")
550 (format "%s\\textwidth" column-width)))
551 ;; Block's opening string.
552 (when env-format
553 (concat
554 (org-fill-template
555 (nth 2 env-format)
556 (nconc
557 ;; If BEAMER_act property has its value enclosed in square
558 ;; brackets, it is a default overlay specification and
559 ;; overlay specification is empty. Otherwise, it is an
560 ;; overlay specification and the default one is nil.
561 (let ((action (org-element-property :beamer-act headline)))
562 (cond
563 ((not action) (list (cons "a" "") (cons "A" "")))
564 ((string-match "\\`\\[.*\\]\\'" action)
565 (list
566 (cons "A" (org-beamer--normalize-argument action 'defaction))
567 (cons "a" "")))
569 (list (cons "a" (org-beamer--normalize-argument action 'action))
570 (cons "A" "")))))
571 (list (cons "o" options)
572 (cons "h" title)
573 (cons "H" (if (equal title "") "" (format "{%s}" title)))
574 (cons "U" (if (equal title "") "" (format "[%s]" title))))))
575 "\n"))
576 contents
577 ;; Block's closing string.
578 (when environment (concat (nth 3 env-format) "\n"))
579 (when column-width "\\end{column}\n")
580 (when end-columns-p "\\end{columns}"))))
582 (defun org-beamer-headline (headline contents info)
583 "Transcode HEADLINE element into Beamer code.
584 CONTENTS is the contents of the headline. INFO is a plist used
585 as a communication channel."
586 (unless (org-element-property :footnote-section-p headline)
587 (let ((level (org-export-get-relative-level headline info))
588 (frame-level (org-beamer--frame-level headline info))
589 (environment (let ((env (org-element-property :beamer-env headline)))
590 (if (stringp env) (downcase env) "block"))))
591 (cond
592 ;; Case 1: Resume frame specified by "BEAMER_ref" property.
593 ((equal environment "againframe")
594 (let ((ref (org-element-property :beamer-ref headline)))
595 ;; Reference to frame being resumed is mandatory. Ignore
596 ;; the whole headline if it isn't provided.
597 (when (org-string-nw-p ref)
598 (concat "\\againframe"
599 ;; Overlay specification.
600 (let ((overlay (org-element-property :beamer-act headline)))
601 (when overlay
602 (org-beamer--normalize-argument
603 overlay
604 (if (string-match "^\\[.*\\]$" overlay) 'defaction
605 'action))))
606 ;; Options.
607 (let ((options (org-element-property :beamer-opt headline)))
608 (when options
609 (org-beamer--normalize-argument options 'option)))
610 ;; Resolve reference provided by "BEAMER_ref"
611 ;; property. This is done by building a minimal fake
612 ;; link and calling the appropriate resolve function,
613 ;; depending on the reference syntax.
614 (let* ((type
615 (progn
616 (string-match "^\\(id:\\|#\\|\\*\\)?\\(.*\\)" ref)
617 (cond
618 ((or (not (match-string 1 ref))
619 (equal (match-string 1 ref) "*")) 'fuzzy)
620 ((equal (match-string 1 ref) "id:") 'id)
621 (t 'custom-id))))
622 (link (list 'link (list :path (match-string 2 ref))))
623 (target (if (eq type 'fuzzy)
624 (org-export-resolve-fuzzy-link link info)
625 (org-export-resolve-id-link link info))))
626 ;; Now use user-defined label provided in TARGET
627 ;; headline, or fallback to standard one.
628 (format "{%s}" (org-beamer--get-label target info)))))))
629 ;; Case 2: Creation of an appendix is requested.
630 ((equal environment "appendix")
631 (concat "\\appendix"
632 (org-element-property :beamer-act headline)
633 "\n"
634 (make-string (org-element-property :pre-blank headline) ?\n)
635 contents))
636 ;; Case 3: Ignore heading.
637 ((equal environment "ignoreheading")
638 (concat (make-string (org-element-property :pre-blank headline) ?\n)
639 contents))
640 ;; Case 4: HEADLINE is a note.
641 ((member environment '("note" "noteNH"))
642 (format "\\note{%s}"
643 (concat (and (equal environment "note")
644 (concat
645 (org-export-data
646 (org-element-property :title headline) info)
647 "\n"))
648 (org-trim contents))))
649 ;; Case 5: HEADLINE is a frame.
650 ((= level frame-level)
651 (org-beamer--format-frame headline contents info))
652 ;; Case 6: Regular section, extracted from
653 ;; `org-latex-classes'.
654 ((< level frame-level)
655 (org-beamer--format-section headline contents info))
656 ;; Case 7: Otherwise, HEADLINE is a block.
657 (t (org-beamer--format-block headline contents info))))))
660 ;;;; Item
662 (defun org-beamer-item (item contents info)
663 "Transcode an ITEM element into Beamer code.
664 CONTENTS holds the contents of the item. INFO is a plist holding
665 contextual information."
666 (let ((action (let ((first-element (car (org-element-contents item))))
667 (and (eq (org-element-type first-element) 'paragraph)
668 (org-beamer--element-has-overlay-p first-element))))
669 (output (org-export-with-backend 'latex item contents info)))
670 (if (not action) output
671 ;; If the item starts with a paragraph and that paragraph starts
672 ;; with an export snippet specifying an overlay, insert it after
673 ;; \item command.
674 (replace-regexp-in-string "\\\\item" (concat "\\\\item" action) output))))
677 ;;;; Keyword
679 (defun org-beamer-keyword (keyword contents info)
680 "Transcode a KEYWORD element into Beamer code.
681 CONTENTS is nil. INFO is a plist used as a communication
682 channel."
683 (let ((key (org-element-property :key keyword))
684 (value (org-element-property :value keyword)))
685 ;; Handle specifically BEAMER and TOC (headlines only) keywords.
686 ;; Otherwise, fallback to `latex' back-end.
687 (cond
688 ((equal key "BEAMER") value)
689 ((and (equal key "TOC") (string-match "\\<headlines\\>" value))
690 (let ((depth (or (and (string-match "[0-9]+" value)
691 (string-to-number (match-string 0 value)))
692 (plist-get info :with-toc)))
693 (options (and (string-match "\\[.*?\\]" value)
694 (match-string 0 value))))
695 (concat
696 "\\begin{frame}"
697 (when (wholenump depth) (format "\\setcounter{tocdepth}{%s}\n" depth))
698 "\\tableofcontents" options "\n"
699 "\\end{frame}")))
700 (t (org-export-with-backend 'latex keyword contents info)))))
703 ;;;; Link
705 (defun org-beamer-link (link contents info)
706 "Transcode a LINK object into Beamer code.
707 CONTENTS is the description part of the link. INFO is a plist
708 used as a communication channel."
709 (let ((type (org-element-property :type link))
710 (path (org-element-property :path link)))
711 ;; Use \hyperlink command for all internal links.
712 (cond
713 ((equal type "radio")
714 (let ((destination (org-export-resolve-radio-link link info)))
715 (when destination
716 (format "\\hyperlink%s{%s}{%s}"
717 (or (org-beamer--element-has-overlay-p link) "")
718 (org-export-solidify-link-text path)
719 (org-export-data (org-element-contents destination) info)))))
720 ((and (member type '("custom-id" "fuzzy" "id"))
721 (let ((destination (if (string= type "fuzzy")
722 (org-export-resolve-fuzzy-link link info)
723 (org-export-resolve-id-link link info))))
724 (case (org-element-type destination)
725 (headline
726 (let ((label
727 (format "sec-%s"
728 (mapconcat
729 'number-to-string
730 (org-export-get-headline-number
731 destination info)
732 "-"))))
733 (if (and (plist-get info :section-numbers) (not contents))
734 (format "\\ref{%s}" label)
735 (format "\\hyperlink%s{%s}{%s}"
736 (or (org-beamer--element-has-overlay-p link) "")
737 label
738 contents))))
739 (target
740 (let ((path (org-export-solidify-link-text path)))
741 (if (not contents) (format "\\ref{%s}" path)
742 (format "\\hyperlink%s{%s}{%s}"
743 (or (org-beamer--element-has-overlay-p link) "")
744 path
745 contents))))))))
746 ;; Otherwise, use `latex' back-end.
747 (t (org-export-with-backend 'latex link contents info)))))
750 ;;;; Plain List
752 ;; Plain lists support `:environment', `:overlay' and `:options'
753 ;; attributes.
755 (defun org-beamer-plain-list (plain-list contents info)
756 "Transcode a PLAIN-LIST element into Beamer code.
757 CONTENTS is the contents of the list. INFO is a plist holding
758 contextual information."
759 (let* ((type (org-element-property :type plain-list))
760 (attributes (org-export-read-attribute :attr_beamer plain-list))
761 (latex-type (let ((env (plist-get attributes :environment)))
762 (cond (env (format "%s" env))
763 ((eq type 'ordered) "enumerate")
764 ((eq type 'descriptive) "description")
765 (t "itemize")))))
766 (org-latex--wrap-label
767 plain-list
768 (format "\\begin{%s}%s%s\n%s\\end{%s}"
769 latex-type
770 ;; Default overlay specification, if any.
771 (org-beamer--normalize-argument
772 (format "%s" (or (plist-get attributes :overlay) ""))
773 'defaction)
774 ;; Second optional argument depends on the list type.
775 (org-beamer--normalize-argument
776 (format "%s" (or (plist-get attributes :options) ""))
777 'option)
778 ;; Eventually insert contents and close environment.
779 contents
780 latex-type))))
783 ;;;; Radio Target
785 (defun org-beamer-radio-target (radio-target text info)
786 "Transcode a RADIO-TARGET object into Beamer code.
787 TEXT is the text of the target. INFO is a plist holding
788 contextual information."
789 (format "\\hypertarget%s{%s}{%s}"
790 (or (org-beamer--element-has-overlay-p radio-target) "")
791 (org-export-solidify-link-text
792 (org-element-property :value radio-target))
793 text))
796 ;;;; Target
798 (defun org-beamer-target (target contents info)
799 "Transcode a TARGET object into Beamer code.
800 CONTENTS is nil. INFO is a plist holding contextual
801 information."
802 (format "\\hypertarget{%s}{}"
803 (org-export-solidify-link-text (org-element-property :value target))))
806 ;;;; Template
808 ;; Template used is similar to the one used in `latex' back-end,
809 ;; excepted for the table of contents and Beamer themes.
811 (defun org-beamer-template (contents info)
812 "Return complete document string after Beamer conversion.
813 CONTENTS is the transcoded contents string. INFO is a plist
814 holding export options."
815 (let ((title (org-export-data (plist-get info :title) info)))
816 (concat
817 ;; 1. Time-stamp.
818 (and (plist-get info :time-stamp-file)
819 (format-time-string "%% Created %Y-%m-%d %a %H:%M\n"))
820 ;; 2. Document class and packages.
821 (let ((class (plist-get info :latex-class))
822 (class-options (plist-get info :latex-class-options)))
823 (org-element-normalize-string
824 (let* ((header (nth 1 (assoc class org-latex-classes)))
825 (document-class-string
826 (and (stringp header)
827 (if (not class-options) header
828 (replace-regexp-in-string
829 "^[ \t]*\\\\documentclass\\(\\(\\[.*\\]\\)?\\)"
830 class-options header t nil 1)))))
831 (when document-class-string
832 (org-latex--guess-babel-language
833 (org-latex--guess-inputenc
834 (org-splice-latex-header
835 document-class-string
836 org-export-latex-default-packages-alist ; defined in org.el
837 org-export-latex-packages-alist nil ; defined in org.el
838 (plist-get info :latex-header-extra)))
839 info)))))
840 ;; 3. Insert themes.
841 (let ((format-theme
842 (function
843 (lambda (prop command)
844 (let ((theme (plist-get info prop)))
845 (when theme
846 (concat command
847 (if (not (string-match "\\[.*\\]" theme))
848 (format "{%s}\n" theme)
849 (format "%s{%s}\n"
850 (match-string 0 theme)
851 (org-trim
852 (replace-match "" nil nil theme)))))))))))
853 (mapconcat (lambda (args) (apply format-theme args))
854 '((:beamer-theme "\\usetheme")
855 (:beamer-color-theme "\\usecolortheme")
856 (:beamer-font-theme "\\usefonttheme")
857 (:beamer-inner-theme "\\useinnertheme")
858 (:beamer-outer-theme "\\useoutertheme"))
859 ""))
860 ;; 4. Possibly limit depth for headline numbering.
861 (let ((sec-num (plist-get info :section-numbers)))
862 (when (integerp sec-num)
863 (format "\\setcounter{secnumdepth}{%d}\n" sec-num)))
864 ;; 5. Author.
865 (let ((author (and (plist-get info :with-author)
866 (let ((auth (plist-get info :author)))
867 (and auth (org-export-data auth info)))))
868 (email (and (plist-get info :with-email)
869 (org-export-data (plist-get info :email) info))))
870 (cond ((and author email (not (string= "" email)))
871 (format "\\author{%s\\thanks{%s}}\n" author email))
872 (author (format "\\author{%s}\n" author))
873 (t "\\author{}\n")))
874 ;; 6. Date.
875 (let ((date (and (plist-get info :with-date) (plist-get info :date))))
876 (format "\\date{%s}\n"
877 (cond ((not date) "")
878 ;; If `:date' consists in a single timestamp and
879 ;; `:date-format' is provided, apply it.
880 ((and (plist-get info :date-format)
881 (not (cdr date))
882 (eq (org-element-type (car date)) 'timestamp))
883 (org-timestamp-format
884 (car date) (plist-get info :date-format)))
885 (t (org-export-data date info)))))
886 ;; 7. Title
887 (format "\\title{%s}\n" title)
888 ;; 8. Hyperref options.
889 (when (plist-get info :latex-hyperref-p)
890 (format "\\hypersetup{\n pdfkeywords={%s},\n pdfsubject={%s},\n pdfcreator={%s}}\n"
891 (or (plist-get info :keywords) "")
892 (or (plist-get info :description) "")
893 (if (not (plist-get info :with-creator)) ""
894 (plist-get info :creator))))
895 ;; 9. Document start.
896 "\\begin{document}\n\n"
897 ;; 10. Title command.
898 (org-element-normalize-string
899 (cond ((string= "" title) nil)
900 ((not (stringp org-latex-title-command)) nil)
901 ((string-match "\\(?:[^%]\\|^\\)%s"
902 org-latex-title-command)
903 (format org-latex-title-command title))
904 (t org-latex-title-command)))
905 ;; 11. Table of contents.
906 (let ((depth (plist-get info :with-toc)))
907 (when depth
908 (concat
909 (format "\\begin{frame}%s{%s}\n"
910 (org-beamer--normalize-argument
911 org-beamer-outline-frame-options 'option)
912 org-beamer-outline-frame-title)
913 (when (wholenump depth)
914 (format "\\setcounter{tocdepth}{%d}\n" depth))
915 "\\tableofcontents\n"
916 "\\end{frame}\n\n")))
917 ;; 12. Document's body.
918 contents
919 ;; 13. Creator.
920 (let ((creator-info (plist-get info :with-creator)))
921 (cond
922 ((not creator-info) "")
923 ((eq creator-info 'comment)
924 (format "%% %s\n" (plist-get info :creator)))
925 (t (concat (plist-get info :creator) "\n"))))
926 ;; 14. Document end.
927 "\\end{document}")))
931 ;;; Minor Mode
934 (defvar org-beamer-mode-map (make-sparse-keymap)
935 "The keymap for `org-beamer-mode'.")
936 (define-key org-beamer-mode-map "\C-c\C-b" 'org-beamer-select-environment)
938 ;;;###autoload
939 (define-minor-mode org-beamer-mode
940 "Support for editing Beamer oriented Org mode files."
941 nil " Bm" 'org-beamer-mode-map)
943 (when (fboundp 'font-lock-add-keywords)
944 (font-lock-add-keywords
945 'org-mode
946 '((":\\(B_[a-z]+\\|BMCOL\\):" 1 'org-beamer-tag prepend))
947 'prepend))
949 (defface org-beamer-tag '((t (:box (:line-width 1 :color grey40))))
950 "The special face for beamer tags."
951 :group 'org-export-beamer)
953 (defun org-beamer-property-changed (property value)
954 "Track the BEAMER_env property with tags.
955 PROPERTY is the name of the modified property. VALUE is its new
956 value."
957 (cond
958 ((equal property "BEAMER_env")
959 (save-excursion
960 (org-back-to-heading t)
961 ;; Filter out Beamer-related tags and install environment tag.
962 (let ((tags (org-remove-if (lambda (x) (string-match "^B_" x))
963 (org-get-tags)))
964 (env-tag (and (org-string-nw-p value) (concat "B_" value))))
965 (org-set-tags-to (if env-tag (cons env-tag tags) tags))
966 (when env-tag (org-toggle-tag env-tag 'on)))))
967 ((equal property "BEAMER_col")
968 (org-toggle-tag "BMCOL" (if (org-string-nw-p value) 'on 'off)))))
970 (add-hook 'org-property-changed-functions 'org-beamer-property-changed)
972 (defun org-beamer-allowed-property-values (property)
973 "Supply allowed values for PROPERTY."
974 (cond
975 ((and (equal property "BEAMER_env")
976 (not (org-entry-get nil (concat property "_ALL") 'inherit)))
977 ;; If no allowed values for BEAMER_env have been defined,
978 ;; supply all defined environments
979 (mapcar 'car (append org-beamer-environments-special
980 org-beamer-environments-extra
981 org-beamer-environments-default)))
982 ((and (equal property "BEAMER_col")
983 (not (org-entry-get nil (concat property "_ALL") 'inherit)))
984 ;; If no allowed values for BEAMER_col have been defined,
985 ;; supply some
986 (org-split-string org-beamer-column-widths " "))))
988 (add-hook 'org-property-allowed-value-functions
989 'org-beamer-allowed-property-values)
993 ;;; Commands
995 ;;;###autoload
996 (defun org-beamer-export-as-latex
997 (&optional async subtreep visible-only body-only ext-plist)
998 "Export current buffer as a Beamer buffer.
1000 If narrowing is active in the current buffer, only export its
1001 narrowed part.
1003 If a region is active, export that region.
1005 A non-nil optional argument ASYNC means the process should happen
1006 asynchronously. The resulting buffer should be accessible
1007 through the `org-export-stack' interface.
1009 When optional argument SUBTREEP is non-nil, export the sub-tree
1010 at point, extracting information from the headline properties
1011 first.
1013 When optional argument VISIBLE-ONLY is non-nil, don't export
1014 contents of hidden elements.
1016 When optional argument BODY-ONLY is non-nil, only write code
1017 between \"\\begin{document}\" and \"\\end{document}\".
1019 EXT-PLIST, when provided, is a property list with external
1020 parameters overriding Org default settings, but still inferior to
1021 file-local settings.
1023 Export is done in a buffer named \"*Org BEAMER Export*\", which
1024 will be displayed when `org-export-show-temporary-export-buffer'
1025 is non-nil."
1026 (interactive)
1027 (if async
1028 (org-export-async-start
1029 (lambda (output)
1030 (with-current-buffer (get-buffer-create "*Org BEAMER Export*")
1031 (erase-buffer)
1032 (insert output)
1033 (goto-char (point-min))
1034 (LaTeX-mode)
1035 (org-export-add-to-stack (current-buffer) 'beamer)))
1036 `(org-export-as 'beamer ,subtreep ,visible-only ,body-only
1037 ',ext-plist))
1038 (let ((outbuf (org-export-to-buffer
1039 'beamer "*Org BEAMER Export*"
1040 subtreep visible-only body-only ext-plist)))
1041 (with-current-buffer outbuf (LaTeX-mode))
1042 (when org-export-show-temporary-export-buffer
1043 (switch-to-buffer-other-window outbuf)))))
1045 ;;;###autoload
1046 (defun org-beamer-export-to-latex
1047 (&optional async subtreep visible-only body-only ext-plist)
1048 "Export current buffer as a Beamer presentation (tex).
1050 If narrowing is active in the current buffer, only export its
1051 narrowed part.
1053 If a region is active, export that region.
1055 A non-nil optional argument ASYNC means the process should happen
1056 asynchronously. The resulting file should be accessible through
1057 the `org-export-stack' interface.
1059 When optional argument SUBTREEP is non-nil, export the sub-tree
1060 at point, extracting information from the headline properties
1061 first.
1063 When optional argument VISIBLE-ONLY is non-nil, don't export
1064 contents of hidden elements.
1066 When optional argument BODY-ONLY is non-nil, only write code
1067 between \"\\begin{document}\" and \"\\end{document}\".
1069 EXT-PLIST, when provided, is a property list with external
1070 parameters overriding Org default settings, but still inferior to
1071 file-local settings.
1073 Return output file's name."
1074 (interactive)
1075 (let ((outfile (org-export-output-file-name ".tex" subtreep)))
1076 (if async
1077 (org-export-async-start
1078 (lambda (f) (org-export-add-to-stack f 'beamer))
1079 `(expand-file-name
1080 (org-export-to-file
1081 'beamer ,outfile ,subtreep ,visible-only ,body-only
1082 ',ext-plist)))
1083 (org-export-to-file
1084 'beamer outfile subtreep visible-only body-only ext-plist))))
1086 ;;;###autoload
1087 (defun org-beamer-export-to-pdf
1088 (&optional async subtreep visible-only body-only ext-plist)
1089 "Export current buffer as a Beamer presentation (PDF).
1091 If narrowing is active in the current buffer, only export its
1092 narrowed part.
1094 If a region is active, export that region.
1096 A non-nil optional argument ASYNC means the process should happen
1097 asynchronously. The resulting file should be accessible through
1098 the `org-export-stack' interface.
1100 When optional argument SUBTREEP is non-nil, export the sub-tree
1101 at point, extracting information from the headline properties
1102 first.
1104 When optional argument VISIBLE-ONLY is non-nil, don't export
1105 contents of hidden elements.
1107 When optional argument BODY-ONLY is non-nil, only write code
1108 between \"\\begin{document}\" and \"\\end{document}\".
1110 EXT-PLIST, when provided, is a property list with external
1111 parameters overriding Org default settings, but still inferior to
1112 file-local settings.
1114 Return PDF file's name."
1115 (interactive)
1116 (if async
1117 (let ((outfile (org-export-output-file-name ".tex" subtreep)))
1118 (org-export-async-start
1119 (lambda (f) (org-export-add-to-stack f 'beamer))
1120 `(expand-file-name
1121 (org-latex-compile
1122 (org-export-to-file
1123 'beamer ,outfile ,subtreep ,visible-only ,body-only
1124 ',ext-plist)))))
1125 (org-latex-compile
1126 (org-beamer-export-to-latex
1127 nil subtreep visible-only body-only ext-plist))))
1129 ;;;###autoload
1130 (defun org-beamer-select-environment ()
1131 "Select the environment to be used by beamer for this entry.
1132 While this uses (for convenience) a tag selection interface, the
1133 result of this command will be that the BEAMER_env *property* of
1134 the entry is set.
1136 In addition to this, the command will also set a tag as a visual
1137 aid, but the tag does not have any semantic meaning."
1138 (interactive)
1139 ;; Make sure `org-beamer-environments-special' has a higher
1140 ;; priority than `org-beamer-environments-extra'.
1141 (let* ((envs (append org-beamer-environments-special
1142 org-beamer-environments-extra
1143 org-beamer-environments-default))
1144 (org-tag-alist
1145 (append '((:startgroup))
1146 (mapcar (lambda (e) (cons (concat "B_" (car e))
1147 (string-to-char (nth 1 e))))
1148 envs)
1149 '((:endgroup))
1150 '(("BMCOL" . ?|))))
1151 (org-fast-tag-selection-single-key t))
1152 (org-set-tags)
1153 (let ((tags (or (ignore-errors (org-get-tags-string)) "")))
1154 (cond
1155 ;; For a column, automatically ask for its width.
1156 ((eq org-last-tag-selection-key ?|)
1157 (if (string-match ":BMCOL:" tags)
1158 (org-set-property "BEAMER_col" (read-string "Column width: "))
1159 (org-delete-property "BEAMER_col")))
1160 ;; For an "againframe" section, automatically ask for reference
1161 ;; to resumed frame and overlay specifications.
1162 ((eq org-last-tag-selection-key ?A)
1163 (if (equal (org-entry-get nil "BEAMER_env") "againframe")
1164 (progn (org-entry-delete nil "BEAMER_env")
1165 (org-entry-delete nil "BEAMER_ref")
1166 (org-entry-delete nil "BEAMER_act"))
1167 (org-entry-put nil "BEAMER_env" "againframe")
1168 (org-set-property
1169 "BEAMER_ref"
1170 (read-string "Frame reference (*Title, #custom-id, id:...): "))
1171 (org-set-property "BEAMER_act"
1172 (read-string "Overlay specification: "))))
1173 ((string-match (concat ":B_\\(" (mapconcat 'car envs "\\|") "\\):") tags)
1174 (org-entry-put nil "BEAMER_env" (match-string 1 tags)))
1175 (t (org-entry-delete nil "BEAMER_env"))))))
1177 ;;;###autoload
1178 (defun org-beamer-insert-options-template (&optional kind)
1179 "Insert a settings template, to make sure users do this right."
1180 (interactive (progn
1181 (message "Current [s]ubtree or [g]lobal?")
1182 (if (eq (read-char-exclusive) ?g) (list 'global)
1183 (list 'subtree))))
1184 (if (eq kind 'subtree)
1185 (progn
1186 (org-back-to-heading t)
1187 (org-reveal)
1188 (org-entry-put nil "EXPORT_LaTeX_CLASS" "beamer")
1189 (org-entry-put nil "EXPORT_LaTeX_CLASS_OPTIONS" "[presentation]")
1190 (org-entry-put nil "EXPORT_FILE_NAME" "presentation.pdf")
1191 (when org-beamer-column-view-format
1192 (org-entry-put nil "COLUMNS" org-beamer-column-view-format))
1193 (org-entry-put nil "BEAMER_col_ALL" org-beamer-column-widths))
1194 (insert "#+LaTeX_CLASS: beamer\n")
1195 (insert "#+LaTeX_CLASS_OPTIONS: [presentation]\n")
1196 (when org-beamer-theme (insert "#+BEAMER_THEME: " org-beamer-theme "\n"))
1197 (when org-beamer-column-view-format
1198 (insert "#+COLUMNS: " org-beamer-column-view-format "\n"))
1199 (insert "#+PROPERTY: BEAMER_col_ALL " org-beamer-column-widths "\n")))
1201 ;;;###autoload
1202 (defun org-beamer-publish-to-latex (plist filename pub-dir)
1203 "Publish an Org file to a Beamer presentation (LaTeX).
1205 FILENAME is the filename of the Org file to be published. PLIST
1206 is the property list for the given project. PUB-DIR is the
1207 publishing directory.
1209 Return output file name."
1210 (org-publish-org-to 'beamer filename ".tex" plist pub-dir))
1212 ;;;###autoload
1213 (defun org-beamer-publish-to-pdf (plist filename pub-dir)
1214 "Publish an Org file to a Beamer presentation (PDF, via LaTeX).
1216 FILENAME is the filename of the Org file to be published. PLIST
1217 is the property list for the given project. PUB-DIR is the
1218 publishing directory.
1220 Return output file name."
1221 ;; Unlike to `org-beamer-publish-to-latex', PDF file is generated in
1222 ;; working directory and then moved to publishing directory.
1223 (org-publish-attachment
1224 plist
1225 (org-latex-compile (org-publish-org-to 'beamer filename ".tex" plist))
1226 pub-dir))
1229 (provide 'ox-beamer)
1231 ;; Local variables:
1232 ;; generated-autoload-file: "org-loaddefs.el"
1233 ;; End:
1235 ;;; ox-beamer.el ends here