1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 #ifndef SCRIPTDOCUMENT_HXX
29 #define SCRIPTDOCUMENT_HXX
30 
31 /** === begin UNO includes === **/
32 #include <com/sun/star/script/XLibraryContainer.hpp>
33 #include <com/sun/star/frame/XModel.hpp>
34 #include <com/sun/star/task/XStatusIndicator.hpp>
35 #include <com/sun/star/io/XInputStreamProvider.hpp>
36 /** === end UNO includes === **/
37 
38 #include <boost/shared_ptr.hpp>
39 #include <vector>
40 
41 class BasicManager;
42 class SfxListener;
43 
44 //........................................................................
45 namespace basctl
46 {
47 //........................................................................
48 
49     //====================================================================
50     //= LibraryContainerType
51     //====================================================================
52     enum LibraryContainerType
53     {
54         E_SCRIPTS,
55         E_DIALOGS
56     };
57 
58     enum LibraryLocation
59     {
60         LIBRARY_LOCATION_UNKNOWN,
61         LIBRARY_LOCATION_USER,
62         LIBRARY_LOCATION_SHARE,
63         LIBRARY_LOCATION_DOCUMENT
64     };
65 
66     enum LibraryType
67     {
68         LIBRARY_TYPE_UNKNOWN,
69         LIBRARY_TYPE_MODULE,
70         LIBRARY_TYPE_DIALOG,
71         LIBRARY_TYPE_ALL
72     };
73 
74     //====================================================================
75 	//= ScriptDocument
76 	//====================================================================
77     class ScriptDocument_Impl;
78 
79     class ScriptDocument;
80     typedef ::std::vector< ScriptDocument >  ScriptDocuments;
81 
82     /** encapsulates a document which contains Basic scripts and dialogs
83     */
84     class ScriptDocument
85 	{
86     private:
87         ::boost::shared_ptr< ScriptDocument_Impl > m_pImpl;
88 
89     private:
90         /** creates a ScriptDocument instance which operates on the application-wide
91             scripts and dialogs
92         */
93                     ScriptDocument();
94 
95     public:
96         enum SpecialDocument { NoDocument };
97         /** creates a ScriptDocument instance which does refers to neither the application-wide,
98             nor a specific real document's scripts.
99 
100             This constructor might come handy when you need some kind of uninitialized
101             ScriptDocument, which you do not want to operate on (yet), but initialize later
102             by assignment.
103 
104             <member>isValid</member> will return <FALSE/> for a ScriptDocument constructed
105             this way.
106         */
107         explicit    ScriptDocument( SpecialDocument _eType );
108 
109         /** creates a ScriptDocument instance which refers to a document given as
110             XModel
111 
112             @param _rxDocument
113                 the document. Must not be <NULL/>.
114         */
115         explicit    ScriptDocument( const ::com::sun::star::uno::Reference< ::com::sun::star::frame::XModel >& _rxDocument );
116 
117         /// copy constructor
118                     ScriptDocument( const ScriptDocument& _rSource );
119 
120         /// destructor
121                     ~ScriptDocument();
122 
123         /** returns a reference to a shared ScriptDocument instance which
124             operates on the application-wide scripts and dialogs
125         */
126         static const ScriptDocument&
127                     getApplicationScriptDocument();
128 
129         /** returns a (newly created) ScriptDocument instance for the document to
130             which a given BasicManager belongs
131 
132             If the basic manager is the application's basic manager, then the (shared)
133             ScriptDocument instance which is responsible for the application is returned.
134 
135             @see getApplicationScriptDocument
136         */
137         static ScriptDocument
138                     getDocumentForBasicManager( const BasicManager* _pManager );
139 
140         /** returns a (newly created) ScriptDocument instance for the document
141             with a given caption or URL
142 
143             If there is no document with the given caption, then the (shared)
144             ScriptDocument instance which is responsible for the application is returned.
145 
146             @see getApplicationScriptDocument
147         */
148         static ScriptDocument
149                     getDocumentWithURLOrCaption( const ::rtl::OUString& _rUrlOrCaption );
150 
151         /** operation mode for getAllScriptDocuments
152         */
153         enum ScriptDocumentList
154         {
155             /** all ScriptDocuments, including the dedicated one which represents
156                 the application-wide scripts/dialogs.
157             */
158             AllWithApplication,
159             /** real documents only
160             */
161             DocumentsOnly,
162             /** real documents only, sorted lexicographically by their title (using the sys locale's default
163                 collator)
164             */
165             DocumentsSorted
166         };
167 
168         /** returns the set of ScriptDocument instances, one for each open document which
169             contains Basic/Dialog containers; plus an additional instance for
170             the application, if desired
171 
172             Documents which are not visible - i.e. do not have a visible frame.
173 
174             @param _bIncludingApplication
175                 <TRUE/> if the application-wide scripts/dialogs should also be represented
176                 by a ScriptDocument
177         */
178         static ScriptDocuments
179                     getAllScriptDocuments( ScriptDocumentList _eListType );
180 
181         // comparison
182                 bool operator==( const ScriptDocument& _rhs ) const;
183         inline  bool operator!=( const ScriptDocument& _rhs ) const { return !( *this == _rhs ); }
184 
185         /// retrieves a (pretty simple) hash code for the document
186         sal_Int32   hashCode() const;
187 
188         /** determines whether the document is actually able to contain Basic/Dialog libraries
189 
190             Note that validity does not automatically imply the document can be used for active
191             work. Instead, it is possible the document is closed already (or being closed currently).
192             In this case, isValid will return <TRUE/>, but isAlive will return <FALSE/>.
193 
194             @return
195                 <TRUE/> if the instance refers to a document which contains Basic/Dialog libraries,
196                 or the application as a whole, <FALSE/> otherwise.
197 
198             @see isAlive
199         */
200         bool        isValid() const;
201 
202         /** determines whether the document instance is alive
203 
204             If the instance is not valid, <FALSE/> is returned.
205 
206             If the instance refers to a real document, which is already closed, or just being closed,
207             the method returns <FALSE/>.
208 
209             If the instance refers to the application, <TRUE/> is returned.
210 
211             @see isValid
212         */
213         bool        isAlive() const;
214 
215         bool        isInVBAMode() const;
216         /// returns the BasicManager associated with this instance
217         BasicManager*
218                     getBasicManager() const;
219 
220         /** returns the UNO component representing the document which the instance operates on
221 
222             Must not be used when the instance operates on the application-wide
223             Basic/Dialog libraries.
224         */
225         ::com::sun::star::uno::Reference< ::com::sun::star::frame::XModel >
226                     getDocument() const;
227 
228         /** returns the UNO component representing the document which the instance operates on
229 
230             May be used when the instance operates on the application-wide
231             Basic/Dialog libraries, in this case it returns <NULL/>.
232         */
233         ::com::sun::star::uno::Reference< ::com::sun::star::frame::XModel >
234                     getDocumentOrNull() const;
235 
236         /** returns the Basic or Dialog library container of the document
237 
238             If the document is not valid, <NULL/> is returned.
239         */
240         ::com::sun::star::uno::Reference< ::com::sun::star::script::XLibraryContainer >
241                     getLibraryContainer( LibraryContainerType _eType ) const;
242 
243         /** determines whether there exists a library of the given type, with the given name
244         */
245         bool        hasLibrary( LibraryContainerType _eType, const ::rtl::OUString& _rLibName ) const;
246 
247         /** returns a script or dialog library given by name
248 
249             @param _eType
250                 the type of library to load
251             @param _rLibName
252                 the name of the script library
253             @param _bLoadLibrary
254                 <TRUE/> if and only if the library should be loaded.
255 
256             @throws NoSuchElementException
257                 if there is no script library with the given name
258         */
259 	    ::com::sun::star::uno::Reference< ::com::sun::star::container::XNameContainer >
260                     getLibrary( LibraryContainerType _eType, const ::rtl::OUString& _rLibName, bool _bLoadLibrary ) const
261                         SAL_THROW((::com::sun::star::container::NoSuchElementException));
262 
263         /** creates a script or dialog library in the document, or returns an existing one
264 
265             If <code>_rLibName</code> denotes an existing library which does not need to be created,
266             then this library will automatically be loaded, and then returned.
267         */
268         ::com::sun::star::uno::Reference< ::com::sun::star::container::XNameContainer >
269                     getOrCreateLibrary( LibraryContainerType _eType, const ::rtl::OUString& _rLibName ) const;
270 
271         /** returns the names of the modules in a given script or dialog library of the document
272         */
273 	    ::com::sun::star::uno::Sequence< ::rtl::OUString >
274                     getObjectNames( LibraryContainerType _eType, const ::rtl::OUString& _rLibName ) const;
275 
276         /** retrieves a name for a newly to be created module or dialog
277         */
278         ::rtl::OUString
279                     createObjectName( LibraryContainerType _eType, const ::rtl::OUString& _rLibName ) const;
280 
281         /** loads a script or dialog library given by name, if there is such a library
282         */
283         void        loadLibraryIfExists( LibraryContainerType _eType, const ::rtl::OUString& _rLibrary );
284 
285         /// retrieves the (combined) names of all script and dialog libraries
286         ::com::sun::star::uno::Sequence< ::rtl::OUString >
287                     getLibraryNames() const;
288 
289         /** removes a given script module from the document
290 
291             @return
292                 <TRUE/> if and only if the removal was successful. When <FALSE/> is returned,
293                 this will reported as assertion in a non-product build.
294         */
295         bool        removeModule( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rModuleName ) const;
296 
297         /** creates a module with the given name in the given library
298             @param  _rLibName
299                 the library name
300             @param  _rModName
301                 the name of the to-be-created module
302             @param  _bCreateMain
303                 determines whether or not a function Main should be created
304             @param  _out_rNewModuleCode
305                 the source code of the newly created module
306             @return
307                 <TRUE/> if and only if the creation was successful
308         */
309         bool        createModule( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rModName, bool _bCreateMain, ::rtl::OUString& _out_rNewModuleCode ) const;
310 
311         /** inserts a given piece as code as module
312             @param  _rLibName
313                 the name of the library to insert the module into. If a library with this name does
314                 not yet exist, it will be created.
315             @param  _rModName
316                 the name of the module to insert the code as. Must denote a name which is not yet
317                 used in the module library.
318             @param  _rModuleCode
319                 the code of the new module
320             @return
321                 <TRUE/> if and only if the insertion was successful.
322         */
323         bool        insertModule( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rModName, const ::rtl::OUString& _rModuleCode ) const;
324 
325         /** updates a given module with new code
326             @param  _rLibName
327                 the name of the library the modules lives in. Must denote an existing module library.
328             @param  _rModName
329                 the name of the module to update. Must denote an existing module in the given library.
330             @param  _rModuleCode
331                 the new module code.
332             @return
333                 <TRUE/> if and only if the insertion was successful.
334         */
335         bool        updateModule( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rModName, const ::rtl::OUString& _rModuleCode ) const;
336 
337         /// determines whether a module with the given name exists in the given library
338         bool        hasModule( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rModName ) const;
339 
340         /** retrieves a module's source
341             @param  _rLibName
342                 the library name where the module is located
343             @param  _rModName
344                 the module name
345             @param  _out_rModuleSource
346                 takes the module's source upon successful return
347             @return
348                 <TRUE/> if and only if the code could be successfully retrieved, <FALSE/> otherwise
349         */
350         bool        getModule( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rModName, ::rtl::OUString& _rModuleSource ) const;
351 
352         /** renames a module
353             @param  _rLibName
354                 the library where the module lives in. Must denote an existing library.
355             @param  _rOldName
356                 the old module name. Must denote an existing module.
357             @param  _rNewName
358                 the new module name
359             @return
360                 <TRUE/> if and only if renaming was successful.
361         */
362         bool        renameModule( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rOldName, const ::rtl::OUString& _rNewName ) const;
363 
364         /** removes a given dialog from the document
365 
366             @return
367                 <TRUE/> if and only if the removal was successful. When <FALSE/> is returned,
368                 this will reported as assertion in a non-product build.
369         */
370         bool        removeDialog( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rDialogName ) const;
371 
372         /// determines whether a dialog with the given name exists in the given library
373         bool        hasDialog( const ::rtl::OUString& _rLibName, const ::rtl::OUString& _rDialogName ) const;
374 
375         /** retrieves a dialog
376             @param  _rLibName
377                 the library name where the module is located
378             @param  _rDialogName
379                 the dialog's name
380             @param  _out_rDialogSource
381                 takes the provider for the dialog's desription, upon successful return
382             @return
383                 <TRUE/> if and only if the dialog could be successfully retrieved, <FALSE/> otherwise
384         */
385         bool        getDialog(
386                         const ::rtl::OUString& _rLibName,
387                         const ::rtl::OUString& _rDialogName,
388                         ::com::sun::star::uno::Reference< ::com::sun::star::io::XInputStreamProvider >& _out_rDialogProvider
389                     ) const;
390 
391         /** renames a dialog
392             @param  _rLibName
393                 the library where the dialog lives in. Must denote an existing library.
394             @param  _rOldName
395                 the old dialog name. Must denote an existing dialog.
396             @param  _rNewName
397                 the new dialog name
398             @param _rxExistingDialogModel
399                 the existing model of the dialog, if already loaded in the IDE
400             @return
401                 <TRUE/> if and only if renaming was successful.
402         */
403         bool        renameDialog(
404                         const ::rtl::OUString& _rLibName,
405                         const ::rtl::OUString& _rOldName,
406                         const ::rtl::OUString& _rNewName,
407                         const ::com::sun::star::uno::Reference< ::com::sun::star::container::XNameContainer >& _rxExistingDialogModel
408                     ) const;
409 
410         /** create a dialog
411             @param  _rLibName
412                 the library name where the module is located
413             @param  _rDialogName
414                 the dialog's name
415             @param  _out_rDialogSource
416                 takes the provider for the dialog's desription, upon successful return
417             @return
418                 <TRUE/> if and only if the dialog could be successfully retrieved, <FALSE/> otherwise
419         */
420         bool        createDialog(
421                         const ::rtl::OUString& _rLibName,
422                         const ::rtl::OUString& _rDialogName,
423                         ::com::sun::star::uno::Reference< ::com::sun::star::io::XInputStreamProvider >& _out_rDialogProvider
424                     ) const;
425 
426         /** inserts a given dialog into a given library
427 
428             @param  _rLibName
429                 the name of the library to insert the dialog into. If a library with this name does
430                 not yet exist, it will be created.
431             @param  _rModName
432                 the name of the dialog to insert. Must denote a name which is not yet
433                 used in the dialog library.
434             @param  _rDialogProvider
435                 the provider of the dialog's description
436             @return
437                 <TRUE/> if and only if the insertion was successful.
438         */
439         bool        insertDialog(
440                         const ::rtl::OUString& _rLibName,
441                         const ::rtl::OUString& _rDialogName,
442                         const ::com::sun::star::uno::Reference< ::com::sun::star::io::XInputStreamProvider >& _rDialogProvider
443                     ) const;
444 
445         /** determines whether the document is read-only
446 
447             cannot be called if the document operates on the application-wide scripts
448         */
449         bool        isReadOnly() const;
450 
451         /** determines whether the ScriptDocument instance operates on the whole application,
452             as opposed to a real document
453         */
454         bool        isApplication() const;
455 
456         /** determines whether the ScriptDocument instance operates on a real document,
457             as opposed to the whole application
458         */
459         bool        isDocument() const { return isValid() && !isApplication(); }
460 
461         /** marks the document as modified
462             @precond
463                 the instance operates on a real document, not on the application
464             @see isDocument
465         */
466         void        setDocumentModified() const;
467 
468         /** determines whether the document is modified
469             @precond
470                 the instance operates on a real document, not on the application
471             @see isDocument
472         */
473         bool        isDocumentModified() const;
474 
475         /** saves the document, if the instance refers to a real document
476             @precond
477                 <code>isApplication</code> returns <FALSE/>
478         */
479         bool        saveDocument(
480                         const ::com::sun::star::uno::Reference< ::com::sun::star::task::XStatusIndicator >& _rxStatusIndicator
481                     ) const;
482 
483         /// returns the location of a library given by name
484         LibraryLocation
485                     getLibraryLocation( const ::rtl::OUString& _rLibName ) const;
486 
487         /// returns the title for the document
488         ::rtl::OUString
489                     getTitle( LibraryLocation _eLocation, LibraryType _eType = LIBRARY_TYPE_ALL ) const;
490 
491         /** returns the title of the document
492 
493             to be used for valid documents only
494         */
495         ::rtl::OUString
496                     getTitle() const;
497 
498         /** returns the URL of the document
499 
500             to be used for valid documents only
501         */
502         ::rtl::OUString
503                     getURL() const;
504 
505         /** determines whether the document is currently the one-and-only application-wide active document
506         */
507         bool        isActive() const;
508 
509         /** determines whether macro execution for this document is allowed
510 
511             only to be called for real documents (->isDocument)
512         */
513         bool    allowMacros() const;
514 	};
515 
516 //........................................................................
517 } // namespace basctl
518 //........................................................................
519 
520 // convenience ... better would be all classes in the project are in
521 // the same namespace ...
522 using ::basctl::ScriptDocument;
523 using ::basctl::ScriptDocuments;
524 using ::basctl::E_SCRIPTS;
525 using ::basctl::E_DIALOGS;
526 using ::basctl::LibraryLocation;
527 using ::basctl::LIBRARY_LOCATION_UNKNOWN;
528 using ::basctl::LIBRARY_LOCATION_USER;
529 using ::basctl::LIBRARY_LOCATION_SHARE;
530 using ::basctl::LIBRARY_LOCATION_DOCUMENT;
531 using ::basctl::LibraryType;
532 using ::basctl::LIBRARY_TYPE_UNKNOWN;
533 using ::basctl::LIBRARY_TYPE_MODULE;
534 using ::basctl::LIBRARY_TYPE_DIALOG;
535 using ::basctl::LIBRARY_TYPE_ALL;
536 
537 #endif // SCRIPTDOCUMENT_HXX
538