1*3b8558fdSAndrew Rist /************************************************************** 2cdf0e10cSrcweir * 3*3b8558fdSAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one 4*3b8558fdSAndrew Rist * or more contributor license agreements. See the NOTICE file 5*3b8558fdSAndrew Rist * distributed with this work for additional information 6*3b8558fdSAndrew Rist * regarding copyright ownership. The ASF licenses this file 7*3b8558fdSAndrew Rist * to you under the Apache License, Version 2.0 (the 8*3b8558fdSAndrew Rist * "License"); you may not use this file except in compliance 9*3b8558fdSAndrew Rist * with the License. You may obtain a copy of the License at 10cdf0e10cSrcweir * 11*3b8558fdSAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0 12cdf0e10cSrcweir * 13*3b8558fdSAndrew Rist * Unless required by applicable law or agreed to in writing, 14*3b8558fdSAndrew Rist * software distributed under the License is distributed on an 15*3b8558fdSAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16*3b8558fdSAndrew Rist * KIND, either express or implied. See the License for the 17*3b8558fdSAndrew Rist * specific language governing permissions and limitations 18*3b8558fdSAndrew Rist * under the License. 19cdf0e10cSrcweir * 20*3b8558fdSAndrew Rist *************************************************************/ 21*3b8558fdSAndrew Rist 22*3b8558fdSAndrew Rist 23cdf0e10cSrcweir 24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove 25cdf0e10cSrcweir #include "precompiled_linguistic.hxx" 26cdf0e10cSrcweir 27cdf0e10cSrcweir #include <tools/fsys.hxx> 28cdf0e10cSrcweir #include <tools/stream.hxx> 29cdf0e10cSrcweir #include <tools/urlobj.hxx> 30cdf0e10cSrcweir #include <unotools/pathoptions.hxx> 31cdf0e10cSrcweir #include <unotools/useroptions.hxx> 32cdf0e10cSrcweir #include <unotools/lingucfg.hxx> 33cdf0e10cSrcweir #include <rtl/instance.hxx> 34cdf0e10cSrcweir #include <cppuhelper/factory.hxx> // helper for factories 35cdf0e10cSrcweir #include <unotools/localfilehelper.hxx> 36cdf0e10cSrcweir #include <com/sun/star/linguistic2/XConversionDictionaryList.hpp> 37cdf0e10cSrcweir #include <com/sun/star/linguistic2/XConversionDictionary.hpp> 38cdf0e10cSrcweir #include <com/sun/star/linguistic2/ConversionDictionaryType.hpp> 39cdf0e10cSrcweir #include <com/sun/star/util/XFlushable.hpp> 40cdf0e10cSrcweir #include <com/sun/star/lang/Locale.hpp> 41cdf0e10cSrcweir #ifndef _COM_SUN_STAR_UNO_REFERENCE_HPP_ 42cdf0e10cSrcweir #include <com/sun/star/uno/Reference.h> 43cdf0e10cSrcweir #endif 44cdf0e10cSrcweir #include <com/sun/star/registry/XRegistryKey.hpp> 45cdf0e10cSrcweir #include <com/sun/star/container/XNameContainer.hpp> 46cdf0e10cSrcweir 47cdf0e10cSrcweir #include <ucbhelper/content.hxx> 48cdf0e10cSrcweir 49cdf0e10cSrcweir #include "convdiclist.hxx" 50cdf0e10cSrcweir #include "convdic.hxx" 51cdf0e10cSrcweir #include "hhconvdic.hxx" 52cdf0e10cSrcweir #include "linguistic/misc.hxx" 53cdf0e10cSrcweir #include "defs.hxx" 54cdf0e10cSrcweir 55cdf0e10cSrcweir //using namespace utl; 56cdf0e10cSrcweir using namespace osl; 57cdf0e10cSrcweir using namespace rtl; 58cdf0e10cSrcweir using namespace com::sun::star; 59cdf0e10cSrcweir using namespace com::sun::star::lang; 60cdf0e10cSrcweir using namespace com::sun::star::uno; 61cdf0e10cSrcweir using namespace com::sun::star::container; 62cdf0e10cSrcweir using namespace com::sun::star::linguistic2; 63cdf0e10cSrcweir using namespace linguistic; 64cdf0e10cSrcweir 65cdf0e10cSrcweir #define SN_CONV_DICTIONARY_LIST "com.sun.star.linguistic2.ConversionDictionaryList" 66cdf0e10cSrcweir 67cdf0e10cSrcweir 68cdf0e10cSrcweir /////////////////////////////////////////////////////////////////////////// 69cdf0e10cSrcweir 70cdf0e10cSrcweir bool operator == ( const Locale &r1, const Locale &r2 ) 71cdf0e10cSrcweir { 72cdf0e10cSrcweir return r1.Language == r2.Language && 73cdf0e10cSrcweir r1.Country == r2.Country && 74cdf0e10cSrcweir r1.Variant == r2.Variant; 75cdf0e10cSrcweir } 76cdf0e10cSrcweir 77cdf0e10cSrcweir /////////////////////////////////////////////////////////////////////////// 78cdf0e10cSrcweir 79cdf0e10cSrcweir String GetConvDicMainURL( const String &rDicName, const String &rDirectoryURL ) 80cdf0e10cSrcweir { 81cdf0e10cSrcweir // build URL to use for new (persistent) dictionaries 82cdf0e10cSrcweir 83cdf0e10cSrcweir String aFullDicName( rDicName ); 84cdf0e10cSrcweir aFullDicName.AppendAscii( CONV_DIC_DOT_EXT ); 85cdf0e10cSrcweir 86cdf0e10cSrcweir INetURLObject aURLObj; 87cdf0e10cSrcweir aURLObj.SetSmartProtocol( INET_PROT_FILE ); 88cdf0e10cSrcweir aURLObj.SetSmartURL( rDirectoryURL ); 89cdf0e10cSrcweir aURLObj.Append( aFullDicName, INetURLObject::ENCODE_ALL ); 90cdf0e10cSrcweir DBG_ASSERT(!aURLObj.HasError(), "invalid URL"); 91cdf0e10cSrcweir if (aURLObj.HasError()) 92cdf0e10cSrcweir return String(); 93cdf0e10cSrcweir else 94cdf0e10cSrcweir return aURLObj.GetMainURL( INetURLObject::DECODE_TO_IURI ); 95cdf0e10cSrcweir } 96cdf0e10cSrcweir 97cdf0e10cSrcweir /////////////////////////////////////////////////////////////////////////// 98cdf0e10cSrcweir 99cdf0e10cSrcweir class ConvDicNameContainer : 100cdf0e10cSrcweir public cppu::WeakImplHelper1 101cdf0e10cSrcweir < 102cdf0e10cSrcweir ::com::sun::star::container::XNameContainer 103cdf0e10cSrcweir > 104cdf0e10cSrcweir { 105cdf0e10cSrcweir uno::Sequence< uno::Reference< XConversionDictionary > > aConvDics; 106cdf0e10cSrcweir ConvDicList &rConvDicList; 107cdf0e10cSrcweir 108cdf0e10cSrcweir // disallow copy-constructor and assignment-operator for now 109cdf0e10cSrcweir ConvDicNameContainer(const ConvDicNameContainer &); 110cdf0e10cSrcweir ConvDicNameContainer & operator = (const ConvDicNameContainer &); 111cdf0e10cSrcweir 112cdf0e10cSrcweir sal_Int32 GetIndexByName_Impl( const OUString& rName ); 113cdf0e10cSrcweir 114cdf0e10cSrcweir public: 115cdf0e10cSrcweir ConvDicNameContainer( ConvDicList &rMyConvDicList ); 116cdf0e10cSrcweir virtual ~ConvDicNameContainer(); 117cdf0e10cSrcweir 118cdf0e10cSrcweir // XElementAccess 119cdf0e10cSrcweir virtual ::com::sun::star::uno::Type SAL_CALL getElementType( ) throw (::com::sun::star::uno::RuntimeException); 120cdf0e10cSrcweir virtual sal_Bool SAL_CALL hasElements( ) throw (::com::sun::star::uno::RuntimeException); 121cdf0e10cSrcweir 122cdf0e10cSrcweir // XNameAccess 123cdf0e10cSrcweir virtual ::com::sun::star::uno::Any SAL_CALL getByName( const ::rtl::OUString& aName ) throw (::com::sun::star::container::NoSuchElementException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException); 124cdf0e10cSrcweir virtual ::com::sun::star::uno::Sequence< ::rtl::OUString > SAL_CALL getElementNames( ) throw (::com::sun::star::uno::RuntimeException); 125cdf0e10cSrcweir virtual sal_Bool SAL_CALL hasByName( const ::rtl::OUString& aName ) throw (::com::sun::star::uno::RuntimeException); 126cdf0e10cSrcweir 127cdf0e10cSrcweir // XNameReplace 128cdf0e10cSrcweir virtual void SAL_CALL replaceByName( const ::rtl::OUString& aName, const ::com::sun::star::uno::Any& aElement ) throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::container::NoSuchElementException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException); 129cdf0e10cSrcweir 130cdf0e10cSrcweir // XNameContainer 131cdf0e10cSrcweir virtual void SAL_CALL insertByName( const ::rtl::OUString& aName, const ::com::sun::star::uno::Any& aElement ) throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::container::ElementExistException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException); 132cdf0e10cSrcweir virtual void SAL_CALL removeByName( const ::rtl::OUString& Name ) throw (::com::sun::star::container::NoSuchElementException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException); 133cdf0e10cSrcweir 134cdf0e10cSrcweir 135cdf0e10cSrcweir // looks for conversion dictionaries with the specified extension 136cdf0e10cSrcweir // in the directory and adds them to the container 137cdf0e10cSrcweir void AddConvDics( const String &rSearchDirPathURL, const String &rExtension ); 138cdf0e10cSrcweir 139cdf0e10cSrcweir // calls Flush for the dictionaries that support XFlushable 140cdf0e10cSrcweir void FlushDics() const; 141cdf0e10cSrcweir 142cdf0e10cSrcweir sal_Int32 GetCount() const { return aConvDics.getLength(); } 143cdf0e10cSrcweir uno::Reference< XConversionDictionary > GetByName( const OUString& rName ); 144cdf0e10cSrcweir 145cdf0e10cSrcweir const uno::Reference< XConversionDictionary > GetByIndex( sal_Int32 nIdx ) 146cdf0e10cSrcweir { 147cdf0e10cSrcweir return aConvDics.getConstArray()[nIdx]; 148cdf0e10cSrcweir } 149cdf0e10cSrcweir }; 150cdf0e10cSrcweir 151cdf0e10cSrcweir 152cdf0e10cSrcweir ConvDicNameContainer::ConvDicNameContainer( ConvDicList &rMyConvDicList ) : 153cdf0e10cSrcweir rConvDicList( rMyConvDicList ) 154cdf0e10cSrcweir { 155cdf0e10cSrcweir } 156cdf0e10cSrcweir 157cdf0e10cSrcweir 158cdf0e10cSrcweir ConvDicNameContainer::~ConvDicNameContainer() 159cdf0e10cSrcweir { 160cdf0e10cSrcweir } 161cdf0e10cSrcweir 162cdf0e10cSrcweir 163cdf0e10cSrcweir void ConvDicNameContainer::FlushDics() const 164cdf0e10cSrcweir { 165cdf0e10cSrcweir sal_Int32 nLen = aConvDics.getLength(); 166cdf0e10cSrcweir const uno::Reference< XConversionDictionary > *pDic = aConvDics.getConstArray(); 167cdf0e10cSrcweir for (sal_Int32 i = 0; i < nLen; ++i) 168cdf0e10cSrcweir { 169cdf0e10cSrcweir uno::Reference< util::XFlushable > xFlush( pDic[i] , UNO_QUERY ); 170cdf0e10cSrcweir if (xFlush.is()) 171cdf0e10cSrcweir { 172cdf0e10cSrcweir try 173cdf0e10cSrcweir { 174cdf0e10cSrcweir xFlush->flush(); 175cdf0e10cSrcweir } 176cdf0e10cSrcweir catch(Exception &) 177cdf0e10cSrcweir { 178cdf0e10cSrcweir DBG_ERROR( "flushing of conversion dictionary failed" ); 179cdf0e10cSrcweir } 180cdf0e10cSrcweir } 181cdf0e10cSrcweir } 182cdf0e10cSrcweir } 183cdf0e10cSrcweir 184cdf0e10cSrcweir 185cdf0e10cSrcweir sal_Int32 ConvDicNameContainer::GetIndexByName_Impl( 186cdf0e10cSrcweir const OUString& rName ) 187cdf0e10cSrcweir { 188cdf0e10cSrcweir sal_Int32 nRes = -1; 189cdf0e10cSrcweir sal_Int32 nLen = aConvDics.getLength(); 190cdf0e10cSrcweir const uno::Reference< XConversionDictionary > *pDic = aConvDics.getConstArray(); 191cdf0e10cSrcweir for (sal_Int32 i = 0; i < nLen && nRes == -1; ++i) 192cdf0e10cSrcweir { 193cdf0e10cSrcweir if (rName == pDic[i]->getName()) 194cdf0e10cSrcweir nRes = i; 195cdf0e10cSrcweir } 196cdf0e10cSrcweir return nRes; 197cdf0e10cSrcweir } 198cdf0e10cSrcweir 199cdf0e10cSrcweir 200cdf0e10cSrcweir uno::Reference< XConversionDictionary > ConvDicNameContainer::GetByName( 201cdf0e10cSrcweir const OUString& rName ) 202cdf0e10cSrcweir { 203cdf0e10cSrcweir uno::Reference< XConversionDictionary > xRes; 204cdf0e10cSrcweir sal_Int32 nIdx = GetIndexByName_Impl( rName ); 205cdf0e10cSrcweir if ( nIdx != -1) 206cdf0e10cSrcweir xRes = aConvDics.getArray()[nIdx]; 207cdf0e10cSrcweir return xRes; 208cdf0e10cSrcweir } 209cdf0e10cSrcweir 210cdf0e10cSrcweir 211cdf0e10cSrcweir uno::Type SAL_CALL ConvDicNameContainer::getElementType( ) 212cdf0e10cSrcweir throw (RuntimeException) 213cdf0e10cSrcweir { 214cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 215cdf0e10cSrcweir return uno::Type( ::getCppuType( (uno::Reference< XConversionDictionary > *) 0) ); 216cdf0e10cSrcweir } 217cdf0e10cSrcweir 218cdf0e10cSrcweir 219cdf0e10cSrcweir sal_Bool SAL_CALL ConvDicNameContainer::hasElements( ) 220cdf0e10cSrcweir throw (RuntimeException) 221cdf0e10cSrcweir { 222cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 223cdf0e10cSrcweir return aConvDics.getLength() > 0; 224cdf0e10cSrcweir } 225cdf0e10cSrcweir 226cdf0e10cSrcweir 227cdf0e10cSrcweir uno::Any SAL_CALL ConvDicNameContainer::getByName( const OUString& rName ) 228cdf0e10cSrcweir throw (NoSuchElementException, WrappedTargetException, RuntimeException) 229cdf0e10cSrcweir { 230cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 231cdf0e10cSrcweir uno::Reference< XConversionDictionary > xRes( GetByName( rName ) ); 232cdf0e10cSrcweir if (!xRes.is()) 233cdf0e10cSrcweir throw NoSuchElementException(); 234cdf0e10cSrcweir return makeAny( xRes ); 235cdf0e10cSrcweir } 236cdf0e10cSrcweir 237cdf0e10cSrcweir 238cdf0e10cSrcweir uno::Sequence< OUString > SAL_CALL ConvDicNameContainer::getElementNames( ) 239cdf0e10cSrcweir throw (RuntimeException) 240cdf0e10cSrcweir { 241cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 242cdf0e10cSrcweir 243cdf0e10cSrcweir sal_Int32 nLen = aConvDics.getLength(); 244cdf0e10cSrcweir uno::Sequence< OUString > aRes( nLen ); 245cdf0e10cSrcweir OUString *pName = aRes.getArray(); 246cdf0e10cSrcweir const uno::Reference< XConversionDictionary > *pDic = aConvDics.getConstArray(); 247cdf0e10cSrcweir for (sal_Int32 i = 0; i < nLen; ++i) 248cdf0e10cSrcweir pName[i] = pDic[i]->getName(); 249cdf0e10cSrcweir return aRes; 250cdf0e10cSrcweir } 251cdf0e10cSrcweir 252cdf0e10cSrcweir 253cdf0e10cSrcweir sal_Bool SAL_CALL ConvDicNameContainer::hasByName( const OUString& rName ) 254cdf0e10cSrcweir throw (RuntimeException) 255cdf0e10cSrcweir { 256cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 257cdf0e10cSrcweir return GetByName( rName ).is(); 258cdf0e10cSrcweir } 259cdf0e10cSrcweir 260cdf0e10cSrcweir 261cdf0e10cSrcweir void SAL_CALL ConvDicNameContainer::replaceByName( 262cdf0e10cSrcweir const OUString& rName, 263cdf0e10cSrcweir const uno::Any& rElement ) 264cdf0e10cSrcweir throw (IllegalArgumentException, NoSuchElementException, WrappedTargetException, RuntimeException) 265cdf0e10cSrcweir { 266cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 267cdf0e10cSrcweir 268cdf0e10cSrcweir sal_Int32 nRplcIdx = GetIndexByName_Impl( rName ); 269cdf0e10cSrcweir if (nRplcIdx == -1) 270cdf0e10cSrcweir throw NoSuchElementException(); 271cdf0e10cSrcweir uno::Reference< XConversionDictionary > xNew; 272cdf0e10cSrcweir rElement >>= xNew; 273cdf0e10cSrcweir if (!xNew.is() || xNew->getName() != rName) 274cdf0e10cSrcweir throw IllegalArgumentException(); 275cdf0e10cSrcweir aConvDics.getArray()[ nRplcIdx ] = xNew; 276cdf0e10cSrcweir } 277cdf0e10cSrcweir 278cdf0e10cSrcweir 279cdf0e10cSrcweir void SAL_CALL ConvDicNameContainer::insertByName( 280cdf0e10cSrcweir const OUString& rName, 281cdf0e10cSrcweir const Any& rElement ) 282cdf0e10cSrcweir throw (IllegalArgumentException, ElementExistException, WrappedTargetException, RuntimeException) 283cdf0e10cSrcweir { 284cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 285cdf0e10cSrcweir 286cdf0e10cSrcweir if (GetByName( rName ).is()) 287cdf0e10cSrcweir throw ElementExistException(); 288cdf0e10cSrcweir uno::Reference< XConversionDictionary > xNew; 289cdf0e10cSrcweir rElement >>= xNew; 290cdf0e10cSrcweir if (!xNew.is() || xNew->getName() != rName) 291cdf0e10cSrcweir throw IllegalArgumentException(); 292cdf0e10cSrcweir 293cdf0e10cSrcweir sal_Int32 nLen = aConvDics.getLength(); 294cdf0e10cSrcweir aConvDics.realloc( nLen + 1 ); 295cdf0e10cSrcweir aConvDics.getArray()[ nLen ] = xNew; 296cdf0e10cSrcweir } 297cdf0e10cSrcweir 298cdf0e10cSrcweir 299cdf0e10cSrcweir void SAL_CALL ConvDicNameContainer::removeByName( const OUString& rName ) 300cdf0e10cSrcweir throw (NoSuchElementException, WrappedTargetException, RuntimeException) 301cdf0e10cSrcweir { 302cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 303cdf0e10cSrcweir 304cdf0e10cSrcweir sal_Int32 nRplcIdx = GetIndexByName_Impl( rName ); 305cdf0e10cSrcweir if (nRplcIdx == -1) 306cdf0e10cSrcweir throw NoSuchElementException(); 307cdf0e10cSrcweir 308cdf0e10cSrcweir // physically remove dictionary 309cdf0e10cSrcweir uno::Reference< XConversionDictionary > xDel = aConvDics.getArray()[nRplcIdx]; 310cdf0e10cSrcweir String aName( xDel->getName() ); 311cdf0e10cSrcweir String aDicMainURL( GetConvDicMainURL( aName, GetDictionaryWriteablePath() ) ); 312cdf0e10cSrcweir INetURLObject aObj( aDicMainURL ); 313cdf0e10cSrcweir DBG_ASSERT( aObj.GetProtocol() == INET_PROT_FILE, "+HangulHanjaOptionsDialog::OkHdl(): non-file URLs cannot be deleted" ); 314cdf0e10cSrcweir if( aObj.GetProtocol() == INET_PROT_FILE ) 315cdf0e10cSrcweir { 316cdf0e10cSrcweir try 317cdf0e10cSrcweir { 318cdf0e10cSrcweir ::ucbhelper::Content aCnt( aObj.GetMainURL( INetURLObject::NO_DECODE ), 319cdf0e10cSrcweir uno::Reference< ::com::sun::star::ucb::XCommandEnvironment > () ); 320cdf0e10cSrcweir aCnt.executeCommand( OUString::createFromAscii( "delete" ), makeAny( sal_Bool( sal_True ) ) ); 321cdf0e10cSrcweir } 322cdf0e10cSrcweir catch( ::com::sun::star::ucb::CommandAbortedException& ) 323cdf0e10cSrcweir { 324cdf0e10cSrcweir DBG_ERRORFILE( "HangulHanjaOptionsDialog::OkHdl(): CommandAbortedException" ); 325cdf0e10cSrcweir } 326cdf0e10cSrcweir catch( ... ) 327cdf0e10cSrcweir { 328cdf0e10cSrcweir DBG_ERRORFILE( "HangulHanjaOptionsDialog::OkHdl(): Any other exception" ); 329cdf0e10cSrcweir } 330cdf0e10cSrcweir } 331cdf0e10cSrcweir 332cdf0e10cSrcweir sal_Int32 nLen = aConvDics.getLength(); 333cdf0e10cSrcweir uno::Reference< XConversionDictionary > *pDic = aConvDics.getArray(); 334cdf0e10cSrcweir for (sal_Int32 i = nRplcIdx; i < nLen - 1; ++i) 335cdf0e10cSrcweir pDic[i] = pDic[i + 1]; 336cdf0e10cSrcweir aConvDics.realloc( nLen - 1 ); 337cdf0e10cSrcweir } 338cdf0e10cSrcweir 339cdf0e10cSrcweir 340cdf0e10cSrcweir void ConvDicNameContainer::AddConvDics( 341cdf0e10cSrcweir const String &rSearchDirPathURL, 342cdf0e10cSrcweir const String &rExtension ) 343cdf0e10cSrcweir { 344cdf0e10cSrcweir const Sequence< OUString > aDirCnt( 345cdf0e10cSrcweir utl::LocalFileHelper::GetFolderContents( rSearchDirPathURL, sal_False ) ); 346cdf0e10cSrcweir const OUString *pDirCnt = aDirCnt.getConstArray(); 347cdf0e10cSrcweir sal_Int32 nEntries = aDirCnt.getLength(); 348cdf0e10cSrcweir 349cdf0e10cSrcweir for (sal_Int32 i = 0; i < nEntries; ++i) 350cdf0e10cSrcweir { 351cdf0e10cSrcweir String aURL( pDirCnt[i] ); 352cdf0e10cSrcweir 353cdf0e10cSrcweir xub_StrLen nPos = aURL.SearchBackward('.'); 354cdf0e10cSrcweir String aExt(aURL.Copy(nPos + 1)); 355cdf0e10cSrcweir aExt.ToLowerAscii(); 356cdf0e10cSrcweir String aSearchExt( rExtension ); 357cdf0e10cSrcweir aSearchExt.ToLowerAscii(); 358cdf0e10cSrcweir if(aExt != aSearchExt) 359cdf0e10cSrcweir continue; // skip other files 360cdf0e10cSrcweir 361cdf0e10cSrcweir sal_Int16 nLang; 362cdf0e10cSrcweir sal_Int16 nConvType; 363cdf0e10cSrcweir if (IsConvDic( aURL, nLang, nConvType )) 364cdf0e10cSrcweir { 365cdf0e10cSrcweir // get decoded dictionary file name 366cdf0e10cSrcweir INetURLObject aURLObj( aURL ); 367cdf0e10cSrcweir String aDicName = aURLObj.getBase( INetURLObject::LAST_SEGMENT, 368cdf0e10cSrcweir true, INetURLObject::DECODE_WITH_CHARSET, 369cdf0e10cSrcweir RTL_TEXTENCODING_UTF8 ); 370cdf0e10cSrcweir 371cdf0e10cSrcweir uno::Reference < XConversionDictionary > xDic; 372cdf0e10cSrcweir if (nLang == LANGUAGE_KOREAN && 373cdf0e10cSrcweir nConvType == ConversionDictionaryType::HANGUL_HANJA) 374cdf0e10cSrcweir { 375cdf0e10cSrcweir xDic = new HHConvDic( aDicName, aURL ); 376cdf0e10cSrcweir } 377cdf0e10cSrcweir else if ((nLang == LANGUAGE_CHINESE_SIMPLIFIED || nLang == LANGUAGE_CHINESE_TRADITIONAL) && 378cdf0e10cSrcweir nConvType == ConversionDictionaryType::SCHINESE_TCHINESE) 379cdf0e10cSrcweir { 380cdf0e10cSrcweir xDic = new ConvDic( aDicName, nLang, nConvType, sal_False, aURL ); 381cdf0e10cSrcweir } 382cdf0e10cSrcweir 383cdf0e10cSrcweir if (xDic.is()) 384cdf0e10cSrcweir { 385cdf0e10cSrcweir uno::Any aAny; 386cdf0e10cSrcweir aAny <<= xDic; 387cdf0e10cSrcweir insertByName( xDic->getName(), aAny ); 388cdf0e10cSrcweir } 389cdf0e10cSrcweir } 390cdf0e10cSrcweir } 391cdf0e10cSrcweir } 392cdf0e10cSrcweir 393cdf0e10cSrcweir /////////////////////////////////////////////////////////////////////////// 394cdf0e10cSrcweir 395cdf0e10cSrcweir namespace 396cdf0e10cSrcweir { 397cdf0e10cSrcweir struct StaticConvDicList : public rtl::StaticWithInit< 398cdf0e10cSrcweir uno::Reference<XInterface>, StaticConvDicList> { 399cdf0e10cSrcweir uno::Reference<XInterface> operator () () { 400cdf0e10cSrcweir return (cppu::OWeakObject *) new ConvDicList; 401cdf0e10cSrcweir } 402cdf0e10cSrcweir }; 403cdf0e10cSrcweir } 404cdf0e10cSrcweir 405cdf0e10cSrcweir 406cdf0e10cSrcweir void ConvDicList::MyAppExitListener::AtExit() 407cdf0e10cSrcweir { 408cdf0e10cSrcweir rMyDicList.FlushDics(); 409cdf0e10cSrcweir StaticConvDicList::get().clear(); 410cdf0e10cSrcweir } 411cdf0e10cSrcweir 412cdf0e10cSrcweir ConvDicList::ConvDicList() : 413cdf0e10cSrcweir aEvtListeners( GetLinguMutex() ) 414cdf0e10cSrcweir { 415cdf0e10cSrcweir pNameContainer = 0; 416cdf0e10cSrcweir bDisposing = sal_False; 417cdf0e10cSrcweir 418cdf0e10cSrcweir pExitListener = new MyAppExitListener( *this ); 419cdf0e10cSrcweir xExitListener = pExitListener; 420cdf0e10cSrcweir pExitListener->Activate(); 421cdf0e10cSrcweir } 422cdf0e10cSrcweir 423cdf0e10cSrcweir 424cdf0e10cSrcweir ConvDicList::~ConvDicList() 425cdf0e10cSrcweir { 426cdf0e10cSrcweir // NameContainer will deleted when the reference xNameContainer 427cdf0e10cSrcweir // is destroyed. 428cdf0e10cSrcweir // delete pNameContainer; 429cdf0e10cSrcweir 430cdf0e10cSrcweir if (!bDisposing && pNameContainer) 431cdf0e10cSrcweir pNameContainer->FlushDics(); 432cdf0e10cSrcweir 433cdf0e10cSrcweir pExitListener->Deactivate(); 434cdf0e10cSrcweir } 435cdf0e10cSrcweir 436cdf0e10cSrcweir 437cdf0e10cSrcweir void ConvDicList::FlushDics() 438cdf0e10cSrcweir { 439cdf0e10cSrcweir // check only pointer to avoid creating the container when 440cdf0e10cSrcweir // the dictionaries were not accessed yet 441cdf0e10cSrcweir if (pNameContainer) 442cdf0e10cSrcweir pNameContainer->FlushDics(); 443cdf0e10cSrcweir } 444cdf0e10cSrcweir 445cdf0e10cSrcweir 446cdf0e10cSrcweir ConvDicNameContainer & ConvDicList::GetNameContainer() 447cdf0e10cSrcweir { 448cdf0e10cSrcweir if (!pNameContainer) 449cdf0e10cSrcweir { 450cdf0e10cSrcweir pNameContainer = new ConvDicNameContainer( *this ); 451cdf0e10cSrcweir pNameContainer->AddConvDics( GetDictionaryWriteablePath(), 452cdf0e10cSrcweir A2OU( CONV_DIC_EXT ) ); 453cdf0e10cSrcweir xNameContainer = pNameContainer; 454cdf0e10cSrcweir 455cdf0e10cSrcweir // access list of text conversion dictionaries to activate 456cdf0e10cSrcweir SvtLinguOptions aOpt; 457cdf0e10cSrcweir SvtLinguConfig().GetOptions( aOpt ); 458cdf0e10cSrcweir sal_Int32 nLen = aOpt.aActiveConvDics.getLength(); 459cdf0e10cSrcweir const OUString *pActiveConvDics = aOpt.aActiveConvDics.getConstArray(); 460cdf0e10cSrcweir for (sal_Int32 i = 0; i < nLen; ++i) 461cdf0e10cSrcweir { 462cdf0e10cSrcweir uno::Reference< XConversionDictionary > xDic = 463cdf0e10cSrcweir pNameContainer->GetByName( pActiveConvDics[i] ); 464cdf0e10cSrcweir if (xDic.is()) 465cdf0e10cSrcweir xDic->setActive( sal_True ); 466cdf0e10cSrcweir } 467cdf0e10cSrcweir 468cdf0e10cSrcweir // since there is no UI to active/deactivate the dictionaries 469cdf0e10cSrcweir // for chinese text conversion they should be activated by default 470cdf0e10cSrcweir uno::Reference< XConversionDictionary > xS2TDic( 471cdf0e10cSrcweir pNameContainer->GetByName( A2OU("ChineseS2T") ), UNO_QUERY ); 472cdf0e10cSrcweir uno::Reference< XConversionDictionary > xT2SDic( 473cdf0e10cSrcweir pNameContainer->GetByName( A2OU("ChineseT2S") ), UNO_QUERY ); 474cdf0e10cSrcweir if (xS2TDic.is()) 475cdf0e10cSrcweir xS2TDic->setActive( sal_True ); 476cdf0e10cSrcweir if (xT2SDic.is()) 477cdf0e10cSrcweir xT2SDic->setActive( sal_True ); 478cdf0e10cSrcweir 479cdf0e10cSrcweir } 480cdf0e10cSrcweir return *pNameContainer; 481cdf0e10cSrcweir } 482cdf0e10cSrcweir 483cdf0e10cSrcweir 484cdf0e10cSrcweir uno::Reference< container::XNameContainer > SAL_CALL ConvDicList::getDictionaryContainer( ) throw (RuntimeException) 485cdf0e10cSrcweir { 486cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 487cdf0e10cSrcweir GetNameContainer(); 488cdf0e10cSrcweir DBG_ASSERT( xNameContainer.is(), "missing name container" ); 489cdf0e10cSrcweir return xNameContainer; 490cdf0e10cSrcweir } 491cdf0e10cSrcweir 492cdf0e10cSrcweir 493cdf0e10cSrcweir uno::Reference< XConversionDictionary > SAL_CALL ConvDicList::addNewDictionary( 494cdf0e10cSrcweir const OUString& rName, 495cdf0e10cSrcweir const Locale& rLocale, 496cdf0e10cSrcweir sal_Int16 nConvDicType ) 497cdf0e10cSrcweir throw (NoSupportException, ElementExistException, RuntimeException) 498cdf0e10cSrcweir { 499cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 500cdf0e10cSrcweir 501cdf0e10cSrcweir sal_Int16 nLang = LocaleToLanguage( rLocale ); 502cdf0e10cSrcweir 503cdf0e10cSrcweir if (GetNameContainer().hasByName( rName )) 504cdf0e10cSrcweir throw ElementExistException(); 505cdf0e10cSrcweir 506cdf0e10cSrcweir uno::Reference< XConversionDictionary > xRes; 507cdf0e10cSrcweir String aDicMainURL( GetConvDicMainURL( rName, GetDictionaryWriteablePath() ) ); 508cdf0e10cSrcweir if (nLang == LANGUAGE_KOREAN && 509cdf0e10cSrcweir nConvDicType == ConversionDictionaryType::HANGUL_HANJA) 510cdf0e10cSrcweir { 511cdf0e10cSrcweir xRes = new HHConvDic( rName, aDicMainURL ); 512cdf0e10cSrcweir } 513cdf0e10cSrcweir else if ((nLang == LANGUAGE_CHINESE_SIMPLIFIED || nLang == LANGUAGE_CHINESE_TRADITIONAL) && 514cdf0e10cSrcweir nConvDicType == ConversionDictionaryType::SCHINESE_TCHINESE) 515cdf0e10cSrcweir { 516cdf0e10cSrcweir xRes = new ConvDic( rName, nLang, nConvDicType, sal_False, aDicMainURL ); 517cdf0e10cSrcweir } 518cdf0e10cSrcweir 519cdf0e10cSrcweir if (!xRes.is()) 520cdf0e10cSrcweir throw NoSupportException(); 521cdf0e10cSrcweir else 522cdf0e10cSrcweir { 523cdf0e10cSrcweir xRes->setActive( sal_True ); 524cdf0e10cSrcweir uno::Any aAny; 525cdf0e10cSrcweir aAny <<= xRes; 526cdf0e10cSrcweir GetNameContainer().insertByName( rName, aAny ); 527cdf0e10cSrcweir } 528cdf0e10cSrcweir return xRes; 529cdf0e10cSrcweir } 530cdf0e10cSrcweir 531cdf0e10cSrcweir 532cdf0e10cSrcweir uno::Sequence< OUString > SAL_CALL ConvDicList::queryConversions( 533cdf0e10cSrcweir const OUString& rText, 534cdf0e10cSrcweir sal_Int32 nStartPos, 535cdf0e10cSrcweir sal_Int32 nLength, 536cdf0e10cSrcweir const Locale& rLocale, 537cdf0e10cSrcweir sal_Int16 nConversionDictionaryType, 538cdf0e10cSrcweir ConversionDirection eDirection, 539cdf0e10cSrcweir sal_Int32 nTextConversionOptions ) 540cdf0e10cSrcweir throw (IllegalArgumentException, NoSupportException, RuntimeException) 541cdf0e10cSrcweir { 542cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 543cdf0e10cSrcweir 544cdf0e10cSrcweir /*sal_Int16 nLang = LocaleToLanguage( rLocale );*/ 545cdf0e10cSrcweir 546cdf0e10cSrcweir sal_Int32 nCount = 0; 547cdf0e10cSrcweir uno::Sequence< OUString > aRes( 20 ); 548cdf0e10cSrcweir OUString *pRes = aRes.getArray(); 549cdf0e10cSrcweir 550cdf0e10cSrcweir sal_Bool bSupported = sal_False; 551cdf0e10cSrcweir sal_Int32 nLen = GetNameContainer().GetCount(); 552cdf0e10cSrcweir for (sal_Int32 i = 0; i < nLen; ++i) 553cdf0e10cSrcweir { 554cdf0e10cSrcweir const uno::Reference< XConversionDictionary > xDic( GetNameContainer().GetByIndex(i) ); 555cdf0e10cSrcweir sal_Bool bMatch = xDic.is() && 556cdf0e10cSrcweir xDic->getLocale() == rLocale && 557cdf0e10cSrcweir xDic->getConversionType() == nConversionDictionaryType; 558cdf0e10cSrcweir bSupported |= bMatch; 559cdf0e10cSrcweir if (bMatch && xDic->isActive()) 560cdf0e10cSrcweir { 561cdf0e10cSrcweir Sequence< OUString > aNewConv( xDic->getConversions( 562cdf0e10cSrcweir rText, nStartPos, nLength, 563cdf0e10cSrcweir eDirection, nTextConversionOptions ) ); 564cdf0e10cSrcweir sal_Int32 nNewLen = aNewConv.getLength(); 565cdf0e10cSrcweir if (nNewLen > 0) 566cdf0e10cSrcweir { 567cdf0e10cSrcweir if (nCount + nNewLen > aRes.getLength()) 568cdf0e10cSrcweir { 569cdf0e10cSrcweir aRes.realloc( nCount + nNewLen + 20 ); 570cdf0e10cSrcweir pRes = aRes.getArray(); 571cdf0e10cSrcweir } 572cdf0e10cSrcweir const OUString *pNewConv = aNewConv.getConstArray(); 573cdf0e10cSrcweir for (sal_Int32 k = 0; k < nNewLen; ++k) 574cdf0e10cSrcweir pRes[nCount++] = pNewConv[k]; 575cdf0e10cSrcweir } 576cdf0e10cSrcweir } 577cdf0e10cSrcweir } 578cdf0e10cSrcweir 579cdf0e10cSrcweir if (!bSupported) 580cdf0e10cSrcweir throw NoSupportException(); 581cdf0e10cSrcweir 582cdf0e10cSrcweir aRes.realloc( nCount ); 583cdf0e10cSrcweir return aRes; 584cdf0e10cSrcweir } 585cdf0e10cSrcweir 586cdf0e10cSrcweir 587cdf0e10cSrcweir sal_Int16 SAL_CALL ConvDicList::queryMaxCharCount( 588cdf0e10cSrcweir const Locale& rLocale, 589cdf0e10cSrcweir sal_Int16 nConversionDictionaryType, 590cdf0e10cSrcweir ConversionDirection eDirection ) 591cdf0e10cSrcweir throw (RuntimeException) 592cdf0e10cSrcweir { 593cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 594cdf0e10cSrcweir 595cdf0e10cSrcweir sal_Int16 nRes = 0; 596cdf0e10cSrcweir GetNameContainer(); 597cdf0e10cSrcweir sal_Int32 nLen = GetNameContainer().GetCount(); 598cdf0e10cSrcweir for (sal_Int32 i = 0; i < nLen; ++i) 599cdf0e10cSrcweir { 600cdf0e10cSrcweir const uno::Reference< XConversionDictionary > xDic( GetNameContainer().GetByIndex(i) ); 601cdf0e10cSrcweir if (xDic.is() && 602cdf0e10cSrcweir xDic->getLocale() == rLocale && 603cdf0e10cSrcweir xDic->getConversionType() == nConversionDictionaryType) 604cdf0e10cSrcweir { 605cdf0e10cSrcweir sal_Int16 nC = xDic->getMaxCharCount( eDirection ); 606cdf0e10cSrcweir if (nC > nRes) 607cdf0e10cSrcweir nRes = nC; 608cdf0e10cSrcweir } 609cdf0e10cSrcweir } 610cdf0e10cSrcweir return nRes; 611cdf0e10cSrcweir } 612cdf0e10cSrcweir 613cdf0e10cSrcweir 614cdf0e10cSrcweir void SAL_CALL ConvDicList::dispose( ) 615cdf0e10cSrcweir throw (RuntimeException) 616cdf0e10cSrcweir { 617cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 618cdf0e10cSrcweir if (!bDisposing) 619cdf0e10cSrcweir { 620cdf0e10cSrcweir bDisposing = sal_True; 621cdf0e10cSrcweir EventObject aEvtObj( (XConversionDictionaryList *) this ); 622cdf0e10cSrcweir aEvtListeners.disposeAndClear( aEvtObj ); 623cdf0e10cSrcweir 624cdf0e10cSrcweir FlushDics(); 625cdf0e10cSrcweir } 626cdf0e10cSrcweir } 627cdf0e10cSrcweir 628cdf0e10cSrcweir 629cdf0e10cSrcweir void SAL_CALL ConvDicList::addEventListener( 630cdf0e10cSrcweir const uno::Reference< XEventListener >& rxListener ) 631cdf0e10cSrcweir throw (RuntimeException) 632cdf0e10cSrcweir { 633cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 634cdf0e10cSrcweir if (!bDisposing && rxListener.is()) 635cdf0e10cSrcweir aEvtListeners.addInterface( rxListener ); 636cdf0e10cSrcweir } 637cdf0e10cSrcweir 638cdf0e10cSrcweir 639cdf0e10cSrcweir void SAL_CALL ConvDicList::removeEventListener( 640cdf0e10cSrcweir const uno::Reference< XEventListener >& rxListener ) 641cdf0e10cSrcweir throw (RuntimeException) 642cdf0e10cSrcweir { 643cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 644cdf0e10cSrcweir if (!bDisposing && rxListener.is()) 645cdf0e10cSrcweir aEvtListeners.removeInterface( rxListener ); 646cdf0e10cSrcweir } 647cdf0e10cSrcweir 648cdf0e10cSrcweir 649cdf0e10cSrcweir OUString SAL_CALL ConvDicList::getImplementationName( ) 650cdf0e10cSrcweir throw (RuntimeException) 651cdf0e10cSrcweir { 652cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 653cdf0e10cSrcweir return getImplementationName_Static(); 654cdf0e10cSrcweir } 655cdf0e10cSrcweir 656cdf0e10cSrcweir 657cdf0e10cSrcweir sal_Bool SAL_CALL ConvDicList::supportsService( const OUString& rServiceName ) 658cdf0e10cSrcweir throw (RuntimeException) 659cdf0e10cSrcweir { 660cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 661cdf0e10cSrcweir return rServiceName.equalsAscii( SN_CONV_DICTIONARY_LIST ); 662cdf0e10cSrcweir } 663cdf0e10cSrcweir 664cdf0e10cSrcweir 665cdf0e10cSrcweir uno::Sequence< OUString > SAL_CALL ConvDicList::getSupportedServiceNames( ) 666cdf0e10cSrcweir throw (RuntimeException) 667cdf0e10cSrcweir { 668cdf0e10cSrcweir MutexGuard aGuard( GetLinguMutex() ); 669cdf0e10cSrcweir return getSupportedServiceNames_Static(); 670cdf0e10cSrcweir } 671cdf0e10cSrcweir 672cdf0e10cSrcweir 673cdf0e10cSrcweir uno::Sequence< OUString > ConvDicList::getSupportedServiceNames_Static() 674cdf0e10cSrcweir throw() 675cdf0e10cSrcweir { 676cdf0e10cSrcweir uno::Sequence< OUString > aSNS( 1 ); 677cdf0e10cSrcweir aSNS.getArray()[0] = A2OU( SN_CONV_DICTIONARY_LIST ); 678cdf0e10cSrcweir return aSNS; 679cdf0e10cSrcweir } 680cdf0e10cSrcweir 681cdf0e10cSrcweir 682cdf0e10cSrcweir /////////////////////////////////////////////////////////////////////////// 683cdf0e10cSrcweir 684cdf0e10cSrcweir uno::Reference< uno::XInterface > SAL_CALL ConvDicList_CreateInstance( 685cdf0e10cSrcweir const uno::Reference< XMultiServiceFactory > & /*rSMgr*/ ) 686cdf0e10cSrcweir throw(Exception) 687cdf0e10cSrcweir { 688cdf0e10cSrcweir return StaticConvDicList::get(); 689cdf0e10cSrcweir } 690cdf0e10cSrcweir 691cdf0e10cSrcweir void * SAL_CALL ConvDicList_getFactory( 692cdf0e10cSrcweir const sal_Char * pImplName, 693cdf0e10cSrcweir XMultiServiceFactory * pServiceManager, void * ) 694cdf0e10cSrcweir { 695cdf0e10cSrcweir void * pRet = 0; 696cdf0e10cSrcweir if ( !ConvDicList::getImplementationName_Static().compareToAscii( pImplName ) ) 697cdf0e10cSrcweir { 698cdf0e10cSrcweir uno::Reference< XSingleServiceFactory > xFactory = 699cdf0e10cSrcweir cppu::createOneInstanceFactory( 700cdf0e10cSrcweir pServiceManager, 701cdf0e10cSrcweir ConvDicList::getImplementationName_Static(), 702cdf0e10cSrcweir ConvDicList_CreateInstance, 703cdf0e10cSrcweir ConvDicList::getSupportedServiceNames_Static()); 704cdf0e10cSrcweir // acquire, because we return an interface pointer instead of a reference 705cdf0e10cSrcweir xFactory->acquire(); 706cdf0e10cSrcweir pRet = xFactory.get(); 707cdf0e10cSrcweir } 708cdf0e10cSrcweir return pRet; 709cdf0e10cSrcweir } 710cdf0e10cSrcweir 711cdf0e10cSrcweir /////////////////////////////////////////////////////////////////////////// 712cdf0e10cSrcweir 713