summaryrefslogtreecommitdiffstats
path: root/svtools/source/misc/sampletext.cxx
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-07 09:06:44 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-07 09:06:44 +0000
commited5640d8b587fbcfed7dd7967f3de04b37a76f26 (patch)
tree7a5f7c6c9d02226d7471cb3cc8fbbf631b415303 /svtools/source/misc/sampletext.cxx
parentInitial commit. (diff)
downloadlibreoffice-upstream/4%7.4.7.tar.xz
libreoffice-upstream/4%7.4.7.zip
Adding upstream version 4:7.4.7.upstream/4%7.4.7upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'svtools/source/misc/sampletext.cxx')
-rw-r--r--svtools/source/misc/sampletext.cxx1672
1 files changed, 1672 insertions, 0 deletions
diff --git a/svtools/source/misc/sampletext.cxx b/svtools/source/misc/sampletext.cxx
new file mode 100644
index 000000000..52351e51d
--- /dev/null
+++ b/svtools/source/misc/sampletext.cxx
@@ -0,0 +1,1672 @@
+/* -*- 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 <svtools/sampletext.hxx>
+#include <vcl/font.hxx>
+#include <vcl/outdev.hxx>
+#include <vcl/virdev.hxx>
+#include <vcl/fontcharmap.hxx>
+#include <i18nutil/unicode.hxx>
+#include <sal/log.hxx>
+#include <com/sun/star/i18n/ScriptType.hpp>
+#include <vector>
+#include <map>
+
+// This should only be used when a commonly used font incorrectly declares its
+// coverage. If you add a font here, please leave a note explaining the issue
+// that caused it to be added
+static UScriptCode lcl_getHardCodedScriptNameForFont (const OutputDevice &rDevice)
+{
+ const OUString &rName = rDevice.GetFont().GetFamilyName();
+
+ if (rName == "GB18030 Bitmap")
+ {
+ // As of OSX 10.9, the system font "GB18030 Bitmap" incorrectly declares
+ // that it only covers "Phoenician" when in fact it's a Chinese font.
+ return USCRIPT_HAN;
+ }
+ else if (rName == "BiauKai")
+ {
+ // "BiauKai" makes crazy claims to cover BUGINESE, SUNDANESE, etc
+ // but in fact it's a Traditional Chinese font.
+ return USCRIPT_TRADITIONAL_HAN;
+ }
+ else if (rName == "GungSeo" || rName == "PCMyungjo" || rName == "PilGi")
+ {
+ // These have no OS/2 tables, but we know they are Korean fonts.
+ return USCRIPT_KOREAN;
+ }
+ else if (rName == "Hei" || rName == "Kai")
+ {
+ // These have no OS/2 tables, but we know they are Chinese fonts.
+ return USCRIPT_HAN;
+ }
+ else if (rName.startsWith("Bangla "))
+ {
+ // "Bangla Sangam MN" claims it supports MALAYALAM, but it doesn't
+ // "Bangla MN" claims just DEVANAGARI and not an additional BENGALI
+ return USCRIPT_BENGALI;
+ }
+ else if (rName.startsWith("Gurmukhi "))
+ {
+ // "Gurmukhi MN" claims it supports TAMIL, but it doesn't
+ return USCRIPT_GURMUKHI;
+ }
+ else if (rName.startsWith("Kannada "))
+ {
+ // "Kannada MN" claims it supports TAMIL, but it doesn't
+ return USCRIPT_KANNADA;
+ }
+ else if (rName.startsWith("Lao "))
+ {
+ // "Lao Sangam MN" claims it supports TAMIL, but it doesn't
+ return USCRIPT_LAO;
+ }
+ else if (rName.startsWith("Malayalam "))
+ {
+ // "Malayalam MN" claims it supports TAMIL, but it doesn't
+ return USCRIPT_MALAYALAM;
+ }
+ else if (rName.startsWith("Sinhala "))
+ {
+ // "Sinhala MN" claims it supports CYRILLIC
+ return USCRIPT_SINHALA;
+ }
+ else if (rName.startsWith("Telugu "))
+ {
+ // "Telugu MN" claims it supports TAMIL, but it doesn't
+ return USCRIPT_TELUGU;
+ }
+ else if (rName.startsWith("Myanmar "))
+ {
+ return USCRIPT_MYANMAR;
+ }
+ else if (rName == "InaiMathi")
+ {
+ // "InaiMathi" claims it supports GOTHIC and CJK_UNIFIED_IDEOGRAPHS as well as
+ // TAMIL, but it doesn't
+ return USCRIPT_TAMIL;
+ }
+ else if (rName == "Hannotate TC" || rName == "HanziPen TC" || rName == "Heiti TC" || rName == "Weibei TC")
+ {
+ // These fonts claim support for ARMENIAN and a bunch of other stuff they don't support
+ return USCRIPT_TRADITIONAL_HAN;
+ }
+ else if (rName == "Hannotate SC" || rName == "HanziPen SC" || rName == "Heiti SC" || rName == "Weibei SC")
+ {
+ // These fonts claim support for ARMENIAN and a bunch of other stuff they don't support
+ return USCRIPT_SIMPLIFIED_HAN;
+ }
+ return USCRIPT_INVALID_CODE;
+}
+
+bool isSymbolFont(const vcl::Font &rFont)
+{
+ return (rFont.GetCharSet() == RTL_TEXTENCODING_SYMBOL) ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Apple Color Emoji") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("cmsy10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("cmex10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("esint10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("feta26") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("jsMath-cmsy10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("jsMath-cmex10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("msam10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("msbm10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("wasy10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Denemo") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("GlyphBasic1") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("GlyphBasic2") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("GlyphBasic3") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("GlyphBasic4") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Letters Laughing") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("MusiQwik") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("MusiSync") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("stmary10") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Symbol") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Webdings") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Wingdings") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Wingdings 2") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Wingdings 3") ||
+ rFont.GetFamilyName().equalsIgnoreAsciiCase("Bookshelf Symbol 7") ||
+ rFont.GetFamilyName().startsWith("STIXIntegrals") ||
+ rFont.GetFamilyName().startsWith("STIXNonUnicode") ||
+ rFont.GetFamilyName().startsWith("STIXSize") ||
+ rFont.GetFamilyName().startsWith("STIXVariants") ||
+ IsStarSymbol(rFont.GetFamilyName());
+}
+
+bool canRenderNameOfSelectedFont(OutputDevice const &rDevice)
+{
+ const vcl::Font &rFont = rDevice.GetFont();
+ return !isSymbolFont(rFont) && ( -1 == rDevice.HasGlyphs(rFont, rFont.GetFamilyName()) );
+}
+
+OUString makeShortRepresentativeSymbolTextForSelectedFont(OutputDevice const &rDevice)
+{
+ if (rDevice.GetFont().GetFamilyName() == "Symbol")
+ {
+ static constexpr OUStringLiteral aImplAppleSymbolText =
+ u"\u03BC\u2202\u2211\u220F\u03C0\u222B\u03A9\u221A";
+ bool bHasSampleTextGlyphs
+ = (-1 == rDevice.HasGlyphs(rDevice.GetFont(), aImplAppleSymbolText));
+ //It's the Apple version
+ if (bHasSampleTextGlyphs)
+ return aImplAppleSymbolText;
+ static constexpr OUStringLiteral aImplAdobeSymbolText =
+ u"\uF06D\uF0B6\uF0E5\uF0D5\uF070\uF0F2\uF057\uF0D6";
+ return aImplAdobeSymbolText;
+ }
+
+ const bool bOpenSymbol = IsStarSymbol(rDevice.GetFont().GetFamilyName());
+
+ if (!bOpenSymbol)
+ {
+ FontCharMapRef xFontCharMap;
+ bool bHasCharMap = rDevice.GetFontCharMap(xFontCharMap);
+ if( bHasCharMap )
+ {
+ // use some sample characters available in the font
+ sal_Unicode aText[8];
+
+ // start just above the PUA used by most symbol fonts
+ sal_uInt32 cNewChar = 0xFF00;
+
+ const int nMaxCount = SAL_N_ELEMENTS(aText) - 1;
+ int nSkip = xFontCharMap->GetCharCount() / nMaxCount;
+ if( nSkip > 10 )
+ nSkip = 10;
+ else if( nSkip <= 0 )
+ nSkip = 1;
+ for( int i = 0; i < nMaxCount; ++i )
+ {
+ sal_uInt32 cOldChar = cNewChar;
+ for( int j = nSkip; --j >= 0; )
+ cNewChar = xFontCharMap->GetPrevChar( cNewChar );
+ if( cOldChar == cNewChar )
+ break;
+ aText[ i ] = static_cast<sal_Unicode>(cNewChar); // TODO: support UCS4 samples
+ aText[ i+1 ] = 0;
+ }
+
+ return OUString(aText);
+ }
+ }
+
+ static const sal_Unicode aImplSymbolFontText[] = {
+ 0xF021,0xF032,0xF043,0xF054,0xF065,0xF076,0xF0B7,0xF0C8,0};
+ static const sal_Unicode aImplStarSymbolText[] = {
+ 0x2702,0x2708,0x270D,0xE033,0x2211,0x2288,0};
+ const sal_Unicode* pText = bOpenSymbol ? aImplStarSymbolText : aImplSymbolFontText;
+ OUString sSampleText(pText);
+ bool bHasSampleTextGlyphs = (-1 == rDevice.HasGlyphs(rDevice.GetFont(), sSampleText));
+ return bHasSampleTextGlyphs ? sSampleText : OUString();
+}
+
+//These ones are typically for use in the font dropdown box beside the
+//fontname, so say things roughly like "Script/Alphabet/Name-Of-Major-Language"
+
+//Here we don't always know the language of course, only the script that can be
+//written with the font. Often that's one single language written in that
+//script, or a handful of related languages where the name of the script is the
+//same between languages, or the name in the major language is known by most
+//readers of the minor languages, e.g. Yiddish is written with the HEBREW
+//script as well, the vast majority of Yiddish readers will be able to read
+//Hebrew as well.
+OUString makeShortRepresentativeTextForScript(UScriptCode eScript)
+{
+ OUString sSampleText;
+ switch (eScript)
+ {
+ case USCRIPT_GREEK:
+ {
+ static constexpr OUStringLiteral aGrek =
+ u"\u0391\u03BB\u03C6\u03AC\u03B2\u03B7\u03C4\u03BF";
+ sSampleText = aGrek;
+ break;
+ }
+ case USCRIPT_HEBREW:
+ {
+ static constexpr OUStringLiteral aHebr =
+ u"\u05D0\u05B8\u05DC\u05B6\u05E3\u05BE\u05D1\u05B5"
+ "\u05BC\u05D9\u05EA \u05E2\u05B4\u05D1\u05B0"
+ "\u05E8\u05B4\u05D9";
+ sSampleText = aHebr;
+ break;
+ }
+ case USCRIPT_ARABIC:
+ {
+ static constexpr OUStringLiteral aArab =
+ u"\u0623\u0628\u062C\u062F\u064A\u0629 \u0639"
+ "\u0631\u0628\u064A\u0629";
+ sSampleText = aArab;
+ break;
+ }
+ case USCRIPT_ARMENIAN:
+ {
+ static constexpr OUStringLiteral aArmenian =
+ u"\u0561\u0575\u0562\u0578\u0582\u0562\u0565"
+ "\u0576";
+ sSampleText = aArmenian;
+ break;
+ }
+ case USCRIPT_DEVANAGARI:
+ {
+ static constexpr OUStringLiteral aDeva =
+ u"\u0926\u0947\u0935\u0928\u093E\u0917\u0930\u0940";
+ sSampleText = aDeva;
+ break;
+ }
+ case USCRIPT_BENGALI:
+ {
+ static constexpr OUStringLiteral aBeng =
+ u"\u09AC\u09BE\u0982\u09B2\u09BE \u09B2\u09BF"
+ "\u09AA\u09BF";
+ sSampleText = aBeng;
+ break;
+ }
+ case USCRIPT_GURMUKHI:
+ {
+ static constexpr OUStringLiteral aGuru =
+ u"\u0A17\u0A41\u0A30\u0A2E\u0A41\u0A16\u0A40";
+ sSampleText = aGuru;
+ break;
+ }
+ case USCRIPT_GUJARATI:
+ {
+ static constexpr OUStringLiteral aGujr =
+ u"\u0A97\u0AC1\u0A9C\u0AB0\u0ABE\u0AA4\u0aC0 "
+ "\u0AB2\u0ABF\u0AAA\u0ABF";
+ sSampleText = aGujr;
+ break;
+ }
+ case USCRIPT_ORIYA:
+ {
+ static constexpr OUStringLiteral aOrya =
+ u"\u0B09\u0B24\u0B4D\u0B15\u0B33 \u0B32\u0B3F"
+ "\u0B2A\u0B3F";
+ sSampleText = aOrya;
+ break;
+ }
+ case USCRIPT_TAMIL:
+ {
+ static constexpr OUStringLiteral aTaml =
+ u"\u0B85\u0BB0\u0BBF\u0B9A\u0BCD\u0B9A\u0BC1\u0BB5"
+ "\u0B9F\u0BBF";
+ sSampleText = aTaml;
+ break;
+ }
+ case USCRIPT_TELUGU:
+ {
+ static constexpr OUStringLiteral aTelu =
+ u"\u0C24\u0C46\u0C32\u0C41\u0C17\u0C41";
+ sSampleText = aTelu;
+ break;
+ }
+ case USCRIPT_KANNADA:
+ {
+ static constexpr OUStringLiteral aKnda =
+ u"\u0C95\u0CA8\u0CCD\u0CA8\u0CA1 \u0CB2\u0CBF"
+ "\u0CAA\u0CBF";
+ sSampleText = aKnda;
+ break;
+ }
+ case USCRIPT_MALAYALAM:
+ {
+ static constexpr OUStringLiteral aMlym =
+ u"\u0D2E\u0D32\u0D2F\u0D3E\u0D33\u0D32\u0D3F\u0D2A"
+ "\u0D3F";
+ sSampleText = aMlym;
+ break;
+ }
+ case USCRIPT_THAI:
+ {
+ static constexpr OUStringLiteral aThai =
+ u"\u0E2D\u0E31\u0E01\u0E29\u0E23\u0E44\u0E17\u0E22";
+ sSampleText = aThai;
+ break;
+ }
+ case USCRIPT_LAO:
+ {
+ static constexpr OUStringLiteral aLao =
+ u"\u0EAD\u0EB1\u0E81\u0EAA\u0EAD\u0E99\u0EA5\u0EB2"
+ "\u0EA7";
+ sSampleText = aLao;
+ break;
+ }
+ case USCRIPT_GEORGIAN:
+ {
+ static constexpr OUStringLiteral aGeorgian =
+ u"\u10D3\u10D0\u10DB\u10EC\u10D4\u10E0\u10DA\u10DD"
+ "\u10D1\u10D0";
+ sSampleText = aGeorgian;
+ break;
+ }
+ case USCRIPT_JAMO:
+ case USCRIPT_HANGUL:
+ case USCRIPT_KOREAN:
+ {
+ static constexpr OUStringLiteral aHang =
+ u"\uD55C\uAE00";
+ sSampleText = aHang;
+ break;
+ }
+ case USCRIPT_TIBETAN:
+ {
+ static constexpr OUStringLiteral aTibt =
+ u"\u0F51\u0F56\u0F74\u0F0B\u0F45\u0F53\u0F0B";
+ sSampleText = aTibt;
+ break;
+ }
+ case USCRIPT_SYRIAC:
+ {
+ static constexpr OUStringLiteral aSyri =
+ u"\u0723\u071B\u072A\u0722\u0713\u0720\u0710";
+ sSampleText = aSyri;
+ break;
+ }
+ case USCRIPT_THAANA:
+ {
+ static constexpr OUStringLiteral aThaa =
+ u"\u078C\u07A7\u0782\u07A6";
+ sSampleText = aThaa;
+ break;
+ }
+ case USCRIPT_SINHALA:
+ {
+ static constexpr OUStringLiteral aSinh =
+ u"\u0DC1\u0DD4\u0DAF\u0DCA\u0DB0 \u0DC3\u0DD2"
+ "\u0D82\u0DC4\u0DBD";
+ sSampleText = aSinh;
+ break;
+ }
+ case USCRIPT_MYANMAR:
+ {
+ static constexpr OUStringLiteral aMymr =
+ u"\u1019\u103C\u1014\u103A\u1019\u102C\u1021\u1000"
+ "\u1039\u1001\u101B\u102C";
+ sSampleText = aMymr;
+ break;
+ }
+ case USCRIPT_ETHIOPIC:
+ {
+ static constexpr OUStringLiteral aEthi =
+ u"\u130D\u12D5\u12DD";
+ sSampleText = aEthi;
+ break;
+ }
+ case USCRIPT_CHEROKEE:
+ {
+ static constexpr OUStringLiteral aCher =
+ u"\u13D7\u13AA\u13EA\u13B6\u13D9\u13D7";
+ sSampleText = aCher;
+ break;
+ }
+ case USCRIPT_KHMER:
+ {
+ static constexpr OUStringLiteral aKhmr =
+ u"\u17A2\u1780\u17D2\u1781\u179A\u1780\u17D2\u179A"
+ "\u1798\u1781\u17C1\u1798\u179A\u1797\u17B6\u179F"
+ "\u17B6";
+ sSampleText = aKhmr;
+ break;
+ }
+ case USCRIPT_MONGOLIAN:
+ {
+ static constexpr OUStringLiteral aMongolian =
+ u"\u182A\u1822\u1834\u1822\u182D\u180C";
+ sSampleText = aMongolian;
+ break;
+ }
+ case USCRIPT_TAGALOG:
+ {
+ static constexpr OUStringLiteral aTagalog =
+ u"\u170A\u170A\u170C\u1712";
+ sSampleText = aTagalog;
+ break;
+ }
+ case USCRIPT_NEW_TAI_LUE:
+ {
+ static constexpr OUStringLiteral aTalu =
+ u"\u1991\u19BA\u199F\u19B9\u19C9";
+ sSampleText = aTalu;
+ break;
+ }
+ case USCRIPT_TRADITIONAL_HAN:
+ {
+ static constexpr OUStringLiteral aHant =
+ u"\u7E41";
+ sSampleText = aHant;
+ break;
+ }
+ case USCRIPT_SIMPLIFIED_HAN:
+ {
+ static constexpr OUStringLiteral aHans =
+ u"\u7B80";
+ sSampleText = aHans;
+ break;
+ }
+ case USCRIPT_HAN:
+ {
+ static constexpr OUStringLiteral aSimplifiedAndTraditionalChinese =
+ u"\u7B80\u7E41";
+ sSampleText = aSimplifiedAndTraditionalChinese;
+ break;
+ }
+ case USCRIPT_JAPANESE:
+ {
+ static constexpr OUStringLiteral aJpan =
+ u"\u65E5\u672C\u8A9E";
+ sSampleText = aJpan;
+ break;
+ }
+ case USCRIPT_YI:
+ {
+ static constexpr OUStringLiteral aYiii =
+ u"\uA188\uA320\uA071\uA0B7";
+ sSampleText = aYiii;
+ break;
+ }
+ case USCRIPT_PHAGS_PA:
+ {
+ static constexpr OUStringLiteral aPhag =
+ u"\uA84F\uA861\uA843 \uA863\uA861\uA859 "
+ u"\uA850\uA85C\uA85E";
+ sSampleText = aPhag;
+ break;
+ }
+ case USCRIPT_TAI_LE:
+ {
+ static constexpr OUStringLiteral aTale =
+ u"\u1956\u196D\u1970\u1956\u196C\u1973\u1951\u1968"
+ "\u1952\u1970";
+ sSampleText = aTale;
+ break;
+ }
+ case USCRIPT_LATIN:
+ sSampleText = "Lorem ipsum";
+ break;
+ default:
+ break;
+ }
+ return sSampleText;
+}
+
+static OUString makeRepresentativeTextForScript(UScriptCode eScript)
+{
+ OUString sSampleText;
+ switch (eScript)
+ {
+ case USCRIPT_TRADITIONAL_HAN:
+ case USCRIPT_SIMPLIFIED_HAN:
+ case USCRIPT_HAN:
+ {
+ //Three Character Classic
+ static constexpr OUStringLiteral aZh =
+ u"\u4EBA\u4E4B\u521D \u6027\u672C\u5584";
+ sSampleText = aZh;
+ break;
+ }
+ case USCRIPT_JAPANESE:
+ {
+ //'Beautiful Japanese'
+ static constexpr OUStringLiteral aJa =
+ u"\u7F8E\u3057\u3044\u65E5\u672C\u8A9E";
+ sSampleText = aJa;
+ break;
+ }
+ case USCRIPT_JAMO:
+ case USCRIPT_KOREAN:
+ case USCRIPT_HANGUL:
+ {
+ //The essential condition for...
+ static constexpr OUStringLiteral aKo =
+ u"\uD0A4\uC2A4\uC758 \uACE0\uC720\uC870"
+ "\uAC74\uC740";
+ sSampleText = aKo;
+ break;
+ }
+ default:
+ break;
+ }
+
+ if (sSampleText.isEmpty())
+ sSampleText = makeShortRepresentativeTextForScript(eScript);
+ return sSampleText;
+}
+
+OUString makeShortMinimalTextForScript(UScriptCode eScript)
+{
+ OUString sSampleText;
+ switch (eScript)
+ {
+ case USCRIPT_GREEK:
+ {
+ static constexpr OUStringLiteral aGrek =
+ u"\u0391\u0392";
+ sSampleText = aGrek;
+ break;
+ }
+ case USCRIPT_HEBREW:
+ {
+ static constexpr OUStringLiteral aHebr =
+ u"\u05D0\u05D1";
+ sSampleText = aHebr;
+ break;
+ }
+ default:
+ break;
+ }
+ return sSampleText;
+}
+
+static OUString makeMinimalTextForScript(UScriptCode eScript)
+{
+ return makeShortMinimalTextForScript(eScript);
+}
+
+//These ones are typically for use in the font preview window in format
+//character
+
+//There we generally know the language. Though it's possible for the language to
+//be "none".
+
+//Currently we fall back to makeShortRepresentativeTextForScript when we don't
+//have suitable strings
+static OUString makeRepresentativeTextForLanguage(LanguageType eLang)
+{
+ OUString sRet;
+ LanguageType pri = primary(eLang);
+ if( pri == primary(LANGUAGE_ARMENIAN) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_ARMENIAN);
+ else if( pri == primary(LANGUAGE_CHINESE) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_HAN);
+ else if( pri == primary(LANGUAGE_GREEK) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_GREEK);
+ else if( pri.anyOf(
+ primary(LANGUAGE_HEBREW),
+ primary(LANGUAGE_YIDDISH)) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_HEBREW);
+ else if( pri == primary(LANGUAGE_ARABIC_SAUDI_ARABIA) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_ARABIC);
+ else if( pri == primary(LANGUAGE_HINDI) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_DEVANAGARI);
+ else if( pri == primary(LANGUAGE_ASSAMESE) )
+ {
+ static constexpr OUStringLiteral aAs =
+ u"\u0985\u09B8\u09AE\u09C0\u09AF\u09BC\u09BE"
+ " \u0986\u0996\u09F0";
+ sRet = aAs;
+ }
+ else if( pri == primary(LANGUAGE_BENGALI) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_BENGALI);
+ else if( pri == primary(LANGUAGE_PUNJABI) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_GURMUKHI);
+ else if( pri == primary(LANGUAGE_GUJARATI) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_GUJARATI);
+ else if( pri == primary(LANGUAGE_ODIA) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_ORIYA);
+ else if( pri == primary(LANGUAGE_TAMIL) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_TAMIL);
+ else if( pri == primary(LANGUAGE_TELUGU) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_TELUGU);
+ else if( pri == primary(LANGUAGE_KANNADA) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_KANNADA);
+ else if( pri == primary(LANGUAGE_MALAYALAM) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_MALAYALAM);
+ else if( pri == primary(LANGUAGE_THAI) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_THAI);
+ else if( pri == primary(LANGUAGE_LAO) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_LAO);
+ else if( pri == primary(LANGUAGE_GEORGIAN) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_GEORGIAN);
+ else if( pri == primary(LANGUAGE_KOREAN) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_KOREAN);
+ else if( pri == primary(LANGUAGE_TIBETAN) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_TIBETAN);
+ else if( pri == primary(LANGUAGE_SYRIAC) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_SYRIAC);
+ else if( pri == primary(LANGUAGE_SINHALESE_SRI_LANKA) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_SINHALA);
+ else if( pri == primary(LANGUAGE_BURMESE) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_MYANMAR);
+ else if( pri == primary(LANGUAGE_AMHARIC_ETHIOPIA) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_ETHIOPIC);
+ else if( pri == primary(LANGUAGE_CHEROKEE_UNITED_STATES) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_CHEROKEE);
+ else if( pri == primary(LANGUAGE_KHMER) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_KHMER);
+ else if( pri == primary(LANGUAGE_MONGOLIAN_MONGOLIAN_LSO) )
+ {
+ if (eLang.anyOf(
+ LANGUAGE_MONGOLIAN_MONGOLIAN_MONGOLIA,
+ LANGUAGE_MONGOLIAN_MONGOLIAN_CHINA,
+ LANGUAGE_MONGOLIAN_MONGOLIAN_LSO))
+ sRet = makeRepresentativeTextForScript(USCRIPT_MONGOLIAN);
+ }
+ else if( pri == primary(LANGUAGE_JAPANESE) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_JAPANESE);
+ else if( pri == primary(LANGUAGE_YI) )
+ sRet = makeRepresentativeTextForScript(USCRIPT_YI);
+ else if( pri == primary(LANGUAGE_GAELIC_IRELAND) )
+ {
+ static constexpr OUStringLiteral aGa =
+ u"T\u00E9acs Samplach";
+ sRet = aGa;
+ }
+
+ return sRet;
+}
+
+namespace
+{
+#if OSL_DEBUG_LEVEL > 0
+ void lcl_dump_unicode_coverage(const std::optional<std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM>> &roIn)
+ {
+ if (!roIn)
+ {
+ SAL_INFO("svtools", "<NOTHING>");
+ return;
+ }
+ auto & rIn(*roIn);
+ if (rIn.none())
+ {
+ SAL_INFO("svtools", "<NONE>");
+ return;
+ }
+ if (rIn[vcl::UnicodeCoverage::BASIC_LATIN])
+ SAL_INFO("svtools", "BASIC_LATIN");
+ if (rIn[vcl::UnicodeCoverage::LATIN_1_SUPPLEMENT])
+ SAL_INFO("svtools", "LATIN_1_SUPPLEMENT");
+ if (rIn[vcl::UnicodeCoverage::LATIN_EXTENDED_A])
+ SAL_INFO("svtools", "LATIN_EXTENDED_A");
+ if (rIn[vcl::UnicodeCoverage::LATIN_EXTENDED_B])
+ SAL_INFO("svtools", "LATIN_EXTENDED_B");
+ if (rIn[vcl::UnicodeCoverage::IPA_EXTENSIONS])
+ SAL_INFO("svtools", "IPA_EXTENSIONS");
+ if (rIn[vcl::UnicodeCoverage::SPACING_MODIFIER_LETTERS])
+ SAL_INFO("svtools", "SPACING_MODIFIER_LETTERS");
+ if (rIn[vcl::UnicodeCoverage::COMBINING_DIACRITICAL_MARKS])
+ SAL_INFO("svtools", "COMBINING_DIACRITICAL_MARKS");
+ if (rIn[vcl::UnicodeCoverage::GREEK_AND_COPTIC])
+ SAL_INFO("svtools", "GREEK_AND_COPTIC");
+ if (rIn[vcl::UnicodeCoverage::COPTIC])
+ SAL_INFO("svtools", "COPTIC");
+ if (rIn[vcl::UnicodeCoverage::CYRILLIC])
+ SAL_INFO("svtools", "CYRILLIC");
+ if (rIn[vcl::UnicodeCoverage::ARMENIAN])
+ SAL_INFO("svtools", "ARMENIAN");
+ if (rIn[vcl::UnicodeCoverage::HEBREW])
+ SAL_INFO("svtools", "HEBREW");
+ if (rIn[vcl::UnicodeCoverage::VAI])
+ SAL_INFO("svtools", "VAI");
+ if (rIn[vcl::UnicodeCoverage::ARABIC])
+ SAL_INFO("svtools", "ARABIC");
+ if (rIn[vcl::UnicodeCoverage::NKO])
+ SAL_INFO("svtools", "NKO");
+ if (rIn[vcl::UnicodeCoverage::DEVANAGARI])
+ SAL_INFO("svtools", "DEVANAGARI");
+ if (rIn[vcl::UnicodeCoverage::BENGALI])
+ SAL_INFO("svtools", "BENGALI");
+ if (rIn[vcl::UnicodeCoverage::GURMUKHI])
+ SAL_INFO("svtools", "GURMUKHI");
+ if (rIn[vcl::UnicodeCoverage::GUJARATI])
+ SAL_INFO("svtools", "GUJARATI");
+ if (rIn[vcl::UnicodeCoverage::ODIA])
+ SAL_INFO("svtools", "ODIA");
+ if (rIn[vcl::UnicodeCoverage::TAMIL])
+ SAL_INFO("svtools", "TAMIL");
+ if (rIn[vcl::UnicodeCoverage::TELUGU])
+ SAL_INFO("svtools", "TELUGU");
+ if (rIn[vcl::UnicodeCoverage::KANNADA])
+ SAL_INFO("svtools", "KANNADA");
+ if (rIn[vcl::UnicodeCoverage::MALAYALAM])
+ SAL_INFO("svtools", "MALAYALAM");
+ if (rIn[vcl::UnicodeCoverage::THAI])
+ SAL_INFO("svtools", "THAI");
+ if (rIn[vcl::UnicodeCoverage::LAO])
+ SAL_INFO("svtools", "LAO");
+ if (rIn[vcl::UnicodeCoverage::GEORGIAN])
+ SAL_INFO("svtools", "GEORGIAN");
+ if (rIn[vcl::UnicodeCoverage::BALINESE])
+ SAL_INFO("svtools", "BALINESE");
+ if (rIn[vcl::UnicodeCoverage::HANGUL_JAMO])
+ SAL_INFO("svtools", "HANGUL_JAMO");
+ if (rIn[vcl::UnicodeCoverage::LATIN_EXTENDED_ADDITIONAL])
+ SAL_INFO("svtools", "LATIN_EXTENDED_ADDITIONAL");
+ if (rIn[vcl::UnicodeCoverage::GREEK_EXTENDED])
+ SAL_INFO("svtools", "GREEK_EXTENDED");
+ if (rIn[vcl::UnicodeCoverage::GENERAL_PUNCTUATION])
+ SAL_INFO("svtools", "GENERAL_PUNCTUATION");
+ if (rIn[vcl::UnicodeCoverage::SUPERSCRIPTS_AND_SUBSCRIPTS])
+ SAL_INFO("svtools", "SUPERSCRIPTS_AND_SUBSCRIPTS");
+ if (rIn[vcl::UnicodeCoverage::CURRENCY_SYMBOLS])
+ SAL_INFO("svtools", "CURRENCY_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::COMBINING_DIACRITICAL_MARKS_FOR_SYMBOLS])
+ SAL_INFO("svtools", "COMBINING_DIACRITICAL_MARKS_FOR_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::LETTERLIKE_SYMBOLS])
+ SAL_INFO("svtools", "LETTERLIKE_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::NUMBER_FORMS])
+ SAL_INFO("svtools", "NUMBER_FORMS");
+ if (rIn[vcl::UnicodeCoverage::ARROWS])
+ SAL_INFO("svtools", "ARROWS");
+ if (rIn[vcl::UnicodeCoverage::MATHEMATICAL_OPERATORS])
+ SAL_INFO("svtools", "MATHEMATICAL_OPERATORS");
+ if (rIn[vcl::UnicodeCoverage::MISCELLANEOUS_TECHNICAL])
+ SAL_INFO("svtools", "MISCELLANEOUS_TECHNICAL");
+ if (rIn[vcl::UnicodeCoverage::CONTROL_PICTURES])
+ SAL_INFO("svtools", "CONTROL_PICTURES");
+ if (rIn[vcl::UnicodeCoverage::OPTICAL_CHARACTER_RECOGNITION])
+ SAL_INFO("svtools", "OPTICAL_CHARACTER_RECOGNITION");
+ if (rIn[vcl::UnicodeCoverage::ENCLOSED_ALPHANUMERICS])
+ SAL_INFO("svtools", "ENCLOSED_ALPHANUMERICS");
+ if (rIn[vcl::UnicodeCoverage::BOX_DRAWING])
+ SAL_INFO("svtools", "BOX_DRAWING");
+ if (rIn[vcl::UnicodeCoverage::BLOCK_ELEMENTS])
+ SAL_INFO("svtools", "BLOCK_ELEMENTS");
+ if (rIn[vcl::UnicodeCoverage::GEOMETRIC_SHAPES])
+ SAL_INFO("svtools", "GEOMETRIC_SHAPES");
+ if (rIn[vcl::UnicodeCoverage::MISCELLANEOUS_SYMBOLS])
+ SAL_INFO("svtools", "MISCELLANEOUS_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::DINGBATS])
+ SAL_INFO("svtools", "DINGBATS");
+ if (rIn[vcl::UnicodeCoverage::CJK_SYMBOLS_AND_PUNCTUATION])
+ SAL_INFO("svtools", "CJK_SYMBOLS_AND_PUNCTUATION");
+ if (rIn[vcl::UnicodeCoverage::HIRAGANA])
+ SAL_INFO("svtools", "HIRAGANA");
+ if (rIn[vcl::UnicodeCoverage::KATAKANA])
+ SAL_INFO("svtools", "KATAKANA");
+ if (rIn[vcl::UnicodeCoverage::BOPOMOFO])
+ SAL_INFO("svtools", "BOPOMOFO");
+ if (rIn[vcl::UnicodeCoverage::HANGUL_COMPATIBILITY_JAMO])
+ SAL_INFO("svtools", "HANGUL_COMPATIBILITY_JAMO");
+ if (rIn[vcl::UnicodeCoverage::PHAGS_PA])
+ SAL_INFO("svtools", "PHAGS_PA");
+ if (rIn[vcl::UnicodeCoverage::ENCLOSED_CJK_LETTERS_AND_MONTHS])
+ SAL_INFO("svtools", "ENCLOSED_CJK_LETTERS_AND_MONTHS");
+ if (rIn[vcl::UnicodeCoverage::CJK_COMPATIBILITY])
+ SAL_INFO("svtools", "CJK_COMPATIBILITY");
+ if (rIn[vcl::UnicodeCoverage::HANGUL_SYLLABLES])
+ SAL_INFO("svtools", "HANGUL_SYLLABLES");
+ if (rIn[vcl::UnicodeCoverage::NONPLANE_0])
+ SAL_INFO("svtools", "NONPLANE_0");
+ if (rIn[vcl::UnicodeCoverage::PHOENICIAN])
+ SAL_INFO("svtools", "PHOENICIAN");
+ if (rIn[vcl::UnicodeCoverage::CJK_UNIFIED_IDEOGRAPHS])
+ SAL_INFO("svtools", "CJK_UNIFIED_IDEOGRAPHS");
+ if (rIn[vcl::UnicodeCoverage::PRIVATE_USE_AREA_PLANE_0])
+ SAL_INFO("svtools", "PRIVATE_USE_AREA_PLANE_0");
+ if (rIn[vcl::UnicodeCoverage::CJK_STROKES])
+ SAL_INFO("svtools", "CJK_STROKES");
+ if (rIn[vcl::UnicodeCoverage::ALPHABETIC_PRESENTATION_FORMS])
+ SAL_INFO("svtools", "ALPHABETIC_PRESENTATION_FORMS");
+ if (rIn[vcl::UnicodeCoverage::ARABIC_PRESENTATION_FORMS_A])
+ SAL_INFO("svtools", "ARABIC_PRESENTATION_FORMS_A");
+ if (rIn[vcl::UnicodeCoverage::COMBINING_HALF_MARKS])
+ SAL_INFO("svtools", "COMBINING_HALF_MARKS");
+ if (rIn[vcl::UnicodeCoverage::VERTICAL_FORMS])
+ SAL_INFO("svtools", "VERTICAL_FORMS");
+ if (rIn[vcl::UnicodeCoverage::SMALL_FORM_VARIANTS])
+ SAL_INFO("svtools", "SMALL_FORM_VARIANTS");
+ if (rIn[vcl::UnicodeCoverage::ARABIC_PRESENTATION_FORMS_B])
+ SAL_INFO("svtools", "ARABIC_PRESENTATION_FORMS_B");
+ if (rIn[vcl::UnicodeCoverage::HALFWIDTH_AND_FULLWIDTH_FORMS])
+ SAL_INFO("svtools", "HALFWIDTH_AND_FULLWIDTH_FORMS");
+ if (rIn[vcl::UnicodeCoverage::SPECIALS])
+ SAL_INFO("svtools", "SPECIALS");
+ if (rIn[vcl::UnicodeCoverage::TIBETAN])
+ SAL_INFO("svtools", "TIBETAN");
+ if (rIn[vcl::UnicodeCoverage::SYRIAC])
+ SAL_INFO("svtools", "SYRIAC");
+ if (rIn[vcl::UnicodeCoverage::THAANA])
+ SAL_INFO("svtools", "THAANA");
+ if (rIn[vcl::UnicodeCoverage::SINHALA])
+ SAL_INFO("svtools", "SINHALA");
+ if (rIn[vcl::UnicodeCoverage::MYANMAR])
+ SAL_INFO("svtools", "MYANMAR");
+ if (rIn[vcl::UnicodeCoverage::ETHIOPIC])
+ SAL_INFO("svtools", "ETHIOPIC");
+ if (rIn[vcl::UnicodeCoverage::CHEROKEE])
+ SAL_INFO("svtools", "CHEROKEE");
+ if (rIn[vcl::UnicodeCoverage::UNIFIED_CANADIAN_ABORIGINAL_SYLLABICS])
+ SAL_INFO("svtools", "UNIFIED_CANADIAN_ABORIGINAL_SYLLABICS");
+ if (rIn[vcl::UnicodeCoverage::OGHAM])
+ SAL_INFO("svtools", "OGHAM");
+ if (rIn[vcl::UnicodeCoverage::RUNIC])
+ SAL_INFO("svtools", "RUNIC");
+ if (rIn[vcl::UnicodeCoverage::KHMER])
+ SAL_INFO("svtools", "KHMER");
+ if (rIn[vcl::UnicodeCoverage::MONGOLIAN])
+ SAL_INFO("svtools", "MONGOLIAN");
+ if (rIn[vcl::UnicodeCoverage::BRAILLE_PATTERNS])
+ SAL_INFO("svtools", "BRAILLE_PATTERNS");
+ if (rIn[vcl::UnicodeCoverage::YI_SYLLABLES])
+ SAL_INFO("svtools", "YI_SYLLABLES");
+ if (rIn[vcl::UnicodeCoverage::TAGALOG])
+ SAL_INFO("svtools", "TAGALOG");
+ if (rIn[vcl::UnicodeCoverage::OLD_ITALIC])
+ SAL_INFO("svtools", "OLD_ITALIC");
+ if (rIn[vcl::UnicodeCoverage::GOTHIC])
+ SAL_INFO("svtools", "GOTHIC");
+ if (rIn[vcl::UnicodeCoverage::DESERET])
+ SAL_INFO("svtools", "DESERET");
+ if (rIn[vcl::UnicodeCoverage::BYZANTINE_MUSICAL_SYMBOLS])
+ SAL_INFO("svtools", "BYZANTINE_MUSICAL_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::MATHEMATICAL_ALPHANUMERIC_SYMBOLS])
+ SAL_INFO("svtools", "MATHEMATICAL_ALPHANUMERIC_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::PRIVATE_USE_PLANE_15])
+ SAL_INFO("svtools", "PRIVATE_USE_PLANE_15");
+ if (rIn[vcl::UnicodeCoverage::VARIATION_SELECTORS])
+ SAL_INFO("svtools", "VARIATION_SELECTORS");
+ if (rIn[vcl::UnicodeCoverage::TAGS])
+ SAL_INFO("svtools", "TAGS");
+ if (rIn[vcl::UnicodeCoverage::LIMBU])
+ SAL_INFO("svtools", "LIMBU");
+ if (rIn[vcl::UnicodeCoverage::TAI_LE])
+ SAL_INFO("svtools", "TAI_LE");
+ if (rIn[vcl::UnicodeCoverage::NEW_TAI_LUE])
+ SAL_INFO("svtools", "NEW_TAI_LUE");
+ if (rIn[vcl::UnicodeCoverage::BUGINESE])
+ SAL_INFO("svtools", "BUGINESE");
+ if (rIn[vcl::UnicodeCoverage::GLAGOLITIC])
+ SAL_INFO("svtools", "GLAGOLITIC");
+ if (rIn[vcl::UnicodeCoverage::TIFINAGH])
+ SAL_INFO("svtools", "TIFINAGH");
+ if (rIn[vcl::UnicodeCoverage::YIJING_HEXAGRAM_SYMBOLS])
+ SAL_INFO("svtools", "YIJING_HEXAGRAM_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::SYLOTI_NAGRI])
+ SAL_INFO("svtools", "SYLOTI_NAGRI");
+ if (rIn[vcl::UnicodeCoverage::LINEAR_B_SYLLABARY])
+ SAL_INFO("svtools", "LINEAR_B_SYLLABARY");
+ if (rIn[vcl::UnicodeCoverage::ANCIENT_GREEK_NUMBERS])
+ SAL_INFO("svtools", "ANCIENT_GREEK_NUMBERS");
+ if (rIn[vcl::UnicodeCoverage::UGARITIC])
+ SAL_INFO("svtools", "UGARITIC");
+ if (rIn[vcl::UnicodeCoverage::OLD_PERSIAN])
+ SAL_INFO("svtools", "OLD_PERSIAN");
+ if (rIn[vcl::UnicodeCoverage::SHAVIAN])
+ SAL_INFO("svtools", "SHAVIAN");
+ if (rIn[vcl::UnicodeCoverage::OSMANYA])
+ SAL_INFO("svtools", "OSMANYA");
+ if (rIn[vcl::UnicodeCoverage::CYPRIOT_SYLLABARY])
+ SAL_INFO("svtools", "CYPRIOT_SYLLABARY");
+ if (rIn[vcl::UnicodeCoverage::KHAROSHTHI])
+ SAL_INFO("svtools", "KHAROSHTHI");
+ if (rIn[vcl::UnicodeCoverage::TAI_XUAN_JING_SYMBOLS])
+ SAL_INFO("svtools", "TAI_XUAN_JING_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::CUNEIFORM])
+ SAL_INFO("svtools", "CUNEIFORM");
+ if (rIn[vcl::UnicodeCoverage::COUNTING_ROD_NUMERALS])
+ SAL_INFO("svtools", "COUNTING_ROD_NUMERALS");
+ if (rIn[vcl::UnicodeCoverage::SUNDANESE])
+ SAL_INFO("svtools", "SUNDANESE");
+ if (rIn[vcl::UnicodeCoverage::LEPCHA])
+ SAL_INFO("svtools", "LEPCHA");
+ if (rIn[vcl::UnicodeCoverage::OL_CHIKI])
+ SAL_INFO("svtools", "OL_CHIKI");
+ if (rIn[vcl::UnicodeCoverage::SAURASHTRA])
+ SAL_INFO("svtools", "SAURASHTRA");
+ if (rIn[vcl::UnicodeCoverage::KAYAH_LI])
+ SAL_INFO("svtools", "KAYAH_LI");
+ if (rIn[vcl::UnicodeCoverage::REJANG])
+ SAL_INFO("svtools", "REJANG");
+ if (rIn[vcl::UnicodeCoverage::CHAM])
+ SAL_INFO("svtools", "CHAM");
+ if (rIn[vcl::UnicodeCoverage::ANCIENT_SYMBOLS])
+ SAL_INFO("svtools", "ANCIENT_SYMBOLS");
+ if (rIn[vcl::UnicodeCoverage::PHAISTOS_DISC])
+ SAL_INFO("svtools", "PHAISTOS_DISC");
+ if (rIn[vcl::UnicodeCoverage::CARIAN])
+ SAL_INFO("svtools", "CARIAN");
+ if (rIn[vcl::UnicodeCoverage::DOMINO_TILES])
+ SAL_INFO("svtools", "DOMINO_TILES");
+ if (rIn[vcl::UnicodeCoverage::RESERVED1])
+ SAL_INFO("svtools", "RESERVED1");
+ if (rIn[vcl::UnicodeCoverage::RESERVED2])
+ SAL_INFO("svtools", "RESERVED2");
+ if (rIn[vcl::UnicodeCoverage::RESERVED3])
+ SAL_INFO("svtools", "RESERVED3");
+ if (rIn[vcl::UnicodeCoverage::RESERVED4])
+ SAL_INFO("svtools", "RESERVED4");
+ if (!(rIn[vcl::UnicodeCoverage::RESERVED5]))
+ return;
+
+ SAL_INFO("svtools", "RESERVED5");
+ }
+
+ void lcl_dump_codepage_coverage(const std::optional<std::bitset<vcl::CodePageCoverage::MAX_CP_ENUM>> &roIn)
+ {
+ if (!roIn)
+ {
+ SAL_INFO("svtools", "<NOTHING>");
+ return;
+ }
+ auto & rIn(*roIn);
+ if (rIn.none())
+ {
+ SAL_INFO("svtools", "<NONE>");
+ return;
+ }
+ if (rIn[vcl::CodePageCoverage::CP1252])
+ SAL_INFO("svtools", "CP1252");
+ if (rIn[vcl::CodePageCoverage::CP1250])
+ SAL_INFO("svtools", "CP1250");
+ if (rIn[vcl::CodePageCoverage::CP1251])
+ SAL_INFO("svtools", "CP1251");
+ if (rIn[vcl::CodePageCoverage::CP1253])
+ SAL_INFO("svtools", "CP1253");
+ if (rIn[vcl::CodePageCoverage::CP1254])
+ SAL_INFO("svtools", "CP1254");
+ if (rIn[vcl::CodePageCoverage::CP1255])
+ SAL_INFO("svtools", "CP1255");
+ if (rIn[vcl::CodePageCoverage::CP1256])
+ SAL_INFO("svtools", "CP1256");
+ if (rIn[vcl::CodePageCoverage::CP1257])
+ SAL_INFO("svtools", "CP1257");
+ if (rIn[vcl::CodePageCoverage::CP1258])
+ SAL_INFO("svtools", "CP1258");
+ if (rIn[vcl::CodePageCoverage::CP874])
+ SAL_INFO("svtools", "CP874");
+ if (rIn[vcl::CodePageCoverage::CP932])
+ SAL_INFO("svtools", "CP932");
+ if (rIn[vcl::CodePageCoverage::CP936])
+ SAL_INFO("svtools", "CP936");
+ if (rIn[vcl::CodePageCoverage::CP949])
+ SAL_INFO("svtools", "CP949");
+ if (rIn[vcl::CodePageCoverage::CP950])
+ SAL_INFO("svtools", "CP950");
+ if (rIn[vcl::CodePageCoverage::CP1361])
+ SAL_INFO("svtools", "CP1361");
+ if (rIn[vcl::CodePageCoverage::CP869])
+ SAL_INFO("svtools", "CP869");
+ if (rIn[vcl::CodePageCoverage::CP866])
+ SAL_INFO("svtools", "CP866");
+ if (rIn[vcl::CodePageCoverage::CP865])
+ SAL_INFO("svtools", "CP865");
+ if (rIn[vcl::CodePageCoverage::CP864])
+ SAL_INFO("svtools", "CP864");
+ if (rIn[vcl::CodePageCoverage::CP863])
+ SAL_INFO("svtools", "CP863");
+ if (rIn[vcl::CodePageCoverage::CP862])
+ SAL_INFO("svtools", "CP862");
+ if (rIn[vcl::CodePageCoverage::CP861])
+ SAL_INFO("svtools", "CP861");
+ if (rIn[vcl::CodePageCoverage::CP860])
+ SAL_INFO("svtools", "CP860");
+ if (rIn[vcl::CodePageCoverage::CP857])
+ SAL_INFO("svtools", "CP857");
+ if (rIn[vcl::CodePageCoverage::CP855])
+ SAL_INFO("svtools", "CP855");
+ if (rIn[vcl::CodePageCoverage::CP852])
+ SAL_INFO("svtools", "CP852");
+ if (rIn[vcl::CodePageCoverage::CP775])
+ SAL_INFO("svtools", "CP775");
+ if (rIn[vcl::CodePageCoverage::CP737])
+ SAL_INFO("svtools", "CP737");
+ if (rIn[vcl::CodePageCoverage::CP780])
+ SAL_INFO("svtools", "CP780");
+ if (rIn[vcl::CodePageCoverage::CP850])
+ SAL_INFO("svtools", "CP850");
+ if (!(rIn[vcl::CodePageCoverage::CP437]))
+ return;
+
+ SAL_INFO("svtools", "CP437");
+ }
+#endif
+
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> getMaskByScriptType(sal_Int16 nScriptType)
+ {
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> aMask;
+ aMask.set();
+
+ for (size_t i = 0; i < vcl::UnicodeCoverage::MAX_UC_ENUM; ++i)
+ {
+ using vcl::UnicodeCoverage::UnicodeCoverageEnum;
+ UScriptCode eScriptCode = otCoverageToScript(static_cast<UnicodeCoverageEnum>(i));
+ if (unicode::getScriptClassFromUScriptCode(eScriptCode) == nScriptType)
+ aMask.set(i, false);
+ }
+
+ return aMask;
+ }
+
+ //false for all bits considered "Latin" by LibreOffice
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> const & getLatinMask()
+ {
+ static std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> s_Mask(getMaskByScriptType(css::i18n::ScriptType::LATIN));
+ return s_Mask;
+ }
+
+ //false for all bits considered "Asian" by LibreOffice
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> const & getCJKMask()
+ {
+ static std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> s_Mask(getMaskByScriptType(css::i18n::ScriptType::ASIAN));
+ return s_Mask;
+ }
+
+ //false for all bits considered "Complex" by LibreOffice
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> const & getCTLMask()
+ {
+ static std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> s_Mask(getMaskByScriptType(css::i18n::ScriptType::COMPLEX));
+ return s_Mask;
+ }
+
+ //false for all bits considered "WEAK" by LibreOffice
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> const & getWeakMask()
+ {
+ static std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> s_Mask(getMaskByScriptType(css::i18n::ScriptType::WEAK));
+ return s_Mask;
+ }
+
+ //Nearly every font supports some basic Latin
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> getCommonLatnSubsetMask()
+ {
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> aMask;
+ aMask.set();
+ aMask.set(vcl::UnicodeCoverage::BASIC_LATIN, false);
+ aMask.set(vcl::UnicodeCoverage::LATIN_1_SUPPLEMENT, false);
+ aMask.set(vcl::UnicodeCoverage::LATIN_EXTENDED_A, false);
+ aMask.set(vcl::UnicodeCoverage::LATIN_EXTENDED_B, false);
+ aMask.set(vcl::UnicodeCoverage::LATIN_EXTENDED_ADDITIONAL, false);
+ return aMask;
+ }
+
+ template<size_t N>
+ size_t find_first(std::bitset<N> const& rSet)
+ {
+ for (size_t i = 0; i < N; ++i)
+ {
+ if (rSet.test(i))
+ return i;
+ }
+ assert(false); // see current usage
+ return N;
+ }
+
+ UScriptCode getScript(const vcl::FontCapabilities &rFontCapabilities)
+ {
+ using vcl::UnicodeCoverage::UnicodeCoverageEnum;
+
+ std::bitset<vcl::UnicodeCoverage::MAX_UC_ENUM> aMasked;
+ if (rFontCapabilities.oUnicodeRange)
+ {
+ aMasked = *rFontCapabilities.oUnicodeRange & getWeakMask();
+ }
+
+ if (aMasked.count() == 1)
+ return otCoverageToScript(static_cast<UnicodeCoverageEnum>(find_first(aMasked)));
+
+ if (aMasked[vcl::UnicodeCoverage::ARABIC])
+ {
+ aMasked.set(vcl::UnicodeCoverage::ARABIC_PRESENTATION_FORMS_A, false);
+ aMasked.set(vcl::UnicodeCoverage::ARABIC_PRESENTATION_FORMS_B, false);
+ aMasked.set(vcl::UnicodeCoverage::NKO, false);
+ //Probably strongly tuned for Arabic
+ if (aMasked.count() == 1)
+ return USCRIPT_ARABIC;
+ if (aMasked.count() == 2 && aMasked[vcl::UnicodeCoverage::SYRIAC])
+ return USCRIPT_SYRIAC;
+ }
+
+ if (aMasked[vcl::UnicodeCoverage::DEVANAGARI])
+ {
+ aMasked.set(vcl::UnicodeCoverage::DEVANAGARI, false);
+ //Probably strongly tuned for a single Indic script
+ if (aMasked.count() == 1)
+ return otCoverageToScript(static_cast<UnicodeCoverageEnum>(find_first(aMasked)));
+ }
+
+ aMasked.set(vcl::UnicodeCoverage::GREEK_EXTENDED, false);
+ aMasked.set(vcl::UnicodeCoverage::GREEK_AND_COPTIC, false);
+ // tdf#88484
+ // Some fonts set the Arabic Presentation Forms-B bit because they
+ // support U+FEFF (Zero Width Space) which happens to be in that block
+ // but it isn’t an Arabic code point. By the time we reach here we
+ // decided this isn’t an Arabic font, so it should be safe.
+ aMasked.set(vcl::UnicodeCoverage::ARABIC_PRESENTATION_FORMS_B, false);
+ if (aMasked.count() == 1)
+ return otCoverageToScript(static_cast<UnicodeCoverageEnum>(find_first(aMasked)));
+
+ if (aMasked[vcl::UnicodeCoverage::CYRILLIC])
+ {
+ //Probably strongly tuned for Georgian
+ if (aMasked.count() == 2 && aMasked[vcl::UnicodeCoverage::GEORGIAN])
+ return USCRIPT_GEORGIAN;
+ }
+
+ aMasked &= getCJKMask();
+
+ aMasked.set(vcl::UnicodeCoverage::CYRILLIC, false);
+ aMasked.set(vcl::UnicodeCoverage::THAI, false);
+ aMasked.set(vcl::UnicodeCoverage::DESERET, false);
+ aMasked.set(vcl::UnicodeCoverage::PHAGS_PA, false);
+
+ //So, possibly a CJK font
+ if (!aMasked.count() && rFontCapabilities.oCodePageRange)
+ {
+ std::bitset<vcl::CodePageCoverage::MAX_CP_ENUM> aCJKCodePageMask;
+ aCJKCodePageMask.set(vcl::CodePageCoverage::CP932);
+ aCJKCodePageMask.set(vcl::CodePageCoverage::CP936);
+ aCJKCodePageMask.set(vcl::CodePageCoverage::CP949);
+ aCJKCodePageMask.set(vcl::CodePageCoverage::CP950);
+ aCJKCodePageMask.set(vcl::CodePageCoverage::CP1361);
+ std::bitset<vcl::CodePageCoverage::MAX_CP_ENUM> aMaskedCodePage =
+ *rFontCapabilities.oCodePageRange & aCJKCodePageMask;
+ //fold Korean
+ if (aMaskedCodePage[vcl::CodePageCoverage::CP1361])
+ {
+ aMaskedCodePage.set(vcl::CodePageCoverage::CP949);
+ aMaskedCodePage.set(vcl::CodePageCoverage::CP1361, false);
+ }
+
+ if (aMaskedCodePage.count() == 1)
+ {
+ if (aMaskedCodePage[vcl::CodePageCoverage::CP932])
+ return USCRIPT_JAPANESE;
+ if (aMaskedCodePage[vcl::CodePageCoverage::CP949])
+ return USCRIPT_KOREAN;
+ if (aMaskedCodePage[vcl::CodePageCoverage::CP936])
+ return USCRIPT_SIMPLIFIED_HAN;
+ if (aMaskedCodePage[vcl::CodePageCoverage::CP950])
+ return USCRIPT_TRADITIONAL_HAN;
+ }
+
+ if (aMaskedCodePage.count())
+ return USCRIPT_HAN;
+ }
+
+ return USCRIPT_COMMON;
+ }
+}
+
+const std::map<UScriptCode, std::vector<OUString>> distCjkMap =
+{
+ { USCRIPT_KOREAN, { " KR", "Korean"} }, // Korean
+ { USCRIPT_JAPANESE, {" JP", "Japanese"} } , // Japanese
+ { USCRIPT_SIMPLIFIED_HAN, {" SC", " GB", "S Chinese"} }, // Simplified Chinese Family
+ { USCRIPT_TRADITIONAL_HAN, {" TC", " HC", " TW", " HK", " MO", "T Chinese"} }// Traditional Chinese Family
+};
+namespace
+{
+ UScriptCode attemptToDisambiguateHan(UScriptCode eScript, OutputDevice const &rDevice)
+ {
+ //If we're a CJK font, see if we seem to be tuned for C, J or K
+ if (eScript == USCRIPT_HAN)
+ {
+ const vcl::Font &rFont = rDevice.GetFont();
+
+ bool bKore = false, bJpan = false, bHant = false, bHans = false;
+
+ static constexpr OUStringLiteral sKorean = u"\u4E6D\u4E76\u596C";
+ if (-1 == rDevice.HasGlyphs(rFont, sKorean))
+ bKore = true;
+
+ static constexpr OUStringLiteral sJapanese = u"\u5968\u67A0\u9D8F";
+ if (-1 == rDevice.HasGlyphs(rFont, sJapanese))
+ bJpan = true;
+
+ static constexpr OUStringLiteral sTraditionalChinese = u"\u555F\u96DE";
+ if (-1 == rDevice.HasGlyphs(rFont, sTraditionalChinese))
+ bHant = true;
+
+ static constexpr OUStringLiteral sSimplifiedChinese = u"\u4E61\u542F\u5956";
+ if (-1 == rDevice.HasGlyphs(rFont, sSimplifiedChinese))
+ bHans = true;
+
+ if (bKore && !bJpan && !bHans && !bHant) {
+ eScript = USCRIPT_KOREAN;
+ return eScript;
+ }
+ else if (bJpan && !bKore && !bHans && !bHant) {
+ eScript = USCRIPT_JAPANESE;
+ return eScript;
+ }
+ else if (bHans && !bHant && !bKore && !bJpan) {
+ eScript = USCRIPT_SIMPLIFIED_HAN;
+ return eScript;
+ }
+ else if (bHant && !bHans && !bKore && !bJpan) {
+ eScript = USCRIPT_TRADITIONAL_HAN;
+ return eScript;
+ }
+
+ // for the last time, Check the ISO code strings or font specific strings
+ const OUString &rName = rDevice.GetFont().GetFamilyName();
+ std::map<UScriptCode, std::vector<OUString>>::const_iterator distCjkMapIt;
+ for (distCjkMapIt = distCjkMap.begin(); distCjkMapIt != distCjkMap.end(); ++distCjkMapIt) {
+ std::vector<OUString> cjkCodeList = distCjkMapIt->second;
+ std::vector<OUString>::const_iterator cjkPtr;
+ for (cjkPtr = cjkCodeList.begin(); cjkPtr != cjkCodeList.end(); ++cjkPtr) {
+ if (rName.indexOf(*cjkPtr) > 0) {
+ return distCjkMapIt->first;
+ }
+ }
+ }
+ //otherwise fall-through as USCRIPT_HAN and expect a combined Hant/Hans preview
+ }
+ return eScript;
+ }
+}
+
+OUString makeShortRepresentativeTextForSelectedFont(OutputDevice const &rDevice)
+{
+ UScriptCode eScript = lcl_getHardCodedScriptNameForFont(rDevice);
+ if (eScript == USCRIPT_INVALID_CODE)
+ {
+ vcl::FontCapabilities aFontCapabilities;
+ if (!rDevice.GetFontCapabilities(aFontCapabilities))
+ return OUString();
+
+#if OSL_DEBUG_LEVEL > 0
+ lcl_dump_unicode_coverage(aFontCapabilities.oUnicodeRange);
+ lcl_dump_codepage_coverage(aFontCapabilities.oCodePageRange);
+#endif
+
+ if (aFontCapabilities.oUnicodeRange)
+ *aFontCapabilities.oUnicodeRange &= getCommonLatnSubsetMask();
+
+ //If this font is probably tuned to display a single non-Latin
+ //script and the font name is itself in Latin, then show a small
+ //chunk of representative text for that script
+ eScript = getScript(aFontCapabilities);
+ if (eScript == USCRIPT_COMMON)
+ return OUString();
+
+ eScript = attemptToDisambiguateHan(eScript, rDevice);
+ }
+
+ OUString sSampleText = makeShortRepresentativeTextForScript(eScript);
+ bool bHasSampleTextGlyphs = (-1 == rDevice.HasGlyphs(rDevice.GetFont(), sSampleText));
+ return bHasSampleTextGlyphs ? sSampleText : OUString();
+}
+
+UScriptCode otCoverageToScript(vcl::UnicodeCoverage::UnicodeCoverageEnum eOTCoverage)
+{
+ UScriptCode eRet = USCRIPT_COMMON;
+ switch (eOTCoverage)
+ {
+ case vcl::UnicodeCoverage::BASIC_LATIN:
+ case vcl::UnicodeCoverage::LATIN_1_SUPPLEMENT:
+ case vcl::UnicodeCoverage::LATIN_EXTENDED_A:
+ case vcl::UnicodeCoverage::LATIN_EXTENDED_B:
+ eRet = USCRIPT_LATIN;
+ break;
+ case vcl::UnicodeCoverage::COMBINING_DIACRITICAL_MARKS:
+ eRet = USCRIPT_INHERITED;
+ break;
+ case vcl::UnicodeCoverage::GREEK_AND_COPTIC:
+ eRet = USCRIPT_GREEK;
+ break;
+ case vcl::UnicodeCoverage::COPTIC:
+ eRet = USCRIPT_COPTIC;
+ break;
+ case vcl::UnicodeCoverage::CYRILLIC:
+ eRet = USCRIPT_CYRILLIC;
+ break;
+ case vcl::UnicodeCoverage::ARMENIAN:
+ eRet = USCRIPT_ARMENIAN;
+ break;
+ case vcl::UnicodeCoverage::HEBREW:
+ eRet = USCRIPT_HEBREW;
+ break;
+ case vcl::UnicodeCoverage::VAI:
+ eRet = USCRIPT_VAI;
+ break;
+ case vcl::UnicodeCoverage::ARABIC:
+ eRet = USCRIPT_ARABIC;
+ break;
+ case vcl::UnicodeCoverage::NKO:
+ eRet = USCRIPT_NKO;
+ break;
+ case vcl::UnicodeCoverage::DEVANAGARI:
+ eRet = USCRIPT_DEVANAGARI;
+ break;
+ case vcl::UnicodeCoverage::BENGALI:
+ eRet = USCRIPT_BENGALI;
+ break;
+ case vcl::UnicodeCoverage::GURMUKHI:
+ eRet = USCRIPT_GURMUKHI;
+ break;
+ case vcl::UnicodeCoverage::GUJARATI:
+ eRet = USCRIPT_GUJARATI;
+ break;
+ case vcl::UnicodeCoverage::ODIA:
+ eRet = USCRIPT_ORIYA;
+ break;
+ case vcl::UnicodeCoverage::TAMIL:
+ eRet = USCRIPT_TAMIL;
+ break;
+ case vcl::UnicodeCoverage::TELUGU:
+ eRet = USCRIPT_TELUGU;
+ break;
+ case vcl::UnicodeCoverage::KANNADA:
+ eRet = USCRIPT_KANNADA;
+ break;
+ case vcl::UnicodeCoverage::MALAYALAM:
+ eRet = USCRIPT_MALAYALAM;
+ break;
+ case vcl::UnicodeCoverage::THAI:
+ eRet = USCRIPT_THAI;
+ break;
+ case vcl::UnicodeCoverage::LAO:
+ eRet = USCRIPT_LAO;
+ break;
+ case vcl::UnicodeCoverage::GEORGIAN:
+ eRet = USCRIPT_GEORGIAN;
+ break;
+ case vcl::UnicodeCoverage::BALINESE:
+ eRet = USCRIPT_BALINESE;
+ break;
+ case vcl::UnicodeCoverage::HANGUL_JAMO:
+ eRet = USCRIPT_HANGUL;
+ break;
+ case vcl::UnicodeCoverage::LATIN_EXTENDED_ADDITIONAL:
+ eRet = USCRIPT_LATIN;
+ break;
+ case vcl::UnicodeCoverage::GREEK_EXTENDED:
+ eRet = USCRIPT_GREEK;
+ break;
+ case vcl::UnicodeCoverage::CURRENCY_SYMBOLS:
+ eRet = USCRIPT_SYMBOLS;
+ break;
+ case vcl::UnicodeCoverage::COMBINING_DIACRITICAL_MARKS_FOR_SYMBOLS:
+ eRet = USCRIPT_INHERITED;
+ break;
+ case vcl::UnicodeCoverage::LETTERLIKE_SYMBOLS:
+ case vcl::UnicodeCoverage::NUMBER_FORMS:
+ case vcl::UnicodeCoverage::ARROWS:
+ eRet = USCRIPT_SYMBOLS;
+ break;
+ case vcl::UnicodeCoverage::MATHEMATICAL_OPERATORS:
+ eRet = USCRIPT_MATHEMATICAL_NOTATION;
+ break;
+ case vcl::UnicodeCoverage::MISCELLANEOUS_TECHNICAL:
+ case vcl::UnicodeCoverage::OPTICAL_CHARACTER_RECOGNITION:
+ case vcl::UnicodeCoverage::BOX_DRAWING:
+ case vcl::UnicodeCoverage::BLOCK_ELEMENTS:
+ case vcl::UnicodeCoverage::GEOMETRIC_SHAPES:
+ case vcl::UnicodeCoverage::MISCELLANEOUS_SYMBOLS:
+ case vcl::UnicodeCoverage::DINGBATS:
+ case vcl::UnicodeCoverage::CJK_SYMBOLS_AND_PUNCTUATION:
+ eRet = USCRIPT_SYMBOLS;
+ break;
+ case vcl::UnicodeCoverage::HIRAGANA:
+ eRet = USCRIPT_HIRAGANA;
+ break;
+ case vcl::UnicodeCoverage::KATAKANA:
+ eRet = USCRIPT_KATAKANA;
+ break;
+ case vcl::UnicodeCoverage::BOPOMOFO:
+ eRet = USCRIPT_BOPOMOFO;
+ break;
+ case vcl::UnicodeCoverage::HANGUL_COMPATIBILITY_JAMO:
+ eRet = USCRIPT_HANGUL;
+ break;
+ case vcl::UnicodeCoverage::PHAGS_PA:
+ eRet = USCRIPT_PHAGS_PA;
+ break;
+ case vcl::UnicodeCoverage::ENCLOSED_CJK_LETTERS_AND_MONTHS:
+ eRet = USCRIPT_HANGUL;
+ break;
+ case vcl::UnicodeCoverage::CJK_COMPATIBILITY:
+ eRet = USCRIPT_HAN;
+ break;
+ case vcl::UnicodeCoverage::HANGUL_SYLLABLES:
+ eRet = USCRIPT_HANGUL;
+ break;
+ case vcl::UnicodeCoverage::PHOENICIAN:
+ eRet = USCRIPT_PHOENICIAN;
+ break;
+ case vcl::UnicodeCoverage::CJK_UNIFIED_IDEOGRAPHS:
+ case vcl::UnicodeCoverage::CJK_STROKES:
+ eRet = USCRIPT_HAN;
+ break;
+ case vcl::UnicodeCoverage::ARABIC_PRESENTATION_FORMS_A:
+ eRet = USCRIPT_ARABIC;
+ break;
+ case vcl::UnicodeCoverage::COMBINING_HALF_MARKS:
+ eRet = USCRIPT_INHERITED;
+ break;
+ case vcl::UnicodeCoverage::ARABIC_PRESENTATION_FORMS_B:
+ eRet = USCRIPT_ARABIC;
+ break;
+ case vcl::UnicodeCoverage::TIBETAN:
+ eRet = USCRIPT_TIBETAN;
+ break;
+ case vcl::UnicodeCoverage::SYRIAC:
+ eRet = USCRIPT_SYRIAC;
+ break;
+ case vcl::UnicodeCoverage::THAANA:
+ eRet = USCRIPT_THAANA;
+ break;
+ case vcl::UnicodeCoverage::SINHALA:
+ eRet = USCRIPT_SINHALA;
+ break;
+ case vcl::UnicodeCoverage::MYANMAR:
+ eRet = USCRIPT_MYANMAR;
+ break;
+ case vcl::UnicodeCoverage::ETHIOPIC:
+ eRet = USCRIPT_ETHIOPIC;
+ break;
+ case vcl::UnicodeCoverage::CHEROKEE:
+ eRet = USCRIPT_CHEROKEE;
+ break;
+ case vcl::UnicodeCoverage::UNIFIED_CANADIAN_ABORIGINAL_SYLLABICS:
+ eRet = USCRIPT_CANADIAN_ABORIGINAL;
+ break;
+ case vcl::UnicodeCoverage::OGHAM:
+ eRet = USCRIPT_OGHAM;
+ break;
+ case vcl::UnicodeCoverage::RUNIC:
+ eRet = USCRIPT_RUNIC;
+ break;
+ case vcl::UnicodeCoverage::KHMER:
+ eRet = USCRIPT_KHMER;
+ break;
+ case vcl::UnicodeCoverage::MONGOLIAN:
+ eRet = USCRIPT_MONGOLIAN;
+ break;
+ case vcl::UnicodeCoverage::BRAILLE_PATTERNS:
+ eRet = USCRIPT_BRAILLE;
+ break;
+ case vcl::UnicodeCoverage::YI_SYLLABLES:
+ eRet = USCRIPT_YI;
+ break;
+ case vcl::UnicodeCoverage::TAGALOG:
+ eRet = USCRIPT_TAGALOG;
+ break;
+ case vcl::UnicodeCoverage::OLD_ITALIC:
+ eRet = USCRIPT_OLD_ITALIC;
+ break;
+ case vcl::UnicodeCoverage::GOTHIC:
+ eRet = USCRIPT_GOTHIC;
+ break;
+ case vcl::UnicodeCoverage::DESERET:
+ eRet = USCRIPT_DESERET;
+ break;
+ case vcl::UnicodeCoverage::BYZANTINE_MUSICAL_SYMBOLS:
+ case vcl::UnicodeCoverage::MATHEMATICAL_ALPHANUMERIC_SYMBOLS:
+ case vcl::UnicodeCoverage::PRIVATE_USE_PLANE_15:
+ eRet = USCRIPT_SYMBOLS;
+ break;
+ case vcl::UnicodeCoverage::VARIATION_SELECTORS:
+ eRet = USCRIPT_INHERITED;
+ break;
+ case vcl::UnicodeCoverage::TAGS:
+ eRet = USCRIPT_SYMBOLS;
+ break;
+ case vcl::UnicodeCoverage::LIMBU:
+ eRet = USCRIPT_LIMBU;
+ break;
+ case vcl::UnicodeCoverage::TAI_LE:
+ eRet = USCRIPT_TAI_LE;
+ break;
+ case vcl::UnicodeCoverage::NEW_TAI_LUE:
+ eRet = USCRIPT_NEW_TAI_LUE;
+ break;
+ case vcl::UnicodeCoverage::BUGINESE:
+ eRet = USCRIPT_BUGINESE;
+ break;
+ case vcl::UnicodeCoverage::GLAGOLITIC:
+ eRet = USCRIPT_GLAGOLITIC;
+ break;
+ case vcl::UnicodeCoverage::TIFINAGH:
+ eRet = USCRIPT_TIFINAGH;
+ break;
+ case vcl::UnicodeCoverage::YIJING_HEXAGRAM_SYMBOLS:
+ eRet = USCRIPT_SYMBOLS;
+ break;
+ case vcl::UnicodeCoverage::SYLOTI_NAGRI:
+ eRet = USCRIPT_SYLOTI_NAGRI;
+ break;
+ case vcl::UnicodeCoverage::LINEAR_B_SYLLABARY:
+ eRet = USCRIPT_LINEAR_B;
+ break;
+ case vcl::UnicodeCoverage::ANCIENT_GREEK_NUMBERS:
+ eRet = USCRIPT_GREEK;
+ break;
+ case vcl::UnicodeCoverage::UGARITIC:
+ eRet = USCRIPT_UGARITIC;
+ break;
+ case vcl::UnicodeCoverage::OLD_PERSIAN:
+ eRet = USCRIPT_OLD_PERSIAN;
+ break;
+ case vcl::UnicodeCoverage::SHAVIAN:
+ eRet = USCRIPT_SHAVIAN;
+ break;
+ case vcl::UnicodeCoverage::OSMANYA:
+ eRet = USCRIPT_OSMANYA;
+ break;
+ case vcl::UnicodeCoverage::CYPRIOT_SYLLABARY:
+ eRet = USCRIPT_CYPRIOT;
+ break;
+ case vcl::UnicodeCoverage::KHAROSHTHI:
+ eRet = USCRIPT_KHAROSHTHI;
+ break;
+ case vcl::UnicodeCoverage::CUNEIFORM:
+ eRet = USCRIPT_CUNEIFORM;
+ break;
+ case vcl::UnicodeCoverage::SUNDANESE:
+ eRet = USCRIPT_SUNDANESE;
+ break;
+ case vcl::UnicodeCoverage::LEPCHA:
+ eRet = USCRIPT_LEPCHA;
+ break;
+ case vcl::UnicodeCoverage::OL_CHIKI:
+ eRet = USCRIPT_OL_CHIKI;
+ break;
+ case vcl::UnicodeCoverage::SAURASHTRA:
+ eRet = USCRIPT_SAURASHTRA;
+ break;
+ case vcl::UnicodeCoverage::KAYAH_LI:
+ eRet = USCRIPT_KAYAH_LI;
+ break;
+ case vcl::UnicodeCoverage::REJANG:
+ eRet = USCRIPT_REJANG;
+ break;
+ case vcl::UnicodeCoverage::CHAM:
+ eRet = USCRIPT_CHAM;
+ break;
+ case vcl::UnicodeCoverage::CARIAN:
+ eRet = USCRIPT_CARIAN;
+ break;
+ case vcl::UnicodeCoverage::DOMINO_TILES:
+ case vcl::UnicodeCoverage::TAI_XUAN_JING_SYMBOLS:
+ case vcl::UnicodeCoverage::COUNTING_ROD_NUMERALS:
+ case vcl::UnicodeCoverage::ANCIENT_SYMBOLS:
+ case vcl::UnicodeCoverage::PHAISTOS_DISC:
+ eRet = USCRIPT_SYMBOLS;
+ break;
+ case vcl::UnicodeCoverage::IPA_EXTENSIONS:
+ case vcl::UnicodeCoverage::SPECIALS:
+ case vcl::UnicodeCoverage::HALFWIDTH_AND_FULLWIDTH_FORMS:
+ case vcl::UnicodeCoverage::VERTICAL_FORMS:
+ case vcl::UnicodeCoverage::SMALL_FORM_VARIANTS:
+ case vcl::UnicodeCoverage::ALPHABETIC_PRESENTATION_FORMS:
+ case vcl::UnicodeCoverage::PRIVATE_USE_AREA_PLANE_0:
+ case vcl::UnicodeCoverage::NONPLANE_0:
+ case vcl::UnicodeCoverage::ENCLOSED_ALPHANUMERICS:
+ case vcl::UnicodeCoverage::CONTROL_PICTURES:
+ case vcl::UnicodeCoverage::SUPERSCRIPTS_AND_SUBSCRIPTS:
+ case vcl::UnicodeCoverage::GENERAL_PUNCTUATION:
+ case vcl::UnicodeCoverage::SPACING_MODIFIER_LETTERS:
+ case vcl::UnicodeCoverage::RESERVED1:
+ case vcl::UnicodeCoverage::RESERVED2:
+ case vcl::UnicodeCoverage::RESERVED3:
+ case vcl::UnicodeCoverage::RESERVED4:
+ case vcl::UnicodeCoverage::RESERVED5:
+ case vcl::UnicodeCoverage::MAX_UC_ENUM:
+ break;
+ }
+ return eRet;
+}
+
+OUString makeRepresentativeTextForFont(sal_Int16 nScriptType, const vcl::Font &rFont)
+{
+ OUString sRet(makeRepresentativeTextForLanguage(rFont.GetLanguage()));
+
+ ScopedVclPtrInstance< VirtualDevice > aDevice;
+ if (sRet.isEmpty() || (-1 != aDevice->HasGlyphs(rFont, sRet)))
+ {
+ aDevice->SetFont(rFont);
+ vcl::FontCapabilities aFontCapabilities;
+ if (aDevice->GetFontCapabilities(aFontCapabilities))
+ {
+#if OSL_DEBUG_LEVEL > 0
+ lcl_dump_unicode_coverage(aFontCapabilities.oUnicodeRange);
+#endif
+
+ if (aFontCapabilities.oUnicodeRange)
+ {
+ *aFontCapabilities.oUnicodeRange &= getWeakMask();
+
+ if (nScriptType != css::i18n::ScriptType::ASIAN)
+ {
+ *aFontCapabilities.oUnicodeRange &= getCJKMask();
+ aFontCapabilities.oCodePageRange.reset();
+ }
+ if (nScriptType != css::i18n::ScriptType::LATIN)
+ *aFontCapabilities.oUnicodeRange &= getLatinMask();
+ if (nScriptType != css::i18n::ScriptType::COMPLEX)
+ *aFontCapabilities.oUnicodeRange &= getCTLMask();
+ }
+
+#if OSL_DEBUG_LEVEL > 0
+ SAL_INFO("svtools", "minimal");
+ lcl_dump_unicode_coverage(aFontCapabilities.oUnicodeRange);
+ lcl_dump_codepage_coverage(aFontCapabilities.oCodePageRange);
+#endif
+
+ UScriptCode eScript = getScript(aFontCapabilities);
+
+ if (nScriptType == css::i18n::ScriptType::ASIAN)
+ eScript = attemptToDisambiguateHan(eScript, *aDevice);
+
+ sRet = makeRepresentativeTextForScript(eScript);
+ }
+
+ if (sRet.isEmpty())
+ {
+ if (nScriptType == css::i18n::ScriptType::COMPLEX)
+ {
+ sRet = makeRepresentativeTextForScript(USCRIPT_HEBREW);
+ if (-1 != aDevice->HasGlyphs(rFont, sRet))
+ {
+ sRet = makeMinimalTextForScript(USCRIPT_HEBREW);
+ if (-1 != aDevice->HasGlyphs(rFont, sRet))
+ sRet = makeRepresentativeTextForScript(USCRIPT_ARABIC);
+ }
+ }
+ else if (nScriptType == css::i18n::ScriptType::LATIN)
+ sRet = makeRepresentativeTextForScript(USCRIPT_LATIN);
+ }
+ }
+
+ return sRet;
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */