summaryrefslogtreecommitdiff
path: root/svx/source
diff options
context:
space:
mode:
authorAttila Szűcs <attila.szucs@collabora.com>2023-01-13 04:49:33 +0100
committerMiklos Vajna <vmiklos@collabora.com>2023-01-20 07:56:29 +0000
commitf9d6dd788e82a1964dab9cc0d0436c8c54b775c0 (patch)
treeed2d99c3771c43530f5883c2fa4e4102bd187854 /svx/source
parent14da39fcfffe8006a79971ac0b670e12d0d7a0ea (diff)
tdf#148000 impress: Handle linebreaks on fontwork.
Split text lines in a paragraph, right before polygons are created for rendering, so eol will brake line in fontwork just like eop. Change-Id: Ie9e6764f9f91c2e19afd43dc9a212bd18c41c99d Reviewed-on: https://gerrit.libreoffice.org/c/core/+/145425 Tested-by: Jenkins Reviewed-by: Miklos Vajna <vmiklos@collabora.com>
Diffstat (limited to 'svx/source')
-rw-r--r--svx/source/customshapes/EnhancedCustomShapeFontWork.cxx57
-rw-r--r--svx/source/svdraw/svdmodel.cxx42
2 files changed, 87 insertions, 12 deletions
diff --git a/svx/source/customshapes/EnhancedCustomShapeFontWork.cxx b/svx/source/customshapes/EnhancedCustomShapeFontWork.cxx
index e8e3bd026cd1..672cd28fbc8e 100644
--- a/svx/source/customshapes/EnhancedCustomShapeFontWork.cxx
+++ b/svx/source/customshapes/EnhancedCustomShapeFontWork.cxx
@@ -36,6 +36,7 @@
#include <editeng/charscaleitem.hxx>
#include <svx/svdoashp.hxx>
#include <svx/sdshitm.hxx>
+#include <svx/svdmodel.hxx>
#include <editeng/outlobj.hxx>
#include <editeng/editobj.hxx>
#include <o3tl/numeric.hxx>
@@ -50,6 +51,7 @@
#include <sal/log.hxx>
#include <rtl/math.hxx>
#include <unotools/configmgr.hxx>
+#include <comphelper/string.hxx>
using namespace com::sun::star;
using namespace com::sun::star::uno;
@@ -116,27 +118,58 @@ static bool InitializeFontWorkData(
if ( pParaObj )
{
const EditTextObject& rTextObj = pParaObj->GetTextObject();
- sal_Int32 nParagraphsLeft = rTextObj.GetParagraphCount();
+ sal_Int32 nParagraphsCount = rTextObj.GetParagraphCount();
+
+ // Collect all the lines from all paragraphs
+ std::vector<int> aLineParaID; // which para this line is in
+ std::vector<int> aLineStart; // where this line start in that para
+ std::vector<int> aLineLength;
+ std::vector<OUString> aParaText;
+ for (sal_Int32 nPara = 0; nPara < nParagraphsCount; ++nPara)
+ {
+ aParaText.push_back(rTextObj.GetText(nPara));
+ sal_Int32 nPos = 0;
+ sal_Int32 nPrevPos = 0;
+ do
+ {
+ // search line break.
+ if (!rSdrObjCustomShape.getSdrModelFromSdrObject().IsLegacySingleLineFontwork())
+ nPos = aParaText[nPara].indexOf(sal_Unicode(u'\1'), nPrevPos);
+ else
+ nPos = -1; // tdf#148000: ignore line breaks in legacy fontworks
+
+ aLineParaID.push_back(nPara);
+ aLineStart.push_back(nPrevPos);
+ aLineLength.push_back((nPos >= 0 ? nPos : aParaText[nPara].getLength())
+ - nPrevPos);
+ nPrevPos = nPos + 1;
+ } while (nPos >= 0);
+ }
+
+ sal_Int32 nLinesLeft = aLineParaID.size();
- rFWData.nMaxParagraphsPerTextArea = ( ( nParagraphsLeft - 1 ) / nTextAreaCount ) + 1;
- sal_Int32 j = 0;
- while( nParagraphsLeft && nTextAreaCount )
+ rFWData.nMaxParagraphsPerTextArea = ((nLinesLeft - 1) / nTextAreaCount) + 1;
+ sal_Int32 nLine = 0;
+ while (nLinesLeft && nTextAreaCount)
{
FWTextArea aTextArea;
- sal_Int32 i, nParagraphs = ( ( nParagraphsLeft - 1 ) / nTextAreaCount ) + 1;
- for ( i = 0; i < nParagraphs; ++i, ++j )
+ sal_Int32 nLinesInPara = ((nLinesLeft - 1) / nTextAreaCount) + 1;
+ for (sal_Int32 i = 0; i < nLinesInPara; ++i, ++nLine)
{
FWParagraphData aParagraphData;
- aParagraphData.aString = rTextObj.GetText( j );
+ aParagraphData.aString = aParaText[aLineParaID[nLine]].subView(
+ aLineStart[nLine], aLineLength[nLine]);
- const SfxItemSet& rParaSet = rTextObj.GetParaAttribs( j ); // retrieving some paragraph attributes
- aParagraphData.nFrameDirection = rParaSet.Get( EE_PARA_WRITINGDIR ).GetValue();
- aTextArea.vParagraphs.push_back( aParagraphData );
+ // retrieving some paragraph attributes
+ const SfxItemSet& rParaSet = rTextObj.GetParaAttribs(aLineParaID[nLine]);
+ aParagraphData.nFrameDirection = rParaSet.Get(EE_PARA_WRITINGDIR).GetValue();
+ aTextArea.vParagraphs.push_back(aParagraphData);
}
- rFWData.vTextAreas.push_back( aTextArea );
- nParagraphsLeft -= nParagraphs;
+ rFWData.vTextAreas.push_back(aTextArea);
+ nLinesLeft -= nLinesInPara;
nTextAreaCount--;
}
+
bNoErr = true;
}
}
diff --git a/svx/source/svdraw/svdmodel.cxx b/svx/source/svdraw/svdmodel.cxx
index 3feb1ae0669b..bc86671c9437 100644
--- a/svx/source/svdraw/svdmodel.cxx
+++ b/svx/source/svdraw/svdmodel.cxx
@@ -72,6 +72,9 @@
#include <comphelper/diagnose_ex.hxx>
#include <tools/UnitConversion.hxx>
#include <svx/ColorSets.hxx>
+#include <svx/svditer.hxx>
+#include <svx/svdoashp.hxx>
+
using namespace ::com::sun::star;
@@ -80,12 +83,14 @@ struct SdrModelImpl
SfxUndoManager* mpUndoManager;
SdrUndoFactory* mpUndoFactory;
bool mbAnchoredTextOverflowLegacy; // tdf#99729 compatibility flag
+ bool mbLegacySingleLineFontwork; // tdf#148000 compatibility flag
std::unique_ptr<svx::Theme> mpTheme;
SdrModelImpl()
: mpUndoManager(nullptr)
, mpUndoFactory(nullptr)
, mbAnchoredTextOverflowLegacy(false)
+ , mbLegacySingleLineFontwork(false)
{}
};
@@ -1718,6 +1723,16 @@ bool SdrModel::IsAnchoredTextOverflowLegacy() const
return mpImpl->mbAnchoredTextOverflowLegacy;
}
+void SdrModel::SetLegacySingleLineFontwork(bool bEnabled)
+{
+ mpImpl->mbLegacySingleLineFontwork = bEnabled;
+}
+
+bool SdrModel::IsLegacySingleLineFontwork() const
+{
+ return mpImpl->mbLegacySingleLineFontwork;
+}
+
void SdrModel::ReformatAllTextObjects()
{
ImpReformatAllTextObjects();
@@ -1761,6 +1776,32 @@ void SdrModel::ReadUserDataSequenceValue(const beans::PropertyValue* pValue)
mpImpl->mbAnchoredTextOverflowLegacy = bBool;
}
}
+ else if (pValue->Name == "LegacySingleLineFontwork")
+ {
+ bool bBool = false;
+ if (pValue->Value >>= bBool)
+ {
+ mpImpl->mbLegacySingleLineFontwork = bBool;
+ // tdf#148000 hack: reset all CustomShape geometry as they may depend on this property
+ // Ideally this ReadUserDataSequenceValue should be called before geometry creation
+ // Once the calling order will be fixed, this hack will not be needed.
+ for (size_t i = 0; i < maPages.size(); ++i)
+ {
+ if (const SdrPage* pPage = maPages[i].get())
+ {
+ SdrObjListIter aIter(pPage, SdrIterMode::DeepWithGroups);
+ while (aIter.IsMore())
+ {
+ SdrObject* pTempObj = aIter.Next();
+ if (SdrObjCustomShape* pShape = dynamic_cast<SdrObjCustomShape*>(pTempObj))
+ {
+ pShape->InvalidateRenderGeometry();
+ }
+ }
+ }
+ }
+ }
+ }
}
template <typename T>
@@ -1773,6 +1814,7 @@ void SdrModel::WriteUserDataSequence(uno::Sequence <beans::PropertyValue>& rValu
{
std::vector< std::pair< OUString, uno::Any > > aUserData;
addPair(aUserData, "AnchoredTextOverflowLegacy", IsAnchoredTextOverflowLegacy());
+ addPair(aUserData, "LegacySingleLineFontwork", IsLegacySingleLineFontwork());
const sal_Int32 nOldLength = rValues.getLength();
rValues.realloc(nOldLength + aUserData.size());