Kaydet (Commit) fd95fb97 authored tarafından Serge Krot's avatar Serge Krot Kaydeden (comit) Thorsten Behrens

tdf#125719 sw: rtf: refactor associated character properties

1. \rtlch, \ltrch should be placed before their properties.
2. Do not mix associated and normal character properties in output.
3. Do not output empty "\rtlch \ltrch", "\ltrch \rtlch" pairs.
4. Handle associated character properties runs instead of
handling separately their parts without order of them.

Change-Id: Ibbf7365d04708682a5f1eb664a579c60a47465d2
Reviewed-on: https://gerrit.libreoffice.org/72578
Tested-by: Jenkins
Reviewed-by: 's avatarThorsten Behrens <Thorsten.Behrens@CIB.de>
üst 50696615
This diff is collapsed.
This diff is collapsed.
......@@ -12,6 +12,7 @@
#include <com/sun/star/text/XFootnote.hpp>
#include <com/sun/star/text/XFootnotesSupplier.hpp>
#include <com/sun/star/text/TextContentAnchorType.hpp>
#include <com/sun/star/awt/FontWeight.hpp>
class Test : public SwModelTestBase
{
......@@ -228,6 +229,24 @@ DECLARE_RTFEXPORT_TEST(testTdf122455, "tdf122455.rtf")
CPPUNIT_ASSERT_EQUAL(16.0, getProperty<double>(getRun(getParagraph(1), 1), "CharHeight"));
}
DECLARE_RTFEXPORT_TEST(testTdf125719_case_1, "tdf125719_case_1.rtf")
{
CPPUNIT_ASSERT_EQUAL(awt::FontWeight::NORMAL,
getProperty<float>(getRun(getParagraph(1), 1), "CharWeight"));
CPPUNIT_ASSERT_EQUAL(awt::FontWeight::NORMAL,
getProperty<float>(getRun(getParagraph(3), 1), "CharWeight"));
}
DECLARE_RTFEXPORT_TEST(testTdf125719_case_2, "tdf125719_case_2.rtf")
{
CPPUNIT_ASSERT_EQUAL(awt::FontWeight::BOLD,
getProperty<float>(getRun(getParagraph(1), 1), "CharWeight"));
CPPUNIT_ASSERT_EQUAL(awt::FontWeight::BOLD,
getProperty<float>(getRun(getParagraph(3), 1), "CharWeight"));
CPPUNIT_ASSERT_EQUAL(awt::FontWeight::NORMAL,
getProperty<float>(getRun(getParagraph(5), 1), "CharWeight"));
}
DECLARE_RTFEXPORT_TEST(testTabs, "tabs.rtf")
{
// Test tab alignment in decimal mode.
......
......@@ -84,7 +84,7 @@ public:
// Access to (anyway) private buffers, used by the sdr exporter
OStringBuffer& RunText();
OStringBuffer& Styles() { return m_aStyles; }
OStringBuffer& StylesEnd();
OString MoveCharacterProperties(bool aAutoWriteRtlLtr = false);
/// Output text (without markup).
void RawText(const OUString& rText, rtl_TextEncoding eCharSet) override;
......@@ -516,9 +516,12 @@ private:
*/
OStringBuffer m_aStyles;
/*
* This is the same as m_aStyles but the contents of it is written last.
* This is the same as m_aStyles but the contents of it is Assoc.
*/
OStringBuffer m_aStylesEnd;
OStringBuffer m_aStylesAssoc;
bool m_bIsRTL;
sal_uInt16 m_nScript;
bool m_bControlLtrRtl;
sal_Int32 m_nNextAnnotationMarkId;
sal_Int32 m_nCurrentAnnotationMarkId;
......
......@@ -706,8 +706,7 @@ void RtfSdrExport::WriteOutliner(const OutlinerParaObject& rParaObj, TextTypes e
const sal_Int32 nEnd = aStr.getLength();
aAttrIter.OutParaAttr(false);
m_rAttrOutput.RunText().append(m_rAttrOutput.Styles().makeStringAndClear());
m_rAttrOutput.RunText().append(m_rAttrOutput.StylesEnd().makeStringAndClear());
m_rAttrOutput.RunText().append(m_rAttrOutput.MoveCharacterProperties(true));
do
{
......@@ -716,8 +715,7 @@ void RtfSdrExport::WriteOutliner(const OutlinerParaObject& rParaObj, TextTypes e
aAttrIter.OutAttr(nCurrentPos);
m_rAttrOutput.RunText().append('{');
m_rAttrOutput.RunText().append(m_rAttrOutput.Styles().makeStringAndClear());
m_rAttrOutput.RunText().append(m_rAttrOutput.StylesEnd().makeStringAndClear());
m_rAttrOutput.RunText().append(m_rAttrOutput.MoveCharacterProperties(true));
m_rAttrOutput.RunText().append(SAL_NEWLINE_STRING);
bool bTextAtr = aAttrIter.IsTextAttr(nCurrentPos);
if (!bTextAtr)
......
......@@ -473,8 +473,7 @@ RTFError RTFDocumentImpl::dispatchFlag(RTFKeyword nKeyword)
m_aStates.top().setCurrentEncoding(getEncoding(getFontIndex(m_nDefaultFontIndex)));
m_aStates.top().getCharacterAttributes() = getDefaultState().getCharacterAttributes();
m_aStates.top().setCurrentCharacterStyleIndex(-1);
m_aStates.top().setIsRightToLeft(false);
m_aStates.top().setRunType(RTFParserState::RunType::LOCH);
m_aStates.top().setRunType(RTFParserState::RunType::NONE);
}
break;
case RTF_PARD:
......@@ -565,6 +564,7 @@ RTFError RTFDocumentImpl::dispatchFlag(RTFKeyword nKeyword)
case RTF_RTLSECT:
{
auto pValue = new RTFValue(nKeyword == RTF_LTRSECT ? 0 : 1);
m_aStates.top().setRunType(RTFParserState::RunType::NONE);
m_aStates.top().getParagraphSprms().set(NS_ooxml::LN_EG_SectPrContents_textDirection,
pValue);
}
......@@ -573,20 +573,29 @@ RTFError RTFDocumentImpl::dispatchFlag(RTFKeyword nKeyword)
case RTF_RTLPAR:
{
auto pValue = new RTFValue(nKeyword == RTF_LTRPAR ? 0 : 1);
m_aStates.top().setRunType(RTFParserState::RunType::NONE);
m_aStates.top().getParagraphSprms().set(NS_ooxml::LN_CT_PPrBase_bidi, pValue);
}
break;
case RTF_LTRROW:
case RTF_RTLROW:
m_aStates.top().setRunType(RTFParserState::RunType::NONE);
m_aStates.top().getTableRowSprms().set(NS_ooxml::LN_CT_TblPrBase_bidiVisual,
new RTFValue(int(nKeyword == RTF_RTLROW)));
break;
case RTF_LTRCH:
// dmapper does not support this.
m_aStates.top().setIsRightToLeft(false);
if (m_aStates.top().getRunType() == RTFParserState::RunType::RTLCH_LTRCH_1)
m_aStates.top().setRunType(RTFParserState::RunType::RTLCH_LTRCH_2);
else
m_aStates.top().setRunType(RTFParserState::RunType::LTRCH_RTLCH_1);
break;
case RTF_RTLCH:
m_aStates.top().setIsRightToLeft(true);
if (m_aStates.top().getRunType() == RTFParserState::RunType::LTRCH_RTLCH_1)
m_aStates.top().setRunType(RTFParserState::RunType::LTRCH_RTLCH_2);
else
m_aStates.top().setRunType(RTFParserState::RunType::RTLCH_LTRCH_1);
if (m_aDefaultState.getCurrentEncoding() == RTL_TEXTENCODING_MS_1255)
m_aStates.top().setCurrentEncoding(m_aDefaultState.getCurrentEncoding());
break;
......
......@@ -164,10 +164,22 @@ RTFError RTFDocumentImpl::dispatchValue(RTFKeyword nKeyword, int nParam)
{
case RTF_FS:
case RTF_AFS:
nSprm = (m_aStates.top().getIsRightToLeft()
|| m_aStates.top().getRunType() == RTFParserState::RunType::HICH)
? NS_ooxml::LN_EG_RPrBase_szCs
: NS_ooxml::LN_EG_RPrBase_sz;
switch (m_aStates.top().getRunType())
{
case RTFParserState::RunType::HICH:
case RTFParserState::RunType::RTLCH_LTRCH_1:
case RTFParserState::RunType::LTRCH_RTLCH_2:
case RTFParserState::RunType::DBCH:
nSprm = NS_ooxml::LN_EG_RPrBase_szCs;
break;
case RTFParserState::RunType::NONE:
case RTFParserState::RunType::LOCH:
case RTFParserState::RunType::LTRCH_RTLCH_1:
case RTFParserState::RunType::RTLCH_LTRCH_2:
default:
nSprm = NS_ooxml::LN_EG_RPrBase_sz;
break;
}
break;
case RTF_EXPNDTW:
nSprm = NS_ooxml::LN_EG_RPrBase_spacing;
......@@ -191,19 +203,23 @@ RTFError RTFDocumentImpl::dispatchValue(RTFKeyword nKeyword, int nParam)
{
case RTF_LANG:
case RTF_ALANG:
if (m_aStates.top().getIsRightToLeft()
|| m_aStates.top().getRunType() == RTFParserState::RunType::HICH)
{
nSprm = NS_ooxml::LN_CT_Language_bidi;
}
else if (m_aStates.top().getRunType() == RTFParserState::RunType::DBCH)
switch (m_aStates.top().getRunType())
{
nSprm = NS_ooxml::LN_CT_Language_eastAsia;
}
else
{
assert(m_aStates.top().getRunType() == RTFParserState::RunType::LOCH);
nSprm = NS_ooxml::LN_CT_Language_val;
case RTFParserState::RunType::HICH:
case RTFParserState::RunType::RTLCH_LTRCH_1:
case RTFParserState::RunType::LTRCH_RTLCH_2:
nSprm = NS_ooxml::LN_CT_Language_bidi;
break;
case RTFParserState::RunType::DBCH:
nSprm = NS_ooxml::LN_CT_Language_eastAsia;
break;
case RTFParserState::RunType::NONE:
case RTFParserState::RunType::LOCH:
case RTFParserState::RunType::LTRCH_RTLCH_1:
case RTFParserState::RunType::RTLCH_LTRCH_2:
default:
nSprm = NS_ooxml::LN_CT_Language_val;
break;
}
break;
case RTF_LANGFE: // this one is always CJK apparently
......@@ -336,20 +352,25 @@ RTFError RTFDocumentImpl::dispatchValue(RTFKeyword nKeyword, int nParam)
{
case RTF_F:
case RTF_AF:
if (m_aStates.top().getIsRightToLeft()
|| m_aStates.top().getRunType() == RTFParserState::RunType::HICH)
{
nSprm = NS_ooxml::LN_CT_Fonts_cs;
}
else if (m_aStates.top().getRunType() == RTFParserState::RunType::DBCH)
switch (m_aStates.top().getRunType())
{
nSprm = NS_ooxml::LN_CT_Fonts_eastAsia;
}
else
{
assert(m_aStates.top().getRunType() == RTFParserState::RunType::LOCH);
nSprm = NS_ooxml::LN_CT_Fonts_ascii;
case RTFParserState::RunType::HICH:
case RTFParserState::RunType::RTLCH_LTRCH_1:
case RTFParserState::RunType::LTRCH_RTLCH_2:
nSprm = NS_ooxml::LN_CT_Fonts_cs;
break;
case RTFParserState::RunType::DBCH:
nSprm = NS_ooxml::LN_CT_Fonts_eastAsia;
break;
case RTFParserState::RunType::NONE:
case RTFParserState::RunType::LOCH:
case RTFParserState::RunType::LTRCH_RTLCH_1:
case RTFParserState::RunType::RTLCH_LTRCH_2:
default:
nSprm = NS_ooxml::LN_CT_Fonts_ascii;
break;
}
if (m_aStates.top().getDestination() == Destination::FONTTABLE
|| m_aStates.top().getDestination() == Destination::FONTENTRY)
{
......
......@@ -1850,17 +1850,41 @@ RTFError RTFDocumentImpl::dispatchToggle(RTFKeyword nKeyword, bool bParam, int n
{
case RTF_B:
case RTF_AB:
nSprm = (m_aStates.top().getIsRightToLeft()
|| m_aStates.top().getRunType() == RTFParserState::RunType::HICH)
? NS_ooxml::LN_EG_RPrBase_bCs
: NS_ooxml::LN_EG_RPrBase_b;
switch (m_aStates.top().getRunType())
{
case RTFParserState::RunType::HICH:
case RTFParserState::RunType::RTLCH_LTRCH_1:
case RTFParserState::RunType::LTRCH_RTLCH_2:
case RTFParserState::RunType::DBCH:
nSprm = NS_ooxml::LN_EG_RPrBase_bCs;
break;
case RTFParserState::RunType::NONE:
case RTFParserState::RunType::LOCH:
case RTFParserState::RunType::LTRCH_RTLCH_1:
case RTFParserState::RunType::RTLCH_LTRCH_2:
default:
nSprm = NS_ooxml::LN_EG_RPrBase_b;
break;
}
break;
case RTF_I:
case RTF_AI:
nSprm = (m_aStates.top().getIsRightToLeft()
|| m_aStates.top().getRunType() == RTFParserState::RunType::HICH)
? NS_ooxml::LN_EG_RPrBase_iCs
: NS_ooxml::LN_EG_RPrBase_i;
switch (m_aStates.top().getRunType())
{
case RTFParserState::RunType::HICH:
case RTFParserState::RunType::RTLCH_LTRCH_1:
case RTFParserState::RunType::LTRCH_RTLCH_2:
case RTFParserState::RunType::DBCH:
nSprm = NS_ooxml::LN_EG_RPrBase_iCs;
break;
case RTFParserState::RunType::NONE:
case RTFParserState::RunType::LOCH:
case RTFParserState::RunType::LTRCH_RTLCH_1:
case RTFParserState::RunType::RTLCH_LTRCH_2:
default:
nSprm = NS_ooxml::LN_EG_RPrBase_i;
break;
}
break;
case RTF_OUTL:
nSprm = NS_ooxml::LN_EG_RPrBase_outline;
......@@ -1950,7 +1974,11 @@ RTFError RTFDocumentImpl::pushState()
else
{
// fdo#85812 group resets run type of _current_ and new state (but not RTL)
m_aStates.top().setRunType(RTFParserState::RunType::LOCH);
if (m_aStates.top().getRunType() != RTFParserState::RunType::LTRCH_RTLCH_2
&& m_aStates.top().getRunType() != RTFParserState::RunType::RTLCH_LTRCH_2)
{
m_aStates.top().setRunType(RTFParserState::RunType::NONE);
}
if (m_aStates.top().getDestination() == Destination::MR)
lcl_DestinationToMath(m_aStates.top().getCurrentDestinationText(), m_aMathBuffer,
......@@ -3567,8 +3595,7 @@ RTFParserState::RTFParserState(RTFDocumentImpl* pDocumentImpl)
, m_nListLevelNum(0)
, m_bLevelNumbersValid(true)
, m_aFrame(this)
, m_eRunType(RunType::LOCH)
, m_bIsRightToLeft(false)
, m_eRunType(RunType::NONE)
, m_nYear(0)
, m_nMonth(0)
, m_nDay(0)
......
......@@ -401,9 +401,14 @@ public:
/// Maps to OOXML's ascii, cs or eastAsia.
enum class RunType
{
NONE,
LOCH,
HICH,
DBCH
DBCH,
LTRCH_RTLCH_1,
LTRCH_RTLCH_2,
RTLCH_LTRCH_1,
RTLCH_LTRCH_2
};
explicit RTFParserState(RTFDocumentImpl* pDocumentImpl);
......@@ -475,8 +480,6 @@ public:
sal_uInt16 getMonth() const { return m_nMonth; }
void setYear(sal_uInt16 nYear) { m_nYear = nYear; }
sal_uInt16 getYear() const { return m_nYear; }
void setIsRightToLeft(bool bIsRightToLeft) { m_bIsRightToLeft = bIsRightToLeft; }
bool getIsRightToLeft() const { return m_bIsRightToLeft; }
void setRunType(RunType eRunType) { m_eRunType = eRunType; }
RunType getRunType() const { return m_eRunType; }
RTFFrame& getFrame() { return m_aFrame; }
......@@ -578,8 +581,6 @@ private:
RTFFrame m_aFrame;
RunType m_eRunType;
/// ltrch or rtlch
bool m_bIsRightToLeft;
// Info group.
sal_Int16 m_nYear;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment