diff options
-rw-r--r-- | oox/source/shape/WpsContext.cxx | 84 | ||||
-rw-r--r-- | sw/qa/extras/ooxmlexport/data/tbrl-textbox.docx | bin | 0 -> 17300 bytes | |||
-rw-r--r-- | sw/qa/extras/ooxmlexport/ooxmlexport13.cxx | 10 | ||||
-rw-r--r-- | sw/source/core/doc/textboxhelper.cxx | 62 |
4 files changed, 84 insertions, 72 deletions
diff --git a/oox/source/shape/WpsContext.cxx b/oox/source/shape/WpsContext.cxx index 19b413f5c329..0f39a850b0ee 100644 --- a/oox/source/shape/WpsContext.cxx +++ b/oox/source/shape/WpsContext.cxx @@ -59,61 +59,39 @@ oox::core::ContextHandlerRef WpsContext::onCreateContext(sal_Int32 nElementToken { uno::Reference<lang::XServiceInfo> xServiceInfo(mxShape, uno::UNO_QUERY); uno::Reference<beans::XPropertySet> xPropertySet(mxShape, uno::UNO_QUERY); - OptValue<OUString> oVert = rAttribs.getString(XML_vert); - if (oVert.has() && oVert.get() == "vert270") + sal_Int32 nVert = rAttribs.getToken(XML_vert, XML_horz); + if (nVert != XML_horz) { - if (xServiceInfo->supportsService("com.sun.star.text.TextFrame")) - { - // No support for this in core, work around by char rotation, as we do so for table cells already. - uno::Reference<text::XText> xText(mxShape, uno::UNO_QUERY); - uno::Reference<text::XTextCursor> xTextCursor = xText->createTextCursor(); - xTextCursor->gotoStart(false); - xTextCursor->gotoEnd(true); - uno::Reference<beans::XPropertyState> xPropertyState(xTextCursor, - uno::UNO_QUERY); - beans::PropertyState aState - = xPropertyState->getPropertyState("CharRotation"); - if (aState == beans::PropertyState_DEFAULT_VALUE) - { - uno::Reference<beans::XPropertySet> xTextCursorPropertySet( - xTextCursor, uno::UNO_QUERY); - xTextCursorPropertySet->setPropertyValue("CharRotation", - uno::makeAny(sal_Int16(900))); - } - } - else - { - // Get the existing rotation of the shape. - drawing::HomogenMatrix3 aMatrix; - xPropertySet->getPropertyValue("Transformation") >>= aMatrix; - basegfx::B2DHomMatrix aTransformation; - aTransformation.set(0, 0, aMatrix.Line1.Column1); - aTransformation.set(0, 1, aMatrix.Line1.Column2); - aTransformation.set(0, 2, aMatrix.Line1.Column3); - aTransformation.set(1, 0, aMatrix.Line1.Column1); - aTransformation.set(1, 1, aMatrix.Line2.Column2); - aTransformation.set(1, 2, aMatrix.Line3.Column3); - aTransformation.set(2, 0, aMatrix.Line1.Column1); - aTransformation.set(2, 1, aMatrix.Line2.Column2); - aTransformation.set(2, 2, aMatrix.Line3.Column3); - basegfx::B2DTuple aScale; - basegfx::B2DTuple aTranslate; - double fRotate = 0; - double fShearX = 0; - aTransformation.decompose(aScale, aTranslate, fRotate, fShearX); + // Get the existing rotation of the shape. + drawing::HomogenMatrix3 aMatrix; + xPropertySet->getPropertyValue("Transformation") >>= aMatrix; + basegfx::B2DHomMatrix aTransformation; + aTransformation.set(0, 0, aMatrix.Line1.Column1); + aTransformation.set(0, 1, aMatrix.Line1.Column2); + aTransformation.set(0, 2, aMatrix.Line1.Column3); + aTransformation.set(1, 0, aMatrix.Line1.Column1); + aTransformation.set(1, 1, aMatrix.Line2.Column2); + aTransformation.set(1, 2, aMatrix.Line3.Column3); + aTransformation.set(2, 0, aMatrix.Line1.Column1); + aTransformation.set(2, 1, aMatrix.Line2.Column2); + aTransformation.set(2, 2, aMatrix.Line3.Column3); + basegfx::B2DTuple aScale; + basegfx::B2DTuple aTranslate; + double fRotate = 0; + double fShearX = 0; + aTransformation.decompose(aScale, aTranslate, fRotate, fShearX); - // If the text is not rotated the way the shape wants it already, set the angle. - const sal_Int32 nRotation = -270; - if (static_cast<long>(basegfx::rad2deg(fRotate)) - != NormAngle36000(static_cast<long>(nRotation) * 100) / 100) - { - comphelper::SequenceAsHashMap aCustomShapeGeometry( - xPropertySet->getPropertyValue("CustomShapeGeometry")); - aCustomShapeGeometry["TextPreRotateAngle"] <<= nRotation; - xPropertySet->setPropertyValue( - "CustomShapeGeometry", - uno::makeAny(aCustomShapeGeometry.getAsConstPropertyValueList())); - } + // If the text is not rotated the way the shape wants it already, set the angle. + const sal_Int32 nRotation = nVert == XML_vert270 ? -270 : -90; + if (static_cast<long>(basegfx::rad2deg(fRotate)) + != NormAngle36000(static_cast<long>(nRotation) * 100) / 100) + { + comphelper::SequenceAsHashMap aCustomShapeGeometry( + xPropertySet->getPropertyValue("CustomShapeGeometry")); + aCustomShapeGeometry["TextPreRotateAngle"] <<= nRotation; + xPropertySet->setPropertyValue( + "CustomShapeGeometry", + uno::makeAny(aCustomShapeGeometry.getAsConstPropertyValueList())); } } diff --git a/sw/qa/extras/ooxmlexport/data/tbrl-textbox.docx b/sw/qa/extras/ooxmlexport/data/tbrl-textbox.docx Binary files differnew file mode 100644 index 000000000000..bdfcc5fff19a --- /dev/null +++ b/sw/qa/extras/ooxmlexport/data/tbrl-textbox.docx diff --git a/sw/qa/extras/ooxmlexport/ooxmlexport13.cxx b/sw/qa/extras/ooxmlexport/ooxmlexport13.cxx index 5bf170249e1a..578d1ac06bd7 100644 --- a/sw/qa/extras/ooxmlexport/ooxmlexport13.cxx +++ b/sw/qa/extras/ooxmlexport/ooxmlexport13.cxx @@ -65,6 +65,16 @@ DECLARE_OOXMLEXPORT_TEST(testendingSectionProps, "endingSectionProps.docx") //CPPUNIT_ASSERT_EQUAL_MESSAGE("Section Left Margin", sal_Int32(2540), getProperty<sal_Int32>(xSect, "SectionLeftMargin")); } +DECLARE_OOXMLEXPORT_TEST(testTbrlTextbox, "tbrl-textbox.docx") +{ + uno::Reference<beans::XPropertySet> xPropertySet(getShape(1), uno::UNO_QUERY); + comphelper::SequenceAsHashMap aGeometry(xPropertySet->getPropertyValue("CustomShapeGeometry")); + // Without the accompanying fix in place, this test would have failed with 'Expected: -90; + // Actual: 0', i.e. tbRl writing direction was imported as lrTb. + CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(-90), + aGeometry["TextPreRotateAngle"].get<sal_Int32>()); +} + DECLARE_OOXMLEXPORT_TEST(testTdf124637_sectionMargin, "tdf124637_sectionMargin.docx") { uno::Reference<text::XTextSectionsSupplier> xTextSectionsSupplier(mxComponent, uno::UNO_QUERY); diff --git a/sw/source/core/doc/textboxhelper.cxx b/sw/source/core/doc/textboxhelper.cxx index 007a568ae7eb..532f1ea9f00f 100644 --- a/sw/source/core/doc/textboxhelper.cxx +++ b/sw/source/core/doc/textboxhelper.cxx @@ -44,6 +44,7 @@ #include <com/sun/star/text/WrapTextMode.hpp> #include <com/sun/star/text/XTextDocument.hpp> #include <com/sun/star/table/BorderLine2.hpp> +#include <com/sun/star/text/WritingMode2.hpp> using namespace com::sun::star; @@ -349,29 +350,49 @@ void SwTextBoxHelper::syncProperty(SwFrameFormat* pShape, const OUString& rPrope uno::makeAny(static_cast<sal_Int32>(convertTwipToMm100(aRectangle.Top())))); } - if (SwFrameFormat* pFormat = getOtherTextBoxFormat(pShape, RES_DRAWFRMFMT)) + SwFrameFormat* pFormat = getOtherTextBoxFormat(pShape, RES_DRAWFRMFMT); + if (!pFormat) + return; + + comphelper::SequenceAsHashMap aCustomShapeGeometry(rValue); + auto it = aCustomShapeGeometry.find("TextPreRotateAngle"); + if (it != aCustomShapeGeometry.end()) { - comphelper::SequenceAsHashMap aCustomShapeGeometry(rValue); - // That would be the btLr text direction which we don't support at a frame level, so do it at a character level. - if (aCustomShapeGeometry.find("TextPreRotateAngle") != aCustomShapeGeometry.end() - && aCustomShapeGeometry["TextPreRotateAngle"].get<sal_Int32>() == -270) + auto nTextPreRotateAngle = it->second.get<sal_Int32>(); + if (nTextPreRotateAngle == -270) { - if (const SwNodeIndex* pNodeIndex = pFormat->GetContent().GetContentIdx()) + // That would be the btLr text direction which we don't support at a frame level, so + // do it at a character level. + const SwNodeIndex* pNodeIndex = pFormat->GetContent().GetContentIdx(); + if (!pNodeIndex) + return; + + SwPaM aPaM(*pFormat->GetDoc()->GetNodes()[pNodeIndex->GetIndex() + 1], 0); + aPaM.SetMark(); + if (SwTextNode* pMark + = pFormat->GetDoc() + ->GetNodes()[pNodeIndex->GetNode().EndOfSectionIndex() - 1] + ->GetTextNode()) { - SwPaM aPaM(*pFormat->GetDoc()->GetNodes()[pNodeIndex->GetIndex() + 1], 0); - aPaM.SetMark(); - if (SwTextNode* pMark - = pFormat->GetDoc() - ->GetNodes()[pNodeIndex->GetNode().EndOfSectionIndex() - 1] - ->GetTextNode()) - { - aPaM.GetMark()->nNode = *pMark; - aPaM.GetMark()->nContent.Assign(pMark, pMark->GetText().getLength()); - SvxCharRotateItem aItem(900, false, RES_CHRATR_ROTATE); - pFormat->GetDoc()->getIDocumentContentOperations().InsertPoolItem(aPaM, - aItem); - } + aPaM.GetMark()->nNode = *pMark; + aPaM.GetMark()->nContent.Assign(pMark, pMark->GetText().getLength()); + SvxCharRotateItem aItem(900, false, RES_CHRATR_ROTATE); + pFormat->GetDoc()->getIDocumentContentOperations().InsertPoolItem(aPaM, aItem); } + return; + } + + sal_Int16 nDirection = 0; + switch (nTextPreRotateAngle) + { + case -90: + nDirection = text::WritingMode2::TB_RL; + break; + } + + if (nDirection) + { + syncProperty(pShape, RES_FRAMEDIR, 0, uno::makeAny(nDirection)); } } } @@ -548,6 +569,9 @@ void SwTextBoxHelper::syncProperty(SwFrameFormat* pShape, sal_uInt16 nWID, sal_u case RES_OPAQUE: aPropertyName = UNO_NAME_OPAQUE; break; + case RES_FRAMEDIR: + aPropertyName = UNO_NAME_WRITING_MODE; + break; } if (!aPropertyName.isEmpty()) |