From a2fa768b73d96352ffafd166564d2c1cb2e140c3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Toma=C5=BE=20Vajngerl?= Date: Sat, 6 Nov 2021 21:45:37 +0100 Subject: [PATCH] extend XML dumpig for primitives to support fontwork objects MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This adds support for 3D drawinglayer primitive XML dumping and adds dumping support for many more primitives and attributes that were missing before. This is needed to be able to check the fontwork objects, which can be rendered in 3D. Change-Id: I0e78be4d4030a0cae3d2b952a1a38de8940ee310 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/124804 Tested-by: Jenkins Reviewed-by: Tomaž Vajngerl --- drawinglayer/Library_drawinglayer.mk | 1 + .../attribute/sdrlightingattribute3d.cxx | 5 + drawinglayer/source/primitive3d/Tools.cxx | 67 +++ .../source/tools/primitive2dxmldump.cxx | 431 ++++++++++++++++++ .../attribute/sdrlightingattribute3d.hxx | 1 + include/drawinglayer/primitive3d/Tools.hxx | 21 + svx/qa/unit/data/FontWork.odg | Bin 0 -> 10515 bytes svx/qa/unit/svdraw.cxx | 40 ++ 8 files changed, 566 insertions(+) create mode 100644 drawinglayer/source/primitive3d/Tools.cxx create mode 100644 include/drawinglayer/primitive3d/Tools.hxx create mode 100644 svx/qa/unit/data/FontWork.odg diff --git a/drawinglayer/Library_drawinglayer.mk b/drawinglayer/Library_drawinglayer.mk index 158ea62be0ac..11edeae98c92 100644 --- a/drawinglayer/Library_drawinglayer.mk +++ b/drawinglayer/Library_drawinglayer.mk @@ -153,6 +153,7 @@ $(eval $(call gb_Library_add_exception_objects,drawinglayer,\ drawinglayer/source/primitive3d/shadowprimitive3d \ drawinglayer/source/primitive3d/textureprimitive3d \ drawinglayer/source/primitive3d/transformprimitive3d \ + drawinglayer/source/primitive3d/Tools \ drawinglayer/source/processor2d/baseprocessor2d \ drawinglayer/source/processor2d/processor2dtools \ drawinglayer/source/processor2d/contourextractor2d \ diff --git a/drawinglayer/source/attribute/sdrlightingattribute3d.cxx b/drawinglayer/source/attribute/sdrlightingattribute3d.cxx index b07fa88c7ce3..90fcc193c271 100644 --- a/drawinglayer/source/attribute/sdrlightingattribute3d.cxx +++ b/drawinglayer/source/attribute/sdrlightingattribute3d.cxx @@ -105,6 +105,11 @@ namespace drawinglayer::attribute return mpSdrLightingAttribute->getLightVector(); } + const basegfx::BColor& SdrLightingAttribute::getAmbientLightColor() const + { + return mpSdrLightingAttribute->maAmbientLight; + } + // color model solver basegfx::BColor SdrLightingAttribute::solveColorModel( const basegfx::B3DVector& rNormalInEyeCoordinates, diff --git a/drawinglayer/source/primitive3d/Tools.cxx b/drawinglayer/source/primitive3d/Tools.cxx new file mode 100644 index 000000000000..c27896b043cc --- /dev/null +++ b/drawinglayer/source/primitive3d/Tools.cxx @@ -0,0 +1,67 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + */ + +#include +#include + +using namespace css; + +namespace drawinglayer::primitive3d +{ +OUString idToString(sal_uInt32 nId) +{ + switch (nId) + { + case PRIMITIVE3D_ID_GROUPPRIMITIVE3D: + return "GROUPPRIMITIVE3D"; + case PRIMITIVE3D_ID_HATCHTEXTUREPRIMITIVE3D: + return "HATCHTEXTUREPRIMITIVE3D"; + case PRIMITIVE3D_ID_MODIFIEDCOLORPRIMITIVE3D: + return "MODIFIEDCOLORPRIMITIVE3D"; + case PRIMITIVE3D_ID_POLYGONHAIRLINEPRIMITIVE3D: + return "POLYGONHAIRLINEPRIMITIVE3D"; + case PRIMITIVE3D_ID_POLYGONSTROKEPRIMITIVE3D: + return "POLYGONSTROKEPRIMITIVE3D"; + case PRIMITIVE3D_ID_POLYGONTUBEPRIMITIVE3D: + return "POLYGONTUBEPRIMITIVE3D"; + case PRIMITIVE3D_ID_POLYPOLYGONMATERIALPRIMITIVE3D: + return "POLYPOLYGONMATERIALPRIMITIVE3D"; + case PRIMITIVE3D_ID_SDRCUBEPRIMITIVE3D: + return "SDRCUBEPRIMITIVE3D"; + case PRIMITIVE3D_ID_SDREXTRUDEPRIMITIVE3D: + return "SDREXTRUDEPRIMITIVE3D"; + case PRIMITIVE3D_ID_SDRLATHEPRIMITIVE3D: + return "SDRLATHEPRIMITIVE3D"; + case PRIMITIVE3D_ID_SDRPOLYPOLYGONPRIMITIVE3D: + return "SDRPOLYPOLYGONPRIMITIVE3D"; + case PRIMITIVE3D_ID_SDRSPHEREPRIMITIVE3D: + return "SDRSPHEREPRIMITIVE3D"; + case PRIMITIVE3D_ID_SHADOWPRIMITIVE3D: + return "SHADOWPRIMITIVE3D"; + case PRIMITIVE3D_ID_UNIFIEDTRANSPARENCETEXTUREPRIMITIVE3D: + return "UNIFIEDTRANSPARENCETEXTUREPRIMITIVE3D"; + case PRIMITIVE3D_ID_GRADIENTTEXTUREPRIMITIVE3D: + return "GRADIENTTEXTUREPRIMITIVE3D"; + case PRIMITIVE3D_ID_BITMAPTEXTUREPRIMITIVE3D: + return "BITMAPTEXTUREPRIMITIVE3D"; + case PRIMITIVE3D_ID_TRANSPARENCETEXTUREPRIMITIVE3D: + return "TRANSPARENCETEXTUREPRIMITIVE3D"; + case PRIMITIVE3D_ID_TRANSFORMPRIMITIVE3D: + return "TRANSFORMPRIMITIVE3D"; + case PRIMITIVE3D_ID_HIDDENGEOMETRYPRIMITIVE3D: + return "HIDDENGEOMETRYPRIMITIVE3D"; + default: + return OUString::number((nId >> 16) & 0xFF) + "|" + OUString::number(nId & 0xFF); + } +} + +} // end of namespace drawinglayer::primitive2d + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/drawinglayer/source/tools/primitive2dxmldump.cxx b/drawinglayer/source/tools/primitive2dxmldump.cxx index 17bb707b666e..b679465a69c2 100644 --- a/drawinglayer/source/tools/primitive2dxmldump.cxx +++ b/drawinglayer/source/tools/primitive2dxmldump.cxx @@ -33,6 +33,7 @@ #include #include #include +#include #include #include #include @@ -42,6 +43,18 @@ #include #include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + using namespace drawinglayer::primitive2d; namespace drawinglayer @@ -69,6 +82,26 @@ void writeMatrix(::tools::XmlWriter& rWriter, const basegfx::B2DHomMatrix& rMatr rWriter.attribute("xy33", rMatrix.get(2, 2)); } +void writeMatrix3D(::tools::XmlWriter& rWriter, const basegfx::B3DHomMatrix& rMatrix) +{ + rWriter.attribute("xy11", rMatrix.get(0, 0)); + rWriter.attribute("xy12", rMatrix.get(0, 1)); + rWriter.attribute("xy13", rMatrix.get(0, 2)); + rWriter.attribute("xy14", rMatrix.get(0, 3)); + rWriter.attribute("xy21", rMatrix.get(1, 0)); + rWriter.attribute("xy22", rMatrix.get(1, 1)); + rWriter.attribute("xy23", rMatrix.get(1, 2)); + rWriter.attribute("xy24", rMatrix.get(1, 3)); + rWriter.attribute("xy31", rMatrix.get(2, 0)); + rWriter.attribute("xy32", rMatrix.get(2, 1)); + rWriter.attribute("xy33", rMatrix.get(2, 2)); + rWriter.attribute("xy34", rMatrix.get(2, 3)); + rWriter.attribute("xy41", rMatrix.get(3, 0)); + rWriter.attribute("xy42", rMatrix.get(3, 1)); + rWriter.attribute("xy43", rMatrix.get(3, 2)); + rWriter.attribute("xy44", rMatrix.get(3, 3)); +} + void writePolyPolygon(::tools::XmlWriter& rWriter, const basegfx::B2DPolyPolygon& rB2DPolyPolygon) { rWriter.startElement("polypolygon"); @@ -141,6 +174,271 @@ void writeLineAttribute(::tools::XmlWriter& rWriter, rWriter.endElement(); } +void writeSdrLineAttribute(::tools::XmlWriter& rWriter, + const drawinglayer::attribute::SdrLineAttribute& rLineAttribute) +{ + if (rLineAttribute.isDefault()) + return; + + rWriter.startElement("line"); + rWriter.attribute("color", convertColorToString(rLineAttribute.getColor())); + rWriter.attribute("width", rLineAttribute.getWidth()); + rWriter.attribute("transparence", rLineAttribute.getTransparence()); + + switch (rLineAttribute.getJoin()) + { + case basegfx::B2DLineJoin::NONE: + rWriter.attribute("linejoin", "NONE"); + break; + case basegfx::B2DLineJoin::Bevel: + rWriter.attribute("linejoin", "Bevel"); + break; + case basegfx::B2DLineJoin::Miter: + rWriter.attribute("linejoin", "Miter"); + break; + case basegfx::B2DLineJoin::Round: + rWriter.attribute("linejoin", "Round"); + break; + default: + rWriter.attribute("linejoin", "Unknown"); + break; + } + switch (rLineAttribute.getCap()) + { + case css::drawing::LineCap::LineCap_BUTT: + rWriter.attribute("linecap", "BUTT"); + break; + case css::drawing::LineCap::LineCap_ROUND: + rWriter.attribute("linecap", "ROUND"); + break; + case css::drawing::LineCap::LineCap_SQUARE: + rWriter.attribute("linecap", "SQUARE"); + break; + default: + rWriter.attribute("linecap", "Unknown"); + break; + } + + if (!rLineAttribute.getDotDashArray().empty()) + { + OUString sDotDash; + for (double fDotDash : rLineAttribute.getDotDashArray()) + { + sDotDash += OUString::number(fDotDash) + " "; + } + rWriter.attribute("dotDashArray", sDotDash); + rWriter.attribute("fullDotDashLength", rLineAttribute.getFullDotDashLen()); + } + + rWriter.endElement(); +} + +void writeSdrFillAttribute(::tools::XmlWriter& rWriter, + const drawinglayer::attribute::SdrFillAttribute& rFillAttribute) +{ + if (rFillAttribute.isDefault()) + return; + + rWriter.startElement("fill"); + rWriter.attribute("color", convertColorToString(rFillAttribute.getColor())); + rWriter.attribute("transparence", rFillAttribute.getTransparence()); + + auto const& rGradient = rFillAttribute.getGradient(); + if (!rGradient.isDefault()) + { + rWriter.startElement("gradient"); + switch (rGradient.getStyle()) + { + case drawinglayer::attribute::GradientStyle::Linear: + rWriter.attribute("style", "Linear"); + break; + case drawinglayer::attribute::GradientStyle::Axial: + rWriter.attribute("style", "Axial"); + break; + case drawinglayer::attribute::GradientStyle::Radial: + rWriter.attribute("style", "Radial"); + break; + case drawinglayer::attribute::GradientStyle::Elliptical: + rWriter.attribute("style", "Elliptical"); + break; + case drawinglayer::attribute::GradientStyle::Square: + rWriter.attribute("style", "Square"); + break; + case drawinglayer::attribute::GradientStyle::Rect: + rWriter.attribute("style", "Rect"); + break; + }; + rWriter.attribute("border", rGradient.getBorder()); + rWriter.attribute("offsetX", rGradient.getOffsetX()); + rWriter.attribute("offsetY", rGradient.getOffsetY()); + rWriter.attribute("angle", rGradient.getAngle()); + rWriter.attribute("steps", rGradient.getSteps()); + rWriter.attribute("startColor", convertColorToString(rGradient.getStartColor())); + rWriter.attribute("endColor", convertColorToString(rGradient.getEndColor())); + rWriter.endElement(); + } + + auto const& rHatch = rFillAttribute.getHatch(); + if (!rHatch.isDefault()) + { + rWriter.startElement("hatch"); + switch (rHatch.getStyle()) + { + case drawinglayer::attribute::HatchStyle::Single: + rWriter.attribute("style", "Single"); + break; + case drawinglayer::attribute::HatchStyle::Double: + rWriter.attribute("style", "Double"); + break; + case drawinglayer::attribute::HatchStyle::Triple: + rWriter.attribute("style", "Triple"); + break; + }; + rWriter.attribute("distance", rHatch.getDistance()); + rWriter.attribute("angle", rHatch.getAngle()); + rWriter.attribute("color", convertColorToString(rHatch.getColor())); + rWriter.attribute("minimalDescreteDistance", rHatch.getMinimalDiscreteDistance()); + rWriter.attribute("isFillBackground", sal_Int32(rHatch.isFillBackground())); + rWriter.endElement(); + } + + auto const& rGraphic = rFillAttribute.getFillGraphic(); + if (!rGraphic.isDefault()) + { + rWriter.startElement("graphic"); + // TODO + rWriter.endElement(); + } + + rWriter.endElement(); +} + +void writeShadeMode(::tools::XmlWriter& rWriter, const css::drawing::ShadeMode& rMode) +{ + switch (rMode) + { + case css::drawing::ShadeMode_FLAT: + rWriter.attribute("shadeMode", "Flat"); + break; + case css::drawing::ShadeMode_SMOOTH: + rWriter.attribute("shadeMode", "Smooth"); + break; + case css::drawing::ShadeMode_PHONG: + rWriter.attribute("shadeMode", "Phong"); + break; + case css::drawing::ShadeMode_DRAFT: + rWriter.attribute("shadeMode", "Draft"); + break; + default: + rWriter.attribute("shadeMode", "Undefined"); + break; + } +} + +void writeProjectionMode(::tools::XmlWriter& rWriter, const css::drawing::ProjectionMode& rMode) +{ + switch (rMode) + { + case css::drawing::ProjectionMode_PARALLEL: + rWriter.attribute("projectionMode", "Parallel"); + break; + case css::drawing::ProjectionMode_PERSPECTIVE: + rWriter.attribute("projectionMode", "Perspective"); + break; + default: + rWriter.attribute("projectionMode", "Undefined"); + break; + } +} + +void writeNormalsKind(::tools::XmlWriter& rWriter, const css::drawing::NormalsKind& rKind) +{ + switch (rKind) + { + case css::drawing::NormalsKind_SPECIFIC: + rWriter.attribute("normalsKind", "Specific"); + break; + case css::drawing::NormalsKind_FLAT: + rWriter.attribute("normalsKind", "Flat"); + break; + case css::drawing::NormalsKind_SPHERE: + rWriter.attribute("normalsKind", "Sphere"); + break; + default: + rWriter.attribute("normalsKind", "Undefined"); + break; + } +} + +void writeTextureProjectionMode(::tools::XmlWriter& rWriter, const char* pElement, + const css::drawing::TextureProjectionMode& rMode) +{ + switch (rMode) + { + case css::drawing::TextureProjectionMode_OBJECTSPECIFIC: + rWriter.attribute(pElement, "Specific"); + break; + case css::drawing::TextureProjectionMode_PARALLEL: + rWriter.attribute(pElement, "Parallel"); + break; + case css::drawing::TextureProjectionMode_SPHERE: + rWriter.attribute(pElement, "Sphere"); + break; + default: + rWriter.attribute(pElement, "Undefined"); + break; + } +} + +void writeTextureKind(::tools::XmlWriter& rWriter, const css::drawing::TextureKind2& rKind) +{ + switch (rKind) + { + case css::drawing::TextureKind2_LUMINANCE: + rWriter.attribute("textureKind", "Luminance"); + break; + case css::drawing::TextureKind2_INTENSITY: + rWriter.attribute("textureKind", "Intensity"); + break; + case css::drawing::TextureKind2_COLOR: + rWriter.attribute("textureKind", "Color"); + break; + default: + rWriter.attribute("textureKind", "Undefined"); + break; + } +} + +void writeTextureMode(::tools::XmlWriter& rWriter, const css::drawing::TextureMode& rMode) +{ + switch (rMode) + { + case css::drawing::TextureMode_REPLACE: + rWriter.attribute("textureMode", "Replace"); + break; + case css::drawing::TextureMode_MODULATE: + rWriter.attribute("textureMode", "Modulate"); + break; + case css::drawing::TextureMode_BLEND: + rWriter.attribute("textureMode", "Blend"); + break; + default: + rWriter.attribute("textureMode", "Undefined"); + break; + } +} + +void writeMaterialAttribute(::tools::XmlWriter& rWriter, + const drawinglayer::attribute::MaterialAttribute3D& rMaterial) +{ + rWriter.startElement("material"); + rWriter.attribute("color", convertColorToString(rMaterial.getColor())); + rWriter.attribute("specular", convertColorToString(rMaterial.getSpecular())); + rWriter.attribute("emission", convertColorToString(rMaterial.getEmission())); + rWriter.attribute("specularIntensity", rMaterial.getSpecularIntensity()); + rWriter.endElement(); +} + } // end anonymous namespace Primitive2dXmlDump::Primitive2dXmlDump() @@ -173,6 +471,102 @@ void Primitive2dXmlDump::dump( pStream->Seek(STREAM_SEEK_TO_BEGIN); } +namespace +{ +class Primitive3DXmlDump +{ +public: + void decomposeAndWrite(const drawinglayer::primitive3d::Primitive3DContainer& rSequence, + ::tools::XmlWriter& rWriter) + { + for (size_t i = 0; i < rSequence.size(); i++) + { + drawinglayer::primitive3d::Primitive3DReference xReference = rSequence[i]; + const auto* pBasePrimitive + = static_cast(xReference.get()); + sal_uInt32 nId = pBasePrimitive->getPrimitive3DID(); + OUString sCurrentElementTag = drawinglayer::primitive3d::idToString(nId); + switch (nId) + { + case PRIMITIVE3D_ID_SDREXTRUDEPRIMITIVE3D: + { + const auto* pExtrudePrimitive3D + = static_cast( + xReference.get()); + rWriter.startElement("extrude3D"); + + rWriter.startElement("matrix3D"); + writeMatrix3D(rWriter, pExtrudePrimitive3D->getTransform()); + rWriter.endElement(); + + rWriter.attribute("textureSizeX", pExtrudePrimitive3D->getTextureSize().getX()); + rWriter.attribute("textureSizeY", pExtrudePrimitive3D->getTextureSize().getY()); + auto const& rLFSAttribute = pExtrudePrimitive3D->getSdrLFSAttribute(); + writeSdrLineAttribute(rWriter, rLFSAttribute.getLine()); + writeSdrFillAttribute(rWriter, rLFSAttribute.getFill()); + + rWriter.startElement("object3Dattributes"); + { + auto const& r3DObjectAttributes + = pExtrudePrimitive3D->getSdr3DObjectAttribute(); + + writeNormalsKind(rWriter, r3DObjectAttributes.getNormalsKind()); + writeTextureProjectionMode(rWriter, "textureProjectionX", + r3DObjectAttributes.getTextureProjectionX()); + writeTextureProjectionMode(rWriter, "textureProjectionY", + r3DObjectAttributes.getTextureProjectionY()); + writeTextureKind(rWriter, r3DObjectAttributes.getTextureKind()); + writeTextureMode(rWriter, r3DObjectAttributes.getTextureMode()); + writeMaterialAttribute(rWriter, r3DObjectAttributes.getMaterial()); + + rWriter.attribute("normalsInvert", + sal_Int32(r3DObjectAttributes.getNormalsInvert())); + rWriter.attribute("doubleSided", + sal_Int32(r3DObjectAttributes.getDoubleSided())); + rWriter.attribute("shadow3D", sal_Int32(r3DObjectAttributes.getShadow3D())); + rWriter.attribute("textureFilter", + sal_Int32(r3DObjectAttributes.getTextureFilter())); + rWriter.attribute("reducedGeometry", + sal_Int32(r3DObjectAttributes.getReducedLineGeometry())); + } + rWriter.endElement(); + + rWriter.attribute("depth", pExtrudePrimitive3D->getDepth()); + rWriter.attribute("diagonal", pExtrudePrimitive3D->getDiagonal()); + rWriter.attribute("backScale", pExtrudePrimitive3D->getBackScale()); + rWriter.attribute("smoothNormals", + sal_Int32(pExtrudePrimitive3D->getSmoothNormals())); + rWriter.attribute("smoothLids", + sal_Int32(pExtrudePrimitive3D->getSmoothLids())); + rWriter.attribute("characterMode", + sal_Int32(pExtrudePrimitive3D->getCharacterMode())); + rWriter.attribute("closeFront", + sal_Int32(pExtrudePrimitive3D->getCloseFront())); + rWriter.attribute("closeBack", sal_Int32(pExtrudePrimitive3D->getCloseBack())); + writePolyPolygon(rWriter, pExtrudePrimitive3D->getPolyPolygon()); + rWriter.endElement(); + } + break; + + default: + { + rWriter.startElement("unhandled"); + rWriter.attribute("id", + OUStringToOString(sCurrentElementTag, RTL_TEXTENCODING_UTF8)); + rWriter.attribute("idNumber", nId); + + drawinglayer::geometry::ViewInformation3D aViewInformation3D; + drawinglayer::primitive3d::Primitive3DContainer aContainer; + aContainer = pBasePrimitive->get3DDecomposition(aViewInformation3D); + decomposeAndWrite(aContainer, rWriter); + rWriter.endElement(); + } + break; + } + } + } +}; +} xmlDocUniquePtr Primitive2dXmlDump::dumpAndParse( const drawinglayer::primitive2d::Primitive2DContainer& rPrimitive2DSequence, const OUString& rStreamName) @@ -620,6 +1014,43 @@ void Primitive2dXmlDump::decomposeAndWrite( break; } + case PRIMITIVE2D_ID_SCENEPRIMITIVE2D: + { + const auto& rScenePrimitive2D + = dynamic_cast( + *pBasePrimitive); + rWriter.startElement("scene"); + + auto const& rSceneAttribute = rScenePrimitive2D.getSdrSceneAttribute(); + + rWriter.attribute("shadowSlant", rSceneAttribute.getShadowSlant()); + rWriter.attribute("isTwoSidedLighting", + sal_Int32(rSceneAttribute.getTwoSidedLighting())); + writeShadeMode(rWriter, rSceneAttribute.getShadeMode()); + writeProjectionMode(rWriter, rSceneAttribute.getProjectionMode()); + + auto const& rLightingAttribute = rScenePrimitive2D.getSdrLightingAttribute(); + rWriter.attribute("ambientLightColor", + convertColorToString(rLightingAttribute.getAmbientLightColor())); + rWriter.startElement("lights"); + for (auto const& rLight : rLightingAttribute.getLightVector()) + { + rWriter.startElement("light"); + rWriter.attribute("color", convertColorToString(rLight.getColor())); + rWriter.attribute("directionVectorX", rLight.getDirection().getX()); + rWriter.attribute("directionVectorY", rLight.getDirection().getY()); + rWriter.attribute("specular", sal_Int32(rLight.getSpecular())); + rWriter.endElement(); + } + rWriter.endElement(); + + Primitive3DXmlDump aPrimitive3DXmlDump; + aPrimitive3DXmlDump.decomposeAndWrite(rScenePrimitive2D.getChildren3D(), rWriter); + + rWriter.endElement(); + break; + } + default: { OString aName("unhandled"); diff --git a/include/drawinglayer/attribute/sdrlightingattribute3d.hxx b/include/drawinglayer/attribute/sdrlightingattribute3d.hxx index d7557ebbd45a..ae2155a542ab 100644 --- a/include/drawinglayer/attribute/sdrlightingattribute3d.hxx +++ b/include/drawinglayer/attribute/sdrlightingattribute3d.hxx @@ -68,6 +68,7 @@ namespace drawinglayer::attribute bool operator==(const SdrLightingAttribute& rCandidate) const; // data read access + const basegfx::BColor& getAmbientLightColor() const; const ::std::vector< Sdr3DLightAttribute >& getLightVector() const; // color model solver diff --git a/include/drawinglayer/primitive3d/Tools.hxx b/include/drawinglayer/primitive3d/Tools.hxx new file mode 100644 index 000000000000..4f0d4967efb1 --- /dev/null +++ b/include/drawinglayer/primitive3d/Tools.hxx @@ -0,0 +1,21 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + */ + +#pragma once + +#include +#include + +namespace drawinglayer::primitive3d +{ +OUString DRAWINGLAYER_DLLPUBLIC idToString(sal_uInt32 nId); +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svx/qa/unit/data/FontWork.odg b/svx/qa/unit/data/FontWork.odg new file mode 100644 index 0000000000000000000000000000000000000000..e14d2f70bde7934e80a6de0da2f27be0cb824877 GIT binary patch literal 10515 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®qFSj65-A0<1xH zkAQr*>%vj7RTUQOC5O(}Q}kauM0l`K$Sm)YK=djn+HxL|U5pK*W97sk z+wk5yd!r&A4obI|Pck`nkd~vy9#|8_=t z={GK3i~riAKgyo|w>(s@Gw`oGf0RM}JWm137 z^HV7G8}om`^FL%$e^2)3?xBGG&tdwrjOw3Ezg)#1_n3ahbH5?|%Jf@S_3IJ-W%tJ< z#?Kw7-;jd;(|**y8vZf*{F&qU4PwkcXFPsc{#|tX+cFRT?_HG~T tqE}7g|654^)#{Hv;HO9Z4NH>0@vrhy5U)Wt0D$!Rp?Y=EGo(My{tLwGEw=yw literal 0 HcmV?d00001 diff --git a/svx/qa/unit/svdraw.cxx b/svx/qa/unit/svdraw.cxx index 8cf0f889eea7..5050136991bf 100644 --- a/svx/qa/unit/svdraw.cxx +++ b/svx/qa/unit/svdraw.cxx @@ -351,6 +351,46 @@ CPPUNIT_TEST_FIXTURE(SvdrawTest, testAutoHeightMultiColShape) static_cast(o3tl::convert(2477601, o3tl::Length::emu, o3tl::Length::mm100)), xShape->getSize().Height, 1); } + +CPPUNIT_TEST_FIXTURE(SvdrawTest, testFontWorks) +{ + OUString aURL = m_directories.getURLFromSrc(u"svx/qa/unit/data/FontWork.odg"); + mxComponent = loadFromDesktop(aURL, "com.sun.star.comp.drawing.DrawingDocument"); + + uno::Reference xDrawPagesSupplier(mxComponent, + uno::UNO_QUERY_THROW); + CPPUNIT_ASSERT(xDrawPagesSupplier.is()); + uno::Reference xDrawPages(xDrawPagesSupplier->getDrawPages()); + uno::Reference xDrawPage(xDrawPages->getByIndex(0), uno::UNO_QUERY_THROW); + CPPUNIT_ASSERT(xDrawPage.is()); + uno::Reference xShape(xDrawPage->getByIndex(0), uno::UNO_QUERY); + CPPUNIT_ASSERT(xShape.is()); + + auto pDrawPage = dynamic_cast(xDrawPage.get()); + CPPUNIT_ASSERT(pDrawPage); + SdrPage* pSdrPage = pDrawPage->GetSdrPage(); + + ScopedVclPtrInstance aVirtualDevice; + sdr::contact::ObjectContactOfObjListPainter aObjectContact(*aVirtualDevice, + { pSdrPage->GetObj(0) }, nullptr); + const auto& rDrawPageVOContact + = pSdrPage->GetViewContact().GetViewObjectContact(aObjectContact); + sdr::contact::DisplayInfo aDisplayInfo; + drawinglayer::primitive2d::Primitive2DContainer xPrimitiveSequence; + rDrawPageVOContact.getPrimitive2DSequenceHierarchy(aDisplayInfo, xPrimitiveSequence); + + drawinglayer::Primitive2dXmlDump aDumper; + xmlDocUniquePtr pXmlDoc = aDumper.dumpAndParse(xPrimitiveSequence); + CPPUNIT_ASSERT(pXmlDoc); + + assertXPath(pXmlDoc, "/primitive2D", 1); + + assertXPath(pXmlDoc, "//scene", "projectionMode", "Perspective"); + assertXPath(pXmlDoc, "//scene/extrude3D[1]/fill", "color", "#ff0000"); + assertXPath(pXmlDoc, "//scene/extrude3D[1]/object3Dattributes/material", "color", "#ff0000"); + assertXPath(pXmlDoc, "//scene/extrude3D[1]/object3Dattributes/material", "specularIntensity", + "20"); +} } /* vim:set shiftwidth=4 softtabstop=4 expandtab: */