Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 :
21 : #include <memory>
22 :
23 : #include <vcl/bitmap.hxx>
24 : #include <vcl/builder.hxx>
25 :
26 : #include "basidesh.hxx"
27 : #include "iderdll.hxx"
28 : #include "iderdll2.hxx"
29 : #include <basidesh.hrc>
30 : #include <bastypes.hxx>
31 : #include <bastype2.hxx>
32 : #include <basobj.hxx>
33 : #include <baside2.hrc>
34 : #include <iderid.hxx>
35 : #include <tools/urlobj.hxx>
36 : #include <tools/diagnose_ex.h>
37 : #include <basic/sbx.hxx>
38 : #include <svtools/imagemgr.hxx>
39 : #include "svtools/treelistentry.hxx"
40 : #include <com/sun/star/script/XLibraryContainer.hpp>
41 : #include <com/sun/star/script/XLibraryContainerPassword.hpp>
42 : #include <com/sun/star/frame/ModuleManager.hpp>
43 : #include <comphelper/processfactory.hxx>
44 : #include <sfx2/dispatch.hxx>
45 :
46 : #include <map>
47 : #include <com/sun/star/script/ModuleType.hpp>
48 : #include <com/sun/star/script/vba/XVBAModuleInfo.hpp>
49 : #include <com/sun/star/container/XNameContainer.hpp>
50 : #include <com/sun/star/lang/XServiceInfo.hpp>
51 : #include <com/sun/star/container/XNamed.hpp>
52 :
53 : namespace basctl
54 : {
55 :
56 : using namespace ::com::sun::star::uno;
57 : using namespace ::com::sun::star;
58 :
59 0 : void ModuleInfoHelper::getObjectName( const uno::Reference< container::XNameContainer >& rLib, const OUString& rModName, OUString& rObjName )
60 : {
61 : try
62 : {
63 0 : uno::Reference< script::vba::XVBAModuleInfo > xVBAModuleInfo( rLib, uno::UNO_QUERY );
64 0 : if ( xVBAModuleInfo.is() && xVBAModuleInfo->hasModuleInfo( rModName ) )
65 : {
66 0 : script::ModuleInfo aModuleInfo = xVBAModuleInfo->getModuleInfo( rModName );
67 0 : uno::Any aObject( aModuleInfo.ModuleObject );
68 0 : uno::Reference< lang::XServiceInfo > xServiceInfo( aObject, uno::UNO_QUERY );
69 0 : if( xServiceInfo.is() && xServiceInfo->supportsService( "ooo.vba.excel.Worksheet" ) )
70 : {
71 0 : uno::Reference< container::XNamed > xNamed( aObject, uno::UNO_QUERY );
72 0 : if( xNamed.is() )
73 0 : rObjName = xNamed->getName();
74 0 : }
75 0 : }
76 : }
77 0 : catch(const uno::Exception& )
78 : {
79 : }
80 0 : }
81 :
82 0 : sal_Int32 ModuleInfoHelper::getModuleType( const uno::Reference< container::XNameContainer >& rLib, const OUString& rModName )
83 : {
84 0 : sal_Int32 nType = script::ModuleType::NORMAL;
85 0 : uno::Reference< script::vba::XVBAModuleInfo > xVBAModuleInfo( rLib, uno::UNO_QUERY );
86 0 : if ( xVBAModuleInfo.is() && xVBAModuleInfo->hasModuleInfo( rModName ) )
87 : {
88 0 : script::ModuleInfo aModuleInfo = xVBAModuleInfo->getModuleInfo( rModName );
89 0 : nType = aModuleInfo.ModuleType;
90 : }
91 0 : return nType;
92 : }
93 :
94 0 : Entry::~Entry()
95 0 : { }
96 :
97 0 : DocumentEntry::DocumentEntry (
98 : ScriptDocument const& rDocument,
99 : LibraryLocation eLocation,
100 : EntryType eType
101 : ) :
102 : Entry(eType),
103 : m_aDocument(rDocument),
104 0 : m_eLocation(eLocation)
105 : {
106 : OSL_ENSURE( m_aDocument.isValid(), "DocumentEntry::DocumentEntry: illegal document!" );
107 0 : }
108 :
109 0 : DocumentEntry::~DocumentEntry()
110 0 : { }
111 :
112 0 : LibEntry::LibEntry (
113 : ScriptDocument const& rDocument,
114 : LibraryLocation eLocation,
115 : OUString const& rLibName,
116 : EntryType eType
117 : ) :
118 : DocumentEntry(rDocument, eLocation, eType),
119 0 : m_aLibName(rLibName)
120 0 : { }
121 :
122 0 : LibEntry::~LibEntry()
123 0 : { }
124 :
125 0 : EntryDescriptor::EntryDescriptor () :
126 0 : m_aDocument(ScriptDocument::getApplicationScriptDocument()),
127 : m_eLocation(LIBRARY_LOCATION_UNKNOWN),
128 0 : m_eType(OBJ_TYPE_UNKNOWN)
129 0 : { }
130 :
131 0 : EntryDescriptor::EntryDescriptor (
132 : ScriptDocument const& rDocument,
133 : LibraryLocation eLocation,
134 : OUString const& rLibName,
135 : OUString const& rLibSubName,
136 : OUString const& rName,
137 : EntryType eType
138 : ) :
139 : m_aDocument(rDocument),
140 : m_eLocation(eLocation),
141 : m_aLibName(rLibName),
142 : m_aLibSubName(rLibSubName),
143 : m_aName(rName),
144 0 : m_eType(eType)
145 : {
146 : OSL_ENSURE( m_aDocument.isValid(), "EntryDescriptor::EntryDescriptor: invalid document!" );
147 0 : }
148 :
149 0 : EntryDescriptor::EntryDescriptor (
150 : ScriptDocument const& rDocument,
151 : LibraryLocation eLocation,
152 : OUString const& rLibName,
153 : OUString const& rLibSubName,
154 : OUString const& rName,
155 : OUString const& rMethodName,
156 : EntryType eType
157 : ) :
158 : m_aDocument(rDocument),
159 : m_eLocation(eLocation),
160 : m_aLibName(rLibName),
161 : m_aLibSubName(rLibSubName),
162 : m_aName(rName),
163 : m_aMethodName(rMethodName),
164 0 : m_eType(eType)
165 : {
166 : OSL_ENSURE( m_aDocument.isValid(), "EntryDescriptor::EntryDescriptor: invalid document!" );
167 0 : }
168 :
169 0 : EntryDescriptor::~EntryDescriptor()
170 0 : { }
171 :
172 0 : bool EntryDescriptor::operator == (EntryDescriptor const& rDesc) const
173 : {
174 : return
175 0 : m_aDocument == rDesc.m_aDocument &&
176 : m_eLocation == rDesc.m_eLocation &&
177 0 : m_aLibName == rDesc.m_aLibName &&
178 0 : m_aLibSubName == rDesc.m_aLibSubName &&
179 0 : m_aName == rDesc.m_aName &&
180 0 : m_aMethodName == rDesc.m_aMethodName &&
181 0 : m_eType == rDesc.m_eType;
182 : }
183 :
184 : //
185 : // TreeListBox
186 : // ===========
187 : //
188 :
189 0 : TreeListBox::TreeListBox (Window* pParent, ResId const& rRes)
190 0 : : SvTreeListBox( pParent, IDEResId( sal::static_int_cast<sal_uInt16>( rRes.GetId() ) ) )
191 0 : , m_aNotifier( *this )
192 : {
193 0 : Init();
194 0 : }
195 :
196 0 : TreeListBox::TreeListBox (Window* pParent)
197 : : SvTreeListBox(pParent, WB_TABSTOP)
198 0 : , m_aNotifier( *this )
199 : {
200 0 : Init();
201 0 : }
202 :
203 0 : void TreeListBox::Init()
204 : {
205 0 : SetNodeDefaultImages();
206 0 : SetSelectionMode( SINGLE_SELECTION );
207 0 : nMode = 0xFF; // everything
208 0 : }
209 :
210 0 : extern "C" SAL_DLLPUBLIC_EXPORT Window* SAL_CALL makeTreeListBox(Window *pParent, VclBuilder::stringmap &)
211 : {
212 0 : return new TreeListBox(pParent);
213 : }
214 :
215 0 : TreeListBox::~TreeListBox ()
216 : {
217 0 : m_aNotifier.dispose();
218 :
219 : // destroy user data
220 0 : SvTreeListEntry* pEntry = First();
221 0 : while ( pEntry )
222 : {
223 0 : delete static_cast<Entry*>(pEntry->GetUserData());
224 0 : pEntry = Next( pEntry );
225 : }
226 0 : }
227 :
228 0 : void TreeListBox::ScanEntry( const ScriptDocument& rDocument, LibraryLocation eLocation )
229 : {
230 : OSL_ENSURE( rDocument.isAlive(), "TreeListBox::ScanEntry: illegal document!" );
231 0 : if ( !rDocument.isAlive() )
232 0 : return;
233 :
234 : // can be called multiple times for updating!
235 :
236 : // actually test if basic's in the tree already?!
237 0 : SetUpdateMode(false);
238 :
239 : // level 1: BasicManager (application, document, ...)
240 0 : SvTreeListEntry* pDocumentRootEntry = FindRootEntry( rDocument, eLocation );
241 0 : if ( pDocumentRootEntry && IsExpanded( pDocumentRootEntry ) )
242 0 : ImpCreateLibEntries( pDocumentRootEntry, rDocument, eLocation );
243 0 : if ( !pDocumentRootEntry )
244 : {
245 0 : OUString aRootName( GetRootEntryName( rDocument, eLocation ) );
246 0 : Image aImage;
247 0 : GetRootEntryBitmaps( rDocument, aImage );
248 : SAL_WNODEPRECATED_DECLARATIONS_PUSH
249 : pDocumentRootEntry = AddEntry(
250 : aRootName,
251 : aImage,
252 : 0, true,
253 0 : std::auto_ptr<Entry>(new DocumentEntry(rDocument, eLocation))
254 0 : );
255 0 : SAL_WNODEPRECATED_DECLARATIONS_POP
256 : }
257 :
258 0 : SetUpdateMode(true);
259 : }
260 :
261 0 : void TreeListBox::ImpCreateLibEntries( SvTreeListEntry* pDocumentRootEntry, const ScriptDocument& rDocument, LibraryLocation eLocation )
262 : {
263 : // get a sorted list of library names
264 0 : Sequence< OUString > aLibNames( rDocument.getLibraryNames() );
265 0 : sal_Int32 nLibCount = aLibNames.getLength();
266 0 : const OUString* pLibNames = aLibNames.getConstArray();
267 :
268 0 : for ( sal_Int32 i = 0 ; i < nLibCount ; i++ )
269 : {
270 0 : OUString aLibName = pLibNames[ i ];
271 :
272 0 : if ( eLocation == rDocument.getLibraryLocation( aLibName ) )
273 : {
274 : // check, if the module library is loaded
275 0 : bool bModLibLoaded = false;
276 0 : OUString aOULibName( aLibName );
277 0 : Reference< script::XLibraryContainer > xModLibContainer( rDocument.getLibraryContainer( E_SCRIPTS ) );
278 0 : if ( xModLibContainer.is() && xModLibContainer->hasByName( aOULibName ) && xModLibContainer->isLibraryLoaded( aOULibName ) )
279 0 : bModLibLoaded = true;
280 :
281 : // check, if the dialog library is loaded
282 0 : bool bDlgLibLoaded = false;
283 0 : Reference< script::XLibraryContainer > xDlgLibContainer( rDocument.getLibraryContainer( E_DIALOGS ) );
284 0 : if ( xDlgLibContainer.is() && xDlgLibContainer->hasByName( aOULibName ) && xDlgLibContainer->isLibraryLoaded( aOULibName ) )
285 0 : bDlgLibLoaded = true;
286 :
287 0 : bool bLoaded = bModLibLoaded || bDlgLibLoaded;
288 :
289 : // if only one of the libraries is loaded, load also the other
290 0 : if ( bLoaded )
291 : {
292 0 : if ( xModLibContainer.is() && xModLibContainer->hasByName( aOULibName ) && !xModLibContainer->isLibraryLoaded( aOULibName ) )
293 0 : xModLibContainer->loadLibrary( aOULibName );
294 :
295 0 : if ( xDlgLibContainer.is() && xDlgLibContainer->hasByName( aOULibName ) && !xDlgLibContainer->isLibraryLoaded( aOULibName ) )
296 0 : xDlgLibContainer->loadLibrary( aOULibName );
297 : }
298 :
299 : // create tree list box entry
300 : sal_uInt16 nId;
301 0 : if ( ( nMode & BROWSEMODE_DIALOGS ) && !( nMode & BROWSEMODE_MODULES ) )
302 0 : nId = bLoaded ? RID_IMG_DLGLIB : RID_IMG_DLGLIBNOTLOADED;
303 : else
304 0 : nId = bLoaded ? RID_IMG_MODLIB : RID_IMG_MODLIBNOTLOADED;
305 0 : SvTreeListEntry* pLibRootEntry = FindEntry( pDocumentRootEntry, aLibName, OBJ_TYPE_LIBRARY );
306 0 : if ( pLibRootEntry )
307 : {
308 0 : SetEntryBitmaps( pLibRootEntry, Image( IDEResId( nId ) ) );
309 0 : if ( IsExpanded( pLibRootEntry ) )
310 0 : ImpCreateLibSubEntries( pLibRootEntry, rDocument, aLibName );
311 : }
312 : else
313 : {
314 : pLibRootEntry = AddEntry(
315 : aLibName,
316 : Image( IDEResId( nId ) ),
317 : pDocumentRootEntry, true,
318 0 : std::auto_ptr<Entry>(new Entry(OBJ_TYPE_LIBRARY))
319 0 : );
320 0 : }
321 : }
322 0 : }
323 0 : }
324 :
325 0 : void TreeListBox::ImpCreateLibSubEntries( SvTreeListEntry* pLibRootEntry, const ScriptDocument& rDocument, const OUString& rLibName )
326 : {
327 : // modules
328 0 : if ( nMode & BROWSEMODE_MODULES )
329 : {
330 0 : Reference< script::XLibraryContainer > xModLibContainer( rDocument.getLibraryContainer( E_SCRIPTS ) );
331 :
332 0 : if ( xModLibContainer.is() && xModLibContainer->hasByName( rLibName ) && xModLibContainer->isLibraryLoaded( rLibName ) )
333 : {
334 : try
335 : {
336 0 : if( rDocument.isInVBAMode() )
337 0 : ImpCreateLibSubEntriesInVBAMode( pLibRootEntry, rDocument, rLibName );
338 : else
339 : {
340 : // get a sorted list of module names
341 0 : Sequence< OUString > aModNames = rDocument.getObjectNames( E_SCRIPTS, rLibName );
342 0 : sal_Int32 nModCount = aModNames.getLength();
343 0 : const OUString* pModNames = aModNames.getConstArray();
344 :
345 0 : for ( sal_Int32 i = 0 ; i < nModCount ; i++ )
346 : {
347 0 : OUString aModName = pModNames[ i ];
348 0 : SvTreeListEntry* pModuleEntry = FindEntry( pLibRootEntry, aModName, OBJ_TYPE_MODULE );
349 0 : if ( !pModuleEntry )
350 : pModuleEntry = AddEntry(
351 : aModName,
352 : Image( IDEResId( RID_IMG_MODULE ) ),
353 : pLibRootEntry, false,
354 0 : std::auto_ptr<Entry>(new Entry(OBJ_TYPE_MODULE))
355 0 : );
356 :
357 : // methods
358 0 : if ( nMode & BROWSEMODE_SUBS )
359 : {
360 0 : Sequence< OUString > aNames = GetMethodNames( rDocument, rLibName, aModName );
361 0 : sal_Int32 nCount = aNames.getLength();
362 0 : const OUString* pNames = aNames.getConstArray();
363 :
364 0 : for ( sal_Int32 j = 0 ; j < nCount ; j++ )
365 : {
366 0 : OUString aName = pNames[ j ];
367 0 : SvTreeListEntry* pEntry = FindEntry( pModuleEntry, aName, OBJ_TYPE_METHOD );
368 0 : if ( !pEntry )
369 : pEntry = AddEntry(
370 : aName,
371 : Image( IDEResId( RID_IMG_MACRO ) ),
372 : pModuleEntry, false,
373 0 : std::auto_ptr<Entry>(new Entry(OBJ_TYPE_METHOD))
374 0 : );
375 0 : }
376 : }
377 0 : }
378 : }
379 : }
380 0 : catch ( const container::NoSuchElementException& )
381 : {
382 : DBG_UNHANDLED_EXCEPTION();
383 : }
384 0 : }
385 : }
386 :
387 : // dialogs
388 0 : if ( nMode & BROWSEMODE_DIALOGS )
389 : {
390 0 : Reference< script::XLibraryContainer > xDlgLibContainer( rDocument.getLibraryContainer( E_DIALOGS ) );
391 :
392 0 : if ( xDlgLibContainer.is() && xDlgLibContainer->hasByName( rLibName ) && xDlgLibContainer->isLibraryLoaded( rLibName ) )
393 : {
394 : try
395 : {
396 : // get a sorted list of dialog names
397 0 : Sequence< OUString > aDlgNames( rDocument.getObjectNames( E_DIALOGS, rLibName ) );
398 0 : sal_Int32 nDlgCount = aDlgNames.getLength();
399 0 : const OUString* pDlgNames = aDlgNames.getConstArray();
400 :
401 0 : for ( sal_Int32 i = 0 ; i < nDlgCount ; i++ )
402 : {
403 0 : OUString aDlgName = pDlgNames[ i ];
404 0 : SvTreeListEntry* pDialogEntry = FindEntry( pLibRootEntry, aDlgName, OBJ_TYPE_DIALOG );
405 0 : if ( !pDialogEntry )
406 : pDialogEntry = AddEntry(
407 : aDlgName,
408 : Image( IDEResId( RID_IMG_DIALOG ) ),
409 : pLibRootEntry, false,
410 0 : std::auto_ptr<Entry>(new Entry(OBJ_TYPE_DIALOG))
411 0 : );
412 0 : }
413 : }
414 0 : catch (const container::NoSuchElementException& )
415 : {
416 : DBG_UNHANDLED_EXCEPTION();
417 : }
418 0 : }
419 : }
420 0 : }
421 :
422 0 : void TreeListBox::ImpCreateLibSubEntriesInVBAMode( SvTreeListEntry* pLibRootEntry, const ScriptDocument& rDocument, const OUString& rLibName )
423 : {
424 :
425 0 : std::vector<std::pair<EntryType, OUString> > aEntries;
426 0 : aEntries.push_back( ::std::make_pair( OBJ_TYPE_DOCUMENT_OBJECTS, IDE_RESSTR(RID_STR_DOCUMENT_OBJECTS) ) );
427 0 : aEntries.push_back( ::std::make_pair( OBJ_TYPE_USERFORMS, IDE_RESSTR(RID_STR_USERFORMS) ) );
428 0 : aEntries.push_back( ::std::make_pair( OBJ_TYPE_NORMAL_MODULES, IDE_RESSTR(RID_STR_NORMAL_MODULES) ) );
429 0 : aEntries.push_back( ::std::make_pair( OBJ_TYPE_CLASS_MODULES, IDE_RESSTR(RID_STR_CLASS_MODULES) ) );
430 :
431 0 : std::vector<std::pair<EntryType, OUString> >::iterator iter;
432 0 : for( iter = aEntries.begin(); iter != aEntries.end(); ++iter )
433 : {
434 0 : EntryType eType = iter->first;
435 0 : OUString aEntryName = iter->second;
436 0 : SvTreeListEntry* pLibSubRootEntry = FindEntry( pLibRootEntry, aEntryName, eType );
437 0 : if( pLibSubRootEntry )
438 : {
439 0 : SetEntryBitmaps( pLibSubRootEntry, Image( IDEResId( RID_IMG_MODLIB ) ) );
440 0 : if ( IsExpanded( pLibSubRootEntry ) )
441 0 : ImpCreateLibSubSubEntriesInVBAMode( pLibSubRootEntry, rDocument, rLibName );
442 : }
443 : else
444 : {
445 : pLibSubRootEntry = AddEntry(
446 : aEntryName,
447 : Image( IDEResId( RID_IMG_MODLIB ) ),
448 : pLibRootEntry, true,
449 0 : std::auto_ptr<Entry>(new Entry(eType))
450 0 : );
451 : }
452 0 : }
453 0 : }
454 :
455 0 : void TreeListBox::ImpCreateLibSubSubEntriesInVBAMode( SvTreeListEntry* pLibSubRootEntry, const ScriptDocument& rDocument, const OUString& rLibName )
456 : {
457 0 : uno::Reference< container::XNameContainer > xLib = rDocument.getOrCreateLibrary( E_SCRIPTS, rLibName );
458 0 : if( !xLib.is() )
459 0 : return;
460 :
461 : try
462 : {
463 : // get a sorted list of module names
464 0 : Sequence< OUString > aModNames = rDocument.getObjectNames( E_SCRIPTS, rLibName );
465 0 : sal_Int32 nModCount = aModNames.getLength();
466 0 : const OUString* pModNames = aModNames.getConstArray();
467 :
468 0 : EntryDescriptor aDesc( GetEntryDescriptor( pLibSubRootEntry ) );
469 0 : EntryType eCurrentType( aDesc.GetType() );
470 :
471 0 : for ( sal_Int32 i = 0 ; i < nModCount ; i++ )
472 : {
473 0 : OUString aModName = pModNames[ i ];
474 0 : EntryType eType = OBJ_TYPE_UNKNOWN;
475 0 : switch( ModuleInfoHelper::getModuleType( xLib, aModName ) )
476 : {
477 : case script::ModuleType::DOCUMENT:
478 0 : eType = OBJ_TYPE_DOCUMENT_OBJECTS;
479 0 : break;
480 : case script::ModuleType::FORM:
481 0 : eType = OBJ_TYPE_USERFORMS;
482 0 : break;
483 : case script::ModuleType::NORMAL:
484 0 : eType = OBJ_TYPE_NORMAL_MODULES;
485 0 : break;
486 : case script::ModuleType::CLASS:
487 0 : eType = OBJ_TYPE_CLASS_MODULES;
488 0 : break;
489 : }
490 0 : if( eType != eCurrentType )
491 0 : continue;
492 :
493 : // display a nice friendly name in the ObjectModule tab,
494 : // combining the objectname and module name, e.g. Sheet1 ( Financials )
495 0 : OUStringBuffer aEntryNameBuf( aModName );
496 0 : if( eType == OBJ_TYPE_DOCUMENT_OBJECTS )
497 : {
498 0 : OUString sObjName;
499 0 : ModuleInfoHelper::getObjectName( xLib, aModName, sObjName );
500 0 : if( !sObjName.isEmpty() )
501 : {
502 0 : aEntryNameBuf.append( " (" );
503 0 : aEntryNameBuf.append(sObjName);
504 0 : aEntryNameBuf.append(')');
505 0 : }
506 : }
507 0 : OUString aEntryName(aEntryNameBuf.makeStringAndClear());
508 0 : SvTreeListEntry* pModuleEntry = FindEntry( pLibSubRootEntry, aEntryName, OBJ_TYPE_MODULE );
509 0 : if ( !pModuleEntry )
510 : pModuleEntry = AddEntry(
511 : aEntryName,
512 : Image( IDEResId( RID_IMG_MODULE ) ),
513 : pLibSubRootEntry, false,
514 0 : std::auto_ptr<Entry>(new Entry(OBJ_TYPE_MODULE))
515 0 : );
516 :
517 : // methods
518 0 : if ( nMode & BROWSEMODE_SUBS )
519 : {
520 0 : Sequence< OUString > aNames = GetMethodNames( rDocument, rLibName, aModName );
521 0 : sal_Int32 nCount = aNames.getLength();
522 0 : const OUString* pNames = aNames.getConstArray();
523 :
524 0 : for ( sal_Int32 j = 0 ; j < nCount ; j++ )
525 : {
526 0 : OUString aName = pNames[ j ];
527 0 : SvTreeListEntry* pEntry = FindEntry( pModuleEntry, aName, OBJ_TYPE_METHOD );
528 0 : if ( !pEntry )
529 : pEntry = AddEntry(
530 : aName,
531 : Image( IDEResId( RID_IMG_MACRO ) ),
532 : pModuleEntry, false,
533 0 : std::auto_ptr<Entry>(new Entry(OBJ_TYPE_METHOD))
534 0 : );
535 0 : }
536 : }
537 0 : }
538 : }
539 0 : catch ( const container::NoSuchElementException& )
540 : {
541 : DBG_UNHANDLED_EXCEPTION();
542 0 : }
543 : }
544 :
545 0 : SvTreeListEntry* TreeListBox::ImpFindEntry( SvTreeListEntry* pParent, const OUString& rText )
546 : {
547 0 : sal_uLong nRootPos = 0;
548 0 : SvTreeListEntry* pEntry = pParent ? FirstChild( pParent ) : GetEntry( nRootPos );
549 0 : while ( pEntry )
550 : {
551 0 : if ( rText.equals(GetEntryText( pEntry )) )
552 0 : return pEntry;
553 :
554 0 : pEntry = pParent ? NextSibling( pEntry ) : GetEntry( ++nRootPos );
555 : }
556 0 : return 0;
557 : }
558 :
559 0 : void TreeListBox::onDocumentCreated( const ScriptDocument& /*_rDocument*/ )
560 : {
561 0 : UpdateEntries();
562 0 : }
563 :
564 0 : void TreeListBox::onDocumentOpened( const ScriptDocument& /*_rDocument*/ )
565 : {
566 0 : UpdateEntries();
567 0 : }
568 :
569 0 : void TreeListBox::onDocumentSave( const ScriptDocument& /*_rDocument*/ )
570 : {
571 : // not interested in
572 0 : }
573 :
574 0 : void TreeListBox::onDocumentSaveDone( const ScriptDocument& /*_rDocument*/ )
575 : {
576 : // not interested in
577 0 : }
578 :
579 0 : void TreeListBox::onDocumentSaveAs( const ScriptDocument& /*_rDocument*/ )
580 : {
581 : // not interested in
582 0 : }
583 :
584 0 : void TreeListBox::onDocumentSaveAsDone( const ScriptDocument& /*_rDocument*/ )
585 : {
586 0 : UpdateEntries();
587 0 : }
588 :
589 0 : void TreeListBox::onDocumentClosed( const ScriptDocument& rDocument )
590 : {
591 0 : UpdateEntries();
592 : // The document is not yet actually deleted, so we need to remove its entry
593 : // manually.
594 0 : RemoveEntry(rDocument);
595 0 : }
596 :
597 0 : void TreeListBox::onDocumentTitleChanged( const ScriptDocument& /*_rDocument*/ )
598 : {
599 : // not interested in
600 0 : }
601 :
602 0 : void TreeListBox::onDocumentModeChanged( const ScriptDocument& /*_rDocument*/ )
603 : {
604 : // not interested in
605 0 : }
606 :
607 0 : void TreeListBox::UpdateEntries()
608 : {
609 0 : EntryDescriptor aCurDesc( GetEntryDescriptor( FirstSelected() ) );
610 :
611 : // removing the invalid entries
612 0 : SvTreeListEntry* pLastValid = 0;
613 0 : SvTreeListEntry* pEntry = First();
614 0 : while ( pEntry )
615 : {
616 0 : if ( IsValidEntry( pEntry ) )
617 0 : pLastValid = pEntry;
618 : else
619 0 : RemoveEntry(pEntry);
620 0 : pEntry = pLastValid ? Next( pLastValid ) : First();
621 : }
622 :
623 0 : ScanAllEntries();
624 :
625 0 : SetCurrentEntry( aCurDesc );
626 0 : }
627 :
628 : // Removes the entry from the tree.
629 0 : void TreeListBox::RemoveEntry (SvTreeListEntry* pEntry)
630 : {
631 : // removing the associated user data
632 0 : delete static_cast<Entry*>(pEntry->GetUserData());
633 : // removing the entry
634 0 : GetModel()->Remove( pEntry );
635 0 : }
636 :
637 : // Removes the entry of rDocument.
638 0 : void TreeListBox::RemoveEntry (ScriptDocument const& rDocument)
639 : {
640 : // finding the entry of rDocument
641 0 : for (SvTreeListEntry* pEntry = First(); pEntry; pEntry = Next(pEntry))
642 0 : if (rDocument == GetEntryDescriptor(pEntry).GetDocument())
643 : {
644 0 : RemoveEntry(pEntry);
645 0 : break;
646 : }
647 0 : }
648 :
649 0 : SvTreeListEntry* TreeListBox::CloneEntry( SvTreeListEntry* pSource )
650 : {
651 0 : SvTreeListEntry* pNew = SvTreeListBox::CloneEntry( pSource );
652 0 : Entry* pUser = static_cast<Entry*>(pSource->GetUserData());
653 :
654 : DBG_ASSERT( pUser, "User-Daten?!" );
655 : DBG_ASSERT( pUser->GetType() != OBJ_TYPE_DOCUMENT, "TreeListBox::CloneEntry: document?!" );
656 :
657 0 : Entry* pNewUser = new Entry( *pUser );
658 0 : pNew->SetUserData( pNewUser );
659 0 : return pNew;
660 : }
661 :
662 0 : SvTreeListEntry* TreeListBox::FindEntry( SvTreeListEntry* pParent, const OUString& rText, EntryType eType )
663 : {
664 0 : sal_uLong nRootPos = 0;
665 0 : SvTreeListEntry* pEntry = pParent ? FirstChild( pParent ) : GetEntry( nRootPos );
666 0 : while ( pEntry )
667 : {
668 0 : Entry* pBasicEntry = static_cast<Entry*>(pEntry->GetUserData());
669 : DBG_ASSERT( pBasicEntry, "FindEntry: no Entry ?!" );
670 0 : if ( ( pBasicEntry->GetType() == eType ) && ( rText.equals(GetEntryText( pEntry )) ) )
671 0 : return pEntry;
672 :
673 0 : pEntry = pParent ? NextSibling( pEntry ) : GetEntry( ++nRootPos );
674 : }
675 0 : return 0;
676 : }
677 :
678 0 : long TreeListBox::ExpandingHdl()
679 : {
680 : // expanding or collapsing?
681 0 : bool bOK = true;
682 0 : if ( GetModel()->GetDepth( GetHdlEntry() ) == 1 )
683 : {
684 0 : SvTreeListEntry* pCurEntry = GetCurEntry();
685 0 : EntryDescriptor aDesc( GetEntryDescriptor( pCurEntry ) );
686 0 : ScriptDocument aDocument( aDesc.GetDocument() );
687 : OSL_ENSURE( aDocument.isAlive(), "TreeListBox::ExpandingHdl: no document, or document is dead!" );
688 0 : if ( aDocument.isAlive() )
689 : {
690 0 : OUString aLibName( aDesc.GetLibName() );
691 0 : OUString aLibSubName( aDesc.GetLibSubName() );
692 0 : OUString aName( aDesc.GetName() );
693 0 : OUString aMethodName( aDesc.GetMethodName() );
694 :
695 0 : if ( !aLibName.isEmpty() && aLibSubName.isEmpty() && aName.isEmpty() && aMethodName.isEmpty() )
696 : {
697 : // check password, if library is password protected and not verified
698 0 : Reference< script::XLibraryContainer > xModLibContainer( aDocument.getLibraryContainer( E_SCRIPTS ) );
699 0 : if ( xModLibContainer.is() && xModLibContainer->hasByName( aLibName ) )
700 : {
701 0 : Reference< script::XLibraryContainerPassword > xPasswd( xModLibContainer, UNO_QUERY );
702 0 : if ( xPasswd.is() && xPasswd->isLibraryPasswordProtected( aLibName ) && !xPasswd->isLibraryPasswordVerified( aLibName ) )
703 : {
704 0 : OUString aPassword;
705 0 : bOK = QueryPassword( xModLibContainer, aLibName, aPassword );
706 0 : }
707 0 : }
708 0 : }
709 0 : }
710 : }
711 0 : return bOK;
712 : }
713 :
714 0 : bool TreeListBox::IsEntryProtected( SvTreeListEntry* pEntry )
715 : {
716 0 : bool bProtected = false;
717 0 : if ( pEntry && ( GetModel()->GetDepth( pEntry ) == 1 ) )
718 : {
719 0 : EntryDescriptor aDesc( GetEntryDescriptor( pEntry ) );
720 0 : ScriptDocument aDocument( aDesc.GetDocument() );
721 : OSL_ENSURE( aDocument.isAlive(), "TreeListBox::IsEntryProtected: no document, or document is dead!" );
722 0 : if ( aDocument.isAlive() )
723 : {
724 0 : OUString aOULibName( aDesc.GetLibName() );
725 0 : Reference< script::XLibraryContainer > xModLibContainer( aDocument.getLibraryContainer( E_SCRIPTS ) );
726 0 : if ( xModLibContainer.is() && xModLibContainer->hasByName( aOULibName ) )
727 : {
728 0 : Reference< script::XLibraryContainerPassword > xPasswd( xModLibContainer, UNO_QUERY );
729 0 : if ( xPasswd.is() && xPasswd->isLibraryPasswordProtected( aOULibName ) && !xPasswd->isLibraryPasswordVerified( aOULibName ) )
730 : {
731 0 : bProtected = true;
732 0 : }
733 0 : }
734 0 : }
735 : }
736 0 : return bProtected;
737 : }
738 :
739 : SAL_WNODEPRECATED_DECLARATIONS_PUSH
740 0 : SvTreeListEntry* TreeListBox::AddEntry(
741 : OUString const& rText,
742 : const Image& rImage,
743 : SvTreeListEntry* pParent,
744 : bool bChildrenOnDemand,
745 : std::auto_ptr<Entry> aUserData
746 : )
747 : {
748 : SvTreeListEntry* p = InsertEntry(
749 : rText, rImage, rImage, pParent, bChildrenOnDemand, LIST_APPEND,
750 0 : aUserData.release() // XXX possible leak
751 0 : );
752 0 : return p;
753 : }
754 : SAL_WNODEPRECATED_DECLARATIONS_POP
755 :
756 0 : void TreeListBox::SetEntryBitmaps( SvTreeListEntry * pEntry, const Image& rImage )
757 : {
758 0 : SetExpandedEntryBmp( pEntry, rImage );
759 0 : SetCollapsedEntryBmp( pEntry, rImage );
760 0 : }
761 :
762 0 : LibraryType TreeListBox::GetLibraryType() const
763 : {
764 0 : LibraryType eType = LIBRARY_TYPE_ALL;
765 0 : if ( ( nMode & BROWSEMODE_MODULES ) && !( nMode & BROWSEMODE_DIALOGS ) )
766 0 : eType = LIBRARY_TYPE_MODULE;
767 0 : else if ( !( nMode & BROWSEMODE_MODULES ) && ( nMode & BROWSEMODE_DIALOGS ) )
768 0 : eType = LIBRARY_TYPE_DIALOG;
769 0 : return eType;
770 : }
771 :
772 0 : OUString TreeListBox::GetRootEntryName( const ScriptDocument& rDocument, LibraryLocation eLocation ) const
773 : {
774 0 : return rDocument.getTitle( eLocation, GetLibraryType() );
775 : }
776 :
777 0 : void TreeListBox::GetRootEntryBitmaps( const ScriptDocument& rDocument, Image& rImage )
778 : {
779 : OSL_ENSURE( rDocument.isValid(), "TreeListBox::GetRootEntryBitmaps: illegal document!" );
780 0 : if ( !rDocument.isValid() )
781 0 : return;
782 :
783 0 : if ( rDocument.isDocument() )
784 : {
785 0 : OUString sFactoryURL;
786 0 : Reference<uno::XComponentContext> xContext( ::comphelper::getProcessComponentContext() );
787 0 : Reference< frame::XModuleManager2 > xModuleManager( frame::ModuleManager::create(xContext) );
788 : try
789 : {
790 0 : OUString sModule( xModuleManager->identify( rDocument.getDocument() ) );
791 0 : Reference< container::XNameAccess > xModuleConfig( xModuleManager, UNO_QUERY );
792 0 : if ( xModuleConfig.is() )
793 : {
794 0 : Sequence< beans::PropertyValue > aModuleDescr;
795 0 : xModuleConfig->getByName( sModule ) >>= aModuleDescr;
796 0 : sal_Int32 nCount = aModuleDescr.getLength();
797 0 : const beans::PropertyValue* pModuleDescr = aModuleDescr.getConstArray();
798 0 : for ( sal_Int32 i = 0; i < nCount; ++i )
799 : {
800 0 : if ( pModuleDescr[ i ].Name == "ooSetupFactoryEmptyDocumentURL" )
801 : {
802 0 : pModuleDescr[ i ].Value >>= sFactoryURL;
803 0 : break;
804 : }
805 0 : }
806 0 : }
807 : }
808 0 : catch( const Exception& )
809 : {
810 : DBG_UNHANDLED_EXCEPTION();
811 : }
812 :
813 0 : if ( !sFactoryURL.isEmpty() )
814 : {
815 0 : rImage = SvFileInformationManager::GetFileImage( INetURLObject( sFactoryURL ), false );
816 : }
817 : else
818 : {
819 : // default icon
820 0 : rImage = Image( IDEResId( RID_IMG_DOCUMENT ) );
821 0 : }
822 : }
823 : else
824 : {
825 0 : rImage = Image( IDEResId( RID_IMG_INSTALLATION ) );
826 : }
827 : }
828 :
829 0 : void TreeListBox::SetCurrentEntry (EntryDescriptor& rDesc)
830 : {
831 0 : SvTreeListEntry* pCurEntry = 0;
832 0 : EntryDescriptor aDesc = rDesc;
833 0 : if ( aDesc.GetType() == OBJ_TYPE_UNKNOWN )
834 : {
835 : aDesc = EntryDescriptor(
836 0 : ScriptDocument::getApplicationScriptDocument(),
837 : LIBRARY_LOCATION_USER, "Standard",
838 : OUString(), ".", OBJ_TYPE_UNKNOWN
839 0 : );
840 : }
841 0 : ScriptDocument aDocument = aDesc.GetDocument();
842 : OSL_ENSURE( aDocument.isValid(), "TreeListBox::SetCurrentEntry: invalid document!" );
843 0 : LibraryLocation eLocation = aDesc.GetLocation();
844 0 : SvTreeListEntry* pRootEntry = FindRootEntry( aDocument, eLocation );
845 0 : if ( pRootEntry )
846 : {
847 0 : pCurEntry = pRootEntry;
848 0 : OUString aLibName( aDesc.GetLibName() );
849 0 : if ( !aLibName.isEmpty() )
850 : {
851 0 : Expand( pRootEntry );
852 0 : SvTreeListEntry* pLibEntry = FindEntry( pRootEntry, aLibName, OBJ_TYPE_LIBRARY );
853 0 : if ( pLibEntry )
854 : {
855 0 : pCurEntry = pLibEntry;
856 0 : OUString aLibSubName( aDesc.GetLibSubName() );
857 0 : if( !aLibSubName.isEmpty() )
858 : {
859 0 : Expand( pLibEntry );
860 0 : SvTreeListEntry* pLibSubEntry = ImpFindEntry( pLibEntry, aLibSubName );
861 0 : if( pLibSubEntry )
862 : {
863 0 : pCurEntry = pLibSubEntry;
864 : }
865 : }
866 0 : OUString aName( aDesc.GetName() );
867 0 : if ( !aName.isEmpty() )
868 : {
869 0 : Expand( pCurEntry );
870 0 : EntryType eType = OBJ_TYPE_MODULE;
871 0 : if ( aDesc.GetType() == OBJ_TYPE_DIALOG )
872 0 : eType = OBJ_TYPE_DIALOG;
873 0 : SvTreeListEntry* pEntry = FindEntry( pCurEntry, aName, eType );
874 0 : if ( pEntry )
875 : {
876 0 : pCurEntry = pEntry;
877 0 : OUString aMethodName( aDesc.GetMethodName() );
878 0 : if ( !aMethodName.isEmpty() )
879 : {
880 0 : Expand( pEntry );
881 0 : SvTreeListEntry* pSubEntry = FindEntry( pEntry, aMethodName, OBJ_TYPE_METHOD );
882 0 : if ( pSubEntry )
883 : {
884 0 : pCurEntry = pSubEntry;
885 : }
886 : else
887 : {
888 0 : pSubEntry = FirstChild( pEntry );
889 0 : if ( pSubEntry )
890 0 : pCurEntry = pSubEntry;
891 : }
892 0 : }
893 : }
894 : else
895 : {
896 0 : pEntry = FirstChild( pLibEntry );
897 0 : if ( pEntry )
898 0 : pCurEntry = pEntry;
899 : }
900 0 : }
901 : }
902 : else
903 : {
904 0 : pLibEntry = FirstChild( pRootEntry );
905 0 : if ( pLibEntry )
906 0 : pCurEntry = pLibEntry;
907 : }
908 0 : }
909 : }
910 : else
911 : {
912 0 : pRootEntry = First();
913 0 : if ( pRootEntry )
914 0 : pCurEntry = pRootEntry;
915 : }
916 :
917 0 : SetCurEntry( pCurEntry );
918 0 : }
919 :
920 0 : void TreeListBox::MouseButtonDown( const MouseEvent& rMEvt )
921 : {
922 0 : SvTreeListBox::MouseButtonDown( rMEvt );
923 0 : if ( rMEvt.IsLeft() && ( rMEvt.GetClicks() == 2 ) )
924 : {
925 0 : EntryDescriptor aDesc = GetEntryDescriptor(GetCurEntry());
926 0 : switch (aDesc.GetType())
927 : {
928 : case OBJ_TYPE_METHOD:
929 : case OBJ_TYPE_MODULE:
930 : case OBJ_TYPE_DIALOG:
931 0 : if (SfxDispatcher* pDispatcher = GetDispatcher())
932 : {
933 : SbxItem aSbxItem(
934 0 : SID_BASICIDE_ARG_SBX, aDesc.GetDocument(),
935 0 : aDesc.GetLibName(), aDesc.GetName(), aDesc.GetMethodName(),
936 : ConvertType(aDesc.GetType())
937 0 : );
938 : pDispatcher->Execute(
939 : SID_BASICIDE_SHOWSBX,
940 : SFX_CALLMODE_SYNCHRON, &aSbxItem, 0L
941 0 : );
942 : }
943 0 : break;
944 :
945 : default:
946 0 : break;
947 0 : }
948 : }
949 0 : }
950 :
951 :
952 : } // namespace basctl
953 :
954 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|