瀏覽代碼

org-odt.el: Support for anchoring an image to a page

* etc/styles/OrgOdtStyles.xml(OrgPageImage)
(OrgPageImageCaptionFrame): New styles for anchoring an image
centrally on a page.

* lisp/org-odt.el (org-odt-entity-frame-styles): Accommodate new
frame styles: \"OrgPageImage\" and \"OrgPageImageCaptionFrame\".
(org-export-odt-format-image): Handle frame-related :anchor,
:style and :attributes options attached to images as shown
below:
		[[./image.png]]
(org-odt-merge-frame-params): New. Auxiliary routine to merge
the default frame params and user-specified frame params.
(org-odt-format-entity): Use the above
`org-odt-merge-frame-params'.

Jérémy Compostella <jeremy.compostella@gmail.com> writes:
  I need to add pictures that are anchored to the \"page\" and not
  to the \"paragraph\". This is very useful to get a \"floating
  picture\" on an entire page without text breaks.

He also adds:
  Sometimes, you want to add a picture but you don't want a page
  break. For example, you want to add a big illustration. To
  render correctly, the picture needs its own page but you don't
  want to break the page. In this case you need to anchor the
  picture to the \"page\".

http://lists.gnu.org/archive/html/emacs-orgmode/2011-11/msg00869.html
Jambunathan K 13 年之前
父節點
當前提交
2512637fce
共有 2 個文件被更改,包括 76 次插入30 次删除
  1. 12 0
      etc/styles/OrgOdtStyles.xml
  2. 64 30
      lisp/org-odt.el

+ 12 - 0
etc/styles/OrgOdtStyles.xml

@@ -391,6 +391,12 @@
    <style:graphic-properties text:anchor-type="paragraph" style:wrap="none" style:vertical-pos="top" style:vertical-rel="paragraph" style:horizontal-pos="center" style:horizontal-rel="paragraph"/>
    <style:graphic-properties text:anchor-type="paragraph" style:wrap="none" style:vertical-pos="top" style:vertical-rel="paragraph" style:horizontal-pos="center" style:horizontal-rel="paragraph"/>
   </style:style>
   </style:style>
 
 
+  <style:style style:name="OrgPageImage" style:family="graphic" style:parent-style-name="Graphics">
+   <style:graphic-properties text:anchor-type="page" fo:margin-top="0.21cm" fo:margin-bottom="0.21cm" style:vertical-pos="middle" style:vertical-rel="page" style:horizontal-pos="center" style:horizontal-rel="page" fo:background-color="transparent" style:background-transparency="100%" style:shadow="none" style:mirror="none" fo:clip="rect(0cm, 0cm, 0cm, 0cm)" draw:luminance="0%" draw:contrast="0%" draw:red="0%" draw:green="0%" draw:blue="0%" draw:gamma="100%" draw:color-inversion="false" draw:image-opacity="100%" draw:color-mode="standard">
+    <style:background-image/>
+   </style:graphic-properties>
+  </style:style>
+
   <!-- Captioned Images  -->
   <!-- Captioned Images  -->
   <style:style style:name="OrgCaptionedImage" style:family="graphic" style:parent-style-name="Graphics">
   <style:style style:name="OrgCaptionedImage" style:family="graphic" style:parent-style-name="Graphics">
    <style:graphic-properties style:rel-width="100%" text:anchor-type="paragraph" fo:margin-left="0cm" fo:margin-right="0cm" fo:margin-top="0cm" fo:margin-bottom="0cm" style:run-through="foreground" style:wrap="none" style:vertical-pos="from-top" style:vertical-rel="paragraph-content" style:horizontal-pos="from-left" style:horizontal-rel="paragraph-content" fo:padding="0cm" fo:border="none" style:shadow="none"/>
    <style:graphic-properties style:rel-width="100%" text:anchor-type="paragraph" fo:margin-left="0cm" fo:margin-right="0cm" fo:margin-top="0cm" fo:margin-bottom="0cm" style:run-through="foreground" style:wrap="none" style:vertical-pos="from-top" style:vertical-rel="paragraph-content" style:horizontal-pos="from-left" style:horizontal-rel="paragraph-content" fo:padding="0cm" fo:border="none" style:shadow="none"/>
@@ -400,6 +406,12 @@
    <style:graphic-properties text:anchor-type="paragraph" fo:margin-left="0cm" fo:margin-right="0cm" fo:margin-top="0cm" fo:margin-bottom="0cm" style:wrap="none" style:vertical-pos="top" style:vertical-rel="paragraph" style:horizontal-pos="center" style:horizontal-rel="paragraph" fo:padding="0cm" fo:border="none"/>
    <style:graphic-properties text:anchor-type="paragraph" fo:margin-left="0cm" fo:margin-right="0cm" fo:margin-top="0cm" fo:margin-bottom="0cm" style:wrap="none" style:vertical-pos="top" style:vertical-rel="paragraph" style:horizontal-pos="center" style:horizontal-rel="paragraph" fo:padding="0cm" fo:border="none"/>
   </style:style>
   </style:style>
 
 
+  <style:style style:name="OrgPageImageCaptionFrame" style:family="graphic" style:parent-style-name="Frame">
+   <style:graphic-properties text:anchor-type="paragraph" fo:margin-left="0cm" fo:margin-right="0cm" fo:margin-top="0.21cm" fo:margin-bottom="0.21cm" style:wrap="none" style:vertical-pos="middle" style:vertical-rel="page" style:horizontal-pos="center" style:horizontal-rel="page" fo:background-color="transparent" style:background-transparency="100%" fo:padding="0cm" fo:border="none" style:shadow="none">
+    <style:background-image/>
+   </style:graphic-properties>
+  </style:style>
+
   <!-- Inlined Images -->
   <!-- Inlined Images -->
   <style:style style:name="OrgInlineImage" style:family="graphic" style:parent-style-name="Graphics">
   <style:style style:name="OrgInlineImage" style:family="graphic" style:parent-style-name="Graphics">
    <style:graphic-properties text:anchor-type="as-char" style:vertical-pos="top" style:vertical-rel="baseline" style:horizontal-pos="center" style:horizontal-rel="paragraph"/>
    <style:graphic-properties text:anchor-type="as-char" style:vertical-pos="top" style:vertical-rel="baseline" style:horizontal-pos="center" style:horizontal-rel="paragraph"/>

+ 64 - 30
lisp/org-odt.el

@@ -1383,7 +1383,7 @@ value of `org-export-odt-fontify-srcblocks."
 	(org-lparse-insert-list-table
 	(org-lparse-insert-list-table
 	 `((,(org-odt-format-entity
 	 `((,(org-odt-format-entity
 	      (if caption "CaptionedDisplayFormula" "DisplayFormula")
 	      (if caption "CaptionedDisplayFormula" "DisplayFormula")
-	      href width height caption nil)
+	      href width height :caption caption :label nil)
 	    ,(if (not label) ""
 	    ,(if (not label) ""
 	       (org-odt-format-entity-caption label nil "__MathFormula__"))))
 	       (org-odt-format-entity-caption label nil "__MathFormula__"))))
 	 nil nil nil "OrgEquation" nil '((1 "c" 8) (2 "c" 1)))
 	 nil nil nil "OrgEquation" nil '((1 "c" 8) (2 "c" 1)))
@@ -1585,7 +1585,7 @@ ATTR is a string of other attributes of the a element."
    (expand-file-name
    (expand-file-name
     (concat (sha1 file-name) "." (file-name-extension file-name)) "Pictures")))
     (concat (sha1 file-name) "." (file-name-extension file-name)) "Pictures")))
 
 
-(defun org-export-odt-format-image (src href &optional embed-as)
+(defun org-export-odt-format-image (src href)
   "Create image tag with source and attributes."
   "Create image tag with source and attributes."
   (save-match-data
   (save-match-data
     (let* ((caption (org-find-text-property-in-string 'org-caption src))
     (let* ((caption (org-find-text-property-in-string 'org-caption src))
@@ -1593,14 +1593,27 @@ ATTR is a string of other attributes of the a element."
 	   (attr (org-find-text-property-in-string 'org-attributes src))
 	   (attr (org-find-text-property-in-string 'org-attributes src))
 	   (label (org-find-text-property-in-string 'org-label src))
 	   (label (org-find-text-property-in-string 'org-label src))
 	   (latex-frag (org-find-text-property-in-string
 	   (latex-frag (org-find-text-property-in-string
-			      'org-latex-src src))
+			'org-latex-src src))
 	   (category (and latex-frag "__DvipngImage__"))
 	   (category (and latex-frag "__DvipngImage__"))
-	   (embed-as (or embed-as
-			 (if latex-frag
-			     (or (org-find-text-property-in-string
-				  'org-latex-src-embed-type src) 'character)
-			   'paragraph)))
 	   (attr-plist (org-lparse-get-block-params attr))
 	   (attr-plist (org-lparse-get-block-params attr))
+	   (user-frame-anchor
+	    (car (assoc-string (plist-get attr-plist :anchor)
+			       (if (or caption label)
+				   '(("paragraph") ("page"))
+				 '(("character") ("paragraph") ("page"))) t)))
+	   (user-frame-style
+	    (and user-frame-anchor (plist-get attr-plist :style)))
+	   (user-frame-attrs
+	    (and user-frame-anchor (plist-get attr-plist :attributes)))
+	   (user-frame-params
+	    (list user-frame-style user-frame-attrs user-frame-anchor))
+	   (embed-as (cond
+		      (latex-frag
+		       (symbol-name
+			(or (org-find-text-property-in-string
+			     'org-latex-src-embed-type src) 'character)))
+		      (user-frame-anchor)
+		      (t "paragraph")))
 	   (size (org-odt-image-size-from-file
 	   (size (org-odt-image-size-from-file
 		  src (plist-get attr-plist :width)
 		  src (plist-get attr-plist :width)
 		  (plist-get attr-plist :height)
 		  (plist-get attr-plist :height)
@@ -1609,15 +1622,12 @@ ATTR is a string of other attributes of the a element."
       (when latex-frag
       (when latex-frag
 	(setq href (org-propertize href :title "LaTeX Fragment"
 	(setq href (org-propertize href :title "LaTeX Fragment"
 				   :description latex-frag)))
 				   :description latex-frag)))
-      (cond
-       ((not (or caption label))
-	(case embed-as
-	  (paragraph (org-odt-format-entity "DisplayImage" href width height))
-	  (character (org-odt-format-entity "InlineImage" href width height))
-	  (t (error "Unknown value for embed-as %S" embed-as))))
-       (t
+      (let ((frame-style-handle (concat (and (or caption label) "Captioned")
+					embed-as "Image")))
 	(org-odt-format-entity
 	(org-odt-format-entity
-	 "CaptionedDisplayImage" href width height caption label category))))))
+	 frame-style-handle href width height
+	 :caption caption :label label :category category
+	 :user-frame-params user-frame-params)))))
 
 
 (defun org-odt-format-object-description (title description)
 (defun org-odt-format-object-description (title description)
   (concat (and title (org-odt-format-tags
   (concat (and title (org-odt-format-tags
@@ -1663,31 +1673,55 @@ ATTR is a string of other attributes of the a element."
 		content) nil nil "OrgInlineTaskFrame" " style:rel-width=\"100%\"")))
 		content) nil nil "OrgInlineTaskFrame" " style:rel-width=\"100%\"")))
 
 
 (defvar org-odt-entity-frame-styles
 (defvar org-odt-entity-frame-styles
-  '(("InlineImage" "__Figure__" ("OrgInlineImage" nil "as-char"))
-    ("DisplayImage" "__Figure__" ("OrgDisplayImage" nil "paragraph"))
-    ("CaptionedDisplayImage" "__Figure__"
+  '(("CharacterImage" "__Figure__" ("OrgInlineImage" nil "as-char"))
+    ("ParagraphImage" "__Figure__" ("OrgDisplayImage" nil "paragraph"))
+    ("PageImage" "__Figure__" ("OrgPageImage" nil "page"))
+    ("CaptionedParagraphImage" "__Figure__"
      ("OrgCaptionedImage"
      ("OrgCaptionedImage"
       " style:rel-width=\"100%\" style:rel-height=\"scale\"" "paragraph")
       " style:rel-width=\"100%\" style:rel-height=\"scale\"" "paragraph")
-     ("OrgImageCaptionFrame"))
+     ("OrgImageCaptionFrame" nil "paragraph"))
+    ("CaptionedPageImage" "__Figure__"
+     ("OrgCaptionedImage"
+      " style:rel-width=\"100%\" style:rel-height=\"scale\"" "paragraph")
+     ("OrgPageImageCaptionFrame" nil "page"))
     ("InlineFormula" "__MathFormula__" ("OrgInlineFormula" nil "as-char"))
     ("InlineFormula" "__MathFormula__" ("OrgInlineFormula" nil "as-char"))
     ("DisplayFormula" "__MathFormula__" ("OrgDisplayFormula" nil "as-char"))
     ("DisplayFormula" "__MathFormula__" ("OrgDisplayFormula" nil "as-char"))
     ("CaptionedDisplayFormula" "__MathFormula__"
     ("CaptionedDisplayFormula" "__MathFormula__"
      ("OrgCaptionedFormula" nil "paragraph")
      ("OrgCaptionedFormula" nil "paragraph")
      ("OrgFormulaCaptionFrame" nil "as-char"))))
      ("OrgFormulaCaptionFrame" nil "as-char"))))
 
 
-(defun org-odt-format-entity (entity href width height
-				     &optional caption label category)
-  (let* ((entity-style (assoc entity org-odt-entity-frame-styles))
-	 (entity-frame (apply 'org-odt-format-frame
-			      href width height (nth 2 entity-style))))
-    (if (not (or caption label)) entity-frame
+(defun org-odt-merge-frame-params(default-frame-params user-frame-params)
+  (if (not user-frame-params) default-frame-params
+    (assert (= (length default-frame-params) 3))
+    (assert (= (length user-frame-params) 3))
+    (loop for user-frame-param in user-frame-params
+	  for default-frame-param in default-frame-params
+	  collect (or user-frame-param default-frame-param))))
+
+(defun* org-odt-format-entity (entity href width height
+				      &key caption label category
+				      user-frame-params)
+  (let* ((entity-style (assoc-string entity org-odt-entity-frame-styles t))
+	 default-frame-params frame-params)
+    (cond
+     ((not (or caption label))
+      (setq default-frame-params (nth 2 entity-style))
+      (setq frame-params (org-odt-merge-frame-params
+			  default-frame-params user-frame-params))
+      (apply 'org-odt-format-frame href width height frame-params))
+     (t
+      (setq default-frame-params (nth 3 entity-style))
+      (setq frame-params (org-odt-merge-frame-params
+			  default-frame-params user-frame-params))
       (apply 'org-odt-format-textbox
       (apply 'org-odt-format-textbox
 	     (org-odt-format-stylized-paragraph
 	     (org-odt-format-stylized-paragraph
 	      'illustration
 	      'illustration
-	      (concat entity-frame
-		      (org-odt-format-entity-caption
-		       label caption (or category (nth 1 entity-style)))))
-	     width height (nth 3 entity-style)))))
+	      (concat
+	       (apply 'org-odt-format-frame href width height
+		      (nth 2 entity-style))
+	       (org-odt-format-entity-caption
+		label caption (or category (nth 1 entity-style)))))
+	     width height frame-params)))))
 
 
 (defvar org-odt-embedded-images-count 0)
 (defvar org-odt-embedded-images-count 0)
 (defun org-odt-copy-image-file (path)
 (defun org-odt-copy-image-file (path)