drawinglayer/source/tools/emfphelperdata.cxx | 44 ++++++---- drawinglayer/source/tools/emfpstringformat.cxx | 8 - emfio/qa/cppunit/emf/EmfImportTest.cxx | 92 ++++++++++++++++++++++ emfio/qa/cppunit/emf/data/TestDrawStringAlign.emf |binary 4 files changed, 122 insertions(+), 22 deletions(-)
New commits: commit b19b08e51163e949ba4aa656196ebb554ca879a2 Author: Bartosz Kosiorek <gan...@poczta.onet.pl> AuthorDate: Thu Jun 24 18:58:39 2021 +0200 Commit: Xisco Fauli <xiscofa...@libreoffice.org> CommitDate: Fri Jul 2 12:50:29 2021 +0200 EMF+ tdf#142995 tdf#142997 tdf#143076 Add alignment support for DrawString With this commit, real size of the text is used to make proper horizontal alignment. Additionally vertical alignment is added and fix for Center alignment was applied Change-Id: I17d9fd7de7f00f5e69f99c5b09061eb6059be67e Reviewed-on: https://gerrit.libreoffice.org/c/core/+/117794 Tested-by: Jenkins Reviewed-by: Bartosz Kosiorek <gan...@poczta.onet.pl> (cherry picked from commit 574dc1e8ff6ea4214fefd91216fca5146a4ff13e) Reviewed-on: https://gerrit.libreoffice.org/c/core/+/118257 Reviewed-by: Xisco Fauli <xiscofa...@libreoffice.org> diff --git a/drawinglayer/source/tools/emfphelperdata.cxx b/drawinglayer/source/tools/emfphelperdata.cxx index e756b16ff70f..23ceb6487d66 100644 --- a/drawinglayer/source/tools/emfphelperdata.cxx +++ b/drawinglayer/source/tools/emfphelperdata.cxx @@ -34,6 +34,7 @@ #include <drawinglayer/primitive2d/PolyPolygonColorPrimitive2D.hxx> #include <drawinglayer/primitive2d/svggradientprimitive2d.hxx> #include <drawinglayer/primitive2d/textdecoratedprimitive2d.hxx> +#include <drawinglayer/primitive2d/textlayoutdevice.hxx> #include <drawinglayer/primitive2d/textprimitive2d.hxx> #include <drawinglayer/primitive2d/bitmapprimitive2d.hxx> #include <drawinglayer/primitive2d/metafileprimitive2d.hxx> @@ -1568,25 +1569,35 @@ namespace emfplushelper css::lang::Locale locale; double stringAlignmentHorizontalOffset = 0.0; + double stringAlignmentVerticalOffset = font->emSize; if (stringFormat) { - SAL_WARN_IF(stringFormat->DirectionRightToLeft(), "drawinglayer.emf", "EMF+\t DrawString Alignment TODO For a right-to-left layout rectangle, the origin should be at the upper right."); + LanguageTag aLanguageTag(static_cast<LanguageType>(stringFormat->language)); + locale = aLanguageTag.getLocale(); + drawinglayer::primitive2d::TextLayouterDevice aTextLayouter; + + aTextLayouter.setFontAttribute(fontAttribute, font->emSize, + font->emSize, locale); + + double fTextWidth = aTextLayouter.getTextWidth(text, 0, stringLength); + SAL_WARN_IF(stringFormat->DirectionRightToLeft(), "drawinglayer.emf", + "EMF+\t DrawString Alignment TODO For a right-to-left layout rectangle, the origin should be at the upper right."); if (stringFormat->stringAlignment == StringAlignmentNear) - // Alignment is to the left side of the layout rectangle (lx, ly, lw, lh) - { + // Alignment is to the left side of the layout rectangle (lx, ly, lw, lh) stringAlignmentHorizontalOffset = stringFormat->leadingMargin * font->emSize; - } else if (stringFormat->stringAlignment == StringAlignmentCenter) - // Alignment is centered between the origin and extent of the layout rectangle - { - stringAlignmentHorizontalOffset = 0.5 * lw + stringFormat->leadingMargin * font->emSize - 0.3 * font->emSize * stringLength; - } else if (stringFormat->stringAlignment == StringAlignmentFar) - // Alignment is to the right side of the layout rectangle - { - stringAlignmentHorizontalOffset = lw - stringFormat->trailingMargin * font->emSize - 0.6 * font->emSize * stringLength; - } - - LanguageTag aLanguageTag(static_cast< LanguageType >(stringFormat->language)); - locale = aLanguageTag.getLocale(); + else if (stringFormat->stringAlignment == StringAlignmentCenter) + // Alignment is centered between the origin and extent of the layout rectangle + stringAlignmentHorizontalOffset = 0.5 * lw + (stringFormat->leadingMargin - stringFormat->trailingMargin) * font->emSize - 0.5 * fTextWidth; + else if (stringFormat->stringAlignment == StringAlignmentFar) + // Alignment is to the right side of the layout rectangle + stringAlignmentHorizontalOffset = lw - stringFormat->trailingMargin * font->emSize - fTextWidth; + + if (stringFormat->lineAlign == StringAlignmentNear) + stringAlignmentVerticalOffset = font->emSize; + else if (stringFormat->lineAlign == StringAlignmentCenter) + stringAlignmentVerticalOffset = 0.5 * lh + 0.5 * font->emSize; + else if (stringFormat->lineAlign == StringAlignmentFar) + stringAlignmentVerticalOffset = lh; } else { @@ -1600,7 +1611,8 @@ namespace emfplushelper const basegfx::B2DHomMatrix transformMatrix = basegfx::utils::createScaleTranslateB2DHomMatrix( ::basegfx::B2DSize(font->emSize, font->emSize), - ::basegfx::B2DPoint(lx + stringAlignmentHorizontalOffset, ly + font->emSize)); + ::basegfx::B2DPoint(lx + stringAlignmentHorizontalOffset, + ly + stringAlignmentVerticalOffset)); Color uncorrectedColor = EMFPGetBrushColorOrARGBColor(flags, brushId); Color color; diff --git a/drawinglayer/source/tools/emfpstringformat.cxx b/drawinglayer/source/tools/emfpstringformat.cxx index 63cc42471b3b..071493c13062 100644 --- a/drawinglayer/source/tools/emfpstringformat.cxx +++ b/drawinglayer/source/tools/emfpstringformat.cxx @@ -217,18 +217,14 @@ namespace emfplushelper SAL_INFO("drawinglayer.emf", "EMF+\t\tTabStopCount: " << tabStopCount); SAL_INFO("drawinglayer.emf", "EMF+\t\tRangeCount: " << rangeCount); - SAL_WARN_IF(stringAlignment != StringAlignment::StringAlignmentNear, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:StringAlignment"); - SAL_WARN_IF(lineAlign != StringAlignment::StringAlignmentNear, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:lineAlign"); SAL_WARN_IF(digitSubstitution != StringDigitSubstitution::StringDigitSubstitutionNone, - "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:digitSubstitution"); + "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:digitSubstitution"); SAL_WARN_IF(firstTabOffset != 0.0, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:firstTabOffset"); SAL_WARN_IF(hotkeyPrefix != HotkeyPrefix::HotkeyPrefixNone, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:hotkeyPrefix"); - SAL_WARN_IF(leadingMargin != 0.0, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:leadingMargin"); - SAL_WARN_IF(trailingMargin != 0.0, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:trailingMargin"); SAL_WARN_IF(tracking != 1.0, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:tracking"); SAL_WARN_IF(trimming != StringTrimming::StringTrimmingNone, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:trimming"); SAL_WARN_IF(tabStopCount, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:tabStopCount"); - SAL_WARN_IF(rangeCount, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:StringFormatData"); + SAL_WARN_IF(rangeCount != 0, "drawinglayer.emf", "EMF+\t TODO EMFPStringFormat:StringFormatData"); } } diff --git a/emfio/qa/cppunit/emf/EmfImportTest.cxx b/emfio/qa/cppunit/emf/EmfImportTest.cxx index 34288bcf61eb..63e1d575803b 100644 --- a/emfio/qa/cppunit/emf/EmfImportTest.cxx +++ b/emfio/qa/cppunit/emf/EmfImportTest.cxx @@ -47,6 +47,7 @@ class Test : public test::BootstrapFixture, public XmlTestTools, public unotest: void testPolyPolygon(); void TestDrawString(); + void TestDrawStringAlign(); void TestDrawStringTransparent(); void TestDrawStringWithBrush(); void TestDrawLine(); @@ -87,6 +88,7 @@ public: CPPUNIT_TEST_SUITE(Test); CPPUNIT_TEST(testPolyPolygon); CPPUNIT_TEST(TestDrawString); + CPPUNIT_TEST(TestDrawStringAlign); CPPUNIT_TEST(TestDrawStringTransparent); CPPUNIT_TEST(TestDrawStringWithBrush); CPPUNIT_TEST(TestDrawLine); @@ -210,6 +212,96 @@ void Test::TestDrawString() #endif } +void Test::TestDrawStringAlign() +{ +#if HAVE_MORE_FONTS + // EMF+ DrawString with alignment (StringAlignmentNear, StringAlignmentFar, StringAlignmentCenter) + // It seems Arial font is replaced with Liberation Sans. These numbers are valid for Liberation Sans. + Primitive2DSequence aSequence = parseEmf(u"/emfio/qa/cppunit/emf/data/TestDrawStringAlign.emf"); + CPPUNIT_ASSERT_EQUAL(1, static_cast<int>(aSequence.getLength())); + drawinglayer::Primitive2dXmlDump dumper; + xmlDocUniquePtr pDocument = dumper.dumpAndParse(comphelper::sequenceToContainer<Primitive2DContainer>(aSequence)); + CPPUNIT_ASSERT(pDocument); + + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform", 9); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[1]/textsimpleportion", + "width", "12"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[1]/textsimpleportion", + "height", "12"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[1]/textsimpleportion", + "x", "12"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[1]/textsimpleportion", + "y", "22"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[1]/textsimpleportion", + "text", "HLVT"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[1]/textsimpleportion", + "fontcolor", "#000000"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[1]/textsimpleportion", + "familyname", "ARIAL"); + + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[2]/textsimpleportion", + "width", "12"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[2]/textsimpleportion", + "height", "12"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[2]/textsimpleportion", + "x", "143"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[2]/textsimpleportion", + "y", "22"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[2]/textsimpleportion", + "text", "HCVT"); + + // TODO Make the position of the text the same across the platforms (Arial vs Liberation Sans). + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[3]/textsimpleportion", + "x", "276"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[3]/textsimpleportion", + "y", "22"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[3]/textsimpleportion", + "text", "HRVT"); + + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[4]/textsimpleportion", + "x", "12"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[4]/textsimpleportion", + "y", "66"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[4]/textsimpleportion", + "text", "HLVC"); + + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[5]/textsimpleportion", + "x", "142"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[5]/textsimpleportion", + "y", "66"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[5]/textsimpleportion", + "text", "HCVC"); + + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[6]/textsimpleportion", + "x", "274"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[6]/textsimpleportion", + "y", "66"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[6]/textsimpleportion", + "text", "HRVC"); + + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[7]/textsimpleportion", + "x", "12"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[7]/textsimpleportion", + "y", "110"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[7]/textsimpleportion", + "text", "HLVB"); + + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[8]/textsimpleportion", + "x", "143"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[8]/textsimpleportion", + "y", "110"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[8]/textsimpleportion", + "text", "HCVB"); + + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[9]/textsimpleportion", + "x", "275"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[9]/textsimpleportion", + "y", "110"); + assertXPath(pDocument, "/primitive2D/metafile/transform/mask/transform[9]/textsimpleportion", + "text", "HRVB"); +#endif +} + void Test::TestDrawStringTransparent() { #if HAVE_MORE_FONTS diff --git a/emfio/qa/cppunit/emf/data/TestDrawStringAlign.emf b/emfio/qa/cppunit/emf/data/TestDrawStringAlign.emf new file mode 100644 index 000000000000..bc3a33c61fc2 Binary files /dev/null and b/emfio/qa/cppunit/emf/data/TestDrawStringAlign.emf differ _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits