--- wmfwr_old.cxx 2007-08-03 12:28:40.000000000 +0000 +++ wmfwr.cxx 2008-03-29 11:07:45.678000000 +0000 @@ -53,6 +53,9 @@ #ifndef _OSL_ENDIAN_H_ #include #endif +#ifndef INCLUDED_I18NUTIL_UNICODE_HXX +# include //unicode::getUnicodeScriptType +#endif #include @@ -166,6 +169,8 @@ #define W_TA_TOP 0x0000 #define W_TA_BOTTOM 0x0008 #define W_TA_BASELINE 0x0018 +#define W_TA_RTLREADING 0x0100 + #define W_SRCCOPY 0x00CC0020L #define W_SRCPAINT 0x00EE0086L @@ -259,6 +264,36 @@ #define PRIVATE_ESCAPE_UNICODE 2 + +/// copied from writerwordglue.cxx + +/* + Utility to categorize unicode characters into the best fit windows charset + range for exporting to ww6, or as a hint to non \u unicode token aware rtf + readers + */ + rtl_TextEncoding getScriptClass(sal_Unicode cChar) + { + using namespace com::sun::star::i18n; + + static ScriptTypeList aScripts[] = + { + { UnicodeScript_kBasicLatin, UnicodeScript_kBasicLatin, RTL_TEXTENCODING_MS_1252}, + { UnicodeScript_kLatin1Supplement, UnicodeScript_kLatin1Supplement, RTL_TEXTENCODING_MS_1252}, + { UnicodeScript_kLatinExtendedA, UnicodeScript_kLatinExtendedA, RTL_TEXTENCODING_MS_1250}, + { UnicodeScript_kLatinExtendedB, UnicodeScript_kLatinExtendedB, RTL_TEXTENCODING_MS_1257}, + { UnicodeScript_kGreek, UnicodeScript_kGreek, RTL_TEXTENCODING_MS_1253}, + { UnicodeScript_kCyrillic, UnicodeScript_kCyrillic, RTL_TEXTENCODING_MS_1251}, + { UnicodeScript_kHebrew, UnicodeScript_kHebrew, RTL_TEXTENCODING_MS_1255}, + { UnicodeScript_kArabic, UnicodeScript_kArabic, RTL_TEXTENCODING_MS_1256}, + { UnicodeScript_kThai, UnicodeScript_kThai, RTL_TEXTENCODING_MS_1258}, + { UnicodeScript_kScriptCount, UnicodeScript_kScriptCount, RTL_TEXTENCODING_MS_1252} + }; + + return unicode::getUnicodeScriptType(cChar, aScripts, + RTL_TEXTENCODING_MS_1252); + } + //========================== Methoden von WMFWriter ========================== void WMFWriter::MayCallback() @@ -578,15 +613,45 @@ sal_Bool WMFWriter::WMFRecord_Escape_Uni if ( aSrcFont.GetCharSet() != RTL_TEXTENCODING_SYMBOL ) // symbol is always byte character, so there is no unicode loss { const sal_Unicode* pBuf = rUniStr.GetBuffer(); - - ByteString aByteStr( rUniStr, aSrcFont.GetCharSet() ); - String aUniStr2( aByteStr, aSrcFont.GetCharSet() ); + const rtl_TextEncoding aTextEncodingOrg = aSrcFont.GetCharSet(); + ByteString aByteStr( rUniStr, aTextEncodingOrg ); + String aUniStr2( aByteStr, aTextEncodingOrg ); const sal_Unicode* pConversion = aUniStr2.GetBuffer(); // this is the unicode array after bytestring <-> unistring conversion for ( i = 0; i < nStringLen; i++ ) { if ( *pBuf++ != *pConversion++ ) break; } + + if ( i != nStringLen ) // after conversion the characters are not original, + { // try again, with determining a better charset from unicode char + const sal_Unicode* pBuf = rUniStr.GetBuffer(); + const sal_Unicode* pCheckChar = pBuf; + rtl_TextEncoding aTextEncoding = getScriptClass (*pCheckChar); // try the first character + for ( i = 1; i < nStringLen; i++) + { + if (aTextEncoding != aTextEncodingOrg) // found something + break; + pCheckChar++; + aTextEncoding = getScriptClass (*pCheckChar); // try the next character + } + + ByteString aByteStr( rUniStr, aTextEncoding ); + String aUniStr2( aByteStr, aTextEncoding ); + const sal_Unicode* pConversion = aUniStr2.GetBuffer(); // this is the unicode array after bytestring <-> unistring conversion + for ( i = 0; i < nStringLen; i++ ) + { + if ( *pBuf++ != *pConversion++ ) + break; + } + if (i == nStringLen) + { + aSrcFont.SetCharSet (aTextEncoding); + SetAllAttr(); + } + + } + if ( ( i != nStringLen ) || IsStarSymbol( aSrcFont.GetName() ) ) // after conversion the characters are not original, so we { // will store the unicode string and a polypoly replacement Color aOldFillColor( aSrcFillColor ); @@ -848,7 +913,7 @@ void WMFWriter::WMFRecord_SetROP2(Raster } -void WMFWriter::WMFRecord_SetTextAlign(FontAlign eFontAlign) +void WMFWriter::WMFRecord_SetTextAlign(FontAlign eFontAlign, UINT32 eHorTextAlign) { USHORT nAlign; @@ -857,7 +922,7 @@ void WMFWriter::WMFRecord_SetTextAlign(F case ALIGN_BOTTOM: nAlign=W_TA_BOTTOM; break; default: nAlign=W_TA_BASELINE; } - nAlign|=W_TA_LEFT; + nAlign|=eHorTextAlign; nAlign|=W_TA_NOUPDATECP; WriteRecordHeader(0x00000004,W_META_SETTEXTALIGN); @@ -1073,10 +1138,11 @@ void WMFWriter::SetAllAttr() aDstTextColor = aSrcTextColor; WMFRecord_SetTextColor(aDstTextColor); } - if ( eDstTextAlign != eSrcTextAlign ) + if ( eDstTextAlign != eSrcTextAlign || eDstHorTextAlign != eSrcHorTextAlign ) { eDstTextAlign = eSrcTextAlign; - WMFRecord_SetTextAlign( eDstTextAlign ); + eDstHorTextAlign = eSrcHorTextAlign; + WMFRecord_SetTextAlign( eDstTextAlign, eDstHorTextAlign ); } if ( aDstFont != aSrcFont ) { @@ -1654,6 +1720,21 @@ void WMFWriter::WriteRecords( const GDIM } break; + case( META_LAYOUTMODE_ACTION ): + { + sal_uInt32 nLayoutMode = ( (MetaLayoutModeAction*) pMA )->GetLayoutMode(); + eSrcHorTextAlign = 0; // TA_LEFT + if (nLayoutMode & TEXT_LAYOUT_BIDI_RTL) + { + eSrcHorTextAlign = W_TA_RIGHT | W_TA_RTLREADING; + } + if (nLayoutMode & TEXT_LAYOUT_TEXTORIGIN_RIGHT) + eSrcHorTextAlign |= W_TA_RIGHT; + else if (nLayoutMode & TEXT_LAYOUT_TEXTORIGIN_LEFT) + eSrcHorTextAlign &= ~W_TA_RIGHT; + break; + } + // Unsupported Actions case META_MASK_ACTION: case META_MASKSCALE_ACTION: @@ -1842,7 +1923,8 @@ BOOL WMFWriter::WriteWMF( const GDIMetaF CreateSelectDeleteFont(aDstFont); eDstTextAlign = eSrcTextAlign = ALIGN_BASELINE; - WMFRecord_SetTextAlign( eDstTextAlign ); + eDstHorTextAlign = eSrcHorTextAlign = W_TA_LEFT; + WMFRecord_SetTextAlign( eDstTextAlign, eDstHorTextAlign ); aDstTextColor = aSrcTextColor = Color( COL_WHITE ); WMFRecord_SetTextColor(aDstTextColor);