From f06809355527394f3c32c0e46e6f9cb48786b668 Mon Sep 17 00:00:00 2001 From: MarLinn Date: Thu, 23 Jul 2015 09:06:14 +0200 Subject: [PATCH] Added odt reader Fully implemented features: * Paragraphs * Headers * Basic styling * Unordered lists * Ordered lists * External Links * Internal Links * Footnotes, Endnotes * Blockquotes Partly implemented features: * Citations Very basic, but pandoc can't do much more * Tables No headers, no sizing, limited styling --- pandoc.cabal | 19 +- pandoc.hs | 4 +- src/Text/Pandoc.hs | 5 +- src/Text/Pandoc/Readers/Odt.hs | 86 ++ src/Text/Pandoc/Readers/Odt/Arrows/State.hs | 253 ++++ src/Text/Pandoc/Readers/Odt/Arrows/Utils.hs | 497 ++++++++ src/Text/Pandoc/Readers/Odt/Base.hs | 43 + src/Text/Pandoc/Readers/Odt/ContentReader.hs | 790 ++++++++++++ .../Pandoc/Readers/Odt/Generic/Fallible.hs | 260 ++++ .../Pandoc/Readers/Odt/Generic/Namespaces.hs | 62 + src/Text/Pandoc/Readers/Odt/Generic/SetMap.hs | 48 + src/Text/Pandoc/Readers/Odt/Generic/Utils.hs | 171 +++ .../Readers/Odt/Generic/XMLConverter.hs | 1064 +++++++++++++++++ src/Text/Pandoc/Readers/Odt/Namespaces.hs | 110 ++ src/Text/Pandoc/Readers/Odt/StyleReader.hs | 737 ++++++++++++ src/Text/Pandoc/Shared.hs | 12 +- tests/Tests/Readers/Odt.hs | 165 +++ tests/odt/markdown/bold.md | 1 + tests/odt/markdown/citation.md | 1 + tests/odt/markdown/endnote.md | 3 + tests/odt/markdown/externalLink.md | 1 + tests/odt/markdown/footnote.md | 3 + tests/odt/markdown/headers.md | 9 + tests/odt/markdown/horizontalRule.md | 1 + tests/odt/markdown/image.md | 1 + tests/odt/markdown/imageIndex.md | 6 + tests/odt/markdown/imageWithCaption.md | 1 + tests/odt/markdown/italic.md | 1 + tests/odt/markdown/listBlocks.md | 6 + tests/odt/markdown/paragraph.md | 5 + tests/odt/markdown/strikeout.md | 1 + tests/odt/markdown/trackedChanges.md | 1 + tests/odt/markdown/underlined.md | 1 + tests/odt/native/blockquote.native | 1 + tests/odt/native/orderedListMixed.native | 1 + tests/odt/native/orderedListRoman.native | 1 + tests/odt/native/orderedListSimple.native | 1 + tests/odt/native/referenceToChapter.native | 1 + tests/odt/native/referenceToListItem.native | 1 + tests/odt/native/referenceToText.native | 1 + tests/odt/native/simpleTable.native | 1 + tests/odt/native/unicode.native | 1 + tests/odt/native/unorderedList.native | 1 + tests/odt/odt/blockquote.odt | Bin 0 -> 8594 bytes tests/odt/odt/bold.odt | Bin 0 -> 10377 bytes tests/odt/odt/citation.odt | Bin 0 -> 10842 bytes tests/odt/odt/endnote.odt | Bin 0 -> 10950 bytes tests/odt/odt/expression.odt | Bin 0 -> 10916 bytes tests/odt/odt/expressionUnevaluated.odt | Bin 0 -> 10829 bytes tests/odt/odt/externalLink.odt | Bin 0 -> 10735 bytes tests/odt/odt/footnote.odt | Bin 0 -> 10843 bytes tests/odt/odt/formula.odt | Bin 0 -> 14252 bytes tests/odt/odt/headers.odt | Bin 0 -> 10515 bytes tests/odt/odt/hiddenTextByStyle.odt | Bin 0 -> 10798 bytes tests/odt/odt/hiddenTextByVariable.odt | Bin 0 -> 10788 bytes tests/odt/odt/horizontalRule.odt | Bin 0 -> 10130 bytes tests/odt/odt/image.odt | Bin 0 -> 33360 bytes tests/odt/odt/imageIndex.odt | Bin 0 -> 34417 bytes tests/odt/odt/imageWithCaption.odt | Bin 0 -> 33811 bytes tests/odt/odt/italic.odt | Bin 0 -> 10426 bytes tests/odt/odt/listBlocks.odt | Bin 0 -> 10565 bytes tests/odt/odt/orderedListMixed.odt | Bin 0 -> 10580 bytes tests/odt/odt/orderedListRoman.odt | Bin 0 -> 10622 bytes tests/odt/odt/orderedListSimple.odt | Bin 0 -> 10570 bytes tests/odt/odt/paragraph.odt | Bin 0 -> 8538 bytes tests/odt/odt/referenceAllInOne.odt | Bin 0 -> 10878 bytes tests/odt/odt/referenceToChapter.odt | Bin 0 -> 10487 bytes tests/odt/odt/referenceToListItem.odt | Bin 0 -> 10855 bytes tests/odt/odt/referenceToText.odt | Bin 0 -> 10179 bytes tests/odt/odt/simpleTable.odt | Bin 0 -> 10705 bytes tests/odt/odt/strikeout.odt | Bin 0 -> 10582 bytes tests/odt/odt/table.odt | Bin 0 -> 10763 bytes tests/odt/odt/tableWithCaption.odt | Bin 0 -> 10623 bytes tests/odt/odt/trackedChanges.odt | Bin 0 -> 11135 bytes tests/odt/odt/underlined.odt | Bin 0 -> 10513 bytes tests/odt/odt/unicode.odt | Bin 0 -> 11787 bytes tests/odt/odt/unorderedList.odt | Bin 0 -> 9505 bytes tests/odt/odt/variable.odt | Bin 0 -> 10851 bytes tests/test-pandoc.hs | 2 + 79 files changed, 4368 insertions(+), 12 deletions(-) create mode 100644 src/Text/Pandoc/Readers/Odt.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Arrows/State.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Arrows/Utils.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Base.hs create mode 100644 src/Text/Pandoc/Readers/Odt/ContentReader.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Generic/Fallible.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Generic/Namespaces.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Generic/SetMap.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Generic/Utils.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Generic/XMLConverter.hs create mode 100644 src/Text/Pandoc/Readers/Odt/Namespaces.hs create mode 100644 src/Text/Pandoc/Readers/Odt/StyleReader.hs create mode 100644 tests/Tests/Readers/Odt.hs create mode 100644 tests/odt/markdown/bold.md create mode 100644 tests/odt/markdown/citation.md create mode 100644 tests/odt/markdown/endnote.md create mode 100644 tests/odt/markdown/externalLink.md create mode 100644 tests/odt/markdown/footnote.md create mode 100644 tests/odt/markdown/headers.md create mode 100644 tests/odt/markdown/horizontalRule.md create mode 100644 tests/odt/markdown/image.md create mode 100644 tests/odt/markdown/imageIndex.md create mode 100644 tests/odt/markdown/imageWithCaption.md create mode 100644 tests/odt/markdown/italic.md create mode 100644 tests/odt/markdown/listBlocks.md create mode 100644 tests/odt/markdown/paragraph.md create mode 100644 tests/odt/markdown/strikeout.md create mode 100644 tests/odt/markdown/trackedChanges.md create mode 100644 tests/odt/markdown/underlined.md create mode 100644 tests/odt/native/blockquote.native create mode 100644 tests/odt/native/orderedListMixed.native create mode 100644 tests/odt/native/orderedListRoman.native create mode 100644 tests/odt/native/orderedListSimple.native create mode 100644 tests/odt/native/referenceToChapter.native create mode 100644 tests/odt/native/referenceToListItem.native create mode 100644 tests/odt/native/referenceToText.native create mode 100644 tests/odt/native/simpleTable.native create mode 100644 tests/odt/native/unicode.native create mode 100644 tests/odt/native/unorderedList.native create mode 100644 tests/odt/odt/blockquote.odt create mode 100644 tests/odt/odt/bold.odt create mode 100644 tests/odt/odt/citation.odt create mode 100644 tests/odt/odt/endnote.odt create mode 100644 tests/odt/odt/expression.odt create mode 100644 tests/odt/odt/expressionUnevaluated.odt create mode 100644 tests/odt/odt/externalLink.odt create mode 100644 tests/odt/odt/footnote.odt create mode 100644 tests/odt/odt/formula.odt create mode 100644 tests/odt/odt/headers.odt create mode 100644 tests/odt/odt/hiddenTextByStyle.odt create mode 100644 tests/odt/odt/hiddenTextByVariable.odt create mode 100644 tests/odt/odt/horizontalRule.odt create mode 100644 tests/odt/odt/image.odt create mode 100644 tests/odt/odt/imageIndex.odt create mode 100644 tests/odt/odt/imageWithCaption.odt create mode 100644 tests/odt/odt/italic.odt create mode 100644 tests/odt/odt/listBlocks.odt create mode 100644 tests/odt/odt/orderedListMixed.odt create mode 100644 tests/odt/odt/orderedListRoman.odt create mode 100644 tests/odt/odt/orderedListSimple.odt create mode 100644 tests/odt/odt/paragraph.odt create mode 100644 tests/odt/odt/referenceAllInOne.odt create mode 100644 tests/odt/odt/referenceToChapter.odt create mode 100644 tests/odt/odt/referenceToListItem.odt create mode 100644 tests/odt/odt/referenceToText.odt create mode 100644 tests/odt/odt/simpleTable.odt create mode 100644 tests/odt/odt/strikeout.odt create mode 100644 tests/odt/odt/table.odt create mode 100644 tests/odt/odt/tableWithCaption.odt create mode 100644 tests/odt/odt/trackedChanges.odt create mode 100644 tests/odt/odt/underlined.odt create mode 100644 tests/odt/odt/unicode.odt create mode 100644 tests/odt/odt/unorderedList.odt create mode 100644 tests/odt/odt/variable.odt diff --git a/pandoc.cabal b/pandoc.cabal index 3001756a4..1924e568d 100644 --- a/pandoc.cabal +++ b/pandoc.cabal @@ -210,7 +210,9 @@ Extra-Source-Files: tests/epub/*.native tests/txt2tags.t2t tests/twiki-reader.twiki - + tests/odt/odt/*.odt + tests/odt/markdown/*.md + tests/odt/native/*.native Source-repository head type: git location: git://github.com/jgm/pandoc.git @@ -327,6 +329,7 @@ Library Text.Pandoc.Readers.TWiki, Text.Pandoc.Readers.Txt2Tags, Text.Pandoc.Readers.Docx, + Text.Pandoc.Readers.Odt, Text.Pandoc.Readers.EPUB, Text.Pandoc.Writers.Native, Text.Pandoc.Writers.Docbook, @@ -364,7 +367,18 @@ Library Text.Pandoc.Readers.Docx.Parse, Text.Pandoc.Readers.Docx.Fonts, Text.Pandoc.Readers.Docx.Util, - Text.Pandoc.Readers.Docx.StyleMap + Text.Pandoc.Readers.Docx.StyleMap, + Text.Pandoc.Readers.Odt.Base, + Text.Pandoc.Readers.Odt.Namespaces, + Text.Pandoc.Readers.Odt.StyleReader, + Text.Pandoc.Readers.Odt.ContentReader, + Text.Pandoc.Readers.Odt.Generic.Fallible, + Text.Pandoc.Readers.Odt.Generic.SetMap, + Text.Pandoc.Readers.Odt.Generic.Utils, + Text.Pandoc.Readers.Odt.Generic.Namespaces, + Text.Pandoc.Readers.Odt.Generic.XMLConverter, + Text.Pandoc.Readers.Odt.Arrows.State, + Text.Pandoc.Readers.Odt.Arrows.Utils, Text.Pandoc.Writers.Shared, Text.Pandoc.Asciify, Text.Pandoc.MIME, @@ -459,6 +473,7 @@ Test-Suite test-pandoc Tests.Readers.Org Tests.Readers.RST Tests.Readers.Docx + Tests.Readers.Odt Tests.Readers.Txt2Tags Tests.Readers.EPUB Tests.Writers.Native diff --git a/pandoc.hs b/pandoc.hs index 5d201ce36..fb9b9abbf 100644 --- a/pandoc.hs +++ b/pandoc.hs @@ -954,7 +954,7 @@ defaultReaderName fallback (x:xs) = ".docx" -> "docx" ".t2t" -> "t2t" ".epub" -> "epub" - ".odt" -> "odt" -- so we get an "unknown reader" error + ".odt" -> "odt" ".pdf" -> "pdf" -- so we get an "unknown reader" error ".doc" -> "doc" -- so we get an "unknown reader" error _ -> defaultReaderName fallback xs @@ -1180,8 +1180,6 @@ main = do Right r -> return r Left e -> err 7 e' where e' = case readerName' of - "odt" -> e ++ - "\nPandoc can convert to ODT, but not from ODT.\nTry using LibreOffice to export as HTML, and convert that with pandoc." "pdf" -> e ++ "\nPandoc can convert to PDF, but not from PDF." "doc" -> e ++ diff --git a/src/Text/Pandoc.hs b/src/Text/Pandoc.hs index 63da88c2e..a4d963221 100644 --- a/src/Text/Pandoc.hs +++ b/src/Text/Pandoc.hs @@ -67,6 +67,7 @@ module Text.Pandoc , Reader (..) , mkStringReader , readDocx + , readOdt , readMarkdown , readCommonMark , readMediaWiki @@ -85,7 +86,7 @@ module Text.Pandoc , readTxt2TagsNoMacros , readEPUB -- * Writers: converting /from/ Pandoc format - , Writer (..) + , Writer (..) , writeNative , writeJSON , writeMarkdown @@ -141,6 +142,7 @@ import Text.Pandoc.Readers.Native import Text.Pandoc.Readers.Haddock import Text.Pandoc.Readers.TWiki import Text.Pandoc.Readers.Docx +import Text.Pandoc.Readers.Odt import Text.Pandoc.Readers.Txt2Tags import Text.Pandoc.Readers.EPUB import Text.Pandoc.Writers.Native @@ -247,6 +249,7 @@ readers = [ ("native" , StringReader $ \_ s -> return $ readNative s) ,("haddock" , mkStringReader readHaddock) ,("twiki" , mkStringReader readTWiki) ,("docx" , mkBSReader readDocx) + ,("odt" , mkBSReader readOdt) ,("t2t" , mkStringReader readTxt2TagsNoMacros) ,("epub" , mkBSReader readEPUB) ] diff --git a/src/Text/Pandoc/Readers/Odt.hs b/src/Text/Pandoc/Readers/Odt.hs new file mode 100644 index 000000000..1c8ec51bc --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt.hs @@ -0,0 +1,86 @@ +{-# LANGUAGE PatternGuards #-} + +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Reader.Odt + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +Entry point to the odt reader. +-} + +module Text.Pandoc.Readers.Odt ( readOdt ) where + +import Codec.Archive.Zip +import qualified Text.XML.Light as XML + +import qualified Data.ByteString.Lazy as B +import Data.Monoid ( mempty ) + +import Text.Pandoc.Definition +import Text.Pandoc.Error +import Text.Pandoc.Options +import Text.Pandoc.MediaBag +import qualified Text.Pandoc.UTF8 as UTF8 + +import Text.Pandoc.Readers.Odt.ContentReader +import Text.Pandoc.Readers.Odt.StyleReader + +import Text.Pandoc.Readers.Odt.Generic.XMLConverter +import Text.Pandoc.Readers.Odt.Generic.Fallible + +-- +readOdt :: ReaderOptions + -> B.ByteString + -> Either PandocError (Pandoc, MediaBag) +readOdt _ bytes = case bytesToOdt bytes of + Right pandoc -> Right (pandoc , mempty) + Left err -> Left err + +-- +bytesToOdt :: B.ByteString -> Either PandocError Pandoc +bytesToOdt bytes = archiveToOdt $ toArchive bytes + +-- +archiveToOdt :: Archive -> Either PandocError Pandoc +archiveToOdt archive + | Just contentEntry <- findEntryByPath "content.xml" archive + , Just stylesEntry <- findEntryByPath "styles.xml" archive + , Just contentElem <- entryToXmlElem contentEntry + , Just stylesElem <- entryToXmlElem stylesEntry + , Right styles <- chooseMax (readStylesAt stylesElem ) + (readStylesAt contentElem) + , startState <- readerState styles + , Right pandoc <- runConverter' read_body + startState + contentElem + = Right pandoc + + | otherwise + -- Not very detailed, but I don't think more information would be helpful + = Left $ ParseFailure "Couldn't parse odt file." + +-- +entryToXmlElem :: Entry -> Maybe XML.Element +entryToXmlElem = XML.parseXMLDoc . UTF8.toStringLazy . fromEntry diff --git a/src/Text/Pandoc/Readers/Odt/Arrows/State.hs b/src/Text/Pandoc/Readers/Odt/Arrows/State.hs new file mode 100644 index 000000000..310ca028e --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Arrows/State.hs @@ -0,0 +1,253 @@ +{-# LANGUAGE Arrows #-} +{-# LANGUAGE TupleSections #-} +{-# LANGUAGE FlexibleInstances #-} +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.Arrows.State + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +An arrow that transports a state. It is in essence a more powerful version of +the standard state monad. As it is such a simple extension, there are +other version out there that do exactly the same. +The implementation is duplicated, though, to add some useful features. +Most of these might be implemented without access to innards, but it's much +faster and easier to implement this way. +-} + +module Text.Pandoc.Readers.Odt.Arrows.State where + +import Prelude hiding ( foldr, foldl ) + +import qualified Control.Category as Cat +import Control.Arrow +import Control.Monad + +import Data.Monoid +import Data.Foldable + +import Text.Pandoc.Readers.Odt.Arrows.Utils +import Text.Pandoc.Readers.Odt.Generic.Fallible + + +newtype ArrowState state a b = ArrowState + { runArrowState :: (state, a) -> (state, b) } + +-- | Constructor +withState :: (state -> a -> (state, b)) -> ArrowState state a b +withState = ArrowState . uncurry + +-- | Constructor +withState' :: ((state, a) -> (state, b)) -> ArrowState state a b +withState' = ArrowState + +-- | Constructor +modifyState :: (state -> state ) -> ArrowState state a a +modifyState = ArrowState . first + +-- | Constructor +ignoringState :: ( a -> b ) -> ArrowState state a b +ignoringState = ArrowState . second + +-- | Constructor +fromState :: (state -> (state, b)) -> ArrowState state a b +fromState = ArrowState . (.fst) + +-- | Constructor +extractFromState :: (state -> b ) -> ArrowState state x b +extractFromState f = ArrowState $ \(state,_) -> (state, f state) + +-- | Constructor +withUnchangedState :: (state -> a -> b ) -> ArrowState state a b +withUnchangedState f = ArrowState $ \(state,a) -> (state, f state a) + +-- | Constructor +tryModifyState :: (state -> Either f state) + -> ArrowState state a (Either f a) +tryModifyState f = ArrowState $ \(state,a) + -> (state,).Left ||| (,Right a) $ f state + +instance Cat.Category (ArrowState s) where + id = ArrowState id + arrow2 . arrow1 = ArrowState $ (runArrowState arrow2).(runArrowState arrow1) + +instance Arrow (ArrowState state) where + arr = ignoringState + first a = ArrowState $ \(s,(aF,aS)) + -> second (,aS) $ runArrowState a (s,aF) + second a = ArrowState $ \(s,(aF,aS)) + -> second (aF,) $ runArrowState a (s,aS) + +instance ArrowChoice (ArrowState state) where + left a = ArrowState $ \(s,e) -> case e of + Left l -> second Left $ runArrowState a (s,l) + Right r -> (s, Right r) + right a = ArrowState $ \(s,e) -> case e of + Left l -> (s, Left l) + Right r -> second Right $ runArrowState a (s,r) + +instance ArrowLoop (ArrowState state) where + loop a = ArrowState $ \(s, x) + -> let (s', (x', _d)) = runArrowState a (s, (x, _d)) + in (s', x') + +instance ArrowApply (ArrowState state) where + app = ArrowState $ \(s, (f,b)) -> runArrowState f (s,b) + + +-- | Embedding of a state arrow in a state arrow with a different state type. +switchState :: (s -> s') -> (s' -> s) -> ArrowState s' x y -> ArrowState s x y +switchState there back a = ArrowState $ first there + >>> runArrowState a + >>> first back + +-- | Lift a state arrow to modify the state of an arrow +-- with a different state type. +liftToState :: (s -> s') -> ArrowState s' s s -> ArrowState s x x +liftToState unlift a = modifyState $ unlift &&& id + >>> runArrowState a + >>> snd + +-- | Switches the type of the state temporarily. +-- Drops the intermediate result state, behaving like the identity arrow, +-- save for side effects in the state. +withSubState :: ArrowState s x s2 -> ArrowState s2 s s -> ArrowState s x x +withSubState unlift a = keepingTheValue (withSubState unlift a) >>^ fst + +-- | Switches the type of the state temporarily. +-- Returns the resulting sub-state. +withSubState' :: ArrowState s x s' -> ArrowState s' s s -> ArrowState s x s' +withSubState' unlift a = ArrowState $ runArrowState unlift + >>> switch + >>> runArrowState a + >>> switch + where switch (x,y) = (y,x) + +-- | Switches the type of the state temporarily. +-- Drops the intermediate result state, behaving like a fallible +-- identity arrow, save for side effects in the state. +withSubStateF :: ArrowState s x (Either f s') + -> ArrowState s' s (Either f s ) + -> ArrowState s x (Either f x ) +withSubStateF unlift a = keepingTheValue (withSubStateF' unlift a) + >>^ spreadChoice + >>^ fmap fst + +-- | Switches the type of the state temporarily. +-- Returns the resulting sub-state. +withSubStateF' :: ArrowState s x (Either f s') + -> ArrowState s' s (Either f s ) + -> ArrowState s x (Either f s') +withSubStateF' unlift a = ArrowState go + where go p@(s,_) = tryRunning unlift + ( tryRunning a (second Right) ) + p + where tryRunning a' b v = case runArrowState a' v of + (_ , Left f) -> (s, Left f) + (x , Right y) -> b (y,x) + +-- | Fold a state arrow through something 'Foldable'. Collect the results +-- in a 'Monoid'. +-- Intermediate form of a fold between one with "only" a 'Monoid' +-- and one with any function. +foldS :: (Foldable f, Monoid m) => ArrowState s x m -> ArrowState s (f x) m +foldS a = ArrowState $ \(s,f) -> foldr a' (s,mempty) f + where a' x (s',m) = second (m <>) $ runArrowState a (s',x) + +-- | Fold a state arrow through something 'Foldable'. Collect the results +-- in a 'Monoid'. +-- Intermediate form of a fold between one with "only" a 'Monoid' +-- and one with any function. +foldSL :: (Foldable f, Monoid m) => ArrowState s x m -> ArrowState s (f x) m +foldSL a = ArrowState $ \(s,f) -> foldl a' (s,mempty) f + where a' (s',m) x = second (m <>) $ runArrowState a (s',x) + +-- | Fold a fallible state arrow through something 'Foldable'. Collect the +-- results in a 'Monoid'. +-- Intermediate form of a fold between one with "only" a 'Monoid' +-- and one with any function. +-- If the iteration fails, the state will be reset to the initial one. +foldS' :: (Foldable f, Monoid m) + => ArrowState s x (Either e m) + -> ArrowState s (f x) (Either e m) +foldS' a = ArrowState $ \(s,f) -> foldr (a' s) (s,Right mempty) f + where a' s x (s',Right m) = case runArrowState a (s',x) of + (s'',Right m') -> (s'', Right (m <> m')) + (_ ,Left e ) -> (s , Left e) + a' _ _ e = e + +-- | Fold a fallible state arrow through something 'Foldable'. Collect the +-- results in a 'Monoid'. +-- Intermediate form of a fold between one with "only" a 'Monoid' +-- and one with any function. +-- If the iteration fails, the state will be reset to the initial one. +foldSL' :: (Foldable f, Monoid m) + => ArrowState s x (Either e m) + -> ArrowState s (f x) (Either e m) +foldSL' a = ArrowState $ \(s,f) -> foldl (a' s) (s,Right mempty) f + where a' s (s',Right m) x = case runArrowState a (s',x) of + (s'',Right m') -> (s'', Right (m <> m')) + (_ ,Left e ) -> (s , Left e) + a' _ e _ = e + +-- | Fold a state arrow through something 'Foldable'. Collect the results in a +-- 'MonadPlus'. +iterateS :: (Foldable f, MonadPlus m) + => ArrowState s x y + -> ArrowState s (f x) (m y) +iterateS a = ArrowState $ \(s,f) -> foldr a' (s,mzero) f + where a' x (s',m) = second ((mplus m).return) $ runArrowState a (s',x) + +-- | Fold a state arrow through something 'Foldable'. Collect the results in a +-- 'MonadPlus'. +iterateSL :: (Foldable f, MonadPlus m) + => ArrowState s x y + -> ArrowState s (f x) (m y) +iterateSL a = ArrowState $ \(s,f) -> foldl a' (s,mzero) f + where a' (s',m) x = second ((mplus m).return) $ runArrowState a (s',x) + + +-- | Fold a fallible state arrow through something 'Foldable'. +-- Collect the results in a 'MonadPlus'. +-- If the iteration fails, the state will be reset to the initial one. +iterateS' :: (Foldable f, MonadPlus m) + => ArrowState s x (Either e y ) + -> ArrowState s (f x) (Either e (m y)) +iterateS' a = ArrowState $ \(s,f) -> foldr (a' s) (s,Right mzero) f + where a' s x (s',Right m) = case runArrowState a (s',x) of + (s'',Right m') -> (s'',Right $ mplus m $ return m') + (_ ,Left e ) -> (s ,Left e ) + a' _ _ e = e + +-- | Fold a fallible state arrow through something 'Foldable'. +-- Collect the results in a 'MonadPlus'. +-- If the iteration fails, the state will be reset to the initial one. +iterateSL' :: (Foldable f, MonadPlus m) + => ArrowState s x (Either e y ) + -> ArrowState s (f x) (Either e (m y)) +iterateSL' a = ArrowState $ \(s,f) -> foldl (a' s) (s,Right mzero) f + where a' s (s',Right m) x = case runArrowState a (s',x) of + (s'',Right m') -> (s'',Right $ mplus m $ return m') + (_ ,Left e ) -> (s ,Left e ) + a' _ e _ = e diff --git a/src/Text/Pandoc/Readers/Odt/Arrows/Utils.hs b/src/Text/Pandoc/Readers/Odt/Arrows/Utils.hs new file mode 100644 index 000000000..9710973b3 --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Arrows/Utils.hs @@ -0,0 +1,497 @@ +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.Arrows.Utils + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +Utility functions for Arrows (Kleisli monads). + +Some general notes on notation: + +* "^" is meant to stand for a pure function that is lifted into an arrow +based on its usage for that purpose in "Control.Arrow". +* "?" is meant to stand for the usage of a 'FallibleArrow' or a pure function +with an equivalent return value. +* "_" stands for the dropping of a value. +-} + +-- We export everything +module Text.Pandoc.Readers.Odt.Arrows.Utils where + +import Control.Arrow +import Control.Monad ( join, MonadPlus(..) ) + +import Data.Monoid +import qualified Data.Foldable as F + +import Text.Pandoc.Readers.Odt.Generic.Fallible +import Text.Pandoc.Readers.Odt.Generic.Utils + + +and2 :: (Arrow a) => a b c -> a b c' -> a b (c,c') +and2 = (&&&) + +and3 :: (Arrow a) + => a b c0->a b c1->a b c2 + -> a b (c0,c1,c2 ) +and4 :: (Arrow a) + => a b c0->a b c1->a b c2->a b c3 + -> a b (c0,c1,c2,c3 ) +and5 :: (Arrow a) + => a b c0->a b c1->a b c2->a b c3->a b c4 + -> a b (c0,c1,c2,c3,c4 ) +and6 :: (Arrow a) + => a b c0->a b c1->a b c2->a b c3->a b c4->a b c5 + -> a b (c0,c1,c2,c3,c4,c5 ) +and7 :: (Arrow a) + => a b c0->a b c1->a b c2->a b c3->a b c4->a b c5->a b c6 + -> a b (c0,c1,c2,c3,c4,c5,c6 ) +and8 :: (Arrow a) + => a b c0->a b c1->a b c2->a b c3->a b c4->a b c5->a b c6->a b c7 + -> a b (c0,c1,c2,c3,c4,c5,c6,c7) + +and3 a b c = (and2 a b ) &&& c + >>^ \((z,y ) , x) -> (z,y,x ) +and4 a b c d = (and3 a b c ) &&& d + >>^ \((z,y,x ) , w) -> (z,y,x,w ) +and5 a b c d e = (and4 a b c d ) &&& e + >>^ \((z,y,x,w ) , v) -> (z,y,x,w,v ) +and6 a b c d e f = (and5 a b c d e ) &&& f + >>^ \((z,y,x,w,v ) , u) -> (z,y,x,w,v,u ) +and7 a b c d e f g = (and6 a b c d e f ) &&& g + >>^ \((z,y,x,w,v,u ) , t) -> (z,y,x,w,v,u,t ) +and8 a b c d e f g h = (and7 a b c d e f g) &&& h + >>^ \((z,y,x,w,v,u,t) , s) -> (z,y,x,w,v,u,t,s) + +liftA2 :: (Arrow a) => (x -> y -> z) -> a b x -> a b y -> a b z +liftA2 f a b = a &&& b >>^ uncurry f + +liftA3 :: (Arrow a) => (z->y->x -> r) + -> a b z->a b y->a b x + -> a b r +liftA4 :: (Arrow a) => (z->y->x->w -> r) + -> a b z->a b y->a b x->a b w + -> a b r +liftA5 :: (Arrow a) => (z->y->x->w->v -> r) + -> a b z->a b y->a b x->a b w->a b v + -> a b r +liftA6 :: (Arrow a) => (z->y->x->w->v->u -> r) + -> a b z->a b y->a b x->a b w->a b v->a b u + -> a b r +liftA7 :: (Arrow a) => (z->y->x->w->v->u->t -> r) + -> a b z->a b y->a b x->a b w->a b v->a b u->a b t + -> a b r +liftA8 :: (Arrow a) => (z->y->x->w->v->u->t->s -> r) + -> a b z->a b y->a b x->a b w->a b v->a b u->a b t->a b s + -> a b r + +liftA3 fun a b c = and3 a b c >>^ uncurry3 fun +liftA4 fun a b c d = and4 a b c d >>^ uncurry4 fun +liftA5 fun a b c d e = and5 a b c d e >>^ uncurry5 fun +liftA6 fun a b c d e f = and6 a b c d e f >>^ uncurry6 fun +liftA7 fun a b c d e f g = and7 a b c d e f g >>^ uncurry7 fun +liftA8 fun a b c d e f g h = and8 a b c d e f g h >>^ uncurry8 fun + +liftA :: (Arrow a) => (y -> z) -> a b y -> a b z +liftA fun a = a >>^ fun + + +-- | Duplicate a value to subsequently feed it into different arrows. +-- Can almost always be replaced with '(&&&)', 'keepingTheValue', +-- or even '(|||)'. +-- Aequivalent to +-- > returnA &&& returnA +duplicate :: (Arrow a) => a b (b,b) +duplicate = arr $ join (,) + +-- | Lifts the combination of two values into an arrow. +joinOn :: (Arrow a) => (x -> y -> z) -> a (x,y) z +joinOn = arr.uncurry + +-- | Applies a function to the uncurried result-pair of an arrow-application. +-- (The §-symbol was chosen to evoke an association with pairs through the +-- shared first character) +(>>§) :: (Arrow a) => a x (b,c) -> (b -> c -> d) -> a x d +a >>§ f = a >>^ uncurry f + +-- | '(>>§)' with its arguments flipped +(§<<) :: (Arrow a) => (b -> c -> d) -> a x (b,c) -> a x d +(§<<) = flip (>>§) + +-- | Precomposition with an uncurried function +(§>>) :: (Arrow a) => (b -> c -> d) -> a d r -> a (b,c) r +f §>> a = uncurry f ^>> a + +-- | Precomposition with an uncurried function (right to left variant) +(<<§) :: (Arrow a) => a d r -> (b -> c -> d) -> a (b,c) r +(<<§) = flip (§>>) + +infixr 2 >>§, §<<, §>>, <<§ + + +-- | Duplicate a value and apply an arrow to the second instance. +-- Aequivalent to +-- > \a -> duplicate >>> second a +-- or +-- > \a -> returnA &&& a +keepingTheValue :: (Arrow a) => a b c -> a b (b,c) +keepingTheValue a = returnA &&& a + +-- | Duplicate a value and apply an arrow to the first instance. +-- Aequivalent to +-- > \a -> duplicate >>> first a +-- or +-- > \a -> a &&& returnA +keepingTheValue' :: (Arrow a) => a b c -> a b (c,b) +keepingTheValue' a = a &&& returnA + +-- | 'bind' from the "Maybe"-Monad lifted into an 'ArrowChoice'. +-- Actually, it's the more complex '(>=>)', because 'bind' alone does not +-- combine as nicely in arrow form. +-- The current implementation is not the most efficient one, because it can +-- not return directly if a 'Nothing' is encountered. That in turn follows +-- from the type system, as 'Nothing' has an "invisible" type parameter that +-- can not be dropped early. +-- +-- Also, there probably is a way to generalize this to other monads +-- or applicatives, but I'm leaving that as an exercise to the reader. +-- I have a feeling there is a new Arrow-typeclass to be found that is less +-- restrictive than 'ArrowApply'. If it is already out there, +-- I have not seen it yet. ('ArrowPlus' for example is not general enough.) +(>>>=) :: (ArrowChoice a) => a x (Maybe b) -> a b (Maybe c) -> a x (Maybe c) +a1 >>>= a2 = a1 >>> maybeToChoice >>> right a2 >>> choiceToMaybe >>^ join + +infixr 2 >>>= + +-- | 'mplus' Lifted into an arrow. No 'ArrowPlus' required. +-- (But still different from a true bind) +(>++<) :: (Arrow a, MonadPlus m) => a x (m b) -> a x (m b) -> a x (m b) +(>++<) = liftA2 mplus + +-- | Left-compose with a pure function +leftLift :: (ArrowChoice a) => (l -> l') -> a (Either l r) (Either l' r) +leftLift = left.arr + +-- | Right-compose with a pure function +rightLift :: (ArrowChoice a) => (r -> r') -> a (Either l r) (Either l r') +rightLift = right.arr + + +( ^+++ ) :: (ArrowChoice a) => (b -> c) -> a b' c' -> a (Either b b') (Either c c') +( +++^ ) :: (ArrowChoice a) => a b c -> (b' -> c') -> a (Either b b') (Either c c') +( ^+++^ ) :: (ArrowChoice a) => (b -> c) -> (b' -> c') -> a (Either b b') (Either c c') + +l ^+++ r = leftLift l >>> right r +l +++^ r = left l >>> rightLift r +l ^+++^ r = leftLift l >>> rightLift r + +infixr 2 ^+++, +++^, ^+++^ + +( ^||| ) :: (ArrowChoice a) => (b -> d) -> a c d -> a (Either b c) d +( |||^ ) :: (ArrowChoice a) => a b d -> (c -> d) -> a (Either b c) d +( ^|||^ ) :: (ArrowChoice a) => (b -> d) -> (c -> d) -> a (Either b c) d + +l ^||| r = arr l ||| r +l |||^ r = l ||| arr r +l ^|||^ r = arr l ||| arr r + +infixr 2 ^||| , |||^, ^|||^ + +( ^&&& ) :: (Arrow a) => (b -> c) -> a b c' -> a b (c,c') +( &&&^ ) :: (Arrow a) => a b c -> (b -> c') -> a b (c,c') +( ^&&&^ ) :: (Arrow a) => (b -> c) -> (b -> c') -> a b (c,c') + +l ^&&& r = arr l &&& r +l &&&^ r = l &&& arr r +l ^&&&^ r = arr l &&& arr r + +infixr 3 ^&&&, &&&^, ^&&&^ + +( ^*** ) :: (Arrow a) => (b -> c) -> a b' c' -> a (b,b') (c,c') +( ***^ ) :: (Arrow a) => a b c -> (b' -> c') -> a (b,b') (c,c') +( ^***^ ) :: (Arrow a) => (b -> c) -> (b' -> c') -> a (b,b') (c,c') + +l ^*** r = arr l *** r +l ***^ r = l *** arr r +l ^***^ r = arr l *** arr r + +infixr 3 ^***, ***^, ^***^ + +-- | A version of +-- +-- >>> \p -> arr (\x -> if p x the Right x else Left x) +-- +-- but with p being an arrow +choose :: (ArrowChoice a) => a b Bool -> a b (Either b b) +choose checkValue = keepingTheValue checkValue >>^ select + where select (x,True ) = Right x + select (x,False ) = Left x + +-- | Converts @Right a@ into @Just a@ and @Left _@ into @Nothing@. +choiceToMaybe :: (ArrowChoice a) => a (Either l r) (Maybe r) +choiceToMaybe = arr eitherToMaybe + +-- | Converts @Nothing@ into @Left ()@ and @Just a@ into @Right a@. +maybeToChoice :: (ArrowChoice a) => a (Maybe b) (Fallible b) +maybeToChoice = arr maybeToEither + +-- | Lifts a constant value into an arrow +returnV :: (Arrow a) => c -> a x c +returnV = arr.const + +-- | 'returnA' dropping everything +returnA_ :: (Arrow a) => a _b () +returnA_ = returnV () + +-- | Wrapper for an arrow that can be evaluated im parallel. All +-- Arrows can be evaluated in parallel, as long as they return a +-- monoid. +newtype ParallelArrow a b c = CoEval { evalParallelArrow :: a b c } + deriving (Eq, Ord, Show) + +instance (Arrow a, Monoid m) => Monoid (ParallelArrow a b m) where + mempty = CoEval $ returnV mempty + (CoEval a) `mappend` (CoEval ~b) = CoEval $ a &&& b >>§ mappend + +-- | Evaluates a collection of arrows in a parallel fashion. +-- +-- This is in essence a fold of '(&&&)' over the collection, +-- so the actual execution order and parallelity depends on the +-- implementation of '(&&&)' in the arrow in question. +-- The default implementation of '(&&&)' for example keeps the +-- order as given in the collection. +-- +-- This function can be seen as a generalization of +-- 'Control.Applicative.sequenceA' to arrows or as an alternative to +-- a fold with 'Control.Applicative.WrappedArrow', which +-- substitutes the monoid with function application. +-- +coEval :: (Arrow a, F.Foldable f, Monoid m) => f (a b m) -> a b m +coEval = evalParallelArrow . (F.foldMap CoEval) + +-- | Defines Left as failure, Right as success +type FallibleArrow a input failure success = a input (Either failure success) + +type ReFallibleArrow a failure success success' + = FallibleArrow a (Either failure success) failure success' + +-- | Wrapper for fallible arrows. Fallible arrows are all arrows that return +-- an Either value where left is a faliure and right is a success value. +newtype AlternativeArrow a input failure success + = TryArrow { evalAlternativeArrow :: FallibleArrow a input failure success } + + +instance (ArrowChoice a, Monoid failure) + => Monoid (AlternativeArrow a input failure success) where + mempty = TryArrow $ returnV $ Left mempty + (TryArrow a) `mappend` (TryArrow b) + = TryArrow $ a &&& b + >>^ \(a',~b') + -> ( (\a'' -> left (mappend a'') b') ||| Right ) + a' + +-- | Evaluates a collection of fallible arrows, trying each one in succession. +-- Left values are interpreted as failures, right values as successes. +-- +-- The evaluation is stopped once an arrow succeeds. +-- Up to that point, all failures are collected in the failure-monoid. +-- Note that '()' is a monoid, and thus can serve as a failure-collector if +-- you are uninterested in the exact failures. +-- +-- This is in essence a fold of '(&&&)' over the collection, enhanced with a +-- little bit of repackaging, so the actual execution order depends on the +-- implementation of '(&&&)' in the arrow in question. +-- The default implementation of '(&&&)' for example keeps the +-- order as given in the collection. +-- +tryArrows :: (ArrowChoice a, F.Foldable f, Monoid failure) + => f (FallibleArrow a b failure success) + -> FallibleArrow a b failure success +tryArrows = evalAlternativeArrow . (F.foldMap TryArrow) + +-- +liftSuccess :: (ArrowChoice a) + => (success -> success') + -> ReFallibleArrow a failure success success' +liftSuccess = rightLift + +-- +liftAsSuccess :: (ArrowChoice a) + => a x success + -> FallibleArrow a x failure success +liftAsSuccess a = a >>^ Right + +-- +asFallibleArrow :: (ArrowChoice a) + => a x success + -> FallibleArrow a x failure success +asFallibleArrow a = a >>^ Right + +-- | Raises an error into a 'ReFallibleArrow' if the arrow is already in +-- "error mode" +liftError :: (ArrowChoice a, Monoid failure) + => failure + -> ReFallibleArrow a failure success success +liftError e = leftLift (e <>) + +-- | Raises an error into a 'FallibleArrow', droping both the arrow input +-- and any previously stored error value. +_raiseA :: (ArrowChoice a) + => failure + -> FallibleArrow a x failure success +_raiseA e = returnV (Left e) + +-- | Raises an empty error into a 'FallibleArrow', droping both the arrow input +-- and any previously stored error value. +_raiseAEmpty :: (ArrowChoice a, Monoid failure) + => FallibleArrow a x failure success +_raiseAEmpty = _raiseA mempty + +-- | Raises an error into a 'ReFallibleArrow', possibly appending the new error +-- to an existing one +raiseA :: (ArrowChoice a, Monoid failure) + => failure + -> ReFallibleArrow a failure success success +raiseA e = arr $ Left.(either (<> e) (const e)) + +-- | Raises an empty error into a 'ReFallibleArrow'. If there already is an +-- error, nothing changes. +-- (Note that this function is only aequivalent to @raiseA mempty@ iff the +-- failure monoid follows the monoid laws.) +raiseAEmpty :: (ArrowChoice a, Monoid failure) + => ReFallibleArrow a failure success success +raiseAEmpty = arr (fromRight (const mempty) >>> Left) + + +-- | Execute the second arrow if the first succeeds +(>>?) :: (ArrowChoice a, Monoid failure) + => FallibleArrow a x failure success + -> FallibleArrow a success failure success' + -> FallibleArrow a x failure success' +a >>? b = a >>> Left ^||| b + +-- | Execute the lifted second arrow if the first succeeds +(>>?^) :: (ArrowChoice a, Monoid failure) + => FallibleArrow a x failure success + -> (success -> success') + -> FallibleArrow a x failure success' +a >>?^ f = a >>^ Left ^|||^ Right . f + +-- | Execute the lifted second arrow if the first succeeds +(>>?^?) :: (ArrowChoice a, Monoid failure) + => FallibleArrow a x failure success + -> (success -> Either failure success') + -> FallibleArrow a x failure success' +a >>?^? b = a >>> Left ^|||^ b + +-- | Execute the second arrow if the lifted first arrow succeeds +(^>>?) :: (ArrowChoice a, Monoid failure) + => (x -> Either failure success) + -> FallibleArrow a success failure success' + -> FallibleArrow a x failure success' +a ^>>? b = a ^>> Left ^||| b + +-- | Execute the lifted second arrow if the lifted first arrow succeeds +(^>>?^) :: (ArrowChoice a, Monoid failure) + => (x -> Either failure success) + -> (success -> success') + -> FallibleArrow a x failure success' +a ^>>?^ f = arr $ a >>> right f + +-- | Execute the lifted second arrow if the lifted first arrow succeeds +(^>>?^?) :: (ArrowChoice a, Monoid failure) + => (x -> Either failure success) + -> (success -> Either failure success') + -> FallibleArrow a x failure success' +a ^>>?^? f = a ^>> Left ^|||^ f + +-- | Execute the second, non-fallible arrow if the first arrow succeeds +(>>?!) :: (ArrowChoice a, Monoid failure) + => FallibleArrow a x failure success + -> a success success' + -> FallibleArrow a x failure success' +a >>?! f = a >>> right f + +--- +(>>?§) :: (ArrowChoice a, Monoid f) + => FallibleArrow a x f (b,b') + -> (b -> b' -> c) + -> FallibleArrow a x f c +a >>?§ f = a >>?^ (uncurry f) + +--- +(^>>?§) :: (ArrowChoice a, Monoid f) + => (x -> Either f (b,b')) + -> (b -> b' -> c) + -> FallibleArrow a x f c +a ^>>?§ f = arr a >>?^ (uncurry f) + +--- +(>>?§?) :: (ArrowChoice a, Monoid f) + => FallibleArrow a x f (b,b') + -> (b -> b' -> (Either f c)) + -> FallibleArrow a x f c +a >>?§? f = a >>?^? (uncurry f) + +infixr 1 >>?, >>?^, >>?^? +infixr 1 ^>>?, ^>>?^, ^>>?^?, >>?! +infixr 1 >>?§, ^>>?§, >>?§? + +-- | Keep values that are Right, replace Left values by a constant. +ifFailedUse :: (ArrowChoice a) => v -> a (Either f v) v +ifFailedUse v = arr $ either (const v) id + +-- | '(&&)' lifted into an arrow +(<&&>) :: (Arrow a) => a x Bool -> a x Bool -> a x Bool +(<&&>) = liftA2 (&&) + +-- | '(||)' lifted into an arrow +(<||>) :: (Arrow a) => a x Bool -> a x Bool -> a x Bool +(<||>) = liftA2 (||) + +-- | An equivalent of '(&&)' in a fallible arrow +(>&&<) :: (ArrowChoice a, Monoid f) => FallibleArrow a x f s + -> FallibleArrow a x f s' + -> FallibleArrow a x f (s,s') +(>&&<) = liftA2 chooseMin + +-- | An equivalent of '(||)' in some forms of fallible arrows +(>||<) :: (ArrowChoice a, Monoid f, Monoid s) => FallibleArrow a x f s + -> FallibleArrow a x f s + -> FallibleArrow a x f s +(>||<) = liftA2 chooseMax + +-- | An arrow version of a short-circuit (<|>) +ifFailedDo :: (ArrowChoice a) + => FallibleArrow a x f y + -> FallibleArrow a x f y + -> FallibleArrow a x f y +ifFailedDo a b = keepingTheValue a >>> repackage ^>> (b |||^ Right) + where repackage (x , Left _) = Left x + repackage (_ , Right y) = Right y + +infixr 4 <&&>, <||>, >&&<, >||< +infixr 1 `ifFailedDo` + + diff --git a/src/Text/Pandoc/Readers/Odt/Base.hs b/src/Text/Pandoc/Readers/Odt/Base.hs new file mode 100644 index 000000000..1f095bade --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Base.hs @@ -0,0 +1,43 @@ +{-# LANGUAGE PatternGuards #-} + +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.Base + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +Core types of the odt reader. +-} + +module Text.Pandoc.Readers.Odt.Base where + +import Text.Pandoc.Readers.Odt.Generic.XMLConverter +import Text.Pandoc.Readers.Odt.Namespaces + +type OdtConverterState s = XMLConverterState Namespace s + +type XMLReader s a b = FallibleXMLConverter Namespace s a b + +type XMLReaderSafe s a b = XMLConverter Namespace s a b + diff --git a/src/Text/Pandoc/Readers/Odt/ContentReader.hs b/src/Text/Pandoc/Readers/Odt/ContentReader.hs new file mode 100644 index 000000000..9bb585b8e --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/ContentReader.hs @@ -0,0 +1,790 @@ +{-# LANGUAGE Arrows #-} +{-# LANGUAGE TupleSections #-} +{-# LANGUAGE PatternGuards #-} +{-# LANGUAGE ViewPatterns #-} +{-# LANGUAGE RecordWildCards #-} + +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.ContentReader + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +The core of the odt reader that converts odt features into Pandoc types. +-} + +module Text.Pandoc.Readers.Odt.ContentReader +( readerState +, read_body +) where + +import Control.Arrow +import Control.Applicative hiding ( liftA, liftA2, liftA3 ) + +import qualified Data.Map as M +import Data.List ( find ) +import Data.Monoid +import Data.Maybe + +import qualified Text.XML.Light as XML + +import Text.Pandoc.Definition +import Text.Pandoc.Builder +import Text.Pandoc.Shared + +import Text.Pandoc.Readers.Odt.Base +import Text.Pandoc.Readers.Odt.Namespaces +import Text.Pandoc.Readers.Odt.StyleReader + +import Text.Pandoc.Readers.Odt.Arrows.Utils +import Text.Pandoc.Readers.Odt.Generic.XMLConverter +import Text.Pandoc.Readers.Odt.Generic.Fallible +import Text.Pandoc.Readers.Odt.Generic.Utils + + +-------------------------------------------------------------------------------- +-- State +-------------------------------------------------------------------------------- + +type Anchor = String + +data ReaderState + = ReaderState { -- | A collection of styles read somewhere else. + -- It is only queried here, not modified. + styleSet :: Styles + -- | A stack of the styles of parent elements. + -- Used to look up inherited style properties. + , styleTrace :: [Style] + -- | Keeps track of the current depth in nested lists + , currentListLevel :: ListLevel + -- | Lists may provide their own style, but they don't have + -- to. If they do not, the style of a parent list may be used + -- or even a default list style from the paragraph style. + -- This value keeps track of the closest list style there + -- currently is. + , currentListStyle :: Maybe ListStyle + -- | A map from internal anchor names to "pretty" ones. + -- The mapping is a purely cosmetic one. + , bookmarkAnchors :: M.Map Anchor Anchor + +-- , sequences +-- , trackedChangeIDs + } + deriving ( Show ) + +readerState :: Styles -> ReaderState +readerState styles = ReaderState styles [] 0 Nothing M.empty + +-- +pushStyle' :: Style -> ReaderState -> ReaderState +pushStyle' style state = state { styleTrace = style : styleTrace state } + +-- +popStyle' :: ReaderState -> ReaderState +popStyle' state = case styleTrace state of + _:trace -> state { styleTrace = trace } + _ -> state + +-- +modifyListLevel :: (ListLevel -> ListLevel) -> (ReaderState -> ReaderState) +modifyListLevel f state = state { currentListLevel = f (currentListLevel state) } + +-- +shiftListLevel :: ListLevel -> (ReaderState -> ReaderState) +shiftListLevel diff = modifyListLevel (+ diff) + +-- +swapCurrentListStyle :: Maybe ListStyle -> ReaderState + -> (ReaderState, Maybe ListStyle) +swapCurrentListStyle mListStyle state = ( state { currentListStyle = mListStyle } + , currentListStyle state + ) + +-- +lookupPrettyAnchor :: Anchor -> ReaderState -> Maybe Anchor +lookupPrettyAnchor anchor ReaderState{..} = M.lookup anchor bookmarkAnchors + +-- +putPrettyAnchor :: Anchor -> Anchor -> ReaderState -> ReaderState +putPrettyAnchor ugly pretty state@ReaderState{..} + = state { bookmarkAnchors = M.insert ugly pretty bookmarkAnchors } + +-- +usedAnchors :: ReaderState -> [Anchor] +usedAnchors ReaderState{..} = M.elems bookmarkAnchors + +-------------------------------------------------------------------------------- +-- Reader type and associated tools +-------------------------------------------------------------------------------- + +type OdtReader a b = XMLReader ReaderState a b + +type OdtReaderSafe a b = XMLReaderSafe ReaderState a b + +-- | Extract something from the styles +fromStyles :: (a -> Styles -> b) -> OdtReaderSafe a b +fromStyles f = keepingTheValue + (getExtraState >>^ styleSet) + >>§ f + +-- +getStyleByName :: OdtReader StyleName Style +getStyleByName = fromStyles lookupStyle >>^ maybeToChoice + +-- +findStyleFamily :: OdtReader Style StyleFamily +findStyleFamily = fromStyles getStyleFamily >>^ maybeToChoice + +-- +lookupListStyle :: OdtReader StyleName ListStyle +lookupListStyle = fromStyles lookupListStyleByName >>^ maybeToChoice + +-- +switchCurrentListStyle :: OdtReaderSafe (Maybe ListStyle) (Maybe ListStyle) +switchCurrentListStyle = keepingTheValue getExtraState + >>§ swapCurrentListStyle + >>> first setExtraState + >>^ snd + +-- +pushStyle :: OdtReaderSafe Style Style +pushStyle = keepingTheValue ( + ( keepingTheValue getExtraState + >>§ pushStyle' + ) + >>> setExtraState + ) + >>^ fst + +-- +popStyle :: OdtReaderSafe x x +popStyle = keepingTheValue ( + getExtraState + >>> arr popStyle' + >>> setExtraState + ) + >>^ fst + +-- +getCurrentListLevel :: OdtReaderSafe _x ListLevel +getCurrentListLevel = getExtraState >>^ currentListLevel + + +type AnchorPrefix = String + +-- | An adaptation of 'uniqueIdent' from "Text.Pandoc.Shared" that generates a +-- unique identifier but without assuming that the id should be for a header. +-- Second argument is a list of already used identifiers. +uniqueIdentFrom :: AnchorPrefix -> [Anchor] -> Anchor +uniqueIdentFrom baseIdent usedIdents = + let numIdent n = baseIdent ++ "-" ++ show n + in if baseIdent `elem` usedIdents + then case find (\x -> numIdent x `notElem` usedIdents) ([1..60000] :: [Int]) of + Just x -> numIdent x + Nothing -> baseIdent -- if we have more than 60,000, allow repeats + else baseIdent + +-- | First argument: basis for a new "pretty" anchor if none exists yet +-- Second argument: a key ("ugly" anchor) +-- Returns: saved "pretty" anchor or created new one +getPrettyAnchor :: OdtReaderSafe (AnchorPrefix, Anchor) Anchor +getPrettyAnchor = proc (baseIdent, uglyAnchor) -> do + state <- getExtraState -< () + case lookupPrettyAnchor uglyAnchor state of + Just prettyAnchor -> returnA -< prettyAnchor + Nothing -> do + let newPretty = uniqueIdentFrom baseIdent (usedAnchors state) + modifyExtraState (putPrettyAnchor uglyAnchor newPretty) -<< newPretty + +-- | Input: basis for a new header anchor +-- Ouput: saved new anchor +getHeaderAnchor :: OdtReaderSafe Inlines Anchor +getHeaderAnchor = proc title -> do + state <- getExtraState -< () + let anchor = uniqueIdent (toList title) (usedAnchors state) + modifyExtraState (putPrettyAnchor anchor anchor) -<< anchor + + +-------------------------------------------------------------------------------- +-- Working with styles +-------------------------------------------------------------------------------- + +-- +readStyleByName :: OdtReader _x Style +readStyleByName = findAttr NsText "style-name" >>? getStyleByName + +-- +isStyleToTrace :: OdtReader Style Bool +isStyleToTrace = findStyleFamily >>?^ (==FaText) + +-- +withNewStyle :: OdtReaderSafe x Inlines -> OdtReaderSafe x Inlines +withNewStyle a = proc x -> do + fStyle <- readStyleByName -< () + case fStyle of + Right style -> do + mFamily <- arr styleFamily -< style + fTextProps <- arr ( maybeToChoice + . textProperties + . styleProperties + ) -< style + case fTextProps of + Right textProps -> do + state <- getExtraState -< () + let triple = (state, textProps, mFamily) + modifier <- arr modifierFromStyleDiff -< triple + fShouldTrace <- isStyleToTrace -< style + case fShouldTrace of + Right shouldTrace -> do + if shouldTrace + then do + pushStyle -< style + inlines <- a -< x + popStyle -< () + arr modifier -<< inlines + else + -- In case anything goes wrong + a -< x + Left _ -> a -< x + Left _ -> a -< x + Left _ -> a -< x + + +type PropertyTriple = (ReaderState, TextProperties, Maybe StyleFamily) +type InlineModifier = Inlines -> Inlines + +-- | Given data about the local style changes, calculates how to modify +-- an instance of 'Inlines' +modifierFromStyleDiff :: PropertyTriple -> InlineModifier +modifierFromStyleDiff propertyTriple = + composition $ + (getVPosModifier propertyTriple) + : map (first ($ propertyTriple) >>> ifThen_else ignore) + [ (hasEmphChanged , emph ) + , (hasChanged isStrong , strong ) + , (hasChanged strikethrough , strikeout ) + ] + where + ifThen_else else' (if',then') = if if' then then' else else' + + ignore = id :: InlineModifier + + getVPosModifier :: PropertyTriple -> InlineModifier + getVPosModifier triple@(_,textProps,_) = + let getVPos = Just . verticalPosition + in case lookupPreviousValueM getVPos triple of + Nothing -> ignore + Just oldVPos -> getVPosModifier' (oldVPos,verticalPosition textProps) + + getVPosModifier' (oldVPos , newVPos ) | oldVPos == newVPos = ignore + getVPosModifier' ( _ , VPosSub ) = subscript + getVPosModifier' ( _ , VPosSuper ) = superscript + getVPosModifier' ( _ , _ ) = ignore + + hasEmphChanged :: PropertyTriple -> Bool + hasEmphChanged = swing any [ hasChanged isEmphasised + , hasChangedM pitch + , hasChanged underline + ] + + hasChanged property triple@(_, property -> newProperty, _) = + maybe True (/=newProperty) (lookupPreviousValue property triple) + + hasChangedM property triple@(_, textProps,_) = + fromMaybe False $ (/=) <$> property textProps <*> lookupPreviousValueM property triple + + lookupPreviousValue f = lookupPreviousStyleValue ((fmap f).textProperties) + + lookupPreviousValueM f = lookupPreviousStyleValue ((f =<<).textProperties) + + lookupPreviousStyleValue f (ReaderState{..},_,mFamily) + = ( findBy f $ extendedStylePropertyChain styleTrace styleSet ) + <|> ( f =<< fmap (lookupDefaultStyle' styleSet) mFamily ) + + +type ParaModifier = Blocks -> Blocks + +_MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_MM_ :: Int +_MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_PERCENT_ :: Int +_MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_MM_ = 5 +_MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_PERCENT_ = 5 + +-- | Returns either 'id' or 'blockQuote' depending on the current indentation +getParaModifier :: Style -> ParaModifier +getParaModifier Style{..} | Just props <- paraProperties styleProperties + , isBlockQuote (indentation props) + (margin_left props) + = blockQuote + | otherwise + = id + where + isBlockQuote mIndent mMargin + | LengthValueMM indent <- mIndent + , indent > _MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_MM_ + = True + | LengthValueMM margin <- mMargin + , margin > _MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_MM_ + = True + | LengthValueMM indent <- mIndent + , LengthValueMM margin <- mMargin + = indent + margin > _MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_MM_ + + | PercentValue indent <- mIndent + , indent > _MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_PERCENT_ + = True + | PercentValue margin <- mMargin + , margin > _MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_PERCENT_ + = True + | PercentValue indent <- mIndent + , PercentValue margin <- mMargin + = indent + margin > _MINIMUM_INDENTATION_FOR_BLOCKQUOTES_IN_PERCENT_ + + | otherwise + = False + +-- +constructPara :: OdtReaderSafe Blocks Blocks -> OdtReaderSafe Blocks Blocks +constructPara reader = proc blocks -> do + fStyle <- readStyleByName -< blocks + case fStyle of + Left _ -> reader -< blocks + Right style -> do + let modifier = getParaModifier style + blocks' <- reader -< blocks + arr modifier -<< blocks' + + + +type ListConstructor = [Blocks] -> Blocks + +getListConstructor :: ListLevelStyle -> ListConstructor +getListConstructor ListLevelStyle{..} = + case listLevelType of + LltBullet -> bulletList + LltImage -> bulletList + LltNumbered -> let listNumberStyle = toListNumberStyle listItemFormat + listNumberDelim = toListNumberDelim listItemPrefix + listItemSuffix + in orderedListWith (1, listNumberStyle, listNumberDelim) + where + toListNumberStyle LinfNone = DefaultStyle + toListNumberStyle LinfNumber = Decimal + toListNumberStyle LinfRomanLC = LowerRoman + toListNumberStyle LinfRomanUC = UpperRoman + toListNumberStyle LinfAlphaLC = LowerAlpha + toListNumberStyle LinfAlphaUC = UpperAlpha + toListNumberStyle (LinfString _) = Example + + toListNumberDelim Nothing (Just ".") = Period + toListNumberDelim (Just "" ) (Just ".") = Period + toListNumberDelim Nothing (Just ")") = OneParen + toListNumberDelim (Just "" ) (Just ")") = OneParen + toListNumberDelim (Just "(") (Just ")") = TwoParens + toListNumberDelim _ _ = DefaultDelim + + +-- | Determines which style to use for a list, which level to use of that +-- style, and which type of list to create as a result of this information. +-- Then prepares the state for eventual child lists and constructs the list from +-- the results. +-- Two main cases are handled: The list may provide its own style or it may +-- rely on a parent list's style. I the former case the current style in the +-- state must be switched before and after the call to the child converter +-- while in the latter the child converter can be called directly. +-- If anything goes wrong, a default ordered-list-constructor is used. +constructList :: OdtReaderSafe x [Blocks] -> OdtReaderSafe x Blocks +constructList reader = proc x -> do + modifyExtraState (shiftListLevel 1) -< () + listLevel <- getCurrentListLevel -< () + fStyleName <- findAttr NsText "style-name" -< () + case fStyleName of + Right styleName -> do + fListStyle <- lookupListStyle -< styleName + case fListStyle of + Right listStyle -> do + fLLS <- arr (uncurry getListLevelStyle) -< (listLevel,listStyle) + case fLLS of + Just listLevelStyle -> do + oldListStyle <- switchCurrentListStyle -< Just listStyle + blocks <- constructListWith listLevelStyle -<< x + switchCurrentListStyle -< oldListStyle + returnA -< blocks + Nothing -> constructOrderedList -< x + Left _ -> constructOrderedList -< x + Left _ -> do + state <- getExtraState -< () + mListStyle <- arr currentListStyle -< state + case mListStyle of + Just listStyle -> do + fLLS <- arr (uncurry getListLevelStyle) -< (listLevel,listStyle) + case fLLS of + Just listLevelStyle -> constructListWith listLevelStyle -<< x + Nothing -> constructOrderedList -< x + Nothing -> constructOrderedList -< x + where + constructOrderedList = + reader + >>> modifyExtraState (shiftListLevel (-1)) + >>^ orderedList + constructListWith listLevelStyle = + reader + >>> getListConstructor listLevelStyle + ^>> modifyExtraState (shiftListLevel (-1)) + +-------------------------------------------------------------------------------- +-- Readers +-------------------------------------------------------------------------------- + +type ElementMatcher result = (Namespace, ElementName, OdtReader result result) + +type InlineMatcher = ElementMatcher Inlines + +type BlockMatcher = ElementMatcher Blocks + + +-- +matchingElement :: (Monoid e) + => Namespace -> ElementName + -> OdtReaderSafe e e + -> ElementMatcher e +matchingElement ns name reader = (ns, name, asResultAccumulator reader) + where + asResultAccumulator :: (ArrowChoice a, Monoid m) => a m m -> a m (Fallible m) + asResultAccumulator a = liftAsSuccess $ keepingTheValue a >>§ (<>) + +-- +matchChildContent' :: (Monoid result) + => [ElementMatcher result] + -> OdtReaderSafe _x result +matchChildContent' ls = returnV mempty >>> matchContent' ls + +-- +matchChildContent :: (Monoid result) + => [ElementMatcher result] + -> OdtReaderSafe (result, XML.Content) result + -> OdtReaderSafe _x result +matchChildContent ls fallback = returnV mempty >>> matchContent ls fallback + + +-------------------------------------------- +-- Matchers +-------------------------------------------- + +---------------------- +-- Basics +---------------------- + +-- +-- | Open Document allows several consecutive spaces if they are marked up +read_plain_text :: OdtReaderSafe (Inlines, XML.Content) Inlines +read_plain_text = fst ^&&& read_plain_text' >>§ recover + where + -- fallible version + read_plain_text' :: OdtReader (Inlines, XML.Content) Inlines + read_plain_text' = ( second ( arr extractText ) + >>^ spreadChoice >>?! second text + ) + >>?§ (<>) + -- + extractText :: XML.Content -> Fallible String + extractText (XML.Text cData) = succeedWith (XML.cdData cData) + extractText _ = failEmpty + + +-- specifically. I honor that, although the current implementation of '(<>)' +-- for 'Inlines' in "Text.Pandoc.Builder" will collaps them agein. +-- The rational is to be prepared for future modifications. +read_spaces :: InlineMatcher +read_spaces = matchingElement NsText "s" ( + readAttrWithDefault NsText "c" 1 -- how many spaces? + >>^ fromList.(`replicate` Space) + ) +-- +read_line_break :: InlineMatcher +read_line_break = matchingElement NsText "line-break" + $ returnV linebreak + +-- +read_span :: InlineMatcher +read_span = matchingElement NsText "span" + $ withNewStyle + $ matchChildContent [ read_span + , read_spaces + , read_line_break + , read_link + , read_note + , read_citation + , read_bookmark + , read_bookmark_start + , read_reference_start + , read_bookmark_ref + , read_reference_ref + ] read_plain_text + +-- +read_paragraph :: BlockMatcher +read_paragraph = matchingElement NsText "p" + $ constructPara + $ liftA para + $ withNewStyle + $ matchChildContent [ read_span + , read_spaces + , read_line_break + , read_link + , read_note + , read_citation + , read_bookmark + , read_bookmark_start + , read_reference_start + , read_bookmark_ref + , read_reference_ref + ] read_plain_text + + +---------------------- +-- Headers +---------------------- + +-- +read_header :: BlockMatcher +read_header = matchingElement NsText "h" + $ proc blocks -> do + level <- ( readAttrWithDefault NsText "outline-level" 1 + ) -< blocks + children <- ( matchChildContent [ read_span + , read_spaces + , read_line_break + , read_link + , read_note + , read_citation + , read_bookmark + , read_bookmark_start + , read_reference_start + , read_bookmark_ref + , read_reference_ref + ] read_plain_text + ) -< blocks + anchor <- getHeaderAnchor -< children + let idAttr = (anchor, [], []) -- no classes, no key-value pairs + arr (uncurry3 headerWith) -< (idAttr, level, children) + +---------------------- +-- Lists +---------------------- + +-- +read_list :: BlockMatcher +read_list = matchingElement NsText "list" +-- $ withIncreasedListLevel + $ constructList +-- $ liftA bulletList + $ matchChildContent' [ read_list_item + ] +-- +read_list_item :: ElementMatcher [Blocks] +read_list_item = matchingElement NsText "list-item" + $ liftA (compactify'.(:[])) + ( matchChildContent' [ read_paragraph + , read_header + , read_list + ] + ) + + +---------------------- +-- Links +---------------------- + +read_link :: InlineMatcher +read_link = matchingElement NsText "a" + $ liftA3 link + ( findAttrWithDefault NsXLink "href" "" ) + ( findAttrWithDefault NsOffice "title" "" ) + ( matchChildContent [ read_span + , read_note + , read_citation + , read_bookmark + , read_bookmark_start + , read_reference_start + , read_bookmark_ref + , read_reference_ref + ] read_plain_text ) + + +------------------------- +-- Footnotes +------------------------- + +read_note :: InlineMatcher +read_note = matchingElement NsText "note" + $ liftA note + $ matchChildContent' [ read_note_body ] + +read_note_body :: BlockMatcher +read_note_body = matchingElement NsText "note-body" + $ matchChildContent' [ read_paragraph ] + +------------------------- +-- Citations +------------------------- + +read_citation :: InlineMatcher +read_citation = matchingElement NsText "bibliography-mark" + $ liftA2 cite + ( liftA2 makeCitation + ( findAttrWithDefault NsText "identifier" "" ) + ( readAttrWithDefault NsText "number" 0 ) + ) + ( matchChildContent [] read_plain_text ) + where + makeCitation :: String -> Int -> [Citation] + makeCitation citeId num = [Citation citeId [] [] NormalCitation num 0] + + +---------------------- +-- Tables +---------------------- + +-- +read_table :: BlockMatcher +read_table = matchingElement NsTable "table" + $ liftA (simpleTable []) + $ matchChildContent' [ read_table_row + ] + +-- +read_table_row :: ElementMatcher [[Blocks]] +read_table_row = matchingElement NsTable "table-row" + $ liftA (:[]) + $ matchChildContent' [ read_table_cell + ] + +-- +read_table_cell :: ElementMatcher [Blocks] +read_table_cell = matchingElement NsTable "table-cell" + $ liftA (compactify'.(:[])) + $ matchChildContent' [ read_paragraph + ] + +---------------------- +-- Internal links +---------------------- + +_ANCHOR_PREFIX_ :: String +_ANCHOR_PREFIX_ = "anchor" + +-- +readAnchorAttr :: OdtReader _x Anchor +readAnchorAttr = findAttr NsText "name" + +-- | Beware: may fail +findAnchorName :: OdtReader AnchorPrefix Anchor +findAnchorName = ( keepingTheValue readAnchorAttr + >>^ spreadChoice + ) >>?! getPrettyAnchor + + +-- +maybeAddAnchorFrom :: OdtReader Inlines AnchorPrefix + -> OdtReaderSafe Inlines Inlines +maybeAddAnchorFrom anchorReader = + keepingTheValue (anchorReader >>? findAnchorName >>?^ toAnchorElem) + >>> + proc (inlines, fAnchorElem) -> do + case fAnchorElem of + Right anchorElem -> + arr (anchorElem <>) -<< inlines + Left _ -> returnA -< inlines + where + toAnchorElem :: Anchor -> Inlines + toAnchorElem anchorID = spanWith (anchorID, [], []) mempty + -- no classes, no key-value pairs + +-- +read_bookmark :: InlineMatcher +read_bookmark = matchingElement NsText "bookmark" + $ maybeAddAnchorFrom (liftAsSuccess $ returnV _ANCHOR_PREFIX_) + +-- +read_bookmark_start :: InlineMatcher +read_bookmark_start = matchingElement NsText "bookmark-start" + $ maybeAddAnchorFrom (liftAsSuccess $ returnV _ANCHOR_PREFIX_) + +-- +read_reference_start :: InlineMatcher +read_reference_start = matchingElement NsText "reference-mark-start" + $ maybeAddAnchorFrom readAnchorAttr + +-- | Beware: may fail +findAnchorRef :: OdtReader _x Anchor +findAnchorRef = ( findAttr NsText "ref-name" + >>?^ (_ANCHOR_PREFIX_,) + ) >>?! getPrettyAnchor + + +-- +maybeInAnchorRef :: OdtReaderSafe Inlines Inlines +maybeInAnchorRef = proc inlines -> do + fRef <- findAnchorRef -< () + case fRef of + Right anchor -> + arr (toAnchorRef anchor) -<< inlines + Left _ -> returnA -< inlines + where + toAnchorRef :: Anchor -> Inlines -> Inlines + toAnchorRef anchor = link ('#':anchor) "" -- no title + +-- +read_bookmark_ref :: InlineMatcher +read_bookmark_ref = matchingElement NsText "bookmark-ref" + $ maybeInAnchorRef + <<< matchChildContent [] read_plain_text + +-- +read_reference_ref :: InlineMatcher +read_reference_ref = matchingElement NsText "reference-ref" + $ maybeInAnchorRef + <<< matchChildContent [] read_plain_text + + +---------------------- +-- Entry point +---------------------- + +--read_plain_content :: OdtReaderSafe _x Inlines +--read_plain_content = strContent >>^ text + +read_text :: OdtReaderSafe _x Pandoc +read_text = matchChildContent' [ read_header + , read_paragraph + , read_list + , read_table + ] + >>^ doc + +read_body :: OdtReader _x Pandoc +read_body = executeIn NsOffice "body" + $ executeIn NsOffice "text" + $ liftAsSuccess read_text + diff --git a/src/Text/Pandoc/Readers/Odt/Generic/Fallible.hs b/src/Text/Pandoc/Readers/Odt/Generic/Fallible.hs new file mode 100644 index 000000000..5922164c9 --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Generic/Fallible.hs @@ -0,0 +1,260 @@ +{-# LANGUAGE GeneralizedNewtypeDeriving #-} + +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.Generic.Fallible + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +Data types and utilities representing failure. Most of it is based on the +"Either" type in its usual configuration (left represents failure). + +In most cases, the failure type is implied or required to be a "Monoid". + +The choice of "Either" instead of a custom type makes it easier to write +compatible instances of "ArrowChoice". +-} + +-- We export everything +module Text.Pandoc.Readers.Odt.Generic.Fallible where + +import Control.Applicative +import Control.Monad + +import qualified Data.Foldable as F +import Data.Monoid + +-- | Default for now. Will probably become a class at some point. +type Failure = () + +type Fallible a = Either Failure a + + +-- | False -> Left (), True -> Right () +boolToEither :: Bool -> Fallible () +boolToEither False = Left () +boolToEither True = Right () + +-- | False -> Left (), True -> Right () +boolToChoice :: Bool -> Fallible () +boolToChoice False = Left () +boolToChoice True = Right () + +-- +maybeToEither :: Maybe a -> Fallible a +maybeToEither (Just a) = Right a +maybeToEither Nothing = Left () + +-- +eitherToMaybe :: Either _l a -> Maybe a +eitherToMaybe (Left _) = Nothing +eitherToMaybe (Right a) = Just a + +-- | > untagEither === either id id +untagEither :: Either a a -> a +untagEither (Left a) = a +untagEither (Right a) = a + +-- | > fromLeft f === either f id +fromLeft :: (a -> b) -> Either a b -> b +fromLeft f (Left a) = f a +fromLeft _ (Right b) = b + +-- | > fromRight f === either id f +fromRight :: (a -> b) -> Either b a -> b +fromRight _ (Left b) = b +fromRight f (Right a) = f a + +-- | > recover a === fromLeft (const a) === either (const a) id +recover :: a -> Either _f a -> a +recover a (Left _) = a +recover _ (Right a) = a + +-- | I would love to use 'fail'. Alas, 'Monad.fail'... +failWith :: failure -> Either failure _x +failWith f = Left f + +-- +failEmpty :: (Monoid failure) => Either failure _x +failEmpty = failWith mempty + +-- +succeedWith :: a -> Either _x a +succeedWith = Right + +-- +collapseEither :: Either failure (Either failure x) + -> Either failure x +collapseEither (Left f ) = Left f +collapseEither (Right (Left f)) = Left f +collapseEither (Right (Right x)) = Right x + +-- | If either of the values represents an error, the result is a +-- (possibly combined) error. If both values represent a success, +-- both are returned. +chooseMin :: (Monoid a) => Either a b -> Either a b' -> Either a (b,b') +chooseMin = chooseMinWith (,) + +-- | If either of the values represents an error, the result is a +-- (possibly combined) error. If both values represent a success, +-- a combination is returned. +chooseMinWith :: (Monoid a) => (b -> b' -> c) + -> Either a b + -> Either a b' + -> Either a c +chooseMinWith (><) (Right a) (Right b) = Right $ a >< b +chooseMinWith _ (Left a) (Left b) = Left $ a <> b +chooseMinWith _ (Left a) _ = Left a +chooseMinWith _ _ (Left b) = Left b + +-- | If either of the values represents a non-error, the result is a +-- (possibly combined) non-error. If both values represent an error, an error +-- is returned. +chooseMax :: (Monoid a, Monoid b) => Either a b -> Either a b -> Either a b +chooseMax = chooseMaxWith (<>) + +-- | If either of the values represents a non-error, the result is a +-- (possibly combined) non-error. If both values represent an error, an error +-- is returned. +chooseMaxWith :: (Monoid a) => (b -> b -> b) + -> Either a b + -> Either a b + -> Either a b +chooseMaxWith (><) (Right a) (Right b) = Right $ a >< b +chooseMaxWith _ (Left a) (Left b) = Left $ a <> b +chooseMaxWith _ (Right a) _ = Right a +chooseMaxWith _ _ (Right b) = Right b + + +-- | Class of containers that can escalate contained 'Either's. +-- The word "Vector" is meant in the sense of a disease transmitter. +class ChoiceVector v where + spreadChoice :: v (Either f a) -> Either f (v a) + +-- Let's do a few examples first + +instance ChoiceVector Maybe where + spreadChoice (Just (Left f)) = Left f + spreadChoice (Just (Right x)) = Right (Just x) + spreadChoice Nothing = Right Nothing + +instance ChoiceVector (Either l) where + spreadChoice (Right (Left f)) = Left f + spreadChoice (Right (Right x)) = Right (Right x) + spreadChoice (Left x ) = Right (Left x) + +instance ChoiceVector ((,) a) where + spreadChoice (_, Left f) = Left f + spreadChoice (x, Right y) = Right (x,y) + -- Wasn't there a newtype somewhere with the elements flipped? + +-- +-- More instances later, first some discussion. +-- +-- I'll have to freshen up on type system details to see how (or if) to do +-- something like +-- +-- > instance (ChoiceVector a, ChoiceVector b) => ChoiceVector (a b) where +-- > : +-- +-- But maybe it would be even better to use something like +-- +-- > class ChoiceVector v v' f | v -> v' f where +-- > spreadChoice :: v -> Either f v' +-- +-- That way, more places in @v@ could spread the cheer, e.g.: +-- +-- As before: +-- -- ( a , Either f b) (a , b) f +-- > instance ChoiceVector ((,) a (Either f b)) ((,) a b) f where +-- > spreadChoice (_, Left f) = Left f +-- > spreadChoice (a, Right b) = Right (a,b) +-- +-- But also: +-- -- ( Either f a , b) (a , b) f +-- > instance ChoiceVector ((,) (Either f a) b) ((,) a b) f where +-- > spreadChoice (Right a,b) = Right (a,b) +-- > spreadChoice (Left f,_) = Left f +-- +-- And maybe even: +-- -- ( Either f a , Either f b) (a , b) f +-- > instance ChoiceVector ((,) (Either f a) (Either f b)) ((,) a b) f where +-- > spreadChoice (Right a , Right b) = Right (a,b) +-- > spreadChoice (Left f , _ ) = Left f +-- > spreadChoice ( _ , Left f) = Left f +-- +-- Of course that would lead to a lot of overlapping instances... +-- But I can't think of a different way. A selector function might help, +-- but not even a "Data.Traversable" is powerful enough for that. +-- But maybe someone has already solved all this with a lens library. +-- +-- Well, it's an interesting academic question. But for practical purposes, +-- I have more than enough right now. + +instance ChoiceVector ((,,) a b) where + spreadChoice (_,_, Left f) = Left f + spreadChoice (a,b, Right x) = Right (a,b,x) + +instance ChoiceVector ((,,,) a b c) where + spreadChoice (_,_,_, Left f) = Left f + spreadChoice (a,b,c, Right x) = Right (a,b,c,x) + +instance ChoiceVector ((,,,,) a b c d) where + spreadChoice (_,_,_,_, Left f) = Left f + spreadChoice (a,b,c,d, Right x) = Right (a,b,c,d,x) + +instance ChoiceVector (Const a) where + spreadChoice (Const c) = Right (Const c) -- need to repackage because of implicit types + +-- | Fails on the first error +instance ChoiceVector [] where + spreadChoice = sequence -- using the monad instance of Either. + -- Could be generalized to "Data.Traversable" - but why play + -- with UndecidableInstances unless this is really needed. + +-- | Wrapper for a list. While the normal list instance of 'ChoiceVector' +-- fails whenever it can, this type will never fail. +newtype SuccessList a = SuccessList { collectNonFailing :: [a] } + deriving ( Eq, Ord, Show ) + +instance ChoiceVector SuccessList where + spreadChoice = Right . SuccessList . (foldr unTagRight []) . collectNonFailing + where unTagRight (Right x) = (x:) + unTagRight _ = id + +-- | Like 'catMaybes', but for 'Either'. +collectRights :: [Either _l r] -> [r] +collectRights = collectNonFailing . untag . spreadChoice . SuccessList + where untag = fromLeft (error "Unexpected Left") + +-- | A version of 'collectRights' generalized to other containers. The +-- container must be both "reducible" and "buildable". Most general containers +-- should fullfill these requirements, but there is no single typeclass +-- (that I know of) for that. +-- Therefore, they are split between 'Foldable' and 'MonadPlus'. +-- (Note that 'Data.Traversable.Traversable' alone would not be enough, either.) +collectRightsF :: (F.Foldable c, MonadPlus c) => c (Either _l r) -> c r +collectRightsF = F.foldr unTagRight mzero + where unTagRight (Right x) = mplus $ return x + unTagRight _ = id diff --git a/src/Text/Pandoc/Readers/Odt/Generic/Namespaces.hs b/src/Text/Pandoc/Readers/Odt/Generic/Namespaces.hs new file mode 100644 index 000000000..82ae3e20e --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Generic/Namespaces.hs @@ -0,0 +1,62 @@ +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.Generic.Namespaces + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +A class containing a set of namespace identifiers. Used to convert between +typesafe Haskell namespace identifiers and unsafe "real world" namespaces. +-} + +module Text.Pandoc.Readers.Odt.Generic.Namespaces where + +import qualified Data.Map as M + +-- +type NameSpaceIRI = String + +-- +type NameSpaceIRIs nsID = M.Map nsID NameSpaceIRI + +-- +class (Eq nsID, Ord nsID) => NameSpaceID nsID where + + -- | Given a IRI, possibly update the map and return the id of the namespace. + -- May fail if the namespace is unknown and the application does not + -- allow unknown namespaces. + getNamespaceID :: NameSpaceIRI + -> NameSpaceIRIs nsID + -> Maybe (NameSpaceIRIs nsID, nsID) + -- | Given a namespace id, lookup its IRI. May be overriden for performance. + getIRI :: nsID + -> NameSpaceIRIs nsID + -> Maybe NameSpaceIRI + -- | The root element of an XML document has a namespace, too, and the + -- "XML.Light-parser" is eager to remove the corresponding namespace + -- attribute. + -- As a result, at least this root namespace must be provided. + getInitialIRImap :: NameSpaceIRIs nsID + + getIRI = M.lookup + getInitialIRImap = M.empty diff --git a/src/Text/Pandoc/Readers/Odt/Generic/SetMap.hs b/src/Text/Pandoc/Readers/Odt/Generic/SetMap.hs new file mode 100644 index 000000000..afd7d616c --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Generic/SetMap.hs @@ -0,0 +1,48 @@ +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.Generic.SetMap + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +A map of values to sets of values. +-} + +module Text.Pandoc.Readers.Odt.Generic.SetMap where + +import qualified Data.Map as M +import qualified Data.Set as S + +type SetMap k v = M.Map k (S.Set v) + +empty :: SetMap k v +empty = M.empty + +fromList :: (Ord k, Ord v) => [(k,v)] -> SetMap k v +fromList = foldr (uncurry insert) empty + +insert :: (Ord k, Ord v) => k -> v -> SetMap k v -> SetMap k v +insert key value setMap = M.insertWith S.union key (S.singleton value) setMap + +union3 :: (Ord k) => SetMap k v -> SetMap k v -> SetMap k v -> SetMap k v +union3 sm1 sm2 sm3 = sm1 `M.union` sm2 `M.union` sm3 diff --git a/src/Text/Pandoc/Readers/Odt/Generic/Utils.hs b/src/Text/Pandoc/Readers/Odt/Generic/Utils.hs new file mode 100644 index 000000000..6c10ed61d --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Generic/Utils.hs @@ -0,0 +1,171 @@ +{-# LANGUAGE TypeOperators #-} +{-# LANGUAGE TupleSections #-} +{-# LANGUAGE PatternGuards #-} +{-# LANGUAGE ViewPatterns #-} + +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Reader.Odt.Generic.Utils + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +General utility functions for the odt reader. +-} + +module Text.Pandoc.Readers.Odt.Generic.Utils +( uncurry3 +, uncurry4 +, uncurry5 +, uncurry6 +, uncurry7 +, uncurry8 +, swap +, reverseComposition +, bool +, tryToRead +, Lookupable(..) +, readLookupables +, readLookupable +, readPercent +, findBy +, swing +, composition +) where + +import Control.Category ( Category, (>>>), (<<<) ) +import qualified Control.Category as Cat ( id ) +import Control.Monad ( msum ) + +import qualified Data.Foldable as F ( Foldable, foldr ) +import Data.Maybe + + +-- | Aequivalent to +-- > foldr (.) id +-- where '(.)' are 'id' are the ones from "Control.Category" +-- and 'foldr' is the one from "Data.Foldable". +-- The noun-form was chosen to be consistend with 'sum', 'product' etc +-- based on the discussion at +-- +-- (that I was not part of) +composition :: (Category cat, F.Foldable f) => f (cat a a) -> cat a a +composition = F.foldr (<<<) Cat.id + +-- | Aequivalent to +-- > foldr (flip (.)) id +-- where '(.)' are 'id' are the ones from "Control.Category" +-- and 'foldr' is the one from "Data.Foldable". +-- A reversed version of 'composition'. +reverseComposition :: (Category cat, F.Foldable f) => f (cat a a) -> cat a a +reverseComposition = F.foldr (>>>) Cat.id + +-- | 'Either' has 'either', 'Maybe' has 'maybe'. 'Bool' should have 'bool'. +-- Note that the first value is selected if the boolean value is 'False'. +-- That makes 'bool' consistent with the other two. Also, 'bool' now takes its +-- arguments in the exact opposite order compared to the normal if construct. +bool :: a -> a -> Bool -> a +bool x _ False = x +bool _ x True = x + +-- | This function often makes it possible to switch values with the functions +-- that are applied to them. +-- +-- Examples: +-- > swing map :: [a -> b] -> a -> [b] +-- > swing any :: [a -> Bool] -> a -> Bool +-- > swing foldr :: b -> a -> [a -> b -> b] -> b +-- > swing scanr :: c -> a -> [a -> c -> c] -> c +-- > swing zipWith :: [a -> b -> c] -> a -> [b] -> [c] +-- > swing find :: [a -> Bool] -> a -> Maybe (a -> Bool) +-- +-- Stolen from +swing :: (((a -> b) -> b) -> c -> d) -> c -> a -> d +swing = flip.(.flip id) +-- swing f c a = f ($ a) c + + +-- | Alternative to 'read'/'reads'. The former of these throws errors +-- (nobody wants that) while the latter returns "to much" for simple purposes. +-- This function instead applies 'reads' and returns the first match (if any) +-- in a 'Maybe'. +tryToRead :: (Read r) => String -> Maybe r +tryToRead = reads >>> listToMaybe >>> fmap fst + +-- | A version of 'reads' that requires a '%' sign after the number +readPercent :: ReadS Int +readPercent s = [ (i,s') | (i , r ) <- reads s + , ("%" , s') <- lex r + ] + +-- | Data that can be looked up. +-- This is mostly a utility to read data with kind *. +class Lookupable a where + lookupTable :: [(String, a)] + +-- | The idea is to use this function as if there was a declaration like +-- +-- > instance (Lookupable a) => (Read a) where +-- > readsPrec _ = readLookupables +-- . +-- But including this code in this form would need UndecideableInstances. +-- That is a bad idea. Luckily 'readLookupable' (without the s at the end) +-- can be used directly in almost any case. +readLookupables :: (Lookupable a) => String -> [(a,String)] +readLookupables s = [ (a,rest) | (word,rest) <- lex s, + let result = lookup word lookupTable, + isJust result, + let Just a = result + ] + +-- | Very similar to a simple 'lookup' in the 'lookupTable', but with a lexer. +readLookupable :: (Lookupable a) => String -> Maybe a +readLookupable s = msum + $ map ((`lookup` lookupTable).fst) + $ lex s + +uncurry3 :: (a->b->c -> z) -> (a,b,c ) -> z +uncurry4 :: (a->b->c->d -> z) -> (a,b,c,d ) -> z +uncurry5 :: (a->b->c->d->e -> z) -> (a,b,c,d,e ) -> z +uncurry6 :: (a->b->c->d->e->f -> z) -> (a,b,c,d,e,f ) -> z +uncurry7 :: (a->b->c->d->e->f->g -> z) -> (a,b,c,d,e,f,g ) -> z +uncurry8 :: (a->b->c->d->e->f->g->h -> z) -> (a,b,c,d,e,f,g,h) -> z + +uncurry3 fun (a,b,c ) = fun a b c +uncurry4 fun (a,b,c,d ) = fun a b c d +uncurry5 fun (a,b,c,d,e ) = fun a b c d e +uncurry6 fun (a,b,c,d,e,f ) = fun a b c d e f +uncurry7 fun (a,b,c,d,e,f,g ) = fun a b c d e f g +uncurry8 fun (a,b,c,d,e,f,g,h) = fun a b c d e f g h + +swap :: (a,b) -> (b,a) +swap (a,b) = (b,a) + +-- | A version of "Data.List.find" that uses a converter to a Maybe instance. +-- The returned value is the first which the converter returns in a 'Just' +-- wrapper. +findBy :: (a -> Maybe b) -> [a] -> Maybe b +findBy _ [] = Nothing +findBy f ((f -> Just x):_ ) = Just x +findBy f ( _:xs) = findBy f xs + diff --git a/src/Text/Pandoc/Readers/Odt/Generic/XMLConverter.hs b/src/Text/Pandoc/Readers/Odt/Generic/XMLConverter.hs new file mode 100644 index 000000000..ec7e0ea5e --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Generic/XMLConverter.hs @@ -0,0 +1,1064 @@ +{-# LANGUAGE Arrows #-} +{-# LANGUAGE TupleSections #-} +{-# LANGUAGE GADTs #-} +{-# LANGUAGE PatternGuards #-} +{-# LANGUAGE RecordWildCards #-} + +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.Generic.XMLConverter + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +A generalized XML parser based on stateful arrows. +It might be sufficient to define this reader as a comonad, but there is +not a lot of use in trying. +-} + +module Text.Pandoc.Readers.Odt.Generic.XMLConverter +( ElementName +, XMLConverterState +, XMLConverter +, FallibleXMLConverter +, swapPosition +, runConverter +, runConverter'' +, runConverter' +, runConverterF' +, runConverterF +, getCurrentElement +, getExtraState +, setExtraState +, modifyExtraState +, convertingExtraState +, producingExtraState +, lookupNSiri +, lookupNSprefix +, readNSattributes +, elemName +, elemNameIs +, strContent +, elContent +, currentElem +, currentElemIs +, expectElement +, elChildren +, findChildren +, filterChildren +, filterChildrenName +, findChild' +, findChild +, filterChild' +, filterChild +, filterChildName' +, filterChildName +, isSet +, isSet' +, isSetWithDefault +, hasAttrValueOf' +, failIfNotAttrValueOf +, isThatTheAttrValue +, searchAttrIn +, searchAttrWith +, searchAttr +, lookupAttr +, lookupAttr' +, lookupAttrWithDefault +, lookupDefaultingAttr +, findAttr' +, findAttr +, findAttrWithDefault +, readAttr +, readAttr' +, readAttrWithDefault +, getAttr +-- , (>/<) +-- , (?>/<) +, executeIn +, collectEvery +, withEveryL +, withEvery +, tryAll +, tryAll' +, IdXMLConverter +, MaybeEConverter +, ElementMatchConverter +, MaybeCConverter +, ContentMatchConverter +, makeMatcherE +, makeMatcherC +, prepareMatchersE +, prepareMatchersC +, matchChildren +, matchContent'' +, matchContent' +, matchContent +) where + +import Control.Applicative hiding ( liftA, liftA2 ) +import Control.Monad ( MonadPlus ) +import Control.Arrow + +import qualified Data.Map as M +import qualified Data.Foldable as F +import Data.Default +import Data.Monoid ( Monoid ) +import Data.Maybe + +import qualified Text.XML.Light as XML + +import Text.Pandoc.Readers.Odt.Arrows.State +import Text.Pandoc.Readers.Odt.Arrows.Utils + +import Text.Pandoc.Readers.Odt.Generic.Namespaces +import Text.Pandoc.Readers.Odt.Generic.Utils +import Text.Pandoc.Readers.Odt.Generic.Fallible + +-------------------------------------------------------------------------------- +-- Basis types for readability +-------------------------------------------------------------------------------- + +-- +type ElementName = String +type AttributeName = String +type AttributeValue = String + +-- +type NameSpacePrefix = String + +-- +type NameSpacePrefixes nsID = M.Map nsID NameSpacePrefix + +-------------------------------------------------------------------------------- +-- Main converter state +-------------------------------------------------------------------------------- + +-- GADT so some of the NameSpaceID restrictions can be deduced +data XMLConverterState nsID extraState where + XMLConverterState :: NameSpaceID nsID + => { -- | A stack of parent elements. The top element is the current one. + -- Arguably, a real Zipper would be better. But that is an + -- optimization that can be made at a later time, e.g. when + -- replacing Text.XML.Light. + parentElements :: [XML.Element] + -- | A map from internal namespace IDs to the namespace prefixes + -- used in XML elements + , namespacePrefixes :: NameSpacePrefixes nsID + -- | A map from internal namespace IDs to namespace IRIs + -- (Only necessary for matching namespace IDs and prefixes) + , namespaceIRIs :: NameSpaceIRIs nsID + -- | A place to put "something else". This feature is used heavily + -- to keep the main code cleaner. More specifically, the main reader + -- is divided into different stages. Each stage lifts something up + -- here, which the next stage can then use. This could of course be + -- generalized to a state-tree or used for the namespace IRIs. The + -- border between states and values is an imaginary one, after all. + -- But the separation as it is seems to be enough for now. + , moreState :: extraState + } + -> XMLConverterState nsID extraState + +-- +createStartState :: (NameSpaceID nsID) + => XML.Element + -> extraState + -> XMLConverterState nsID extraState +createStartState element extraState = + XMLConverterState + { parentElements = [element] + , namespacePrefixes = M.empty + , namespaceIRIs = getInitialIRImap + , moreState = extraState + } + +-- | Functor over extra state +instance Functor (XMLConverterState nsID) where + fmap f ( XMLConverterState parents prefixes iRIs extraState ) + = XMLConverterState parents prefixes iRIs (f extraState) + +-- +replaceExtraState :: extraState + -> XMLConverterState nsID _x + -> XMLConverterState nsID extraState +replaceExtraState x s + = fmap (const x) s + +-- +currentElement :: XMLConverterState nsID extraState + -> XML.Element +currentElement state = head (parentElements state) + +-- | Replace the current position by another, modifying the extra state +-- in the process +swapPosition :: (extraState -> extraState') + -> [XML.Element] + -> XMLConverterState nsID extraState + -> XMLConverterState nsID extraState' +swapPosition f stack state + = state { parentElements = stack + , moreState = f (moreState state) + } + +-- | Replace the current position by another, modifying the extra state +-- in the process +swapStack' :: XMLConverterState nsID extraState + -> [XML.Element] + -> ( XMLConverterState nsID extraState , [XML.Element] ) +swapStack' state stack + = ( state { parentElements = stack } + , parentElements state + ) + +-- +pushElement :: XML.Element + -> XMLConverterState nsID extraState + -> XMLConverterState nsID extraState +pushElement e state = state { parentElements = e:(parentElements state) } + +-- | Pop the top element from the call stack, unless it is the last one. +popElement :: XMLConverterState nsID extraState + -> Maybe (XMLConverterState nsID extraState) +popElement state + | _:es@(_:_) <- parentElements state = Just $ state { parentElements = es } + | otherwise = Nothing + +-------------------------------------------------------------------------------- +-- Main type +-------------------------------------------------------------------------------- + +-- It might be a good idea to pack the converters in a GADT +-- Downside: data instead of type +-- Upside: 'Failure' could be made a parameter as well. + +-- +type XMLConverter nsID extraState input output + = ArrowState (XMLConverterState nsID extraState ) input output + +type FallibleXMLConverter nsID extraState input output + = XMLConverter nsID extraState input (Fallible output) + +-- +runConverter :: XMLConverter nsID extraState input output + -> XMLConverterState nsID extraState + -> input + -> output +runConverter converter state input = snd $ runArrowState converter (state,input) + +-- +runConverter'' :: (NameSpaceID nsID) + => XMLConverter nsID extraState (Fallible ()) output + -> extraState + -> XML.Element + -> output +runConverter'' converter extraState element = runConverter (readNSattributes >>> converter) (createStartState element extraState) () + +runConverter' :: (NameSpaceID nsID) + => FallibleXMLConverter nsID extraState () success + -> extraState + -> XML.Element + -> Fallible success +runConverter' converter extraState element = runConverter (readNSattributes >>? converter) (createStartState element extraState) () + +-- +runConverterF' :: FallibleXMLConverter nsID extraState x y + -> XMLConverterState nsID extraState + -> Fallible x -> Fallible y +runConverterF' a s e = runConverter (returnV e >>? a) s e + +-- +runConverterF :: (NameSpaceID nsID) + => FallibleXMLConverter nsID extraState XML.Element x + -> extraState + -> Fallible XML.Element -> Fallible x +runConverterF a s = either failWith + (\e -> runConverter a (createStartState e s) e) + +-- +getCurrentElement :: XMLConverter nsID extraState x XML.Element +getCurrentElement = extractFromState currentElement + +-- +getExtraState :: XMLConverter nsID extraState x extraState +getExtraState = extractFromState moreState + +-- +setExtraState :: XMLConverter nsID extraState extraState extraState +setExtraState = withState $ \state extra + -> (replaceExtraState extra state , extra) + + +-- | Lifts a function to the extra state. +modifyExtraState :: (extraState -> extraState) + -> XMLConverter nsID extraState x x +modifyExtraState = modifyState.fmap + + +-- | First sets the extra state to the new value. Then modifies the original +-- extra state with a converter that uses the new state. Finally, the +-- intermediate state is dropped and the extra state is lifted into the +-- state as it was at the beginning of the function. +-- As a result, exactly the extra state and nothing else is changed. +-- The resulting converter even behaves like an identity converter on the +-- value level. +-- +-- (The -ing form is meant to be mnemonic in a sequence of arrows as in +-- convertingExtraState () converter >>> doOtherStuff) +-- +convertingExtraState :: extraState' + -> FallibleXMLConverter nsID extraState' extraState extraState + -> FallibleXMLConverter nsID extraState x x +convertingExtraState v a = withSubStateF setVAsExtraState modifyWithA + where + setVAsExtraState = liftAsSuccess $ extractFromState id >>^ replaceExtraState v + modifyWithA = keepingTheValue (moreState ^>> a) + >>^ spreadChoice >>?§ flip replaceExtraState + +-- | First sets the extra state to the new value. Then produces a new +-- extra state with a converter that uses the new state. Finally, the +-- intermediate state is dropped and the extra state is lifted into the +-- state as it was at the beginning of the function. +-- As a result, exactly the extra state and nothing else is changed. +-- The resulting converter even behaves like an identity converter on the +-- value level. +-- +-- Aequivalent to +-- +-- > \v x a -> convertingExtraState v (returnV x >>> a) +-- +-- (The -ing form is meant to be mnemonic in a sequence of arrows as in +-- producingExtraState () () producer >>> doOtherStuff) +-- +producingExtraState :: extraState' + -> a + -> FallibleXMLConverter nsID extraState' a extraState + -> FallibleXMLConverter nsID extraState x x +producingExtraState v x a = convertingExtraState v (returnV x >>> a) + + +-------------------------------------------------------------------------------- +-- Work in namespaces +-------------------------------------------------------------------------------- + +-- | Arrow version of 'getIRI' +lookupNSiri :: (NameSpaceID nsID) + => nsID + -> XMLConverter nsID extraState x (Maybe NameSpaceIRI) +lookupNSiri nsID = extractFromState + $ \state -> getIRI nsID $ namespaceIRIs state + +-- +lookupNSprefix :: (NameSpaceID nsID) + => nsID + -> XMLConverter nsID extraState x (Maybe NameSpacePrefix) +lookupNSprefix nsID = extractFromState + $ \state -> M.lookup nsID $ namespacePrefixes state + +-- | Extracts namespace attributes from the current element and tries to +-- update the current mapping accordingly +readNSattributes :: (NameSpaceID nsID) + => FallibleXMLConverter nsID extraState x () +readNSattributes = fromState $ \state -> maybe (state, failEmpty ) + ( , succeedWith ()) + (extractNSAttrs state ) + where + extractNSAttrs :: (NameSpaceID nsID) + => XMLConverterState nsID extraState + -> Maybe (XMLConverterState nsID extraState) + extractNSAttrs startState + = foldl (\state d -> state >>= addNS d) + (Just startState) + nsAttribs + where nsAttribs = mapMaybe readNSattr (XML.elAttribs element) + element = currentElement startState + readNSattr (XML.Attr (XML.QName name _ (Just "xmlns")) iri) + = Just (name, iri) + readNSattr _ = Nothing + addNS (prefix, iri) state = fmap updateState + $ getNamespaceID iri + $ namespaceIRIs state + where updateState (iris,nsID) + = state { namespaceIRIs = iris + , namespacePrefixes = M.insert nsID prefix + $ namespacePrefixes state + } + +-------------------------------------------------------------------------------- +-- Common namespace accessors +-------------------------------------------------------------------------------- + +-- | Given a namespace id and an element name, creates a 'XML.QName' for +-- internal use +elemName :: (NameSpaceID nsID) + => nsID -> ElementName + -> XMLConverter nsID extraState x XML.QName +elemName nsID name = lookupNSiri nsID + &&& lookupNSprefix nsID + >>§ XML.QName name + +-- | Checks if a given element matches both a specified namespace id +-- and a specified element name +elemNameIs :: (NameSpaceID nsID) + => nsID -> ElementName + -> XMLConverter nsID extraState XML.Element Bool +elemNameIs nsID name = keepingTheValue (lookupNSiri nsID) >>§ hasThatName + where hasThatName e iri = let elName = XML.elName e + in XML.qName elName == name + && XML.qURI elName == iri + +-------------------------------------------------------------------------------- +-- General content +-------------------------------------------------------------------------------- + +-- +strContent :: XMLConverter nsID extraState x String +strContent = getCurrentElement + >>^ XML.strContent + +-- +elContent :: XMLConverter nsID extraState x [XML.Content] +elContent = getCurrentElement + >>^ XML.elContent + +-------------------------------------------------------------------------------- +-- Current element +-------------------------------------------------------------------------------- + +-- +currentElem :: XMLConverter nsID extraState x (XML.QName) +currentElem = getCurrentElement + >>^ XML.elName + +currentElemIs :: (NameSpaceID nsID) + => nsID -> ElementName + -> XMLConverter nsID extraState x Bool +currentElemIs nsID name = getCurrentElement + >>> elemNameIs nsID name + + + +{- +currentElemIs'' nsID name = ( (getCurrentElement >>^ XML.elName >>> + (XML.qName >>^ (&&).(== name) ) + ^&&&^ + (XML.qIRI >>^ (==) ) + ) >>§ (.) + ) &&& lookupNSiri nsID >>§ ($) +-} + +-- +expectElement :: (NameSpaceID nsID) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState x () +expectElement nsID name = currentElemIs nsID name + >>^ boolToChoice + +-------------------------------------------------------------------------------- +-- Chilren +-------------------------------------------------------------------------------- + +-- +elChildren :: XMLConverter nsID extraState x [XML.Element] +elChildren = getCurrentElement + >>^ XML.elChildren + +-- +findChildren :: (NameSpaceID nsID) + => nsID -> ElementName + -> XMLConverter nsID extraState x [XML.Element] +findChildren nsID name = elemName nsID name + &&& getCurrentElement + >>§ XML.findChildren + +-- +filterChildren :: (XML.Element -> Bool) + -> XMLConverter nsID extraState x [XML.Element] +filterChildren p = getCurrentElement + >>^ XML.filterChildren p + +-- +filterChildrenName :: (XML.QName -> Bool) + -> XMLConverter nsID extraState x [XML.Element] +filterChildrenName p = getCurrentElement + >>^ XML.filterChildrenName p + +-- +findChild' :: (NameSpaceID nsID) + => nsID + -> ElementName + -> XMLConverter nsID extraState x (Maybe XML.Element) +findChild' nsID name = elemName nsID name + &&& getCurrentElement + >>§ XML.findChild + +-- +findChild :: (NameSpaceID nsID) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState x XML.Element +findChild nsID name = findChild' nsID name + >>> maybeToChoice + +-- +filterChild' :: (XML.Element -> Bool) + -> XMLConverter nsID extraState x (Maybe XML.Element) +filterChild' p = getCurrentElement + >>^ XML.filterChild p + +-- +filterChild :: (XML.Element -> Bool) + -> FallibleXMLConverter nsID extraState x XML.Element +filterChild p = filterChild' p + >>> maybeToChoice + +-- +filterChildName' :: (XML.QName -> Bool) + -> XMLConverter nsID extraState x (Maybe XML.Element) +filterChildName' p = getCurrentElement + >>^ XML.filterChildName p + +-- +filterChildName :: (XML.QName -> Bool) + -> FallibleXMLConverter nsID extraState x XML.Element +filterChildName p = filterChildName' p + >>> maybeToChoice + + +-------------------------------------------------------------------------------- +-- Attributes +-------------------------------------------------------------------------------- + +-- +isSet :: (NameSpaceID nsID) + => nsID -> AttributeName + -> (Either Failure Bool) + -> FallibleXMLConverter nsID extraState x Bool +isSet nsID attrName deflt + = findAttr' nsID attrName + >>^ maybe deflt stringToBool + +-- +isSet' :: (NameSpaceID nsID) + => nsID -> AttributeName + -> XMLConverter nsID extraState x (Maybe Bool) +isSet' nsID attrName = findAttr' nsID attrName + >>^ (>>= stringToBool') + +isSetWithDefault :: (NameSpaceID nsID) + => nsID -> AttributeName + -> Bool + -> XMLConverter nsID extraState x Bool +isSetWithDefault nsID attrName def' + = isSet' nsID attrName + >>^ fromMaybe def' + +-- +hasAttrValueOf' :: (NameSpaceID nsID) + => nsID -> AttributeName + -> AttributeValue + -> XMLConverter nsID extraState x Bool +hasAttrValueOf' nsID attrName attrValue + = findAttr nsID attrName + >>> ( const False ^|||^ (==attrValue)) + +-- +failIfNotAttrValueOf :: (NameSpaceID nsID) + => nsID -> AttributeName + -> AttributeValue + -> FallibleXMLConverter nsID extraState x () +failIfNotAttrValueOf nsID attrName attrValue + = hasAttrValueOf' nsID attrName attrValue + >>^ boolToChoice + +-- | Is the value that is currently transported in the arrow the value of +-- the specified attribute? +isThatTheAttrValue :: (NameSpaceID nsID) + => nsID -> AttributeName + -> FallibleXMLConverter nsID extraState AttributeValue Bool +isThatTheAttrValue nsID attrName + = keepingTheValue + (findAttr nsID attrName) + >>§ right.(==) + +-- | Lookup value in a dictionary, fail if no attribute found or value +-- not in dictionary +searchAttrIn :: (NameSpaceID nsID) + => nsID -> AttributeName + -> [(AttributeValue,a)] + -> FallibleXMLConverter nsID extraState x a +searchAttrIn nsID attrName dict + = findAttr nsID attrName + >>?^? maybeToChoice.(`lookup` dict ) + + +-- | Lookup value in a dictionary. Fail if no attribute found. If value not in +-- dictionary, return default value +searchAttrWith :: (NameSpaceID nsID) + => nsID -> AttributeName + -> a + -> [(AttributeValue,a)] + -> FallibleXMLConverter nsID extraState x a +searchAttrWith nsID attrName defV dict + = findAttr nsID attrName + >>?^ (fromMaybe defV).(`lookup` dict ) + +-- | Lookup value in a dictionary. If attribute or value not found, +-- return default value +searchAttr :: (NameSpaceID nsID) + => nsID -> AttributeName + -> a + -> [(AttributeValue,a)] + -> XMLConverter nsID extraState x a +searchAttr nsID attrName defV dict + = searchAttrIn nsID attrName dict + >>> const defV ^|||^ id + +-- | Read a 'Lookupable' attribute. Fail if no match. +lookupAttr :: (NameSpaceID nsID, Lookupable a) + => nsID -> AttributeName + -> FallibleXMLConverter nsID extraState x a +lookupAttr nsID attrName = lookupAttr' nsID attrName + >>^ maybeToChoice + + +-- | Read a 'Lookupable' attribute. Return the result as a 'Maybe'. +lookupAttr' :: (NameSpaceID nsID, Lookupable a) + => nsID -> AttributeName + -> XMLConverter nsID extraState x (Maybe a) +lookupAttr' nsID attrName + = findAttr' nsID attrName + >>^ (>>= readLookupable) + +-- | Read a 'Lookupable' attribute with explicit default +lookupAttrWithDefault :: (NameSpaceID nsID, Lookupable a) + => nsID -> AttributeName + -> a + -> XMLConverter nsID extraState x a +lookupAttrWithDefault nsID attrName deflt + = lookupAttr' nsID attrName + >>^ fromMaybe deflt + +-- | Read a 'Lookupable' attribute with implicit default +lookupDefaultingAttr :: (NameSpaceID nsID, Lookupable a, Default a) + => nsID -> AttributeName + -> XMLConverter nsID extraState x a +lookupDefaultingAttr nsID attrName + = lookupAttrWithDefault nsID attrName def + +-- | Return value as a (Maybe String) +findAttr' :: (NameSpaceID nsID) + => nsID -> AttributeName + -> XMLConverter nsID extraState x (Maybe AttributeValue) +findAttr' nsID attrName = elemName nsID attrName + &&& getCurrentElement + >>§ XML.findAttr + +-- | Return value as string or fail +findAttr :: (NameSpaceID nsID) + => nsID -> AttributeName + -> FallibleXMLConverter nsID extraState x AttributeValue +findAttr nsID attrName = findAttr' nsID attrName + >>> maybeToChoice + +-- | Return value as string or return provided default value +findAttrWithDefault :: (NameSpaceID nsID) + => nsID -> AttributeName + -> AttributeValue + -> XMLConverter nsID extraState x AttributeValue +findAttrWithDefault nsID attrName deflt + = findAttr' nsID attrName + >>^ fromMaybe deflt + +-- | Read and return value or fail +readAttr :: (NameSpaceID nsID, Read attrValue) + => nsID -> AttributeName + -> FallibleXMLConverter nsID extraState x attrValue +readAttr nsID attrName = readAttr' nsID attrName + >>> maybeToChoice + +-- | Read and return value or return Nothing +readAttr' :: (NameSpaceID nsID, Read attrValue) + => nsID -> AttributeName + -> XMLConverter nsID extraState x (Maybe attrValue) +readAttr' nsID attrName = findAttr' nsID attrName + >>^ (>>= tryToRead) + +-- | Read and return value or return provided default value +readAttrWithDefault :: (NameSpaceID nsID, Read attrValue) + => nsID -> AttributeName + -> attrValue + -> XMLConverter nsID extraState x attrValue +readAttrWithDefault nsID attrName deflt + = findAttr' nsID attrName + >>^ (>>= tryToRead) + >>^ fromMaybe deflt + +-- | Read and return value or return default value from 'Default' instance +getAttr :: (NameSpaceID nsID, Read attrValue, Default attrValue) + => nsID -> AttributeName + -> XMLConverter nsID extraState x attrValue +getAttr nsID attrName = readAttrWithDefault nsID attrName def + +-------------------------------------------------------------------------------- +-- Movements +-------------------------------------------------------------------------------- + +-- +jumpThere :: XMLConverter nsID extraState XML.Element XML.Element +jumpThere = withState (\state element + -> ( pushElement element state , element ) + ) + +-- +swapStack :: XMLConverter nsID extraState [XML.Element] [XML.Element] +swapStack = withState swapStack' + +-- +jumpBack :: FallibleXMLConverter nsID extraState _x _x +jumpBack = tryModifyState (popElement >>> maybeToChoice) + +-- | Support function for "procedural" converters: jump to an element, execute +-- a converter, jump back. +-- This version is safer than 'executeThere', because it does not rely on the +-- internal stack. As a result, the converter can not move around in arbitrary +-- ways. The downside is of course that some of the environment is not +-- accessible to the converter. +switchingTheStack :: XMLConverter nsID moreState a b + -> XMLConverter nsID moreState (a, XML.Element) b +switchingTheStack a = second ( (:[]) ^>> swapStack ) + >>> first a + >>> second swapStack + >>^ fst + +-- | Support function for "procedural" converters: jumps to an element, executes +-- a converter, jumps back. +-- Make sure that the converter is well-behaved; that is it should +-- return to the exact position it started from in /every possible path/ of +-- execution, even if it "fails". If it does not, you may encounter +-- strange bugs. If you are not sure about the behaviour or want to use +-- shortcuts, you can often use 'switchingTheStack' instead. +executeThere :: FallibleXMLConverter nsID moreState a b + -> FallibleXMLConverter nsID moreState (a, XML.Element) b +executeThere a = second jumpThere + >>> fst + ^>> a + >>> jumpBack -- >>? jumpBack would not ensure the jump. + >>^ collapseEither + +-- | Do something in a sub-element, tnen come back +executeIn :: (NameSpaceID nsID) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState f s + -> FallibleXMLConverter nsID extraState f s +executeIn nsID name a = keepingTheValue + (findChild nsID name) + >>> ignoringState liftFailure + >>? switchingTheStack a + where liftFailure (_, (Left f)) = Left f + liftFailure (x, (Right e)) = Right (x, e) + +-------------------------------------------------------------------------------- +-- Iterating over children +-------------------------------------------------------------------------------- + +-- Helper converter to prepare different types of iterations. +-- It lifts the children (of a certain type) of the current element +-- into the value level and pairs each one with the current input value. +prepareIteration :: (NameSpaceID nsID) + => nsID -> ElementName + -> XMLConverter nsID extraState b [(b, XML.Element)] +prepareIteration nsID name = keepingTheValue + (findChildren nsID name) + >>§ distributeValue + +-- | Applies a converter to every child element of a specific type. +-- Collects results in a 'Monoid'. +-- Fails completely if any conversion fails. +collectEvery :: (NameSpaceID nsID, Monoid m) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState a m + -> FallibleXMLConverter nsID extraState a m +collectEvery nsID name a = prepareIteration nsID name + >>> foldS' (switchingTheStack a) + +-- +withEveryL :: (NameSpaceID nsID) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState a b + -> FallibleXMLConverter nsID extraState a [b] +withEveryL = withEvery + +-- | Applies a converter to every child element of a specific type. +-- Collects results in a 'MonadPlus'. +-- Fails completely if any conversion fails. +withEvery :: (NameSpaceID nsID, MonadPlus m) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState a b + -> FallibleXMLConverter nsID extraState a (m b) +withEvery nsID name a = prepareIteration nsID name + >>> iterateS' (switchingTheStack a) + +-- | Applies a converter to every child element of a specific type. +-- Collects all successful results in a list. +tryAll :: (NameSpaceID nsID) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState b a + -> XMLConverter nsID extraState b [a] +tryAll nsID name a = prepareIteration nsID name + >>> iterateS (switchingTheStack a) + >>^ collectRights + +-- | Applies a converter to every child element of a specific type. +-- Collects all successful results. +tryAll' :: (NameSpaceID nsID, F.Foldable c, MonadPlus c) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState b a + -> XMLConverter nsID extraState b (c a) +tryAll' nsID name a = prepareIteration nsID name + >>> iterateS (switchingTheStack a) + >>^ collectRightsF + +-------------------------------------------------------------------------------- +-- Matching children +-------------------------------------------------------------------------------- + +type IdXMLConverter nsID moreState x + = XMLConverter nsID moreState x x + +type MaybeEConverter nsID moreState x + = Maybe (IdXMLConverter nsID moreState (x, XML.Element)) + +-- Chainable converter that helps deciding which converter to actually use. +type ElementMatchConverter nsID extraState x + = IdXMLConverter nsID + extraState + (MaybeEConverter nsID extraState x, XML.Element) + +type MaybeCConverter nsID moreState x + = Maybe (IdXMLConverter nsID moreState (x, XML.Content)) + +-- Chainable converter that helps deciding which converter to actually use. +type ContentMatchConverter nsID extraState x + = IdXMLConverter nsID + extraState + (MaybeCConverter nsID extraState x, XML.Content) + +-- Helper function: The @c@ is actually a converter that is to be selected by +-- matching XML elements to the first two parameters. +-- The fold used to match elements however is very simple, so to use it, +-- this function wraps the converter in another converter that unifies +-- the accumulator. Think of a lot of converters with the resulting type +-- chained together. The accumulator not only transports the element +-- unchanged to the next matcher, it also does the actual selecting by +-- combining the intermediate results with '(<|>)'. +makeMatcherE :: (NameSpaceID nsID) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState a a + -> ElementMatchConverter nsID extraState a +makeMatcherE nsID name c = ( second ( + elemNameIs nsID name + >>^ bool Nothing (Just tryC) + ) + >>§ (<|>) + ) &&&^ snd + where tryC = (fst ^&&& executeThere c >>§ recover) &&&^ snd + +-- Helper function: The @c@ is actually a converter that is to be selected by +-- matching XML content to the first two parameters. +-- The fold used to match elements however is very simple, so to use it, +-- this function wraps the converter in another converter that unifies +-- the accumulator. Think of a lot of converters with the resulting type +-- chained together. The accumulator not only transports the element +-- unchanged to the next matcher, it also does the actual selecting by +-- combining the intermediate results with '(<|>)'. +makeMatcherC :: (NameSpaceID nsID) + => nsID -> ElementName + -> FallibleXMLConverter nsID extraState a a + -> ContentMatchConverter nsID extraState a +makeMatcherC nsID name c = ( second ( contentToElem + >>> returnV Nothing + ||| ( elemNameIs nsID name + >>^ bool Nothing (Just cWithJump) + ) + ) + >>§ (<|>) + ) &&&^ snd + where cWithJump = ( fst + ^&&& ( second contentToElem + >>> spreadChoice + ^>>? executeThere c + ) + >>§ recover) + &&&^ snd + contentToElem :: FallibleXMLConverter nsID extraState XML.Content XML.Element + contentToElem = arr $ \e -> case e of + XML.Elem e' -> succeedWith e' + _ -> failEmpty + +-- Creates and chains a bunch of matchers +prepareMatchersE :: (NameSpaceID nsID) + => [(nsID, ElementName, FallibleXMLConverter nsID extraState x x)] + -> ElementMatchConverter nsID extraState x +--prepareMatchersE = foldSs . (map $ uncurry3 makeMatcherE) +prepareMatchersE = reverseComposition . (map $ uncurry3 makeMatcherE) + +-- Creates and chains a bunch of matchers +prepareMatchersC :: (NameSpaceID nsID) + => [(nsID, ElementName, FallibleXMLConverter nsID extraState x x)] + -> ContentMatchConverter nsID extraState x +--prepareMatchersC = foldSs . (map $ uncurry3 makeMatcherC) +prepareMatchersC = reverseComposition . (map $ uncurry3 makeMatcherC) + +-- | Takes a list of element-data - converter groups and +-- * Finds all children of the current element +-- * Matches each group to each child in order (at most one group per child) +-- * Filters non-matched children +-- * Chains all found converters in child-order +-- * Applies the chain to the input element +matchChildren :: (NameSpaceID nsID) + => [(nsID, ElementName, FallibleXMLConverter nsID extraState a a)] + -> XMLConverter nsID extraState a a +matchChildren lookups = let matcher = prepareMatchersE lookups + in keepingTheValue ( + elChildren + >>> map (Nothing,) + ^>> iterateSL matcher + >>^ catMaybes.map (\(m,e) -> fmap (swallowElem e) m) + -- >>> foldSs + >>> reverseComposition + ) + >>> swap + ^>> app + where + -- let the converter swallow the element and drop the element + -- in the return value + swallowElem element converter = (,element) ^>> converter >>^ fst + +-- +matchContent'' :: (NameSpaceID nsID) + => [(nsID, ElementName, FallibleXMLConverter nsID extraState a a)] + -> XMLConverter nsID extraState a a +matchContent'' lookups = let matcher = prepareMatchersC lookups + in keepingTheValue ( + elContent + >>> map (Nothing,) + ^>> iterateSL matcher + >>^ catMaybes.map (\(m,c) -> fmap (swallowContent c) m) + -- >>> foldSs + >>> reverseComposition + ) + >>> swap + ^>> app + where + -- let the converter swallow the content and drop the content + -- in the return value + swallowContent content converter = (,content) ^>> converter >>^ fst + + +-- | Takes a list of element-data - converter groups and +-- * Finds all content of the current element +-- * Matches each group to each piece of content in order +-- (at most one group per piece of content) +-- * Filters non-matched content +-- * Chains all found converters in content-order +-- * Applies the chain to the input element +matchContent' :: (NameSpaceID nsID) + => [(nsID, ElementName, FallibleXMLConverter nsID extraState a a)] + -> XMLConverter nsID extraState a a +matchContent' lookups = matchContent lookups (arr fst) + +-- | Takes a list of element-data - converter groups and +-- * Finds all content of the current element +-- * Matches each group to each piece of content in order +-- (at most one group per piece of content) +-- * Adds a default converter for all non-matched content +-- * Chains all found converters in content-order +-- * Applies the chain to the input element +matchContent :: (NameSpaceID nsID) + => [(nsID, ElementName, FallibleXMLConverter nsID extraState a a)] + -> XMLConverter nsID extraState (a,XML.Content) a + -> XMLConverter nsID extraState a a +matchContent lookups fallback + = let matcher = prepareMatchersC lookups + in keepingTheValue ( + elContent + >>> map (Nothing,) + ^>> iterateSL matcher + >>^ map swallowOrFallback + -- >>> foldSs + >>> reverseComposition + ) + >>> swap + ^>> app + where + -- let the converter swallow the content and drop the content + -- in the return value + swallowOrFallback (Just converter,content) = (,content) ^>> converter >>^ fst + swallowOrFallback (Nothing ,content) = (,content) ^>> fallback + +-------------------------------------------------------------------------------- +-- Internals +-------------------------------------------------------------------------------- + +stringToBool :: (Monoid failure) => String -> Either failure Bool +stringToBool val -- stringToBool' val >>> maybeToChoice + | val `elem` trueValues = succeedWith True + | val `elem` falseValues = succeedWith False + | otherwise = failEmpty + where trueValues = ["true" ,"on" ,"1"] + falseValues = ["false","off","0"] + +stringToBool' :: String -> Maybe Bool +stringToBool' val | val `elem` trueValues = Just True + | val `elem` falseValues = Just False + | otherwise = Nothing + where trueValues = ["true" ,"on" ,"1"] + falseValues = ["false","off","0"] + + +distributeValue :: a -> [b] -> [(a,b)] +distributeValue = map.(,) + +-------------------------------------------------------------------------------- + +{- +NOTES +It might be a good idea to refactor the namespace stuff. +E.g.: if a namespace constructor took a string as a parameter, things like +> a ?>/< (NsText,"body") +would be nicer. +Together with a rename and some trickery, something like +> |< NsText "body" >< NsText "p" ?> a | +might even be possible. + +Some day, XML.Light should be replaced by something better. +While doing that, it might be useful to replace String as the type of element +names with something else, too. (Of course with OverloadedStrings). +While doing that, maybe the types can be created in a way that something like +> NsText:"body" +could be used. Overloading (:) does not sounds like the best idea, but if the +element name type was a list, this might be possible. +Of course that would be a bit hackish, so the "right" way would probably be +something like +> InNS NsText "body" +but isn't that a bit boring? ;) +-} diff --git a/src/Text/Pandoc/Readers/Odt/Namespaces.hs b/src/Text/Pandoc/Readers/Odt/Namespaces.hs new file mode 100644 index 000000000..e28056814 --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/Namespaces.hs @@ -0,0 +1,110 @@ +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Reader.Odt.Namespaces + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +Namespaces used in odt files. +-} + +module Text.Pandoc.Readers.Odt.Namespaces ( Namespace (..) + ) where + +import Data.List ( isPrefixOf ) +import Data.Maybe ( fromMaybe, listToMaybe ) +import qualified Data.Map as M ( empty, insert ) + +import Text.Pandoc.Readers.Odt.Generic.Namespaces + + +instance NameSpaceID Namespace where + + getInitialIRImap = nsIDmap + + getNamespaceID "" m = Just(m, NsXML) + getNamespaceID iri m = asPair $ fromMaybe (NsOther iri) (findID iri) + where asPair nsID = Just (M.insert nsID iri m, nsID) + + +findID :: NameSpaceIRI -> Maybe Namespace +findID iri = listToMaybe [nsID | (iri',~nsID) <- nsIDs, iri' `isPrefixOf` iri] + +nsIDmap :: NameSpaceIRIs Namespace +nsIDmap = foldr (uncurry $ flip M.insert) M.empty nsIDs + +data Namespace = -- Open Document core + NsOffice | NsStyle | NsText | NsTable | NsForm + | NsDraw | Ns3D | NsAnim | NsChart | NsConfig + | NsDB | NsMeta | NsNumber | NsScript | NsManifest + | NsPresentation + -- Metadata + | NsODF + -- Compatible elements + | NsXSL_FO | NsSVG | NsSmil + -- External standards + | NsMathML | NsXForms | NsXLink | NsXHtml | NsGRDDL + | NsDublinCore + -- Metadata manifest + | NsPKG + -- Others + | NsOpenFormula + -- Core XML (basically only for the 'id'-attribute) + | NsXML + -- Fallback + | NsOther String + deriving ( Eq, Ord, Show ) + +-- | Not the actual iri's, but large prefixes of them - this way there are +-- less versioning problems and the like. +nsIDs :: [(String,Namespace)] +nsIDs = [ + ("urn:oasis:names:tc:opendocument:xmlns:animation" , NsAnim ), + ("urn:oasis:names:tc:opendocument:xmlns:chart" , NsChart ), + ("urn:oasis:names:tc:opendocument:xmlns:config" , NsConfig ), + ("urn:oasis:names:tc:opendocument:xmlns:database" , NsDB ), + ("urn:oasis:names:tc:opendocument:xmlns:dr3d" , Ns3D ), + ("urn:oasis:names:tc:opendocument:xmlns:drawing" , NsDraw ), + ("urn:oasis:names:tc:opendocument:xmlns:form" , NsForm ), + ("urn:oasis:names:tc:opendocument:xmlns:manifest" , NsManifest ), + ("urn:oasis:names:tc:opendocument:xmlns:meta" , NsMeta ), + ("urn:oasis:names:tc:opendocument:xmlns:datastyle" , NsNumber ), + ("urn:oasis:names:tc:opendocument:xmlns:of" , NsOpenFormula ), + ("urn:oasis:names:tc:opendocument:xmlns:office:1.0" , NsOffice ), + ("urn:oasis:names:tc:opendocument:xmlns:presentation" , NsPresentation ), + ("urn:oasis:names:tc:opendocument:xmlns:script" , NsScript ), + ("urn:oasis:names:tc:opendocument:xmlns:style" , NsStyle ), + ("urn:oasis:names:tc:opendocument:xmlns:table" , NsTable ), + ("urn:oasis:names:tc:opendocument:xmlns:text" , NsText ), + ("urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible", NsXSL_FO ), + ("urn:oasis:names:tc:opendocument:xmlns:smil-compatible" , NsSmil ), + ("urn:oasis:names:tc:opendocument:xmlns:svg-compatible" , NsSVG ), + ("http://docs.oasis-open.org/ns/office/1.2/meta/odf" , NsODF ), + ("http://docs.oasis-open.org/ns/office/1.2/meta/pkg" , NsPKG ), + ("http://purl.org/dc/elements" , NsDublinCore ), + ("http://www.w3.org/2003/g/data-view" , NsGRDDL ), + ("http://www.w3.org/1998/Math/MathML" , NsMathML ), + ("http://www.w3.org/1999/xhtml" , NsXHtml ), + ("http://www.w3.org/2002/xforms" , NsXForms ), + ("http://www.w3.org/1999/xlink" , NsXLink ) + ] \ No newline at end of file diff --git a/src/Text/Pandoc/Readers/Odt/StyleReader.hs b/src/Text/Pandoc/Readers/Odt/StyleReader.hs new file mode 100644 index 000000000..1cf87cc59 --- /dev/null +++ b/src/Text/Pandoc/Readers/Odt/StyleReader.hs @@ -0,0 +1,737 @@ +{-# LANGUAGE TupleSections #-} +{-# LANGUAGE PatternGuards #-} +{-# LANGUAGE ViewPatterns #-} +{-# LANGUAGE RecordWildCards #-} +{-# LANGUAGE Arrows #-} + +{- +Copyright (C) 2015 Martin Linnemann + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +-} + +{- | + Module : Text.Pandoc.Readers.Odt.StyleReader + Copyright : Copyright (C) 2015 Martin Linnemann + License : GNU GPL, version 2 or above + + Maintainer : Martin Linnemann + Stability : alpha + Portability : portable + +Reader for the style information in an odt document. +-} + +module Text.Pandoc.Readers.Odt.StyleReader +( Style (..) +, StyleName +, StyleFamily (..) +, Styles (..) +, StyleProperties (..) +, TextProperties (..) +, ParaProperties (..) +, VerticalTextPosition (..) +, ListItemNumberFormat (..) +, ListLevel +, ListStyle (..) +, ListLevelStyle (..) +, ListLevelType (..) +, LengthOrPercent (..) +, lookupStyle +, getTextProperty +, getTextProperty' +, getParaProperty +, getListStyle +, getListLevelStyle +, getStyleFamily +, lookupDefaultStyle +, lookupDefaultStyle' +, lookupListStyleByName +, getPropertyChain +, textPropertyChain +, stylePropertyChain +, stylePropertyChain' +, getStylePropertyChain +, extendedStylePropertyChain +, extendedStylePropertyChain' +, liftStyles +, readStylesAt +) where + +import Control.Arrow +import Control.Applicative hiding ( liftA, liftA2, liftA3 ) + +import qualified Data.Foldable as F +import qualified Data.Map as M +import qualified Data.Set as S +import Data.List ( unfoldr ) +import Data.Default +import Data.Monoid +import Data.Maybe + +import qualified Text.XML.Light as XML + +import Text.Pandoc.Readers.Odt.Arrows.State +import Text.Pandoc.Readers.Odt.Arrows.Utils + +import Text.Pandoc.Readers.Odt.Generic.Utils +import qualified Text.Pandoc.Readers.Odt.Generic.SetMap as SM +import Text.Pandoc.Readers.Odt.Generic.Fallible +import Text.Pandoc.Readers.Odt.Generic.XMLConverter + +import Text.Pandoc.Readers.Odt.Namespaces +import Text.Pandoc.Readers.Odt.Base + + +readStylesAt :: XML.Element -> Fallible Styles +readStylesAt e = runConverter' readAllStyles mempty e + +-------------------------------------------------------------------------------- +-- Reader for font declarations and font pitches +-------------------------------------------------------------------------------- + +-- Pandoc has no support for different font pitches. Yet knowing them can be +-- very helpful in cases where Pandoc has more semantics than OpenDocument. +-- In these cases, the pitch can help deciding as what to define a block of +-- text. So let's start with a type for font pitches: + +data FontPitch = PitchVariable | PitchFixed + deriving ( Eq, Show ) + +instance Lookupable FontPitch where + lookupTable = [ ("variable" , PitchVariable) + , ("fixed" , PitchFixed ) + ] + +instance Default FontPitch where + def = PitchVariable + +-- The font pitch can be specifed in a style directly. Normally, however, +-- it is defined in the font. That is also the specs' recommendation. +-- +-- Thus, we want + +type FontFaceName = String + +type FontPitches = M.Map FontFaceName FontPitch + +-- To get there, the fonts have to be read and the pitches extracted. +-- But the resulting map are only needed at one later place, so it should not be +-- transported on the value level, especially as we already use a state arrow. +-- So instead, the resulting map is lifted into the state of the reader. +-- (An alternative might be ImplicitParams, but again, we already have a state.) +-- +-- So the main style readers will have the types +type StyleReader a b = XMLReader FontPitches a b +-- and +type StyleReaderSafe a b = XMLReaderSafe FontPitches a b +-- respectively. +-- +-- But before we can work with these, we need to define the reader that reads +-- the fonts: + +-- | A reader for font pitches +fontPitchReader :: XMLReader _s _x FontPitches +fontPitchReader = executeIn NsOffice "font-face-decls" ( + ( withEveryL NsStyle "font-face" $ liftAsSuccess ( + findAttr' NsStyle "name" + &&& + lookupDefaultingAttr NsStyle "font-pitch" + ) + ) + >>?^ ( M.fromList . (foldl accumLegalPitches []) ) + ) + where accumLegalPitches ls (Nothing,_) = ls + accumLegalPitches ls (Just n,p) = (n,p):ls + + +-- | A wrapper around the font pitch reader that lifts the result into the +-- state. +readFontPitches :: StyleReader x x +readFontPitches = producingExtraState () () fontPitchReader + + +-- | Looking up a pitch in the state of the arrow. +-- +-- The function does the following: +-- * Look for the font pitch in an attribute. +-- * If that fails, look for the font name, look up the font in the state +-- and use the pitch from there. +-- * Return the result in a Maybe +-- +findPitch :: XMLReaderSafe FontPitches _x (Maybe FontPitch) +findPitch = ( lookupAttr NsStyle "font-pitch" + `ifFailedDo` findAttr NsStyle "font-name" + >>? ( keepingTheValue getExtraState + >>§ M.lookup + >>^ maybeToChoice + ) + ) + >>> choiceToMaybe + +-------------------------------------------------------------------------------- +-- Definitions of main data +-------------------------------------------------------------------------------- + +type StyleName = String + +-- | There are two types of styles: named styles with a style family and an +-- optional style parent, and default styles for each style family, +-- defining default style properties +data Styles = Styles + { stylesByName :: M.Map StyleName Style + , listStylesByName :: M.Map StyleName ListStyle + , defaultStyleMap :: M.Map StyleFamily StyleProperties + } + deriving ( Show ) + +-- Styles from a monoid under union +instance Monoid Styles where + mempty = Styles M.empty M.empty M.empty + mappend (Styles sBn1 dSm1 lsBn1) + (Styles sBn2 dSm2 lsBn2) + = Styles (M.union sBn1 sBn2) + (M.union dSm1 dSm2) + (M.union lsBn1 lsBn2) + +-- Not all families from the specifications are implemented, only those we need. +-- But there are none that are not mentioned here. +data StyleFamily = FaText | FaParagraph +-- | FaTable | FaTableCell | FaTableColumn | FaTableRow +-- | FaGraphic | FaDrawing | FaChart +-- | FaPresentation +-- | FaRuby + deriving ( Eq, Ord, Show ) + +instance Lookupable StyleFamily where + lookupTable = [ ( "text" , FaText ) + , ( "paragraph" , FaParagraph ) +-- , ( "table" , FaTable ) +-- , ( "table-cell" , FaTableCell ) +-- , ( "table-column" , FaTableColumn ) +-- , ( "table-row" , FaTableRow ) +-- , ( "graphic" , FaGraphic ) +-- , ( "drawing-page" , FaDrawing ) +-- , ( "chart" , FaChart ) +-- , ( "presentation" , FaPresentation ) +-- , ( "ruby" , FaRuby ) + ] + +-- | A named style +data Style = Style { styleFamily :: Maybe StyleFamily + , styleParentName :: Maybe StyleName + , listStyle :: Maybe StyleName + , styleProperties :: StyleProperties + } + deriving ( Eq, Show ) + +data StyleProperties = SProps { textProperties :: Maybe TextProperties + , paraProperties :: Maybe ParaProperties +-- , tableColProperties :: Maybe TColProperties +-- , tableRowProperties :: Maybe TRowProperties +-- , tableCellProperties :: Maybe TCellProperties +-- , tableProperties :: Maybe TableProperties +-- , graphicProperties :: Maybe GraphProperties + } + deriving ( Eq, Show ) + +instance Default StyleProperties where + def = SProps { textProperties = Just def + , paraProperties = Just def + } + +data TextProperties = PropT { isEmphasised :: Bool + , isStrong :: Bool + , pitch :: Maybe FontPitch + , verticalPosition :: VerticalTextPosition + , underline :: Maybe UnderlineMode + , strikethrough :: Maybe UnderlineMode + } + deriving ( Eq, Show ) + +instance Default TextProperties where + def = PropT { isEmphasised = False + , isStrong = False + , pitch = Just def + , verticalPosition = def + , underline = Nothing + , strikethrough = Nothing + } + +data ParaProperties = PropP { paraNumbering :: ParaNumbering + , indentation :: LengthOrPercent + , margin_left :: LengthOrPercent + } + deriving ( Eq, Show ) + +instance Default ParaProperties where + def = PropP { paraNumbering = NumberingNone + , indentation = def + , margin_left = def + } + +---- +-- All the little data types that make up the properties +---- + +data VerticalTextPosition = VPosNormal | VPosSuper | VPosSub + deriving ( Eq, Show ) + +instance Default VerticalTextPosition where + def = VPosNormal + +instance Read VerticalTextPosition where + readsPrec _ s = [ (VPosSub , s') | ("sub" , s') <- lexS ] + ++ [ (VPosSuper , s') | ("super" , s') <- lexS ] + ++ [ (signumToVPos n , s') | ( n , s') <- readPercent s ] + where + lexS = lex s + signumToVPos n | n < 0 = VPosSub + | n > 0 = VPosSuper + | otherwise = VPosNormal + +data UnderlineMode = UnderlineModeNormal | UnderlineModeSkipWhitespace + deriving ( Eq, Show ) + +instance Lookupable UnderlineMode where + lookupTable = [ ( "continuous" , UnderlineModeNormal ) + , ( "skip-white-space" , UnderlineModeSkipWhitespace ) + ] + + +data ParaNumbering = NumberingNone | NumberingKeep | NumberingRestart Int + deriving ( Eq, Show ) + +data LengthOrPercent = LengthValueMM Int | PercentValue Int + deriving ( Eq, Show ) + +instance Default LengthOrPercent where + def = LengthValueMM 0 + +instance Read LengthOrPercent where + readsPrec _ s = + [ (PercentValue percent , s' ) | (percent , s' ) <- readPercent s] + ++ [ (LengthValueMM lengthMM , s'') | (length' , s' ) <- reads s + , (unit , s'') <- reads s' + , let lengthMM = estimateInMillimeter + length' unit + ] + +data XslUnit = XslUnitMM | XslUnitCM + | XslUnitInch + | XslUnitPoints | XslUnitPica + | XslUnitPixel + | XslUnitEM + +instance Show XslUnit where + show XslUnitMM = "mm" + show XslUnitCM = "cm" + show XslUnitInch = "in" + show XslUnitPoints = "pt" + show XslUnitPica = "pc" + show XslUnitPixel = "px" + show XslUnitEM = "em" + +instance Read XslUnit where + readsPrec _ "mm" = [(XslUnitMM , "")] + readsPrec _ "cm" = [(XslUnitCM , "")] + readsPrec _ "in" = [(XslUnitInch , "")] + readsPrec _ "pt" = [(XslUnitPoints , "")] + readsPrec _ "pc" = [(XslUnitPica , "")] + readsPrec _ "px" = [(XslUnitPixel , "")] + readsPrec _ "em" = [(XslUnitEM , "")] + readsPrec _ _ = [] + +-- | Rough conversion of measures into millimeters. +-- Pixels and em's are actually implemetation dependant/relative measures, +-- so I could not really easily calculate anything exact here even if I wanted. +-- But I do not care about exactness right now, as I only use measures +-- to determine if a paragraph is "indented" or not. +estimateInMillimeter :: Int -> XslUnit -> Int +estimateInMillimeter n XslUnitMM = n +estimateInMillimeter n XslUnitCM = n * 10 +estimateInMillimeter n XslUnitInch = n * 25 -- * 25.4 +estimateInMillimeter n XslUnitPoints = n `div` 3 -- * 1/72 * 25.4 +estimateInMillimeter n XslUnitPica = n * 4 -- * 12 * 1/72 * 25.4 +estimateInMillimeter n XslUnitPixel = n `div`3 -- * 1/72 * 25.4 +estimateInMillimeter n XslUnitEM = n * 7 -- * 16 * 1/72 * 25.4 + + +---- +-- List styles +---- + +type ListLevel = Int + +newtype ListStyle = ListStyle { levelStyles :: M.Map ListLevel ListLevelStyle + } + deriving ( Eq, Show ) + +-- +getListLevelStyle :: ListLevel -> ListStyle -> Maybe ListLevelStyle +getListLevelStyle level ListStyle{..} = + let (lower , exactHit , _) = M.splitLookup level levelStyles + in exactHit <|> fmap fst (M.maxView lower) + -- findBy (`M.lookup` levelStyles) [level, (level-1) .. 1] + -- ^ simpler, but in general less efficient + +data ListLevelStyle = ListLevelStyle { listLevelType :: ListLevelType + , listItemPrefix :: Maybe String + , listItemSuffix :: Maybe String + , listItemFormat :: ListItemNumberFormat + } + deriving ( Eq, Ord ) + +instance Show ListLevelStyle where + show ListLevelStyle{..} = "" + where maybeToString = fromMaybe "" + +data ListLevelType = LltBullet | LltImage | LltNumbered + deriving ( Eq, Ord, Show ) + +data ListItemNumberFormat = LinfNone + | LinfNumber + | LinfRomanLC | LinfRomanUC + | LinfAlphaLC | LinfAlphaUC + | LinfString String + deriving ( Eq, Ord ) + +instance Show ListItemNumberFormat where + show LinfNone = "" + show LinfNumber = "1" + show LinfRomanLC = "i" + show LinfRomanUC = "I" + show LinfAlphaLC = "a" + show LinfAlphaUC = "A" + show (LinfString s) = s + +instance Default ListItemNumberFormat where + def = LinfNone + +instance Read ListItemNumberFormat where + readsPrec _ "" = [(LinfNone , "")] + readsPrec _ "1" = [(LinfNumber , "")] + readsPrec _ "i" = [(LinfRomanLC , "")] + readsPrec _ "I" = [(LinfRomanUC , "")] + readsPrec _ "a" = [(LinfAlphaLC , "")] + readsPrec _ "A" = [(LinfAlphaUC , "")] + readsPrec _ s = [(LinfString s , "")] + +-------------------------------------------------------------------------------- +-- Readers +-- +-- ...it seems like a whole lot of this should be automatically deriveable +-- or at least moveable into a class. Most of this is data concealed in +-- code. +-------------------------------------------------------------------------------- + +-- +readAllStyles :: StyleReader _x Styles +readAllStyles = ( readFontPitches + >>?! ( readAutomaticStyles + &&& readStyles )) + >>?§? chooseMax + -- all top elements are always on the same hierarchy level + +-- +readStyles :: StyleReader _x Styles +readStyles = executeIn NsOffice "styles" $ liftAsSuccess + $ liftA3 Styles + ( tryAll NsStyle "style" readStyle >>^ M.fromList ) + ( tryAll NsText "list-style" readListStyle >>^ M.fromList ) + ( tryAll NsStyle "default-style" readDefaultStyle >>^ M.fromList ) + +-- +readAutomaticStyles :: StyleReader _x Styles +readAutomaticStyles = executeIn NsOffice "automatic-styles" $ liftAsSuccess + $ liftA3 Styles + ( tryAll NsStyle "style" readStyle >>^ M.fromList ) + ( tryAll NsText "list-style" readListStyle >>^ M.fromList ) + ( returnV M.empty ) + +-- +readDefaultStyle :: StyleReader _x (StyleFamily, StyleProperties) +readDefaultStyle = lookupAttr NsStyle "family" + >>?! keepingTheValue readStyleProperties + +-- +readStyle :: StyleReader _x (StyleName,Style) +readStyle = findAttr NsStyle "name" + >>?! keepingTheValue + ( liftA4 Style + ( lookupAttr' NsStyle "family" ) + ( findAttr' NsStyle "parent-style-name" ) + ( findAttr' NsStyle "list-style-name" ) + readStyleProperties + ) + +-- +readStyleProperties :: StyleReaderSafe _x StyleProperties +readStyleProperties = liftA2 SProps + ( readTextProperties >>> choiceToMaybe ) + ( readParaProperties >>> choiceToMaybe ) + +-- +readTextProperties :: StyleReader _x TextProperties +readTextProperties = + executeIn NsStyle "text-properties" $ liftAsSuccess + ( liftA6 PropT + ( searchAttr NsXSL_FO "font-style" False isFontEmphasised ) + ( searchAttr NsXSL_FO "font-weight" False isFontBold ) + ( findPitch ) + ( getAttr NsStyle "text-position" ) + ( readUnderlineMode ) + ( readStrikeThroughMode ) + ) + where isFontEmphasised = [("normal",False),("italic",True),("oblique",True)] + isFontBold = ("normal",False):("bold",True) + :(map ((,True).show) ([100,200..900]::[Int])) + +readUnderlineMode :: StyleReaderSafe _x (Maybe UnderlineMode) +readUnderlineMode = readLineMode "text-underline-mode" + "text-underline-style" + +readStrikeThroughMode :: StyleReaderSafe _x (Maybe UnderlineMode) +readStrikeThroughMode = readLineMode "text-line-through-mode" + "text-line-through-style" + +readLineMode :: String -> String -> StyleReaderSafe _x (Maybe UnderlineMode) +readLineMode modeAttr styleAttr = proc x -> do + isUL <- searchAttr NsStyle styleAttr False isLinePresent -< x + mode <- lookupAttr' NsStyle modeAttr -< x + if isUL + then case mode of + Just m -> returnA -< Just m + Nothing -> returnA -< Just UnderlineModeNormal + else returnA -< Nothing + where + isLinePresent = [("none",False)] ++ map (,True) + [ "dash" , "dot-dash" , "dot-dot-dash" , "dotted" + , "long-dash" , "solid" , "wave" + ] + +-- +readParaProperties :: StyleReader _x ParaProperties +readParaProperties = + executeIn NsStyle "paragraph-properties" $ liftAsSuccess + ( liftA3 PropP + ( liftA2 readNumbering + ( isSet' NsText "number-lines" ) + ( readAttr' NsText "line-number" ) + ) + ( liftA2 readIndentation + ( isSetWithDefault NsStyle "auto-text-indent" False ) + ( getAttr NsXSL_FO "text-indent" ) + ) + ( getAttr NsXSL_FO "margin-left" ) + ) + where readNumbering (Just True) (Just n) = NumberingRestart n + readNumbering (Just True) _ = NumberingKeep + readNumbering _ _ = NumberingNone + + readIndentation False indent = indent + readIndentation True _ = def + +---- +-- List styles +---- + +-- +readListStyle :: StyleReader _x (StyleName, ListStyle) +readListStyle = + findAttr NsStyle "name" + >>?! keepingTheValue + ( liftA ListStyle + $ ( liftA3 SM.union3 + ( readListLevelStyles NsText "list-level-style-number" LltNumbered ) + ( readListLevelStyles NsText "list-level-style-bullet" LltBullet ) + ( readListLevelStyles NsText "list-level-style-image" LltImage ) + ) >>^ M.mapMaybe chooseMostSpecificListLevelStyle + ) +-- +readListLevelStyles :: Namespace -> ElementName + -> ListLevelType + -> StyleReaderSafe _x (SM.SetMap Int ListLevelStyle) +readListLevelStyles namespace elementName levelType = + ( tryAll namespace elementName (readListLevelStyle levelType) + >>^ SM.fromList + ) + +-- +readListLevelStyle :: ListLevelType -> StyleReader _x (Int, ListLevelStyle) +readListLevelStyle levelType = readAttr NsText "level" + >>?! keepingTheValue + ( liftA4 toListLevelStyle + ( returnV levelType ) + ( findAttr' NsStyle "num-prefix" ) + ( findAttr' NsStyle "num-suffix" ) + ( getAttr NsStyle "num-format" ) + ) + where + toListLevelStyle _ p s LinfNone = ListLevelStyle LltBullet p s LinfNone + toListLevelStyle _ p s f@(LinfString _) = ListLevelStyle LltBullet p s f + toListLevelStyle t p s f = ListLevelStyle t p s f + +-- +chooseMostSpecificListLevelStyle :: S.Set ListLevelStyle -> Maybe ListLevelStyle +chooseMostSpecificListLevelStyle ls | ls == mempty = Nothing + | otherwise = Just ( F.foldr1 select ls ) + where + select ( ListLevelStyle t1 p1 s1 f1 ) + ( ListLevelStyle t2 p2 s2 f2 ) + = ListLevelStyle (select' t1 t2) (p1 <|> p2) (s1 <|> s2) (selectLinf f1 f2) + select' LltNumbered _ = LltNumbered + select' _ LltNumbered = LltNumbered + select' _ _ = LltBullet + selectLinf LinfNone f2 = f2 + selectLinf f1 LinfNone = f1 + selectLinf (LinfString _) f2 = f2 + selectLinf f1 (LinfString _) = f1 + selectLinf f1 _ = f1 + + +-------------------------------------------------------------------------------- +-- Tools to access style data +-------------------------------------------------------------------------------- + +-- +lookupStyle :: StyleName -> Styles -> Maybe Style +lookupStyle name Styles{..} = M.lookup name stylesByName + +-- +lookupDefaultStyle :: StyleFamily -> Styles -> StyleProperties +lookupDefaultStyle family Styles{..} = fromMaybe def + (M.lookup family defaultStyleMap) + +-- +lookupDefaultStyle' :: Styles -> StyleFamily -> StyleProperties +lookupDefaultStyle' Styles{..} family = fromMaybe def + (M.lookup family defaultStyleMap) + +-- +getListStyle :: Style -> Styles -> Maybe ListStyle +getListStyle Style{..} styles = listStyle >>= (`lookupListStyleByName` styles) + +-- +lookupListStyleByName :: StyleName -> Styles -> Maybe ListStyle +lookupListStyleByName name Styles{..} = M.lookup name listStylesByName + + +-- | Returns a chain of parent of the current style. The direct parent will +-- be the first element of the list, followed by its parent and so on. +-- The current style is not in the list. +parents :: Style -> Styles -> [Style] +parents style styles = unfoldr findNextParent style -- Ha! + where findNextParent Style{..} + = fmap duplicate $ (`lookupStyle` styles) =<< styleParentName + +-- | Looks up the style family of the current style. Normally, every style +-- should have one. But if not, all parents are searched. +getStyleFamily :: Style -> Styles -> Maybe StyleFamily +getStyleFamily style@Style{..} styles + = styleFamily + <|> (F.asum $ map (`getStyleFamily` styles) $ parents style styles) + +-- | Each 'Style' has certain 'StyleProperties'. But sometimes not all property +-- values are specified. Instead, a value might be inherited from a +-- parent style. This function makes this chain of inheritance +-- concrete and easily accessible by encapsulating the necessary lookups. +-- The resulting list contains the direct properties of the style as the first +-- element, the ones of the direct parent element as the next one, and so on. +-- +-- Note: There should also be default properties for each style family. These +-- are @not@ contained in this list because properties inherited from +-- parent elements take precedence over default styles. +-- +-- This function is primarily meant to be used through convenience wrappers. +-- +stylePropertyChain :: Style -> Styles -> [StyleProperties] +stylePropertyChain style styles + = map styleProperties (style : parents style styles) + +-- +extendedStylePropertyChain :: [Style] -> Styles -> [StyleProperties] +extendedStylePropertyChain [] _ = [] +extendedStylePropertyChain [style] styles = (stylePropertyChain style styles) + ++ (maybeToList (fmap (lookupDefaultStyle' styles) (getStyleFamily style styles))) +extendedStylePropertyChain (style:trace) styles = (stylePropertyChain style styles) + ++ (extendedStylePropertyChain trace styles) +-- Optimizable with Data.Sequence + +-- +extendedStylePropertyChain' :: [Style] -> Styles -> Maybe [StyleProperties] +extendedStylePropertyChain' [] _ = Nothing +extendedStylePropertyChain' [style] styles = Just ( + (stylePropertyChain style styles) + ++ (maybeToList (fmap (lookupDefaultStyle' styles) (getStyleFamily style styles))) + ) +extendedStylePropertyChain' (style:trace) styles = fmap ((stylePropertyChain style styles) ++) + (extendedStylePropertyChain' trace styles) + +-- +stylePropertyChain' :: Styles -> Style -> [StyleProperties] +stylePropertyChain' = flip stylePropertyChain + +-- +getStylePropertyChain :: StyleName -> Styles -> [StyleProperties] +getStylePropertyChain name styles = maybe [] + (`stylePropertyChain` styles) + (lookupStyle name styles) + +-- +getPropertyChain :: (StyleProperties -> Maybe a) -> Style -> Styles -> [a] +getPropertyChain extract style styles = catMaybes + $ map extract + $ stylePropertyChain style styles + +-- +textPropertyChain :: Style -> Styles -> [TextProperties] +textPropertyChain = getPropertyChain textProperties + +-- +paraPropertyChain :: Style -> Styles -> [ParaProperties] +paraPropertyChain = getPropertyChain paraProperties + +-- +getTextProperty :: (TextProperties -> a) -> Style -> Styles -> Maybe a +getTextProperty extract style styles = fmap extract + $ listToMaybe + $ textPropertyChain style styles + +-- +getTextProperty' :: (TextProperties -> Maybe a) -> Style -> Styles -> Maybe a +getTextProperty' extract style styles = F.asum + $ map extract + $ textPropertyChain style styles + +-- +getParaProperty :: (ParaProperties -> a) -> Style -> Styles -> Maybe a +getParaProperty extract style styles = fmap extract + $ listToMaybe + $ paraPropertyChain style styles + +-- | Lifts the reader into another readers' state. +liftStyles :: (OdtConverterState s -> OdtConverterState Styles) + -> (OdtConverterState Styles -> OdtConverterState s ) + -> XMLReader s x x +liftStyles extract inject = switchState extract inject + $ convertingExtraState M.empty readAllStyles + diff --git a/src/Text/Pandoc/Shared.hs b/src/Text/Pandoc/Shared.hs index edf2619c0..c09c2f2a0 100644 --- a/src/Text/Pandoc/Shared.hs +++ b/src/Text/Pandoc/Shared.hs @@ -683,16 +683,16 @@ headerLtEq _ _ = False -- | Generate a unique identifier from a list of inlines. -- Second argument is a list of already used identifiers. uniqueIdent :: [Inline] -> [String] -> String -uniqueIdent title' usedIdents = - let baseIdent = case inlineListToIdentifier title' of +uniqueIdent title' usedIdents + = let baseIdent = case inlineListToIdentifier title' of "" -> "section" x -> x - numIdent n = baseIdent ++ "-" ++ show n - in if baseIdent `elem` usedIdents - then case find (\x -> numIdent x `notElem` usedIdents) ([1..60000] :: [Int]) of + numIdent n = baseIdent ++ "-" ++ show n + in if baseIdent `elem` usedIdents + then case find (\x -> numIdent x `notElem` usedIdents) ([1..60000] :: [Int]) of Just x -> numIdent x Nothing -> baseIdent -- if we have more than 60,000, allow repeats - else baseIdent + else baseIdent -- | True if block is a Header block. isHeaderBlock :: Block -> Bool diff --git a/tests/Tests/Readers/Odt.hs b/tests/Tests/Readers/Odt.hs new file mode 100644 index 000000000..cf30b8398 --- /dev/null +++ b/tests/Tests/Readers/Odt.hs @@ -0,0 +1,165 @@ +module Tests.Readers.Odt (tests) where + +import Control.Monad ( liftM ) +import Text.Pandoc.Options +import Text.Pandoc.Readers.Native +import Text.Pandoc.Readers.Markdown +import Text.Pandoc.Definition +import Text.Pandoc.Error +import Tests.Helpers +import Test.Framework +--import Test.HUnit (assertBool) +--import Test.Framework.Providers.HUnit +import qualified Data.ByteString.Lazy as B +import Text.Pandoc.Readers.Odt +import Text.Pandoc.Writers.Native (writeNative) +import qualified Data.Map as M +--import Text.Pandoc.MediaBag (MediaBag, lookupMedia, mediaDirectory) +--import Codec.Archive.Zip + + +tests :: [Test] +tests = testsComparingToMarkdown ++ testsComparingToNative + +testsComparingToMarkdown :: [Test] +testsComparingToMarkdown = map nameToTest namesOfTestsComparingToMarkdown + where nameToTest name = createTest + compareOdtToMarkdown + name + (toOdtPath name) + (toMarkdownPath name) + toOdtPath name = "odt/odt/" ++ name ++ ".odt" + toMarkdownPath name = "odt/markdown/" ++ name ++ ".md" + +testsComparingToNative :: [Test] +testsComparingToNative = map nameToTest namesOfTestsComparingToNative + where nameToTest name = createTest + compareOdtToNative + name + (toOdtPath name) + (toNativePath name) + toOdtPath name = "odt/odt/" ++ name ++ ".odt" + toNativePath name = "odt/native/" ++ name ++ ".native" + + +newtype NoNormPandoc = NoNormPandoc {unNoNorm :: Pandoc} + deriving ( Show ) + +instance ToString NoNormPandoc where + toString d = writeNative def{ writerStandalone = s } $ toPandoc d + where s = case d of + NoNormPandoc (Pandoc (Meta m) _) + | M.null m -> False + | otherwise -> True + +instance ToPandoc NoNormPandoc where + toPandoc = unNoNorm + +getNoNormVia :: (a -> Pandoc) -> String -> Either PandocError a -> NoNormPandoc +getNoNormVia _ readerName (Left _) = error (readerName ++ " reader failed") +getNoNormVia f _ (Right a) = NoNormPandoc (f a) + +type TestCreator = ReaderOptions + -> FilePath -> FilePath + -> IO (NoNormPandoc, NoNormPandoc) + +compareOdtToNative :: TestCreator +compareOdtToNative opts odtPath nativePath = do + nativeFile <- Prelude.readFile nativePath + odtFile <- B.readFile odtPath + let native = getNoNormVia id "native" $ readNative nativeFile + let odt = getNoNormVia fst "odt" $ readOdt opts odtFile + return (odt,native) + +compareOdtToMarkdown :: TestCreator +compareOdtToMarkdown opts odtPath markdownPath = do + markdownFile <- Prelude.readFile markdownPath + odtFile <- B.readFile odtPath + let markdown = getNoNormVia id "markdown" $ readMarkdown opts markdownFile + let odt = getNoNormVia fst "odt" $ readOdt opts odtFile + return (odt,markdown) + + +createTest :: TestCreator + -> TestName + -> FilePath -> FilePath + -> Test +createTest creator name path1 path2 = + buildTest $ liftM (test id name) (creator def path1 path2) + +{- +-- + +getMedia :: FilePath -> FilePath -> IO (Maybe B.ByteString) +getMedia archivePath mediaPath = do + zf <- B.readFile archivePath >>= return . toArchive + return $ findEntryByPath ("Pictures/" ++ mediaPath) zf >>= (Just . fromEntry) + +compareMediaPathIO :: FilePath -> MediaBag -> FilePath -> IO Bool +compareMediaPathIO mediaPath mediaBag odtPath = do + odtMedia <- getMedia odtPath mediaPath + let mbBS = case lookupMedia mediaPath mediaBag of + Just (_, bs) -> bs + Nothing -> error ("couldn't find " ++ + mediaPath ++ + " in media bag") + odtBS = case odtMedia of + Just bs -> bs + Nothing -> error ("couldn't find " ++ + mediaPath ++ + " in media bag") + return $ mbBS == odtBS + +compareMediaBagIO :: FilePath -> IO Bool +compareMediaBagIO odtFile = do + df <- B.readFile odtFile + let (_, mb) = readOdt def df + bools <- mapM + (\(fp, _, _) -> compareMediaPathIO fp mb odtFile) + (mediaDirectory mb) + return $ and bools + +testMediaBagIO :: String -> FilePath -> IO Test +testMediaBagIO name odtFile = do + outcome <- compareMediaBagIO odtFile + return $ testCase name (assertBool + ("Media didn't match media bag in file " ++ odtFile) + outcome) + +testMediaBag :: String -> FilePath -> Test +testMediaBag name odtFile = buildTest $ testMediaBagIO name odtFile +-} +-- + + + +namesOfTestsComparingToMarkdown :: [ String ] +namesOfTestsComparingToMarkdown = [ "bold" +-- , "citation" + , "endnote" + , "externalLink" + , "footnote" + , "headers" +-- , "horizontalRule" +-- , "image" + , "italic" +-- , "listBlocks" + , "paragraph" + , "strikeout" +-- , "trackedChanges" + , "underlined" + ] + +namesOfTestsComparingToNative :: [ String ] +namesOfTestsComparingToNative = [ "blockquote" + , "orderedListMixed" + , "orderedListRoman" + , "orderedListSimple" + , "referenceToChapter" + , "referenceToListItem" + , "referenceToText" + , "simpleTable" +-- , "table" + , "unicode" + , "unorderedList" + ] \ No newline at end of file diff --git a/tests/odt/markdown/bold.md b/tests/odt/markdown/bold.md new file mode 100644 index 000000000..fa4eb0431 --- /dev/null +++ b/tests/odt/markdown/bold.md @@ -0,0 +1 @@ +Here comes **bold** text \ No newline at end of file diff --git a/tests/odt/markdown/citation.md b/tests/odt/markdown/citation.md new file mode 100644 index 000000000..adcc9f0ff --- /dev/null +++ b/tests/odt/markdown/citation.md @@ -0,0 +1 @@ +Some text[@Ex] with a citation. \ No newline at end of file diff --git a/tests/odt/markdown/endnote.md b/tests/odt/markdown/endnote.md new file mode 100644 index 000000000..679af3fdc --- /dev/null +++ b/tests/odt/markdown/endnote.md @@ -0,0 +1,3 @@ +Some text[^1] with an endnote. + +[^1]: Endnote text \ No newline at end of file diff --git a/tests/odt/markdown/externalLink.md b/tests/odt/markdown/externalLink.md new file mode 100644 index 000000000..14f48d0f5 --- /dev/null +++ b/tests/odt/markdown/externalLink.md @@ -0,0 +1 @@ +Here comes an [external link](http://example.com/) to example.com. \ No newline at end of file diff --git a/tests/odt/markdown/footnote.md b/tests/odt/markdown/footnote.md new file mode 100644 index 000000000..973ae2d3a --- /dev/null +++ b/tests/odt/markdown/footnote.md @@ -0,0 +1,3 @@ +Some text[^1] with a footnote. + +[^1]: Footnote text \ No newline at end of file diff --git a/tests/odt/markdown/headers.md b/tests/odt/markdown/headers.md new file mode 100644 index 000000000..ea5d4452c --- /dev/null +++ b/tests/odt/markdown/headers.md @@ -0,0 +1,9 @@ +# A header (Lv 1) + +A paragraph + +## Another header (Lv 2) + +Another paragraph + +# Back to Level 1 \ No newline at end of file diff --git a/tests/odt/markdown/horizontalRule.md b/tests/odt/markdown/horizontalRule.md new file mode 100644 index 000000000..73b314ff7 --- /dev/null +++ b/tests/odt/markdown/horizontalRule.md @@ -0,0 +1 @@ +--- \ No newline at end of file diff --git a/tests/odt/markdown/image.md b/tests/odt/markdown/image.md new file mode 100644 index 000000000..3862d709e --- /dev/null +++ b/tests/odt/markdown/image.md @@ -0,0 +1 @@ +![](10000000000000FA000000FAD6A15225.jpg) \ No newline at end of file diff --git a/tests/odt/markdown/imageIndex.md b/tests/odt/markdown/imageIndex.md new file mode 100644 index 000000000..6719ab8a8 --- /dev/null +++ b/tests/odt/markdown/imageIndex.md @@ -0,0 +1,6 @@ +# Abbildungsverzeichnis + +Abbildung 1: Image caption + +![Abbildung 1: Image caption](10000000000000FA000000FAD6A15225.jpg) + diff --git a/tests/odt/markdown/imageWithCaption.md b/tests/odt/markdown/imageWithCaption.md new file mode 100644 index 000000000..0046ae141 --- /dev/null +++ b/tests/odt/markdown/imageWithCaption.md @@ -0,0 +1 @@ +![Abbildung 1: Image caption](10000000000000FA000000FAD6A15225.jpg) \ No newline at end of file diff --git a/tests/odt/markdown/italic.md b/tests/odt/markdown/italic.md new file mode 100644 index 000000000..b4d2f3d40 --- /dev/null +++ b/tests/odt/markdown/italic.md @@ -0,0 +1 @@ +Here comes *italic* text \ No newline at end of file diff --git a/tests/odt/markdown/listBlocks.md b/tests/odt/markdown/listBlocks.md new file mode 100644 index 000000000..22c77bb2b --- /dev/null +++ b/tests/odt/markdown/listBlocks.md @@ -0,0 +1,6 @@ + + +Indented text in a list. + + +This is a numbered block.It contains several paragraphs of text.Like this.Next item. \ No newline at end of file diff --git a/tests/odt/markdown/paragraph.md b/tests/odt/markdown/paragraph.md new file mode 100644 index 000000000..0a822e322 --- /dev/null +++ b/tests/odt/markdown/paragraph.md @@ -0,0 +1,5 @@ +This is a paragraph. + +This is another paragraph. + +This is a third one. \ No newline at end of file diff --git a/tests/odt/markdown/strikeout.md b/tests/odt/markdown/strikeout.md new file mode 100644 index 000000000..6ae4571dd --- /dev/null +++ b/tests/odt/markdown/strikeout.md @@ -0,0 +1 @@ +Here comes text that was ~~striken out~~. \ No newline at end of file diff --git a/tests/odt/markdown/trackedChanges.md b/tests/odt/markdown/trackedChanges.md new file mode 100644 index 000000000..f0bd478a3 --- /dev/null +++ b/tests/odt/markdown/trackedChanges.md @@ -0,0 +1 @@ +Some text with and inserted text. \ No newline at end of file diff --git a/tests/odt/markdown/underlined.md b/tests/odt/markdown/underlined.md new file mode 100644 index 000000000..05fb92379 --- /dev/null +++ b/tests/odt/markdown/underlined.md @@ -0,0 +1 @@ +Here comes *underlined* text \ No newline at end of file diff --git a/tests/odt/native/blockquote.native b/tests/odt/native/blockquote.native new file mode 100644 index 000000000..8c9409dde --- /dev/null +++ b/tests/odt/native/blockquote.native @@ -0,0 +1 @@ +[Para [Str "Normal"],BlockQuote [Para [Str "Indented",Space,Str "(1cm)"]]] \ No newline at end of file diff --git a/tests/odt/native/orderedListMixed.native b/tests/odt/native/orderedListMixed.native new file mode 100644 index 000000000..a50f5e2ad --- /dev/null +++ b/tests/odt/native/orderedListMixed.native @@ -0,0 +1 @@ +Pandoc (Meta {unMeta = fromList []}) [OrderedList (1,Decimal,Period) [[Plain [Str "A",Space,Str "list",Space,Str "item"]],[Plain [Str "A",Space,Str "second"]],[Para [Str "A",Space,Str "third"],OrderedList (1,Decimal,Period) [[Para [Str "New",Space,Str "level!"],OrderedList (1,LowerAlpha,OneParen) [[Plain [Str "And",Space,Str "another!"]],[Plain [Str "It's",Space,Str "great",Space,Str "up",Space,Str "here!"]]]],[Plain [Str "Oh",Space,Str "noes"]],[Plain [Str "We",Space,Str "fell!"]]]],[Plain [Str "Maybe",Space,Str "someone"]],[Plain [Str "Pushed",Space,Str "us?"]]]] \ No newline at end of file diff --git a/tests/odt/native/orderedListRoman.native b/tests/odt/native/orderedListRoman.native new file mode 100644 index 000000000..f186e0735 --- /dev/null +++ b/tests/odt/native/orderedListRoman.native @@ -0,0 +1 @@ +Pandoc (Meta {unMeta = fromList []}) [OrderedList (1,UpperRoman,Period) [[Plain[Str "A",Space,Str "list",Space,Str "item"]],[Plain [Str "A",Space,Str "second"]],[Para [Str "A",Space,Str "third"],OrderedList (1,UpperRoman,Period) [[Para [Str "New",Space,Str "level!"],OrderedList (1,UpperRoman,Period) [[Plain [Str "And",Space,Str "another!"]],[Plain [Str "It's",Space,Str "great",Space,Str "up",Space,Str "here!"]]]],[Plain [Str "Oh",Space,Str "noes"]],[Plain [Str "We",Space,Str "fell!"]]]],[Plain [Str "Maybe",Space,Str "someone"]],[Plain [Str "Pushed",Space,Str "us?"]]]] \ No newline at end of file diff --git a/tests/odt/native/orderedListSimple.native b/tests/odt/native/orderedListSimple.native new file mode 100644 index 000000000..90a51856a --- /dev/null +++ b/tests/odt/native/orderedListSimple.native @@ -0,0 +1 @@ +Pandoc (Meta {unMeta = fromList []}) [OrderedList (1,Decimal,Period) [[Plain [Str "A",Space,Str "list",Space,Str "item"]],[Plain [Str "A",Space,Str "second"]],[Para [Str "A",Space,Str "third"],OrderedList (1,Decimal,Period) [[Para [Str "New",Space,Str "level!"],OrderedList (1,Decimal,Period) [[Plain [Str "And",Space,Str "another!"]],[Plain [Str "It's",Space,Str "great",Space,Str "up",Space,Str "here!"]]]],[Plain [Str "Oh",Space,Str "noes"]],[Plain [Str "We",Space,Str "fell!"]]]],[Plain [Str "Maybe",Space,Str "someone"]],[Plain [Str "Pushed",Space,Str "us?"]]]] \ No newline at end of file diff --git a/tests/odt/native/referenceToChapter.native b/tests/odt/native/referenceToChapter.native new file mode 100644 index 000000000..fc6c6cf5c --- /dev/null +++ b/tests/odt/native/referenceToChapter.native @@ -0,0 +1 @@ +[Header 1 ("a-chapter",[],[]) [Span ("anchor",[],[]) [],Str "A",Space,Str "chapter"],Para [Str "Some",Space,Str "text."],Header 1 ("another-chapter",[],[]) [Str "Another",Space,Str "chapter"],Para [Str "A",Space,Str "reference",Space,Str "to",Space,Str "."],Para [Str "A",Space,Str "reference",Space,Str "to",Space,Link [Str "A",Space,Str "chapter"] ("#anchor",""),Str "."]] \ No newline at end of file diff --git a/tests/odt/native/referenceToListItem.native b/tests/odt/native/referenceToListItem.native new file mode 100644 index 000000000..d009f8d23 --- /dev/null +++ b/tests/odt/native/referenceToListItem.native @@ -0,0 +1 @@ +[OrderedList (1,Decimal,Period) [[Plain [Span ("anchor",[],[]) [],Str "A",Space,Str "list",Space,Str "item"]],[Plain [Str "Another",Space,Str "list",Space,Str "item"]]],Para [Str "A",Space,Str "reference",Space,Str "to",Space,Str "list",Space,Str "item",Space,Link [Str "1."] ("#anchor",""),Str "."],Para [],Para []] \ No newline at end of file diff --git a/tests/odt/native/referenceToText.native b/tests/odt/native/referenceToText.native new file mode 100644 index 000000000..45f7ac44c --- /dev/null +++ b/tests/odt/native/referenceToText.native @@ -0,0 +1 @@ +[Para [Span ("an anchor",[],[]) [],Str "Some",Space,Str "text."],Para [Str "A",Space,Str "reference",Space,Str "to",Space,Link [Str "Some",Space,Str "text"] ("#an anchor",""),Str "."]] \ No newline at end of file diff --git a/tests/odt/native/simpleTable.native b/tests/odt/native/simpleTable.native new file mode 100644 index 000000000..f94026bd5 --- /dev/null +++ b/tests/odt/native/simpleTable.native @@ -0,0 +1 @@ +[Table [] [] [] [] [[[Plain [Str "Content"]],[Plain [Str "More",Space,Str "content"]]]],Para []] \ No newline at end of file diff --git a/tests/odt/native/unicode.native b/tests/odt/native/unicode.native new file mode 100644 index 000000000..b6ac9760c --- /dev/null +++ b/tests/odt/native/unicode.native @@ -0,0 +1 @@ +[Para [Str "\8220\8221\8217\231\1256\169\188\1074\1073\1060\1064\246\201\181"]] \ No newline at end of file diff --git a/tests/odt/native/unorderedList.native b/tests/odt/native/unorderedList.native new file mode 100644 index 000000000..a8c083d13 --- /dev/null +++ b/tests/odt/native/unorderedList.native @@ -0,0 +1 @@ +[BulletList [[Plain [Str "A",Space,Str "list",Space,Str "item"]],[Plain [Str "A",Space,Str "second"]],[Para [Str "A",Space,Str "third"],BulletList [[Para [Str "New",Space,Str "level!"],BulletList [[Plain [Str "And",Space,Str "another!"]],[Plain [Str "It's",Space,Str "great",Space,Str "up",Space,Str "here!"]]]],[Plain [Str "Oh",Space,Str "noes"]],[Plain [Str "We",Space,Str "fell!"]]]],[Plain [Str "Maybe",Space,Str "someone"]],[Plain [Str "Pushed",Space,Str "us?"]]]] \ No newline at end of file diff --git a/tests/odt/odt/blockquote.odt b/tests/odt/odt/blockquote.odt new file mode 100644 index 0000000000000000000000000000000000000000..0114e308f30ed11bfc0016cafe192b43ce138a84 GIT binary patch literal 8594 zcmeHMc|6qL*B`QPQ6#cu>6^sNSi;zaOtOV!&6pWX#>|+-zJw4`%2p^#kw~&e_ANrz zWD5~WLbgQGGowWP>ic@0=ileK^O~8@=iYPP_uO;u=X~xxZzH{3G@Jkc0|0=KN9))= zm1g+|002`@331o{;1si6D0rs4vTVuIU)%_O%%}uh9dy~uDt&b$_{8OjEKblix%G>v~YN= zBOXa0*u(x!^H2SeT}S$NE#5!%hsBX_6xDyR^G|vNB8*7-Usy@RV$uI|D=Aty7zT;{ z&B`w1xcxkNZYf`iPfVRiF7_B03QYhKw=Sh{7{@RpgA=Swyi8;fR;aGlY4U#&06+y` zpsWiojg-se6;cA#(lGT%ni;6c3N+$W@4UG2EnbpAz_@hRwO;X;ybNRGY{!NP4U116 z{?musSfbvqFUaX@w4~8Vul@H6q@iF-e*HPeuQ7A^i(g$MUVEvy$(<@FxEhaTXjs3k z;=A53Zyk1PqLEKId3d*=Rgf;rVTX9s6}75YSa9CZ4ZF(Ps@vGdf$Ys^=~w36+&ymC z2w=>lpFfy`hg?NDEZ4}crMwGD+a0cY`2R2dZ#scnkyd-Ilb4H`yp#b@Z3C@`ns$MI z51$kaK z8H{B-m=az_TFq9ryH|ek`Gir!INx+BA!%kKD@#gRWgccaXqvUG_qON0^WAV=9y=4C zo>Fd?a7@lzz&J;Fz3oDdb*E>%C)_MGZ0|#(yOR$;7IuVW2bf*%)V|zfku>tGe~Ce$ zKxJgDbo_$K>+6lH*F-#89pVZJ�KS`MdR0;>$^UVtKP{4~#YVTcFd8{Nq*!yiM$0 z70+mU`=+`CbIZ%iD|ngI%8s6bBelTcrQ-*0)I~(l3OtfqL16r-lnkJ9%OZ~p^o}cg zc9}iC?;v4sq8}6TFzi-NB!en?PA+j|*!kGx%lh1ZycPsTf@C&Iss^2FUJ~H6A2jY~ zayfiDrnGb;x5(f=ou<1w{E2ydJl1tZMf34Lqd8o+2RV{%Uo;U$WtBX<%EgLfW?`t8 z*T{f=PG!dg;)0djsg;hEF3o)@qkl3f*B{idXeS!8s5K)2Kfd>n`x=`Srf~T_XktBp zap=j((i~sOdsn?bvUM~|yKyp2S;H09a34E#K7N|0QC7|gJ;0{{EeUKHjS)px@mI>d z3V*a$IEdY7CdEmJ%_W?ptlPewZ%EsG^?Zp3q!W_FB4(|gDHol}8(eM}9P=u>tYDXJ}ftLc+Zz2L!X z_ekyW`hM8Odmx`fIAmC zTIh6H&4nK~MV(h4Ki*WxCyl#avK(0U;Dvf#tdZ`*p2?2D+PD=Ri7dIZKyPOc`WjF<6ny9-giwokj-;uG)ql0$n9{Y)MGt%kkdBpz%~Q8pe|?!i^g z?g9YNECBLGgt9sM(|(5B2p}MdL=?u6K-shuSy~YWAnbl>Rl;xFH8s7wsG~c;1}K!S z-33{~+My4$+1H8$pll!K+M5rdn$tt~Plttx&7AaJt+Ww0PmT*y@T5yuY<8YoUuspN z;<2xvSRe4dL3EBEzW3>zxkBPRyCp}61$Ea8+5N{&mKY`DpO~?n^S*gq5|J<+hhTgc z$7ppU(8uDXmr_}*ghb_0+IYiWTlA@ctX}SjhN-bJ&Yp6=Vf3--)pso~*e5Qx?=~}Q z^~+}BILFmb+u(plMivz8ULM2FAu689XP`W0xRuKJs(g#i7_Gl338){KM11YX%nXRc z<~XuNm}h&Iz5H4^sq}n>>k(tdaLXl&blKYU`2k1sWf#U!y_vdJ1@g1Ce@F{)X|uk*-o z?J}e9qtBMLUA*xeM-L7Z_sqU-?lrQ^?1Al@(>`F;qhmbo<#M1=EYf9SmbrXV`^}}# zebJ)a{>kz!Og%nFQWj*NrJuRgRoc-x{DEwNM-msriRI82>ACWx4}zDTT@-Z*vAFzR zf$x0*m%}0TYhrkr#NIAF%xe4++n5P*s@x@BikUTQ$Qv6ct8aK!L)}T}{gE{z`?pG} zmD;hsb8W6=8go1AuYj<_a#z*$ z?N9<-dh~eESH=2@53XA3pN(Y^;rjcLV+zRBA=t8I2oWzsZ8cMUXvzGa5&IWWim-lq z)?FM!j?Xw_j_+mVdLPr}Bs*1h`kMDZK=84Ap=wc>^guvOitrraYA)OT1iA#u+yZ-A>9|Av0n^g^OrK#h?j6V`gS>UEH>jGn@I=uXn$)>*5IJz6E?2A`0J#;q<3O3 zRr=o!1V6@~@SWg56;{8dW{uJovEw+IhZpi|y*(OHExuQN+FO@dt*xmwevkez+e~Be z_28uB414YL;Cy6w5Z*>g{I2F_Dke3cc*oiCsCq~}$Z#Lb+QZ)0U-wo(>eCB8uFO`c z%WX{akI&SF881`}Th4SgKDUE z+g!WUGtqL1I?gU=9lk1RC)`T&#pE0T9eCl%NF}G2IkV>T70WLEjwc=38OuwOho_v| z#zE1k&yoh}MPm4U*ZX~V_ShX?%5=(lA8t0xS_+0I>yO5! zTKCUI_Gn9;9N;P+L|XxP*%j*mw5Bt_(@u1*=IF zAPAh?C`Zey?NC>>M6z&2ssAH#$fH!=wW-FYSeXfKyH~7QH2uw>d4IDY`=v9Pya%IT zWBwT{OR-BlZ_ zrFPMh9M=~Xz$Y^boHUzb91CA5>-c|LR`R;!=eIU1cPY2|L(uI?UC$xjPW<2LxomQv7&9PZ=uH}O>8D)v$+=&VnNB8BW z7PH-xJZHx2P?9fu=&}=B+8_h^!Gk&N*FHogU1z9XE$D2JGUFb4xe8OR|4?*jWu|F)QODs%BtbDCmBk+FHM&C$-7GS)b zmzBNn%!>(iY2{DFHF%&meY{+lv-ofKVO3@t->FE+-w^AhIntQN88gE#7H-&5Rde|v z4QrD-=Q-={j*u8FqbAzYJEw2U%txfWZp@>S_cN$yH#Uyd1Y^KW=SACZ_?h36t&6@| z5))me$5atT!?(&|ZoR?zy69rJ)NHzNgPsq1Om=^Dyw%mvJ=r{u4*=dGbzYV@JTI?0q3x4>1xoYuQk~bJbM`6Fq8B3?%ERM>9`o z#l<~xFAkDlK`~1*9to`y$fx`7`bNrwVk|OZdeiqru~lunG)O-DPVe1bj&#?dBTEkV zNy6{gN{9&uYII8P__pz<=Z!I7Rr#j75A4;sO)p#gBIy&U`0iuDG`6-N%>yRBk{g}R zw5XdFd}E{cOfzY*IP%ybeZUh zaggM-;o!3JL_x4wQLFb+U?yu>-oieh&U#_q+X^o3C!ECFH3_WHI-D43Pt^<19-m$r zHj#?7buHas&Jp(5>0Pl>PY5BtLC50NG#Qa+5uL9GUI#Wlig_*Y!q8m5acx6LVX@i6 zh@Yj2YD zy~*p>Kl_uM3`0pv#1Reu)dbHZU6Ty6D{Z$r!o)dWBi56K?Fu3{LPi6i4C}$^y*<4~ zQ#V@_yv-19vH32nA@*+cvxiWhXeT@#k_N$&v{u}G`E~t>Q+HCETw}@k zV_#L#|Cw>_6>3IWlx zrM>n^oL*O{w&7Z3sr22qE4$PmUleF_SRVt8*z&ZxFAh>ADV^Nyq*tQQ2}v{1~NZ_3;}c*zG+#`ySnGX6rL2)X8q#Br|;c1)=14~bBT<7-mor@YCK?%!I3 zD@vqq%yA!AaE}q_h{L(wjqW$o@RhkW6!In2Q1QY5hb{H;!Do$CpLcEnNhorfnqnxxt;IicxS#e zpG=9)XySNf^OPoOq?&6_AX|7K1XmeKHIWO+!`doS|q7pyj7ux~S zJ*`OE7r~QcCkPRl{mPcZ(E945^KC>NjmJkzwfNw(xKCKgSk_{FDkZ6uGdAqAe(#1; zT3d!!WEQzsuXd*5odpa$h>54Ldh(Gc?wBKr=i-7TAF*=wV6Q@(6JXeHNB8DLMQ}UT$#iuJmi-oQQs7ErM zYQ9Je;(KDC*B}$OXslS1Iy2U2SJ54mrfm07;!1np@FkXv3ES5dk7lidMtowOyk_BE zr0$0K5s?_XBKw!QgT3esjNo+5pqM~3FJJyiZECTBrJr)z_AGODO5$+ z%v48GL0Ca^PA#Qdj4Fbsmzu#~5v19Su;U__Xt8w%+zA}sX7k2@SLEv&lbU5Xj1%A3ZZFeoAlhL(imkrXmRRUd{Y zCkBL0p)eREdFf-6fqxYHuDq#4o=-_~&q!5i5LiwUBqIryHU-H;*ihb7fgU;}ULIwNhzf2$z0w zi0LU%UQ=Cpb7JGuLUHTzh9V=&px~r6AtF=igMFdWnr*ok%6cij-Wk~51PV$fRcY;0ui?yptJ@6Ki;EfS+a zFFaE0ZepWfZ)x0&uMJ>QigOpd~;G?XYzMa>ELI~z*&^p3K{jc#e}OcQP~ zmlWD_yXccIe`hQILV|9A{*Cn92EF?S(Ep%7e;wDh@^=Dm`+oEfVB3`F-%%)}=yu^I z`}6m4{z{Sl9f?8+ZWrS}AZ=5oe@CH^pW7w$4=A`D6zYE$r|J(lJ1Nz_=eS`E^v1UGzvBE(x^8<1Nyhmb1-rEjx7PN~PRBit_hjK5~mf7jf(%cSIlwu?X8&J5A-dONpQzxH@y->*B;EzPZG?f321c8?+4 sWKD9ErfkNxw6H=l}px03b9Bs%F(8LdgdJ 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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/citation.odt b/tests/odt/odt/citation.odt new file mode 100644 index 0000000000000000000000000000000000000000..b6dbe649e5a4dd0b8b5e67acbd08a9395328ad33 GIT binary patch literal 10842 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 Bri}mq literal 0 HcmV?d00001 diff --git a/tests/odt/odt/expressionUnevaluated.odt b/tests/odt/odt/expressionUnevaluated.odt new file mode 100644 index 0000000000000000000000000000000000000000..64df660b65f71a8115f6bbcadceaca5718842b22 GIT binary patch literal 10829 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 BqznK6 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/externalLink.odt b/tests/odt/odt/externalLink.odt new file mode 100644 index 0000000000000000000000000000000000000000..1d8f554895e7c9fd9ea7040c98175edc3b83562e GIT binary patch literal 10735 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 z zcEt}xg3t$H3QDLi_UllDC+d=4kyBJygp(Z#2fIU1CuNG9rY7n_GMq|4A_aFxM;I6? zcXsbDgdzxl*ilfpr`-1{MNTgST<#k~Kn@OagL=v#!E(P+1>}C!miyMwcZrWH4DO=H z>5N2r$N>P}-rmCA;==9-CxED|tSsPLE$5G>AmD%WJiHLD-?SiL0E!uax)w)z0z`#H z0cW~s5C3_6i8OTfiAfoIW0y8%@A<_ruDL&89=LSO_G&3ORofe@&}OLkot91cZI zeYgVPk80n+-$1DG6hgHO1&WD?N(zaH3yFxDh)TF zIZ07r8A%1eSv^|u@2>q)`Q0HX1l1e3lMv(w4FqUtA}XRMZv4ZE|55#K6xbJxI#mFQ z{igjx{9V@x3jfXy0UDsj%i!B=1xN^s2#a!?!{Fj#>_5fmVZ4IkZd`?ekpKx1Q8!8M zi(W8Sh>)zbsKk#pewzDk{-1e|=2E~skuWg(xA-GL4z5rku)7x=smO_XbiNM?npE<; z(A@#u-tSV6Uo=I3z&$_+kP`yr;e4iiR^jcAfSk#se<*{UQQBY>pXRJWLYxx-RQNGN z<PcS#>oHPZGnKfUhaf)>Ta#~}-dM!Y3V5GRH!69L-lAr! zgx)u<%5eFU2WvCSOZ8Obc8){IM%hU8UagG70D$%=i^mPtHVFr0Qu` z%kz7Ey|sKcEj@LHRv}@T$LvU=-1@Zi>ckKGEux@`&g6MNqR-h6!aNpCi1WIx+xZ7- zZd0XJT^=Uidvb%JunjQc?nryvKOnb{X058!5A25 z#?{Y6hl=O##{SK}`nx4G+vsPy{0B>DQq^~+)8DP2nN>ei#2>79{KC)r-?h{B2Rpy= zwf=7B-@Q8ggPouJt-o9Ocdvv{)8qFj|H|k3x1HY^T|c7(McMfqzw2xQoz2Q$FYwUB zm7l2_b>-Os3Ef%o; zdq;YPJR=1DzWw^y;sWZSK`+PX&Da_0EHu9^B3;zckBI>Q literal 0 HcmV?d00001 diff --git a/tests/odt/odt/footnote.odt b/tests/odt/odt/footnote.odt new file mode 100644 index 0000000000000000000000000000000000000000..74915c33c4163dd5d3016378d9625a3c58aee8e9 GIT binary patch literal 10843 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 VjR1Qs3jk1Ie~{SxGsKB&{VzyL&@})6 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/formula.odt b/tests/odt/odt/formula.odt new file mode 100644 index 0000000000000000000000000000000000000000..5cf5f3451693cbf208d22876d36c3f67f9ef3dc0 GIT binary patch literal 14252 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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/headers.odt b/tests/odt/odt/headers.odt new file mode 100644 index 0000000000000000000000000000000000000000..9212e9fb1980c0657fdfc8d383212f2bcc4580b8 GIT binary patch literal 10515 zcmeHNcRZDE*gvv~?3pc_W0oyDn@~pLI1Y|+4$iSf*?VuwrU;qY8JQ(p$d(;RMkwBM z8o&DW{`$S+kN2|U`?{}nU(fwq?&rR~x*C{R6aWAo0I(SdQn}qFe4Y~k0H7}v z3E&8IgdjbgARs3v2PhbXgu-D!H<*Ii`$1&|OAr0(C8q2&K+ zG^jg8ILsPq?gu@;F=hhHN5YqL3;U(Id z69@)z_|3~1-{ISfm;eC!LPyiU*45Dx27)>ufXE-W0!}cSFkNj`A_6)B6bq5sHKpsQ z|7!pM3;-Vb346(BM*;wtkJOap4LmZpribhnuL7>>5q>!{-xk1&w_bE~*W9Yh{HQD1 z#r(E7P3_%DcXv1Tw#V5Pb?fk+{1C1(6U80ff4Si}@$mL;H1nu!p0W4+n6tS%%Qql& zcI2Gev)wiK>I?i4T$i2{q|JqL)Hl41a zNF^k3R?%G1XbYBpFZZA+>ILRvI@yEwnVWLHqaN!dIwEp%<2I|^jfcrhvog~w%~~H2 zR5G%Lt*lgA0m_-<-FtfZ9Ro@IF>vn%IRn$_c67kB?l70;*oWv;u=8}!X0;+RbPm!V(*$CgW-DQLB=1YzI zsSL(Z9|-@e$Mi2x@c)PYeTDyD#^)3e_25A%CZ}gT>fHsXDQhd0DOmXbIr9^uxWI52 z@_TmQ%It?NT_)*%e}_OGJN$sTcUP6Hag)!@l){u5N@zvB<|waGt;Kh#nDvY6rhfGy zqt_aEUrll}Wm&1R0Bca45~!y1DmL$kNc9!dliSU+-Ue?LW64(rT;E(=qdQ<&A@dV^ zE!T9`RySlm=lda?KjnFwNQwmgg_CxtRN(wmoLSkd&ML$m@?();@dXhk&(wiH5irJq ze!20i7u6PJjFWSA(hS>D)6-UOy)omd2cL44_wS?o^ton+Hc&#f{zjm&;i^ngSG@dq zGXQ^=D_rK%X;FO(6>F;TIP9s2J6l2!?~4c8MK?qxKui{zaiMq4gYe=FZ6dNYe8Uzq!?Mt=Vs^1tbU{h>Y{IggQZ6M+4E3Jo7s6ce z6X-V?Ir5ke-MdZjnv1>F-Xs`Eu;BB|Sv%Z6w26e|sE2&ItFl0h8&E-MzWUhRrr(`~ zRQzR{lubW_(tW(Rxhr
    UCIP>y5oPS&q65aK- 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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/hiddenTextByStyle.odt b/tests/odt/odt/hiddenTextByStyle.odt new file mode 100644 index 0000000000000000000000000000000000000000..79c40ca9827e4fb8eebe10ecde2e987251d3a9f1 GIT binary patch literal 10798 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 Nb4TT$N^W%P{{hkPkO=?) literal 0 HcmV?d00001 diff --git a/tests/odt/odt/hiddenTextByVariable.odt b/tests/odt/odt/hiddenTextByVariable.odt new file mode 100644 index 0000000000000000000000000000000000000000..ec793d46642f30704b529aa912fd8af10e9db8c4 GIT binary patch literal 10788 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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/horizontalRule.odt b/tests/odt/odt/horizontalRule.odt new file mode 100644 index 0000000000000000000000000000000000000000..df09386bcdd47ddc35cd355b283fbcf4bc8eab72 GIT binary patch literal 10130 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 CX*JFO literal 0 HcmV?d00001 diff --git a/tests/odt/odt/image.odt b/tests/odt/odt/image.odt new file mode 100644 index 0000000000000000000000000000000000000000..c2fd1e407ca32b79584ce1fad98af7b6dac9bd5d GIT binary patch literal 33360 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 OA%7zf(H0l@?E62w269IL literal 0 HcmV?d00001 diff --git a/tests/odt/odt/imageWithCaption.odt b/tests/odt/odt/imageWithCaption.odt new file mode 100644 index 0000000000000000000000000000000000000000..99b5b7af11a6ad6dabc9cd3a35d6b8de0d4c6c7a GIT binary patch literal 33811 zcmeFYby!@{k}ul0haf>4cXw#q-QC^YJva%$ElAJ?LU6a>?rwqLuEE`J=gc{C@11Yv zzBljvdslyZ_wK#wS5>R_s@k=rRpen{u>k-?0H83+RLW?89hC+E0Q@~5w*Zc|j+P$2 zE|#V)E)KTlrXIG=PApzd7R=73?zZmC&MuZt7S86Lj+Ray%pR6L9xDGEGYJ0Q3m)W3 z+}X*>*4oqUA8g#&S*#qKO+75#SpE%#h=}+P75*Ipx%jKbe?*y@n_D_qLYO$av6y?h zx&4*x6r8|q5t%swji~B!y`j=V$!SA1^ z|Ewht19+O5{;MVb84CEHh;(stwsy00cmF>l3H~#rvx}$8U!ng^Jw2SA9sc{$+&xS^ zJpVsv`B$2YsgtF{f6x+jw^->TJ^=9d_-joK8&5|wCsSJocNUL-T{62kSx2fUNuwbX zAVWydWMw4OAm0rD02Bc6?-TYD1;+pY_~Nn>q8dI~Cs{}y*p`ihWu>j9X&!up7Gxm_ zXqNaIu*CTeqFt&Iq0pu(7i1&kY^3yKgb9l54it!?1&H*l!SDPeaG(-RRiRY7L}dVI zCPUC<^45oiEoDb9Wh49Fn#T6W_<3n~1@F8Ccpbep8-BgqwBMCI9@W`p3}E!FcQ38H zK}ke^ekRpPAb~}>3^Nf8e9t(99t!s$T1_g9h_i#x9r|BZn(hwb?oT3y(nrOGev+Ta z5wx$-d3FOx@MS?eCtCjAjB>c1XNV$q`AABuU!j$_{XsJ&OtcfTKC)4y>&&Y)K**RD zyQc^QJ$V%s^2650v1$22OjA?zJ!N-3a@)97FaILknMs`qt4&iB)u&J60qhx{t1n?T zcYGWdDzo=HUl@u?GfH)Njod(aUsm@-h6FWJqKFOVP3zprB-B$r!1;HRmvyjMe~^qH zq=+Kd=(+__=QHn59ot+asP7TLCOcLV~yo4;qC z1OKyKA?MM#$3{>n%}svg+OFu-eG=9i9xih(0M#RYlXMRdF6vX2@Qq?4BD& zO1c?3Liva_!gh9+Wcdc;1e|=QuwLI15_@IR4i}G=%6Y=SD zB9-Z`w759T>tlcrC3-*tIigb0EKrwpM}>@PDfLN#K9p>;`}g1jfj!Lj#wb60eYRu>L2-0UuzvLVBNL=$62@8a>f%1PZ zenv3eML2?%%KY%*19KV*%)3lV{MZm4Zth=WB)y-}2vhj=k|ZS2o`L@1b>-!Z*r+#u zeq#{^-OOvhJl!o^MNobtB>jZfAYRu4AL7lo!l2crrfT#$HdiA0+r~uPFFCquz#FU{ z@?|`LIwPj~GK@nnp|4Lu13w(uRSYZ2H42DKC(vnoyqEsdMk6@MJ}o&p`KGd`n243M z!}GZ}UZ8w|TJ~t6ibO3s5LVNZkHV#EG%eb>c^7AgU_1XyVfpjm&GCZrN57-)u-u!I zW%O3kkfA8t3OaiH#%{LECr(a$Nc+fRF~flGw>ZD1tH?CU;Am@TC@S9kV$vs4B4n{S zU`&WQkr>{;6Q$r}7<#{FiGJk=&;FkL7;u@0lc>EDl9C96n`4ZyKA5*(!Zw6n3XQBhG5)$)nF zYtuC_SgA3Wro{V5M36=%9vC}fH7G(|Z0u3D?C=k(x?I7qWpdf$px$>JK+goKsr8iW zvY6Df2Xz~S^OBL7{;sv$1M@I3Rb1|k9~{^et7vN%p@*TJL$`mSjohP!=ay()t)_v< z!<(r}&VQ>YFApbK#QO%%YdcB9PXgo|?H`pu7paTlr$?O*LTgOOOd%(S#VhlOcltsHK_kFz*P zW}n&mAi3;UIg>uOaux{x$!$~JsAm*iI{d1vN*SJ)i;d3o<+JD2-ekMS#U;OU z#R9_@(xvR%tu2PS{kE?;sX{*I38vx^@x)gyO-`%V_Qpy@l2Zsocm?EbUabYnxk5wu z7Z(>UTc2=qq&Wz&u!yj*2nlg%Mjr)*|D+@*n>Q9OVtk|N*;QeU!?_2GEez^WIxf}I zF)*OqKfCWU>Q2Y0s)U64hF{)*-nHUR%1_Ro$);( zj$>@2lirTx6suC2s&evGg$>H$?s|rXM1+L)Y(KqDmYUu7A8(GW>CHsF$F9&(12zic zh1g?}(0fMEDZ?nF<0y;1GwRk_ygoma85#O-ExHbu8qZIi^}~iG(UJ=;QU*Nhs;jsA z-_c}pJ4qF$b66{RdEK_(t(8eHnIXYiyd?RO2B-eW-x|ntb^rzJ9j~_DMrrBGAdwSp zg7h05zHvLYEG!&UH)~bs!M%Z(l9l7uJKxmJ2U*F=pBG!bS?I+K0}P+)cb=a=D%I&p z*mqSK%kdPQL&BmaM;P-t<(>O6FaWPQS5;DwQLiZL*}P&SAbjuQ ze;e#iqc}z=$cMYVb3Hcq`Oz^7Y*2?@;br6O@?&gK?$QN zF|su$+-W0PWIY5+3D_5ln6#BT+ z7rC7PhWPX}TTQ^zt#PXt+6;_w(IgZ-1H)i3Ud#2-JW4+m1%v0@0mhW%`=7(fG!?p6 zdhWTA)D-2<=c7u-6p;O>nY@9e)`?Wc_>_miIYg6`Q6N?gu$Z`vzfuhy~o9kxNx~U9d5|c3n0$` zD`g7JXC;0w$)MC_pdUGWv_+9rzvdn0${}d&$mzEe_Dzji#}%(B2EuD@{VOM0>$ANRO1}7t*=g;|nKV zc37%EoGVeEEmC%GEx7(Y@h+mYc%LO_9|R}#X>zrh^$Mm&Iw)96T(jYDw#eV<7gZn4 z%1>AEYWWJi1~~-E=Lj%$5v6WL{$Z@IJM+v5P=Kv%J2H%q8DBG#W_Q*ll}ezg!pQqljK3%0Nd&ja{a70zY0)d*Y3x zb8rXxmG-B9L?(N@KAa^~Jmo3Ut}=p?B=+4&G-`iU+<@b(ZuLG3tID7xHJd|``rfw)~Yp11LMr#7?kz!$9~hv{iHh%xJ;erc9z&(F<) z$;O9ocHqnhI#tvc`4!hI~E~Au-bk>EBu4okBhpJ@+etKwL0DoxaFGEE1UHS=eL&8r~j z($cc*)1iTZfy|T!n7T9nxAqf(DjaM^0b?DXykc6R4o^o%M+pguvY$UMFE7i>;}Fn^ zJzFUv-VwDNZwvOiyCv|BJq(|ybHo!1E^$+xJl;fo@8f>V^7#(@GKf;4e~eI4S=piL zE1tXQ;60hiQ}vYXE%bU{km!Uv$xtaH?U>#4&omiiSg9f+<;e?)u5Yg|3suI(uI+PH zxC?E!b`WVn_j&gvMLBk}KhVr3bNTP~T6j`f^iQw2T-vzZu6qaLgG$y{v>!4xHKBse z?$J6&g=>a4~ePg~C*eea=leLRQ5f9H#8TS> z(G^Z-zmg{U`tD@(`QRw z`wkPP=d7eG%5BhT>8I`WfpnwudSH87PpZX}$&;7EpSvf?g5d;9UO@_&Ls*tT+Skol z7zBcLBW($Ze?}q^mG&IJPDc3w1GJ)EU1Q_*2K$9bEE*vWPd81?`GWWtc(gwLv&z=M z0!}iaHM0*_S4B+vjT)W7c|3KPjFFL!FrKVZl1{99DYhtkxH0&GUKcaaxsyCT=Ns@a zyzjqwv=S*DCy@QVw^MecDAE;dXxO_>{MTTn+IE1kszq<|_HJ#`my(95Vl|+1qNC1V z+a`o;7~-b<-bdF{=bMkDsr#mrqbw}gumSApRc!ZrEuMpM0r<#t-C&2N7@vD@v_CUvon!lfBy8jp``7tA7`L#Zyv;cN(=HTFW;~jp z$HOAf*Ir`VA80R|yhp-%)KIy`nEeSqBqgPJIJt?1Uq8UJYgZcho-}Yxs~*LU*bfg6 z3v~(;TMiv7D#(D`?p^MP1&uyl^dFVBc=L3$T3jSq=LX<>vwFDPg`|P*pg#i6qQZ$d zzbnDuu8;I2u@$SQE_}eYV8%;DD=V$jbT+M*7Dt!4;zYbvuviKGYLIPWpM<1;fKkzC zi7jxe-n92~f2Z;5bleH#W!rx9D{db}`E03ypM|BWvU1|kLrOy8y5q@d*vj8Z&ZtPq z@b+X`TU)!+ZC7p^3BHq7E+jZ+L0Ry|!_Tku)u1zU&R>)+zgTQ&^e=;<8wzsz-wy(ZRei2T^Hg44lrDwYid1CYN zbsDH^TA%(Pb`c83n|;5j=-}WW_K`4GIq)t!wz;|4-|K9F# ztLRheSA%vHpBncx=GWjmZ9{&qLv|YPv0@^AuNBV)LmT;;6h;J0tYr;NO|P~Fbq9sx z2}AbQ)!#L3PeNS86S6kOzH_bMW=It?DfjAUknt@nld1cAxg>u8=D;}YXzVIAD zzZf9zWf5C+jU1o?eO63Vu{$2`Vg2Mw@u10%f$gX`y{myt!u2)qx-i@6>e;;w0w!uB z=T3sD8sxEu*DEq zQCsTQO}YS(p&b#C z<8;8xXTj^KQ^Tj*v-Q@?`IH5@5%iCZce5`MW@ctE1N7Dh3L280QlOHKdX=`=Sg&nf z_-F9(F(GRoZKqLULc+!!+~p6UrjLhPUt|V9<)a+p<0D$Ds+v|Ac{eC4euCnfpTF9h zSgn6h)|_t`;-6IbHnXd32rK%sm+3rZz39M==K^tYqjo>EHtnJxOLdl`TAXZqVXU;Y zqP#W>gZypH38w!HcaV65;ShpbK0w4C&cwwv-`22KQZYO_O7gfdHQkJ!E9j3yl9Hxv z@Y971GFoJ2R@$x~hQwfqjdT1@neSghA0Hn@z!)c^j!mmpr-9A)M@jubUFUdocAKLp zG>RFN2w{7(&3MT8_REK5#!E5HQyxK`pP+duRd;+kT3QIuU@1kuv#FuM@BXUL_itZ2 zA#o7CIvM`Jpp_pYa>wd_>+qGB5~(;LH#eTuxXlMcmyCu6K@}Y@z6N|EBBfhzgYnAc z-xXX2$!<5MOl>4?WTo0VK$W`H8^}hP?vurDHhDi+69op3qrYucofS#iiRXd)?LwgT zwwWvoQ6{qN_xVoFAFBro$Hnp1jw_M z+BwkRdCgTn55WJNwqX>;@50l0HzMS`E#B+4RMg`VN2{Pet$MkPI;Xe+et<{2-*i~cp z9kP`o6u)|)e-sjZv@LX~gC#BYdj=UL0T(w$b}^sptS5!iMlG3z;LB9f&lgZ&U>$(v zl_m8$oRYtC`y{Qy;$uokAHQmXiY_v;>)sYF#knUAlzVMI%vE2Cr@|oCP41_)2fF_N z8wYJD8jCATf!a!RVKp@gRBX!0^L31kt;-Mc9}|=b2t!3<0yN@_xZfw-l$bq!w`6*+ zqR=$fT03y^;R6ECRd~l2CmCb2Wd|V*b60u2+{#aGdsC+FP~f1CX+d63L0pi*Vcq## z`(@S3T?$;#uO5w^Tt|Y}wdo$nRMPf7mGj%AGXC20mg!s2yH8N2yAi`I15eKOBX5D- zi+_R~uqt`CosqYoY&N7J5Ts zx$iaoqwP2$i|BlgB^T-A=Msowm7g2G8#3P(QRT<}(b} zZYyjN6{S0|NrrrDT(k{oXRwJ(`mL6q`gQB4c0kl^2X6a;`APC0GP+?8@*o>%pYIvX z)fAV&z^rw${^yWj7U2My!vkV>QJqE?Xy-pME;zMcEQWg?PL~%>W3LWZjg4wS)MPo* zjEw48ADo72p*y5EvLl--4M9|sd#Fg{d-!rS>A0I&yP&f6y&pFQH-+*NHF-3x4Cb?~ zUFiKK6Ej|exJ=4ty7-xE7}Ce;*@aB7^B(cPOD51mTiC*ii+JgW3RDGDl3sqgXh|kc z1_ZSm`5%`I`fMRIH8pjVI>H0Fy?lpDYNNzR)EW7)0yp3S9W%F}v-yNC8$kh^>VVSFJAJDqTEQ}pWnbaf<1emNB0 zD+C>fxg*VXiLwJVd~uug!qd~7F~42$ZT}?GdlR|H#$F+gu$2-EZlp1B6SHUS+r-B> z_kn0?){8?z>ZuG)bNvr=tDP&Bj*c1Uw02ydHWdPN9;?q+{6iN=PX0thTy6f+mQvip zR5;e0S=5^CM(5p=n1EINhUi33YLftD%q3jo!(~w3Hso|YJ;IGw(%a;LV`~du!TYor z>mt*?D&HQ$*-!DpI9TJdmd_~4=^|CFK1WTLm)SCKf&LVPhUMQRn-iD^&XSHo=N8oC6pn?_>4RzD<*(L?MN-=z&LJad!DPKiO# zF8&QKAPoZ~zL6U8jJB)rT-UFq4J6)@!UhFQ;4!TDUu`_JKRsR6(Mwx)Z>)-lX*bML zRz9xa+mD6)sI&WuB>fN-?&%u$Qy{toL7TsQ?|gSIR_oU39m>0_P!qN&{I(1qG4`}A zyv8zDMD-;cx1{o%R2;@2wMGj`GH-j$@>YFuZxkAH{7U&#%c|<`)-JD25e{W~&}TGc z>d-lzpU+#mSvzr~39WKs+L-Vr0h!lqDHU9!IfFw~1#x zaFvw$BPetR``vi=qD>HMcO*_4mtYkGLHyO~+fY2mKi9$c^b-sNzxmZR4#?oQ6B` z7Wi5r>s3HOu}%^Xr529;9vRnaH_E^%(Ju#^DUV<+T$VZ>)p1;iy<|!26I;R83fCQG zvZNU}CAzq2UV)x#-L>l~B|Mf=jbtwox=<mc@eD_wRJ5 z&ti8M))8WMy#$U&BwMr4#;)7DpDzbZx)s`fYw|Fs4F0Y*Fx=wiz6r%8T97|+<7Tas zUm5zbrZ|-neF-8=J(gb?sB9}Mi#sm#;w4PSP5YTR-gcq*Z^#t`2=dAZ_MgZmNTs3w zY@7joe4Q!MK-$lEL;oh8>~5R1{Uo+h8|!<7QMzigdl$E<4!XzJJ|h`HOA(ixvNirTdG;{)(qbF4>Hhy={+I|3e@>a z%?zPNOodQ?{!1P5mwFRI4K{&Li~NKzWz-X#5q@sRz1R34kK>quaA>4j<&03u0_~@_ zXb|wpCUVs*S-jeOL`AhJT%Wn$=^-@xz6(^_cbvE&c*s|@ofX}UQS9@3IGKK1@M7<0B_3x zaR59l96TH>JUkpc0s=fD@_S@tBqU_)cj&0^ak266aItZ42#Bai2nZ>FI5?z?q!iRN zbo6xiBuuPKw5(LLbhLk&Kp`L?AR{7UAtPha65tTf{fx-YlV?e=R zK)v+={%-a`fGGPv3luaAL|p^`BBWO6JpdXC1_l}y78VW~4h{eVfYbtDG2k%C;MuUq zMO6_@T|=*}tA|4HxDY%1Z_FWkVxVCm6@(c7sDSxj z1Vdp!W0J9nzAXVzA-AD1U@!o}fTdNuJY*MTyOgp1Kpszo(CWqCN2s&RA2p;l0(0dS zC@?boBln0oI~CX-eHO)LFEdGuGq0=gBRMLvG#|Q=P@`o^c17#^@L&Vawq1cfgRe^Ze4oTAB zTQEWbDylWmEclZWqJy#Q|lqf8P0$Y&)J7XifDfYV; zhz!^D1rAMzkq^DJ0VC59^S%rS?-PYSw^h#NJpGF3skk!I5}umMnxh+&Lk9CYz4CIj zBJo=I1}J*a;&$XQlBI+hN!CA^BtBBUEw?E&dL}&P*QD~e-v{JAaFo#ean&DU;EPwZ zZ!yT@Vj_Qq2R?v7!mewD7+C{dEhj>yT^EmYh-oXmizI$<6jt4UfGZJnvXirZKn(2_ zYL=?YsdBFmE24P{74kazZ>GYdNy+^2I8P z(-FtEZD<%`2$COuo9;^%~&d12{CsDCM%6+t99Qaziug^c&xpSqx*aiJ8Lo|nSDPiw%6b-J^a zjv{|1I@GV725-tjsRfHxu8vhbcJbbOCB_6C*s8Fz%M$OX8sNc%D#J8jMqIsn7ZA)T zD=Wj^txXff9OL@j{4gzHp2Quh2(>A8R^t`(lofalhgpob=JN*l5vm&Zu@|{{0~vbk zFoj*ZU3AA9pZGUe4DR&Xl9G}jEuWe^EKLKn177h)D15+APTpS##xOQu%5@{H*Pm20Y*OL6C1z$c8B17qlV|Day^ zazg{dp(xaZGKbjAlL?{g=?Yr{$I3Lj)L%H$`Xafhpaphw)!VWU0tOSuB9~q(!1AYyg@e-kt6<>TDH`eB8Hh<&{dxArwxL z@gLDOU*|nc^-jY|Y;e!4%a#P|kC%h29>Nx*;0b>&=LkyTsCX@hbw8*S@&qqZehkj% zjmM**ycn!NL^X+d^iu`H)35kFO<_T~w`QrhoV$+l9MDp~cZxSPf*Rfn{#B>n&)FeB z3}UM-O=YP0a@j<5u@;iCQv(|lq}>ix7;3Z4Zb84{qWtle)bAEd_-)hQ-vVcgM&zTc zC~rc}@9QqGoRSJLI&nQ3wUGMC{-X_JHp(<#r_QQlO>|F`=$HLHT98E(Cty5S-g<=HhApuC$WiMJ zpvIxg5^WCip#CU#*YlVx8gv-#CG;-OmCnB`T{GC`Hf7=+;!8U%v4Nd-i%~ZA0?wJY z$K@XkYN#b;nm@EO6-Dx8ni-^Q9OPQd7aVWy>n_%K5SS;e`V7-52GqvfBzB>u&v^+354`AjI zq?p9L4Pw`RK+WR!EKDDVTdYRBZf)*~6zk0P?RkWGHevVgk20jrqKu?`_*KyUD~!mL6U;5|_%J-BgIieAK*`a{T3}T}XC`+V;!NO}d0uutNjy2gpo1-FuS6K?QLK z(0(ytBZBj)zTQsY?kfe@h}r%X4C6gC_$wGW>&|#iMKDp8(&X+`ke1TVUozKtK52#q zqX+(B*Zfly+e6k199)=cbdj2L%{1pj1_GEo;0AneDUrHCsT)!$&q-OUV( zEKF2n0IXJ8qm;h8Es?aY@UvQ0ZmrEM`lTN&zc@CP70Px5_K&KT`^b3jFRXqP>s>a; zNMKmDCCSiGX!;zsdm5-goF0mI!ZgF+qe&j?_1z8tc-MujiZZvVN}_zASYpsi@&!P? zBnw@$KYN%l+Uw}QH8F_)Yr^U_-M?bV%n+Xgx(j?$%it>(p#p+UqeD%TY z{`C#86?~gX87_-IGCUD*z$X#Jy0%CG@K=${b{ZK~3zKd3#q?6GS@AU{5%xn$zz)_3 z73_yHlm#NA@^AC>yaDeU&xyx!N4YhrAB` zri2bwq5P~x8)wP0D{{uZ&qpI{dn>M+=K-amCNW_lxqbu~6WB?RTz0C^_m2(Z3r$gPvHdhkZ#2KBeROj7 zD?v=+9f-saM%k0Ou++e)HtCKXGnmIT3o72JCv-P|6xOf3NYUW15t4UtugS@p;n(fN zBmrP3j@+d@@n@Ixo3xjgM3IM4y?a=79ug2v1ADP?zA*0uP?R^|8B|4=NhQ{t?FPL8 zKqZoa`+A|b`(nu|QuZ<|G-6$MVxmK+paDtIlF7V-j4s>&jxxd6t#}6g5wYAv?01ZQ znR*h{=?JG9NZQ;DyOi0fJTf}>A$>>Qe zfecr$uEA8R?Hze`=Io!f9CnSf;vH1z7gUxRRh3!S`e-Qw%|%+zMFCBm&{fUiCk#2P zHX!b`*RL>b#PIGSq#I_zBd?#s3Ov6Og#*32!5;{v{8c{W0(LM1HJ~FXTwzgFq>l9} zIx>OKTenLy`jN0M-v+#!sUvaNI!E_gfSv0gZEj;>r&|KWQhoOG9pw*ua zQ3E~Bpfi3HJ@jo6FJ)!~)-;-Ttcl0-VGXW$J!yV8gxCK>;s>1qfCgu&=KU175cN7l z^a5m!{axpwt8=U&VA;Z#LM2fOVZBiIo@l#j#mE! z%2q1yb$QI{s)obxHQ1lK2su`mk;K(}mMq8l#RDS59^q~jU7v6h5>dxRb7){_+8zho0AOD=OG<368C-ty-}(W=b!Wi#5x5IAvdNgQyg<-wwpTT7R@25b?HDlt4Z@* zId}!XsD2|E%ci+x7h+(Xnut)r=u0upcEX4-W1?I!equWr4`tSSB*j}`^n-s#hsyLhDeM(Au?D=2>Vh@ z?m3F`qAbaMhankRC`xI1wKJjg4j$e7wv0A;w!WdEDUSSvymWg^U~o^lf>So1Ug`q? z-~|mH59Iggu{We&NR)25QW_f(*(th0zq&0e7>5(54r~zf|9o*h=yYxPZiHa|j9d|G zb5i+tEm_i|bz6#YOpIwzOK!vag&!xvbA0Yb`WmV7dpcb*PY$a&fj{#;w+sj1DmjvG zaq={kQ#TuV4@5txJi7UA)iSk6HsqxJuzgf2usgfYI?70pBGeonR+v(XLcHMBa#}y*lx*Cutg@V0mpNj<@V48aPu{f{bgMWM$yGXN z$sk+c<9^i6_qKQEd}2$aNpe~8t9JH=@0Qx z#4Uo|3V_7d@U$+jQSf&zO#OBJ1|(kCxv zVsODQUP5z7_wg@|k5l#}n3bk1;6W!8Y2t4 zo8)|0ensk)R_nseZ?yiDh>QIU^Q6o8k%Cj{4__sY_zG8_{U%jbRyY;?6x-N>)GROo zw*d6DdP1WcqPQ|^mdBhlU|Kg0h&oQ3KneiBENCuJ)e87YQ9~khjU=-}3mb}1%!ynd zbs+FlXyZyODxC)Zb0;9HCvlU_P3FxjCt6Y4;WHu??_;Y5@xKF1qH!36| zrCT*QH_b1UAN)$iqjDT{$Wtwr{BS#rvP0B9_y#ZwlNKO;CV;<9^IG8VM5iBN*Jc=k zb&-S)|L*vlmm89+2fP2xRPl_ut9=4#a#2Nc#nUSrb45UiGI1Ggc1Sga0}X_ zb-AR2?fQ>t!RPL?Y^5Fd9fK#}mBM=>;fwNY86v3x+7n7oypS)591mais~^>A*H2iO z&KS3vo4!#sC3-U!yCL5FfC@cjNEt(wxdBl;%^?ry)S)ZOAv!8;F6cKl#Ve(1rgA&? zlMzx-1S7s2kcitd6}GYd_F)6_26W{Jx{5@o*xwQ`DlE8Dx;ZkI{=p{6ovB0>*T3&~ zb+7R8y31c0c`uVlMyasQmbJZnQ_T4qav$>J#(&hls9(UX8_#_!=9H)|arsR2+Z*6W zTn58V&#Jf>ELQ;=?w8;uY_~8S!^X4%T@a!{(SmONsDTsFp7Tnm&M%OI>?17{nZp)^ z)QzryKj(7K?Mh4dJ4VH;i7SKKA3$Q_4yx55g{1|LK?)6s9TQp9fo3nAK`qs|g)$b*AQ4+km&^slA@S#>{VwS&{c2EdcK1jkTrwqNC1zd<$ zedN0jju-qDJ3sSX+wzNiB;sOkV~@X|cZuXe;iI(tOiP@iwoL73$`nJxXso83!^5z} zIb=^Box$(+ska!?R4Yj|8MN=~ekgxUKro-IDuj9A*KNvKR4kCj>KczkNB$6>_Ykrc z>O`m!sr#(hKd~imVZEC(_nzb;C)e7()X>hYA9-1By4)9a48aU=S0TE;{)Nc5*wd@< z-X9%@2t-uVQ{WWn7=I;de;;%nI&g`2<`;U&kY?KMXqxuvc11dEz)3kn71pRnx=OpdWt9n$3rm1&8+}U0L83jL7uoWeU(>1MO_C z!c2?T)~xnS(z;SzV(>R}G1SeP2CqkAcU_EJ;`+^iDUK0bCVP6tD;SXQTEo!g=~dg# z#x|FYLiO;K1`ZnctvpH<4gy1B!#PLdwSa1AEuZ1>AyBzO(cLD;xi>#STlo51NcXyc z7R_1*c!;AF6y6ZCk@q~&J0D*H4qrnYhPBw4F5bb1%OoX{gEL3QwZ%K@hw`EWxpn(r zh=`R!QB@1ph)4~fm|zO8+0ZO)4=^E;`9H!eTo*&yGclugA-SFg$dwfB%_TSFfK8DJBn& zk)|?0{}>n4AjjM@S=PcYFCWWy!F*C7l4OsLfQn#L}NG5;WqZWCr*x_UZ)==Ub|_8+iNc)s~l}20(e%qqIQxQ{@NFcYMNyH7(!Nz-xTQ;082$rleyb*cjxrA?xLnNxQE~2G_Suj)a17-)U0d&8&t# zh79OuJzl8D9PnL@Ta=X}o>W0;IDnRRHY@}8LY?#@nYLZXleRPrmo;6`r=FgRf%5!= zc&<)oIY-~2Y0lUYR;2s6fLh9MmA$9fm|l?ISs zsxs1geE|%oNV(R{3U%DrOr808%O0cXx7L{b(yn8Wn%UG+i2L1dp-705*-lMFFM)hJ z`i@zjIG_y^v~dUK(YJLh^++xFzBE+Ac$pNY$d|vNG~d6Nk?Q5?s%(Sdz_d zH=1>4=(v&GloXKNXU_QX$V)nYh#i|%(#{xZAsfM+N@StN7Bz^bKH?>lR zyEO1AZ@ZwwraBR>ne1gkQDV(zP#AQ6X^F_{?y`gpy#bydpXLhmtDP}<31n6^C$?&@ zLgE&0i$6qtNKZH?7eh#tHWM-jsxY9{b5H+il8luG!NgaCBYvGWAYMl|%`&BUBB(X? zI3(x`E<2kZYfFE<8MV(wFR_kRWuTgo?@;^MZ650LG#}a@bV2`kBH7S}h87irnD0)! zecJCUEFuYOl{cSpEk!4Q=P)k-?sY0lUa`oLeVURv$i?wI;o64UN>0okefaFpGkPe; z_4@Tlk)!NKs5tzJ43xIYqJtBqKk6-4;&+tT9^qbeY^>OkUI2PFjE$%C1#|3tRfs(n zcI;}~OagD$?d=`-*wAd`#@vQ#*=4v*oc4SL+I0w=U>3mYK4C*JX$d!Wp~%(7!bro` zN=v2u6YPmC7d8@Xog@Oo37fM=OH7$6@>y#!_zl2zOHv3c)$Rosm)E@Yo~oc#rfQ$) zVX%qlaOffxyhbtN9~z+Sw~7&n+Bw$%mz>0%YW@aLa_uK535?e?s+iHa?2P)7^#)j> z9i8gLSeEfg)BNse#zAXj2bfnbE2E0_t5Y^QXV z#DSA!bA`S2=7eTyAcWT{13wjV7AA`rs+-C`F^tpMm4ZSMhZ3{LfeCX|^*NVxOxvN9 z7b*tA5tJpTrT$a%ekLL&y5i>WpQC(W!m|9P^K@Xcu&xXET&=C|M>Fj;H!CT1LWI77 z#t}-cnNSoDGvxzFL>uBSGGT`K!Bz;5(Im#E8Tz4C3v!loOg~x@#tu_gR$_7?s}_2U z)Le-CaA#r1DzpgZqRaBczwf|Os?Va!cqgLSo=pfA`AR39s=PyA{r(1`A^y}pz#i0?3s*dv0A@!%E5YEPcF zAUrTd<6hj5m_(i250GzOpb~pzae6smQ@*#ZJniuWH2F7JzvCXkuUWs`zkH$PnTVcW z<&5@eP$Nqqk3h?k+E4m^JAerODK)gg&R(0-2b{vs#eV-HPg!$thuKxQBgym$@+al& zPIeHu>N`V`hv!a9xJ#r}$dV);3f_`el|TaB(4}MdIzyI;6OGX4CUFjY%F7_R&~EbJ z-Aq87?`{6vg6Nkwz&08wUucCVe)k*Tr^z&7QU8HMZb4P0vq<8G_y!pb3fTrQVBEsD zOmVid!G5QyCVY~Cl~8-i|Aj%m0)5LU*Vd%vqn~EE%D5*C*I4PAH^oo>cqdRksh|G$ z{UgC-AJj&i5p^GuZ%>dpZxm}i{X;K9@ghCD*;>72(NAKTVL%sF!Iu|Ww&O^R5t*w{ zAN)b$Ir!R|=FSY`?!F0fb&6o=lz?GQLrex==2JCVjPEHE7~0K3a}sX=*=w(w(i@-` zmLzpHRR?vFt~P3zfQdI{4m`chjZobAlC4U%+!j?cJ!};PeT{SaB#E3JwWDHNaTQhp z-JcORVO13-?DNrFxapx&s9_R2nB@ACSMwn-o5>g5y7)9swD2h<9jT*T^mMujp?bg* zrId;2≫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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/italic.odt b/tests/odt/odt/italic.odt new file mode 100644 index 0000000000000000000000000000000000000000..d05cfeade44128100d76b66d46ac6e6671888de7 GIT binary patch literal 10426 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 X`j_y~Q3C)d(Eps#>(2{LOzXb@0OmxF literal 0 HcmV?d00001 diff --git a/tests/odt/odt/orderedListMixed.odt b/tests/odt/odt/orderedListMixed.odt new file mode 100644 index 0000000000000000000000000000000000000000..1aa50ff06507f11eaf329300d31a48ea17153fae GIT binary patch literal 10580 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 NpA#yTce9*b{SO8qh<*S7 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/orderedListRoman.odt b/tests/odt/odt/orderedListRoman.odt new file mode 100644 index 0000000000000000000000000000000000000000..7266e89bc62f0cf5b22d3399688913b2aa142340 GIT binary patch literal 10622 zcmeHtcUV(Rw=dF>A|g#dIx12^=uMhb=~bx`LV!R>VhFuTf29gi1f&Uw6zNEjDjfj@ zq!*DUy@_-Niy8-hfE5e@LPJo1uTq4BgkM}Z6~X={ck0IPQXnuG0)t?b zAW#6XBMNnD+r=J+gQcZPaO(2E!hd&$=?`k5_8@DB13(Unwg({{zWMY$ET?L}mp_dJ z697jG(D#x2Ns0j@{`*LfD1ZX^2Q&!n_ntC>l_7-pu6y^Xxf3NZ);nx3XX(*ANr8|pZAyrY9 z*TMXjVPT!YB0QZQZnCMNSXellD)O>=E=en6Z*50qC}m{v_D|}Ps7VxK@-HZvm5uOi zky|uZ;H6xE*>+I6ZiBOpJu?r+)NHKX+g1>VK#x?eFgH4vjf}o^MMj*zt?d zG}l>6mKNq5W16^csQWsU?DO5F_nli!D`Fv{S&kVI2Z=R1T~+uHwUzgWMIQ5EBH^#? z>bEi2rWXiN(yVbQQ~7&fS9@HL*+A>n*7?5KVHJxl)mBUKYT$gt_UoeK zj^&BP>1KWYx$RYtDoJ|nJ)q)qZ^@PE1*_zeZf-@hy5*JjM+$R7Fey`m5O9R%?K|B= zMTu=bQf?xv8&5mpgSUYl@1@LAbf%RQ2bV-Q4mT>aUx;KskKmftY1z5EyZP>;o2=hK zuyJQB&4dfYq-%E%ymw&xc__rgIe3bF-mFd%KF^yw$tDtUF77B(__#=SpLYA4r@#Z{ znMnz|wLnd%4XY7Y&ovdJX4APk39d+3P&*dAbTu8S&|f zL;3Zbb2{Aei>=cnN@M|FFRc~zR$lbQMBIHa#cO0pJh(>xbE|P@(_Qt}lan#$7n2{T zD!7-x4@;ybH)DcKCVhIIj;hfEvyG%5cQ@>TuP3!QBr{5{U)iiG^*YpAJMwVy9<1H|h)~31F!xXvja8Gxz

    #;GJw@{*8(K|WZ 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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/orderedListSimple.odt b/tests/odt/odt/orderedListSimple.odt new file mode 100644 index 0000000000000000000000000000000000000000..4fe543794d5786f7753a6f9cf35b9f2fa06bebd8 GIT binary patch literal 10570 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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/paragraph.odt b/tests/odt/odt/paragraph.odt new file mode 100644 index 0000000000000000000000000000000000000000..b635b216406c1d63484ee4355acf3294d3687675 GIT binary patch literal 8538 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 URIDBi?F#D88MXerVLmVY7dXcbEC2ui literal 0 HcmV?d00001 diff --git a/tests/odt/odt/referenceToText.odt b/tests/odt/odt/referenceToText.odt new file mode 100644 index 0000000000000000000000000000000000000000..281055aa0fa17d563498495ff129ef0446be283a GIT binary patch literal 10179 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 L^GEX-vGxA|Z%3z( literal 0 HcmV?d00001 diff --git a/tests/odt/odt/simpleTable.odt b/tests/odt/odt/simpleTable.odt new file mode 100644 index 0000000000000000000000000000000000000000..a006229182a24fde92f80acb4ba11cdd902d60b3 GIT binary patch literal 10705 zcmeHtcRbba-~Um_j!3eTRmR~U`;?K686tZe$FZGra*n;SlRZL4X2>R#y(vOQ_DJ?7 zS&{Ce@@d?kzQ6na{rme}9`ED2Ue{|~uXDX$=NeB{#nZS{00031kmm=LGi(KsZ~y>+ z;|EIu*jn1cG0rGB6os;}gh4TuNCeOUVakhyqAk(9NE94liiFwQ!Vwr=4BQE$`kOMW z{6B>TTa!T|%q-3A?Y^l&gMel>NGJww2mCHYKtS-#g=3LZKjeIH9`)`s+ls)R$=>O7B3=(Pczqf|QKr#0J7hWD) zLqQR6n?Jnt&{?iVo(2GppW|q1SlHW|AfT2uXdvdK%8Npn2db*vA|;|F!m^OcLuA#l z|H}XX900-b^l*_%2?hX8Uz3-W(r`*#9T`PiLnQpGf1n89%N%7v| zI!+eUj6N;woeZk{9+|~bbRSm$C>$n!j(Wo zr6;#==*BDe3mwG9;LWPXo3y*0M?(#Gp9K8g8LV%!+Y_$?=N%+Q@bx|qZO%46_By)W zdjFGD&zYM{RPL((zw-Z75WqOTQU&i@#~+qrUnGG1O%>S!X=Cs2`SKJtd)=Vul;eF& zGB=A40Cac(0K`}>7!rZ`k!n|yx{;&TsM^-QaFLuJg5GECs9SBhGD3D5pLO(pX*~ju zr-zJRp&ud^iu}S=en2L^(mi4XQja!mk6;*?kbY=|COA1FU>Bxnsro7uSDqR)>P zv(|g0G3wqGFE&ZM)b+UCC6PtGJndx`>%Q&Mn8ITfH_tL%=iGv}y~eYx)5Xc#F*pHF z4Ju~@pFfmlx|7F2>G2-V14;)AjBm}dT@8@7pu}?WNcxIJMS?;K8>5YfJk*$?ioAP{b`6CU##EcN8KJC$?;9`)*sxh?% zH6m+#ZGY}Lyk^9@_Jgbm;&Fg$r;Kb9Xqvk~F}{S@4LqZ2{A9nEhNkZ}t6Di=rdgBRCk3tWl& z@WNOsr===ubw688RXE}n8fxt{ec9&Q5lAmV5oWery<)r7*06hJPWC!sS|$0Ic6P?I z55|klAFq|gx$2s$wN<#ivpR1c_DpYT)D~?|Qh}y25pKM6zEaUXz9wVE`f;~d#xrzC zBwm_VpL&8E^c-a+uM2%$1M~IVGc`JG0&>=^#bOD;+l*?U=?t?J<*?O)gE2f64U>13 z=eSs8)14>myq6kzMwk+s${~Ry@75dwq6>Nb*td*$WX`1ykSfS7!=(GU@CyRx=%PWJ z1|j*2Lrn9!5c=z)Z>z~1s9&LdQB&)@@6*bA)Is(S!{2twyjd}hRte=)xqTJ53Do&;OETUC`bWxTiACwW>JqU!x2h;xc^Wtabqhy_ua5>twd9v5YJ0Dmz3#>D5@3G{Hd-c4 zj(p+>OnegiVBdEBkZl~{CWY6{MHe>m<@)0Otdv34gLJ%Gi?%(fw4ZjTR(!0h5&eo# zUnh+?RhArlEgw+a%E3Zwii-(;!W-mDw#%8!ebn=(=WdrPWg)a&U%WHPaQ1KXUV33alj+oD*GCO2X#q&aI$2`fRrgLMmoIRxZ4- zv&D$cn{9dQx_6iQP|}jKY;!jd{n9%r{rut9dZALoy(-Ua-`3fFT8FTKjWEyJtEA$F zb&heq6>ZPXuQY(Is8(DWHtIFCUnc4{fmbs8{L|m75(Lr@Z)CuVHx~PWfq@GecxW494R14)<39qyIwKYAH$L{f`{qbtC~}RzESq#OH1s zNwhn7w7-FrWcS|yzXLh6*nv5A@3cLq+h!8H@p&0Uo;=SAmMdwpU%g*o-sKglSx(&k zM2JD`?jYlW%iNm3k7c01GH@?x!`rY7lsPc_d^Qc{ z714WKdL!vCHJM(XM{&KsTc3Yl59h@x1l}0YzY%f;X6~N;KXQH3qf(#WPA9Qku*hAo zkyvbz6c+JfAtDFw^2WMiq6V^PyvMqPnj%8I)L~d%JLUw8@jNJu{3-sK*fp4}mhr17R`c_>vlyht3I>6#{og(`+>8|wK z4B7jpI$pDkjk6*xkPi?UUeC6L#QdwdMWE-j9_!Ufop>D&c#F9PpDk&zrQI<*tM@7# zJeCI9-`@H3gbh^n-~jZM=eE6WVD}{1#=^p6jq0bt;OV{!TuVe;TVi1!W@0P^C;7u zM30D&d(_pjOgk#1ES5pfiTOvz_~YV31O|nnK<$vcZHV3duSa*U&8YK9n&fe?$CPrd zhOLi2vfFk(AN1T@H9oz1hjzWIMj#x=U!S+2Ccv_A=k>wZ(K69In(+o#GjoVkd^|qP z;vqPFR{h1tDQlo+iJuaBJdzuK93(|d89oZnAAGL&xa6=y0kw}=z1hl|@8VveU#nN^ z8DOP`)HgI7c;2(x5135^hH5_Q_Q)rqFrpg9+cyKjJGZuiT#jBimJiQx^$FJO43LdZ zzbL#$^f8%Mm|Sl((H1!Zx{v}H*hj*+Zi0zy4pu!AsJ_9eXxWD{@v!E3w)20Q^- z93>aqbal?Gbf7pd)ChiOsVSp#8f@EYf))o&)7wE&0Rzub0(x= zPj%_h*v{={Cxu9dX>MtIT5{4M+Bt!J0AM2M&wH^(j{;Ty<{+}IS#qo_Nn&bmq9mm62Ie0h?CAp-IBb zt3$-K^fODhAhOS#39N{?wz9QB(M`jJ6pR^Rl&2ccHc{NMY3HQmAS7NP%N+!zMJ4bL z*`0AHt`pm*PM3Q_*a^0vdAI=%F;Ah7x5!ZCh?bjPtbg?IO&=L|X%wD8FpRzF6baZb z1hK)`xvN13HaeS~*Bdq_>!_5egvoyBY8S!m4P?D&Yr>aGHABsi^TKeBR+W-(k=Iqv z`pCU!D)QO3+IzKy2ff;|5tB0Kzn+l`OxWxGU>Dq>cVCiN!v}p)fOH=1?Qj7SU$LQ> z7*}?gWa%DxYBH@GMB0qZ&c+$9sei~2enW)ksJOipU0(+_JV(-L-i%r!+Fi?cTDX*rD&KS>WRLC<3Q>`H zP}}cYzLFn+5~syNc4zNfUzlj8-wp}L=sD#>EO>)D)XR^vWyEWb(AB^2l)2KF4KEAN zp~z(cBLzVnaSY9<0=1n-$lC2I(!z<}b8sG(q}_m}%A8v!Z<5gQy*Cxu ziN|7(?@xRBV++rU-vAv~^Q0~*hurHOs}8v{y=X{Dw1}Swh01$N8C|;Cc#~E`1M)^3 zsYn}1e6cg0{#WLl79Psx@f!J472(p&Fm-SkuzPD1UEdbUVkgKx_@bC9T*ln*hGZSb z$tTt~)is**j;x(i3RS-t*Z)k}rsCbDF>Owz-I3>4Ki_MhG}2=+$9dcti-U8`H|$|% z&J%6(@o+i;vLO;fn)XLuYDaXZ&U&Ft=J`^GsBUN`5mUn9Rz&nYX`L)XorvQeUrY@`6VX#FZM4oTIJR~JPZSBI1)2(0vSn1X=xGi)}Y#mh5>8p7&6ZK}#ux z<-wxy9;rzLNPYU!qYc-QSl)dxnqS7C%c`@px`-Ju?>DJ8Y`B1o48ON;$P^Ig5VK?3 zu|_;0)TP?Dsb=U5=`oXRlZW-CkT9gggL&v&oBPyZv`D|m*4l=+-6@98o!F;jg%-|5 z${uxO&RpV|eEm^vcwWNJP3K*uSvILLr}#v@7!F@5nWv{DZVaQ68jSnrliAj6c@C}- zf)XJshCEdP(uGALI=R94ZVpT$N{6!J8Ym7-uWl#edIP_Fi3xMi93fHOG}TmD`#>tV znp3lgmvU08q!H!sP9TKBY+b1zP2TxtA((Ser}ao?*iUW4?(3=V||!>z*8zQnmazDx!>Yx0@UiyLnSGMIeL@O}D( z7S+=lqjW%wMjp+pWL2f!I!-6iRF4N$f=$bJTH~7Xw|)9t*Ow0kkn;xw{0dCKx9o2m zFG!=o8F23pn(r@q3xBm~C2UrT#4DoH2_L4`RX%6VEzM%m+btKyTl*a2=T;(=I!$Fh zx0TLcULqEyJI5ggUJpMHx_u}AOde5E zMU8Y^+qGAB*(YguRO1vv$4+^}2sb?;Ygg5$lU84?%yA^dU>r}w8=Ri2$*3@|9_yT|m# zEXssWMpg};30 zPn$t%@o3=Ncv&N;XZk=yy=ksNbt6R@g@ymC-G;k1+}!j{#tc+V$OYsk`^OSeElATv zGr}$WQ6@*o6eN@BhPGTOrM8ekRd9@ZY)C^KJiEHSkag&)^_Zw+r~_N#t(uj@ZgHJS zzo;t%A%ke6;i{rn7d2xQH)!!9qL{pG=m2&DC5ox&fO`WEG^! zPL}Gz&mvSyRObMf!2~XiD$KuCCv0D*X)}|H5z*^GUnH%BF?2B4866Q_nn`aKF0GKd ze<4lKZ%XPgx(AcJZbY-MPGkK}N=D6&@10DbMRq&MWXhDV`NnACp7^_>P%MN{rtws;xF<6hhFdKMHZbWpAR6VC1-3Y^N6)QQl-()6usog^2$AJwdu27; z8z9t+cRI?G5TYUp>7w(QNd)v}vtKN0DyWnciAfuQ<_;Kk-YyI{60W4k-1!Qqbn4Nr zAWXHXx!MhnsT?3IoPEQ^m=nK8D2~ea(#zkj#wEvBL|r;t`gWc4WpkadB{jDLyX0l5 zEIkqM>gfEZrynfb=M?q+dPMw~?y*t*NM*VQ^hFPdeorU_d{GypkooR31OT#9UiR*h6fY5#a zerL70b6@(#H}|A$5+57k=B<3Thy$@rss}hlJYr$XXqP{&Y2NK0;~)mN9HkvPtDx8s zEvZP{ILsrt68AKzxb-bws)_l4hl4t&Mava^^{f7KzR&eWR^y(wO$WC2vOP7i zR1v9q%7j(XMoaRpBUNemc`0+^c<*$m&dB5JSeeJ_#ey8zb`-X)nPnNMTKwEKf>m-g z?s40lq$EX!mbZy02gOkzmB%g?q;gB!s+lW~b;(uux54t|*Zb^exO1NYVzabI!^`9) z=Y<|FU5R#&R^+k2W&Y5$QiuDLNQ~Z9^CIK`9sYoY*gJZtqQWde2O(*V)M*Iu%S3Vg z7PE2&jU6^9?F95{H+_D3do4yIWDRw`D$GH(Or$80EXpD?vO>f zkCl^rT&rVT`_}!@bDZob{%m%~Y+Q}Y)_fKfr>R&j_*lCHeI%{O@`5MG;z`BT4wkNp4we^TZdzQ-Y#`~FTF|a+ z@MuRR;C1*1XWdl%g31p6M$+#a^|Qu3ASBg|*Wi>bsJf;ebitxpr@nRIt)|v3|CoF! zrB~HZXH%y<2~c(HEyEq2P&>lv1!0lh$Oolm{qJ}m@k#1`=JIkC&A4whLYA}mG_^8T zru}9&&U9`viJFP##$?bXBp_z=9QSUo@wnn8HtnbwV`W~_ff{mkFb3|ksb_PF_{jCr z3~4=W8Ll{<0x%#M#Eve0850*tRXTH|n4`rkFec$fa-43~ZPx zz*m;!N|SNGr|*7q+7ZyuS=ZQ0NK;UYzbStI{hX2bA}+~`FADO)%r7@%Z;IhGuGZo9 zQqUB9rSM-%N8uIPzHAGfUHdY~ZTOitVC@~Cv*%0Z*|k&7Q*wF9pJJHcMNiuTbI8Hi zTz!E>_}<>v=R|UtCRD|U7QKOx_S*hHz3A8Tld+lvG<1XYy!p<8N4v>iC%E}4jY?@$ z9u)~*y@+Dz8`{_nJJ4mWNYw)jS9iVTXJ&g9@BNsvfbQ+w`Je(Ev4I-foEG$0cFd#16mU<l}>`(!$x{@tB^8*H&uYsX6*8(;t1PQ+2vzWn4@I840f_A7H)r8UO5Pn z2dCHxmN}}SzX}X4RKyY25ULM7HHO^d?!Tu;lIJCPMVw-gC;?3(V15|Q0i@D&dh0#$ zA=g9-T(kPXr_X3dA6ylw&)b_ zB!+T;lLtdpGaI7O_vEW)VMk;ew{!N)#`*0u9aCJXz3a#OfnQhszwZZ1cP)DHZ~y=w z>;>WRX^SlsVQB_OV|eXM%{rqx5k7q6zUvZx@UEd7Ks-D<&h`qcJi7G;ZEVpY5qPe;W@hRV5^;u$ur ze4Zv>t#m|O6*Y?S;}IsY>3*KZ=@h>ual4wO;ho4m2uW*cC;=g3h_vPQj2o?J*9Sr~ zEj7$?O1Sebvt-b?*t3)pB51jKO+Yzwgx8G_LZxHshK; zpEL>M4X)7cp@|11nX`uPYl_zNeJ0%=S-7mhT*nKW+|9*6JOAbk(t$-T4xnzF^Nq_C2E^X|AHxmMKz?3+;0f=shyPQjj(LA| z35i7hW9WDc--r0k9Eguk5cs`)V#(aj)YRr5{$B=w84d>V@eA?r3GndoYw!z;fv$=1gLnn_e<=8!Rl*b|_AfGmLSi66UO_$y;7R{6 zuwe5m7#9FIkIk>jH#MYqaD9!UzcNab0%y$j_R0vhE`O%sBaPUIOPoydz#^; z?36W>n=l>hetfiAo*Qz zp#&Q3=c_q1&LPFBbNeX9Du#Z!N0_w~lbq$eo`)YxMNB$@)O*oy2vsmaLNN)Zw!>G% zG?e&?Uo};?C$zPeUeT{^DO1(;@k{*7j3G*W5ffVyzP(k=4=rqrnsOmJOwRH{O=}RR zH8~i%dqUPI9~G;;CI49Kdhux;um@>I9eG=RH-8N|P9VGA)7D1ZH{2*$(w9qSzlDk7 z>vvjn$+ka}fj>>RxqNoW1Lrsk{~AhFMVwPqfWL#Ou#x_yoItDol=_9`8#?A^TNzvZ z6GQY9L-pPE-%wOPwfOvtmcL-C{*!CR7^7g}?uH_hG^|L7dip4a@{Va9=qUR?f>+f2A_h$QF zwET+D`k(6I!J?@CjPkFDt>5+hiP`!&DmYfp-w<3U6XgBzn&c*uLyq@8q(iyJQ xi!Iof<~SW6FUC%!PDc1^B00{s@1LY-|85H}~NGnx+#^+fCaOBqJ~ zpF)eNDIuI~?d{xLzp6nA@!P@?U^LW~|CmgS{t>}cux|V=1%^PNa41Fz!j&K5 z=IV;I?db%^1?Xv>#<~o^!QL?C@6NDbdVg1I?*z7kqWBf<(N16_>bp-rrsb=?@3%jV z1Tz6{*5Dr_`I8jmA50=$5q7Rn6zV@q(*H>kfpkM+js7qFL?aOJ|GhO78jN=PKX{3? zh6Fo9;lFw5ey0=$z{Ly;b75!G5a#A&?F_buqxjK3s(eUiyKp@nH8Ns)VhjrzNL|?g z^S=TBI0YcYKH-}R>5-Uc-3C%tF!W4a9qV%l6adKg5r00hbPv!|gse+l9Jl%?Ls$VK z>{9tOVcSCEIwi7???ZNAA+6^o74yQWqg62_)~Oj+Pw84_22dUZlBf9hS26 z!=y_NKOC$|IIXwMXP|n$3+qh7X;yq{vP{QA9gy=icy8^`w}bRSI5se@~ue(TIiL__fxAAEI7++ zmTQx$< z)g2~%U*$`!<5w6nmN5sZ$9e0oaDiER<8^2Ku8peF;B(IbY^ zO~J`#9r{L@SaDI^&N)bl`8AJV{t^RcFTGu3304W#O6v+QuN;6w=e{N{p1EXO-V7m*AcP z1-@=<_Ubn6dDSB9K^;{Xu`|^df34D_k@yU&cd!inXe4W9CTdc?Y{viAH5Z-&?v|mj zy9K9KsGfr47tC)!s-llhaByqtNfJ`2MPl=PG9Ro{aCC-ImAmA=uF043j-s2RNQfDs zWP7wUlMJ|1|}RDysh)ZRR`4# z*NkPDXCB5#c!DB{*806Rwk9Xa4jS4wf3 zv+y>K8(jnoeASIiIxZS`MKnX1k-_W{W86;3K+5Tdc?|LQrE*V82hB%Z0F}@dR5CA| ziQgpHHlUsf98#HBA>AiUDR#H?#^fJru}2y9yxQTYQdcTUi3s>qU3CdDb6A!1 znWd_o4)GxRf@ey@)2OL?2OONzGx;PXV`~~bGCGpAz?O%telL?-(tMU$gu6HLUk}+A z!sj(+BiprGUMzRjaS=T=0j@XGFD0dQi_kT?DX}~tZ;lA|Zw7n$Jfk!5!X-wqiM)Q} zs>zjrYyPxjdeULB?KtDe3BGqr#-|u@2Uyy-_Wb6y+4YlK$J`9=MOp8r*4qH$oWSWa zc=H29bMMr1$_66`uzq=v!-&PO)gv}qp zLw-IcS9Sv=HU$}Qt|m05mWOt~wn-SoyL96m!RKO|4=w* z^F9*!ohmgV1h!jn0l(t`69I^wSYaE-CXBSRJbHYjh3?^y8UIsFh?TAHyLQg*(Oka7 zkt{);i@xt#bGp$tP<4;_qWmRSXH~^eA$Gf!?95SM$>muwF_ey)=&dA#z}4sj;$Q7+GGdYywu68!KCA zR-H+yr74Q@S$9|00q;tiZBSt}lG7KCYYI2!F0;I@Q?K_qU&H|6^pN9SrE9v&;BBMF zj62lVW^XDwnW@}V)O8Up5*iFKdMva@a(|pZR7)K3FAFtN^Hz`J_ZHP)DD^ zI98|cs##P%O$GS;Q<}Qqx0N|qVh)zb&4eLdW~$46Tlpn+EAOe_o5(NVo#cYHdim&soAHkze|_%v4VnsCcsc(1eM7SE^O=xj(gq_g#tnviS*&;Zdr@ z@UUIS@X+#McnA{uu1E!AR6Pv9s+z{AdI76YKS64~48Cv3Q{|T^duczYy5S{4P}=9} zGB~32^)J_ndDvu=OXB9Krc^r%dSoJ(1>rTl0V(FU4+TY|?VasV*o}Y14O7&Z z6veG8FM+cjI2lge{-6a~gB$c`X<1*V))RR*I@lDd#o-b+}eI=2VDTcX3@P=*3p_e%0>q`EFa8+qPi}^noJh$y$4< zd{sNMoj)`WTjbfCd+?!}%Y?MrK7f;xRlGA9VJ9vOJxt7=+BzJIhy*3SU9v8fu=J5o z6D_t7p^tJ9tA0SAp1OHhnzuEIFk+j@2iCB@*UBld$oDPy;OA|(tX(gtJ>lrIQX+Y4 z*`bj2bnTxnA>y30Z7DcQKi%(HIA-K# z+_Y(MBp`gIMQ*cK`Dkv4A&u{goc5mh)HZBAXL(n(&_e4#qUjZ(;vN14Wvy-n1XmJ} z*s9-=?!KZRlkDiV%3fqB8)KXtM3IHJ{_L~IO;AEjLJy~kE0txU_oyA*QeSyb4_&L! zr>e5(Y;{q9m{x`2tY_Zx@-i`7@#i_zU_CQwg(Yk=h~25pBxp&5b?MppoSZ;l)V#Y?aW>7nE&fHPmXG~gUc-Fm)U<|2 z`;(Vo$&Z)=Z#T$~80};H1%H5yGo*$44w5`9$a|eF(B;5g}FfOl!TWcSc*pF!!8BR^Q`w4V4e}r>Vy}0?xDw z#!oYo$^}O`Z!mZ58#2h5?mjK(*L|n#p_QXm{`8Kwdn{`}4+otSTp)vLj+&|Cg~bPY zJ&3@fn765;#Vt7M_2AN_jgjTBrt8YF?^Vv9;AFLEAKSS|Hof9)xQpM>SQYtz;2E7l z4GDXf*#U>nn+{3>H_5PGT{1a#HsRBf&np8I9N@+M7gMQEZa~K*rzS2vZ-)(OtBxiy z5mUP5|^et zY~vWzlQ=LLoPWZ0(Im7h+yXce?^|T<$&DHmXO2@PA?51@m`LDIXHs#Wo@rabuP06w za(PxCR=zPC`NoH<&t|n34ClVyeh30yGrV!hG)Lmn@O+%&<=ZUj8=Y}DQNd?G1=^(B zaLU%;i$gSFgLJeGr0p~>O3vL_FQD*q6iub&7|-WrU{dd4du=d-H=``!|3uWj@X#TE z&f86%@H8H%Y?p9>@fe>oX*PrVY-zO*ok7D{c#I!U8aj#4pz+J#aB4DZ`kDuS@Z{S7 zz3sXL^yzXwWURfcFNwydWMN4ysFlGJvC{c#DM(0>z=VBI$3h#vu8&iAD!z@FB>~KWt92z6vmMKlA-_VZGwTc zo2*XCm7Ve=JbU;9)MTT)+x{1m!g{jq;6wo{rY#Sud0vX7$5WnzuW2*7A`^Lao05i= z7p+ozH&>s*7s&~gxecQz+66YRaDX-!>L8pBR~4)xLRQu~^v~8;kGO`-rp%ssdyUvU zrnoSdWn1mQe}!-mDr;_|OaAuZ>Ca0Uer~YOr?D}XvNt~VGClyn!}gzIEcTNdh4z9& zzed~uL&9+w%_c=NgU>~eugkVDt`#z~tk=1sO> zUUB8@oz$vAdjbMe&1PEXmsmib-CjIyRb9Vz%ObSyV(Q~l;ml;?^t7^!UM=LA^I4nA zFZ`0v&3@eX^HigbXlNEr^Gp%FDD z3n2IK@9WEiD(rmjyACyxS>As!URc3&gWY6rbrC&gH)!2p(MW@ci*Y%$U|q&n5CMo=ore7 ztG#4Y!gubyaaj{G#FtPMiQeXF7*E^V(yjaa#JAOEXRDTL-l5Ht|Lk^vynzKPd5YX# z)6QpUW<3>Dv|rA^EfKjaSh(W&g2EhOf*Zve-m8V-&J&!#<7(3$P_7;uWpwW0?Ix>7 zc*IN`D%4LzP~jI+@umzG#ncBN=EtH$F%B`ApObDrxNt^@-1-xdKM($#`f!?<#Z=a$ zF;#Y*Wfma8uzYt&5eab{LW~uBx zY-b6UgiPK5y)z1b^xd|NUjrc5gS#)peia_ceYg>Vm53o>MsNI!|#IL(NMDTv*=N z##;+0DeFTYdb6{aaJ-HqYhm*wcGL=F5il4J7apPx7)SJ;P4?-Yi`BlzF?Gi8L`~2) zwQug5a+KIp(Ct2DhRAg?=M zXEQ=S8O7h5tZWJP%NmMpu*o;CZKBMigoU*4H(rDD@Gv%8F;O)m77&}9TV-U%>dkbv zMB4=8EFS99>Nza(*Hz2UT^BX4iA?ZKjA~4R=GHb8vyWVMd?zV;*PSC(t!^c?N803l za6H#g)G*3&w5Ft;&L~lHgC0K?B);9Wo{F2}8DDgn=VA-N`!vvN?v}Fg4ajUNy9iZo znnE|h6C(XogNt$%5Mj1)jgP$sL>=q2ZMLcj5~h79I4P39G0$=uQESWAW-7yDjAThAMnoWtw`mAF`<2asDu;JdR5h+K@`UqM^bI zOzcRML$w$i?uD{5hQcng4aUEIGIe4NTLwGHOz4)>*V-_PI@256kMdP>vo<&d7f%~F z-SWJzn2=lxsKBdK9LaCKP@2qKEKzC>y}?5k+2npYlT{Q(dABXWc~UjoY8l7WT_Q!q z1g0sdU__Xo;rP5jgNbUVHllUJFG%~-HaCz(z_+43jj44wBGP9%)88>a-n6^#nWc4e zNA(EI>71s-sLdM#wp*D;q&0jB*R+i{QRAN>iyuuHd5lYPyFd%e6RF|q%6uH{4x{~{ zqW$=|@qR?=Ib!&*JS{Alt2UVp2x1$xexJI2PzAVq7&7Rk z|KaTCfr-rn1$gQMOT2=WPp~8*j`s$kp0W3V9FIFdxJGt8AqnnMQ2TNE5poU9&U><& zBu%5dvMWj14@+Bn@iVOLhHkkFM@!k-4%6AMm>FCS`4IHXbZj*#yKOeSwVxx~+FnPZ zCYuGLqK%&PZD)qo=(BRx)QSGtyC!1~aubyv7?g@!#I)lvZKEgl;d-UdykpsASCbyJ zU48gaQ{z={D$-qZJW%JsO&FQ#(ym_4%7YseI)b}$pyyWx+~#=lp8^t}Tpy3A0Lgw7 zy|cu1&-b1tubZ0P9q(!r9vq1T)5~@xh#>}oA(+%#MzE&FJYgphS)Br|I!R@!wAm}$ z=S+rs9ANrM@Z}!H!mN&Zv|-d5@_bFSyIzGvN$Qz+@6f03*q`6M{IOqu7a5vA0(&0l z;0a1<^+@X2zCC{S5+_nHm(wE`&+vky0IUj^3P=;^cr!FVC?9GQ#m8V$UgFYr2QvSh zoOl1eq9*VKZv^a7)#XlLcU33wMYNAGH!FvbVnV&peozxx4l#nJXwlHTzQ8{s!px21 zF?G>&R}<86y6mk{42jZi++}rM!>p8G2bkmqHz1G2M`;;iWNdy>$Y9g_B#+qz$AUxV zwxMGb*}!EP;8Ql}0)WuXfni%Yiwt3b ziih5`kBE`xtXXUb*gFgC0;)z zZP5v3$XXT>zu2j=?e6^A=V2a;PkfpL599aJ;5f3(|HHSfC}@ZQ*$oa+p|6 z0~B{TIC(~_if%?$jTtkVi(X$l9BPm}IsZP(_HxPhKE>FenjlxYZ&kkHwrlJ%LAjT9j^k~ew!#bdBFx0od6%Ro z6wx+hZM;f`VYNh=$r}2~LaE8j;na<;@g>s2-uR7g5S}I!aeX~eX(g08Ys7N@-ooho+b(G-N z^A462DxEIE{NpA@JBO$W;Wsq^Tw6{MP7+Z^1}7*Xoi$#`-+b>$)q?Kl<&~o-kX*W} zNQH+!>O^>Wp(=@_j>upn+e+PqXVArzw7_4MOPX?+I0Z#2Y+eZQ$4Xu~C`gBuIf6+7aQNp>Q zOT1{Ry7?%>fk!7s#hr0&JYKnT8|Qa3O>FQK4!)kb%za#>8^NR#USl#3f6q5y&s?0q z&i1xY6q?V~#u13h#NAdC4<*TSm7Q*!Wh$MV+*@{4OC8bCja}?wk+3WcLh_t+76OIX%W} zpH((uLh5OH88P^|L0#x`)>wb}C?c(nAao#OwT|X1;e>5{$;OP;nKrAsfxt`|s}1hE zJtLE0q&f2zQ*|Y4W`Xa0?!#`bL2kMYyxM$!;ht5h(3OH{8IoxASRXh?|d^axU}a8L&aWSGwDz?7<*hLa|Lr_ zb%(m5Fu8PDpdg7KGf&9aVbaRD&<+6eBV-oO~>@yn0FUTjz|AQCn;s4YrEbp%_ zArOdv3}MIcZHQmZ2?+>@@PBLnuw>_IV*~$(|Ca$^c!l}x_-(*wFt58k)Z+q>_4_>j zGT}l%xgWEObwf_(t26e__Go)BoEPE>#X<|@w85^JBSuy&duL}TX6ZZ2@c)tRoA6g5 z%=6^MScb|82?&bv3JCKG2pS5CO9_cd2@3HE3w~GdZ&n!_h}0isL`9?o#Q6loWcYvd zV;TSM+Ap2o9D>?lM&oS9Yx5m#A*W|3D4;ET^}7@Qt^40n5HASk(_c>LH}3D`Z@hL; z=WiekIbF>2(*3$x`9=5y_ypOF?VW{%SbvhSkI@nXc5r|~(EK6-f=;6Bif;CB8(v9q zL6Pq^eyaPX{-1S^1s~X>(Do44uk()vTf?Ee5QLjES{8_Tb-q0mEOz5}BElML?{_Nl z7f!+N;z+P7*v=JUz>Mo9c@@zeJz8lPLU9PMx2Uwxh* zbrnV*#vYp9j-oBLe`O%QXe6Sa=}N(2zbM@>wmb&_-C9qi=@(6*z5Z-9kJc-yRPVzf zlDURyQ1w1~E!{eAxuEaPR=I?A7eDpEy*ETU=m^n-6dR{eE-6DTfztNo+K!aA)^aYh z+E*2NHv)rGKe3{TGhQSlmc{ID*9wA*o8qT$5+A2M2}aHul4Lf!Tlo5^ubsPJs^3eo zRqsug{gS^AVM`sS3)(MSLrf4VANIAikqnGB$(9Y|pK;qp#|sR4uHDRaJN=komSJ<5 zeB{gTAS7(IW3QT-Os37D<@@y(9f0`2&0R z`}XUnMGeeLgAK>n&DamAA5-&dAi>7upT+UQUm~=gCO#%*2>?)H{*ajX)60%+{TD;@ BJJkRH literal 0 HcmV?d00001 diff --git a/tests/odt/odt/table.odt b/tests/odt/odt/table.odt new file mode 100644 index 0000000000000000000000000000000000000000..7a2b1cfae90bef66e89c6f7477eae58c767a989d GIT binary patch literal 10763 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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/tableWithCaption.odt b/tests/odt/odt/tableWithCaption.odt new file mode 100644 index 0000000000000000000000000000000000000000..d44654460afc501ffb429ce5454a706f3c6abaf7 GIT binary patch literal 10623 zcmeHtcT`hN*Ds*-CSB>hNlECTOOf6|5djGyKrjRdp(;g?A_yW?q<5uC?_EGaK#KGt zMS4d>LEsB2kL7)Q*LUxKcda|D9OlgI{o8x?nKPNp{^@F*J5Py$fro+79|FE=-Y!JM zg@J)_`aw5g*u(6hC=W*{*wGOVgMd*m2ZW$2!b-pa>$00nhN z>HY?W*8itmMAsA@5Y{jo7vwh>XCXmrxC0mkMGAh`!o$P+=E6TJ=*p=Ze`phM^K-?eD}&7Om!i{q*4fARC*^qf&(l*|8x zmna7Z`2V?=r&^9+1Qh;sI#hoBf{o^uC@v> z0WASqgjh{gNgw^c90LOr1Ml<+dtOO>h=Fkqp{8`j&^>W|Y+QRq9z(t_^7Bb!{=$U^ zL9xW)rtQ`RT>M&zX|-7pk2^j-x8D0zUMKZ^zU-e)8Y0Vmkh=7@3Y!-_Nl@)0|HaSC z!_7EFOm~ikMr{u6B#jB7EOoZOAnErP?|~STH*sNJO~-Fp>Y!T*1MxQD1|N&>wiVwk zNAg;a<{p)MVsYaFf9PaXl&wiget7qR9T&4wKcr#1J+waOK@ZU;eF<32S)SyFR{X>T=} zdYV*xkq7V242+~K#J6wC6&7wIZk*4xLT>2r{Ff;H|E~W&%l@B>PbcoSkgB!kVC5GDKk2!KU%=KAZ zRAG+qtV*12zmdgC*~@5Dck z23uw8?$xEnZoY7*HubIzqZy*+VKFiy&JDfS?<`c)(7-u0e!-f!kh^^A*+a4m?>U97 zL@quS6~omy+;JWe&&L*OCbYOIJdweKkWUbgSltOaKAbsz%+H)d2aqGt zt`dpu3=KQxFIASCCl`oix3KhtVMj6GD&1Cq0JWR`-->bN5#>SM52?acGdd zt1Z~wa+EQpAhjci^Ecj%#JMSmn@sq2qToKkbv!kMt_UBAQD(uCZm5e@9!=QX>zeKR z>7tpyH!m#xf(}wDQKUXuNZ{L zOI!glnmUOXEQ|ZHKCd!k?{8Gp)9Z^V0`^MbCHZUY)JO~-F9T=(D4 zC%fsdS}{p8*L6$K$Mf94qZ8bLyh=d*YR}!4xAhv7TJ}$$jQLs5FnCK`G(Y5(pEF!0 zLa|y{*Fz+%J*=YN-}s1FIvE3WFA}~~<4Ciw$Xz0nHX5q2o+7@hICXqkv`1wd@s)uK zKJ5PK>s_u;xe%!!TB}X4xl}gqO;OT~9#HkRxX!tgX!m-=(-sZLyw)Z0fYdyt80sPi zUs^uQTl0=AQw(J%2EqNtVY`=?C6Yx(25Rmli4l0qctlLMYK?YH6+GRvIWFC>uVoN6 z_R^1Jn7-!jb&aVBa+|G)_)8UCx>30>4i>4l>hx-oQ#XQ~gN3oY=&%eH+d`ocq^GngY1akM{-SvH> zQtB2nKBbB%<>NNStyJ)*MTelE=5GMu_-GNf_HM(jk>ktGDqp%vk$Wy!&|%H_J&A<- z%@vu*rTt8aMTh$z?P(3Jvhf^1c z-oDPke8Y=a?SQjfzppN3@gW8yzMmOmT<>Q9H%1zPpE~w2(BV)=ysZ;bG&B#y~yr_+>oCqxCdN}wzyVvjg_Ug&laGu zWf)1l|C)1+Li5AW(jzu{rl2=m!m~wPxg%92p!d|44M{KQjtTPg@n1~zmsiX&1Qcu| zgz9=zdbM3UYMRx08WPvum;fO zSeS^G^3WW%rEwYX~?Q{X65Uw5&Kv9C@QRHFh_h zFIySEVd28rNcqtDOg!HdMXP;Syf>kqmSe8;JTCpjboCM6a6uw&Ym~**LAc+{vTZoi z)oDU`rVF`>!#Bgh0EVThAeGh3=}TF}R%~5Y(8dN=(hop(%w5Xbz9yIl;db0i(?pMH zjGcxYE=QRc*?i%tQ7%BBNX$ql)1;>08Ox#8ZR-5tp2WTbN0{eJ4Q?+7CGF-hwRWdc z*Oad)`eJwtHZqILV|aGLFl`T0!2Q~@w|`t?p4_jqRGkqXpDj1>*gSI!jE*%<#c1t`AMWjsBbpXz6sizvf%U@NcQvA45S6%M&B@Npw*4MW{j~6 z<)zENq)su`N$Em&Ag_muL(%68Y1Dbqdnt)dUaqNVK5z$^UEY@TghZ}A@{;Alyfs^d zGkkno7qbnRqzGd{#aq5#3hr*ol-^M~U)0<5_JsrB!Ho#8IqE(z?LnK_wd;<`(gmS+ zN~}#bbuL$MFMCUV5@L;hc->5lwkbJ?J&D|mylqg`-GseBxdG`BTMt)we(yYf6*Q$u zvgP{hjx^&_b=IfUma-T5?i0U#)Wao~ZLYAbVgo;v#3NhZBMkYl2dS4@Dtm-8t=-G3 za!%D&X~WsHE_ImIcT#xf5wVBPc}1a@`3V3Wj;kCwp+bb|8qDq`6%V9d;tLT&*j;Km z7=wv{q%D%$Oy_+Gf_h42qAmf&wx85}02=Jn_EELr2EJH4w#1;;#2@tLREnl56$>|F z4W8n1Y40s*EmMB7Yrx?BQBb_5?A3;{xI_VyIs^Gpl9{NSfiK6EbYsSCI?X0 z)SvzwcSd=@q2Im}*Ucs)XKTnBdJS}CV+=pE_!2W(l$7Q~YUz*WPRh{KE*?a`z?Qhp z7snq6F52PqD3ew*iG&ieUAkj!(G*lalB;*3x>8ijQEvZnV=>2N@XkvZb>!z}x7afWT;cebp_ zUcH?-X>gLvE)lD+&$}+|-?!?k^XN^y5ksP1c6#5Oo%`8O zgvz^<_0AP|Nht4!6Sn z7Pi8%j9kN(I(=WGwk`#KZR|}^zoj~?b!b_4CwpfA0F%~gF6g9C2uTydBul+pwc#ki z7~Dv;Vb6akM$Ds4<=PlKsq*-iabmv9)pN2o81!P^RtVl|12I^JwL`@0{min9uhKpI zuvV*--3yi^g@R}@)Q6z7=S{9%?6Jj2!wE;o1-c&&m>)l{Jb^dG=bI;s$C$30Y(g!~ zFQ|4B&O@Y{yrb)VxUh0CMDO}EzH{)%x z3gJRcgk=wQCIbc&Nn!EnR#XSE^W7&EQIwXPSuAT;spq{33&hm8A4NPFS#!wipq@U2 z2Vj+yr_B)=94p_ro4tjN39RH!QTO2s=Url?9-H}`_gz4#=px(m*Vq^ zAU@~$(79`2Jrm|+ZyPdi{MP_({?iBUCafi3$PqCWkqqH;) z9D^E9GM>n0zo;9XcB0))BMj)|i`S;3zC@|fU2Rcl+V7pu&atUXE_)X=*zrl6%v;Eo z?^)i9+)`$*ua+?j6NF`)eb+~(b6wa0qjqumjt`B`kC72zy`W+uB<JGfc$ zz^jIg;D$siA9%{*aE^qB;Wdc@Ue^;Bti0^S=)RK868wv$L@_p>W3X;Q!=$o0iVHJ$ zm*SEJJh(P%9fi7UwmmoUJZWM<87oL0^9(@6sI~b)(w(Mgc!^QK2kc^&Pd4g1Aum?M zW=ABrcnGl0+1_i`H*tOnXX$b z_pzdJVu9kSTddJgfOK$*&{LAVBf<=Md`O0*Ew?&Jg*P{l&?shxPUPzXiBCe5MGoCi zF<-@1p3IAY8!gl$#a%QbC0^RxP#Y@aI}GAnPIS8g;tPa=Ar-c93>sYOg|Ec3Vl;sQ z=N6#Ng+_y{$oRX9ffsFY81r=9A-kXrDdj_93iY4Ahl(k|BW z=9o!7j+^$jILpI=>mNY9`ooel<%u3`iY^pB%_I}H@2}mi=f+f;Avb-6%fD8AFXHn) zXU2@BO{p+BswQA=pux+$!H_=e5u3m<0pkIE*Y!`(JD&`3HNEh80@KfpPwXxdXuEFu+hrsLq?g` z@+#_XkHAD}iHLvB*xF-8EE+y|m+MKjttj*vdt^XeDkdnH#-KRAJ{=U{VNr~GQ?i^Y z)>PcVG=iJ;CjH26l0=ZMNM&?SXvx#Hl=XHlH)KZ75$im33b*ST&lhUh7DAJd=m)J$t0(ewXyPu*GJSKp`cQ!^W79;h6 zWz2~a{pKBfGVz+ku>w3)8iXyc`MrjDG-{7#R2%7Yqh&NS&@D2{PqHSTdxH#rNXV=| z$&&GUdJTk(y@1WRQtUjPu4b+UfVau1xExc1{)^Ak8V_Y-H4k zWbTBs%DYM8Ld%R%lH5KJ`00cNZ|^yCjnt~9(bT6?sgb&2hppf)hEz%rooOkZDTgUP z+wHqkuPg(?=&oU1F7mSVD55kWsJ6fHax47$4QeMHGwN#Z`C1c9p2v?%)+p*#DD43T z?)8q{)(1OKVpE0r^vf*ej$wt=0v&j98AX1HmvR>kuh^y0-r_gRXpkD>YMI?_Zq4w$ zP`zZQ%5OULu0?c1hp5+ye)kyJzX0kPH&nEnsi`%o+BirC)?_Q%qtqUU7KRMAh*q0a zWgk7q6sVNzzsG?sP$QsEIP}r38Oc0%sjt70o|ofW)9{+-3~j4-i*GComHOkZ!mzgF0M zh0eG_dVqJRmPNDA<@iS`3Z~35ayLD?syBsJ{g&E#2Uxq ze7+AKQOUPE9E`r{AVlF5RyYg#qnH9ii)_D=FjpPu7)xTdwhc3T<6ba5vf)bdovD%I zS;jek{kT|_OTOy(k-Q{U>xagcw_cP2?@Ng{M~WwEkDj(UH+}$k(OO8<+}dk4V-=hX z-j6cd%_9omk<_DVkvfuE(x2xgIq?~44lcYX(EIs8MhWp~m*sC1puFTWY9UpHu;bj6)gv<%Umn3mAv2GXuoLivh#_BBl zMCG}%i?qVrwQ1i)PEqzOynBRb2CYa1-kKGe~wZH>8`3bvC9 zx-^eI&j$tlx8DY*Cua6w1k4)hj1oXvS$9WuBm4mu?r%y5Kzl~y1+lS_+?~~SDNUk* z#@K>8Psyhm!lSO~W#+D=49*o^6`l?+OIQcfzX~mR)@&#O;o<01wJl%1ELkg1oi#2w zHd1k!=_$juoqtveZ;cy*7j!E&fM1*l-dmc^?f!IETBnY+`JIH5Dp7k`I37M@m;!8X z{w^)3XBOZ3x*lpZHNs<`StfK+@_A|r0k}fHKB$8E@jdx4e9g}LD1Z7IZH+eJ*j+tP zbK3fBheiE>f4a2A*5&Ztk*Q#!><{Me>tAe``cL1DvGv@5c)ARA z`uUb|hoZozhmF#5=nJze6zPo4xy!Hu1putfPz1!m3Vj+W!)j!Bm0yBYPL@F0!P*)I zfl8jG;rY?|dN4Cu72z!Ty-SAG1&NUSmavyZfbF5qk|>DeubF$vU!^6#8T#Jh4u>Ib z%dpy_P>zybC{6+{r7s6XWfI12&= zfP!bTryl-qojR5M)g=c9hkp#6j^XUN<1YahVwF9M?x`EH(%+ncAz&yN7|sttLQg3OvRYsy`hb{O6NW%Q z(NiBGE%>iu-<7{9p`Rx|+A>sD2mlo22MF^6fQCSENg**wppbwt@CU%}qS96n$^X!i zkQ5S<6c!f{0!a&=^`8p<-L+pjzdHoALXQSv!*BJ2l_9HZ2n1*e8~kwMKe~U{f_OmC z#{jZIe@Opm{w`|+MSLe~$m*bsf)W$~ z0PRKD6mLPvWUk7-?7xvq(SK;i*2iXg2rHm)RMZ?_HzE^3LI@g(?~k`v%K zXGoad>T2%gqq;#6Q>^#)!cN1TOIeMAeGb;tkveMo1se{NcuHUTIywjkMq6Y`2J%Q; zc2QA)LH7;MXD+yzICFH{tE3~|n5WBdwOxNID|#80MdyBWH88O#G5$_{LPz?Saz=#u zQ|lLzZ(Nq2_gd)cpCqH7jHmCmf6Y3b(Uwj*Pd|%4y80)|Ul>sT&9zg;)6X)7uKo%7 zAN;4^qw`Z41LKqd^|R2R>`#N45ViI6wJRe@FR!RQ%}a@n@8O`dz{G`}t+r)%=h63zCP6-U&`49i!0-@pE; zC&&SCvjYC;$v>eO{=ua)3~CDlxw`&4lJ1|7P-i!1l+*uVoNy@A@qg~k6%K^E{V$?K zd2WCa0&9bEL{ue1pUITE>fWd+CwBwyKrYy-_uj zkBw?HT}s${S4pN~7A0SXo>@Ts{jM@m+|}DxdV{U@rw6anm}$t$xhm80=Q5_}HCwDQ z4552R5W(k}vRk3Uo^qi~)E_fEj#G6%E>HA4728YdQRUC~qbch;vfQfO;U7L7>F(sD zez-QhJ1BFvWYH-1nUS-D)gGk)^?mLK2XnN0SGFR(j4loM?0u>Hl9iwK?sQ@PxDdMM z)8*8_SkkwBaoAH#B(r8VCI9G5*{hV;qUGA+@xKN9FMav{rhlL7|9j)p1hD15tCG0N z9*X=a0JPL}Rm+qu1OJ>z@sV2APzd~cvfO;s2U!#+>Ds=Fr-JD{oT5Nx65Y6pjYpw5 zsZyy3#W&7&wBpvMT$5}%;GXm$mfNp5X6I1TimR&R8px8Z1m{{ zpNNmEq?`oTD@9Fvgw$gXMHOwTL}wIEZTh1{I*P^9$#3;hen& zV|f+Y;TmWvy==^Zy^Bp6)|$IqrQv-$dE_I zk-=xJ0y7+v2Y9~pR$SE9H4b&|Tl7jq>+dh!?ct6yLxgH=4grYdpL8=yR9|afe6I>V z<}x_l&~QOzoMIs;v_Ym(;|mv#Krmm-nu_(A}WCdRSNUQE)y-_Gw2;N{Hnp z^v)V#>V95HsRO9T^Uq(X)aTyPnz@UU0vTdgy4lHEUq9;qfYB*BuLf*ACNvnNqpoxE z3chCH0q!%C&>}H>5dr6{sXbm;NQ=SQYL;IQTN!9;)qNBZ6v^BV)tZ0kge~78s06zN z=n1k^*P*z|Kt$)0XXi#$^=ioW&4kf1lkEDSa6Ju92X-tiI#W8@zL3du0hT^N%t%$Q zHFyfG5^X|EJ=%4%X|(T|e8UP09%;__22S^=HC3oq>+WkpD3@+~`qMI>Uw z=^`$-e+sYA*7i+d)=RRHzXv|9)QGAT@Sb2JsUSNH$%A^x4&!oua ziV0S+h*#bh^LPl;Vl!@oiM5N1S3eyN{mem(#2%2)zwL#+@2j;TEd{0#S48)fI6R-f z`&z~LLKTe_TYV)bVI8W;bY1k8FSAM|OE=2p@tK_gSX%Vg2O z8{A|ULJnx*5uLR~@Q8o~d$UG6g5oQUG`uBaV$n#UXf#T=h7{_r(eRdz9mHhZQaQ7J zdO%$2=X>-F@#PJhsqy(LDQ~IYK0(Tug7*dO4W`D{yn`6?mZ4*f7-#TVjs@a4+s_ny zrn13gA&*kTK`CM&73JEHiZd^fisdN9TYuT3E+txH`t)e9mwWK~t0_{6`&qRIY-8si2*AAu6J5HAEsF)N9KuHmlqrus#EN0Uf zO)Hm3oYPCT{3nEHr&*OPF>vZCwAI&W07SQ}yB?+Wx5KBfJ+|ub2VC^KMvOk3*+q*+ z9}c&94|KGkX<3#GF#uyJMf!`6GhUcokMKTlDSuCS5SMdXmQ^SFO9p181*d+a*-0<= zYYXCpX59C~Eeq2cfbFc;#1+gWR(PH_89Oju;qOe&xp_a-U1^)!meD*F39_#NRL}$k zX?ZZPq4$+6N@+x%MeRJeZ}lpIQmfg$GVF9z8v0P}^zgmbJ;UvfKKvliXuo;B4_(WM z{3Kh`#iZ@m1^ZP;mDUu6?=(EL_XS*buc>#}+myFYvbhBUoe|l%AE+Yg8kUJ|I-Tr0rKydD+mq;Lu_49yZ&n9S=UKPl6%d~ ztcxDX%J1rfv{q^I5u)sZit%+#xIQiRHl-Tz7fwGvuVhIHTqAv!nQAmthEQmN-s&D* z0kQU*D}o>FPS(pdf9zKbrE!sJ{=~>RJvlqG@`>q|vr zw-bHWC5+jom-UXm_Tn+r^_R5eO&REEVodi6{k!+rQ;gkoSCln;hJ#?+!&=!gb_AT1 z`7^}rHp=lei@fS?bR-9F@kGe8UXj&3>UUU6$-lDAEPpF`px%A0axjZ$)@M(1cz>S; zBN!{YESp&4L&MUdiP2k$2KAy{-1hJ=SGye+gI*H0<}jTg9q!3xLJ`Mq(TQ21J3Ldk zP3TMO*qW+^UKsZ1+IzW1(y>8n11wv4G34m2G1)8zj;&neUEKJaM8)I6xd{(RCt%n$ z70uE|R5_u&xP9_=G~uiA+E23>((MZL@)Ol_v}ThcriO`l5lNV6oVW?saj_mNyGVG( zy!UxZ__*}g@aEbj$bt-~2&c4Rhg`iTNy|!nl(=}RJ{~NRXw*c&gRnp-)$w6tso44H z#C&|=sM6f^_3)gEaMtEXo+IKYeTkjNUCTJs&jB)21z0PvJ9NEwFgE#PMLp(I*u^eu z(2OiIvnq%j#;W&zSe{s2o z+BZGS$+eOxW#**`$jf?xm!NM~&`nrF?m|(`ff)+z3@zMr&yHwYIu%6kb}k;4PzR$6 zL@e-Mp+5FyagH| zE3Gl0Yj%p!XPd_k)HB@|527`4-=GKKiz-q@`>SzvbO#&?`2>`s=j%+B2(a>K`_00z`JxRN_m-wFOkoHA#nqy#X{Litak{~3g~1FV;^G)^{T;HY$e~oS6wF{ z5W`xEG?~CH^|%?{jG)tvir*ehjwZ^bjjP%YuNP^Wl?LBGV*a|w+c$T_inoNhplF>V&60#zvVv`!Y^E! z4^`5#aODh3Be?p0gtKO9odnWLc}HgRHsx9ETwyt1TvcrE`<_?;efA|agB!O>b|J5# zX-^#S$_bXc?^!sNetf7XS>Z}!;E0!1)E{zxS6Ixl@HNE*k)7aKA@-1Za6JLyrIm%C z)0@~?;cc(L`$w{6+=E=g^j|bAQYcff;KEjceU0~3h_))1wP^OzxzISdFV4#M-2CFN zh)^EI2_PUpH;89oYV_!BzsQ5*h%{p+b*1$dwF!}nuPcL|Q{Euv(PYGNg=a9+E5)p` z^)*&M?}BaF)$z|~#VRKjsPw8pCiR8`69C|4`M30ndewG?dpUx>Cf7}~zWBu&(xw$| zLzq($EK5~?NHg8@!6Y*JD?h9!>I~0lklxX`pXIX0qfJ2rGh+v2o zjpt>mk^KNU-5;N}6V;r5xBWa|)~C~DA?{-#l(6?6aTt+Hqw~SY`9V)iXUX}Qhu?8B zZ%Sqmli7j|8j%5;mWRBqH!}lgOvd5Jz{1D4tafci6^gkfAvZ>?U=@~qE?0%hvP1GQ zBNLZSUhRC(hc%Q>8z^rh>}Ex*lk=u&oF?%M%m)j3o7kN~p5KS^-k*F{O%`30MY zT;;O4g7{RDkW#wDY&pY(l^YI`p5|b~#ggk&lj1b4lrwSf7-!-x_h50EIS8f^DqM&= z+dDD<?7SLE@TCXSiWNPl{!(fF2g&gM)-{RQ|1EjnGE87@(3XaL=v{*+y{6-`eZ-P~22YY>%d?F_d5ZCo> zT&{@Rlx(lS=1g*IV3!){n6)A<#Ny6mvNwMp-Y|mp_?|kmHk#DnL4NO!>BtFYh}QP_ zU=Ro8WvpFWinyh6Jab(;#sz*Y7w29Y*V<}#XWwm=M|a;3crmi5uPtzNpUT#g@U5sA zcW@c|=vsVy??-=~K%P9G(S}WXw>BUj>%RVb78aq^*)v8nU#0{x*y~RJ2jm%a@A8|Z zXruz-Yl}$@jA#jrG%Mm%Uj=}sj1neJ@LZMULDja=y#sLHe)-F)nKh+b6+Dx@2g_}; z;^r^JJ*^O`_gHC_gRR;PFI|3+z||a3nK&r_Qd*Xpyg%a9E?O1aktULcO;b9a!jXlN zg6?Q-0{z)+eiIY@TDBFF`KlEi1dPsoO`SkLiWHqO6>y)-Uhx=6{Q*AZQ}vpRz#fOY zsKhnw5JNv+wErb>i~dAg`w1Rf^#?A{fUn>QLFrsvPZ~pf2$t$zVShEOknCksL8$3qQyC`5wi?OIIbxQv59-@6iZId}H*f3<+~3K+SJ)qs zQ@zuqe14{`f}T|B@rEue+&gQYZ5-3AqC(JPzwzbe(AlAxY+m?Kl!WFq?H$}btZ623 zO`vAzMu15ug4{^#(#>Z}K`5w4)L}@gB$mo~8JsT3oJr+GK zV)6FHvv69sgh&_vhQX}Y4bNnJVz|5G-J+LqX6KI5C>nfu9}>=r^K0su1x(VmI||Y< zso{z(Sj&i8RTjDtU9;CclIe_#i>K5bhg+yW+S2QSg-s>>@JD8otl^5%(DqXuvE zJvC2DGNJWV?>xUX)0okH&yM?`B&`ZjLA)L!Ri*9^a}UCjAzz}dD6OM&%Y3*x$&1KK z&Eg3j9jrFFnMZ`@J)`FEK|wjb>8{$6+?YAr?xnDu16ekU+JZ&n^|@r%{gRZ`XEppa z#_!t6bSo3V-CYBs1JBaYZOq)nWS(DIVt(xg1*;LWrcAo-RwygFNx!) zNj=q8tbC|cIZMNSf)m?G*iu06ey~5M7rq`^`r^Rb*IRDCc~CWV{ag;w5!uk}l5919l+?StkS}GGElm`fF+ncM{50Yhqw&Jpe2^}97 z9ZTISlw4)P);X2LKZ}bMW#^VJe?#d-ahMBkN+7??Bw$eUHf^Ao_EzsG8w~VRJ?6$v z=COLqfJ~l@c227cUGMHk+p)F?hBt}r!t7~gpG5pVQ#ExJ8`KB&bBHi4T8q8;R5t=l ze8=Y4L|aR|J2?g+^(j!Aaf%z#Y#wac;LOpYyxh5)?OPFFVo?(Jf%5YPaXW_A!pSjcL)LScYB{Ngm0Gk{7=Kc*o&A}Vm{#I#+^rN^sd0xwX( zrgz7q4X1I+GJA)vlz%V^epKme-RdV&5igb;z|nR3DlRNC_%O2= z_|}vEu2&f4>rsXyyY4-vP44a*g5FVU3a{`JY!xxp5hrA$W1p;GwY9CBo62y?o+>dnOGI zEz0st)h*PvUZXzdauBtffb-^J8=O;;Tke1z;R}y&dec>Xf>Wukd>R|wy^G6#ds_L* zNV+HX_WhtMe3i%A@2|)4$rd+45>WJHnxisu9_IxyLCGHW|QOz;_0r9 z)7hM;9ZjSK-0E+!j%zHit! zX0%)LwvA)wZe>eZ#l(&Zr6$^m{z``odLDUN&{|NbR??L#gc7=32PGMzdTz&#h2WE? zqE3W58%l-XH2pUS<_y!}9Qt8|+$h%z=8^s0%*UpEi}VJ2?Tillruy~~?}HN@ykXYq znYy-gS5p$xpGwUyrQfUNzWVNhYpyvF=!)8Kpfl|1HK@+;C!I!y?(Z6z)2UA{tqbyz z+IweaaA*!db^3G*>vlrGu$zxe) zxfe`7T`Xfw+r&z8(@jur06b-@LIXW2*M)4Pg-xeexnOeG15v(B5wjdi<`K zam$(V{vC+|^_5_-cUa*Rv5qu)2Sz{E=m(-Ce|uTMz6Z2fBvSOIdordRrWfTLe9Z^4 zL!xDFG8AihjHfrmJ7_JHfk^wXFN1Ek%e&oPI*w}|#nZeW6`R*Au^V+tFpO1BU3O$@ z*5v3P8EFdV$R#a%GujFQ&sUDzh!s&ei09E{Gh8eVu@`;TwXSG%O4a@4raw|q45|2f zv{j5zM{GqhS-v^LU8>9Lp}i)XDe*1*@ixosgRNx*T=oWQv}Ioz6)!$(CKca7&lBYZl*qXc8I8~qIUPduiC(y=yHhTyfZdKg+Cw6B zayK^{(PyIJxM>o+F;PTG8tR{SU-js^Bx=vyzUI8eLCRe{GRmJMD3@`fIcHA9ot5qp zWPcA*u(ccudsC%!v@W5NXheDX+3FR&zt|ei*wU2cv^EQeQPl&>zJ9{7MiTudI4EFO zhCKlDypd!V%Q9LfP)uIJ=(DgU?ihm2XxKH#O(5_UJ&=5){ENC)BR$nA)CfS!#N!_| zyI++SLv2S;^7f$*?b0V;?O{YG6CkkoJb0PYvi6X!{cGjJ60)*&?F!^V;N^3pB~HcK zFENS`jL;sxkoiy7YyAhrIm2p}6Hdx+H|(1bP3NPfm!8~!PGRo0Mj0u*7HjUd)G8+* zW%1Q(4&qlWv)VhSri@yRm`}G;aLFiWNzZ@~ntrsf@w*-3U$H|qF|aLvaQ^x6xjCQU z3kw8IU(z!K53Mt+L&Y-mEpfFXOw9vOdH2zLr+*@|1O6S|T1Ulqw|F6hgN0iT27H;r zH>-0cLaOc_EY{315c2j3xY+Mdu%-~&om}ZIMUzfj6V~I)GF_@fbFxUN6H{Cn?q}>) z87@n6Rpvzji5I!5SQ4xEV{I!*c2n z&Afo8XIkIJj-Hq+DZZ*&l)-c6X@3^}mM@q7#4sVssy71toT6_@Ezs|NvzCs4oLSt2 z_IQf{(-HEx^E^v0-@Pg+vY6WB?Bf#}%(KR6GOVOB+Usrx^tbuRc^emoELpwS^0@Vy zd%)(a?UI&^(!eeBO>fQDkEVk1{q}$=(L*=89c_+1Y?64NWFZrG1Ip{5RXUIjfT)aE5M? zB*ra?k=D!)^>S{{^CLrj3kdn8ScnftW7$g4Dai{hI=N$R<6UV}*&G?80EyHv@Hpg9 z#B>Dm;GAQlULePwfF9ry0RT@^{_O=4bw1|=gn;jWT;cpMn>&38eUKnQlHhIG5K#Yw zq5vi)jH|oO{_#t(P$Nu%-E^{SjK@wZZC`Sz+;<` zguL_qJ2653MS8*sQi}R~rCfmEK-AHutOD|j*&PIPMUpP$ScUinS(!l)Yp4zK>{E{Q zhM_v2B&&ivo-Fjv9k4Y>`Uek#4@uYnG9#f7SLts}a;$DJi1b&+hBO4|1ag&zTTA~+ z-H`rOTl%Y`ZxT;OFvLNQ)ea7KmKG53@bKXG5aEZyYz2g*q@)DCwz7VAWn=x9p0gXw z@vD}NwE&W-fut$GT?K^rg#>=+q9Xk728Gi7H6$n$`j;bAAHH?*t2<#qK~aHk^&g&W zVKz37f9e0y0i>>ofUSTH5Dw&X2ZKD=Sed_%<1Yg)%qst5bWvf*%YF?83<1NzKu11n z7zo8dk-rLrA&;Y(b-)k^2)XnjvI768_6__Mgq%-4q-T)4u%M6_pP&ezppc=EgtV}@ zw2&~rh|qTfe^-^Yv6lW1jHI-Xl(et}zp$9Bz>jv6;-5qNrSV%pARAl*}5yWQ=b%Vg=Sdl-SZ?E_MDzQ|LR~83+T~!hp_pKa_>PH+Vo{ zHa}z%-(}WzNNsB*zv)MVs1U1wyzKWCDvgTgXYH?Ed=>xs9-k7KU$3eeD)DLQstf#; zXpz6x(!>@>8#6)Z_T7l^4T=fxbiH9l&Q07G*p}^DaW7RZi#}~?@Z`O&fg2aiIQD#L zW(u14pxaNSf%C?*WCGvs4rbP;>XsTSrjyURNt-pr(FS&O;p|~quUu)$!5#XFYd1u% zXTwN1z-uxuCpVS=TKBe7sE5QJ(il~37SVV`SLnSza%QZ*IHH~e-^#Ko+9-Jwv5Szj z>Jy+kOzg$gg-41dKeTar%PnoFBUtgOt)cs2S0{qow4tL~&p0R~cSs>+bUN%TukJ)2Tu?j@!aw*aKp~UTBP6EAfC8~hRVWq_Cr~$$Sf?6fy%;Y z=oElIQ{Rvy{Y&{lg!>)!i^^9n)6e=<i>qWfJ-LyV3vPzx{o5euBSowtm*Bk>mNhF%&iJ8_(>|R#1$%pXKU5Sou3Y z?$4G`47r~r?4KAW{URNR_U1K{^OX?*f8?6saoG zJBTz9l$)p=J$`zgd+(q3xy$p0-PxJh+1brx-<_Yn76v8-8X687T51?j-Ks}~fC~)` z4fP;NXs!@fFv1rO2EySk5D*Xnfk6RYP&+{w&;#Nj2!n&6b}*2qD;SCpM1Xw|`u|df zl>evDAZscxs6E8N)BT$o4-tU93k-+=y92&U;o#tWGvOZ*WCdl$?@~Yz2;u!n~&@O(CZlKhhokgoImZz;MzjR%8!!cn6CVdtOZJP<&H=l_M32pG)e z|J+KH6dVWzyZmM)IH~*EK5~^%56UM-j-IZzP$0y`1AsWM3c{fdclC9z5aQ9{Az27D zHB=3e|7+3EE}-F{R`{k;b~JLWn>1CGjC?Y;riUYg710!jL%*J-=tNMut@ljNQ)TWk zi!XD(&>?6X-186ODnARj;4c=SzppfWQH_b>@0BFB0PWHJuWf^MiTo8QThPJF()chL zpR@Xk)$!`&h4)@NK1OXVr|i|^d8vDhn;^@wwlo<2op4ZOsJ2oQBITt8FY3p#; zi#b8yM#Jv*oa|nYPt&JOLhG`K5C=i;x=Z#sYjCR0ol8EV!q;j&K=hTgSArvGRW4CI zd6nkI^rYK4x%Q!2z+*B}h2fFyc(-xc?vu*WCpGdP)doJwU+FQ0Nh&r~4~|eJq)OIWbhQxs&MKDiZoQy9+ocJt$8Hkb-13sF3!rAU zr*iM&GY$^)>v?S4L99_vB8j z>p^DKy9Z*kSnSM zx9?=>H*-RSrC}~)oXXuqX}Ij6o$U{~8lA`8h0 zicZ?8%6;HmS}f*{!sTgVy`k{OjI;&hDK_b)31bqMh~Aw@F}t%z^xw6)iJpL+7;^F? z`e}MpmBTVW9bMGodxOO5laLNPB4&>}3@(k6Ikvm%uFMcOJ^2Bt`XVr`9#9ooz z-E8|jkA*i!zh3TW-_C00D3sQ*;~f&)Bh0mBkr0xjf-N-pQ4N;Wx>KZjF1YJ@M2$yuQdgHg&ZHgt<*3#T5sL8+w)^T~|Dhh|pv0 ze#ar)Q;)yWvD7l7wkIlhWhSm`N|8a-iR(fA@KD~3z)Sf7&y+rMD{i12XXK;fErR)P z3f-TO-_#Jqd($0C=H>$T^VAp_&}Fhh@WQm!=b4$bnUVoS%E4-|XRj5#Q%fZ)k2_f5 zu_F1r+LQAneC5gElFv>i743z|XYbmCSKvvsx{^&M;bh7=^k!F66SM5{URGavNK{oH zG+__i53~#Fm^yY*G8#|;Vi=2%N*XFqFKD^PhgyhJOCK0}7`*A;@DM%*xW@~>6QREN zK_ZBpzJtdNU)!tuKDAB5Tgn?!neIMn5i&7fq2}{>-p{+f-t?y-iY~oyCyFno$qLHz z45(+^?_R%7vo74E7s!~_!gM%WGH@rtHK~cm`ucLuWu~v%LH08JHUXC~7^>MrPwwOP zhVuCPD*D1d4-!Tu>l5<1zg)Z{P%-7e={9397kRDUdr~|_Xeb~54QY(_$_JdTm0Qz+ zh_)uLW}KU1qBt)IuwT7w^%PI<7Qciy9;$R!B6J{iyN^+1?BP{^EdDMN(D6bA6)5eH z%ea9%Wx74uig5X;%^cs}QK#p1efOnWAg#9>J-unjM&t&E+hf8P`BC&!eT}q6OJu%d zVN1nPGn12av3%tz-31at6P9oKIIo{QqDz^~li-)MeAB}@evmzXQ`5o;Lv(9i-3uJU z>wZ_>sY_(l+l{HI`jO=Q4(=4K=XS*dj+iQCq>eG!4{p?`ztRvgV{>GuDkBx6iXO+I zi%@gMB*e-S4-T^(rc+|;K(alyn9e1Qu2Ihx5BB|;@fs$oL$x@(XBayN(m`K@2 z?vN;TA;B@6u`^)SYn)rrFL2D6=Aus~Z$6qVzixL~veYH#bjOT+cG^s<-fKy5t_Y1! zPkNQVbowB)zy9NX=)L)3OK=eZpB{LXyEHai-l*q(p*(`hJ?xB=7U_3 za=8b&dG$^v0N$?tYXBMi5-*)RBvB_1MU+7jjb&uCO1!?X%^4eoBW@*_k7CS=}m=iP_n!&%K4jD8^1C zBUJ~IaR9|Aj$-6RF;brEn^r4P`W$Zg={UdM_W9eweWk|UF|4nyQB!lG+5miGDhpQs z$cNgkgn1Q--Q=uk#7>;2ifh+HFC^e5gftgbg)b%=q|~AZTD|Fex;~Rc`gFeZ7?7g= zx%Tn1BdK=za6h4fg&Y3eRx)zh(Q2P@X(ZPOwW;G>E#5QT=1V#x1vkBS&W{SbfI4>v zON{wPVxyrABF@j%<+Ab-LfnJov)7uLdrZra+`8Pxy5NnT0~rd^T%|EI zqa&kXexBKi>(}9AS9T=<8NPU^w;aQRZ`aeQdh()ti>=1W+cm}j*gm0FcpUf*kLd2+xxoBC+GR>EtNq0O`Qdfb^&ebD6evdfn#=+-pb z{g>24Q6?q6C*xmQm*baD@Fp?IVWPIzabw_+=IdL z2WD}e(0}l)@g6<6nRgw)>CZ4{i^=kg8o|oBlKqrIn-oiEtv32ZX}2rs%HX*UAjex4@lCrnw_6D!>c%*;Qq4RD!$>N&*}C z1rHUI{fj6Gqpy@78!4{&CTI%C7K-NNg{&zx9PP3XyNY2is66&I&^{#Y_EAo#Ti{pr zq$4?)!n-!A6yM`6`(R=OA9|d!FEQ@{Ic|1N5yU4b{^AFt5Yy3%RZ_HJ-sJtPZ?od3 z(0b>-N|$r~^yMI$T_2*Cm-8cOZ5NN?AY8_gUcOxf86t#--qDZoyn+E28`eq544f_n zr?-#D@gx&0+I;qixVW|udiz5cypJM7sK48-6TPYHV=ckjqCIBan;_RsfL`mfA{Gzj zC&YBvtj&50Jlx@&bi8A@1;dUb-UY0CH5mA=V5N%-sn6lW*jb(Gl0LD^e#L}YWuJ|% zuW>!GFr;SFI(0%*g1Jp_-uNr z0{L_Mc5)*FgAC?5zdosFn471v=|x|9Z_%S2G8LWu7AwJC@RW?pehDX}kwJB}5Su9> zE-i$?+@gb7yv}5eTsJDPOk|7U1C+wtPHclS&*cRX7Cy7GlK=X9icsaDhRcUWE`^k# z(rlHOMkc^!YPx>+kS$dPwXKKfU6P=#F)vwz9-zoAnhW6i*K727VnNhuZqx<%0j(tU zef*yo3mG{vNQlf%8&t6@%WJAKC-Ndq(jOwyG9E;nE|58KGo13Te;kcVEbUrW1;lSZ zSC|lNzAwE_Ppp}Tg-z{vo1ftVzCq-Dj9t(nx;2(=TD_^Ys@W$ub^F#N$7-)tp*l+b z#Zz`tK3;(&folv&8}6DclbvO&1^>jVVi*o#r-lelHx z*CX0$>2#wLwq7U45aqAL+3~ocyRl}rkEYj*`-^u(x5zMuVg$2K-NZx?eMKjKvHObh z?hVUU0v;P&iN4FpdNSIWk8J|iopp6c^pBcSly{tzijJ+c8ZpeM>-%aRwqkJvyi8+w zBqH?qTE?V%iB7$+N$Pfu1M;{R%+*?_I*2Zk0l+|a!O5b~F}AGgZ)B0Q-+aQ;ERw`` z5>Q*)$%H=FJqXmU;<;TcL(SRWKSrdbUEJ=a7_z1(A1A^32AqvWbrKAT3foLRZYS67 zUNKM$Qjeeh0Pwd=wx)aaJOWqZh?7XVeju3(_`*3CA*8$d>Cm)p{~~5CWwAPrUFxT- zgnXaGxN)s5U8K8rU%G`m@!b*Zo47s}d(3vK=!Lmn{ZO#FFnoP5 z%Z?x2j zO)qz9=b*=tkzZ}x)*52kVa&GOs)HJq5a)Jm#T1_Em3-(ru#Nvtd{BRM*TBkGW7uB4R}(av zO~9C)t{_0~*F9(4|FM~8$*I=|K(-gGXlTVuoS|^ox&KA>lD?WpY~Z8OTVe`%j(3%3 zR+ScUl08YbF`unY44k2doHm*dX%^|Tkj54r-|n<|h>6F@p+;3G=5d!T6Z5^{nuNwE z$nsPiH_j<8_e<){G&Uj;V%yKSLHt;Y8WUL(R`2uPnNSq8Sm&W7822wpxN4b1vt=$Bg`GG`5xr|=7fbOTG_)wE_Db|!=bWVx&`-U3k0cLM zc=UPL0((C!S4Z8E={;jmEUtqZuvs}5Ln7KYnAAmPgutJLoFe^rZF2m5TdaC&>XiS` z<>0qS9F{zcn0>0EZu)_Fc~#lv!Nr5Y`@2yF=^lVr>8jSiz`XJJcDoYG z=1$UFQpd2qqmJt?{QL}EHjETquvOSD=f`S76OArfd)z(j876OyIgLk5iZ|42$Zv>S zHbo}~q{MWjf{U8lE7&J_o!>~y-}BjNED zyr$${=T0WZBcH@_UVg4_?Aa{M=X~AOGao<;ne1W|MOjLN*oC+TnTA{nwIETJnX4rIBfQ!lXDKsWc2$`CVk)Dl)Q#wp2ht}DIDNU`4> z)iW6ws`Gh|kCjO%ptdiIv1cMG+J7!L$hjoZd~o=QwQW~_KK(E3Yv~AF`N< zHd4e%TiaFMC@+7Q_A;blSQWe3feB-mPT7UG&$JB0P!ZITcwelJdWHl;#yDTS?>mHmQwM}G#l-BG!H zSOy8v;aG69S^2L1;CRUg3a<7>BezP5?blm;B|wGeGRd~NCmdhxN56D_=p%REipC$D z)>P>waEaF<_B*|EEgFwat5I6kJEh+c_aSJcVv?j@6=>c_KcrT|!k?%?SBZ|Xh@rvZDPx-8M(V$7Pj^jiw91p)6Cjvza@e8qn??hmH9fER%g1eY^Wf$t5$*8nbls zvtz0V$E;zvPyBsWj{JU23}c6(uw*Y8Fl2^qlK86DK$5%`e&>{c{AOywgQ}iaSUI*1 zN zd^@sm&vZJiC`BdBuu6;z*-k{ZjSC@n^{bxv#k0$ArKa^>d+a$mwa4)Ty5Z$z! zj)dy#2l|gT)67V8g%1=o>n@LaF7lT=MoTHYF%ws-DZe5fxz3XmkfbHxdBq{puhEnr zT`Jj}*P#+NPLDnADD#>DsC9J-X8@P5MF~R#zdlpe;+cINqtPJ;knSCjcZi`ZufG*x z6tfMdY>M^Lua&CIBuexPfBc5M?jG;Th`|9oykyd`F2u=4GquM%wSVvS3>h~kT)2qS zy9m>W%~{B?0fT~-I>h;Acu8mp*e*tp-n6FDtv3?1R7WgubYEGE^{GIV{LQ%HhG|OUlE>I+xz@Td+Bo9$)Gm-vRWxw)XmFIB5u25KH1u zge*DbIg9A4r;s$P7b9s48F!p*b;RJ(s_eIa>^&wN3C()qWYriqHz3UV4#RQlD1E-aK}5g6DSf0&J8fuSYO zkntal*u2$Z;kc2QY@;JcINm~HsDJ>6?3%lvML~f2w*eh7&hziv{@T18;5wZwSTkuBfc-huD zf=g50ioGj)`~9-D>>4J)(=S&wC7J7YQ`BTGbZ)g_j*!xnpOJ=b=fSZmTnhlYNlU9iko?CVk1**kurM(Y|H-TRedytHuE(a8@-u_tEC4LRm$ zQ_X{~gqb<|(u32;%jsV&Q%03vkQr}rEq>>RCuf0wa2^q25Uay50lBqxdjjuElV**qYuxFD+UsJ z`F)EPKTsazn%ZG1eY%W#A6Q&jqn$)%1)hif*ZTnK&czi7h1i2V5Q6S@_Ae7(LPLZ| zLU-iufCncP0a#e>-2DwsS?%IsH?RO7)5+eo-b=i0kYBu>HMUT$E;@U!CSwc8&=*x* z)L|qB;^FAmaI9V9lW7ucD43C%o~+|zN@v`43Mt6qZS;onN?Rx25s)Ns8G4e-?UTMI zr`OEd@mk7FgP^D89uDrM7-h)8qCcJV;5@Fqi2-6GJI?orSw8Bm%;W58JYbz+OL!e~ ze2`)cu6BPYB7~t)SL>N*@}7ZoN6yxKuT9HnNUogC2flkllkXx39xYkDZ>ik22$}W2 z?|5??bklS6+3qY`l1-+_w%&S^tnb;%SHYn(+WCqaFI5-C!90i0aVs?+nT)Sgpxjq; z{ef`bu2)OD5IW#k957uekcnFg0<6&4g?Wd=h* zFgxUZmOQJmk-C5s>tzKzIhegY1O%2j&x{KoQ|Lfuq$t!w=6jbstEW3u=35S31`2cq zd&nR_GQTF%Wq#$B`8LpZijNBf>MYOdh(N$)003`qZ$WQSL72M(Kv-H@8t|=`^~X?l zpnv$_p6)K+xa>dxWbPc9I7WB?gaw5G=e#Hj|96c-@&0NO3|Flg|78M5UQvJpzz&E23V1=l-fXPQKm7QM!$nvX&b^B=LqYDFF%T#O z0Rg%QfZV|-RDgmG&>eZj$gB;4Lcz$b50wM_k?p(iHzDMD3Lr-YD~JdQiwg*e3J3`s z2}{a|NXQ6_2#N~-Q1EY7IXjTdA7sQuWW=NeCB)?b=lv+gznk_;=XZm^cF5U49R%!t z03{Ukjf91CM6dlY;(v7iTMFb0LcaPdi2TO=gZ!P>0Sx_)pHR?4u9x1o-3kyB6cQ9> zH-SJ!MVNn*QOjtJL^n8rK?s1Dkg%&byRs+5#ZEw4QdsQA7(dm0SO3qxN1+WM9ta4C z`J4X{KwB5E00`y@MaZ)vzdGL+1qHkKod~l}nvLuF9*{A~R*i*Mw=r)4RT@l{97NJ&6bR~_(A zphbRL%aS^vUCabwI{}dq8x)f_)AdI$ac+ab(A;>kRZQa>Q>DLr48PRGIHrCdv7K#OyiqzF`LRaI z_9cMoQ_>4uT||_4a)zDj6pxINwop}HS95vcsWm#Q>x<* z_L_x(6`hH5H}Ouh3h%%djPP^2ysQEOHMYs`R~ft_`Pk}5ThIm=hS^gk=xH96ZNuK; zs2&gZ_TrCDb;?(dmJoUFArghge70{Ed0x!NUZCIIAfCMSEpgD`G?LAVjKT_-s3?2^ zodWIeU?ilce<|nCq~E1}VfltG`PtS%R)2^6{KO!AAN$v|1qx<@Dkv1v&k};H{;uUO zn56$Q4TVAaS*DTI-(eECzqjgn}J? z#{&Ib3krMmvxNUa3;Y)Z)BmoXwm<0k718u}J^!B7(I52uL^%Cj%fDwOfZQIxd-+$y z)4%onj(Pg&9WYYQ-w;se8|Zvj{+eb(;X!_uSmebp=qEblcfnupj!`GVpT!W_{52={ zyX3E@Ow`@-&r(PF>rM0Ta=#w0{ykz3|E;HHNOTD gR80O^INAOZq4l+}kSR+vG*aXr92tM2*io(j1;TjpQ~&?~ literal 0 HcmV?d00001 diff --git a/tests/odt/odt/unicode.odt b/tests/odt/odt/unicode.odt new file mode 100644 index 0000000000000000000000000000000000000000..07e200425f616622d13a31ffd8fd3f68579720ad GIT binary patch literal 11787 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 literal 0 HcmV?d00001 diff --git a/tests/odt/odt/unorderedList.odt b/tests/odt/odt/unorderedList.odt new file mode 100644 index 0000000000000000000000000000000000000000..50a950024070c7cdb08a5302d71e578bf64fe2ee GIT binary patch literal 9505 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 A$N&HU literal 0 HcmV?d00001 diff --git a/tests/test-pandoc.hs b/tests/test-pandoc.hs index 9bc26416f..f7c2f0c1f 100644 --- a/tests/test-pandoc.hs +++ b/tests/test-pandoc.hs @@ -11,6 +11,7 @@ import qualified Tests.Readers.Org import qualified Tests.Readers.HTML import qualified Tests.Readers.RST import qualified Tests.Readers.Docx +import qualified Tests.Readers.Odt import qualified Tests.Readers.Txt2Tags import qualified Tests.Readers.EPUB import qualified Tests.Writers.ConTeXt @@ -51,6 +52,7 @@ tests = [ testGroup "Old" Tests.Old.tests , testGroup "Org" Tests.Readers.Org.tests , testGroup "RST" Tests.Readers.RST.tests , testGroup "Docx" Tests.Readers.Docx.tests + , testGroup "Odt" Tests.Readers.Odt.tests , testGroup "Txt2Tags" Tests.Readers.Txt2Tags.tests , testGroup "EPUB" Tests.Readers.EPUB.tests ]