emacs-orgmode@gnu.org archives
 help / color / mirror / code / Atom feed
* Re: [PATCH][ANN] org-html/org-odt
@ 2011-03-21  9:32 Rustom Mody
  2011-03-21  9:51 ` Jambunathan K
  0 siblings, 1 reply; 23+ messages in thread
From: Rustom Mody @ 2011-03-21  9:32 UTC (permalink / raw)
  To: emacs-orgmode

[-- Attachment #1: Type: text/plain, Size: 177 bytes --]

How does this relate to the docbook exporter?
I ask because I needed a generic exporter (this was more than a year ago)
and I made do with the docbook exporter for that purpose

[-- Attachment #2: Type: text/html, Size: 184 bytes --]

^ permalink raw reply	[flat|nested] 23+ messages in thread
* [PATCH][ANN] org-html/org-odt
@ 2011-03-20 18:32 Jambunathan K
  2011-03-21  8:21 ` Bastien
                   ` (4 more replies)
  0 siblings, 5 replies; 23+ messages in thread
From: Jambunathan K @ 2011-03-20 18:32 UTC (permalink / raw)
  To: emacs-orgmode

[-- Attachment #1: Type: text/plain, Size: 807 bytes --]


This is a formal request to integrate my org-html.el & org-odt.el
changes in to the master branch. 

This patch introduces 3 major features:
1. A generic exporter
2. All new html backend re-implemented as a plugin to (1).
3. A odt backend as a plugin to (1).

The patch is based on git commit 3d802.

I am attaching a sample test.org and test.html file generated by the
above set of changes. 

Http URL for the repo is:
- http://repo.or.cz/w/org-mode/org-jambu.git/shortlog/refs/heads/staging
(`staging' branch of `org-jambu.git')

Let me know if you have any questions. 

ps: Considering the amount of effort I have already invested in these
patches it is almost impossible for me to break down this monolithic
patch in to series of smaller patches. I would be willing to accommodate
all other requests.


[-- Attachment #2: 0001-Re-implement-org-export-as-html-and-add-support-for-.patch --]
[-- Type: text/x-patch, Size: 115753 bytes --]

From 8ebbd9f81a8abb4ccadc25c512119a6369f03406 Mon Sep 17 00:00:00 2001
From: Jambunathan K <kjambunathan@gmail.com>
Date: Sun, 20 Mar 2011 17:37:59 +0530
Subject: [PATCH] Re-implement org-export-as-html and add support for odt backend.

* lisp/org.el (org-structure-template-alist): Allow easy
insertion of odt blocks.

* lisp/org-footnote.el
(insertion-point-for-normalized-footnotes): New variable that
controls the where the normalized footnote definitions are
inserted. Affects only pre-processor related
normalization. html and odt backends bind this to `point-min'
so that the footnote definitions are seen before the footnote
references.
(org-footnote-normalize): Honor above var.

* lisp/org-exp.el (org-export): Register `org-export-as-odt'
and `org-export-as-odt-and-open'. Define default keybindings
for the same.
(org-export-select-backend-specific-text): Register odt.
(org-export-do-format-source-code-or-example): Renamed from
`org-export-fromat-source-code-or-example'.
(org-export-format-source-code-or-example): New
function. Preferentially call backend-specific formatter if
available with a fallback to a generic formatter.

* lisp/org-html.el (org-do-export): The core generic
exporter. Derived from org-export-as-html. Binds
`insertion-point-for-normalized-footnotes' to point-min.

(org-export-as-html): Make use of `org-do-export'.

(org-html-entity-control-callbacks-alist)
(org-html-entity-format-callbacks-alist): New variables.

(org-html-get): Get callback for html backend.

(org-html-get-coding-system-for-save)
(org-html-get-coding-system-for-write): Get routines for html
backend.

(org-html-format-tags, org-html-format-footnotes-section)
(org-html-format-footnote-reference, org-html-format-anchor)
(org-html-format-headline, org-html-format-heading)
(org-html-format-link, org-html-format-fontify)
(org-html-format-comment, org-html-format-plain)
(org-html-format-horizontal-line, org-html-format-line-break)
(org-html-format-tabs, org-html-format-spaces)
(org-html-format-table-cell, org-html-format-table-row)
(org-html-format-toc-item, org-html-format-toc-entry):
Formatting callbacks for html backend.

(org-html-begin-footnote-definition)
(org-html-end-footnote-definition, org-html-end-table)
(org-html-begin-table, org-html-end-table-rowgroup)
(org-html-begin-table-rowgroup, org-html-begin-list-item)
(org-html-end-list-item, org-html-begin-list)
(org-html-end-list)
(org-html-html-list-type-to-canonical-list-type)
(org-html-begin-environment, org-html-end-environment)
(org-html-format-environment, org-html-begin-paragraph)
(org-html-end-paragraph, org-html-begin-section)
(org-html-end-section, org-html-begin-level)
(org-html-end-level, org-html-begin-document-content)
(org-html-end-document-content, org-html-begin-document-body)
(org-html-end-document-body, org-html-end-export): Control
callbacks for html backend.

(org-html-protect): New variable. Controls emitting of
protected tags - @<tag> ... @</tag>
(org-html-emphasis-alist): New variable. Takes over
`org-html-emphasis-alist'.

(org-html-insert-postamble, org-html-insert-preamble): New
functions. Factored out from `org-export-as-html'.

(org-parse-table-of-contents): New variable. Contains table of
contents.
(org-html-prepare-toc): New function that emits table of
contents. Uses a temporary buffer for reaping the table of
contents and sets `org-parse-table-of-contents'.

(org-html-footnote-number, org-html-footnote-definitions): New
variables let bound witin `org-do-export'.
(org-html-footnote-buffer): New variable. The temporary buffer
in which footnote definitions are reaped.
(org-html-output-buffer): New variable. The buffer that holds
the exported output.

(org-table-style, org-table-ncols, org-table-rownum)
(org-table-is-styled, org-table-begin-marker)
(org-table-num-numeric-items-per-column)
(org-table-colalign-info, org-table-colalign-vector)
(org-table-get-colalign-info, org-table-rowgroup-info)
(org-table-rowgroup-open)
(org-table-current-rowgroup-is-header): ): New variables that
are let bound by routines that emit tables
`org-do-format-org-table-html' and
`org-do-format-table-table-html'.
(org-format-org-table-html): Derived from
`org-format-org-table-html'.
(org-do-format-org-table-html): Wrapper around
`org-do-format-org-table-html'. Switches to a temporary buffer
and returns the formattted table as a string.
(org-do-format-table-table-html): Derived from
`org-format-table-table-html'.
(org-format-table-table-html): Wrapper around
`org-do-format-table-table-html'. Switches to a temporary
buffer and returns the formattted table as a string.

(org-html-export-list-line, org-html-format-section-number)
(org-html-format-org-tags, org-html-format-extra-targets)
(org-html-format-todo, org-html-insert-toc)
(org-html-insert-tag, org-html-bind-local-variables): Newly
introduced helper routines.

(org-html-format-org-link): Derived from `org-html-make-link'.

(org-export-html-format-image): Change signature. Use macro
`with-org-html-preserve-paragraph-state'.

(org-html-handle-time-stamps)
(org-export-html-convert-sub-super): Modified.
(org-export-html-convert-emphasize): Modified. Use
`org-html-emphasis-alist' instead of `org-emphasis-alist'.

(org-html-insert-tag-with-newlines): New variable. Controls
inclusion of newlines in the tag related routines.

(org-close-li): Modified.

(org-html-export-list-line): Modified

(org-html-level-start): Renamed to org-html-begin-level.
(org-html-level-close): Renamed to org-html-end-level.

(with-org-html-preserve-paragraph-state): New macro.

(org-open-par): Removed. Superceded by
`org-parse-begin-paragraph'.
(org-close-par-maybe): Removed. Superceded by
`org-parse-end-paragraph'.
(org-close-li): Modified.

(org-parse-debug): New variable. Use this to embed useful
debugging info as comment sections in the exported document.

(org-parse-begin, org-parse-end): Parse routines that invoke
control callbacks on the backend.
(org-parse-format): Parser routine that invokes formatting
callbacks on the backend.
(org-parse-get): Parser routine that invokes the get callback
on the backend.

(org-parse-link-description-is-image)
(org-parse-dyn-current-environment): New variables that are
backend agnostic.

(org-parse-begin-paragraph): Derived from `org-open-par'.
(org-parse-end-paragraph): Derived from `org-close-par-maybe'.
(org-parse-format-org-link, org-parse-format-table-row)
(org-parse-end-table, org-parse-begin-table-rowgroup)
(org-parse-begin-footnote-definition)
(org-parse-end-footnote-definition)
(org-parse-current-environment-p, org-parse-begin-environment)
(org-parse-end-environment): New routines that are backend
agnostic.

* lisp/org-odt.el: New backend file for export to
OpenDocumentText.

* contrib/odt/: New directory. Holds data files used in
conjunction with org-odt.el
* contrib/odt/OrgOdtAutomaticStyles.xml:
* contrib/odt/OrgOdtStyles.xml: Default style file used by
org-odt.el
* contrib/odt/OpenDocument-schema-v1.1.rng: Copy of
http://docs.oasis-open.org/office/v1.1/OS/OpenDocument-schema-v1.1.rng
* contrib/odt/OpenDocument-schema-v1.1.rnc: Relax-NG schema
file for validating OpenDocumentText files. Auto-generated
from rng file using trang -
http://www.thaiopensource.com/relaxng/trang.html.
* contrib/odt/schemas.xml: Sample schema locating file for use
with auto-validation of OpenDocumentText files.
* contrib/odt/setup.el: Suggested code for use within user's
.emacs file.
* contrib/odt/files/: Unit test directory for org-odt.el.
* contrib/odt/files/test.org: Sample org file for testing.
* contrib/odt/files/org-mode-unicorn.png: Image file for use
within the unit test file.
---
 contrib/odt/OpenDocument-schema-v1.1.rnc | 6444 +++++++++++
 contrib/odt/OpenDocument-schema-v1.1.rng |17891 ++++++++++++++++++++++++++++++
 contrib/odt/OrgOdtAutomaticStyles.xml    |  152 +
 contrib/odt/OrgOdtStyles.xml             |  611 +
 contrib/odt/files/org-mode-unicorn.png   |  Bin 0 -> 10527 bytes
 contrib/odt/files/test.org               |  486 +
 contrib/odt/schemas.xml                  |    5 +
 contrib/odt/setup.el                     |   33 +
 lisp/org-exp.el                          |   19 +-
 lisp/org-footnote.el                     |    9 +-
 lisp/org-html.el                         | 2428 +++--
 lisp/org-odt.el                          | 1365 +++
 lisp/org.el                              |    7 +-
 13 files changed, 28571 insertions(+), 879 deletions(-)
 create mode 100644 contrib/odt/OpenDocument-schema-v1.1.rnc
 create mode 100644 contrib/odt/OpenDocument-schema-v1.1.rng
 create mode 100644 contrib/odt/OrgOdtAutomaticStyles.xml
 create mode 100644 contrib/odt/OrgOdtStyles.xml
 create mode 100644 contrib/odt/files/org-mode-unicorn.png
 create mode 100644 contrib/odt/files/test.org
 create mode 100755 contrib/odt/schemas.xml
 create mode 100644 contrib/odt/setup.el
 create mode 100644 lisp/org-odt.el

diff --git a/lisp/org-exp.el b/lisp/org-exp.el
index 3e84314..90b3c97 100644
--- a/lisp/org-exp.el
+++ b/lisp/org-exp.el
@@ -914,6 +914,8 @@ Pressing `1' will switch between these two options."
 
 \[D] export as DocBook   [V] export as DocBook, process to PDF, and open
 
+\[o] export as ODT   [O] export as ODT and open
+
 \[j] export as TaskJuggler                         [J] ... and open
 
 \[m] export as Freemind mind map
@@ -942,6 +944,8 @@ Pressing `1' will switch between these two options."
 	    (?g org-export-generic t)
 	    (?D org-export-as-docbook t)
 	    (?V org-export-as-docbook-pdf-and-open t)
+	    (?o org-export-as-odt t)
+	    (?O org-export-as-odt-and-open nil)
 	    (?j org-export-as-taskjuggler t)
 	    (?J org-export-as-taskjuggler-and-open t)
 	    (?m org-export-as-freemind t)
@@ -1603,7 +1607,8 @@ from the buffer."
 	   (html "HTML" "BEGIN_HTML" "END_HTML")
 	   (beamer "BEAMER" "BEGIN_BEAMER" "END_BEAMER")
 	   (ascii "ASCII" "BEGIN_ASCII" "END_ASCII")
-	   (latex "LaTeX" "BEGIN_LaTeX" "END_LaTeX")))
+	   (latex "LaTeX" "BEGIN_LaTeX" "END_LaTeX")
+	   (odt "ODT" "BEGIN_ODT" "END_ODT")))
 	(case-fold-search t)
 	fmt beg beg-content end end-content ind)
 
@@ -2371,7 +2376,7 @@ in the list) and remove property and value from the list in LISTVAR."
 (defvar org-export-latex-listings-options) ;; defined in org-latex.el
 (defvar org-export-latex-minted-options) ;; defined in org-latex.el
 
-(defun org-export-format-source-code-or-example
+(defun org-export-do-format-source-code-or-example
   (lang code &optional opts indent caption)
   "Format CODE from language LANG and return it formatted for export.
 If LANG is nil, do not add any fontification.
@@ -2567,6 +2572,16 @@ INDENT was the original indentation of the block."
                       "#+END_ASCII\n"))))
       (org-add-props rtn nil 'original-indentation indent))))
 
+(defun org-export-format-source-code-or-example
+  (lang code &optional opts indent caption)
+  (let* ((backend-name (symbol-name org-export-current-backend))
+	 (f (intern (format "org-export-%s-format-source-code-or-example"
+			    backend-name))))
+    (if (fboundp f)
+	(funcall f lang code opts indent caption)
+      (org-export-do-format-source-code-or-example
+       lang code opts indent caption))))
+
 (defun org-export-number-lines (text &optional skip1 skip2 number cont
 				     replace-labels label-format)
   (setq skip1 (or skip1 0) skip2 (or skip2 0))
diff --git a/lisp/org-footnote.el b/lisp/org-footnote.el
index 9dbd6be..e8710d0 100644
--- a/lisp/org-footnote.el
+++ b/lisp/org-footnote.el
@@ -361,6 +361,8 @@ With prefix arg SPECIAL, offer additional commands in a menu."
       (org-footnote-goto-previous-reference (nth 1 tmp)))
      (t (org-footnote-new)))))
 
+(defvar insertion-point-for-normalized-footnotes 'point-max)
+
 ;;;###autoload
 (defun org-footnote-normalize (&optional sort-only for-preprocessor)
   "Collect the footnotes in various formats and normalize them.
@@ -460,7 +462,12 @@ referenced sequence."
 	(setq ins-point (point))))
 
       ;; Insert the footnotes again
-      (goto-char (or ins-point (point-max)))
+      (goto-char (or (and for-preprocessor
+			  (equal insertion-point-for-normalized-footnotes
+				 'point-min)
+			  (point-min))
+		     ins-point
+		     (point-max)))
       (setq ref-table (reverse ref-table))
       (when sort-only
 	;; remove anonymous and inline footnotes from the list
diff --git a/lisp/org-html.el b/lisp/org-html.el
index eea425f..fd49715 100644
--- a/lisp/org-html.el
+++ b/lisp/org-html.el
@@ -775,10 +775,10 @@ description.  See variables `org-export-html-inline-images' and
 	(org-file-image-p
 	 filename org-export-html-inline-image-extensions)))
 
-;;; org-html-make-link
-(defun org-html-make-link (opt-plist type path fragment desc attr
-			     may-inline-p)
-   "Make an HTML link.
+;;; org-html-format-org-link
+(defun org-html-format-org-link (opt-plist type-1 path fragment desc attr
+					   descp)
+  "Make an HTML link.
 OPT-PLIST is an options list.
 TYPE is the device-type of the link (THIS://foo.html)
 PATH is the path of the link (http://THIS#locationx)
@@ -787,82 +787,87 @@ DESC is the link description, if any.
 ATTR is a string of other attributes of the a element.
 MAY-INLINE-P allows inlining it as an image."
 
-   (declare (special org-par-open))
-   (save-match-data
-      (let* ((filename path)
-	       ;;First pass.  Just sanity stuff.
-	       (components-1
-		  (cond
-		     ((string= type "file")
-			(list
-			   type
-			   ;;Substitute just if original path was absolute.
-			   ;;(Otherwise path must remain relative)
-			   (if (file-name-absolute-p path)
-			      (concat "file://" (expand-file-name path))
-			      path)))
-		     ((string= type "")
-			(list nil path))
-		     (t (list type path))))
-
-	       ;;Second pass.  Components converted so they can refer
-	       ;;to a remote site.
-	       (components-2
-		  (or
-		     (and org-html-cvt-link-fn
-			(apply org-html-cvt-link-fn
-			   opt-plist components-1))
-		     (apply #'org-html-cvt-org-as-html
-			opt-plist components-1)
-		     components-1))
-	       (type    (first  components-2))
-	       (thefile (second components-2)))
-
-
-	 ;;Third pass.  Build final link except for leading type
-	 ;;spec.
-	 (cond
-	    ((or
-		(not type)
-		(string= type "http")
-		(string= type "https")
-		(string= type "file"))
-	       (if fragment
-		  (setq thefile (concat thefile "#" fragment))))
-
-	    (t))
-
-	 ;;Final URL-build, for all types.
-	 (setq thefile
+  (declare (special org-par-open))
+  (save-match-data
+    (let* ((may-inline-p
+	    (and (member type-1 '("http" "https" "file"))
+		 (org-html-should-inline-p path descp)
+		 (not fragment)))
+	   (type (if (equal type-1 "id") "file" type-1))
+	   (filename path)
+	   ;;First pass.  Just sanity stuff.
+	   (components-1
+	    (cond
+	     ((string= type "file")
+	      (list
+	       type
+	       ;;Substitute just if original path was absolute.
+	       ;;(Otherwise path must remain relative)
+	       (if (file-name-absolute-p path)
+		   (concat "file://" (expand-file-name path))
+		 path)))
+	     ((string= type "")
+	      (list nil path))
+	     (t (list type path))))
+
+	   ;;Second pass.  Components converted so they can refer
+	   ;;to a remote site.
+	   (components-2
+	    (or
+	     (and org-html-cvt-link-fn
+		  (apply org-html-cvt-link-fn
+			 opt-plist components-1))
+	     (apply #'org-html-cvt-org-as-html
+		    opt-plist components-1)
+	     components-1))
+	   (type    (first  components-2))
+	   (thefile (second components-2)))
+
+
+      ;;Third pass.  Build final link except for leading type
+      ;;spec.
+      (cond
+       ((or
+	 (not type)
+	 (string= type "http")
+	 (string= type "https")
+	 (string= type "file"))
+	(if fragment
+	    (setq thefile (concat thefile "#" fragment))))
+
+       (t))
+
+      ;;Final URL-build, for all types.
+      (setq thefile
 	    (let
-	       ((str (org-export-html-format-href thefile)))
+		((str (org-export-html-format-href thefile)))
 	      (if (and type (not (string= "file" type)))
 		  (concat type ":" str)
-		  str)))
-
-	 (if (and
-		may-inline-p
-		;;Can't inline a URL with a fragment.
-		(not fragment))
-	    (progn
-	       (message "image %s %s" thefile org-par-open)
-	       (org-export-html-format-image thefile org-par-open))
-	    (concat
-	       "<a href=\"" thefile "\"" (if attr (concat " " attr)) ">"
-	       (org-export-html-format-desc desc)
-	       "</a>")))))
-
-(defun org-html-handle-links (line opt-plist)
+		str)))
+
+      (if may-inline-p
+	  (org-export-html-format-image thefile)
+	(org-parse-format
+	 'LINK (org-export-html-format-desc desc) thefile attr)))))
+
+(defun org-html-format-inline-image (desc)
+  ;; FIXME: alt text missing here?
+  (org-html-format-tags '("<img src=\"%s\" alt=\"\">" . "</img>") "" desc))
+
+(defvar org-parse-link-description-is-image)
+(defun org-parse-format-org-link (line opt-plist)
   "Return LINE with markup of Org mode links.
 OPT-PLIST is the export options list."
   (let ((start 0)
 	(current-dir (if buffer-file-name
-			  (file-name-directory buffer-file-name)
-			default-directory))
+			 (file-name-directory buffer-file-name)
+		       default-directory))
 	(link-validate (plist-get opt-plist :link-validation-function))
 	type id-file fnc
-	rpl path attr desc descp desc1 desc2 link)
+	rpl path attr desc descp desc1 desc2 link
+	org-parse-link-description-is-image)
     (while (string-match org-bracket-link-analytic-regexp++ line start)
+      (setq org-parse-link-description-is-image nil)
       (setq start (match-beginning 0))
       (setq path (save-match-data (org-link-unescape
 				   (match-string 3 line))))
@@ -882,12 +887,14 @@ OPT-PLIST is the export options list."
       ;; Make an image out of the description if that is so wanted
       (when (and descp (org-file-image-p
 			desc org-export-html-inline-image-extensions))
+	(setq org-parse-link-description-is-image t)
 	(save-match-data
 	  (if (string-match "^file:" desc)
 	      (setq desc (substring desc (match-end 0)))))
-	(setq desc (org-add-props
-		       (concat "@<img src=\"" desc "\"/>")
-		       '(org-protected t))))
+	(save-match-data
+	  (setq desc (org-add-props
+			 (org-parse-format 'INLINE-IMAGE desc)
+			 '(org-protected t)))))
       (cond
        ((equal type "internal")
 	(let
@@ -896,14 +903,11 @@ OPT-PLIST is the export options list."
 		  (substring path 1)
 		path)))
 	  (setq rpl
-		(org-html-make-link
-		 opt-plist
-		 ""
-		 ""
-		 (org-solidify-link-text
-		  (save-match-data (org-link-unescape frag-0))
-		  nil)
-		 desc attr nil))))
+		(org-parse-format
+		 'ORG-LINK opt-plist "" "" (org-solidify-link-text
+					    (save-match-data
+					      (org-link-unescape frag-0))
+					    nil) desc attr descp))))
        ((and (equal type "id")
 	     (setq id-file (org-id-find-id-file path)))
 	;; This is an id: link to another file (if it was the same file,
@@ -913,28 +917,20 @@ OPT-PLIST is the export options list."
 			 id-file
 			 (file-name-directory org-current-export-file)))
 	  (setq rpl
-		(org-html-make-link opt-plist
-				    "file" id-file
-				    (concat (if (org-uuidgen-p path) "ID-") path)
-				    desc
-				    attr
-				    nil))))
+		(org-parse-format
+		 'ORG-LINK opt-plist type id-file
+		 (concat (if (org-uuidgen-p path) "ID-") path)
+		 desc attr descp))))
        ((member type '("http" "https"))
 	;; standard URL, can inline as image
 	(setq rpl
-	      (org-html-make-link opt-plist
-				  type path nil
-				  desc
-				  attr
-				  (org-html-should-inline-p path descp))))
+	      (org-parse-format
+	       'ORG-LINK opt-plist type path nil desc attr descp)))
        ((member type '("ftp" "mailto" "news"))
 	;; standard URL, can't inline as image
 	(setq rpl
-	      (org-html-make-link opt-plist
-				  type path nil
-				  desc
-				  attr
-				  nil)))
+	      (org-parse-format
+	       'ORG-LINK opt-plist type path nil desc attr descp)))
 
        ((string= type "coderef")
 	(let*
@@ -943,15 +939,13 @@ OPT-PLIST is the export options list."
 	      (format "class=\"coderef\" onmouseover=\"CodeHighlightOn(this, '%s');\" onmouseout=\"CodeHighlightOff(this, '%s');\""
 		      coderef-str coderef-str)))
 	  (setq rpl
-		(org-html-make-link opt-plist
-				    type "" coderef-str
-				    (format
-				     (org-export-get-coderef-format
-				      path
-				      (and descp desc))
-				     (cdr (assoc path org-export-code-refs)))
-				    attr-1
-				    nil))))
+		(org-parse-format
+		 'ORG-LINK opt-plist type "" coderef-str
+		 (format
+		  (org-export-get-coderef-format
+		   path
+		   (and descp desc))
+		  (cdr (assoc path org-export-code-refs))) attr-1 descp))))
 
        ((functionp (setq fnc (nth 2 (assoc type org-link-protocols))))
 	;; The link protocol has a function for format the link
@@ -1006,15 +1000,15 @@ OPT-PLIST is the export options list."
 		       (functionp link-validate)
 		       (not (funcall link-validate path-1 current-dir)))
 		      desc
-		    (org-html-make-link opt-plist
-					"file" path-1 fragment-1 desc-2 attr
-					(org-html-should-inline-p path-1 descp)))))))
+		    (org-parse-format
+		     'ORG-LINK opt-plist "file" path-1 fragment-1
+		     desc-2 attr descp))))))
 
        (t
 	;; just publish the path, as default
-	(setq rpl (concat "@<i>&lt;" type ":"
+	(setq rpl (concat "<i>&lt;" type ":"
 			  (save-match-data (org-link-unescape path))
-			  "&gt;@</i>"))))
+			  "&gt;</i>"))))
       (setq line (replace-match rpl t t line)
 	    start (+ start (length rpl))))
     line))
@@ -1040,6 +1034,12 @@ PUB-DIR is set, use this as the publishing directory."
   (interactive "P")
   (run-hooks 'org-export-first-hook)
 
+  (let* ((org-parse-get-callback 'org-html-get))
+    (org-do-export arg hidden ext-plist to-buffer body-only pub-dir)))
+
+(defun org-do-export (arg &optional hidden ext-plist
+			  to-buffer body-only pub-dir)
+  "Export the outline as a pretty HTML file."
   ;; Make sure we have a file name when we need it.
   (when (and (not (or to-buffer body-only))
 	     (not buffer-file-name))
@@ -1054,21 +1054,18 @@ PUB-DIR is set, use this as the publishing directory."
   (setq-default org-deadline-line-regexp org-deadline-line-regexp)
   (setq-default org-done-keywords org-done-keywords)
   (setq-default org-maybe-keyword-time-regexp org-maybe-keyword-time-regexp)
-  (let* ((opt-plist
+  (let* (org-html-protect org-par-open
+	 (org-parse-entity-control-callbacks-alist
+	  (org-parse-get 'ENTITY-CONTROL))
+	 (org-parse-entity-format-callbacks-alist
+	  (org-parse-get 'ENTITY-FORMAT))
+	 (opt-plist
 	  (org-export-process-option-filters
 	   (org-combine-plists (org-default-export-plist)
 			       ext-plist
 			       (org-infile-export-plist))))
 	 (body-only (or body-only (plist-get opt-plist :body-only)))
-	 (style (concat (if (plist-get opt-plist :style-include-default)
-			    org-export-html-style-default)
-			(plist-get opt-plist :style)
-			(plist-get opt-plist :style-extra)
-			"\n"
-			(if (plist-get opt-plist :style-include-scripts)
-			    org-export-html-scripts)))
-	 (html-extension (plist-get opt-plist :html-extension))
-	 valid thetoc have-headings first-heading-pos
+	 valid org-html-dyn-first-heading-pos
 	 (odd org-odd-levels-only)
 	 (region-p (org-region-active-p))
 	 (rbeg (and region-p (region-beginning)))
@@ -1094,7 +1091,7 @@ PUB-DIR is set, use this as the publishing directory."
 	 ;; The following two are dynamically scoped into other
 	 ;; routines below.
 	 (org-current-export-dir
-	  (or pub-dir (org-export-directory :html opt-plist)))
+	  (or pub-dir (org-parse-get 'EXPORT-DIR opt-plist)))
 	 (org-current-export-file buffer-file-name)
 	 (level 0) (line "") (origline "") txt todo
 	 (umax nil)
@@ -1107,21 +1104,29 @@ PUB-DIR is set, use this as the publishing directory."
 				 (org-entry-get (region-beginning)
 						"EXPORT_FILE_NAME" t))
 			    (file-name-nondirectory buffer-file-name)))
-		       "." html-extension)
+		       "." (org-parse-get 'FILE-NAME-EXTENSION opt-plist))
 		      (file-name-as-directory
-		       (or pub-dir (org-export-directory :html opt-plist))))))
+		       (or pub-dir (org-parse-get 'EXPORT-DIR opt-plist))))))
 	 (current-dir (if buffer-file-name
 			  (file-name-directory buffer-file-name)
 			default-directory))
 	 (buffer (if to-buffer
 		     (cond
-		      ((eq to-buffer 'string) (get-buffer-create "*Org HTML Export*"))
+		      ((eq to-buffer 'string)
+		       (get-buffer-create (org-parse-get 'EXPORT-BUFFER-NAME)))
 		      (t (get-buffer-create to-buffer)))
-		   (find-file-noselect filename)))
+		   (find-file-noselect
+		    (or (let ((f (org-parse-get 'INIT-METHOD)))
+			  (and f (functionp f) (funcall f filename)))
+			filename))))
 	 (org-levels-open (make-vector org-level-max nil))
 	 (date (plist-get opt-plist :date))
-	 (author      (plist-get opt-plist :author))
-	 (html-validation-link (or org-export-html-validation-link ""))
+	 (date (cond
+		((and date (string-match "%" date))
+		 (format-time-string date))
+		(date date)
+		(t (format-time-string "%Y-%m-%d %T %Z"))))
+	 (dummy (setq opt-plist (plist-put opt-plist :effective-date date)))
 	 (title       (org-html-expand
 		       (or (and subtree-p (org-export-get-title-from-subtree))
 			   (plist-get opt-plist :title)
@@ -1133,47 +1138,33 @@ PUB-DIR is set, use this as the publishing directory."
 				(file-name-sans-extension
 				 (file-name-nondirectory buffer-file-name)))
 			   "UNTITLED")))
-	 (link-up (and (plist-get opt-plist :link-up)
-		       (string-match "\\S-" (plist-get opt-plist :link-up))
-		       (plist-get opt-plist :link-up)))
-	 (link-home (and (plist-get opt-plist :link-home)
-			 (string-match "\\S-" (plist-get opt-plist :link-home))
-			 (plist-get opt-plist :link-home)))
 	 (dummy (setq opt-plist (plist-put opt-plist :title title)))
 	 (html-table-tag (plist-get opt-plist :html-table-tag))
 	 (quote-re0   (concat "^[ \t]*" org-quote-string "\\>"))
 	 (quote-re    (concat "^\\(\\*+\\)\\([ \t]+" org-quote-string "\\>\\)"))
-	 (inquote     nil)
-	 (infixed     nil)
-	 (inverse     nil)
-	 (email       (plist-get opt-plist :email))
-	 (language    (plist-get opt-plist :language))
-	 (keywords    (plist-get opt-plist :keywords))
-	 (description (plist-get opt-plist :description))
-	 (lang-words  nil)
+	 (org-parse-dyn-current-environment nil)
+	 ;; Get the language-dependent settings
+	 (lang-words (or (assoc (plist-get opt-plist :language)
+				org-export-language-setup)
+			 (assoc "en" org-export-language-setup)))
+	 (dummy (setq opt-plist (plist-put opt-plist :lang-words lang-words)))
 	 (head-count  0) cnt
 	 (start       0)
-	 (coding-system (and (boundp 'buffer-file-coding-system)
-			     buffer-file-coding-system))
-	 (coding-system-for-write (or org-export-html-coding-system
-				      coding-system))
-	 (save-buffer-coding-system (or org-export-html-coding-system
-					coding-system))
-	 (charset (and coding-system-for-write
-		       (fboundp 'coding-system-get)
-		       (coding-system-get coding-system-for-write
-					  'mime-charset)))
+	 (coding-system-for-write (org-html-get-coding-system-for-write))
+	 (save-buffer-coding-system (org-html-get-coding-system-for-save))
 	 (region
 	  (buffer-substring
 	   (if region-p (region-beginning) (point-min))
 	   (if region-p (region-end) (point-max))))
 	 (org-export-have-math nil)
+	 (insertion-point-for-normalized-footnotes 'point-min)
+	 (org-parse-backend (org-parse-get 'BACKEND))
 	 (lines
 	  (org-split-string
 	   (org-export-preprocess-string
 	    region
 	    :emph-multiline t
-	    :for-backend 'html
+	    :for-backend org-parse-backend
 	    :skip-before-1st-heading
 	    (plist-get opt-plist :skip-before-1st-heading)
 	    :drawers (plist-get opt-plist :drawers)
@@ -1191,22 +1182,17 @@ PUB-DIR is set, use this as the publishing directory."
 	    :LaTeX-fragments
 	    (plist-get opt-plist :LaTeX-fragments))
 	   "[\r\n]"))
-	 (mathjax
-	  (if (or (eq (plist-get opt-plist :LaTeX-fragments) 'mathjax)
-		  (and org-export-have-math
-		       (eq (plist-get opt-plist :LaTeX-fragments) t)))
-
-	      (org-export-html-mathjax-config
-	       org-export-html-mathjax-template
-	       org-export-html-mathjax-options
-	       (or (plist-get opt-plist :mathjax) ""))
-	    ""))
 	 table-open
 	 table-buffer table-orig-buffer
 	 ind
 	 rpl path attr desc descp desc1 desc2 link
 	 snumber fnc
 	 footnotes footref-seen
+	 org-html-output-buffer
+	 org-html-footnote-definitions
+	 org-html-footnote-number
+	 org-html-footnote-buffer
+	 org-parse-table-of-contents
 	 href
 	 )
 
@@ -1216,23 +1202,11 @@ PUB-DIR is set, use this as the publishing directory."
 			       '(:org-license-to-kill t))))
 
     (message "Exporting...")
-
-    (setq org-min-level (org-get-min-level lines level-offset))
-    (setq org-last-level org-min-level)
     (org-init-section-numbers)
 
-    (cond
-     ((and date (string-match "%" date))
-      (setq date (format-time-string date)))
-     (date)
-     (t (setq date (format-time-string "%Y-%m-%d %T %Z"))))
-
-    ;; Get the language-dependent settings
-    (setq lang-words (or (assoc language org-export-language-setup)
-			 (assoc "en" org-export-language-setup)))
-
     ;; Switch to the output buffer
-    (set-buffer buffer)
+    (setq org-html-output-buffer buffer)
+    (set-buffer org-html-output-buffer)
     (let ((inhibit-read-only t)) (erase-buffer))
     (fundamental-mode)
     (org-install-letbind)
@@ -1253,187 +1227,40 @@ PUB-DIR is set, use this as the publishing directory."
       (setq umax-toc (if (integerp org-export-with-toc)
 			 (min org-export-with-toc umax)
 		       umax))
+
+      (when (and org-export-with-toc (not body-only))
+	(setq lines (org-html-prepare-toc
+		     lines level-offset opt-plist umax-toc)))
+
       (unless body-only
-	;; File header
-	(insert (format
-		 "%s
-<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Strict//EN\"
-               \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\">
-<html xmlns=\"http://www.w3.org/1999/xhtml\"
-lang=\"%s\" xml:lang=\"%s\">
-<head>
-<title>%s</title>
-<meta http-equiv=\"Content-Type\" content=\"text/html;charset=%s\"/>
-<meta name=\"generator\" content=\"Org-mode\"/>
-<meta name=\"generated\" content=\"%s\"/>
-<meta name=\"author\" content=\"%s\"/>
-<meta name=\"description\" content=\"%s\"/>
-<meta name=\"keywords\" content=\"%s\"/>
-%s
-%s
-</head>
-<body>
-<div id=\"content\">
-%s
-"
-		 (format
-		  (or (and (stringp org-export-html-xml-declaration)
-			   org-export-html-xml-declaration)
-		      (cdr (assoc html-extension org-export-html-xml-declaration))
-		      (cdr (assoc "html" org-export-html-xml-declaration))
-
-		      "")
-		  (or charset "iso-8859-1"))
-		 language language
-		 title
-		 (or charset "iso-8859-1")
-		 date author description keywords
-		 style
-		 mathjax
-		 (if (or link-up link-home)
-		     (concat
-		      (format org-export-html-home/up-format
-			      (or link-up link-home)
-			      (or link-home link-up))
-		      "\n")
-		   "")))
-
-	;; insert html preamble
-	(when (plist-get opt-plist :html-preamble)
-	  (let ((html-pre (plist-get opt-plist :html-preamble)))
-	    (cond ((stringp html-pre)
-		   (insert
-		    (format-spec html-pre `((?t . ,title) (?a . ,author)
-					    (?d . ,date) (?e . ,email)))))
-		  ((functionp html-pre)
-		   (funcall html-pre opt-plist))
-		  (t
-		   (insert
-		    (format-spec
-		     (or (cadr (assoc (nth 0 lang-words)
-				      org-export-html-preamble-format))
-			 (cadr (assoc "en" org-export-html-preamble-format)))
-		     `((?t . ,title) (?a . ,author)
-		       (?d . ,date) (?e . ,email)))))))))
-
-      (if (and org-export-with-toc (not body-only))
-	  (progn
-	    (push (format "<h%d>%s</h%d>\n"
-			  org-export-html-toplevel-hlevel
-			  (nth 3 lang-words)
-			  org-export-html-toplevel-hlevel)
-		  thetoc)
-	    (push "<div id=\"text-table-of-contents\">\n" thetoc)
-	    (push "<ul>\n<li>" thetoc)
-	    (setq lines
-		  (mapcar '(lambda (line)
-			     (if (and (string-match org-todo-line-regexp line)
-				      (not (get-text-property 0 'org-protected line)))
-				 ;; This is a headline
-				 (progn
-				   (setq have-headings t)
-				   (setq level (- (match-end 1) (match-beginning 1)
-						  level-offset)
-					 level (org-tr-level level)
-					 txt (save-match-data
-					       (org-html-expand
-						(org-export-cleanup-toc-line
-						 (match-string 3 line))))
-					 todo
-					 (or (and org-export-mark-todo-in-toc
-						  (match-beginning 2)
-						  (not (member (match-string 2 line)
-							       org-done-keywords)))
-					; TODO, not DONE
-					     (and org-export-mark-todo-in-toc
-						  (= level umax-toc)
-						  (org-search-todo-below
-						   line lines level))))
-				   (if (string-match
-					(org-re "[ \t]+:\\([[:alnum:]_@:]+\\):[ \t]*$") txt)
-				       (setq txt (replace-match  "&nbsp;&nbsp;&nbsp;<span class=\"tag\"> \\1</span>" t nil txt)))
-				   (if (string-match quote-re0 txt)
-				       (setq txt (replace-match "" t t txt)))
-				   (setq snumber (org-section-number level))
-				   (if org-export-with-section-numbers
-				       (setq txt (concat snumber " " txt)))
-				   (if (<= level (max umax umax-toc))
-				       (setq head-count (+ head-count 1)))
-				   (if (<= level umax-toc)
-				       (progn
-					 (if (> level org-last-level)
-					     (progn
-					       (setq cnt (- level org-last-level))
-					       (while (>= (setq cnt (1- cnt)) 0)
-						 (push "\n<ul>\n<li>" thetoc))
-					       (push "\n" thetoc)))
-					 (if (< level org-last-level)
-					     (progn
-					       (setq cnt (- org-last-level level))
-					       (while (>= (setq cnt (1- cnt)) 0)
-						 (push "</li>\n</ul>" thetoc))
-					       (push "\n" thetoc)))
-					 ;; Check for targets
-					 (while (string-match org-any-target-regexp line)
-					   (setq line (replace-match
-						       (concat "@<span class=\"target\">" (match-string 1 line) "@</span> ")
-						       t t line)))
-					 (while (string-match "&lt;\\(&lt;\\)+\\|&gt;\\(&gt;\\)+" txt)
-					   (setq txt (replace-match "" t t txt)))
-					 (setq href
-					       (replace-regexp-in-string
-						"\\." "_" (format "sec-%s" snumber)))
-					 (setq href (org-solidify-link-text (or (cdr (assoc href org-export-preferred-target-alist)) href)))
-					 (push
-					  (format
-					   (if todo
-					       "</li>\n<li><a href=\"#%s\"><span class=\"todo\">%s</span></a>"
-					     "</li>\n<li><a href=\"#%s\">%s</a>")
-					   href txt) thetoc)
-
-					 (setq org-last-level level))
-				     )))
-			     line)
-			  lines))
-	    (while (> org-last-level (1- org-min-level))
-	      (setq org-last-level (1- org-last-level))
-	      (push "</li>\n</ul>\n" thetoc))
-	    (push "</div>\n" thetoc)
-	    (setq thetoc (if have-headings (nreverse thetoc) nil))))
+	(org-parse-begin 'DOCUMENT-CONTENT opt-plist)
+	(org-parse-begin 'DOCUMENT-BODY opt-plist))
 
       (setq head-count 0)
       (org-init-section-numbers)
 
-      (org-open-par)
+      (org-parse-begin-paragraph)
 
       (while (setq line (pop lines) origline line)
 	(catch 'nextline
+	  (when (and (org-parse-current-environment-p 'quote)
+		     (string-match "^\\*+ " line))
+	    (org-parse-end-environment 'quote))
 
-	  ;; end of quote section?
-	  (when (and inquote (string-match "^\\*+ " line))
-	    (insert "</pre>\n")
-	    (org-open-par)
-	    (setq inquote nil))
-	  ;; inside a quote section?
-	  (when inquote
-	    (insert (org-html-protect line) "\n")
+	  (when (org-parse-current-environment-p 'quote)
+	    (insert (org-parse-format 'PLAIN line))
 	    (throw 'nextline nil))
 
 	  ;; Fixed-width, verbatim lines (examples)
 	  (when (and org-export-with-fixed-width
 		     (string-match "^[ \t]*:\\(\\([ \t]\\|$\\)\\(.*\\)\\)" line))
-	    (when (not infixed)
-	      (setq infixed t)
-	      (org-close-par-maybe)
-
-	      (insert "<pre class=\"example\">\n"))
-	    (insert (org-html-protect (match-string 3 line)) "\n")
+	    (when (not (org-parse-current-environment-p 'fixedwidth))
+	      (org-parse-begin-environment 'fixedwidth))
+	    (insert (org-parse-format 'PLAIN (match-string 3 line)))
 	    (when (or (not lines)
 		      (not (string-match "^[ \t]*:\\(\\([ \t]\\|$\\)\\(.*\\)\\)"
 					 (car lines))))
-	      (setq infixed nil)
-	      (insert "</pre>\n")
-	      (org-open-par))
+	      (org-parse-end-environment 'fixedwidth))
 	    (throw 'nextline nil))
 
 	  ;; Protected HTML
@@ -1442,62 +1269,37 @@ lang=\"%s\" xml:lang=\"%s\">
 		     (not (< (or (next-single-property-change
 				  0 'org-protected line) 10000)
 			     (length line))))
-	    (let (par (ind (get-text-property 0 'original-indentation line)))
-	      (when (re-search-backward
-		     "\\(<p>\\)\\([ \t\r\n]*\\)\\=" (- (point) 100) t)
-		(setq par (match-string 1))
-		(replace-match "\\2\n"))
-	      (insert line "\n")
-	      (while (and lines
-			  (or (= (length (car lines)) 0)
-			      (not ind)
-			      (equal ind (get-text-property 0 'original-indentation (car lines))))
-			  (or (= (length (car lines)) 0)
-			      (get-text-property 0 'org-protected (car lines))))
-		(insert (pop lines) "\n"))
-	      (and par (insert "<p>\n")))
+	    (let ((ind (get-text-property 0 'original-indentation line)))
+	      (with-org-html-preserve-paragraph-state
+	       (insert (org-parse-format 'PLAIN line))
+	       (while (and lines
+			   (or (= (length (car lines)) 0)
+			       (not ind)
+			       (equal ind (get-text-property
+					   0 'original-indentation (car lines))))
+			   (or (= (length (car lines)) 0)
+			       (get-text-property 0 'org-protected (car lines))))
+		 (insert (org-parse-format 'PLAIN (pop lines))))))
 	    (throw 'nextline nil))
 
 	  ;; Blockquotes, verse, and center
-	  (when (equal "ORG-BLOCKQUOTE-START" line)
-	    (org-close-par-maybe)
-	    (insert "<blockquote>\n")
-	    (org-open-par)
-	    (throw 'nextline nil))
-	  (when (equal "ORG-BLOCKQUOTE-END" line)
-	    (org-close-par-maybe)
-	    (insert "\n</blockquote>\n")
-	    (org-open-par)
-	    (throw 'nextline nil))
-	  (when (equal "ORG-VERSE-START" line)
-	    (org-close-par-maybe)
-	    (insert "\n<p class=\"verse\">\n")
-	    (setq org-par-open t)
-	    (setq inverse t)
-	    (throw 'nextline nil))
-	  (when (equal "ORG-VERSE-END" line)
-	    (insert "</p>\n")
-	    (setq org-par-open nil)
-	    (org-open-par)
-	    (setq inverse nil)
-	    (throw 'nextline nil))
-	  (when (equal "ORG-CENTER-START" line)
-	    (org-close-par-maybe)
-	    (insert "\n<div style=\"text-align: center\">")
-	    (org-open-par)
-	    (throw 'nextline nil))
-	  (when (equal "ORG-CENTER-END" line)
-	    (org-close-par-maybe)
-	    (insert "\n</div>")
-	    (org-open-par)
-	    (throw 'nextline nil))
+	  (when (string-match  "^ORG-\\(.+\\)-\\(START\\|END\\)$" line)
+	    (let* ((style (intern (downcase (match-string 1 line))))
+		   (f (cdr (assoc (match-string 2 line)
+				  '(("START" . org-parse-begin-environment)
+				    ("END" . org-parse-end-environment))))))
+	      (when (memq style '(blockquote verse center))
+		(funcall f style)
+		(throw 'nextline nil))))
+
 	  (run-hooks 'org-export-html-after-blockquotes-hook)
-	  (when inverse
+	  (when (org-parse-current-environment-p 'verse)
 	    (let ((i (org-get-string-indentation line)))
 	      (if (> i 0)
-		  (setq line (concat (mapconcat 'identity
-						(make-list (* 2 i) "\\nbsp") "")
-				     " " (org-trim line))))
+		  (setq line (concat
+			      (let ((org-html-protect t))
+				(org-parse-format 'SPACES (* 2 i)))
+			      " " (org-trim line))))
 	      (unless (string-match "\\\\\\\\[ \t]*$" line)
 		(setq line (concat line "\\\\")))))
 
@@ -1510,27 +1312,31 @@ lang=\"%s\" xml:lang=\"%s\">
 	      (setq start (match-end 1)))
 	     ((match-end 2)
 	      (setq line (replace-match
-			  (format
-			   "@<a name=\"%s\" id=\"%s\">@</a>"
-			   (org-solidify-link-text (match-string 1 line))
-			   (org-solidify-link-text (match-string 1 line)))
+			  (let ((org-html-protect t))
+			    (org-parse-format
+			     'ANCHOR "" (org-solidify-link-text
+					 (match-string 1 line))))
 			  t t line)))
 	     ((and org-export-with-toc (equal (string-to-char line) ?*))
 	      ;; FIXME: NOT DEPENDENT on TOC?????????????????????
 	      (setq line (replace-match
-			  (concat "@<span class=\"target\">"
-				  (match-string 1 line) "@</span> ")
+			  (let ((org-html-protect t))
+			    (org-parse-format
+			     'FONTIFY (match-string 1 line) "target"))
 			  ;; (concat "@<i>" (match-string 1 line) "@</i> ")
 			  t t line)))
 	     (t
 	      (setq line (replace-match
-			  (concat "@<a name=\""
-				  (org-solidify-link-text (match-string 1 line))
-				  "\" class=\"target\">" (match-string 1 line)
-				  "@</a> ")
+			  (concat
+			   (let ((org-html-protect t))
+			     (org-parse-format
+			      'ANCHOR (match-string 1 line)
+			      (org-solidify-link-text (match-string 1 line))
+			      "target")) " ")
 			  t t line)))))
 
-	  (setq line (org-html-handle-time-stamps line))
+	  (let ((org-html-protect t))
+	    (setq line (org-html-handle-time-stamps line)))
 
 	  ;; replace "&" by "&amp;", "<" and ">" by "&lt;" and "&gt;"
 	  ;; handle @<..> HTML tags (replace "@&gt;..&lt;" by "<..>")
@@ -1538,44 +1344,37 @@ lang=\"%s\" xml:lang=\"%s\">
 	  (or (string-match org-table-hline-regexp line)
 	      (setq line (org-html-expand line)))
 
-	  ;; Format the links
-	  (setq line (org-html-handle-links line opt-plist))
+	  (setq line (org-parse-format-org-link line opt-plist))
 
 	  ;; TODO items
 	  (if (and (string-match org-todo-line-regexp line)
 		   (match-beginning 2))
-
-	      (setq line
-		    (concat (substring line 0 (match-beginning 2))
-			    "<span class=\""
-			    (if (member (match-string 2 line)
-					org-done-keywords)
-				"done" "todo")
-			    " " (match-string 2 line)
-			    "\"> " (org-export-html-get-todo-kwd-class-name
-				    (match-string 2 line))
-			    "</span>" (substring line (match-end 2)))))
+	      (setq line (concat
+			  (substring line 0 (match-beginning 2))
+			  (org-parse-format 'TODO (match-string 2 line))
+			  (substring line (match-end 2)))))
 
 	  ;; Does this contain a reference to a footnote?
 	  (when org-export-with-footnotes
 	    (setq start 0)
-	    (while (string-match "\\([^* \t].*?\\)\\[\\([0-9]+\\)\\]" line start)
+	    (while (string-match "\\([^* \t].*?\\)[ \t]*\\[\\([0-9]+\\)\\]" line start)
 	      (if (get-text-property (match-beginning 2) 'org-protected line)
 		  (setq start (match-end 2))
-		(let ((n (match-string 2 line)) extra a)
+		(let ((n (match-string 2 line)) refcnt a)
 		  (if (setq a (assoc n footref-seen))
 		      (progn
 			(setcdr a (1+ (cdr a)))
-			(setq extra (format ".%d" (cdr a))))
-		    (setq extra "")
+			(setq refcnt (cdr a)))
+		    (setq refcnt 1)
 		    (push (cons n 1) footref-seen))
 		  (setq line
 			(replace-match
-			 (format
-			  (concat "%s"
-			 	  (format org-export-html-footnote-format
-			 		  "<a class=\"footref\" name=\"fnr.%s%s\" href=\"#fn.%s\">%s</a>"))
-			  (or (match-string 1 line) "") n extra n n)
+			 (concat
+			  (or (match-string 1 line) "")
+			  (org-parse-format
+			   'FOOTNOTE-REFERENCE
+			   n (cdr (assoc n org-html-footnote-definitions))
+			   refcnt))
 			 t t line))))))
 
 	  (cond
@@ -1588,16 +1387,15 @@ lang=\"%s\" xml:lang=\"%s\">
 		(setq txt (replace-match "" t t txt)))
 	    (if (<= level (max umax umax-toc))
 		(setq head-count (+ head-count 1)))
-	    (setq first-heading-pos (or first-heading-pos (point)))
-	    (org-html-level-start level txt umax
-				  (and org-export-with-toc (<= level umax))
-				  head-count)
+	    (unless org-html-dyn-first-heading-pos
+	      (setq org-html-dyn-first-heading-pos (point)))
+	    (org-parse-begin 'LEVEL level txt umax
+			     (and org-export-with-toc (<= level umax))
+			     head-count)
 
 	    ;; QUOTES
 	    (when (string-match quote-re line)
-	      (org-close-par-maybe)
-	      (insert "<pre>")
-	      (setq inquote t)))
+	      (org-parse-begin-environment 'quote)))
 
 	   ((and org-export-with-tables
 		 (string-match "^\\([ \t]*\\)\\(|\\|\\+-+\\+\\)" line))
@@ -1614,7 +1412,7 @@ lang=\"%s\" xml:lang=\"%s\">
 	      (setq table-open nil
 		    table-buffer (nreverse table-buffer)
 		    table-orig-buffer (nreverse table-orig-buffer))
-	      (org-close-par-maybe)
+	      (org-parse-end-paragraph)
 	      (insert (org-format-table-html table-buffer table-orig-buffer))))
 
 	   ;; Normal lines
@@ -1630,15 +1428,18 @@ lang=\"%s\" xml:lang=\"%s\">
 
 	    ;; Horizontal line
 	    (when (string-match "^[ \t]*-\\{5,\\}[ \t]*$" line)
-	      (if org-par-open
-		  (insert "\n</p>\n<hr/>\n<p>\n")
-		(insert "\n<hr/>\n"))
+	      (with-org-html-preserve-paragraph-state
+	       (insert (org-parse-format 'HORIZONTAL-LINE)))
 	      (throw 'nextline nil))
 
 	    ;; Empty lines start a new paragraph.  If hand-formatted lists
 	    ;; are not fully interpreted, lines starting with "-", "+", "*"
 	    ;; also start a new paragraph.
-	    (if (string-match "^ [-+*]-\\|^[ \t]*$" line) (org-open-par))
+	    (when (string-match "^ [-+*]-\\|^[ \t]*$" line)
+	      (when org-html-footnote-number
+		(org-parse-end-footnote-definition org-html-footnote-number)
+		(setq org-html-footnote-number nil))
+	      (org-parse-begin-paragraph))
 
 	    ;; Is this the start of a footnote?
 	    (when org-export-with-footnotes
@@ -1648,26 +1449,24 @@ lang=\"%s\" xml:lang=\"%s\">
 		;; ignore this line
 		(throw 'nextline nil))
 	      (when (string-match "^[ \t]*\\[\\([0-9]+\\)\\]" line)
-		(org-close-par-maybe)
-		(let ((n (match-string 1 line)))
-		  (setq org-par-open t
-			line (replace-match
-			      (format
-			       (concat "<p class=\"footnote\">"
-				       (format org-export-html-footnote-format
-					       "<a class=\"footnum\" name=\"fn.%s\" href=\"#fnr.%s\">%s</a>"))
-			       n n n) t t line)))))
+		(org-parse-end-paragraph)
+		(setq org-html-footnote-number (match-string 1 line))
+		(setq line (replace-match "" t t line))
+		(org-parse-begin-footnote-definition org-html-footnote-number)))
 	    ;; Check if the line break needs to be conserved
 	    (cond
 	     ((string-match "\\\\\\\\[ \t]*$" line)
-	      (setq line (replace-match "<br/>" t t line)))
+	      (setq line (replace-match
+			  (org-parse-format 'LINE-BREAK)
+			  t t line)))
 	     (org-export-preserve-breaks
-	      (setq line (concat line "<br/>"))))
+	      (setq line (concat line (org-parse-format 'LINE-BREAK)))))
 
 	    ;; Check if a paragraph should be started
 	    (let ((start 0))
 	      (while (and org-par-open
 			  (string-match "\\\\par\\>" line start))
+		(error "FIXME")
 		;; Leave a space in the </p> so that the footnote matcher
 		;; does not see this.
 		(if (not (get-text-property (match-beginning 0)
@@ -1675,139 +1474,42 @@ lang=\"%s\" xml:lang=\"%s\">
 		    (setq line (replace-match "</p ><p >" t t line)))
 		(setq start (match-end 0))))
 
-	    (insert line "\n")))))
+	    (insert (org-parse-format 'PLAIN line))))))
 
       ;; Properly close all local lists and other lists
-      (when inquote
-	(insert "</pre>\n")
-	(org-open-par))
+      (when (org-parse-current-environment-p 'quote)
+	(org-parse-end-environment 'quote))
+
+      (org-parse-end 'LEVEL 1 umax)
 
-      (org-html-level-start 1 nil umax
-			    (and org-export-with-toc (<= level umax))
-			    head-count)
       ;; the </div> to close the last text-... div.
-      (when (and (> umax 0) first-heading-pos) (insert "</div>\n"))
+      (when (and (> umax 0) org-html-dyn-first-heading-pos)
+	(org-parse-end 'SECTION))
 
-      (save-excursion
-	(goto-char (point-min))
-	(while (re-search-forward "<p class=\"footnote\">[^\000]*?\\(</p>\\|\\'\\)" nil t)
-	  (push (match-string 0) footnotes)
-	  (replace-match "" t t)))
-      (when footnotes
-	(insert (format org-export-html-footnotes-section
-			(nth 4 lang-words)
-			(mapconcat 'identity (nreverse footnotes) "\n"))
-		"\n"))
-      (let ((bib (org-export-html-get-bibliography)))
-	(when bib
-	  (insert "\n" bib "\n")))
-
-      ;; export html postamble
+      (org-parse-end 'DOCUMENT-BODY opt-plist)
       (unless body-only
-	(let ((html-post (plist-get opt-plist :html-postamble))
-	      (email
-	       (mapconcat (lambda(e)
-			    (format "<a href=\"mailto:%s\">%s</a>" e e))
-			  (split-string email ",+ *")
-			  ", "))
-	      (creator-info
-	       (concat "Org version " org-version " with Emacs version "
-		       (number-to-string emacs-major-version))))
-	  (when (plist-get opt-plist :html-postamble)
-	    (cond ((stringp html-post)
-		   (insert "<div id=\"postamble\">\n")
-		   (insert (format-spec html-post
-					`((?a . ,author) (?e . ,email)
-					  (?d . ,date)   (?c . ,creator-info)
-					  (?v . ,html-validation-link))))
-		   (insert "</div>"))
-		  ((functionp html-post)
-		   (funcall html-post opt-plist))
-		  ((eq html-post 'auto)
-		   ;; fall back on default postamble
-		   (insert "<div id=\"postamble\">\n")
-		   (when (plist-get opt-plist :time-stamp-file)
-		     (insert "<p class=\"date\">" (nth 2 lang-words) ": " date "</p>\n"))
-		   (when (and (plist-get opt-plist :author-info) author)
-		       (insert "<p class=\"author\">" (nth 1 lang-words) ": " author "</p>\n"))
-		   (when (and (plist-get opt-plist :email-info) email)
-		     (insert "<p class=\"email\">" email "</p>\n"))
-		   (when (plist-get opt-plist :creator-info)
-		     (insert "<p class=\"creator\">"
-			     (concat "Org version " org-version " with Emacs version "
-				     (number-to-string emacs-major-version) "</p>\n")))
-		   (insert html-validation-link "\n</div>"))
-		  (t
-		   (insert "<div id=\"postamble\">\n")
-		   (insert (format-spec
-			    (or (cadr (assoc (nth 0 lang-words)
-					     org-export-html-postamble-format))
-				(cadr (assoc "en" org-export-html-postamble-format)))
-			    `((?a . ,author) (?e . ,email)
-			      (?d . ,date)   (?c . ,creator-info)
-			      (?v . ,html-validation-link))))
-		   (insert "</div>"))))))
-
-      (if org-export-html-with-timestamp
-	  (insert org-export-html-html-helper-timestamp))
-
-      (unless body-only (insert "\n</div>\n</body>\n</html>\n"))
+	(org-parse-end 'DOCUMENT-CONTENT))
 
       (unless (plist-get opt-plist :buffer-will-be-killed)
-	(normal-mode)
-	(if (eq major-mode (default-value 'major-mode))
-	    (html-mode)))
+	(set-auto-mode t))
+
+      (org-parse-end 'EXPORT)
 
-      ;; insert the table of contents
-      (goto-char (point-min))
-      (when thetoc
-	(if (or (re-search-forward
-		 "<p>\\s-*\\[TABLE-OF-CONTENTS\\]\\s-*</p>" nil t)
-		(re-search-forward
-		 "\\[TABLE-OF-CONTENTS\\]" nil t))
-	    (progn
-	      (goto-char (match-beginning 0))
-	      (replace-match ""))
-	  (goto-char first-heading-pos)
-	  (when (looking-at "\\s-*</p>")
-	    (goto-char (match-end 0))
-	    (insert "\n")))
-	(insert "<div id=\"table-of-contents\">\n")
-	(let ((beg (point)))
-	  (mapc 'insert thetoc)
-	  (insert "</div>\n")
-	  (while (re-search-backward "<li>[ \r\n\t]*</li>\n?" beg t)
-	    (replace-match ""))))
-      ;; remove empty paragraphs
-      (goto-char (point-min))
-      (while (re-search-forward "<p>[ \r\n\t]*</p>" nil t)
-	(replace-match ""))
-      (goto-char (point-min))
-      ;; Convert whitespace place holders
-      (goto-char (point-min))
-      (let (beg end n)
-	(while (setq beg (next-single-property-change (point) 'org-whitespace))
-	  (setq n (get-text-property beg 'org-whitespace)
-		end (next-single-property-change beg 'org-whitespace))
-	  (goto-char beg)
-	  (delete-region beg end)
-	  (insert (format "<span style=\"visibility:hidden;\">%s</span>"
-			  (make-string n ?x)))))
-      ;; Remove empty lines at the beginning of the file.
-      (goto-char (point-min))
-      (when (looking-at "\\s-+\n") (replace-match ""))
-      ;; Remove display properties
-      (remove-text-properties (point-min) (point-max) '(display t))
-      ;; Run the hook
-      (run-hooks 'org-export-html-final-hook)
-      (or to-buffer (save-buffer))
       (goto-char (point-min))
-      (or (org-export-push-to-kill-ring "HTML")
+      (or (org-export-push-to-kill-ring
+	   (upcase (symbol-name org-parse-backend)))
 	  (message "Exporting... done"))
-      (if (eq to-buffer 'string)
-	  (prog1 (buffer-substring (point-min) (point-max))
-	    (kill-buffer (current-buffer)))
-	(current-buffer)))))
+
+      (cond
+       ((not to-buffer)
+	(let ((f (org-parse-get 'SAVE-METHOD)))
+	  (or (and f (functionp f) (funcall f filename))
+	      (save-buffer)))
+	(current-buffer))
+       ((eq to-buffer 'string)
+	(prog1 (buffer-substring (point-min) (point-max))
+	  (kill-buffer (current-buffer))))
+       (t (current-buffer))))))
 
 (defun org-export-html-format-href (s)
   "Make sure the S is valid as a href reference in an XHTML document."
@@ -1825,7 +1527,7 @@ lang=\"%s\" xml:lang=\"%s\">
 	(org-html-do-expand s))
     s))
 
-(defun org-export-html-format-image (src par-open)
+(defun org-export-html-format-image (src)
   "Create image tag with source and attributes."
   (save-match-data
     (if (string-match "^ltxpng/" src)
@@ -1833,24 +1535,29 @@ lang=\"%s\" xml:lang=\"%s\">
                 src (org-find-text-property-in-string 'org-latex-src src))
       (let* ((caption (org-find-text-property-in-string 'org-caption src))
 	     (attr (org-find-text-property-in-string 'org-attributes src))
-	     (label (org-find-text-property-in-string 'org-label src)))
-	(setq caption (and caption (org-html-do-expand caption)))
-	(concat
-	(if caption
-	    (format "%s<div %sclass=\"figure\">
-<p>"
-		    (if org-par-open "</p>\n" "")
-		    (if label (format "id=\"%s\" " (org-solidify-link-text label)) "")))
-	(format "<img src=\"%s\"%s />"
-		src
-		(if (string-match "\\<alt=" (or attr ""))
-		    (concat " " attr )
-		  (concat " " attr " alt=\"" src "\"")))
+	     (label (org-find-text-property-in-string 'org-label src))
+	     (caption (and caption (org-html-do-expand caption)))
+	     (img (format "<img src=\"%s\"%s />"
+			  src
+			  (if (string-match "\\<alt=" (or attr ""))
+			      (concat " " attr )
+			    (concat " " attr " alt=\"" src "\""))))
+	     (extra (concat
+		     (and label
+			  (format "id=\"%s\" " (org-solidify-link-text label)))
+		     "class=\"figure\"")))
 	(if caption
-	    (format "</p>%s
-</div>%s"
-		(concat "\n<p>" caption "</p>")
-		(if org-par-open "\n<p>" ""))))))))
+	    (with-temp-buffer
+	      (with-org-html-preserve-paragraph-state
+	       (insert
+		(org-parse-format
+		 '("<div %s>" . "\n</div>")
+		 (concat
+		  (org-parse-format '("\n<p>" . "</p>") img)
+		  (org-parse-format '("\n<p>" . "</p>") caption))
+		 extra)))
+	      (buffer-string))
+	  img)))))
 
 (defun org-export-html-get-bibliography ()
   "Find bibliography, cut it out and return it."
@@ -1897,8 +1604,26 @@ NO-CSS is passed to the exporter."
 	;; Need to use the code generator in table.el, with the original text.
 	(org-format-table-table-html-using-table-generate-source olines)))))
 
+(defun org-table-get-colalign-info (lines)
+  (let ((forced-aligns (org-find-text-property-in-string
+			'org-forced-aligns (car lines))))
+    (when (and forced-aligns org-table-clean-did-remove-column)
+      (setq forced-aligns
+	    (mapcar (lambda (x) (cons (1- (car x)) (cdr x))) forced-aligns)))
+
+    forced-aligns))
+
+(defvar org-table-style)
+(defvar org-table-ncols)
+(defvar org-table-rownum)
+
+(defvar org-table-is-styled)
+(defvar org-table-begin-marker)
+(defvar org-table-num-numeric-items-per-column)
+(defvar org-table-colalign-info)
+(defvar org-table-colalign-vector)
 (defvar org-table-number-fraction) ; defined in org-table.el
-(defun org-format-org-table-html (lines &optional splice no-css)
+(defun org-do-format-org-table-html (lines &optional splice no-css)
   "Format a table into HTML.
 LINES is a list of lines.  Optional argument SPLICE means, do not
 insert header and surrounding <table> tags, just format the lines.
@@ -1916,131 +1641,53 @@ for formatting.  This is required for the DocBook exporter."
     (setq lines (org-table-clean-before-export lines)))
 
   (let* ((caption (org-find-text-property-in-string 'org-caption (car lines)))
+	 (caption (and caption (org-html-do-expand caption)))
 	 (label (org-find-text-property-in-string 'org-label (car lines)))
-	 (forced-aligns (org-find-text-property-in-string 'org-forced-aligns
-							  (car lines)))
+	 (org-table-colalign-info (org-table-get-colalign-info lines))
 	 (attributes (org-find-text-property-in-string 'org-attributes
 						       (car lines)))
-	 (html-table-tag (org-export-splice-attributes
-			  html-table-tag attributes))
 	 (head (and org-export-highlight-first-table-line
 		    (delq nil (mapcar
 			       (lambda (x) (string-match "^[ \t]*|-" x))
 			       (cdr lines)))))
-	 (nline 0) fnum nfields i (cnt 0)
-	 tbopen line fields html gr colgropen rowstart rowend
-	 ali align aligns n)
-    (setq caption (and caption (org-html-do-expand caption)))
-    (when (and forced-aligns org-table-clean-did-remove-column)
-    (setq forced-aligns
-	  (mapcar (lambda (x) (cons (1- (car x)) (cdr x))) forced-aligns)))
-    (if splice (setq head nil))
-    (unless splice (push (if head "<thead>" "<tbody>") html))
-    (setq tbopen t)
-    (while (setq line (pop lines))
-      (catch 'next-line
-	(if (string-match "^[ \t]*|-" line)
-	    (progn
-	      (unless splice
-		(push (if head "</thead>" "</tbody>") html)
-		(if lines (push "<tbody>" html) (setq tbopen nil)))
-	      (setq head nil)   ;; head ends here, first time around
-	      ;; ignore this line
-	      (throw 'next-line t)))
-	;; Break the line into fields
-	(setq fields (org-split-string line "[ \t]*|[ \t]*"))
-	(unless fnum (setq fnum (make-vector (length fields) 0)
-			   nfields (length fnum)))
-	(setq nline (1+ nline) i -1
-	      rowstart (eval (car org-export-table-row-tags))
-	      rowend (eval (cdr org-export-table-row-tags)))
-	(push (concat rowstart
-		      (mapconcat
-		       (lambda (x)
-			 (setq i (1+ i) ali (format "@@class%03d@@" i))
-			 (if (and (< i nfields) ; make sure no rogue line causes an error here
-				  (string-match org-table-number-regexp x))
-			     (incf (aref fnum i)))
-			 (cond
-			  (head
-			   (concat
-			    (format (car org-export-table-header-tags)
-				    "col" ali)
-			    x
-			    (cdr org-export-table-header-tags)))
-			  ((and (= i 0) org-export-html-table-use-header-tags-for-first-column)
-			   (concat
-			    (format (car org-export-table-header-tags)
-				    "row" ali)
-			    x
-			    (cdr org-export-table-header-tags)))
-			  (t
-			   (concat (format (car org-export-table-data-tags) ali)
-				   x
-				   (cdr org-export-table-data-tags)))))
-		       fields "")
-		      rowend)
-	      html)))
-    (unless splice (if tbopen (push "</tbody>" html)))
-    (unless splice (push "</table>\n" html))
-    (setq html (nreverse html))
-    (unless splice
-      ;; Put in col tags with the alignment (unfortunately often ignored...)
-      (unless (car org-table-colgroup-info)
-	(setq org-table-colgroup-info
-	      (cons :start (cdr org-table-colgroup-info))))
-      (setq i 0)
-      (push (mapconcat
-	     (lambda (x)
-	       (setq gr (pop org-table-colgroup-info)
-		     i (1+ i)
-		     align (if (assoc i forced-aligns)
-			       (cdr (assoc (cdr (assoc i forced-aligns))
-					   '(("l" . "left") ("r" . "right")
-					     ("c" . "center"))))
-			     (if (> (/ (float x) nline)
-				    org-table-number-fraction)
-				 "right" "left")))
-	       (push align aligns)
-	       (format (if no-css
-			   "%s<col align=\"%s\" />%s"
-			 "%s<col class=\"%s\" />%s")
-		       (if (memq gr '(:start :startend))
-			   (prog1
-			       (if colgropen
-				   "</colgroup>\n<colgroup>"
-				 "<colgroup>")
-			     (setq colgropen t))
-			 "")
-		       align
-		       (if (memq gr '(:end :startend))
-			   (progn (setq colgropen nil) "</colgroup>")
-			 "")))
-	     fnum "")
-	    html)
-      (setq aligns (nreverse aligns))
-      (if colgropen (setq html (cons (car html)
-				     (cons "</colgroup>" (cdr html)))))
-      ;; Since the output of HTML table formatter can also be used in
-      ;; DocBook document, we want to always include the caption to make
-      ;; DocBook XML file valid.
-      (push (format "<caption>%s</caption>" (or caption "")) html)
-      (when label
-	      (setq html-table-tag (org-export-splice-attributes html-table-tag (format "id=\"%s\"" (org-solidify-link-text label)))))
-      (push html-table-tag html))
-    (setq html (mapcar
-		(lambda (x)
-		  (replace-regexp-in-string
-		   "@@class\\([0-9]+\\)@@"
-		   (lambda (txt)
-		     (if (not org-export-html-table-align-individual-fields)
-			 ""
-		       (setq n (string-to-number (match-string 1 txt)))
-		       (format (if no-css " align=\"%s\"" " class=\"%s\"")
-			       (or (nth n aligns) "left"))))
-		   x))
-		html))
-    (concat (mapconcat 'identity html "\n") "\n")))
+	 (org-table-rownum -1) org-table-ncols i (cnt 0)
+	 tbopen line fields
+	 org-table-current-rowgroup-is-header
+	 org-table-rowgroup-open
+	 org-table-num-numeric-items-per-column
+	 org-table-colalign-vector n
+	 org-table-rowgroup-info
+	 org-table-begin-marker
+	 (org-table-style 'org-table)
+	 org-table-is-styled)
+    (cond
+     (splice
+      (setq org-table-is-styled nil)
+      (while (setq line (pop lines))
+	(unless (string-match "^[ \t]*|-" line)
+	  (insert
+	   (org-parse-format-table-row
+	    (org-split-string line "[ \t]*|[ \t]*")) "\n"))))
+     (t
+      (setq org-table-is-styled t)
+      (org-parse-begin 'TABLE caption label attributes)
+      (setq org-table-begin-marker (point))
+      (org-parse-begin-table-rowgroup head)
+      (while (setq line (pop lines))
+	(cond
+	 ((string-match "^[ \t]*|-" line)
+	  (when lines (org-parse-begin-table-rowgroup)))
+	 (t
+	  (insert
+	   (org-parse-format-table-row
+	    (org-split-string line "[ \t]*|[ \t]*")) "\n"))))
+      (org-parse-end 'TABLE-ROWGROUP)
+      (org-parse-end-table)))))
+
+(defun org-format-org-table-html (lines &optional splice no-css)
+  (with-temp-buffer
+    (org-do-format-org-table-html lines splice no-css)
+    (buffer-substring-no-properties (point-min) (point-max))))
 
 (defun org-export-splice-attributes (tag attributes)
   "Read attributes in string ATTRIBUTES, add and replace in HTML tag TAG."
@@ -2058,53 +1705,47 @@ for formatting.  This is required for the DocBook exporter."
 			       t t tag)))
       tag)))
 
-(defun org-format-table-table-html (lines)
+(defun org-do-format-table-table-html (lines)
   "Format a table generated by table.el into HTML.
 This conversion does *not* use `table-generate-source' from table.el.
 This has the advantage that Org-mode's HTML conversions can be used.
 But it has the disadvantage, that no cell- or row-spanning is allowed."
   (let (line field-buffer
-	     (head org-export-highlight-first-table-line)
-	     fields html empty i)
-    (setq html (concat html-table-tag "\n"))
+	     (org-table-current-rowgroup-is-header
+	      org-export-highlight-first-table-line)
+	     (caption nil)
+	     (attributes nil)
+	     (label nil)
+	     (org-table-style 'table-table)
+	     (org-table-is-styled nil)
+	     fields org-table-ncols i (org-table-rownum -1))
+    (org-parse-begin 'TABLE caption label attributes)
     (while (setq line (pop lines))
-      (setq empty "&nbsp;")
-      (catch 'next-line
-	(if (string-match "^[ \t]*\\+-" line)
-	    (progn
-	      (if field-buffer
-		  (progn
-		    (setq
-		     html
-		     (concat
-		      html
-		      "<tr>"
-		      (mapconcat
-		       (lambda (x)
-			 (if (equal x "") (setq x empty))
-			 (if head
-			     (concat
-			      (format (car org-export-table-header-tags) "col" "")
-			      x
-			      (cdr org-export-table-header-tags))
-			   (concat (format (car org-export-table-data-tags) "") x
-				   (cdr org-export-table-data-tags))))
-		       field-buffer "\n")
-		      "</tr>\n"))
-		    (setq head nil)
-		    (setq field-buffer nil)))
-	      ;; Ignore this line
-	      (throw 'next-line t)))
+      (setq empty (org-parse-format 'SPACES 1))
+      (cond
+       ((string-match "^[ \t]*\\+-" line)
+	(when field-buffer
+	  (let ((org-export-table-row-tags '("<tr>" . "</tr>"))
+		(org-export-html-table-use-header-tags-for-first-column nil))
+	    (insert (org-parse-format-table-row field-buffer empty)))
+	  (setq org-table-current-rowgroup-is-header nil)
+	  (setq field-buffer nil)))
+       (t
 	;; Break the line into fields and store the fields
 	(setq fields (org-split-string line "[ \t]*|[ \t]*"))
 	(if field-buffer
 	    (setq field-buffer (mapcar
 				(lambda (x)
-				  (concat x "<br/>" (pop fields)))
+				  (concat x (org-parse-format 'LINE-BREAK)
+					  (pop fields)))
 				field-buffer))
-	  (setq field-buffer fields))))
-    (setq html (concat html "</table>\n"))
-    html))
+	  (setq field-buffer fields)))))
+    (org-parse-end-table)))
+
+(defun org-format-table-table-html (lines)
+  (with-temp-buffer
+    (org-do-format-table-table-html lines)
+    (buffer-substring-no-properties (point-min) (point-max))))
 
 (defun org-format-table-table-html-using-table-generate-source (lines)
   "Format a table into html, using `table-generate-source' from table.el.
@@ -2141,21 +1782,25 @@ But it has the disadvantage, that Org-mode's HTML conversions cannot be used."
 	(or b (setq b (substring s 0 (match-beginning 0))))
 	(setq r (concat
 		 r (substring s 0 (match-beginning 0))
-		 " @<span class=\"timestamp-wrapper\">"
-		 (if (match-end 1)
-		     (format "@<span class=\"timestamp-kwd\">%s @</span>"
-			     (match-string 1 s)))
-		 (format " @<span class=\"timestamp\">%s@</span>"
-			 (substring
-			  (org-translate-time (match-string 3 s)) 1 -1))
-		 "@</span>")
+		 (org-parse-format
+		  'FONTIFY
+		  (concat
+		   (if (match-end 1)
+		       (org-parse-format
+			'FONTIFY
+			(match-string 1 s) "timestamp-kwd"))
+		   (org-parse-format
+		    'FONTIFY
+		    (substring (org-translate-time (match-string 3 s)) 1 -1)
+		    "timestamp"))
+		  "timestamp-wrapper"))
 	      s (substring s (match-end 0))))
       ;; Line break if line started and ended with time stamp stuff
       (if (not r)
 	  s
 	(setq r (concat r s))
 	(unless (string-match "\\S-" (concat b s))
-	  (setq r (concat r "<br/>")))
+	  (setq r (concat r (org-parse-format 'LINE-BREAK))))
 	r))))
 
 (defvar htmlize-buffer-places)  ; from htmlize.el
@@ -2281,13 +1926,14 @@ If there are links in the string, don't modify these."
 	(setq s (match-end 2)))
        (t
 	(setq s (match-end 1)
-	      key (if (string= (match-string 2 string) "_") "sub" "sup")
+	      key (if (string= (match-string 2 string) "_")
+		      'subscript 'superscript)
 	      c (or (match-string 8 string)
 		    (match-string 6 string)
 		    (match-string 5 string))
 	      string (replace-match
 		      (concat (match-string 1 string)
-			      "<" key ">" c "</" key ">")
+			      (org-parse-format 'FONTIFY c key))
 		      t t string)))))
     (while (string-match "\\\\\\([_^]\\)" string)
       (setq string (replace-match (match-string 1 string) t t string)))
@@ -2304,113 +1950,24 @@ If there are links in the string, don't modify these."
 		rpl
 		(concat
 		 (match-string 1 string)
-		 (nth 2 (assoc (match-string 3 string) org-emphasis-alist))
-		 (match-string 4 string)
-		 (nth 3 (assoc (match-string 3 string)
-			       org-emphasis-alist))
+		 (org-parse-format
+		  'FONTIFY (match-string 4 string)
+		  (nth 1 (assoc (match-string 3 string)
+				org-html-emphasis-alist)))
 		 (match-string 5 string))
 		string (replace-match rpl t t string)
 		s (+ s (- (length rpl) 2)))
 	(setq s (1+ s))))
     string))
 
-(defun org-open-par ()
-  "Insert <p>, but first close previous paragraph if any."
-  (org-close-par-maybe)
-  (insert "\n<p>")
-  (setq org-par-open t))
-(defun org-close-par-maybe ()
-  "Close paragraph if there is one open."
-  (when org-par-open
-    (insert "</p>")
-    (setq org-par-open nil)))
-(defun org-close-li (&optional type)
-  "Close <li> if necessary."
-  (org-close-par-maybe)
-  (insert (if (equal type "d") "</dd>\n" "</li>\n")))
+(defmacro with-org-html-preserve-paragraph-state (&rest body)
+  `(let ((org-do-open-par org-par-open))
+     (org-parse-end-paragraph)
+     ,@body
+     (when org-do-open-par
+       (org-parse-begin-paragraph))))
 
 (defvar body-only) ; dynamically scoped into this.
-(defun org-html-level-start (level title umax with-toc head-count)
-  "Insert a new level in HTML export.
-When TITLE is nil, just close all open levels."
-  (org-close-par-maybe)
-  (let* ((target (and title (org-get-text-property-any 0 'target title)))
-	 (extra-targets (and target
-			     (assoc target org-export-target-aliases)))
-	 (extra-class (and title (org-get-text-property-any 0 'html-container-class title)))
-	 (preferred (and target
-			 (cdr (assoc target org-export-preferred-target-alist))))
-	 (l org-level-max)
-	 snumber snu href suffix)
-    (setq extra-targets (remove (or preferred target) extra-targets))
-    (setq extra-targets
-	  (mapconcat (lambda (x)
-		       (setq x (org-solidify-link-text
-				(if (org-uuidgen-p x) (concat "ID-" x) x)))
-		       (format "<a name=\"%s\" id=\"%s\"></a>"
-			       x x))
-		     extra-targets
-		     ""))
-    (while (>= l level)
-      (if (aref org-levels-open (1- l))
-	  (progn
-	    (org-html-level-close l umax)
-	    (aset org-levels-open (1- l) nil)))
-      (setq l (1- l)))
-    (when title
-      ;; If title is nil, this means this function is called to close
-      ;; all levels, so the rest is done only if title is given
-	(when (string-match (org-re "\\(:[[:alnum:]_@#%:]+:\\)[ \t]*$") title)
-	  (setq title (replace-match
-		       (if org-export-with-tags
-			   (save-match-data
-			     (concat
-			      "&nbsp;&nbsp;&nbsp;<span class=\"tag\">"
-			      (mapconcat
-			       (lambda (x)
-				 (format "<span class=\"%s\">%s</span>"
-					 (org-export-html-get-tag-class-name x)
-					 x))
-			       (org-split-string (match-string 1 title) ":")
-			       "&nbsp;")
-			      "</span>"))
-			 "")
-		       t t title)))
-      (if (> level umax)
-	  (progn
-	    (if (aref org-levels-open (1- level))
-		(progn
-		  (org-close-li)
-		  (if target
-		      (insert (format "<li id=\"%s\">" (org-solidify-link-text (or preferred target)))
-			      extra-targets title "<br/>\n")
-		    (insert "<li>" title "<br/>\n")))
-	      (aset org-levels-open (1- level) t)
-	      (org-close-par-maybe)
-	      (if target
-		  (insert (format "<ul>\n<li id=\"%s\">" (org-solidify-link-text (or preferred target)))
-			  extra-targets title "<br/>\n")
-		(insert "<ul>\n<li>" title "<br/>\n"))))
-	(aset org-levels-open (1- level) t)
-	(setq snumber (org-section-number level)
-	      snu (replace-regexp-in-string "\\." "_" snumber))
-	(setq level (+ level org-export-html-toplevel-hlevel -1))
-	(if (and org-export-with-section-numbers (not body-only))
-	    (setq title (concat
-			 (format "<span class=\"section-number-%d\">%s</span>"
-				 level snumber)
-			 " " title)))
-	(unless (= head-count 1) (insert "\n</div>\n"))
-	(setq href (cdr (assoc (concat "sec-" snu) org-export-preferred-target-alist)))
-	(setq suffix (org-solidify-link-text (or href snu)))
-	(setq href (org-solidify-link-text (or href (concat "sec-" snu))))
-	(insert (format "\n<div id=\"outline-container-%s\" class=\"outline-%d%s\">\n<h%d id=\"%s\">%s%s</h%d>\n<div class=\"outline-text-%d\" id=\"text-%s\">\n"
-			suffix level (if extra-class (concat " " extra-class) "")
-			level href
-			extra-targets
-			title level level suffix))
-	(org-open-par)))))
-
 (defun org-export-html-get-tag-class-name (tag)
   "Turn tag into a valid class name.
 Replaces invalid characters with \"_\" and then prepends a prefix."
@@ -2427,13 +1984,6 @@ Replaces invalid characters with \"_\" and then prepends a prefix."
       (setq kwd (replace-match "_" t t kwd))))
   (concat org-export-html-todo-kwd-class-prefix kwd))
 
-(defun org-html-level-close (level max-outline-level)
-  "Terminate one level in HTML export."
-  (if (<= level max-outline-level)
-      (insert "</div>\n")
-    (org-close-li)
-    (insert "</ul>\n")))
-
 (defun org-html-export-list-line (line pos struct prevs)
   "Insert list syntax in export buffer. Return LINE, maybe modified.
 
@@ -2470,13 +2020,13 @@ the alist of previous items."
 	    (let* ((lastp (= (org-list-get-last-item e struct prevs) e))
 		   (first-item (org-list-get-list-begin e struct prevs))
 		   (type (funcall get-type first-item struct prevs)))
-	      (org-close-par-maybe)
+	      (org-parse-end-paragraph)
 	      ;; Ending for every item
 	      (org-close-li type)
 	      ;; We're ending last item of the list: end list.
 	      (when lastp
-		(insert (format "</%sl>\n" type))
-		(org-open-par))))
+		(org-parse-end 'LIST type)
+		(org-parse-begin-paragraph))))
 	  (funcall get-closings pos))
     (cond
      ;; At an item: insert appropriate tags in export buffer.
@@ -2503,22 +2053,28 @@ the alist of previous items."
 			 ((string-match "[0-9]+" count-tmp)
 			  count-tmp)))))
 	(when firstp
-	  (org-close-par-maybe)
-	  (insert (format "<%sl>\n" type)))
-	(insert (cond
-		 ((equal type "d")
-		  (format "<dt>%s</dt><dd>" desc-tag))
-		 ((and (equal type "o") counter)
-		  (format "<li value=\"%s\">" counter))
-		 (t "<li>")))
+	  (org-parse-end-paragraph)
+	  (org-parse-begin 'LIST type))
+
+	(let ((arg (cond ((equal type "d") desc-tag)
+			 ((equal type "o") counter))))
+	  (org-parse-begin 'LIST-ITEM type arg))
+
 	;; If line had a checkbox, some additional modification is required.
 	(when checkbox
 	  (setq body
 		(concat
-		 (cond
-		  ((string-match "X" checkbox) "<code>[X]</code> ")
-		  ((string-match " " checkbox) "<code>[&nbsp;]</code> ")
-		  (t "<code>[-]</code> "))
+		 (org-parse-format
+		  'FONTIFY (concat
+			    "["
+			    (cond
+			     ((string-match "X" checkbox) "X")
+			     ((string-match " " checkbox)
+			      (org-parse-format 'SPACES 1))
+			     (t "-"))
+			    "]")
+		  'code)
+		 " "
 		 body)))
 	;; Return modified line
 	body))
@@ -2527,6 +2083,1132 @@ the alist of previous items."
      ;; Not at an item: return line unchanged (side-effects only).
      (t line))))
 
+;; miscellaneous
+
+(defun org-html-bind-local-variables (opt-plist)
+  (mapc (lambda (x)
+	  (set (make-local-variable (nth 2 x))
+	       (plist-get opt-plist (car x))))
+	org-export-plist-vars))
+
+
+;; This replaces org-emphasis-alist
+(defvar org-table-rowgroup-open)
+(defvar org-table-current-rowgroup-is-header)
+(defvar org-html-footnote-number)
+(defvar org-html-footnote-definitions)
+(defvar org-html-footnote-buffer)
+(defvar org-html-output-buffer)
+
+
+(defun org-html-end-export ()
+  ;; insert the table of contents
+  (when (and org-export-with-toc (not body-only))
+    (org-html-insert-toc org-parse-table-of-contents))
+
+  ;; remove empty paragraphs
+  (goto-char (point-min))
+  (while (re-search-forward "<p>[ \r\n\t]*</p>" nil t)
+    (replace-match ""))
+
+  ;; Convert whitespace place holders
+  (goto-char (point-min))
+  (let (beg end n)
+    (while (setq beg (next-single-property-change (point) 'org-whitespace))
+      (setq n (get-text-property beg 'org-whitespace)
+	    end (next-single-property-change beg 'org-whitespace))
+      (goto-char beg)
+      (delete-region beg end)
+      (insert (format "<span style=\"visibility:hidden;\">%s</span>"
+		      (make-string n ?x)))))
+
+  ;; Remove empty lines at the beginning of the file.
+  (goto-char (point-min))
+  (when (looking-at "\\s-+\n") (replace-match ""))
+
+  ;; Remove display properties
+  (remove-text-properties (point-min) (point-max) '(display t))
+
+  ;; kill temporary buffers
+  (when org-html-footnote-buffer
+    (kill-buffer org-html-footnote-buffer))
+
+  ;; Run the hook
+  (run-hooks 'org-export-html-final-hook))
+
+
+;;;_ org-parse.el
+;;;_. preamble
+;;;_ , user-specific
+;;;_  . custom-settings
+(defcustom org-parse-debug nil
+  ""
+  :group 'org-parse
+  :type 'boolean)
+
+
+
+
+;;;_ , callbacks
+;;;_  . control callbacks
+;;;_   , generic
+(defun org-parse-begin (entity &rest args)
+  (when (and (member org-parse-debug '(t control))
+	     (not (eq entity 'DOCUMENT-CONTENT)))
+    (insert (org-parse-format 'COMMENT "%s BEGIN %S" entity args)))
+
+  (let ((f (cadr (assoc entity org-parse-entity-control-callbacks-alist))))
+    (unless f (error "Unknown entity: %s" entity))
+    (apply f args)))
+
+(defun org-parse-end (entity &rest args)
+  (when (and (member org-parse-debug '(t control))
+	     (not (eq entity 'DOCUMENT-CONTENT)))
+    (insert (org-parse-format 'COMMENT "%s END %S" entity args)))
+
+  (let ((f (caddr (assoc entity org-parse-entity-control-callbacks-alist))))
+    (unless f (error "Unknown entity: %s" entity))
+    (apply f args)))
+
+
+;;;_   , paragraph
+(defun org-parse-begin-paragraph (&optional style)
+  "Insert <p>, but first close previous paragraph if any."
+  (org-parse-end-paragraph)
+  (org-parse-begin 'PARAGRAPH style)
+  (setq org-par-open t))
+
+(defun org-parse-end-paragraph ()
+  "Close paragraph if there is one open."
+  (when org-par-open
+    (org-parse-end 'PARAGRAPH)
+    (setq org-par-open nil)))
+
+;;;_   , list
+(defun org-close-li (&optional type)
+  "Close <li> if necessary."
+  (org-parse-end-paragraph)
+  (org-parse-end 'LIST-ITEM (or type "u")))
+
+
+;;;_   , environment
+(defvar org-parse-dyn-current-environment nil)
+(defun org-parse-begin-environment (style)
+  (assert (not org-parse-dyn-current-environment) t)
+  (setq org-parse-dyn-current-environment style)
+  (org-parse-begin 'ENVIRONMENT  style))
+
+(defun org-parse-end-environment (style)
+  (org-parse-end 'ENVIRONMENT style)
+
+  (assert (eq org-parse-dyn-current-environment style) t)
+  (setq org-parse-dyn-current-environment nil))
+
+(defun org-parse-current-environment-p (style)
+  (eq org-parse-dyn-current-environment style))
+
+
+;;;_   , footnote definition
+(defun org-parse-begin-footnote-definition (n)
+  (unless org-html-footnote-buffer
+    (setq org-html-footnote-buffer
+	  (get-buffer-create "*Org HTML Export Footnotes*")))
+  (set-buffer org-html-footnote-buffer)
+  (erase-buffer)
+  (org-parse-begin 'FOOTNOTE-DEFINITION n))
+
+(defun org-parse-end-footnote-definition (n)
+  (org-parse-end 'FOOTNOTE-DEFINITION n)
+  (push (cons n (buffer-string)) org-html-footnote-definitions)
+  (set-buffer org-html-output-buffer))
+
+
+
+
+;;;_  . format callbacks
+;;;_   , generic
+(defun org-parse-format (entity &rest args)
+  (when (and (member org-parse-debug '(t format))
+	     (not (equal entity 'COMMENT)))
+    (insert (org-parse-format 'COMMENT "%s: %S" entity args)))
+  (cond
+   ((consp entity)
+    (let ((text (pop args)))
+      (apply 'org-parse-format 'TAGS entity text args)))
+   (t
+    (let ((f (cdr (assoc entity org-parse-entity-format-callbacks-alist))))
+      (unless f (error "Unknown entity: %s" entity))
+      (apply f args)))))
+
+
+;;;_   , toc (rename these routines)
+(defun org-html-format-toc-entry (snumber todo headline tags href)
+  (setq headline (concat
+		  (and org-export-with-section-numbers
+		       (concat snumber " "))
+		  headline
+		  (and tags
+		    (concat
+		     (org-parse-format 'SPACES 3)
+		     (org-parse-format 'FONTIFY tags "tag")))))
+  (when todo
+    (setq headline (org-parse-format 'FONTIFY headline "todo")))
+  (org-parse-format 'LINK headline (concat  "#" href)))
+
+(defun org-html-format-toc-item (toc-entry level org-last-level)
+  (when (> level org-last-level)
+    (let ((cnt (- level org-last-level)))
+      (while (>= (setq cnt (1- cnt)) 0)
+	(org-parse-begin 'LIST 'unordered)
+	(org-parse-begin 'LIST-ITEM 'unordered))))
+  (when (< level org-last-level)
+    (let ((cnt (- org-last-level level)))
+      (while (>= (setq cnt (1- cnt)) 0)
+	(org-close-li)
+	(org-parse-end 'LIST 'unordered))))
+
+  (org-close-li)
+  (org-parse-begin 'LIST-ITEM 'unordered)
+  (insert toc-entry))
+
+(defun org-html-prepare-toc (lines level-offset opt-plist umax-toc)
+  (let* ((org-min-level (org-get-min-level lines level-offset))
+	 (org-last-level org-min-level)
+	 level)
+    (with-temp-buffer
+      (org-html-bind-local-variables opt-plist)
+      (erase-buffer)
+      (org-parse-begin 'SECTION "table-of-contents")
+      (insert
+       (org-parse-format 'HEADING
+			(nth 3 (plist-get opt-plist :lang-words))
+			org-export-html-toplevel-hlevel))
+      (org-parse-begin 'SECTION "text-table-of-contents")
+      (org-parse-begin 'LIST 'unordered)
+      (org-parse-begin 'LIST-ITEM 'unordered)
+      (setq
+       lines
+       (mapcar
+	'(lambda (line)
+	   (when (and (string-match org-todo-line-regexp line)
+		      (not (get-text-property 0 'org-protected line))
+		      (<= (setq level (org-tr-level
+				       (- (match-end 1) (match-beginning 1)
+					  level-offset)))
+			  umax-toc))
+	     (let ((txt (save-match-data
+			  (org-html-expand
+			   (org-export-cleanup-toc-line
+			    (match-string 3 line)))))
+		   (todo (and
+			  org-export-mark-todo-in-toc
+			  (or (and (match-beginning 2)
+				   (not (member (match-string 2 line)
+						org-done-keywords)))
+			      (and (= level umax-toc)
+				   (org-search-todo-below
+				    line lines level)))))
+		   tags)
+	       ;; Check for targets
+	       (while (string-match org-any-target-regexp line)
+		 (setq line
+		       (replace-match
+			(let ((org-html-protect t))
+			  (org-parse-format 'FONTIFY
+					   (match-string 1 line) "target"))
+			t t line)))
+	       (when (string-match
+		      (org-re "[ \t]+:\\([[:alnum:]_@:]+\\):[ \t]*$") txt)
+		 (setq txt (replace-match "" t nil txt)
+		       tags (match-string 1 txt)))
+	       (when (string-match quote-re0 txt)
+		 (setq txt (replace-match "" t t txt)))
+	       (while (string-match "&lt;\\(&lt;\\)+\\|&gt;\\(&gt;\\)+" txt)
+		 (setq txt (replace-match "" t t txt)))
+	       (org-parse-format
+		'TOC-ITEM
+		(let* ((snumber (org-section-number level))
+		       (href (replace-regexp-in-string
+			      "\\." "_" (format "sec-%s" snumber)))
+		       (href
+			(or
+			 (cdr (assoc
+			       href org-export-preferred-target-alist))
+			 href))
+		       (href (org-solidify-link-text href)))
+		  (org-parse-format 'TOC-ENTRY snumber todo txt tags href))
+		level org-last-level)
+	       (setq org-last-level level)))
+	   line)
+	lines))
+      (while (> org-last-level (1- org-min-level))
+	(setq org-last-level (1- org-last-level))
+	(org-close-li)
+	(org-parse-end 'LIST 'unordered))
+      (org-parse-end 'SECTION)
+      (org-parse-end 'SECTION)
+      ;; cleanup empty list items in toc
+      (while (re-search-backward "<li>[ \r\n\t]*</li>\n?" (point-min) t)
+	(replace-match ""))
+      (setq org-parse-table-of-contents (buffer-string))))
+  lines)
+
+
+;;;_   , table row
+(defun org-parse-format-table-row (fields &optional text-for-empty-fields)
+  (unless org-table-ncols
+    ;; first row of the table
+    (setq org-table-ncols (length fields))
+    (when org-table-is-styled
+      (setq org-table-num-numeric-items-per-column (make-vector org-table-ncols 0))
+      (setq org-table-colalign-vector (make-vector org-table-ncols nil))
+      (let ((c -1))
+	(while  (< (incf c) org-table-ncols)
+	  (let ((cookie (cdr (assoc (1+ c) org-table-colalign-info))))
+	    (setf (aref org-table-colalign-vector c)
+		  (cond
+		   ((string= cookie "l") "left")
+		   ((string= cookie "r") "right")
+		   ((string= cookie "c") "center")
+		   (t nil))))))))
+  (incf org-table-rownum)
+  (setq i -1)
+  (org-parse-format
+   'TABLE-ROW
+   (mapconcat
+    (lambda (x)
+      (when (string= x "")
+	(setq x text-for-empty-fields))
+      (incf i)
+      (and org-table-is-styled
+	   (< i org-table-ncols)
+	   (string-match org-table-number-regexp x)
+	   (incf (aref org-table-num-numeric-items-per-column i)))
+      (org-parse-format 'TABLE-CELL x org-table-rownum i))
+    fields "\n")))
+
+;;;_  . get callback
+(defun org-parse-get (what &optional opt-plist)
+  (funcall org-parse-get-callback what opt-plist))
+
+;;;_. postamble
+
+
+;;;_ org-newhtml.el
+;;;_. preamble
+;;;_. obsolete
+;;;_. maybe
+;;;_. hacks (to be documented)
+(defconst org-html-emphasis-alist
+  `(("*" bold)
+    ("/" emphasis)
+    ("_" underline)
+    ("=" code)
+    ("~" verbatim)
+    ("+" strike)))
+
+
+;;;_. user-specific
+;;;_ , custom settings
+;;;_  . potential custom settings
+;;;_ , interactive commands
+;;;_. parser
+;;;_ , initialization
+(defvar org-html-entity-control-callbacks-alist
+  `((EXPORT
+     . (org-html-begin-export org-html-end-export))
+    (DOCUMENT-CONTENT
+     . (org-html-begin-document-content org-html-end-document-content))
+    (DOCUMENT-BODY
+     . (org-html-begin-document-body org-html-end-document-body))
+    (ENVIRONMENT
+     . (org-html-begin-environment org-html-end-environment))
+    (LEVEL
+     . (org-html-begin-level org-html-end-level))
+    (FOOTNOTE-DEFINITION
+     . (org-html-begin-footnote-definition org-html-end-footnote-definition))
+    (TABLE
+     . (org-html-begin-table org-html-end-table))
+    (TABLE-ROWGROUP
+     . (org-html-begin-table-rowgroup org-html-end-table-rowgroup))
+    (LIST
+     . (org-html-begin-list org-html-end-list))
+    (LIST-ITEM
+     . (org-html-begin-list-item org-html-end-list-item))
+    (SECTION
+     . (org-html-begin-section org-html-end-section))
+    (PARAGRAPH
+     . (org-html-begin-paragraph org-html-end-paragraph)))
+  "")
+
+(defvar org-html-entity-format-callbacks-alist
+  `((EXTRA-TARGETS . org-html-format-extra-targets)
+    (ORG-TAGS . org-html-format-org-tags)
+    (SECTION-NUMBER . org-html-format-section-number)
+    (HEADLINE . org-html-format-headline)
+    (TOC-ENTRY . org-html-format-toc-entry)
+    (TOC-ITEM . org-html-format-toc-item)
+    (TAGS . org-html-format-tags)
+    (SPACES . org-html-format-spaces)
+    (TABS . org-html-format-tabs)
+    (LINE-BREAK . org-html-format-line-break)
+    (FONTIFY . org-html-format-fontify)
+    (TODO . org-html-format-todo)
+    (ORG-LINK . org-html-format-org-link)
+    (LINK . org-html-format-link)
+    (INLINE-IMAGE . org-html-format-inline-image)
+    (HEADING . org-html-format-heading)
+    (ANCHOR . org-html-format-anchor)
+    (TABLE-ROW . org-html-format-table-row)
+    (TABLE-CELL . org-html-format-table-cell)
+    (FOOTNOTES-SECTION . org-html-format-footnotes-section)
+    (FOOTNOTE-REFERENCE . org-html-format-footnote-reference)
+    (HORIZONTAL-LINE . org-html-format-horizontal-line)
+    (PLAIN . org-html-format-plain)
+    (COMMENT . org-html-format-comment))
+  "")
+
+
+
+;;;_ , callbacks
+;;;_  . control callbacks
+;;;_   , generic
+(defvar org-html-insert-tag-with-newlines 'both)
+
+(defun org-html-insert-tag (tag &rest args)
+  (when (member org-html-insert-tag-with-newlines '(lead both))
+    (insert  "\n"))
+  (insert (apply 'format tag args))
+  (when (member org-html-insert-tag-with-newlines '(trail both))
+    (insert  "\n")))
+
+;;;_   , document body
+(defun org-html-begin-document-body (opt-plist)
+  (let ((link-up (and (plist-get opt-plist :link-up)
+		      (string-match "\\S-" (plist-get opt-plist :link-up))
+		      (plist-get opt-plist :link-up)))
+	(link-home (and (plist-get opt-plist :link-home)
+			(string-match "\\S-" (plist-get opt-plist :link-home))
+			(plist-get opt-plist :link-home))))
+    (insert "\n<body>")
+    (org-parse-begin 'SECTION "content")
+    (insert  "\n"
+	     (or (and (or link-up link-home)
+		      (format org-export-html-home/up-format
+			      (or link-up link-home)
+			      (or link-home link-up))) "")
+	     "\n"))
+  (org-html-insert-preamble opt-plist))
+
+(defun org-html-end-document-body (opt-plist)
+  (org-html-insert-postamble opt-plist)
+  (unless body-only
+    (org-parse-end 'SECTION)
+    (insert "\n</body>")))
+
+
+;;;_   , document content
+(defun org-html-begin-document-content (opt-plist)
+  (let* ((language (plist-get opt-plist :language))
+	 (charset (or (and coding-system-for-write
+			   (fboundp 'coding-system-get)
+			   (coding-system-get coding-system-for-write
+					      'mime-charset))
+		      "iso-8859-1"))
+	 (style (concat (if (plist-get opt-plist :style-include-default)
+			    org-export-html-style-default)
+			(plist-get opt-plist :style)
+			(plist-get opt-plist :style-extra)
+			"\n"
+			(if (plist-get opt-plist :style-include-scripts)
+			    org-export-html-scripts)))
+	 (mathjax
+	  (if (or (eq (plist-get opt-plist :LaTeX-fragments) 'mathjax)
+		  (and org-export-have-math
+		       (eq (plist-get opt-plist :LaTeX-fragments) t)))
+
+	      (org-export-html-mathjax-config
+	       org-export-html-mathjax-template
+	       org-export-html-mathjax-options
+	       (or (plist-get opt-plist :mathjax) "")) "")))
+    (insert (format
+	     "%s
+<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Strict//EN\"
+	       \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\">
+<html xmlns=\"http://www.w3.org/1999/xhtml\"
+lang=\"%s\" xml:lang=\"%s\">
+<head>
+<title>%s</title>
+<meta http-equiv=\"Content-Type\" content=\"text/html;charset=%s\"/>
+<meta name=\"generator\" content=\"Org-mode\"/>
+<meta name=\"generated\" content=\"%s\"/>
+<meta name=\"author\" content=\"%s\"/>
+<meta name=\"description\" content=\"%s\"/>
+<meta name=\"keywords\" content=\"%s\"/>
+%s
+%s
+</head>
+"
+	     (format
+	      (or (and (stringp org-export-html-xml-declaration)
+		       org-export-html-xml-declaration)
+		  (cdr (assoc (plist-get opt-plist :html-extension)
+			      org-export-html-xml-declaration))
+		  (cdr (assoc "html" org-export-html-xml-declaration))
+
+		  "")
+	      charset)
+	     language language
+	     (plist-get opt-plist :title)
+	     charset
+	     (plist-get opt-plist :effective-date)
+	     (plist-get opt-plist :author)
+	     (plist-get opt-plist :description)
+	     (plist-get opt-plist :keywords)
+	     style
+	     mathjax))))
+
+(defun org-html-end-document-content ()
+  (insert "\n</html>\n"))
+
+
+;;;_   , level
+(defun org-html-begin-level (level title umax with-toc head-count)
+  "Insert a new level in HTML export.
+When TITLE is nil, just close all open levels."
+  (org-parse-end 'LEVEL level umax)
+  (unless title (error "Why is heading nil"))
+  (let* ((target (org-get-text-property-any 0 'target title))
+	 (extra-targets (and target
+			     (assoc target org-export-target-aliases)))
+	 (extra-class (org-get-text-property-any 0 'html-container-class title))
+	 (preferred (and target
+			 (cdr (assoc target org-export-preferred-target-alist))))
+	 snumber snu href suffix tags level1)
+    (setq extra-targets (remove (or preferred target) extra-targets))
+    (when (string-match (org-re "\\(:[[:alnum:]_@#%:]+:\\)[ \t]*$") title)
+      (setq tags (and org-export-with-tags (match-string 1 title)))
+      (setq title (replace-match "" t t title)))
+    (if (> level umax)
+	(progn
+	  (if (aref org-levels-open (1- level))
+	      (org-close-li)
+	    (aset org-levels-open (1- level) t)
+	    (org-parse-end-paragraph)
+	    (org-parse-begin 'LIST 'unordered))
+	  (org-parse-begin
+	   'LIST-ITEM 'unordered (and target (org-solidify-link-text
+					      (or preferred target))))
+
+	  (insert
+	   (org-parse-format 'HEADLINE title extra-targets tags))
+	  (insert "<br/>\n"))
+      (aset org-levels-open (1- level) t)
+      (setq snumber (org-section-number level)
+	    snu (replace-regexp-in-string "\\." "_" snumber))
+      (setq level1 (+ level org-export-html-toplevel-hlevel -1))
+      (unless (= head-count 1)
+	(org-parse-end 'SECTION))
+      (setq href (cdr (assoc (concat "sec-" snu)
+			     org-export-preferred-target-alist)))
+      (setq suffix (org-solidify-link-text (or href snu)))
+      (setq href (org-solidify-link-text (or href (concat "sec-" snu))))
+      (let ((id (format "outline-container-%s" suffix))
+	    (class (format "outline-%d%s" level1
+			   (if extra-class (concat " " extra-class) ""))))
+	(org-parse-begin 'SECTION id class))
+      (insert
+       (org-parse-format 'HEADING
+			(org-parse-format
+			 'HEADLINE title extra-targets tags snumber level1)
+			level1 href))
+      (let ((id (format "text-%s" suffix))
+	    (class (format "outline-text-%d" level1)))
+	(org-parse-begin 'SECTION id class))
+
+      (org-parse-begin-paragraph))))
+
+(defun org-html-end-level (level umax)
+  (org-parse-end-paragraph)
+  (let* ((l org-level-max))
+    (while (>= l level)
+      (if (aref org-levels-open (1- l))
+	  (progn
+	    ;; Terminate one level in HTML export
+	    (if (<= l umax)
+		(org-parse-end 'SECTION)
+	      (org-close-li)
+	      (org-parse-end 'LIST 'unordered))
+	    (aset org-levels-open (1- l) nil)))
+      (setq l (1- l)))))
+
+
+;;;_   , section
+(defun org-html-begin-section (&optional id class)
+  (let ((extra (concat (when id (format " id=\"%s\"" id))
+		       (when class (format " class=\"%s\"" class)))))
+    (org-html-insert-tag "<div%s>" extra)))
+
+(defun org-html-end-section ()
+  (org-html-insert-tag  "</div>"))
+
+
+
+;;;_   , paragraph
+(defun org-html-begin-paragraph (&optional style)
+  (let* ((class (cdr (assoc style '((footnote . "footnote")
+				    (verse . nil)))))
+	 (extra (if class (format " class=\"%s\"" class) "")))
+    (org-html-insert-tag "<p%s>" extra)))
+
+(defun org-html-end-paragraph ()
+  (insert "</p>"))
+
+
+;;;_   , environment
+(defun org-html-format-environment (style beg-end)
+  (assert (memq style '(blockquote center verse fixedwidth quote)) t)
+  (case style
+    (blockquote
+     (case beg-end
+       (BEGIN
+	(org-parse-end-paragraph)
+	(insert "<blockquote>\n")
+	(org-parse-begin-paragraph))
+       (END
+	(org-parse-end-paragraph)
+	(insert "\n</blockquote>\n")
+	(org-parse-begin-paragraph))))
+    (verse
+     (case beg-end
+       (BEGIN
+	(org-parse-end-paragraph)
+	(insert "\n<p class=\"verse\">\n")
+	(setq org-par-open t))
+       (END
+	(insert "</p>\n")
+	(setq org-par-open nil)
+	(org-parse-begin-paragraph))))
+    (center
+     (case beg-end
+       (BEGIN
+	(org-parse-end-paragraph)
+	(insert "\n<div style=\"text-align: center\">")
+	(org-parse-begin-paragraph))
+       (END
+	(org-parse-end-paragraph)
+	(insert "\n</div>")
+	(org-parse-begin-paragraph))))
+    (fixedwidth
+     (case beg-end
+       (BEGIN
+	(org-parse-end-paragraph)
+	(insert "<pre class=\"example\">\n"))
+       (END
+	(insert "</pre>\n")
+	(org-parse-begin-paragraph))))
+    (quote
+     (case beg-end
+       (BEGIN
+	(org-parse-end-paragraph)
+	(insert "<pre>"))
+       (END
+	(insert "</pre>\n")
+	(org-parse-begin-paragraph))))
+    (t (error "Unknown environment %s" style))))
+
+
+(defun org-html-begin-environment (style)
+  (org-html-format-environment style 'BEGIN))
+
+(defun org-html-end-environment (style)
+  (org-html-format-environment style 'END))
+
+
+;;;_   , list
+(defun org-html-html-list-type-to-canonical-list-type (ltype)
+  (cdr (assoc ltype '(("o" . ordered)
+		      ("u" . unordered)
+		      ("d" . description)))))
+
+(defun org-html-begin-list (ltype &optional arg1)
+  (setq ltype (or (org-html-html-list-type-to-canonical-list-type ltype)
+		  ltype))
+
+  (case ltype
+    (ordered (let ((extra (if arg1 (format " start=\"%d\"" arg1) "")))
+	       (org-html-insert-tag "<ol%s>" extra)))
+    (unordered (org-html-insert-tag "<ul>"))
+    (description (org-html-insert-tag "<dl>"))
+    (t (error "Unknown list type: %s"  ltype))))
+
+(defun org-html-end-list (ltype)
+  (setq ltype (or (org-html-html-list-type-to-canonical-list-type ltype)
+		  ltype))
+
+  (org-html-insert-tag
+     (case ltype
+       (ordered "</ol>")
+       (unordered "</ul>")
+       (description "</dl>")
+       (t (error "Unknown list type: %s" ltype)))))
+
+(defun org-html-begin-list-item (ltype &optional arg)
+  (setq ltype (or (org-html-html-list-type-to-canonical-list-type ltype)
+		  ltype))
+  (case ltype
+    (ordered
+     (let* ((counter arg)
+	   (extra (if counter (format " value=\"%s\"" counter) "")))
+       (org-html-insert-tag "<li%s>" extra)))
+    (unordered
+     (let* ((id arg)
+	   (extra (if id (format " id=\"%s\"" id) "")))
+       (org-html-insert-tag "<li%s>" extra)))
+    (description
+     (let* ((desc-tag (or arg "(no term)")))
+       (insert
+	(org-html-format-tags '("<dt>" . "</dt>") desc-tag))
+       (org-html-insert-tag "<dd>")))
+    (t (error "Unknown list type"))))
+
+(defun org-html-end-list-item (ltype)
+  (setq ltype (or (org-html-html-list-type-to-canonical-list-type ltype)
+		  ltype))
+  (case ltype
+    (ordered (org-html-insert-tag "</li>"))
+    (unordered (org-html-insert-tag "</li>"))
+    (description (org-html-insert-tag "</dd>"))
+    (t (error "Unknown list type"))))
+
+
+;;;_   , table
+
+(defvar org-table-rowgroup-info)
+(defun org-parse-begin-table-rowgroup (&optional is-header-row)
+  (push (cons (1+ org-table-rownum) :start) org-table-rowgroup-info)
+  (org-parse-begin 'TABLE-ROWGROUP is-header-row))
+
+(defun org-html-begin-table-rowgroup (&optional is-header-row)
+  (when org-table-rowgroup-open
+    (org-parse-end 'TABLE-ROWGROUP))
+  (org-html-insert-tag (if is-header-row "<thead>" "<tbody>"))
+  (setq org-table-rowgroup-open t)
+  (setq org-table-current-rowgroup-is-header is-header-row))
+
+(defun org-html-end-table-rowgroup ()
+  (when org-table-rowgroup-open
+    (setq org-table-rowgroup-open nil)
+    (org-html-insert-tag
+     (if org-table-current-rowgroup-is-header "</thead>" "</tbody>"))))
+
+(defun org-html-begin-table (caption label attributes)
+  (let ((html-table-tag
+	 (org-export-splice-attributes html-table-tag attributes)))
+    (when label
+      (setq html-table-tag
+	    (org-export-splice-attributes
+	     html-table-tag
+	     (format "id=\"%s\"" (org-solidify-link-text label)))))
+    (org-html-insert-tag html-table-tag))
+
+  ;; Since the output of HTML table formatter can also be used in
+  ;; DocBook document, we want to always include the caption to make
+  ;; DocBook XML file valid.
+  (insert (format "<caption>%s</caption>" (or caption "")) "\n"))
+
+(defun org-parse-end-table ()
+  (when org-table-is-styled
+    ;; column groups
+    (unless (car org-table-colgroup-info)
+      (setq org-table-colgroup-info
+	    (cons :start (cdr org-table-colgroup-info))))
+
+    ;; column alignment
+    (let ((c -1))
+      (mapc
+       (lambda (x)
+	 (incf c)
+	 (setf (aref org-table-colalign-vector c)
+	       (or (aref org-table-colalign-vector c)
+		   (if (> (/ (float x) (1+ org-table-rownum))
+			  org-table-number-fraction)
+		       "right" "left"))))
+       org-table-num-numeric-items-per-column)))
+  (org-parse-end 'TABLE))
+
+(defun org-html-end-table ()
+  (when org-table-is-styled
+    (goto-char org-table-begin-marker)
+    (setq org-table-begin-marker nil)
+
+    (let ((c -1) gr colgropen)
+      (insert
+       (mapconcat
+	(lambda (x)
+	  (incf c)
+	  (setq gr (pop org-table-colgroup-info))
+
+	  (concat
+	   (if (memq gr '(:start :startend))
+	       (prog1
+		   (if colgropen
+		       "</colgroup>\n<colgroup>"
+		     "<colgroup>")
+		 (setq colgropen t))
+	     "")
+
+	   (let* ((align (aref org-table-colalign-vector c))
+		  (alignspec (if no-css " align=\"%s\"" " class=\"%s\""))
+		  (extra (format alignspec  align)))
+	     (format "<col%s />" extra))
+
+	   (if (memq gr '(:end :startend))
+	       (progn (setq colgropen nil) "</colgroup>")
+	     "")))
+	org-table-num-numeric-items-per-column ""))
+
+      (if colgropen (insert "</colgroup>")))
+
+    ;; fill style attributes for table cells
+    (while (re-search-forward "@@class\\([0-9]+\\)@@" nil t)
+      (let ((c (string-to-number (match-string 1))))
+	(replace-match
+	 (if org-export-html-table-align-individual-fields
+	     (format (if no-css " align=\"%s\"" " class=\"%s\"")
+		     (or (aref org-table-colalign-vector c) "left")) "")
+	 t t)))
+    (goto-char (point-max)))
+  (org-html-insert-tag "</table>\n"))
+
+(defun org-html-format-table-row (row)
+  (org-html-format-tags
+   (cons (eval (car org-export-table-row-tags))
+	 (eval (cdr org-export-table-row-tags))) row))
+
+(defun org-html-format-table-cell (text r c)
+  (let ((cell-style-cookie (or (and org-table-is-styled
+				    (format "@@class%03d@@" c)) "")))
+    (cond
+     (org-table-current-rowgroup-is-header
+      (org-html-format-tags
+       org-export-table-header-tags x  "col" cell-style-cookie))
+     ((and (= c 0) org-export-html-table-use-header-tags-for-first-column)
+      (org-html-format-tags
+       org-export-table-header-tags x "row" cell-style-cookie))
+     (t
+      (org-html-format-tags
+       org-export-table-data-tags x cell-style-cookie)))))
+
+
+;;;_   , footnote definition
+(defun org-html-begin-footnote-definition (n)
+  (org-parse-begin-paragraph 'footnote)
+  (insert
+   (format
+    (format org-export-html-footnote-format
+	    "<a class=\"footnum\" name=\"fn.%s\" href=\"#fnr.%s\">%s</a>")
+    n n n)))
+
+(defun org-html-end-footnote-definition (n)
+  (org-parse-end-paragraph))
+
+
+
+;;;_  . format callbacks
+
+(defvar org-html-protect nil)
+;;;_   , spaces
+(defun org-html-format-spaces (n)
+  (let ((space (or (and org-html-protect "\\nbsp") "&nbsp;")) out)
+    (while (> n 0)
+      (setq out (concat out space))
+      (setq n (1- n))) out))
+
+;;;_   , tabs
+(defun org-html-format-tabs (&optional n)
+  (ignore))
+
+;;;_   , line break
+(defun org-html-format-line-break ()
+  (org-html-format-tags '("<br>" . "</br>") ""))
+
+;;;_   , horizontal line
+(defun org-html-format-horizontal-line ()
+  (concat  "\n" "<hr/>" "\n"))
+
+;;;_   , line
+
+(defun org-html-format-plain (line)
+  (case org-parse-dyn-current-environment
+    ((quote fixedwidth) (concat (org-html-protect line) "\n"))
+    (t (concat line "\n"))))
+
+(defun org-html-format-comment (fmt &rest args)
+  (let ((comment (apply 'format fmt args)))
+    (format "\n<!-- %s  -->\n" comment)))
+
+
+;;;_   , character styles
+(defun org-html-format-fontify (text style &optional id)
+  (let (class extra how)
+    (cond
+     ((eq style 'underline)
+      (setq extra " style=\"text-decoration:underline;\"" ))
+     ((setq how (cdr (assoc style
+			    '((bold . ("<b>" . "</b>"))
+			      (emphasis . ("<i>" . "</i>"))
+			      (code . ("<code>" . "</code>"))
+			      (verbatim . ("<code>" . "</code>"))
+			      (strike . ("<del>" . "</del>"))
+			      (subscript . ("<sub>" . "</sub>"))
+			      (superscript . ("<sup>" . "</sup>")))))))
+     ((listp style)
+      (setq class (mapconcat 'identity style " ")))
+     ((stringp style)
+      (setq class style))
+     (t (error "Unknown style %S" style)))
+
+    (setq extra (concat (when class (format " class=\"%s\"" class))
+			(when id (format " id=\"%s\""  id))
+			extra))
+    (org-html-format-tags
+     (or how '("<span%s>" . "</span>")) text extra)))
+
+;;;_   , link
+(defun org-html-format-link (text href &optional extra)
+  (let* ((extra (concat (format " href=\"%s\"" href) extra)))
+    (org-html-format-tags '("<a%s>" . "</a>") text extra)))
+
+;;;_   , heading
+(defun org-html-format-heading (text level &optional id class)
+  (let* ((extra (concat
+		 (when id (format " id=\"%s\"" id))
+		 (when class (format " class=\"%s\"" class)))))
+    ;; (org-html-format-tags
+    ;;  text '("<h%d%s>" . "</h%d>") level extra)
+
+    ;; Also look at org-export-html-preamble-format
+    (concat
+     (format "<h%d%s>" level extra) text (format "</h%d>"  level))))
+
+;;;_   , headline
+(defun org-html-format-headline (title extra-targets tags
+					    &optional snumber level)
+  (concat
+   (org-parse-format 'EXTRA-TARGETS extra-targets)
+   (concat (org-parse-format 'SECTION-NUMBER snumber level) " ")
+   title
+   (and tags (concat (org-parse-format 'SPACES 3)
+		     (org-parse-format 'ORG-TAGS tags)))))
+
+;;;_   , anchor
+(defun org-html-format-anchor (text name &optional class)
+  (let* ((id name)
+	 (extra (concat
+		 (when name (format " name=\"%s\""  name))
+		 (when id (format " id=\"%s\""  id))
+		 (when class (format " class=\"%s\""  class)))))
+    (org-html-format-tags '("<a%s>" . "</a>") text extra)))
+
+
+
+;;;_   , target
+;;;_   , footnote reference
+(defun org-html-format-footnote-reference (n def refcnt)
+  (let ((extra (if (= refcnt 1) "" (format ".%d"  refcnt))))
+    (format org-export-html-footnote-format
+	    (format
+	     "<a class=\"footref\" name=\"fnr.%s%s\" href=\"#fn.%s\">%s</a>"
+	     n extra n n))))
+
+
+
+;;;_   , footnotes section
+(defun org-html-format-footnotes-section (section-name definitions)
+  (if (not definitions) ""
+    (format org-export-html-footnotes-section section-name definitions)))
+
+
+;;;_   , image
+;;;_   , generic
+(defun org-html-format-tags (tag text &rest args)
+  (let ((prefix (when org-html-protect "@"))
+	(suffix (when org-html-protect "@")))
+    (concat prefix (apply 'format (car tag) args)
+	    text
+	    suffix (format (cdr tag)))))
+
+
+;;;_  . maintenance callbacks
+;;;_   , init method
+;;;_   , save method
+;;;_   , cleanup method
+;;;_  . get callback
+(defun org-html-get (what &optional opt-plist)
+  (case what
+    (BACKEND 'html)
+    (INIT-METHOD nil)
+    (SAVE-METHOD nil)
+    (CLEANUP-METHOD nil)
+    (EXPORT-DIR (org-export-directory :html opt-plist))
+    (FILE-NAME-EXTENSION (plist-get opt-plist :html-extension))
+    (EXPORT-BUFFER-NAME "*Org HTML Export*")
+    (ENTITY-CONTROL org-html-entity-control-callbacks-alist)
+    (ENTITY-FORMAT org-html-entity-format-callbacks-alist)
+    (t (error "Unknown property: %s"  what))))
+
+
+;;;_   , coding system
+(defun org-html-get-coding-system-for-write ()
+  (or org-export-html-coding-system
+      (and (boundp 'buffer-file-coding-system) buffer-file-coding-system)))
+
+(defun org-html-get-coding-system-for-save ()
+  (or org-export-html-coding-system
+      (and (boundp 'buffer-file-coding-system) buffer-file-coding-system)))
+
+
+;;;_. newhtml (non-parser & misc)
+(defun org-html-insert-toc (toc)
+  ;; locate where toc needs to be inserted
+  (goto-char (point-min))
+  (if (or (re-search-forward
+	   "<p>\\s-*\\[TABLE-OF-CONTENTS\\]\\s-*</p>" nil t)
+	  (re-search-forward
+	   "\\[TABLE-OF-CONTENTS\\]" nil t))
+      (progn
+	(goto-char (match-beginning 0))
+	(replace-match ""))
+    (goto-char org-html-dyn-first-heading-pos)
+    (when (looking-at "\\s-*</p>")
+      (goto-char (match-end 0))
+      (insert "\n")))
+  (insert toc))
+
+(defun org-html-insert-preamble (opt-plist)
+  (when (plist-get opt-plist :html-preamble)
+    (let ((html-pre (plist-get opt-plist :html-preamble))
+	  (title (plist-get opt-plist :title))
+	  (date (plist-get opt-plist :effective-date))
+	  (author (plist-get opt-plist :author))
+	  (lang-words (plist-get opt-plist :lang-words))
+	  (email (plist-get opt-plist :email)))
+      (cond ((stringp html-pre)
+	     (insert
+	      (format-spec html-pre `((?t . ,title) (?a . ,author)
+				      (?d . ,date) (?e . ,email)))))
+	    ((functionp html-pre)
+	     (funcall html-pre opt-plist))
+	    (t
+	     (insert
+	      (format-spec
+	       (or (cadr (assoc (nth 0 lang-words)
+				org-export-html-preamble-format))
+		   (cadr (assoc "en" org-export-html-preamble-format)))
+	       `((?t . ,title) (?a . ,author)
+		 (?d . ,date) (?e . ,email)))))))))
+
+(defun org-html-insert-postamble (opt-plist)
+  (when org-html-footnote-definitions
+    (insert
+     (org-parse-format
+      'FOOTNOTES-SECTION (nth 4 (plist-get opt-plist :lang-words))
+      (mapconcat (lambda (x) (cdr x))
+		 (nreverse org-html-footnote-definitions) "\n"))))
+  (let ((bib (org-export-html-get-bibliography)))
+    (when bib
+      (insert "\n" bib "\n")))
+
+  ;; export html postamble
+  (unless body-only
+    (let* ((html-post (plist-get opt-plist :html-postamble))
+	   (date (plist-get opt-plist :effective-date))
+	   (author (plist-get opt-plist :author))
+	   (email  (plist-get opt-plist :email))
+	   (lang-words (plist-get opt-plist :lang-words))
+	   (html-validation-link (or org-export-html-validation-link ""))
+	   (email
+	    (mapconcat (lambda(e)
+			 (format "<a href=\"mailto:%s\">%s</a>" e e))
+		       (split-string email ",+ *")
+		       ", "))
+	   (creator-info
+	    (concat "Org version " org-version " with Emacs version "
+		    (number-to-string emacs-major-version))))
+      (when (plist-get opt-plist :html-postamble)
+	(cond ((stringp html-post)
+	       (insert "<div id=\"postamble\">\n")
+	       (insert (format-spec html-post
+				    `((?a . ,author) (?e . ,email)
+				      (?d . ,date)   (?c . ,creator-info)
+				      (?v . ,html-validation-link))))
+	       (insert "</div>"))
+	      ((functionp html-post)
+	       (funcall html-post opt-plist))
+	      ((eq html-post 'auto)
+	       ;; fall back on default postamble
+	       (insert "<div id=\"postamble\">\n")
+	       (when (plist-get opt-plist :time-stamp-file)
+		 (insert "<p class=\"date\">" (nth 2 lang-words) ": " date "</p>\n"))
+	       (when (and (plist-get opt-plist :author-info) author)
+		 (insert "<p class=\"author\">" (nth 1 lang-words) ": " author "</p>\n"))
+	       (when (and (plist-get opt-plist :email-info) email)
+		 (insert "<p class=\"email\">" email "</p>\n"))
+	       (when (plist-get opt-plist :creator-info)
+		 (insert "<p class=\"creator\">"
+			 (concat "Org version " org-version " with Emacs version "
+				 (number-to-string emacs-major-version) "</p>\n")))
+	       (insert html-validation-link "\n</div>"))
+	      (t
+	       (insert "<div id=\"postamble\">\n")
+	       (insert (format-spec
+			(or (cadr (assoc (nth 0 lang-words)
+					 org-export-html-postamble-format))
+			    (cadr (assoc "en" org-export-html-postamble-format)))
+			`((?a . ,author) (?e . ,email)
+			  (?d . ,date)   (?c . ,creator-info)
+			  (?v . ,html-validation-link))))
+	       (insert "</div>"))))))
+
+  (if org-export-html-with-timestamp
+      (insert org-export-html-html-helper-timestamp)))
+
+
+(defun org-html-format-todo (todo)
+  (org-parse-format 'FONTIFY
+		   (org-export-html-get-todo-kwd-class-name todo)
+		   (list (if (member todo org-done-keywords) "done" "todo")
+			 todo)))
+
+
+
+(defun org-html-format-extra-targets (extra-targets)
+  (if (not extra-targets) ""
+      (mapconcat (lambda (x)
+	       (setq x (org-solidify-link-text
+			(if (org-uuidgen-p x) (concat "ID-" x) x)))
+	       (org-parse-format 'ANCHOR "" x))
+	     extra-targets "")))
+
+(defun org-html-format-org-tags (tags)
+  (if (not tags) ""
+    (org-parse-format
+     'FONTIFY (mapconcat
+	       (lambda (x)
+		 (org-parse-format
+		  'FONTIFY x (org-export-html-get-tag-class-name x)))
+	       (org-split-string tags ":")
+	       (org-parse-format 'SPACES 1)) "tag")))
+
+(defun org-html-format-section-number (&optional snumber level)
+  (and org-export-with-section-numbers
+       (not body-only) snumber level
+       (org-parse-format 'FONTIFY snumber (format "section-number-%d" level))))
+
+;;;_. preprocessor
+;;;_. postamble
+
 (provide 'org-html)
 
 ;; arch-tag: 8109d84d-eb8f-460b-b1a8-f45f3a6c7ea1
diff --git a/lisp/org.el b/lisp/org.el
index 27a3949..a119c09 100644
--- a/lisp/org.el
+++ b/lisp/org.el
@@ -8711,7 +8711,7 @@ If optional argument MERGE is set, merge TABLE into
 
 (defun org-link-unescape (str)
   "Unhex hexified unicode strings as returned from the JavaScript function
-encodeURIComponent. E.g. `%C3%B6' is the german Umlaut `ö'."
+encodeURIComponent. E.g. `%C3%B6' is the german Umlaut `ö'."
   (unless (and (null str) (string= "" str))
     (let ((pos 0) (case-fold-search t) unhexed)
       (while (setq pos (string-match "\\(%[0-9a-f][0-9a-f]\\)+" str pos))
@@ -8721,9 +8721,9 @@ encodeURIComponent. E.g. `%C3%B6' is the german Umlaut `ö'."
   str)
 
 (defun org-link-unescape-compound (hex)
-  "Unhexify unicode hex-chars. E.g. `%C3%B6' is the German Umlaut `ö'.
+  "Unhexify unicode hex-chars. E.g. `%C3%B6' is the German Umlaut `ö'.
 Note: this function also decodes single byte encodings like
-`%E1' (\"á\") if not followed by another `%[A-F0-9]{2}' group."
+`%E1' (\"á\") if not followed by another `%[A-F0-9]{2}' group."
   (save-match-data
     (let* ((bytes (cdr (split-string hex "%")))
 	   (ret "")
@@ -10749,6 +10749,7 @@ This function can be used in a hook."
          "<literal style=\"html\">?</literal>")
     ("a" "#+begin_ascii\n?\n#+end_ascii")
     ("A" "#+ascii: ")
+    ("o" "#+begin_odt\n?\n#+end_odt")
     ("i" "#+include %file ?"
          "<include file=%file markup=\"?\">")
     )
-- 
1.7.2.3


[-- Attachment #3: test.org --]
[-- Type: text/plain, Size: 13003 bytes --]

#+TITLE: Testfile for OpenDocumentText Exporter
#+AUTHOR:    Jambunathan K
#+EMAIL:     kjambunathan@gmail.com
#+DATE:      2010-10-26 Sat
#+LANGUAGE:  en
#+OPTIONS:   H:3 num:t  \n:nil @:t ::t |:t ^:t -:t f:t *:t <:t
#+OPTIONS:   LaTeX:dvipng
#+STARTUP:   inlineimages overview

* Character Styles
** Bold

   *This is bold text*
   
** Italic

   /This is an italicized text/
   
** Underline

   _This is an underlined text_
   
** Code

   =This is a code text=
   
** Verbatim

   ~This is a verbatim text~
   
** Strikethrough

   +This is a strikethorugh text+

** Super and Subscripts

   Y = a_{0}X^{2}+a_{1}X^{1}+a_{2}
* Miscellaneous
  
  Here is a ndash --, a mdash ---, an ellipsis ....
  
  and a horizontal line
  ---------------------
  
* Paragraph Styles
** Quotation
   
*** Style1

#+BEGIN_QUOTE
    Everything should be made as simple as possible,
    but not any simpler -- Albert Einstein
#+END_QUOTE
    
*** QUOTE Style2

    Everything should be made as simple as possible,
    but not any simpler -- Albert Einstein

** Verse

#+BEGIN_VERSE
  Great clouds overhead
  Tiny black birds rise and fall
  Snow covers Emacs
 
      -- AlexSchroeder
#+END_VERSE
      
** Centered

#+BEGIN_CENTER
   This is a centered paragraph.
#+END_CENTER
  
** Example
*** Example Style 1

#+begin_example
  First line of the example.
  Second line of the example.
#+end_example  
  
*** Example Style 2

:     First line of the example.
:     Second line of the example.
    
  
** Source Block
*** Emacs Lisp Block 
#+begin_src emacs-lisp
  (defun helloworld () 
    ""
    (message "hello world"))
#+end_src  
    
*** Org Source Block
    
#+begin_src org
  ,* Some Appointment
  ,  SCHEDULED: <2010-11-17 Wed>
#+end_src    

* Embedded ODT
** Handcrafted Para
   
#+begin_html
  <p> 
    This is a handwritten html para
  </p>
#+end_html
   

#+begin_odt
  <text:p> This is a handwritten odt para</text:p>
#+end_odt

** An Equation as Embeded MathML
   A trigonometric equation embedded in *MathML*

#+begin_odt
  <text:p>
    <draw:frame draw:style-name="fr2" draw:name="Object3" text:anchor-type="as-char" svg:width="6.371cm" svg:height="0.483cm" draw:z-index="3">
      <draw:object>
        <math xmlns="http://www.w3.org/1998/Math/MathML">
          <semantics>
            <mrow>
              <mi>sin</mi>
              <mrow>
                <mrow>
                  <mo stretchy="false">(</mo>
                  <mrow>
                    <mi>A</mi>
                    <mo stretchy="false">+</mo>
                    <mi>B</mi>
                  </mrow>
                  <mo stretchy="false">)</mo>
                </mrow>
                <mi mathvariant="normal">=</mi>
                <mi>sin</mi>
              </mrow>
              <mi mathvariant="italic">ACos</mi>
              <mrow>
                <mi>B</mi>
                <mo stretchy="false">+</mo>
                <mi>cos</mi>
              </mrow>
              <mi>A</mi>
              <mi>sin</mi>
              <mi>B</mi>
            </mrow>
            <annotation encoding="StarMath 5.0">sin (A+B) = sin ACos B + cos A sin B
            </annotation>
          </semantics>
        </math>
      </draw:object>
    </draw:frame>
  </text:p>
#+end_odt

* Lists
** Simple Lists
*** Numbered List
    
    This is a numbered list.
    
    1. L1N1
    2. L1N2
    3. L1N3
    
*** Bulleted List
    
    This is a bulleted list.
    - L1B1
    - L1B2
    - L1B3
    
*** Description List
    
    There is a nested description list down below
    - Term-1 :: This is a definition for Term-1 which wraps around to
                the next line
    - Term-2 :: This is a definition for Term-2 which wraps around to
                the next line
      - Term-2.1 :: Definition for Term-2.1
      - Term-2.2 :: Definition for Term-2.2
    
*** A Complex List
    
    1. L1N1
       1. L2N2
       2. L2N3
    2. L1N4
       * L2B1
       * L2B2
	 - L3B3
	   
	   First paragraph.
	   
	   Second paragraph.
	   
	 - L3B4
    3. L1N5
       1. L2N6
          1. L3N7

** A Very Complex List
*** Lord of the Rings

    My favorite scenes are (in this order)
    1. The attack of the Rohirrim
    2. Eowyn's fight with the witch king
       + this was already my favorite scene in the book
       + I really like Miranda Otto.
         - Definition-1 :: Description-1
         - Definition-2 :: Description-2
			   
			   
    3. Peter Jackson being shot by Legolas
       He makes a really funny face when it happens.
       - on DVD only
	 
	 
    But in the end, no individual scenes matter but the film as a whole.
    Important actors in this film are:
    - Elijah Wood :: He plays Frodo
    - Sean Austin :: He plays Sam, Frodo's friend.  I still remember
		     him very well from his role as Mikey Walsh in
		     The Goonies
		     
      - Embedded Definition 1 :: Embedded Description 1
      - Embedded Definition 2 :: Embedded Description 2
	   
	   
    

* Images
** Image URLs
   See the You can see the official logo of Orgmode here:
   [[http://orgmode.org/img/org-mode-unicorn.png]]

** Inlined Images
*** A simple inlined image

   [[./org-mode-unicorn.png]]
   
*** A simple image with caption and label
  
#+CAPTION: Unicorn Logo
#+LABEL: fig:1024
  [[./org-mode-unicorn.png]]

*** An image that is explicitly sized
#+CAPTION: Unicorn Logo
#+LABEL: fig:1025
#+ATTR_ODT: (:width 10 :height 10)
  [[./org-mode-unicorn.png]]

*** An image that is scaled
#+ATTR_ODT: (:scale 0.5)
  [[./org-mode-unicorn.png]]

** Thumbnails
   This is a clickable image [[http://orgmode.org][./org-mode-unicorn.png]]
  

** Reference to an Image
   Please refer to \ref{fig:1024} for further information.
   
** LaTeX Fragments 

*** LaTeX Fragment1
#   See org-format-latex-options
    
    There is a equation down below.

   \begin{equation}
     e = \frac{1}{2}mv^2
   \end{equation}
   
*** LaTeX Fragment2
    
    \begin{equation}
    x=\sqrt{b} 
    \end{equation}
    
    If $a^2=b$ and \( b=2 \), then the solution must be either $$
    a=+\sqrt{2} $$ or \[ a=-\sqrt{2} \].

* File URLs
** Relative URL
   [[../../lisp/org-html.el][This is a relative link to org-html.el]]

** Absolute URL
   [[file:~/src/orgmode.org/contrib/odt/OrgOdtStyles.xml][This is an absolute link to styles file]]

* Links
** Targets
*** Fuzzy Target
*** Target with CUSTOMID
    :PROPERTIES:
    :CUSTOM_ID: aabbccddeeff
    :END:
    
*** Dedicated Target Style1
#   <<Dedicated Target>>    
    
*** Dedicated Target Style2

    There is a dedicated target at the end of this sentence -
    <<Dedicated Target1>>.
    
*** <<<Radioed Target>>>
    
** References
*** References to Fuzzy Target

    This is a link to [[Fuzzy Target]].
    
*** References to CUSTOMID links

    This is a link to [[#aabbccddeeff][Target with CUSTOMID]]. This is nodesc link to [[#aabbccddeeff]].
    
*** References to Dedicated Target

    There is a link to nodesc [[Dedicated Target]] here. There is a link
    to [[Dedicated%20Target][Jump to Dedicated Target]] here.
    
    There is a link to [[Dedicated%20Target1][Dedicated Target1]] here.
    
*** References to Radioed Links

    This section has references to Radioed Target. One more reference
    to Radioed Target.

* Tables
** A simple Orgmode Table
   
   | EST | New York | -5:00 |
   | IST | Madras   | +5:30 |
   | AST | Bahrain  | +3:00 |

** A formatted Orgmode Table

#+CAPTION: An Example Table
#+LABEL:   table:10

  |     Labels | C1          | C2            |           C3 |
  |------------+-------------+---------------+--------------|
  |          / | <           | >             |           <> |
  |        <r> | <l>         | <c>           |          <r> |
  | R1 (Right) | R1C1 (Left) | R1C2 (Center) | R1C3 (Right) |
  |         R2 | R2C1        | R2C2          |         R2C3 |
  |------------+-------------+---------------+--------------|
  |         R3 | R3C1        | R3C2          |         R3C3 |
  |------------+-------------+---------------+--------------|
  |         R5 | R5C1        | R5C2          |         R5C3 |
  |         R6 | R6C1        | R6C2          |         R6C3 |
  |------------+-------------+---------------+--------------|

** Table.el Table with no Spanning
   +---------------+---------------+
   |Term           |Percentage     |
   +---------------+---------------+
   |Quarter        |25%            |
   |One-Fourth     |               |
   +---------------+---------------+
   |Half           |50%            |
   |One-by-Two     |               |
   +---------------+---------------+
   |Three-Quarters |75%            |
   |Three-Fourths  |               |
   +---------------+---------------+
   |Full           |100%           |
   |Whole          |               |
   +---------------+---------------+
   
** COMMENT Table.el Table with Spanning
    
   +----------+---------------------+----------+
   |Name      |cmd        calls     |Percentage|
   +----------+                     +----------+
   |rgb       |93         534       |46%       |
   +----------+                     +----------+
   |Xah       |82         090       |40%       |
   +----------+                     +----------+
   |total     |203        118       |100%      |
   +----------+---------------------+----------+
   
** COMMENT Another Table.el Table with Spanning
   
   +----------+----------+
   | Header 1 | Header 2 |
   +----------+----------+
   | R1 C1-2             |
   +----------+----------+
   | R2 C1    | R2-3 C2  |
   +          +----------+
   |          |          |
   +----------+----------+
   
* Table Referenced

  Please refer to \ref{table:10} for further information.

* Footnote Definitions (Part 1)

[fn:XYZ] There is a link to [[http://Orgmode.org][Orgmode.org]].

* Footnote Usage
** Plain Footnotes

   Footnote [1]. One more reference to footnote [1].
   
** Named Footnotes

   Footnote named XYZ [fn:XYZ].

** Inlined Footnote

   Inlined footnote [fn:: inline definition]
   
** Named and Inlined Footnote

   Named and Inlined footnote [fn:name: named definition]


# Footnote Definitions (Part 2)
[1] Quick brown fox jumps over the lazy dog. Quick brown fox jumps ove
the lazy dog. 

* About Orgmode
  Org is a mode for keeping notes, maintaining TODO lists, and doing
  project planning with a fast and effective plain-text system.

  Org develops organizational tasks around NOTES files that contain
  lists or information about projects as plain text. Org is
  implemented on top of Outline mode, which makes it possible to keep
  the content of large files well structured. Visibility cycling and
  structure editing help to work with the tree. Tables are easily
  created with a built-in table editor. Org supports TODO items,
  deadlines, timestamps, and scheduling. It dynamically compiles
  entries into an agenda that utilizes and smoothly integrates much of
  the Emacs calendar and diary. Plain text URL-like links connect to
  websites, emails, Usenet messages, BBDB entries, and any files
  related to the projects. For printing and sharing of notes, an Org
  file can be exported as a structured ASCII file, as HTML, or (TODO
  and agenda items only) as an iCalendar file. It can also serve as a
  publishing tool for a set of linked web pages.

  As a project planning environment, Org works by adding metadata to
  outline nodes. Based on this data, specific entries can be extracted
  in queries and create dynamic agenda views.

  Org mode contains the Org Babel environment which allows you to work
  with embedded source code blocks in a file, to facilitate code
  evaluation, documentation, and tangling.

  Org's automatic, context-sensitive table editor with spreadsheet
  capabilities can be integrated into any major mode by activating the
  minor Orgtbl mode. Using a translation step, it can be used to
  maintain tables in arbitrary file types, for example in LaTeX. The
  structure editing and list creation capabilities can be used outside
  Org with the minor Orgstruct mode.

  Org keeps simple things simple. When first fired up, it should feel
  like a straightforward, easy to use outliner. Complexity is not
  imposed, but a large amount of functionality is available when you
  need it. Org is a toolbox and can be used in different ways and for
  different ends, for example:

  -  an outline extension with visibility cycling and structure editing
  -  an ASCII system and table editor for taking structured notes
  -  a TODO list editor
  -  a full agenda and planner with deadlines and work scheduling
  -  an environment in which to implement David Allen's GTD system
  -  a simple hypertext system, with HTML and LaTeX export
  -  a publishing tool to create a set of interlinked webpages
  -  an environment for literate programming

  There is a website for Org which provides links to the newest
  version of Org, as well as additional information, frequently asked
  questions (FAQ), links to tutorials, etc. This page is located at
  http://orgmode.org.


[-- Attachment #4: test.html --]
[-- Type: text/html, Size: 34171 bytes --]

[-- Attachment #5: Type: text/plain, Size: 22 bytes --]



Jambunathan K.

-- 

^ permalink raw reply related	[flat|nested] 23+ messages in thread

end of thread, other threads:[~2011-05-02  6:00 UTC | newest]

Thread overview: 23+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-03-21  9:32 [PATCH][ANN] org-html/org-odt Rustom Mody
2011-03-21  9:51 ` Jambunathan K
  -- strict thread matches above, loose matches on Subject: below --
2011-03-20 18:32 Jambunathan K
2011-03-21  8:21 ` Bastien
2011-03-21  8:53   ` Christian Moe
2011-03-21  9:31     ` Jambunathan K
2011-03-21 11:06       ` Christian Moe
2011-03-21 13:31         ` Jambunathan K
2011-03-21 15:20           ` Christian Moe
2011-03-21 16:39             ` Jambunathan K
2011-03-21  9:40     ` Jambunathan K
2011-03-21  8:55   ` Jambunathan K
2011-03-21 10:03 ` Jambunathan K
2011-03-21 21:26 ` Christian Moe
2011-04-12  8:33   ` Jambunathan K
2011-04-12 14:47     ` Christian Moe
2011-04-25 12:47     ` Christian Moe
2011-04-26 16:09       ` Jambunathan K
2011-03-25 22:32 ` Sean O'Halpin
2011-03-26  4:57   ` Jambunathan K
2011-04-30  6:06 ` Jambunathan K
2011-04-30  6:54   ` Christian Moe
2011-05-01 12:52   ` Matt Lundin
2011-05-01 13:31     ` Matt Lundin
2011-05-02  6:00     ` Jambunathan K

Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs/org-mode.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).