diff options
author | Jaume Pujantell <jaume.pujantell@collabora.com> | 2024-02-19 09:07:42 +0100 |
---|---|---|
committer | Miklos Vajna <vmiklos@collabora.com> | 2024-03-19 14:01:56 +0100 |
commit | aac02f9141fcaf0acc1bce2ff6a5c2e9618f9235 (patch) | |
tree | 464b1d8cb83b67039903bed9b9ada2066ad46dc6 /src | |
parent | c58eda83afcee4965254397868eba856df89447c (diff) |
Implemented the reading of simple solid fills from the fill styles list
in a theme. And it's use with the quick style fill matrix value.
Change-Id: I658340f73ced475bbc8999b4d09c4666fd50dea5
Reviewed-on: https://gerrit.libreoffice.org/c/libvisio/+/163580
Tested-by: Miklos Vajna <vmiklos@collabora.com>
Reviewed-by: Miklos Vajna <vmiklos@collabora.com>
Diffstat (limited to 'src')
-rw-r--r-- | src/lib/VSDStyles.h | 19 | ||||
-rw-r--r-- | src/lib/VSDXTheme.cpp | 104 | ||||
-rw-r--r-- | src/lib/VSDXTheme.h | 7 | ||||
-rw-r--r-- | src/test/data/qs-box.vsdx | bin | 0 -> 21037 bytes | |||
-rw-r--r-- | src/test/importtest.cpp | 12 |
5 files changed, 128 insertions, 14 deletions
diff --git a/src/lib/VSDStyles.h b/src/lib/VSDStyles.h index 93eff0e..ba13805 100644 --- a/src/lib/VSDStyles.h +++ b/src/lib/VSDStyles.h @@ -129,9 +129,7 @@ struct VSDOptionalFillStyle ASSIGN_OPTIONAL(style.qsFillColour, qsFillColour); ASSIGN_OPTIONAL(style.qsShadowColour, qsShadowColour); ASSIGN_OPTIONAL(style.qsFillMatrix, qsFillMatrix); - // Colour 'Blue, Variant 1' is special. It is the default, - // and it is not saved explicitely in the VSDX file. - ASSIGN_OPTIONAL(style.fgColour, fgColour);else fgColour = Colour(0x5b, 0x9b, 0xd5, 0); + ASSIGN_OPTIONAL(style.fgColour, fgColour); ASSIGN_OPTIONAL(style.bgColour, bgColour); ASSIGN_OPTIONAL(style.shadowFgColour, shadowFgColour); } @@ -179,14 +177,13 @@ struct VSDFillStyle ASSIGN_OPTIONAL(style.qsFillMatrix, qsFillMatrix); if (theme) { - if (!!style.qsFillColour && style.qsFillColour.get() >= 0) - ASSIGN_OPTIONAL(theme->getThemeColour(style.qsFillColour.get()), fgColour); - - if (!!style.qsFillColour && style.qsFillColour.get() >= 0) - ASSIGN_OPTIONAL(theme->getThemeColour(style.qsFillColour.get()), bgColour); - - if (!!style.qsShadowColour && style.qsShadowColour.get() >= 0) - ASSIGN_OPTIONAL(theme->getThemeColour(style.qsShadowColour.get()), shadowFgColour); + // Quick Style Colour 100 is special. It is the default, + // and it is not saved explicitely in the VSDX file. + ASSIGN_OPTIONAL(theme->getThemeColour(style.qsFillColour.value_or(100)), fgColour); + ASSIGN_OPTIONAL(theme->getThemeColour(style.qsFillColour.value_or(100)), bgColour); + ASSIGN_OPTIONAL(theme->getThemeColour(style.qsShadowColour.value_or(100)), shadowFgColour); + if (!!style.qsFillMatrix && style.qsFillMatrix.get() >= 0) + ASSIGN_OPTIONAL(theme->getFillStyleColour(style.qsFillMatrix.get()), fgColour); } ASSIGN_OPTIONAL(style.fgColour, fgColour); ASSIGN_OPTIONAL(style.bgColour, bgColour); diff --git a/src/lib/VSDXTheme.cpp b/src/lib/VSDXTheme.cpp index 59044b5..537e2ad 100644 --- a/src/lib/VSDXTheme.cpp +++ b/src/lib/VSDXTheme.cpp @@ -63,7 +63,8 @@ libvisio::VSDXFontScheme::VSDXFontScheme() libvisio::VSDXTheme::VSDXTheme() : m_clrScheme(), - m_fontScheme() + m_fontScheme(), + m_fillStyleLst(std::vector<boost::optional<libvisio::Colour>>(6)) { } @@ -102,6 +103,9 @@ bool libvisio::VSDXTheme::parse(librevenge::RVNGInputStream *input) case XML_A_FONTSCHEME: readFontScheme(reader.get()); break; + case XML_A_FMTSCHEME: + readFmtScheme(reader.get()); + break; default: break; } @@ -320,7 +324,7 @@ void libvisio::VSDXTheme::readClrScheme(xmlTextReaderPtr reader) while ((XML_A_CLRSCHEME != tokenId || XML_READER_TYPE_END_ELEMENT != tokenType) && 1 == ret); } -void libvisio::VSDXTheme::readThemeColour(xmlTextReaderPtr reader, int idToken, Colour &clr) +bool libvisio::VSDXTheme::readThemeColour(xmlTextReaderPtr reader, int idToken, Colour &clr) { int ret = 1; int tokenId = XML_TOKEN_INVALID; @@ -350,7 +354,11 @@ void libvisio::VSDXTheme::readThemeColour(xmlTextReaderPtr reader, int idToken, while ((idToken != tokenId || XML_READER_TYPE_END_ELEMENT != tokenType) && 1 == ret); if (colour) + { clr = *colour; + return true; + } + return false; } void libvisio::VSDXTheme::readVariationClrSchemeLst(xmlTextReaderPtr reader) @@ -491,4 +499,96 @@ boost::optional<libvisio::Colour> libvisio::VSDXTheme::getThemeColour(unsigned v return boost::optional<libvisio::Colour>(); } +void libvisio::VSDXTheme::readFmtScheme(xmlTextReaderPtr reader) +{ + VSD_DEBUG_MSG(("VSDXTheme::readFmtScheme\n")); + int ret = 1; + int tokenId = XML_TOKEN_INVALID; + int tokenType = -1; + do + { + ret = xmlTextReaderRead(reader); + tokenId = getElementToken(reader); + if (XML_TOKEN_INVALID == tokenId) + { + VSD_DEBUG_MSG(("VSDXTheme::readFmtScheme: unknown token %s\n", xmlTextReaderConstName(reader))); + } + tokenType = xmlTextReaderNodeType(reader); + switch (tokenId) + { + case XML_A_FILLSTYLELST: + { + readFillStyleLst(reader); + break; + } + default: + // Other style lists not implemented + break; + } + } while ((XML_A_FMTSCHEME != tokenId || XML_READER_TYPE_END_ELEMENT != tokenType) && 1 == ret); +} + +void libvisio::VSDXTheme::skipUnimplemented(xmlTextReaderPtr reader, int idToken) +{ + int ret = 1; + int tokenId = XML_TOKEN_INVALID; + int tokenType = -1; + do + { + ret = xmlTextReaderRead(reader); + tokenId = getElementToken(reader); + if (XML_TOKEN_INVALID == tokenId) + { + VSD_DEBUG_MSG(("VSDXTheme::skipUnimplemented: unknown token %s\n", xmlTextReaderConstName(reader))); + } + tokenType = xmlTextReaderNodeType(reader); + } while ((idToken != tokenId || XML_READER_TYPE_END_ELEMENT != tokenType) && 1 == ret); +} + +void libvisio::VSDXTheme::readFillStyleLst(xmlTextReaderPtr reader) +{ + VSD_DEBUG_MSG(("VSDXTheme::readFillStyleLst\n")); + int ret = xmlTextReaderRead(reader); + int tokenId = getElementToken(reader); + if (XML_TOKEN_INVALID == tokenId) + { + VSD_DEBUG_MSG(("VSDXTheme::readFillStyleLst: unknown token %s\n", xmlTextReaderConstName(reader))); + } + int tokenType = xmlTextReaderNodeType(reader); + int i = 0; + while ((XML_A_FILLSTYLELST != tokenId || XML_READER_TYPE_END_ELEMENT != tokenType) && 1 == ret) + { + switch (tokenId) + { + case XML_A_SOLIDFILL: + { + Colour colour; + if (readThemeColour(reader, tokenId, colour)) + { + m_fillStyleLst[i] = colour; + } + break; + } + default: + // Skip unimplemented fill type + skipUnimplemented(reader, tokenId); + break; + } + ret = xmlTextReaderRead(reader); + tokenId = getElementToken(reader); + if (XML_TOKEN_INVALID == tokenId) + { + VSD_DEBUG_MSG(("VSDXTheme::readFillStyleLst: unknown token %s\n", xmlTextReaderConstName(reader))); + } + tokenType = xmlTextReaderNodeType(reader); + } +} + +boost::optional<libvisio::Colour> libvisio::VSDXTheme::getFillStyleColour(unsigned value) const +{ + if (value == 0 || value > m_fillStyleLst.size()) + return boost::optional<libvisio::Colour>(); + return m_fillStyleLst[value - 1]; +} + /* vim:set shiftwidth=2 softtabstop=2 expandtab: */ diff --git a/src/lib/VSDXTheme.h b/src/lib/VSDXTheme.h index f600c96..2451ca8 100644 --- a/src/lib/VSDXTheme.h +++ b/src/lib/VSDXTheme.h @@ -80,6 +80,7 @@ public: ~VSDXTheme(); bool parse(librevenge::RVNGInputStream *input); boost::optional<Colour> getThemeColour(unsigned value, unsigned variationIndex = 0) const; + boost::optional<Colour> getFillStyleColour(unsigned value) const; private: VSDXTheme(const VSDXTheme &); @@ -89,18 +90,22 @@ private: boost::optional<Colour> readSysClr(xmlTextReaderPtr reader); void readClrScheme(xmlTextReaderPtr reader); - void readThemeColour(xmlTextReaderPtr reader, int idToken, Colour &clr); + bool readThemeColour(xmlTextReaderPtr reader, int idToken, Colour &clr); void readVariationClrSchemeLst(xmlTextReaderPtr reader); void readVariationClrScheme(xmlTextReaderPtr reader, VSDXVariationClrScheme &varClrSch); void readFontScheme(xmlTextReaderPtr reader); void readFont(xmlTextReaderPtr reader, int idToken, VSDXFont &font); bool readTypeFace(xmlTextReaderPtr reader, librevenge::RVNGString &typeFace); bool readTypeFace(xmlTextReaderPtr reader, int &script, librevenge::RVNGString &typeFace); + void readFmtScheme(xmlTextReaderPtr reader); + void readFillStyleLst(xmlTextReaderPtr reader); int getElementToken(xmlTextReaderPtr reader); + void skipUnimplemented(xmlTextReaderPtr reader, int idToken); VSDXClrScheme m_clrScheme; VSDXFontScheme m_fontScheme; + std::vector<boost::optional<Colour>> m_fillStyleLst; }; } // namespace libvisio diff --git a/src/test/data/qs-box.vsdx b/src/test/data/qs-box.vsdx Binary files differnew file mode 100644 index 0000000..59be43c --- /dev/null +++ b/src/test/data/qs-box.vsdx diff --git a/src/test/importtest.cpp b/src/test/importtest.cpp index 89e497f..12e909a 100644 --- a/src/test/importtest.cpp +++ b/src/test/importtest.cpp @@ -218,6 +218,7 @@ class ImportTest : public CPPUNIT_NS::TestFixture CPPUNIT_TEST(testBmpFileHeader); CPPUNIT_TEST(testBmpFileHeader2); CPPUNIT_TEST(testVsdxImportDefaultFillColour); + CPPUNIT_TEST(testVsdxQickStyleFillStyle); CPPUNIT_TEST_SUITE_END(); void testVsdxMetadataTitle(); @@ -236,6 +237,7 @@ class ImportTest : public CPPUNIT_NS::TestFixture void testBmpFileHeader(); void testBmpFileHeader2(); void testVsdxImportDefaultFillColour(); + void testVsdxQickStyleFillStyle(); xmlBufferPtr m_buffer; xmlDocPtr m_doc; @@ -533,6 +535,16 @@ void ImportTest::testVsdxImportDefaultFillColour() assertXPath(m_doc, "/document/page/layer[1]//setStyle[2]", "fill-color", "#5b9bd5"); } +void ImportTest::testVsdxQickStyleFillStyle() +{ + // Without the accompanying fix in place, this test would have failed with: + // equality assertion failed + // - Expected: #ffffff + // - Actual : #fec000 + m_doc = parse("qs-box.vsdx", m_buffer); + assertXPath(m_doc, "/document/page/layer[1]//setStyle[2]", "fill-color", "#ffffff"); +} + CPPUNIT_TEST_SUITE_REGISTRATION(ImportTest); /* vim:set shiftwidth=2 softtabstop=2 expandtab: */ |