summaryrefslogtreecommitdiff
path: root/external/libepubgen
diff options
context:
space:
mode:
authorMiklos Vajna <vmiklos@collabora.co.uk>2017-11-30 16:33:03 +0100
committerMiklos Vajna <vmiklos@collabora.co.uk>2017-12-01 09:17:01 +0100
commit7dcb4fef3b2383f4dd4d5d5c9ebbe8f19f8f4c8e (patch)
tree1f98cde1b37dc8fce39a571243435e4e9cbb6409 /external/libepubgen
parent553a35bed7a7ffb5bcda98987eb4af8b79bc031f (diff)
EPUB export: support image popup for images and text
Handle relative links on image / text as data for a popup. Pick the images up from <base directory>/<base name>/<relative url> as a start. Change-Id: I9b6183d554e3792aa71dfffc19a671a0e4c302cc Reviewed-on: https://gerrit.libreoffice.org/45601 Tested-by: Jenkins <ci@libreoffice.org> Reviewed-by: Miklos Vajna <vmiklos@collabora.co.uk>
Diffstat (limited to 'external/libepubgen')
-rw-r--r--external/libepubgen/libepubgen-epub3.patch.1301
1 files changed, 301 insertions, 0 deletions
diff --git a/external/libepubgen/libepubgen-epub3.patch.1 b/external/libepubgen/libepubgen-epub3.patch.1
index 28f9c3771708..e2948c43bd34 100644
--- a/external/libepubgen/libepubgen-epub3.patch.1
+++ b/external/libepubgen/libepubgen-epub3.patch.1
@@ -5053,3 +5053,304 @@ index 96e7623..6b4c7c2 100644
--
2.13.6
+From bc80bf98172e8e0f8c803dec0b8e74e233ac482e Mon Sep 17 00:00:00 2001
+From: Miklos Vajna <vmiklos@collabora.co.uk>
+Date: Fri, 24 Nov 2017 16:28:58 +0100
+Subject: [PATCH 1/2] EPUBHTMLGenerator: support image popup for images
+
+If the user of the lib uses the librevenge:mime-type and
+office:binary-data keys (instead of xlink:href) for a link around an
+image, then open that image in a popup (using the footnote markup).
+
+The usual assumption is that the footnote anchor is trivial (just a
+string) and the content is complex, but here the situation is the
+opposite: the anchor can be something complex, OTOH the footnote content
+is always a single inline image -- this requires the new
+closeAnchor mode when adding the footnote label.
+---
+ src/lib/EPUBHTMLGenerator.cpp | 79 ++++++++++++++++++++++++++++++--------
+ src/test/EPUBTextGeneratorTest.cpp | 34 ++++++++++++++++
+ 2 files changed, 96 insertions(+), 17 deletions(-)
+
+diff --git a/src/lib/EPUBHTMLGenerator.cpp b/src/lib/EPUBHTMLGenerator.cpp
+index 6b4c7c2..75b0866 100644
+--- a/src/lib/EPUBHTMLGenerator.cpp
++++ b/src/lib/EPUBHTMLGenerator.cpp
+@@ -222,7 +222,8 @@ struct TextZoneSink
+ //! destructor
+ ~TextZoneSink() { }
+ //! add a label called on main and a label in this ( delayed to allow openParagraph to be called )
+- void addLabel(EPUBXMLSink &output, const librevenge::RVNGString &number)
++ //! @param closeAnchor determintes if the anchor on the main sink should be closed or not.
++ void addLabel(EPUBXMLSink &output, const librevenge::RVNGString &number, bool closeAnchor)
+ {
+ // Unique label, e.g. 'F1' for the first footnote.
+ std::string lbl=label();
+@@ -244,9 +245,12 @@ struct TextZoneSink
+ aAttrs.insert("epub:type", "noteref");
+ aAttrs.insert("href", ("#data" + lbl).c_str());
+ output.openElement("a", aAttrs);
+- output.insertCharacters(uiLabel.c_str());
+- output.closeElement("a");
+- output.closeElement("sup");
++ if (closeAnchor)
++ {
++ output.insertCharacters(uiLabel.c_str());
++ output.closeElement("a");
++ output.closeElement("sup");
++ }
+ }
+ flush();
+ if (version == 30)
+@@ -259,13 +263,16 @@ struct TextZoneSink
+ RVNGPropertyList supAttrs;
+ if (version < 30)
+ supAttrs.insert("id", ("data" + lbl).c_str());
+- m_delayedLabel.openElement("sup", supAttrs);
+- RVNGPropertyList aAttrs;
+- aAttrs.insert("href", ("#called" + lbl).c_str());
+- m_delayedLabel.openElement("a", aAttrs);
+- m_delayedLabel.insertCharacters(uiLabel.c_str());
+- m_delayedLabel.closeElement("a");
+- m_delayedLabel.closeElement("sup");
++ if (closeAnchor)
++ {
++ m_delayedLabel.openElement("sup", supAttrs);
++ RVNGPropertyList aAttrs;
++ aAttrs.insert("href", ("#called" + lbl).c_str());
++ m_delayedLabel.openElement("a", aAttrs);
++ m_delayedLabel.insertCharacters(uiLabel.c_str());
++ m_delayedLabel.closeElement("a");
++ m_delayedLabel.closeElement("sup");
++ }
+ }
+ //! flush delayed label, ...
+ void flush()
+@@ -379,6 +386,7 @@ struct EPUBHTMLGeneratorImpl
+ , m_version(version)
+ , m_frameAnchorTypes()
+ , m_framePropertiesStack()
++ , m_linkPropertiesStack()
+ , m_stylesMethod(stylesMethod)
+ , m_actualSink()
+ , m_sinkStack()
+@@ -475,6 +483,8 @@ struct EPUBHTMLGeneratorImpl
+
+ std::stack<std::string> m_frameAnchorTypes;
+ std::stack<RVNGPropertyList> m_framePropertiesStack;
++ /// This is used for links which don't have a href.
++ std::stack<RVNGPropertyList> m_linkPropertiesStack;
+
+ EPUBStylesMethod m_stylesMethod;
+
+@@ -702,14 +712,29 @@ void EPUBHTMLGenerator::openLink(const RVNGPropertyList &propList)
+
+ attrs.insert("href", href.c_str());
+ }
+- m_impl->output(false).openElement("a", attrs);
++ const librevenge::RVNGProperty *binaryDataProp = propList["office:binary-data"];
++ const librevenge::RVNGProperty *mimeTypeProp = propList["librevenge:mime-type"];
++ if (binaryDataProp && mimeTypeProp)
++ {
++ // This is not a real link, but more an additional image on top of an
++ // existing one, map it to footnotes instead.
++ RVNGPropertyList linkProperties;
++ linkProperties.insert("office:binary-data", binaryDataProp->clone());
++ linkProperties.insert("librevenge:mime-type", mimeTypeProp->clone());
++ m_impl->m_linkPropertiesStack.push(linkProperties);
++ }
++ else
++ m_impl->output(false).openElement("a", attrs);
+ }
+
+ void EPUBHTMLGenerator::closeLink()
+ {
+ if (m_impl->m_ignore)
+ return;
+- m_impl->output().closeElement("a");
++ if (!m_impl->m_linkPropertiesStack.empty())
++ m_impl->m_linkPropertiesStack.pop();
++ else
++ m_impl->output().closeElement("a");
+ }
+
+ void EPUBHTMLGenerator::insertTab()
+@@ -820,7 +845,8 @@ void EPUBHTMLGenerator::openFootnote(const RVNGPropertyList &propList)
+ librevenge::RVNGString number;
+ if (const librevenge::RVNGProperty *numProp = propList["librevenge:number"])
+ number = numProp->getStr();
+- m_impl->getSink().addLabel(output, number);
++ bool closeAnchor = m_impl->m_linkPropertiesStack.empty();
++ m_impl->getSink().addLabel(output, number, closeAnchor);
+ }
+
+ void EPUBHTMLGenerator::closeFootnote()
+@@ -838,7 +864,7 @@ void EPUBHTMLGenerator::openEndnote(const RVNGPropertyList &)
+ return;
+ EPUBXMLSink &output = m_impl->output();
+ m_impl->push(EPUBHTMLTextZone::Z_EndNote);
+- m_impl->getSink().addLabel(output, librevenge::RVNGString());
++ m_impl->getSink().addLabel(output, librevenge::RVNGString(), true);
+ }
+
+ void EPUBHTMLGenerator::closeEndnote()
+@@ -854,7 +880,7 @@ void EPUBHTMLGenerator::openComment(const RVNGPropertyList & /*propList*/)
+ return;
+ EPUBXMLSink &output = m_impl->output();
+ m_impl->push(EPUBHTMLTextZone::Z_Comment);
+- m_impl->getSink().addLabel(output, librevenge::RVNGString());
++ m_impl->getSink().addLabel(output, librevenge::RVNGString(), true);
+ }
+
+ void EPUBHTMLGenerator::closeComment()
+@@ -1067,7 +1093,26 @@ void EPUBHTMLGenerator::insertBinaryObject(const RVNGPropertyList &propList)
+ attrs.insert("src", path.relativeTo(m_impl->m_path).str().c_str());
+ // FIXME: use alternative repr. if available
+ attrs.insert("alt", path.str().c_str());
+- m_impl->output().insertEmptyElement("img", attrs);
++ if (!m_impl->m_linkPropertiesStack.empty())
++ {
++ RVNGPropertyList &linkProperties = m_impl->m_linkPropertiesStack.top();
++ // Save the main sink, as m_impl->output() will point to the footnote sink.
++ libepubgen::EPUBXMLSink &main = m_impl->output();
++ openFootnote(RVNGPropertyList());
++ main.insertEmptyElement("img", attrs);
++ main.closeElement("a");
++ main.closeElement("sup");
++ const EPUBPath &linkPath = m_impl->m_imageManager.insert(
++ RVNGBinaryData(linkProperties["office:binary-data"]->getStr()),
++ linkProperties["librevenge:mime-type"]->getStr());
++ RVNGPropertyList linkAttrs;
++ linkAttrs.insert("src", linkPath.relativeTo(m_impl->m_path).str().c_str());
++ linkAttrs.insert("alt", linkPath.str().c_str());
++ m_impl->output().insertEmptyElement("img", linkAttrs);
++ closeFootnote();
++ }
++ else
++ m_impl->output().insertEmptyElement("img", attrs);
+
+ if (!wrapStyle.empty())
+ {
+--
+2.13.6
+
+
+From 6e094bbe9fd8c1784ef3c348d04e2add8b48fc67 Mon Sep 17 00:00:00 2001
+From: Miklos Vajna <vmiklos@collabora.co.uk>
+Date: Fri, 24 Nov 2017 17:18:53 +0100
+Subject: [PATCH 2/2] EPUBHTMLGenerator: support image popup for text
+
+And also make sure that the popup anchor is not superscript.
+---
+ src/lib/EPUBHTMLGenerator.cpp | 44 ++++++++++++++++++++++++++------------
+ src/lib/EPUBHTMLGenerator.h | 4 ++++
+ src/test/EPUBTextGeneratorTest.cpp | 31 ++++++++++++++++++++++++++-
+ 3 files changed, 64 insertions(+), 15 deletions(-)
+
+diff --git a/src/lib/EPUBHTMLGenerator.cpp b/src/lib/EPUBHTMLGenerator.cpp
+index 75b0866..5c6421c 100644
+--- a/src/lib/EPUBHTMLGenerator.cpp
++++ b/src/lib/EPUBHTMLGenerator.cpp
+@@ -239,7 +239,8 @@ struct TextZoneSink
+ {
+ RVNGPropertyList supAttrs;
+ supAttrs.insert("id", ("called" + lbl).c_str());
+- output.openElement("sup", supAttrs);
++ if (closeAnchor)
++ output.openElement("sup", supAttrs);
+ RVNGPropertyList aAttrs;
+ if (version == 30)
+ aAttrs.insert("epub:type", "noteref");
+@@ -769,7 +770,9 @@ void EPUBHTMLGenerator::insertText(const RVNGString &text)
+ {
+ if (m_impl->m_ignore)
+ return;
+- m_impl->output().insertCharacters(text);
++ EPUBXMLSink &sink = openPopup();
++ sink.insertCharacters(text);
++ closePopup(sink);
+ m_impl->m_hasText = true;
+ }
+
+@@ -1093,15 +1096,37 @@ void EPUBHTMLGenerator::insertBinaryObject(const RVNGPropertyList &propList)
+ attrs.insert("src", path.relativeTo(m_impl->m_path).str().c_str());
+ // FIXME: use alternative repr. if available
+ attrs.insert("alt", path.str().c_str());
++ EPUBXMLSink &sink = openPopup();
++ sink.insertEmptyElement("img", attrs);
++ closePopup(sink);
++
++ if (!wrapStyle.empty())
++ {
++ attrs.clear();
++ attrs.insert("style", wrapStyle);
++ m_impl->output().insertEmptyElement("br", attrs);
++ }
++}
++
++EPUBXMLSink &EPUBHTMLGenerator::openPopup()
++{
+ if (!m_impl->m_linkPropertiesStack.empty())
+ {
+- RVNGPropertyList &linkProperties = m_impl->m_linkPropertiesStack.top();
+ // Save the main sink, as m_impl->output() will point to the footnote sink.
+ libepubgen::EPUBXMLSink &main = m_impl->output();
+ openFootnote(RVNGPropertyList());
+- main.insertEmptyElement("img", attrs);
++ return main;
++ }
++ else
++ return m_impl->output();
++}
++
++void EPUBHTMLGenerator::closePopup(EPUBXMLSink &main)
++{
++ if (!m_impl->m_linkPropertiesStack.empty())
++ {
++ RVNGPropertyList &linkProperties = m_impl->m_linkPropertiesStack.top();
+ main.closeElement("a");
+- main.closeElement("sup");
+ const EPUBPath &linkPath = m_impl->m_imageManager.insert(
+ RVNGBinaryData(linkProperties["office:binary-data"]->getStr()),
+ linkProperties["librevenge:mime-type"]->getStr());
+@@ -1111,15 +1136,6 @@ void EPUBHTMLGenerator::insertBinaryObject(const RVNGPropertyList &propList)
+ m_impl->output().insertEmptyElement("img", linkAttrs);
+ closeFootnote();
+ }
+- else
+- m_impl->output().insertEmptyElement("img", attrs);
+-
+- if (!wrapStyle.empty())
+- {
+- attrs.clear();
+- attrs.insert("style", wrapStyle);
+- m_impl->output().insertEmptyElement("br", attrs);
+- }
+ }
+
+ void EPUBHTMLGenerator::insertEquation(const RVNGPropertyList & /* propList */) {}
+diff --git a/src/lib/EPUBHTMLGenerator.h b/src/lib/EPUBHTMLGenerator.h
+index 11f20cb..3699179 100644
+--- a/src/lib/EPUBHTMLGenerator.h
++++ b/src/lib/EPUBHTMLGenerator.h
+@@ -27,6 +27,7 @@ class EPUBSpanStyleManager;
+ class EPUBParagraphStyleManager;
+ class EPUBTableStyleManager;
+ class EPUBPath;
++class EPUBXMLSink;
+
+ class EPUBHTMLGenerator : public librevenge::RVNGTextInterface
+ {
+@@ -112,6 +113,9 @@ public:
+ void insertEquation(const librevenge::RVNGPropertyList &propList) override;
+
+ private:
++ EPUBXMLSink &openPopup();
++ void closePopup(EPUBXMLSink &main);
++
+ std::unique_ptr<EPUBHTMLGeneratorImpl> m_impl;
+
+ // Unimplemented to prevent compiler from creating crasher ones
+--
+2.13.6
+