1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: transliterationImpl.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_i18npool.hxx"
34 #include "transliterationImpl.hxx"
35 #include "servicename.hxx"
37 #include <com/sun/star/i18n/TransliterationType.hpp>
38 #include <com/sun/star/lang/XComponent.hpp>
39 #include <com/sun/star/container/XContentEnumerationAccess.hpp>
40 #include <com/sun/star/container/XEnumeration.hpp>
41 #include <com/sun/star/lang/XServiceInfo.hpp>
42 #include <com/sun/star/lang/XSingleServiceFactory.hpp>
44 #include <comphelper/processfactory.hxx>
45 #include <rtl/string.h>
46 #include <rtl/ustring.hxx>
47 #include <rtl/ustrbuf.hxx>
49 #if OSL_DEBUG_LEVEL > 1
53 using namespace com::sun::star::uno
;
54 using namespace com::sun::star::lang
;
56 using namespace com::sun::star::container
;
58 namespace com
{ namespace sun
{ namespace star
{ namespace i18n
{
60 #define ERROR RuntimeException()
62 #define TmItem1( name ) \
63 {TransliterationModules_##name, TransliterationModulesNew_##name, #name}
65 #define TmItem2( name ) \
66 {(TransliterationModules)0, TransliterationModulesNew_##name, #name}
69 static struct TMlist
{
70 TransliterationModules tm
;
71 TransliterationModulesNew tmn
;
72 const sal_Char
*implName
;
73 } TMlist
[] = { // Modules ModulesNew
74 TmItem1 (IGNORE_CASE
), // 0. (1<<8 256) (7)
75 TmItem1 (IGNORE_WIDTH
), // 1. (1<<9 512) (8)
76 TmItem1 (IGNORE_KANA
), // 2. (1<<10 1024) (9)
77 // No enum define for this trans. application has to use impl name to load it
78 // TmItem1 (IGNORE_CASE_SIMPLE), // (1<<11 1024) (66)
80 TmItem1 (ignoreTraditionalKanji_ja_JP
), // 3. (1<<12 4096) (10)
81 TmItem1 (ignoreTraditionalKana_ja_JP
), // 4. (1<<13 8192) (11)
82 TmItem1 (ignoreMinusSign_ja_JP
), // 5. (1<<13 16384) (12)
83 TmItem1 (ignoreIterationMark_ja_JP
), // 6. (1<<14 32768) (13)
84 TmItem1 (ignoreSeparator_ja_JP
), // 7. (1<<15 65536) (14)
85 TmItem1 (ignoreSize_ja_JP
), // 15. (1<<23 16777216) (22)
86 TmItem1 (ignoreMiddleDot_ja_JP
), // 17. (1<<25 67108864) (24)
87 TmItem1 (ignoreSpace_ja_JP
), // 18. (1<<26 134217728) (25)
88 TmItem1 (ignoreZiZu_ja_JP
), // 8. (1<<16 131072) (15)
89 TmItem1 (ignoreBaFa_ja_JP
), // 9. (1<<17 262144) (16)
90 TmItem1 (ignoreTiJi_ja_JP
), // 10. (1<<18 524288) (17)
91 TmItem1 (ignoreHyuByu_ja_JP
), // 11. (1<<19 1048576) (18)
92 TmItem1 (ignoreSeZe_ja_JP
), // 12. (1<<20 2097152) (19)
93 TmItem1 (ignoreIandEfollowedByYa_ja_JP
), // 13. (1<<21 4194304) (20)
94 TmItem1 (ignoreKiKuFollowedBySa_ja_JP
), // 14. (1<<22 8388608) (21)
95 TmItem1 (ignoreProlongedSoundMark_ja_JP
), // 16. (1<<24 33554432) (23)
97 TmItem1 (UPPERCASE_LOWERCASE
), // 19. (1) (1)
98 TmItem1 (LOWERCASE_UPPERCASE
), // 20. (2) (2)
99 TmItem1 (HALFWIDTH_FULLWIDTH
), // 21. (3) (3)
100 TmItem1 (FULLWIDTH_HALFWIDTH
), // 22. (4) (4)
101 TmItem1 (KATAKANA_HIRAGANA
), // 23. (5) (5)
102 TmItem1 (HIRAGANA_KATAKANA
), // 24. (6) (6)
104 TmItem1 (smallToLarge_ja_JP
), // 25. (1<<27 268435456) (26)
105 TmItem1 (largeToSmall_ja_JP
), // 26. (1<<28 536870912) (27)
106 TmItem2 (NumToTextLower_zh_CN
), // 27. () (28)
107 TmItem2 (NumToTextUpper_zh_CN
), // 28. () (29)
108 TmItem2 (NumToTextLower_zh_TW
), // 29. () (30)
109 TmItem2 (NumToTextUpper_zh_TW
), // 30. () (31)
110 TmItem2 (NumToTextFormalHangul_ko
), // 31. () (32)
111 TmItem2 (NumToTextFormalLower_ko
), // 32. () (33)
112 TmItem2 (NumToTextFormalUpper_ko
), // 33. () (34)
113 TmItem2 (NumToTextInformalHangul_ko
), // 34. () (35)
114 TmItem2 (NumToTextInformalLower_ko
), // 35. () (36)
115 TmItem2 (NumToTextInformalUpper_ko
), // 36. () (37)
116 TmItem2 (NumToCharLower_zh_CN
), // 37. () (38)
117 TmItem2 (NumToCharUpper_zh_CN
), // 38. () (39)
118 TmItem2 (NumToCharLower_zh_TW
), // 39. () (40)
119 TmItem2 (NumToCharUpper_zh_TW
), // 40. () (41)
120 TmItem2 (NumToCharHangul_ko
), // 41. () (42)
121 TmItem2 (NumToCharLower_ko
), // 42. () (43)
122 TmItem2 (NumToCharUpper_ko
), // 43. () (44)
123 TmItem2 (NumToCharFullwidth
), // 44. () (45)
124 TmItem2 (NumToCharKanjiShort_ja_JP
), // 45. () (46)
125 TmItem2 (TextToNumLower_zh_CN
), // 46. () (47)
126 TmItem2 (TextToNumUpper_zh_CN
), // 47. () (48)
127 TmItem2 (TextToNumLower_zh_TW
), // 48. () (49)
128 TmItem2 (TextToNumUpper_zh_TW
), // 49. () (50)
129 TmItem2 (TextToNumFormalHangul_ko
), // 50. () (51)
130 TmItem2 (TextToNumFormalLower_ko
), // 51. () (52)
131 TmItem2 (TextToNumFormalUpper_ko
), // 52. () (53)
132 TmItem2 (TextToNumInformalHangul_ko
), // 53. () (54)
133 TmItem2 (TextToNumInformalLower_ko
), // 54. () (55)
134 TmItem2 (TextToNumInformalUpper_ko
), // 55. () (56)
136 TmItem2 (CharToNumLower_zh_CN
), // 56. () (59)
137 TmItem2 (CharToNumUpper_zh_CN
), // 57. () (60)
138 TmItem2 (CharToNumLower_zh_TW
), // 58. () (61)
139 TmItem2 (CharToNumUpper_zh_TW
), // 59. () (62)
140 TmItem2 (CharToNumHangul_ko
), // 60. () (63)
141 TmItem2 (CharToNumLower_ko
), // 61. () (64)
142 TmItem2 (CharToNumUpper_ko
), // 62. () (65)
144 // no enum defined for these trans. application has to use impl name to load them
145 // TmItem2 (NumToCharArabic_Indic), // () (67)
146 // TmItem2 (NumToCharEstern_Arabic_Indic),// () (68)
147 // TmItem2 (NumToCharIndic), // () (69)
148 // TmItem2 (NumToCharThai), // () (70)
149 {(TransliterationModules
)0, (TransliterationModulesNew
)0, NULL
}
152 TransliterationImpl::TransBody
TransliterationImpl::lastTransBody
;
154 // Constructor/Destructor
155 TransliterationImpl::TransliterationImpl(const Reference
<XMultiServiceFactory
>& xMSF
) : xSMgr(xMSF
)
158 caseignoreOnly
= sal_True
;
162 Reference
< XInterface
> xI
=
163 xMSF
->createInstance(OUString::createFromAscii("com.sun.star.i18n.LocaleData"));
165 Any x
= xI
->queryInterface( ::getCppuType( (const uno::Reference
< i18n::XLocaleData
>*)0) );
171 TransliterationImpl::~TransliterationImpl()
180 TransliterationImpl::getName() throw(RuntimeException
)
182 if (numCascade
== 1 && bodyCascade
[0].is())
183 return bodyCascade
[0]->getName();
185 return ( OUString::createFromAscii("Not Loaded"));
190 TransliterationImpl::getType() throw(RuntimeException
)
193 return (TransliterationType::CASCADE
|TransliterationType::IGNORE
);
194 if (numCascade
> 0 && bodyCascade
[0].is())
195 return(bodyCascade
[0]->getType());
200 TransliterationImpl::loadModule( TransliterationModules modType
, const Locale
& rLocale
)
201 throw(RuntimeException
)
204 if (modType
&TransliterationModules_IGNORE_MASK
&& modType
&TransliterationModules_NON_IGNORE_MASK
) {
206 } else if (modType
&TransliterationModules_IGNORE_MASK
) {
207 #define TransliterationModules_IGNORE_CASE_MASK (TransliterationModules_IGNORE_CASE | \
208 TransliterationModules_IGNORE_WIDTH | \
209 TransliterationModules_IGNORE_KANA)
210 sal_Int32 mask
= ((modType
&TransliterationModules_IGNORE_CASE_MASK
) == modType
) ?
211 TransliterationModules_IGNORE_CASE_MASK
: TransliterationModules_IGNORE_MASK
;
212 for (sal_Int16 i
= 0; TMlist
[i
].tm
& mask
; i
++) {
213 if (modType
& TMlist
[i
].tm
)
214 if (loadModuleByName(OUString::createFromAscii(TMlist
[i
].implName
),
215 bodyCascade
[numCascade
], rLocale
))
218 } else if (modType
&TransliterationModules_NON_IGNORE_MASK
) {
219 for (sal_Int16 i
= 0; TMlist
[i
].tm
; i
++) {
220 if (TMlist
[i
].tm
== modType
) {
221 if (loadModuleByName(OUString::createFromAscii(TMlist
[i
].implName
), bodyCascade
[numCascade
], rLocale
))
230 TransliterationImpl::loadModuleNew( const Sequence
< TransliterationModulesNew
> & modType
, const Locale
& rLocale
)
231 throw(RuntimeException
)
234 sal_Int32 mask
= 0, count
= modType
.getLength();
235 if (count
> maxCascade
)
236 throw ERROR
; // could not handle more than maxCascade
237 for (sal_Int16 i
= 0; i
< count
; i
++) {
238 for (sal_Int16 j
= 0; TMlist
[j
].tmn
; j
++) {
239 if (TMlist
[j
].tmn
== modType
[i
]) {
241 mask
= TMlist
[i
].tm
&& (TMlist
[i
].tm
&TransliterationModules_IGNORE_MASK
) ?
242 TransliterationModules_IGNORE_MASK
: TransliterationModules_NON_IGNORE_MASK
;
243 else if (mask
== TransliterationModules_IGNORE_MASK
&&
244 (TMlist
[i
].tm
&TransliterationModules_IGNORE_MASK
) == 0)
245 throw ERROR
; // could not mess up ignore trans. with non_ignore trans.
246 if (loadModuleByName(OUString::createFromAscii(TMlist
[j
].implName
), bodyCascade
[numCascade
], rLocale
))
255 TransliterationImpl::loadModuleByImplName(const OUString
& implName
, const Locale
& rLocale
)
256 throw(RuntimeException
)
259 if (loadModuleByName(implName
, bodyCascade
[numCascade
], rLocale
))
265 TransliterationImpl::loadModulesByImplNames(const Sequence
< OUString
>& implNameList
, const Locale
& rLocale
) throw(RuntimeException
)
267 if (implNameList
.getLength() > maxCascade
|| implNameList
.getLength() <= 0)
271 for (sal_Int32 i
= 0; i
< implNameList
.getLength(); i
++)
272 if (loadModuleByName(implNameList
[i
], bodyCascade
[numCascade
], rLocale
))
277 Sequence
<OUString
> SAL_CALL
278 TransliterationImpl::getAvailableModules( const Locale
& rLocale
, sal_Int16 sType
) throw(RuntimeException
)
280 const Sequence
<OUString
> &translist
= localedata
->getTransliterations(rLocale
);
281 Sequence
<OUString
> r(translist
.getLength());
282 Reference
<XExtendedTransliteration
> body
;
284 for (sal_Int32 i
= 0; i
< translist
.getLength(); i
++)
286 if (loadModuleByName(translist
[i
], body
, rLocale
)) {
287 if (body
->getType() & sType
)
288 r
[n
++] = translist
[i
];
298 TransliterationImpl::transliterate( const OUString
& inStr
, sal_Int32 startPos
, sal_Int32 nCount
,
299 Sequence
< sal_Int32
>& offset
) throw(RuntimeException
)
305 if (offset
.getLength() != nCount
)
306 offset
.realloc(nCount
);
309 if ( startPos
== 0 && nCount
== inStr
.getLength() )
310 return bodyCascade
[0]->transliterate( inStr
, 0, nCount
, offset
);
313 OUString tmpStr
= inStr
.copy(startPos
, nCount
);
314 tmpStr
= bodyCascade
[0]->transliterate(tmpStr
, 0, nCount
, offset
);
317 sal_Int32
* pArr
= offset
.getArray();
318 nCount
= offset
.getLength();
319 for (sal_Int32 j
= 0; j
< nCount
; j
++)
327 OUString tmpStr
= inStr
.copy(startPos
, nCount
);
328 sal_Int32
* pArr
= offset
.getArray();
329 for (sal_Int32 j
= 0; j
< nCount
; j
++)
330 pArr
[j
] = startPos
+ j
;
332 sal_Int16 from
= 0, to
= 1, tmp
;
333 Sequence
<sal_Int32
> off
[2];
336 off
[from
].realloc(nCount
);
337 for (sal_Int32 i
= 0; i
< numCascade
; i
++) {
338 tmpStr
= bodyCascade
[i
]->transliterate(tmpStr
, 0, nCount
, off
[from
]);
340 nCount
= tmpStr
.getLength();
342 tmp
= from
; from
= to
; to
= tmp
;
343 for (sal_Int32 j
= 0; j
< nCount
; j
++)
344 off
[to
][j
] = off
[from
][off
[to
][j
]];
354 TransliterationImpl::folding( const OUString
& inStr
, sal_Int32 startPos
, sal_Int32 nCount
,
355 Sequence
< sal_Int32
>& offset
) throw(RuntimeException
)
360 if (offset
.getLength() != nCount
)
361 offset
.realloc(nCount
);
364 if ( startPos
== 0 && nCount
== inStr
.getLength() )
365 return bodyCascade
[0]->folding( inStr
, 0, nCount
, offset
);
368 OUString tmpStr
= inStr
.copy(startPos
, nCount
);
369 tmpStr
= bodyCascade
[0]->folding(tmpStr
, 0, nCount
, offset
);
372 sal_Int32
* pArr
= offset
.getArray();
373 nCount
= offset
.getLength();
374 for (sal_Int32 j
= 0; j
< nCount
; j
++)
382 OUString tmpStr
= inStr
.copy(startPos
, nCount
);
383 sal_Int32
* pArr
= offset
.getArray();
384 for (sal_Int32 j
= 0; j
< nCount
; j
++)
385 pArr
[j
] = startPos
+ j
;
387 sal_Int16 from
= 0, to
= 1, tmp
;
388 Sequence
<sal_Int32
> off
[2];
391 for (sal_Int32 i
= 0; i
< numCascade
; i
++) {
392 tmpStr
= bodyCascade
[i
]->folding(tmpStr
, 0, nCount
, off
[from
]);
394 nCount
= tmpStr
.getLength();
396 tmp
= from
; from
= to
; to
= tmp
;
397 for (sal_Int32 j
= 0; j
< nCount
; j
++)
398 off
[to
][j
] = off
[from
][off
[to
][j
]];
406 TransliterationImpl::transliterateString2String( const OUString
& inStr
, sal_Int32 startPos
, sal_Int32 nCount
) throw(RuntimeException
)
410 else if (numCascade
== 1)
411 return bodyCascade
[0]->transliterateString2String( inStr
, startPos
, nCount
);
413 OUString tmpStr
= bodyCascade
[0]->transliterateString2String(inStr
, startPos
, nCount
);
415 for (sal_Int32 i
= 1; i
< numCascade
; i
++)
416 tmpStr
= bodyCascade
[i
]->transliterateString2String(tmpStr
, 0, tmpStr
.getLength());
422 TransliterationImpl::transliterateChar2String( sal_Unicode inChar
) throw(RuntimeException
)
425 return OUString(&inChar
, 1);
426 else if (numCascade
== 1)
427 return bodyCascade
[0]->transliterateChar2String( inChar
);
429 OUString tmpStr
= bodyCascade
[0]->transliterateChar2String(inChar
);
431 for (sal_Int32 i
= 1; i
< numCascade
; i
++)
432 tmpStr
= bodyCascade
[i
]->transliterateString2String(tmpStr
, 0, tmpStr
.getLength());
438 TransliterationImpl::transliterateChar2Char( sal_Unicode inChar
) throw(MultipleCharsOutputException
, RuntimeException
)
440 sal_Unicode tmpChar
= inChar
;
441 for (sal_Int32 i
= 0; i
< numCascade
; i
++)
442 tmpChar
= bodyCascade
[i
]->transliterateChar2Char(tmpChar
);
448 TransliterationImpl::equals(
449 const OUString
& str1
, sal_Int32 pos1
, sal_Int32 nCount1
, sal_Int32
& nMatch1
,
450 const OUString
& str2
, sal_Int32 pos2
, sal_Int32 nCount2
, sal_Int32
& nMatch2
)
451 throw(RuntimeException
)
453 // since this is an API function make it user fail safe
462 if ( !nCount1
|| !nCount2
||
463 pos1
>= str1
.getLength() || pos2
>= str2
.getLength() ||
464 pos1
< 0 || pos2
< 0 ) {
465 nMatch1
= nMatch2
= 0;
466 // two empty strings return true, else false
467 return !nCount1
&& !nCount2
&& pos1
== str1
.getLength() && pos2
== str2
.getLength();
469 if ( pos1
+ nCount1
> str1
.getLength() )
470 nCount1
= str1
.getLength() - pos1
;
471 if ( pos2
+ nCount2
> str2
.getLength() )
472 nCount2
= str2
.getLength() - pos2
;
474 if (caseignoreOnly
&& caseignore
.is())
475 return caseignore
->equals(str1
, pos1
, nCount1
, nMatch1
, str2
, pos2
, nCount2
, nMatch2
);
477 Sequence
<sal_Int32
> offset1
, offset2
;
479 OUString tmpStr1
= folding(str1
, pos1
, nCount1
, offset1
);
480 OUString tmpStr2
= folding(str2
, pos2
, nCount2
, offset2
);
482 const sal_Unicode
*p1
= tmpStr1
.getStr();
483 const sal_Unicode
*p2
= tmpStr2
.getStr();
484 sal_Int32 i
, nLen
= (tmpStr1
.getLength() < tmpStr1
.getLength() ?
485 tmpStr1
.getLength() : tmpStr2
.getLength());
486 for (i
= 0; i
< nLen
; ++i
, ++p1
, ++p2
) {
488 // return number of matched code points so far
489 nMatch1
= offset1
[i
];
490 nMatch2
= offset2
[i
];
495 if ( tmpStr1
.getLength() != tmpStr2
.getLength() ) {
496 // return number of matched code points so far
497 nMatch1
= offset1
[i
-1] + 1;
498 nMatch2
= offset2
[i
-1] + 1;
509 Sequence
< OUString
> SAL_CALL
510 TransliterationImpl::getRange(const Sequence
< OUString
> &inStrs
,
511 const sal_Int32 length
, sal_Int16 _numCascade
) throw(RuntimeException
)
513 if (_numCascade
>= numCascade
|| ! bodyCascade
[_numCascade
].is())
517 Sequence
< OUString
> ostr(MaxOutput
*length
);
518 for (sal_Int32 j
= 0; j
< length
; j
+=2) {
519 const Sequence
< OUString
>& temp
= bodyCascade
[_numCascade
]->transliterateRange(inStrs
[j
], inStrs
[j
+1]);
521 for ( sal_Int32 k
= 0; k
< temp
.getLength(); k
++) {
522 if ( j_tmp
>= MaxOutput
*length
) throw ERROR
;
523 ostr
[j_tmp
++] = temp
[k
];
528 return this->getRange(ostr
, j_tmp
, ++_numCascade
);
532 Sequence
< OUString
> SAL_CALL
533 TransliterationImpl::transliterateRange( const OUString
& str1
, const OUString
& str2
)
534 throw(RuntimeException
)
537 return bodyCascade
[0]->transliterateRange(str1
, str2
);
539 Sequence
< OUString
> ostr(2);
543 return this->getRange(ostr
, 2, 0);
548 TransliterationImpl::compareSubstring(
549 const OUString
& str1
, sal_Int32 off1
, sal_Int32 len1
,
550 const OUString
& str2
, sal_Int32 off2
, sal_Int32 len2
)
551 throw(RuntimeException
)
553 if (caseignoreOnly
&& caseignore
.is())
554 return caseignore
->compareSubstring(str1
, off1
, len1
, str2
, off2
, len2
);
556 Sequence
<sal_Int32
> offset
;
558 OUString in_str1
= this->transliterate(str1
, off1
, len1
, offset
);
559 OUString in_str2
= this->transliterate(str2
, off2
, len2
, offset
);
560 const sal_Unicode
* unistr1
= in_str1
.getStr();
561 const sal_Unicode
* unistr2
= in_str2
.getStr();
562 sal_Int32 strlen1
= in_str1
.getLength();
563 sal_Int32 strlen2
= in_str2
.getLength();
565 while (strlen1
&& strlen2
) {
566 if (*unistr1
!= *unistr2
)
567 return *unistr1
> *unistr2
? 1 : -1;
569 unistr1
++; unistr2
++; strlen1
--; strlen2
--;
571 return strlen1
== strlen2
? 0 : (strlen1
> strlen2
? 1 : -1);
576 TransliterationImpl::compareString(const OUString
& str1
, const OUString
& str2
) throw (RuntimeException
)
578 if (caseignoreOnly
&& caseignore
.is())
579 return caseignore
->compareString(str1
, str2
);
581 return this->compareSubstring(str1
, 0, str1
.getLength(), str2
, 0, str2
.getLength());
586 TransliterationImpl::clear()
588 for (sal_Int32 i
= 0; i
< numCascade
; i
++)
589 if (bodyCascade
[i
].is())
590 bodyCascade
[i
].clear();
593 caseignoreOnly
= sal_True
;
596 void TransliterationImpl::loadBody( OUString
&implName
, Reference
<XExtendedTransliteration
>& body
)
597 throw (RuntimeException
)
599 ::osl::MutexGuard
guard(lastTransBody
.mutex
);
601 if (implName
.equals(lastTransBody
.Name
))
603 // Use the cached body instead of going through the expensive looping again.
604 body
= lastTransBody
.Body
;
608 Reference
< XContentEnumerationAccess
> xEnumAccess( xSMgr
, UNO_QUERY
);
609 Reference
< XEnumeration
> xEnum(xEnumAccess
->createContentEnumeration(
610 OUString::createFromAscii(TRLT_SERVICELNAME_L10N
)));
612 while (xEnum
->hasMoreElements()) {
613 Any a
= xEnum
->nextElement();
614 Reference
< XServiceInfo
> xsInfo
;
616 if (implName
.equals(xsInfo
->getImplementationName())) {
617 Reference
< XSingleServiceFactory
> xFactory
;
618 if (a
>>= xFactory
) {
619 Reference
< XInterface
> xI
= xFactory
->createInstance();
621 a
= xI
->queryInterface(::getCppuType((
622 const Reference
<XExtendedTransliteration
>*)0));
624 lastTransBody
.Name
= implName
;
625 lastTransBody
.Body
= body
;
637 TransliterationImpl::loadModuleByName( const OUString
& implName
,
638 Reference
<XExtendedTransliteration
>& body
, const Locale
& rLocale
) throw(RuntimeException
)
640 OUString cname
= OUString::createFromAscii(TRLT_IMPLNAME_PREFIX
) + implName
;
641 loadBody(cname
, body
);
643 body
->loadModule((TransliterationModules
)0, rLocale
); // toUpper/toLoad need rLocale
645 // if the module is ignore case/kana/width, load caseignore for equals/compareString mothed
646 for (sal_Int16 i
= 0; i
< 3; i
++) {
647 if (implName
.compareToAscii(TMlist
[i
].implName
) == 0) {
648 if (i
== 0) // current module is caseignore
649 body
->loadModule(TMlist
[0].tm
, rLocale
); // caseingore need to setup module name
650 if (! caseignore
.is()) {
651 OUString bname
= OUString::createFromAscii(TRLT_IMPLNAME_PREFIX
) +
652 OUString::createFromAscii(TMlist
[0].implName
);
653 loadBody(bname
, caseignore
);
656 caseignore
->loadModule(TMlist
[i
].tm
, rLocale
);
660 caseignoreOnly
= sal_False
; // has other module than just ignore case/kana/width
665 const sal_Char cTrans
[] = "com.sun.star.i18n.Transliteration";
668 TransliterationImpl::getImplementationName() throw( RuntimeException
)
670 return OUString::createFromAscii(cTrans
);
675 TransliterationImpl::supportsService(const OUString
& rServiceName
) throw( RuntimeException
)
677 return !rServiceName
.compareToAscii(cTrans
);
680 Sequence
< OUString
> SAL_CALL
681 TransliterationImpl::getSupportedServiceNames(void) throw( RuntimeException
)
683 Sequence
< OUString
> aRet(1);
684 aRet
[0] = OUString::createFromAscii(cTrans
);