xref: /trunk/main/dbaccess/source/ui/app/AppController.cxx (revision cdf0e10c4e3984b49a9502b011690b615761d4a3)
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 // MARKER(update_precomp.py): autogen include statement, do not remove
29 #include "precompiled_dbaccess.hxx"
30 
31 #include "AppController.hxx"
32 #include "dbustrings.hrc"
33 #include "advancedsettingsdlg.hxx"
34 #include "subcomponentmanager.hxx"
35 #include "closeveto.hxx"
36 
37 /** === begin UNO includes === **/
38 #include <com/sun/star/beans/NamedValue.hpp>
39 #include <com/sun/star/container/XChild.hpp>
40 #include <com/sun/star/container/XContainer.hpp>
41 #include <com/sun/star/container/XContentEnumerationAccess.hpp>
42 #include <com/sun/star/container/XHierarchicalNameAccess.hpp>
43 #include <com/sun/star/container/XHierarchicalNameContainer.hpp>
44 #include <com/sun/star/container/XNameContainer.hpp>
45 #include <com/sun/star/frame/FrameSearchFlag.hpp>
46 #include <com/sun/star/frame/XStorable.hpp>
47 #include <com/sun/star/sdb/CommandType.hpp>
48 #include <com/sun/star/sdb/SQLContext.hpp>
49 #include <com/sun/star/sdb/XBookmarksSupplier.hpp>
50 #include <com/sun/star/sdb/XOfficeDatabaseDocument.hpp>
51 #include <com/sun/star/sdb/XQueryDefinitionsSupplier.hpp>
52 #include <com/sun/star/sdbc/XDataSource.hpp>
53 #include <com/sun/star/sdbcx/XAlterView.hpp>
54 #include <com/sun/star/sdbcx/XAppend.hpp>
55 #include <com/sun/star/sdbcx/XRename.hpp>
56 #include <com/sun/star/sdbcx/XTablesSupplier.hpp>
57 #include <com/sun/star/sdbcx/XViewsSupplier.hpp>
58 #include <com/sun/star/ui/dialogs/TemplateDescription.hpp>
59 #include <com/sun/star/uno/XNamingService.hpp>
60 #include <com/sun/star/util/XFlushable.hpp>
61 #include <com/sun/star/util/XModifiable.hpp>
62 #include <com/sun/star/util/XModifyBroadcaster.hpp>
63 #include <com/sun/star/util/XNumberFormatter.hpp>
64 #include <com/sun/star/ui/dialogs/XExecutableDialog.hpp>
65 #include <com/sun/star/document/XEmbeddedScripts.hpp>
66 #include <com/sun/star/frame/XModel2.hpp>
67 #include <com/sun/star/container/XHierarchicalNameContainer.hpp>
68 #include <com/sun/star/util/XModifyBroadcaster.hpp>
69 #include <com/sun/star/util/XModifiable.hpp>
70 #include <com/sun/star/frame/FrameSearchFlag.hpp>
71 #include <com/sun/star/util/XFlushable.hpp>
72 #include "com/sun/star/ui/dialogs/TemplateDescription.hpp"
73 #include "com/sun/star/beans/NamedValue.hpp"
74 #include <com/sun/star/awt/XTopWindow.hpp>
75 #include <com/sun/star/task/XInteractionHandler.hpp>
76 #include <com/sun/star/sdb/application/DatabaseObject.hpp>
77 #include <com/sun/star/sdb/application/DatabaseObjectContainer.hpp>
78 #include <com/sun/star/document/XDocumentEventBroadcaster.hpp>
79 #include <com/sun/star/container/XHierarchicalName.hpp>
80 /** === end UNO includes === **/
81 #include <tools/debug.hxx>
82 #include <tools/diagnose_ex.h>
83 #include <tools/string.hxx>
84 
85 #include <svl/urihelper.hxx>
86 #include <svl/filenotation.hxx>
87 #include <svtools/svtreebx.hxx>
88 #include <svtools/transfer.hxx>
89 #include <svtools/cliplistener.hxx>
90 #include <svtools/svlbitm.hxx>
91 #include <svtools/insdlg.hxx>
92 
93 #include <comphelper/sequence.hxx>
94 #include <comphelper/uno3.hxx>
95 #include <comphelper/string.hxx>
96 #include <comphelper/types.hxx>
97 #include <comphelper/interaction.hxx>
98 #include <comphelper/componentcontext.hxx>
99 
100 #include <vcl/msgbox.hxx>
101 #include <vcl/stdtext.hxx>
102 #include <vcl/svapp.hxx>
103 #include <vcl/menu.hxx>
104 #include <vcl/lstbox.hxx>
105 
106 #include <unotools/pathoptions.hxx>
107 #include <unotools/tempfile.hxx>
108 #include <unotools/internaloptions.hxx>
109 #include <unotools/moduleoptions.hxx>
110 #include <unotools/historyoptions.hxx>
111 
112 #include <sfx2/mailmodelapi.hxx>
113 #include <sfx2/filedlghelper.hxx>
114 #include <sfx2/docfilt.hxx>
115 #include <sfx2/QuerySaveDocument.hxx>
116 
117 #include <cppuhelper/typeprovider.hxx>
118 #include <cppuhelper/exc_hlp.hxx>
119 
120 #include <connectivity/dbtools.hxx>
121 #include <connectivity/dbexception.hxx>
122 
123 #include <svx/dbaexchange.hxx>
124 #include <svx/dbaobjectex.hxx>
125 #include <svx/svxdlg.hxx>
126 
127 #include <vos/mutex.hxx>
128 #include "AppView.hxx"
129 #include "browserids.hxx"
130 #include "dbu_reghelper.hxx"
131 #include "dbu_app.hrc"
132 #include "defaultobjectnamecheck.hxx"
133 #include "databaseobjectview.hxx"
134 #include "listviewitems.hxx"
135 #include "AppDetailView.hxx"
136 #include "linkeddocuments.hxx"
137 #include "sqlmessage.hxx"
138 #include "UITools.hxx"
139 #include "dsntypes.hxx"
140 #include "dbaccess_helpid.hrc"
141 #include "dlgsave.hxx"
142 #include "dbaccess_slotid.hrc"
143 
144 #include <algorithm>
145 #include <functional>
146 
147 #include <boost/noncopyable.hpp>
148 
149 extern "C" void SAL_CALL createRegistryInfo_ODBApplication()
150 {
151     static ::dbaui::OMultiInstanceAutoRegistration< ::dbaui::OApplicationController > aAutoRegistration;
152 }
153 //........................................................................
154 namespace dbaui
155 {
156 //........................................................................
157 using namespace ::dbtools;
158 using namespace ::svx;
159 using namespace ::com::sun::star;
160 using namespace ::com::sun::star::uno;
161 using namespace ::com::sun::star::ucb;
162 using namespace ::com::sun::star::view;
163 using namespace ::com::sun::star::util;
164 using namespace ::com::sun::star::beans;
165 using namespace ::com::sun::star::lang;
166 using namespace ::com::sun::star::frame;
167 using namespace ::com::sun::star::container;
168 using namespace ::com::sun::star::sdb;
169 using namespace ::com::sun::star::sdbc;
170 using namespace ::com::sun::star::sdbcx;
171 using namespace ::com::sun::star::datatransfer;
172 using namespace ::com::sun::star::ui::dialogs;
173 using namespace ::com::sun::star::task;
174 using ::com::sun::star::document::XEmbeddedScripts;
175 using ::com::sun::star::document::XDocumentEventBroadcaster;
176 using ::com::sun::star::document::DocumentEvent;
177 using ::com::sun::star::sdb::application::NamedDatabaseObject;
178 
179 namespace DatabaseObject = ::com::sun::star::sdb::application::DatabaseObject;
180 namespace DatabaseObjectContainer = ::com::sun::star::sdb::application::DatabaseObjectContainer;
181 
182 //------------------------------------------------------------------------------
183 ::rtl::OUString SAL_CALL OApplicationController::getImplementationName() throw( RuntimeException )
184 {
185     return getImplementationName_Static();
186 }
187 
188 //------------------------------------------------------------------------------
189 ::rtl::OUString OApplicationController::getImplementationName_Static() throw( RuntimeException )
190 {
191     return ::rtl::OUString(SERVICE_SDB_APPLICATIONCONTROLLER);
192 }
193 //------------------------------------------------------------------------------
194 Sequence< ::rtl::OUString> OApplicationController::getSupportedServiceNames_Static(void) throw( RuntimeException )
195 {
196     Sequence< ::rtl::OUString> aSupported(1);
197     aSupported.getArray()[0] = ::rtl::OUString::createFromAscii("com.sun.star.sdb.application.DefaultViewController");
198     return aSupported;
199 }
200 //-------------------------------------------------------------------------
201 Sequence< ::rtl::OUString> SAL_CALL OApplicationController::getSupportedServiceNames() throw(RuntimeException)
202 {
203     return getSupportedServiceNames_Static();
204 }
205 // -------------------------------------------------------------------------
206 Reference< XInterface > SAL_CALL OApplicationController::Create(const Reference<XMultiServiceFactory >& _rxFactory)
207 {
208     return *(new OApplicationController(_rxFactory));
209 }
210 // -----------------------------------------------------------------------------
211 
212 struct XContainerFunctor : public ::std::unary_function< OApplicationController::TContainerVector::value_type , bool>
213 {
214     Reference<XContainerListener> m_xContainerListener;
215     XContainerFunctor( const Reference<XContainerListener>& _xContainerListener)
216         : m_xContainerListener(_xContainerListener){}
217 
218     bool operator() (const OApplicationController::TContainerVector::value_type& lhs) const
219     {
220         if ( lhs.is() )
221             lhs->removeContainerListener(m_xContainerListener);
222         return true;
223     }
224 };
225 
226 //====================================================================
227 //= OApplicationController
228 //====================================================================
229 class SelectionNotifier : public ::boost::noncopyable
230 {
231 private:
232     ::cppu::OInterfaceContainerHelper   m_aSelectionListeners;
233     ::cppu::OWeakObject&                m_rContext;
234     sal_Int32                           m_nSelectionNestingLevel;
235 
236 public:
237     SelectionNotifier( ::osl::Mutex& _rMutex, ::cppu::OWeakObject& _rContext )
238         :m_aSelectionListeners( _rMutex )
239         ,m_rContext( _rContext )
240         ,m_nSelectionNestingLevel( 0 )
241     {
242     }
243 
244     void addListener( const Reference< XSelectionChangeListener >& _Listener )
245     {
246         m_aSelectionListeners.addInterface( _Listener );
247     }
248 
249     void removeListener( const Reference< XSelectionChangeListener >& _Listener )
250     {
251         m_aSelectionListeners.removeInterface( _Listener );
252     }
253 
254     void disposing()
255     {
256         EventObject aEvent( m_rContext );
257         m_aSelectionListeners.disposeAndClear( aEvent );
258     }
259 
260     ~SelectionNotifier()
261     {
262     }
263 
264     struct SelectionGuardAccess { friend class SelectionGuard; private: SelectionGuardAccess() { }  };
265 
266     /** enters a block which modifies the selection of our owner.
267 
268         Can be called multiple times, the only important thing is to call leaveSelection
269         equally often.
270     */
271     void    enterSelection( SelectionGuardAccess )
272     {
273         ++m_nSelectionNestingLevel;
274     }
275 
276     /** leaves a block which modifies the selection of our owner
277 
278         Must be paired with enterSelection calls.
279 
280         When the last block is left, i.e. the last leaveSelection call is made on the current stack,
281         then our SelectionChangeListeners are notified
282     */
283     void    leaveSelection( SelectionGuardAccess )
284     {
285         if ( --m_nSelectionNestingLevel == 0 )
286         {
287             EventObject aEvent( m_rContext );
288             m_aSelectionListeners.notifyEach( &XSelectionChangeListener::selectionChanged, aEvent );
289         }
290     }
291 };
292 
293 class SelectionGuard : public ::boost::noncopyable
294 {
295 public:
296     SelectionGuard( SelectionNotifier& _rNotifier )
297         :m_rNotifier( _rNotifier )
298     {
299         m_rNotifier.enterSelection( SelectionNotifier::SelectionGuardAccess() );
300     }
301 
302     ~SelectionGuard()
303     {
304         m_rNotifier.leaveSelection( SelectionNotifier::SelectionGuardAccess() );
305     }
306 
307 private:
308     SelectionNotifier&  m_rNotifier;
309 };
310 
311 //====================================================================
312 //= OApplicationController
313 //====================================================================
314 DBG_NAME(OApplicationController)
315 //--------------------------------------------------------------------
316 OApplicationController::OApplicationController(const Reference< XMultiServiceFactory >& _rxORB)
317     :OApplicationController_CBASE( _rxORB )
318     ,m_aContextMenuInterceptors( getMutex() )
319     ,m_pSubComponentManager( new SubComponentManager( *this, getSharedMutex() ) )
320     ,m_aTypeCollection(_rxORB)
321     ,m_aTableCopyHelper(this)
322     ,m_pClipbordNotifier(NULL)
323     ,m_nAsyncDrop(0)
324     ,m_aControllerConnectedEvent( LINK( this, OApplicationController, OnFirstControllerConnected ) )
325     ,m_aSelectContainerEvent( LINK( this, OApplicationController, OnSelectContainer ) )
326     ,m_ePreviewMode(E_PREVIEWNONE)
327     ,m_eCurrentType(E_NONE)
328     ,m_bNeedToReconnect(sal_False)
329     ,m_bSuspended( sal_False )
330     ,m_pSelectionNotifier( new SelectionNotifier( getMutex(), *this ) )
331 {
332     DBG_CTOR(OApplicationController,NULL);
333 }
334 //------------------------------------------------------------------------------
335 OApplicationController::~OApplicationController()
336 {
337     if ( !rBHelper.bDisposed && !rBHelper.bInDispose )
338     {
339         OSL_ENSURE(0,"Please check who doesn't dispose this component!");
340         // increment ref count to prevent double call of Dtor
341         osl_incrementInterlockedCount( &m_refCount );
342         dispose();
343     }
344     ::std::auto_ptr< Window> aTemp( getView() );
345     clearView();
346 
347     DBG_DTOR(OApplicationController,NULL);
348 }
349 //--------------------------------------------------------------------
350 IMPLEMENT_FORWARD_XTYPEPROVIDER2(OApplicationController,OApplicationController_CBASE,OApplicationController_Base)
351 IMPLEMENT_FORWARD_XINTERFACE2(OApplicationController,OApplicationController_CBASE,OApplicationController_Base)
352 // -----------------------------------------------------------------------------
353 void OApplicationController::disconnect()
354 {
355     if ( m_xDataSourceConnection.is() )
356         stopConnectionListening( m_xDataSourceConnection );
357 
358     try
359     {
360         // temporary (hopefully!) hack for #i55274#
361         Reference< XFlushable > xFlush( m_xDataSourceConnection, UNO_QUERY );
362         if ( xFlush.is() && m_xMetaData.is() && !m_xMetaData->isReadOnly() )
363             xFlush->flush();
364     }
365     catch( const Exception& )
366     {
367         DBG_UNHANDLED_EXCEPTION();
368     }
369 
370     m_xDataSourceConnection.clear();
371     m_xMetaData.clear();
372 
373     InvalidateAll();
374 }
375 
376 //--------------------------------------------------------------------
377 void SAL_CALL OApplicationController::disposing()
378 {
379     m_aControllerConnectedEvent.CancelCall();
380 
381     ::std::for_each(m_aCurrentContainers.begin(),m_aCurrentContainers.end(),XContainerFunctor(this));
382     m_aCurrentContainers.clear();
383     m_pSubComponentManager->disposing();
384     m_pSelectionNotifier->disposing();
385 
386     if ( getView() )
387     {
388         getContainer()->showPreview(NULL);
389         m_pClipbordNotifier->ClearCallbackLink();
390         m_pClipbordNotifier->AddRemoveListener( getView(), sal_False );
391         m_pClipbordNotifier->release();
392         m_pClipbordNotifier = NULL;
393     }
394 
395     disconnect();
396     try
397     {
398         Reference < XFrame > xFrame;
399         attachFrame( xFrame );
400 
401         if ( m_xDataSource.is() )
402         {
403             m_xDataSource->removePropertyChangeListener(::rtl::OUString(), this);
404             m_xDataSource->removePropertyChangeListener(PROPERTY_INFO, this);
405             m_xDataSource->removePropertyChangeListener(PROPERTY_URL, this);
406             m_xDataSource->removePropertyChangeListener(PROPERTY_ISPASSWORDREQUIRED, this);
407             m_xDataSource->removePropertyChangeListener(PROPERTY_LAYOUTINFORMATION, this);
408             m_xDataSource->removePropertyChangeListener(PROPERTY_SUPPRESSVERSIONCL, this);
409             m_xDataSource->removePropertyChangeListener(PROPERTY_TABLEFILTER, this);
410             m_xDataSource->removePropertyChangeListener(PROPERTY_TABLETYPEFILTER, this);
411             m_xDataSource->removePropertyChangeListener(PROPERTY_USER, this);
412             // otherwise we may delete our datasource twice
413             Reference<XPropertySet> xProp = m_xDataSource;
414             m_xDataSource = NULL;
415         }
416 
417         Reference< XModifyBroadcaster > xBroadcaster( m_xModel, UNO_QUERY );
418         if ( xBroadcaster.is() )
419             xBroadcaster->removeModifyListener(static_cast<XModifyListener*>(this));
420 
421         if ( m_xModel.is() )
422         {
423             ::rtl::OUString sUrl = m_xModel->getURL();
424             if ( sUrl.getLength() )
425             {
426                 ::comphelper::NamedValueCollection aArgs( m_xModel->getArgs() );
427                 if ( true == aArgs.getOrDefault( "PickListEntry", true ) )
428                 {
429                     ::rtl::OUString     aFilter;
430                     INetURLObject       aURL( m_xModel->getURL() );
431                     const SfxFilter* pFilter = getStandardDatabaseFilter();
432                     if ( pFilter )
433                         aFilter = pFilter->GetFilterName();
434 
435                     // add to svtool history options
436                     SvtHistoryOptions().AppendItem( ePICKLIST,
437                             aURL.GetURLNoPass( INetURLObject::NO_DECODE ),
438                             aFilter,
439                             getStrippedDatabaseName(),
440                             ::rtl::OUString() );
441                 }
442             }
443 
444             m_xModel->disconnectController( this );
445 
446             m_xModel.clear();
447         }
448     }
449     catch(Exception)
450     {
451         DBG_UNHANDLED_EXCEPTION();
452     }
453 
454     clearView();
455     OApplicationController_CBASE::disposing(); // here the m_refCount must be equal 5
456 }
457 
458 //--------------------------------------------------------------------
459 sal_Bool OApplicationController::Construct(Window* _pParent)
460 {
461     setView( * new OApplicationView( _pParent, getORB(), *this, m_ePreviewMode ) );
462     getView()->SetUniqueId(UID_APP_VIEW);
463 
464     // late construction
465     sal_Bool bSuccess = sal_False;
466     try
467     {
468         getContainer()->Construct();
469         bSuccess = sal_True;
470     }
471     catch(SQLException&)
472     {
473     }
474     catch(Exception&)
475     {
476         DBG_ERROR("OApplicationController::Construct : the construction of UnoDataBrowserView failed !");
477     }
478 
479     if ( !bSuccess )
480     {
481         ::std::auto_ptr< Window> aTemp( getView() );
482         clearView();
483         return sal_False;
484     }
485 
486     // now that we have a view we can create the clipboard listener
487     m_aSystemClipboard = TransferableDataHelper::CreateFromSystemClipboard( getView() );
488     m_aSystemClipboard.StartClipboardListening( );
489 
490     m_pClipbordNotifier = new TransferableClipboardListener( LINK( this, OApplicationController, OnClipboardChanged ) );
491     m_pClipbordNotifier->acquire();
492     m_pClipbordNotifier->AddRemoveListener( getView(), sal_True );
493 
494     OApplicationController_CBASE::Construct( _pParent );
495     getView()->Show();
496 
497     return sal_True;
498 }
499 
500 //--------------------------------------------------------------------
501 void SAL_CALL OApplicationController::disposing(const EventObject& _rSource) throw( RuntimeException )
502 {
503     ::osl::MutexGuard aGuard( getMutex() );
504     Reference<XConnection> xCon(_rSource.Source, UNO_QUERY);
505     if ( xCon.is() )
506     {
507         DBG_ASSERT( m_xDataSourceConnection == xCon,
508             "OApplicationController::disposing: which connection does this come from?" );
509 
510         if ( getContainer() && getContainer()->getElementType() == E_TABLE )
511             getContainer()->clearPages();
512         if ( m_xDataSourceConnection == xCon )
513         {
514             m_xMetaData.clear();
515             m_xDataSourceConnection.clear();
516         }
517     }
518     else if ( _rSource.Source == m_xModel )
519     {
520         m_xModel.clear();
521     }
522     else if ( _rSource.Source == m_xDataSource )
523     {
524         m_xDataSource = NULL;
525     }
526     else
527     {
528         Reference<XContainer> xContainer( _rSource.Source, UNO_QUERY );
529         if ( xContainer.is() )
530         {
531             TContainerVector::iterator aFind = ::std::find(m_aCurrentContainers.begin(),m_aCurrentContainers.end(),xContainer);
532             if ( aFind != m_aCurrentContainers.end() )
533                 m_aCurrentContainers.erase(aFind);
534         }
535         OApplicationController_CBASE::disposing( _rSource );
536     }
537 }
538 //--------------------------------------------------------------------
539 sal_Bool SAL_CALL OApplicationController::suspend(sal_Bool bSuspend) throw( RuntimeException )
540 {
541     // notify the OnPrepareViewClosing event (before locking any mutex)
542     Reference< XDocumentEventBroadcaster > xBroadcaster( m_xModel, UNO_QUERY );
543     if ( xBroadcaster.is() )
544     {
545         xBroadcaster->notifyDocumentEvent(
546             ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "OnPrepareViewClosing" ) ),
547             this,
548             Any()
549         );
550     }
551 
552     ::vos::OGuard aSolarGuard( Application::GetSolarMutex() );
553     ::osl::MutexGuard aGuard( getMutex() );
554 
555     if ( getView() && getView()->IsInModalMode() )
556         return sal_False;
557 
558     sal_Bool bCanSuspend = sal_True;
559 
560     if ( m_bSuspended != bSuspend )
561     {
562         if ( bSuspend && !closeSubComponents() )
563             return sal_False;
564 
565         Reference<XModifiable> xModi(m_xModel,UNO_QUERY);
566         Reference<XStorable> xStor(getModel(),UNO_QUERY);
567 
568         if  (   bSuspend
569             &&  xStor.is()
570             &&  !xStor->isReadonly()
571             &&  (   xModi.is()
572                 &&  xModi->isModified()
573                 )
574             )
575         {
576             switch (ExecuteQuerySaveDocument(getView(),getStrippedDatabaseName()))
577             {
578                 case RET_YES:
579                     Execute(ID_BROWSER_SAVEDOC,Sequence<PropertyValue>());
580                     bCanSuspend = !xModi->isModified();
581                     // when we save the document this must be false else some press cancel
582                     break;
583                 case RET_CANCEL:
584                     bCanSuspend = sal_False;
585                 default:
586                     break;
587             }
588         }
589     }
590 
591     if ( bCanSuspend )
592         m_bSuspended = bSuspend;
593 
594     return bCanSuspend;
595 }
596 // -----------------------------------------------------------------------------
597 FeatureState OApplicationController::GetState(sal_uInt16 _nId) const
598 {
599     FeatureState aReturn;
600     aReturn.bEnabled = sal_False;
601     // check this first
602     if ( !getContainer() || m_bReadOnly )
603         return aReturn;
604 
605     try
606     {
607         switch (_nId)
608         {
609             case SID_OPENURL:
610                 aReturn.bEnabled = sal_True;
611                 if ( m_xModel.is() )
612                     aReturn.sTitle = m_xModel->getURL();
613                 break;
614             case ID_BROWSER_COPY:
615                 {
616                     sal_Int32 nCount = getContainer()->getSelectionCount();
617                     aReturn.bEnabled = nCount >= 1;
618                     if ( aReturn.bEnabled && nCount == 1 && getContainer()->getElementType() == E_TABLE )
619                         aReturn.bEnabled = getContainer()->isALeafSelected();
620                 }
621                 break;
622             case ID_BROWSER_CUT:
623                 aReturn.bEnabled = !isDataSourceReadOnly() && getContainer()->getSelectionCount() >= 1;
624                 aReturn.bEnabled = aReturn.bEnabled && ( (ID_BROWSER_CUT == _nId && getContainer()->getElementType() == E_TABLE) ? getContainer()->isCutAllowed() : sal_True);
625                 break;
626             case ID_BROWSER_PASTE:
627                 switch( getContainer()->getElementType() )
628                 {
629                     case E_TABLE:
630                         aReturn.bEnabled = !isDataSourceReadOnly() && !isConnectionReadOnly() && isTableFormat();
631                         break;
632                     case E_QUERY:
633                         aReturn.bEnabled = !isDataSourceReadOnly() && getViewClipboard().HasFormat(SOT_FORMATSTR_ID_DBACCESS_QUERY);
634                         break;
635                     default:
636                         aReturn.bEnabled = !isDataSourceReadOnly() && OComponentTransferable::canExtractComponentDescriptor(getViewClipboard().GetDataFlavorExVector(),getContainer()->getElementType() == E_FORM);
637                 }
638                 break;
639             case SID_DB_APP_PASTE_SPECIAL:
640                 aReturn.bEnabled = getContainer()->getElementType() == E_TABLE && !isDataSourceReadOnly() && !isConnectionReadOnly() && isTableFormat();
641                 break;
642             case SID_OPENDOC:
643             case SID_HELP_INDEX:
644                 aReturn.bEnabled = sal_True;
645                 break;
646             case ID_BROWSER_SAVEDOC:
647                 aReturn.bEnabled = !isDataSourceReadOnly() && m_xDocumentModify.is() && m_xDocumentModify->isModified();
648                 break;
649             case ID_BROWSER_SAVEASDOC:
650                 aReturn.bEnabled = sal_True;
651                 break;
652             case ID_BROWSER_SORTUP:
653                 aReturn.bEnabled = getContainer()->isFilled() && getContainer()->getElementCount();
654                 aReturn.bChecked = aReturn.bEnabled && getContainer()->isSortUp();
655                 break;
656             case ID_BROWSER_SORTDOWN:
657                 aReturn.bEnabled = getContainer()->isFilled() && getContainer()->getElementCount();
658                 aReturn.bChecked = aReturn.bEnabled && !getContainer()->isSortUp();
659                 break;
660 
661             case SID_NEWDOC:
662             case SID_APP_NEW_FORM:
663             case ID_DOCUMENT_CREATE_REPWIZ:
664                 aReturn.bEnabled = !isDataSourceReadOnly() && SvtModuleOptions().IsModuleInstalled(SvtModuleOptions::E_SWRITER);
665                 break;
666             case SID_APP_NEW_REPORT:
667                 aReturn.bEnabled = !isDataSourceReadOnly()
668                                     && SvtModuleOptions().IsModuleInstalled(SvtModuleOptions::E_SWRITER);
669                 if ( aReturn.bEnabled )
670                 {
671                     Reference< XContentEnumerationAccess > xEnumAccess(m_xServiceFactory, UNO_QUERY);
672                     aReturn.bEnabled = xEnumAccess.is();
673                     if ( aReturn.bEnabled )
674                     {
675                         const ::rtl::OUString sReportEngineServiceName = ::dbtools::getDefaultReportEngineServiceName(m_xServiceFactory);
676                         aReturn.bEnabled = sReportEngineServiceName.getLength() != 0;
677                         if ( aReturn.bEnabled )
678                         {
679                             const Reference< XEnumeration > xEnumDrivers = xEnumAccess->createContentEnumeration(sReportEngineServiceName);
680                             aReturn.bEnabled = xEnumDrivers.is() && xEnumDrivers->hasMoreElements();
681                         }
682                     }
683                 }
684                 break;
685             case SID_DB_APP_VIEW_TABLES:
686                 aReturn.bEnabled = sal_True;
687                 aReturn.bChecked = getContainer()->getElementType() == E_TABLE;
688                 break;
689             case SID_DB_APP_VIEW_QUERIES:
690                 aReturn.bEnabled = sal_True;
691                 aReturn.bChecked = getContainer()->getElementType() == E_QUERY;
692                 break;
693             case SID_DB_APP_VIEW_FORMS:
694                 aReturn.bEnabled = sal_True;
695                 aReturn.bChecked = getContainer()->getElementType() == E_FORM;
696                 break;
697             case SID_DB_APP_VIEW_REPORTS:
698                 aReturn.bEnabled = sal_True;
699                 aReturn.bChecked = getContainer()->getElementType() == E_REPORT;
700                 break;
701             case ID_NEW_QUERY_DESIGN:
702             case ID_NEW_QUERY_SQL:
703             case ID_APP_NEW_QUERY_AUTO_PILOT:
704             case SID_DB_FORM_NEW_PILOT:
705                 aReturn.bEnabled = !isDataSourceReadOnly();
706                 break;
707             case ID_NEW_VIEW_DESIGN:
708             case SID_DB_NEW_VIEW_SQL:
709             case ID_NEW_VIEW_DESIGN_AUTO_PILOT:
710                 aReturn.bEnabled = !isDataSourceReadOnly() && !isConnectionReadOnly();
711                 if ( aReturn.bEnabled )
712                 {
713                     Reference<XViewsSupplier> xViewsSup( getConnection(), UNO_QUERY );
714                     aReturn.bEnabled = xViewsSup.is();
715                 }
716                 break;
717             case ID_NEW_TABLE_DESIGN:
718             case ID_NEW_TABLE_DESIGN_AUTO_PILOT:
719                 aReturn.bEnabled = !isDataSourceReadOnly() && !isConnectionReadOnly();
720                 break;
721             case ID_DIRECT_SQL:
722                 aReturn.bEnabled = sal_True;
723                 break;
724             case ID_MIGRATE_SCRIPTS:
725             {
726                 // Our document supports embedding scripts into it, if and only if there are no
727                 // forms/reports with macros/scripts into them. So, we need to enable migration
728                 // if and only if the database document does *not* support embedding scripts.
729                 bool bAvailable =
730                         !Reference< XEmbeddedScripts >( m_xModel, UNO_QUERY ).is()
731                     &&  !Reference< XStorable >( m_xModel, UNO_QUERY_THROW )->isReadonly();
732                 aReturn.bEnabled = bAvailable;
733                 if ( !bAvailable )
734                     aReturn.bInvisible = true;
735             }
736             break;
737             case SID_APP_NEW_FOLDER:
738                 aReturn.bEnabled = !isDataSourceReadOnly() && getContainer()->getSelectionCount() <= 1;
739                 if ( aReturn.bEnabled )
740                 {
741                     const ElementType eType = getContainer()->getElementType();
742                     aReturn.bEnabled = eType == E_REPORT || eType == E_FORM;
743                 }
744                 break;
745             case SID_FORM_CREATE_REPWIZ_PRE_SEL:
746             case SID_REPORT_CREATE_REPWIZ_PRE_SEL:
747             case SID_APP_NEW_REPORT_PRE_SEL:
748                 aReturn.bEnabled = !isDataSourceReadOnly()
749                                     && SvtModuleOptions().IsModuleInstalled(SvtModuleOptions::E_SWRITER)
750                                     && getContainer()->isALeafSelected();
751                 if ( aReturn.bEnabled )
752                 {
753                     ElementType eType = getContainer()->getElementType();
754                     aReturn.bEnabled = eType == E_QUERY || eType == E_TABLE;
755                     if ( aReturn.bEnabled && SID_APP_NEW_REPORT_PRE_SEL == _nId )
756                     {
757                         Reference< XContentEnumerationAccess > xEnumAccess(m_xServiceFactory, UNO_QUERY);
758                         aReturn.bEnabled = xEnumAccess.is();
759                         if ( aReturn.bEnabled )
760                         {
761                             static ::rtl::OUString s_sReportDesign(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.report.pentaho.SOReportJobFactory"));
762                             Reference< XEnumeration > xEnumDrivers = xEnumAccess->createContentEnumeration(s_sReportDesign);
763                             aReturn.bEnabled = xEnumDrivers.is() && xEnumDrivers->hasMoreElements();
764                         }
765                     }
766                 }
767                 break;
768             case SID_DB_APP_DELETE:
769             case SID_DB_APP_RENAME:
770                 aReturn.bEnabled = isRenameDeleteAllowed(getContainer()->getElementType(), _nId == SID_DB_APP_DELETE);
771                 break;
772             case SID_DB_APP_TABLE_DELETE:
773             case SID_DB_APP_TABLE_RENAME:
774                 aReturn.bEnabled = isRenameDeleteAllowed(E_TABLE, _nId == SID_DB_APP_TABLE_DELETE);
775                 break;
776             case SID_DB_APP_QUERY_DELETE:
777             case SID_DB_APP_QUERY_RENAME:
778                 aReturn.bEnabled = isRenameDeleteAllowed(E_QUERY, _nId == SID_DB_APP_QUERY_DELETE);
779                 break;
780             case SID_DB_APP_FORM_DELETE:
781             case SID_DB_APP_FORM_RENAME:
782                 aReturn.bEnabled = isRenameDeleteAllowed(E_FORM, _nId == SID_DB_APP_FORM_DELETE);
783                 break;
784             case SID_DB_APP_REPORT_DELETE:
785             case SID_DB_APP_REPORT_RENAME:
786                 aReturn.bEnabled = isRenameDeleteAllowed(E_REPORT, _nId == SID_DB_APP_REPORT_DELETE);
787                 break;
788 
789             case SID_SELECTALL:
790                 aReturn.bEnabled = getContainer()->getElementCount() > 0 && getContainer()->getSelectionCount() != getContainer()->getElementCount();
791                 break;
792             case SID_DB_APP_EDIT:
793             case SID_DB_APP_TABLE_EDIT:
794             case SID_DB_APP_QUERY_EDIT:
795             case SID_DB_APP_FORM_EDIT:
796             case SID_DB_APP_REPORT_EDIT:
797                 aReturn.bEnabled = !isDataSourceReadOnly() && getContainer()->getSelectionCount() > 0
798                                     && getContainer()->isALeafSelected();
799                 break;
800             case SID_DB_APP_EDIT_SQL_VIEW:
801                 if ( isDataSourceReadOnly() )
802                     aReturn.bEnabled = sal_False;
803                 else
804                 {
805                     switch ( getContainer()->getElementType() )
806                     {
807                     case E_QUERY:
808                         aReturn.bEnabled =  ( getContainer()->getSelectionCount() > 0 )
809                                         &&  ( getContainer()->isALeafSelected() );
810                         break;
811                     case E_TABLE:
812                         aReturn.bEnabled = sal_False;
813                         // there's one exception: views which support altering their underlying
814                         // command can be edited in SQL view, too
815                         if  (   ( getContainer()->getSelectionCount() > 0 )
816                             &&  ( getContainer()->isALeafSelected() )
817                             )
818                         {
819                             ::std::vector< ::rtl::OUString > aSelected;
820                             getSelectionElementNames( aSelected );
821                             bool bAlterableViews = true;
822                             for (   ::std::vector< ::rtl::OUString >::const_iterator selectedName = aSelected.begin();
823                                     bAlterableViews && ( selectedName != aSelected.end() ) ;
824                                     ++selectedName
825                                 )
826                             {
827                                 bAlterableViews &= impl_isAlterableView_nothrow( *selectedName );
828                             }
829                             aReturn.bEnabled = bAlterableViews;
830                         }
831                         break;
832                     default:
833                         break;
834                     }
835                 }
836                 break;
837             case SID_DB_APP_OPEN:
838             case SID_DB_APP_TABLE_OPEN:
839             case SID_DB_APP_QUERY_OPEN:
840             case SID_DB_APP_FORM_OPEN:
841             case SID_DB_APP_REPORT_OPEN:
842                 aReturn.bEnabled = getContainer()->getSelectionCount() > 0 && getContainer()->isALeafSelected();
843                 break;
844             case SID_DB_APP_DSUSERADMIN:
845                 aReturn.bEnabled = !m_aTypeCollection.isEmbeddedDatabase(::comphelper::getString(m_xDataSource->getPropertyValue(PROPERTY_URL)));
846                 break;
847             case SID_DB_APP_DSRELDESIGN:
848                 aReturn.bEnabled = sal_True;
849                 break;
850             case SID_DB_APP_TABLEFILTER:
851                 aReturn.bEnabled = !isDataSourceReadOnly();
852                 break;
853             case SID_DB_APP_REFRESH_TABLES:
854                 aReturn.bEnabled = getContainer()->getElementType() == E_TABLE && isConnected();
855                 break;
856             case SID_DB_APP_DSPROPS:
857                 aReturn.bEnabled = m_xDataSource.is() && m_aTypeCollection.isShowPropertiesEnabled(::comphelper::getString(m_xDataSource->getPropertyValue(PROPERTY_URL)));
858                 break;
859             case SID_DB_APP_DSCONNECTION_TYPE:
860                 aReturn.bEnabled = !isDataSourceReadOnly() && m_xDataSource.is() && !m_aTypeCollection.isEmbeddedDatabase(::comphelper::getString(m_xDataSource->getPropertyValue(PROPERTY_URL)));
861                 break;
862             case SID_DB_APP_DSADVANCED_SETTINGS:
863                 aReturn.bEnabled = m_xDataSource.is() && AdvancedSettingsDialog::doesHaveAnyAdvancedSettings( m_aTypeCollection.getType(::comphelper::getString( m_xDataSource->getPropertyValue( PROPERTY_URL ) )) );
864                 break;
865             case SID_DB_APP_CONVERTTOVIEW:
866                 aReturn.bEnabled = !isDataSourceReadOnly();
867                 if ( aReturn.bEnabled )
868                 {
869                     ElementType eType = getContainer()->getElementType();
870                     aReturn.bEnabled = eType == E_QUERY && getContainer()->getSelectionCount() > 0;
871                     if ( aReturn.bEnabled )
872                     {
873                         Reference<XViewsSupplier> xViewSup( getConnection(), UNO_QUERY );
874                         aReturn.bEnabled = xViewSup.is() && Reference<XAppend>(xViewSup->getViews(),UNO_QUERY).is();
875                     }
876                 }
877                 break;
878             case SID_DB_APP_DISABLE_PREVIEW:
879                 aReturn.bEnabled = sal_True;
880                 aReturn.bChecked = getContainer()->getPreviewMode() == E_PREVIEWNONE;
881                 break;
882             case SID_DB_APP_VIEW_DOCINFO_PREVIEW:
883                 {
884                     ElementType eType = getContainer()->getElementType();
885                     aReturn.bEnabled = (E_REPORT == eType || E_FORM == eType);
886                     aReturn.bChecked = getContainer()->getPreviewMode() == E_DOCUMENTINFO;
887                 }
888                 break;
889             case SID_DB_APP_VIEW_DOC_PREVIEW:
890                 aReturn.bEnabled = sal_True;
891                 aReturn.bChecked = getContainer()->getPreviewMode() == E_DOCUMENT;
892                 break;
893             case ID_BROWSER_UNDO:
894                 aReturn.bEnabled = sal_False;
895                 break;
896             case SID_MAIL_SENDDOC:
897                 aReturn.bEnabled = sal_True;
898                 break;
899             case SID_DB_APP_SENDREPORTASMAIL:
900                 {
901                     ElementType eType = getContainer()->getElementType();
902                     aReturn.bEnabled = E_REPORT == eType && getContainer()->getSelectionCount() > 0 && getContainer()->isALeafSelected();
903                 }
904                 break;
905             case SID_DB_APP_SENDREPORTTOWRITER:
906             case SID_DB_APP_DBADMIN:
907                 aReturn.bEnabled = sal_False;
908                 break;
909             case SID_DB_APP_STATUS_TYPE:
910                 aReturn.bEnabled = m_xDataSource.is();
911                 if ( aReturn.bEnabled )
912                 {
913                     ::rtl::OUString sURL;
914                     m_xDataSource->getPropertyValue(PROPERTY_URL) >>= sURL;
915                     ::rtl::OUString sDSTypeName;
916                     if ( m_aTypeCollection.isEmbeddedDatabase( sURL ) )
917                     {
918                         sDSTypeName = String( ModuleRes( RID_STR_EMBEDDED_DATABASE ) );
919                     }
920                     else
921                     {
922                         sDSTypeName = m_aTypeCollection.getTypeDisplayName(sURL);
923                     }
924                     aReturn.sTitle = sDSTypeName;
925                 }
926                 break;
927             case SID_DB_APP_STATUS_DBNAME:
928                 aReturn.bEnabled = m_xDataSource.is();
929                 if ( aReturn.bEnabled )
930                 {
931                     ::rtl::OUString sURL;
932                     m_xDataSource->getPropertyValue(PROPERTY_URL) >>= sURL;
933                     String sDatabaseName;
934                     String sHostName;
935                     sal_Int32 nPortNumber( -1 );
936 
937                     m_aTypeCollection.extractHostNamePort( sURL, sDatabaseName, sHostName, nPortNumber );
938 
939                     if ( !sDatabaseName.Len() )
940                         sDatabaseName = m_aTypeCollection.cutPrefix( sURL );
941                     if ( m_aTypeCollection.isFileSystemBased(sURL) )
942                     {
943                         sDatabaseName = SvtPathOptions().SubstituteVariable( sDatabaseName );
944                         if ( sDatabaseName.Len() )
945                         {
946                             ::svt::OFileNotation aFileNotation(sDatabaseName);
947                             // set this decoded URL as text
948                             sDatabaseName = aFileNotation.get(::svt::OFileNotation::N_SYSTEM);
949                         }
950                     }
951 
952                     if ( sDatabaseName.Len() == 0 )
953                         sDatabaseName = m_aTypeCollection.getTypeDisplayName( sURL );
954 
955                     aReturn.sTitle = sDatabaseName;
956                 }
957                 break;
958             case SID_DB_APP_STATUS_USERNAME:
959                 aReturn.bEnabled = m_xDataSource.is();
960                 if ( aReturn.bEnabled )
961                     m_xDataSource->getPropertyValue( PROPERTY_USER ) >>= aReturn.sTitle;
962                 break;
963             case SID_DB_APP_STATUS_HOSTNAME:
964                 aReturn.bEnabled = m_xDataSource.is();
965                 if ( aReturn.bEnabled )
966                 {
967                     ::rtl::OUString sURL;
968                     m_xDataSource->getPropertyValue( PROPERTY_URL ) >>= sURL;
969 
970                     String sHostName, sDatabaseName;
971                     sal_Int32 nPortNumber = -1;
972                     m_aTypeCollection.extractHostNamePort( sURL, sDatabaseName, sHostName, nPortNumber );
973                     aReturn.sTitle = sHostName;
974                 }
975                 break;
976             default:
977                 aReturn = OApplicationController_CBASE::GetState(_nId);
978         }
979     }
980     catch(const Exception& )
981     {
982         DBG_UNHANDLED_EXCEPTION();
983     }
984     return aReturn;
985 }
986 
987 // -----------------------------------------------------------------------------
988 namespace
989 {
990     bool lcl_handleException_nothrow( const Reference< XModel >& _rxDocument, const Any& _rException )
991     {
992         bool bHandled = false;
993 
994         // try handling the error with an interaction handler
995         ::comphelper::NamedValueCollection aArgs( _rxDocument->getArgs() );
996         Reference< XInteractionHandler > xHandler( aArgs.getOrDefault( "InteractionHandler", Reference< XInteractionHandler >() ) );
997         if ( xHandler.is() )
998         {
999             ::rtl::Reference< ::comphelper::OInteractionRequest > pRequest( new ::comphelper::OInteractionRequest( _rException ) );
1000             ::rtl::Reference< ::comphelper::OInteractionApprove > pApprove( new ::comphelper::OInteractionApprove );
1001             pRequest->addContinuation( pApprove.get() );
1002 
1003             try
1004             {
1005                 xHandler->handle( pRequest.get() );
1006             }
1007             catch( const Exception& )
1008             {
1009                 DBG_UNHANDLED_EXCEPTION();
1010             }
1011 
1012             bHandled = pApprove->wasSelected();
1013         }
1014         return bHandled;
1015     }
1016 }
1017 
1018 // -----------------------------------------------------------------------------
1019 void OApplicationController::Execute(sal_uInt16 _nId, const Sequence< PropertyValue >& aArgs)
1020 {
1021     ::vos::OGuard aSolarGuard( Application::GetSolarMutex() );
1022     ::osl::MutexGuard aGuard( getMutex() );
1023 
1024     if ( isUserDefinedFeature( _nId ) )
1025     {
1026         OApplicationController_CBASE::Execute( _nId, aArgs );
1027         return;
1028     }
1029 
1030     if ( !getContainer() || m_bReadOnly )
1031         return; // return without execution
1032 
1033     try
1034     {
1035         switch(_nId)
1036         {
1037             case ID_BROWSER_CUT:
1038                 getContainer()->cut();
1039                 break;
1040             case ID_BROWSER_COPY:
1041                 {
1042                     TransferableHelper* pTransfer = copyObject( );
1043                     Reference< XTransferable> aEnsureDelete = pTransfer;
1044 
1045                     if ( pTransfer )
1046                         pTransfer->CopyToClipboard(getView());
1047                 }
1048                 break;
1049             case ID_BROWSER_PASTE:
1050                 {
1051                     const TransferableDataHelper& rTransferData( getViewClipboard() );
1052                     ElementType eType = getContainer()->getElementType();
1053 
1054                     switch( eType )
1055                     {
1056                         case E_TABLE:
1057                             {
1058                                 // get the selected tablename
1059                                 ::std::vector< ::rtl::OUString > aList;
1060                                 getSelectionElementNames( aList );
1061                                 if ( !aList.empty() )
1062                                     m_aTableCopyHelper.SetTableNameForAppend( *aList.begin() );
1063                                 else
1064                                     m_aTableCopyHelper.ResetTableNameForAppend();
1065 
1066                                 m_aTableCopyHelper.pasteTable( rTransferData , getDatabaseName(), ensureConnection() );
1067                             }
1068                             break;
1069 
1070                         case E_QUERY:
1071                             if ( rTransferData.HasFormat(SOT_FORMATSTR_ID_DBACCESS_QUERY) )
1072                                 paste( E_QUERY, ODataAccessObjectTransferable::extractObjectDescriptor( rTransferData ) );
1073                             break;
1074                         default:
1075                             {
1076                                 ::std::vector< ::rtl::OUString> aList;
1077                                 getSelectionElementNames(aList);
1078                                 ::rtl::OUString sFolderNameToInsertInto;
1079                                 if ( !aList.empty() )
1080                                 {
1081                                     Reference< XHierarchicalNameAccess > xContainer(getElements(eType),UNO_QUERY);
1082                                     if ( xContainer.is()
1083                                         && xContainer->hasByHierarchicalName(*aList.begin())
1084                                         && (xContainer->getByHierarchicalName(*aList.begin()) >>= xContainer)
1085                                         && xContainer.is()
1086                                         )
1087                                         sFolderNameToInsertInto = *aList.begin();
1088                                 }
1089                                 paste( eType, OComponentTransferable::extractComponentDescriptor( rTransferData ),
1090                                     sFolderNameToInsertInto );
1091                             }
1092                             break;
1093                     }
1094                 }
1095                 break;
1096             case SID_DB_APP_PASTE_SPECIAL:
1097                 {
1098                     if ( !aArgs.getLength() )
1099                     {
1100                         SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
1101                         ::std::auto_ptr<SfxAbstractPasteDialog> pDlg(pFact->CreatePasteDialog( getView() ));
1102                         ::std::vector<SotFormatStringId> aFormatIds;
1103                         getSupportedFormats(getContainer()->getElementType(),aFormatIds);
1104                         const ::std::vector<SotFormatStringId>::iterator aEnd = aFormatIds.end();
1105                         ::rtl::OUString sEmpty;
1106                         for (::std::vector<SotFormatStringId>::iterator aIter = aFormatIds.begin();aIter != aEnd; ++aIter)
1107                             pDlg->Insert(*aIter,sEmpty);
1108 
1109                         const TransferableDataHelper& rClipboard = getViewClipboard();
1110                         pasteFormat(pDlg->GetFormat(rClipboard.GetTransferable()));
1111                     }
1112                     else
1113                     {
1114                         const PropertyValue* pIter = aArgs.getConstArray();
1115                         const PropertyValue* pEnd  = pIter + aArgs.getLength();
1116                         for( ; pIter != pEnd ; ++pIter)
1117                         {
1118                             if ( pIter->Name.equalsAscii("FormatStringId") )
1119                             {
1120                                 SotFormatStringId nFormatId = 0;
1121                                 if ( pIter->Value >>= nFormatId )
1122                                     pasteFormat(nFormatId);
1123                                 break;
1124                             }
1125                         }
1126                     }
1127                 }
1128                 break;
1129             case SID_OPENDOC:
1130             case SID_HELP_INDEX:
1131                 {
1132                     Reference < XDispatchProvider > xProv( getFrame(), UNO_QUERY );
1133                     if ( xProv.is() )
1134                     {
1135                         URL aURL;
1136                         switch(_nId)
1137                         {
1138                             case SID_HELP_INDEX:
1139                                 aURL.Complete = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(".uno:HelpIndex"));
1140                                 break;
1141                             case SID_OPENDOC:
1142                                 aURL.Complete = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(".uno:Open"));
1143                                 break;
1144                         }
1145 
1146                         if ( m_xUrlTransformer.is() )
1147                             m_xUrlTransformer->parseStrict( aURL );
1148                         Reference < XDispatch > xDisp = xProv->queryDispatch( aURL, String(), 0 );
1149                         if ( xDisp.is() )
1150                             xDisp->dispatch( aURL, Sequence < PropertyValue >() );
1151                     }
1152                 }
1153                 break;
1154             case ID_BROWSER_SAVEDOC:
1155                 {
1156                     Reference< XStorable > xStore( m_xModel, UNO_QUERY_THROW );
1157                     try
1158                     {
1159                         xStore->store();
1160                     }
1161                     catch( const Exception& )
1162                     {
1163                         lcl_handleException_nothrow( m_xModel, ::cppu::getCaughtException() );
1164                     }
1165                 }
1166                 break;
1167 
1168             case ID_BROWSER_SAVEASDOC:
1169                 {
1170                     WinBits nBits(WB_STDMODAL|WB_SAVEAS);
1171                     ::rtl::OUString sUrl;
1172                     if ( m_xModel.is() )
1173                         sUrl = m_xModel->getURL();
1174                     if ( !sUrl.getLength() )
1175                         sUrl = SvtPathOptions().GetWorkPath();
1176 
1177                     ::sfx2::FileDialogHelper aFileDlg( com::sun::star::ui::dialogs::TemplateDescription::FILESAVE_AUTOEXTENSION,static_cast<sal_uInt32>(nBits) ,getView());
1178                     aFileDlg.SetDisplayDirectory( sUrl );
1179 
1180                     const SfxFilter* pFilter = getStandardDatabaseFilter();
1181                     if ( pFilter )
1182                     {
1183                         aFileDlg.AddFilter(pFilter->GetUIName(),pFilter->GetDefaultExtension());
1184                         aFileDlg.SetCurrentFilter(pFilter->GetUIName());
1185                     }
1186 
1187                     if ( aFileDlg.Execute() != ERRCODE_NONE )
1188                         break;
1189 
1190                     Reference<XStorable> xStore( m_xModel, UNO_QUERY_THROW );
1191                     INetURLObject aURL( aFileDlg.GetPath() );
1192                     try
1193                     {
1194                         xStore->storeAsURL( aURL.GetMainURL( INetURLObject::NO_DECODE ), Sequence< PropertyValue >() );
1195                     }
1196                     catch( const Exception& )
1197                     {
1198                         lcl_handleException_nothrow( m_xModel, ::cppu::getCaughtException() );
1199                     }
1200 
1201                     /*updateTitle();*/
1202                     m_bCurrentlyModified = sal_False;
1203                     InvalidateFeature(ID_BROWSER_SAVEDOC);
1204                     if ( getContainer()->getElementType() == E_NONE )
1205                     {
1206                         getContainer()->selectContainer(E_NONE);
1207                         getContainer()->selectContainer(E_TABLE);
1208                         // #i95524#
1209                         getContainer()->Invalidate();
1210                         refreshTables();
1211                     }
1212 
1213                 }
1214                 break;
1215             case ID_BROWSER_SORTUP:
1216                 getContainer()->sortUp();
1217                 InvalidateFeature(ID_BROWSER_SORTDOWN);
1218                 break;
1219             case ID_BROWSER_SORTDOWN:
1220                 getContainer()->sortDown();
1221                 InvalidateFeature(ID_BROWSER_SORTUP);
1222                 break;
1223 
1224             case ID_NEW_TABLE_DESIGN_AUTO_PILOT:
1225             case ID_NEW_VIEW_DESIGN_AUTO_PILOT:
1226             case ID_APP_NEW_QUERY_AUTO_PILOT:
1227             case SID_DB_FORM_NEW_PILOT:
1228             case SID_REPORT_CREATE_REPWIZ_PRE_SEL:
1229             case SID_APP_NEW_REPORT_PRE_SEL:
1230             case SID_FORM_CREATE_REPWIZ_PRE_SEL:
1231             case ID_DOCUMENT_CREATE_REPWIZ:
1232             case SID_APP_NEW_FORM:
1233             case SID_APP_NEW_REPORT:
1234             case ID_NEW_QUERY_SQL:
1235             case ID_NEW_QUERY_DESIGN:
1236             case ID_NEW_TABLE_DESIGN:
1237                 {
1238                     ElementType eType = E_TABLE;
1239                     sal_Bool bAutoPilot = sal_False;
1240                     ::comphelper::NamedValueCollection aCreationArgs;
1241 
1242                     switch( _nId )
1243                     {
1244                         case SID_DB_FORM_NEW_PILOT:
1245                         case SID_FORM_CREATE_REPWIZ_PRE_SEL:
1246                             bAutoPilot = sal_True;
1247                             // run through
1248                         case SID_APP_NEW_FORM:
1249                             eType = E_FORM;
1250                             break;
1251                         case ID_DOCUMENT_CREATE_REPWIZ:
1252                         case SID_REPORT_CREATE_REPWIZ_PRE_SEL:
1253                             bAutoPilot = sal_True;
1254                             // run through
1255                         case SID_APP_NEW_REPORT:
1256                         case SID_APP_NEW_REPORT_PRE_SEL:
1257                             eType = E_REPORT;
1258                             break;
1259                         case ID_APP_NEW_QUERY_AUTO_PILOT:
1260                             bAutoPilot = sal_True;
1261                             eType = E_QUERY;
1262                             break;
1263                         case ID_NEW_QUERY_DESIGN:
1264                             aCreationArgs.put( (::rtl::OUString)PROPERTY_GRAPHICAL_DESIGN, sal_True );
1265                             // run through
1266                         case ID_NEW_QUERY_SQL:
1267                             eType = E_QUERY;
1268                             break;
1269                         case ID_NEW_TABLE_DESIGN_AUTO_PILOT:
1270                             bAutoPilot = sal_True;
1271                             // run through
1272                         case ID_NEW_TABLE_DESIGN:
1273                             break;
1274                         default:
1275                             OSL_ENSURE(0,"illegal switch call!");
1276                     }
1277                     if ( bAutoPilot )
1278                         getContainer()->PostUserEvent( LINK( this, OApplicationController, OnCreateWithPilot ), reinterpret_cast< void* >( eType ) );
1279                     else
1280                     {
1281                         Reference< XComponent > xDocDefinition;
1282                         newElement( eType, aCreationArgs, xDocDefinition );
1283                     }
1284                 }
1285                 break;
1286             case SID_APP_NEW_FOLDER:
1287                 {
1288                     ElementType eType = getContainer()->getElementType();
1289                     ::rtl::OUString sName = getContainer()->getQualifiedName( NULL );
1290                     insertHierachyElement(eType,sName);
1291                 }
1292                 break;
1293             case ID_NEW_VIEW_DESIGN:
1294             case SID_DB_NEW_VIEW_SQL:
1295                 {
1296                     SharedConnection xConnection( ensureConnection() );
1297                     if ( xConnection.is() )
1298                     {
1299                         QueryDesigner aDesigner( getORB(), this, getFrame(), true );
1300 
1301                         ::comphelper::NamedValueCollection aCreationArgs;
1302                         aCreationArgs.put( (::rtl::OUString)PROPERTY_GRAPHICAL_DESIGN, ID_NEW_VIEW_DESIGN == _nId );
1303 
1304                         const Reference< XDataSource > xDataSource( m_xDataSource, UNO_QUERY );
1305                         const Reference< XComponent > xComponent( aDesigner.createNew( xDataSource, aCreationArgs ), UNO_QUERY );
1306                         onDocumentOpened( ::rtl::OUString(), E_QUERY, E_OPEN_DESIGN, xComponent, NULL );
1307                     }
1308                 }
1309                 break;
1310             case SID_DB_APP_DELETE:
1311             case SID_DB_APP_TABLE_DELETE:
1312             case SID_DB_APP_QUERY_DELETE:
1313             case SID_DB_APP_FORM_DELETE:
1314             case SID_DB_APP_REPORT_DELETE:
1315                 deleteEntries();
1316                 break;
1317             case SID_DB_APP_RENAME:
1318             case SID_DB_APP_TABLE_RENAME:
1319             case SID_DB_APP_QUERY_RENAME:
1320             case SID_DB_APP_FORM_RENAME:
1321             case SID_DB_APP_REPORT_RENAME:
1322                 renameEntry();
1323                 break;
1324             case SID_DB_APP_EDIT:
1325             case SID_DB_APP_EDIT_SQL_VIEW:
1326             case SID_DB_APP_TABLE_EDIT:
1327             case SID_DB_APP_QUERY_EDIT:
1328             case SID_DB_APP_FORM_EDIT:
1329             case SID_DB_APP_REPORT_EDIT:
1330                 doAction( _nId, E_OPEN_DESIGN );
1331                 break;
1332             case SID_DB_APP_OPEN:
1333             case SID_DB_APP_TABLE_OPEN:
1334             case SID_DB_APP_QUERY_OPEN:
1335             case SID_DB_APP_FORM_OPEN:
1336             case SID_DB_APP_REPORT_OPEN:
1337                 doAction( _nId, E_OPEN_NORMAL );
1338                 break;
1339             case SID_DB_APP_CONVERTTOVIEW:
1340                 doAction( _nId, E_OPEN_NORMAL );
1341                 break;
1342             case SID_SELECTALL:
1343                 getContainer()->selectAll();
1344                 InvalidateAll();
1345                 break;
1346             case SID_DB_APP_DSRELDESIGN:
1347             {
1348                 Reference< XComponent > xRelationDesigner;
1349                 if ( !m_pSubComponentManager->activateSubFrame( ::rtl::OUString(), SID_DB_APP_DSRELDESIGN, E_OPEN_DESIGN, xRelationDesigner ) )
1350                 {
1351                     SharedConnection xConnection( ensureConnection() );
1352                     if ( xConnection.is() )
1353                     {
1354                         RelationDesigner aDesigner( getORB(), this, m_aCurrentFrame.getFrame() );
1355 
1356                         const Reference< XDataSource > xDataSource( m_xDataSource, UNO_QUERY );
1357                         const Reference< XComponent > xComponent( aDesigner.createNew( xDataSource ), UNO_QUERY );
1358                         onDocumentOpened( ::rtl::OUString(), SID_DB_APP_DSRELDESIGN, E_OPEN_DESIGN, xComponent, NULL );
1359                     }
1360                 }
1361             }
1362             break;
1363             case SID_DB_APP_DSUSERADMIN:
1364                 {
1365                     SharedConnection xConnection( ensureConnection() );
1366                     if ( xConnection.is() )
1367                         openDialog(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.sdb.UserAdministrationDialog")));
1368                 }
1369                 break;
1370             case SID_DB_APP_TABLEFILTER:
1371                 openTableFilterDialog();
1372                 askToReconnect();
1373                 break;
1374             case SID_DB_APP_REFRESH_TABLES:
1375                 refreshTables();
1376                 break;
1377             case SID_DB_APP_DSPROPS:
1378                 openDataSourceAdminDialog();
1379                 askToReconnect();
1380                 break;
1381             case SID_DB_APP_DSADVANCED_SETTINGS:
1382                 openDialog(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.sdb.AdvancedDatabaseSettingsDialog")));
1383                 askToReconnect();
1384                 break;
1385             case SID_DB_APP_DSCONNECTION_TYPE:
1386                 openDialog(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.sdb.DataSourceTypeChangeDialog")));
1387                 askToReconnect();
1388                 break;
1389             case ID_DIRECT_SQL:
1390                 {
1391                     SharedConnection xConnection( ensureConnection() );
1392                     if ( xConnection.is() )
1393                         openDirectSQLDialog();
1394                 }
1395                 break;
1396             case ID_MIGRATE_SCRIPTS:
1397                 impl_migrateScripts_nothrow();
1398                 break;
1399             case SID_DB_APP_VIEW_TABLES:
1400                 m_aSelectContainerEvent.Call( reinterpret_cast< void* >( E_TABLE ) );
1401                 break;
1402             case SID_DB_APP_VIEW_QUERIES:
1403                 m_aSelectContainerEvent.Call( reinterpret_cast< void* >( E_QUERY ) );
1404                 break;
1405             case SID_DB_APP_VIEW_FORMS:
1406                 m_aSelectContainerEvent.Call( reinterpret_cast< void* >( E_FORM ) );
1407                 break;
1408             case SID_DB_APP_VIEW_REPORTS:
1409                 m_aSelectContainerEvent.Call( reinterpret_cast< void* >( E_REPORT ) );
1410                 break;
1411             case SID_DB_APP_DISABLE_PREVIEW:
1412                 m_ePreviewMode = E_PREVIEWNONE;
1413                 getContainer()->switchPreview(m_ePreviewMode);
1414                 break;
1415             case SID_DB_APP_VIEW_DOCINFO_PREVIEW:
1416                 m_ePreviewMode = E_DOCUMENTINFO;
1417                 getContainer()->switchPreview(m_ePreviewMode);
1418                 break;
1419             case SID_DB_APP_VIEW_DOC_PREVIEW:
1420                 m_ePreviewMode = E_DOCUMENT;
1421                 getContainer()->switchPreview(m_ePreviewMode);
1422                 break;
1423             case SID_MAIL_SENDDOC:
1424                 {
1425                     SfxMailModel aSendMail;
1426                     if ( aSendMail.AttachDocument(rtl::OUString(),getModel(), rtl::OUString()) == SfxMailModel::SEND_MAIL_OK )
1427                         aSendMail.Send( getFrame() );
1428                 }
1429                 break;
1430             case SID_DB_APP_SENDREPORTASMAIL:
1431                 doAction( _nId, E_OPEN_FOR_MAIL );
1432                 break;
1433         }
1434     }
1435     catch( const Exception& )
1436     {
1437         DBG_UNHANDLED_EXCEPTION();
1438     }
1439     InvalidateFeature(_nId);
1440 }
1441 // -----------------------------------------------------------------------------
1442 void OApplicationController::describeSupportedFeatures()
1443 {
1444     OApplicationController_CBASE::describeSupportedFeatures();
1445 
1446     implDescribeSupportedFeature( ".uno:Save",               ID_BROWSER_SAVEDOC,        CommandGroup::DOCUMENT );
1447     implDescribeSupportedFeature( ".uno:SaveAs",             ID_BROWSER_SAVEASDOC,      CommandGroup::DOCUMENT );
1448     implDescribeSupportedFeature( ".uno:SendMail",           SID_MAIL_SENDDOC,          CommandGroup::DOCUMENT );
1449     implDescribeSupportedFeature( ".uno:DBSendReportAsMail",SID_DB_APP_SENDREPORTASMAIL,
1450                                                                                         CommandGroup::DOCUMENT );
1451     implDescribeSupportedFeature( ".uno:DBSendReportToWriter",SID_DB_APP_SENDREPORTTOWRITER,
1452                                                                                         CommandGroup::DOCUMENT );
1453     implDescribeSupportedFeature( ".uno:DBNewForm",          SID_APP_NEW_FORM,          CommandGroup::INSERT );
1454     implDescribeSupportedFeature( ".uno:DBNewFolder",        SID_APP_NEW_FOLDER,        CommandGroup::INSERT );
1455     implDescribeSupportedFeature( ".uno:DBNewFormAutoPilot", SID_DB_FORM_NEW_PILOT,     CommandGroup::INSERT );
1456     implDescribeSupportedFeature( ".uno:DBNewFormAutoPilotWithPreSelection",
1457                                                              SID_FORM_CREATE_REPWIZ_PRE_SEL,
1458                                                                                         CommandGroup::APPLICATION );
1459 
1460     implDescribeSupportedFeature( ".uno:DBNewReport",        SID_APP_NEW_REPORT,        CommandGroup::INSERT );
1461     implDescribeSupportedFeature( ".uno:DBNewReportAutoPilot",
1462                                                              ID_DOCUMENT_CREATE_REPWIZ, CommandGroup::INSERT );
1463     implDescribeSupportedFeature( ".uno:DBNewReportAutoPilotWithPreSelection",
1464                                                              SID_REPORT_CREATE_REPWIZ_PRE_SEL,
1465                                                                                         CommandGroup::APPLICATION );
1466     implDescribeSupportedFeature( ".uno:DBNewQuery",         ID_NEW_QUERY_DESIGN,       CommandGroup::INSERT );
1467     implDescribeSupportedFeature( ".uno:DBNewQuerySql",      ID_NEW_QUERY_SQL,          CommandGroup::INSERT );
1468     implDescribeSupportedFeature( ".uno:DBNewQueryAutoPilot",ID_APP_NEW_QUERY_AUTO_PILOT,
1469                                                                                         CommandGroup::INSERT );
1470     implDescribeSupportedFeature( ".uno:DBNewTable",         ID_NEW_TABLE_DESIGN,       CommandGroup::INSERT );
1471     implDescribeSupportedFeature( ".uno:DBNewTableAutoPilot",ID_NEW_TABLE_DESIGN_AUTO_PILOT,
1472                                                                                         CommandGroup::INSERT );
1473     implDescribeSupportedFeature( ".uno:DBNewView",          ID_NEW_VIEW_DESIGN,        CommandGroup::INSERT );
1474     implDescribeSupportedFeature( ".uno:DBNewViewSQL",       SID_DB_NEW_VIEW_SQL,       CommandGroup::INSERT );
1475 
1476     implDescribeSupportedFeature( ".uno:DBDelete",           SID_DB_APP_DELETE,         CommandGroup::EDIT );
1477     implDescribeSupportedFeature( ".uno:Delete",             SID_DB_APP_DELETE,         CommandGroup::EDIT );
1478     implDescribeSupportedFeature( ".uno:DBRename",           SID_DB_APP_RENAME,         CommandGroup::EDIT );
1479     implDescribeSupportedFeature( ".uno:DBEdit",             SID_DB_APP_EDIT,           CommandGroup::EDIT );
1480     implDescribeSupportedFeature( ".uno:DBEditSqlView",      SID_DB_APP_EDIT_SQL_VIEW,  CommandGroup::EDIT );
1481     implDescribeSupportedFeature( ".uno:DBOpen",             SID_DB_APP_OPEN,           CommandGroup::EDIT );
1482 
1483     implDescribeSupportedFeature( ".uno:DBTableDelete",      SID_DB_APP_TABLE_DELETE,   CommandGroup::EDIT );
1484     implDescribeSupportedFeature( ".uno:DBTableRename",      SID_DB_APP_TABLE_RENAME,   CommandGroup::EDIT );
1485     implDescribeSupportedFeature( ".uno:DBTableEdit",        SID_DB_APP_TABLE_EDIT,     CommandGroup::EDIT );
1486     implDescribeSupportedFeature( ".uno:DBTableOpen",        SID_DB_APP_TABLE_OPEN,     CommandGroup::EDIT );
1487 
1488     implDescribeSupportedFeature( ".uno:DBQueryDelete",      SID_DB_APP_QUERY_DELETE,   CommandGroup::EDIT );
1489     implDescribeSupportedFeature( ".uno:DBQueryRename",      SID_DB_APP_QUERY_RENAME,   CommandGroup::EDIT );
1490     implDescribeSupportedFeature( ".uno:DBQueryEdit",        SID_DB_APP_QUERY_EDIT,     CommandGroup::EDIT );
1491     implDescribeSupportedFeature( ".uno:DBQueryOpen",        SID_DB_APP_QUERY_OPEN,     CommandGroup::EDIT );
1492 
1493     implDescribeSupportedFeature( ".uno:DBFormDelete",       SID_DB_APP_FORM_DELETE,    CommandGroup::EDIT );
1494     implDescribeSupportedFeature( ".uno:DBFormRename",       SID_DB_APP_FORM_RENAME,    CommandGroup::EDIT );
1495     implDescribeSupportedFeature( ".uno:DBFormEdit",         SID_DB_APP_FORM_EDIT,      CommandGroup::EDIT );
1496     implDescribeSupportedFeature( ".uno:DBFormOpen",         SID_DB_APP_FORM_OPEN,      CommandGroup::EDIT );
1497 
1498     implDescribeSupportedFeature( ".uno:DBReportDelete",     SID_DB_APP_REPORT_DELETE,  CommandGroup::EDIT );
1499     implDescribeSupportedFeature( ".uno:DBReportRename",     SID_DB_APP_REPORT_RENAME,  CommandGroup::EDIT );
1500     implDescribeSupportedFeature( ".uno:DBReportEdit",       SID_DB_APP_REPORT_EDIT,    CommandGroup::EDIT );
1501     implDescribeSupportedFeature( ".uno:DBReportOpen",       SID_DB_APP_REPORT_OPEN,    CommandGroup::EDIT );
1502 
1503     implDescribeSupportedFeature( ".uno:SelectAll",          SID_SELECTALL,             CommandGroup::EDIT );
1504     implDescribeSupportedFeature( ".uno:Undo",               ID_BROWSER_UNDO,           CommandGroup::EDIT );
1505 
1506     implDescribeSupportedFeature( ".uno:Sortup",             ID_BROWSER_SORTUP,         CommandGroup::VIEW );
1507     implDescribeSupportedFeature( ".uno:SortDown",           ID_BROWSER_SORTDOWN,       CommandGroup::VIEW );
1508     implDescribeSupportedFeature( ".uno:DBRelationDesign",   SID_DB_APP_DSRELDESIGN,    CommandGroup::APPLICATION );
1509     implDescribeSupportedFeature( ".uno:DBUserAdmin",        SID_DB_APP_DSUSERADMIN,    CommandGroup::APPLICATION );
1510     implDescribeSupportedFeature( ".uno:DBTableFilter",      SID_DB_APP_TABLEFILTER,    CommandGroup::APPLICATION );
1511     implDescribeSupportedFeature( ".uno:DBDSProperties",     SID_DB_APP_DSPROPS,        CommandGroup::EDIT );
1512     implDescribeSupportedFeature( ".uno:DBDSConnectionType", SID_DB_APP_DSCONNECTION_TYPE,
1513                                                                                         CommandGroup::EDIT );
1514     implDescribeSupportedFeature( ".uno:DBDSAdvancedSettings",
1515                                                              SID_DB_APP_DSADVANCED_SETTINGS,
1516                                                                                         CommandGroup::EDIT );
1517     implDescribeSupportedFeature( ".uno:PasteSpecial",       SID_DB_APP_PASTE_SPECIAL,  CommandGroup::EDIT );
1518     implDescribeSupportedFeature( ".uno:DBConvertToView",    SID_DB_APP_CONVERTTOVIEW,  CommandGroup::EDIT );
1519     implDescribeSupportedFeature( ".uno:DBRefreshTables",    SID_DB_APP_REFRESH_TABLES, CommandGroup::APPLICATION );
1520     implDescribeSupportedFeature( ".uno:DBDirectSQL",        ID_DIRECT_SQL,             CommandGroup::APPLICATION );
1521     implDescribeSupportedFeature( ".uno:DBMigrateScripts",   ID_MIGRATE_SCRIPTS,        CommandGroup::APPLICATION );
1522     implDescribeSupportedFeature( ".uno:DBViewTables",       SID_DB_APP_VIEW_TABLES,    CommandGroup::VIEW );
1523     implDescribeSupportedFeature( ".uno:DBViewQueries",      SID_DB_APP_VIEW_QUERIES,   CommandGroup::VIEW );
1524     implDescribeSupportedFeature( ".uno:DBViewForms",        SID_DB_APP_VIEW_FORMS,     CommandGroup::VIEW );
1525     implDescribeSupportedFeature( ".uno:DBViewReports",      SID_DB_APP_VIEW_REPORTS,   CommandGroup::VIEW );
1526     implDescribeSupportedFeature( ".uno:DBDisablePreview",   SID_DB_APP_DISABLE_PREVIEW,CommandGroup::VIEW );
1527     implDescribeSupportedFeature( ".uno:DBShowDocInfoPreview",
1528                                                              SID_DB_APP_VIEW_DOCINFO_PREVIEW,
1529                                                                                         CommandGroup::VIEW );
1530     implDescribeSupportedFeature( ".uno:DBShowDocPreview",   SID_DB_APP_VIEW_DOC_PREVIEW,
1531                                                                                         CommandGroup::VIEW );
1532 
1533     implDescribeSupportedFeature( ".uno:OpenUrl",            SID_OPENURL,               CommandGroup::APPLICATION );
1534 
1535     // this one should not appear under Tools->Customize->Keyboard
1536     implDescribeSupportedFeature( ".uno:DBNewReportWithPreSelection",
1537                                                              SID_APP_NEW_REPORT_PRE_SEL,CommandGroup::INTERNAL );
1538     implDescribeSupportedFeature( ".uno:DBDSImport",        SID_DB_APP_DSIMPORT, CommandGroup::INTERNAL);
1539     implDescribeSupportedFeature( ".uno:DBDSExport",        SID_DB_APP_DSEXPORT, CommandGroup::INTERNAL);
1540     implDescribeSupportedFeature( ".uno:DBDBAdmin",         SID_DB_APP_DBADMIN, CommandGroup::INTERNAL);
1541 
1542     // status info
1543     implDescribeSupportedFeature( ".uno:DBStatusType",      SID_DB_APP_STATUS_TYPE, CommandGroup::INTERNAL);
1544     implDescribeSupportedFeature( ".uno:DBStatusDBName",    SID_DB_APP_STATUS_DBNAME, CommandGroup::INTERNAL);
1545     implDescribeSupportedFeature( ".uno:DBStatusUserName",  SID_DB_APP_STATUS_USERNAME, CommandGroup::INTERNAL);
1546     implDescribeSupportedFeature( ".uno:DBStatusHostName",  SID_DB_APP_STATUS_HOSTNAME, CommandGroup::INTERNAL);
1547 }
1548 // -----------------------------------------------------------------------------
1549 OApplicationView*   OApplicationController::getContainer() const
1550 {
1551     return static_cast< OApplicationView* >( getView() );
1552 }
1553 
1554 // -----------------------------------------------------------------------------
1555 // ::com::sun::star::container::XContainerListener
1556 void SAL_CALL OApplicationController::elementInserted( const ContainerEvent& _rEvent ) throw(RuntimeException)
1557 {
1558     ::vos::OGuard aSolarGuard(Application::GetSolarMutex());
1559     ::osl::MutexGuard aGuard( getMutex() );
1560 
1561     Reference< XContainer > xContainer(_rEvent.Source, UNO_QUERY);
1562     if ( ::std::find(m_aCurrentContainers.begin(),m_aCurrentContainers.end(),xContainer) != m_aCurrentContainers.end() )
1563     {
1564         OSL_ENSURE(getContainer(),"View is NULL! -> GPF");
1565         if ( getContainer() )
1566         {
1567             ::rtl::OUString sName;
1568             _rEvent.Accessor >>= sName;
1569             ElementType eType = getElementType(xContainer);
1570 
1571             switch( eType )
1572             {
1573                 case E_TABLE:
1574                     ensureConnection();
1575                     break;
1576                 case E_FORM:
1577                 case E_REPORT:
1578                     {
1579                         Reference< XContainer > xSubContainer(_rEvent.Element,UNO_QUERY);
1580                         if ( xSubContainer.is() )
1581                             containerFound(xSubContainer);
1582                     }
1583                     break;
1584                 default:
1585                     break;
1586             }
1587             getContainer()->elementAdded(eType,sName,_rEvent.Element);
1588         }
1589     }
1590 }
1591 // -----------------------------------------------------------------------------
1592 void SAL_CALL OApplicationController::elementRemoved( const ContainerEvent& _rEvent ) throw(RuntimeException)
1593 {
1594     ::vos::OGuard aSolarGuard(Application::GetSolarMutex());
1595     ::osl::MutexGuard aGuard( getMutex() );
1596 
1597     Reference< XContainer > xContainer(_rEvent.Source, UNO_QUERY);
1598     if ( ::std::find(m_aCurrentContainers.begin(),m_aCurrentContainers.end(),xContainer) != m_aCurrentContainers.end() )
1599     {
1600         OSL_ENSURE(getContainer(),"View is NULL! -> GPF");
1601         ::rtl::OUString sName;
1602         _rEvent.Accessor >>= sName;
1603         ElementType eType = getElementType(xContainer);
1604         switch( eType )
1605         {
1606             case E_TABLE:
1607                 ensureConnection();
1608                 break;
1609             case E_FORM:
1610             case E_REPORT:
1611                 {
1612                     Reference<XContent> xContent(xContainer,UNO_QUERY);
1613                     if ( xContent.is() )
1614                     {
1615                         sName = xContent->getIdentifier()->getContentIdentifier() + ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("/")) + sName;
1616                     }
1617                 }
1618                 break;
1619             default:
1620                 break;
1621         }
1622         getContainer()->elementRemoved(eType,sName);
1623     }
1624 }
1625 // -----------------------------------------------------------------------------
1626 void SAL_CALL OApplicationController::elementReplaced( const ContainerEvent& _rEvent ) throw(RuntimeException)
1627 {
1628     ::vos::OGuard aSolarGuard(Application::GetSolarMutex());
1629     ::osl::MutexGuard aGuard( getMutex() );
1630 
1631     Reference< XContainer > xContainer(_rEvent.Source, UNO_QUERY);
1632     if ( ::std::find(m_aCurrentContainers.begin(),m_aCurrentContainers.end(),xContainer) != m_aCurrentContainers.end() )
1633     {
1634         OSL_ENSURE(getContainer(),"View is NULL! -> GPF");
1635         ::rtl::OUString sName;
1636         try
1637         {
1638             _rEvent.Accessor >>= sName;
1639             Reference<XConnection> xConnection;
1640             Reference<XPropertySet> xProp(_rEvent.Element,UNO_QUERY);
1641             ::rtl::OUString sNewName;
1642 
1643             ElementType eType = getElementType(xContainer);
1644             switch( eType )
1645             {
1646                 case E_TABLE:
1647                 {
1648                     ensureConnection();
1649                     if ( xProp.is() && m_xMetaData.is() )
1650                         sNewName = ::dbaui::composeTableName( m_xMetaData, xProp, ::dbtools::eInDataManipulation, false, false, false );
1651                 }
1652                 break;
1653                 case E_FORM:
1654                 case E_REPORT:
1655                     {
1656                         Reference<XContent> xContent(xContainer,UNO_QUERY);
1657                         if ( xContent.is() )
1658                         {
1659                             sName = xContent->getIdentifier()->getContentIdentifier() + ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("/")) + sName;
1660                         }
1661                     }
1662                     break;
1663                 default:
1664                     break;
1665             }
1666             //  getContainer()->elementReplaced(getContainer()->getElementType(),sName,sNewName);
1667         }
1668         catch( Exception& )
1669         {
1670             DBG_UNHANDLED_EXCEPTION();
1671         }
1672     }
1673 }
1674 namespace
1675 {
1676     ::rtl::OUString lcl_getToolBarResource(ElementType _eType)
1677     {
1678         ::rtl::OUString sToolbar;
1679         switch(_eType)
1680         {
1681             case E_TABLE:
1682                 sToolbar = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "private:resource/toolbar/tableobjectbar" ));
1683                 break;
1684             case E_QUERY:
1685                 sToolbar = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "private:resource/toolbar/queryobjectbar" ));
1686                 break;
1687             case E_FORM:
1688                 sToolbar = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "private:resource/toolbar/formobjectbar" ));
1689                 break;
1690             case E_REPORT:
1691                 sToolbar = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "private:resource/toolbar/reportobjectbar" ));
1692                 break;
1693             case E_NONE:
1694                 break;
1695             default:
1696                 OSL_ENSURE(0,"Invalid ElementType!");
1697                 break;
1698         }
1699         return sToolbar;
1700     }
1701 }
1702 // -----------------------------------------------------------------------------
1703 sal_Bool OApplicationController::onContainerSelect(ElementType _eType)
1704 {
1705     OSL_ENSURE(getContainer(),"View is NULL! -> GPF");
1706 
1707     if ( m_eCurrentType != _eType && _eType != E_NONE )
1708     {
1709         SelectionGuard aSelGuard( *m_pSelectionNotifier );
1710 
1711         if ( _eType == E_TABLE )
1712         {
1713             try
1714             {
1715                 SharedConnection xConnection( ensureConnection() );
1716                 if ( xConnection.is() && getContainer()->getDetailView() )
1717                 {
1718                     getContainer()->getDetailView()->createTablesPage(xConnection);
1719                     Reference<XTablesSupplier> xTabSup(xConnection,UNO_QUERY);
1720                     if ( xTabSup.is() )
1721                         addContainerListener(xTabSup->getTables());
1722                 }
1723                 else
1724                 {
1725                     return sal_False;
1726                 }
1727             }
1728             catch( const Exception& )
1729             {
1730                 return sal_False;
1731             }
1732         }
1733         Reference< XLayoutManager > xLayoutManager = getLayoutManager( getFrame() );
1734         if ( xLayoutManager.is() )
1735         {
1736             ::rtl::OUString sToolbar = lcl_getToolBarResource(_eType);
1737             ::rtl::OUString sDestroyToolbar = lcl_getToolBarResource(m_eCurrentType);
1738 
1739             xLayoutManager->lock();
1740             xLayoutManager->destroyElement( sDestroyToolbar );
1741             if ( sToolbar.getLength() )
1742             {
1743                 xLayoutManager->createElement( sToolbar );
1744                 xLayoutManager->requestElement( sToolbar );
1745             }
1746             xLayoutManager->unlock();
1747             xLayoutManager->doLayout();
1748         }
1749 
1750         if ( _eType != E_TABLE && getContainer()->getDetailView() )
1751         {
1752             Reference< XNameAccess > xContainer = getElements(_eType);
1753             addContainerListener(xContainer);
1754             getContainer()->getDetailView()->createPage(_eType,xContainer);
1755         }
1756 
1757         SelectionByElementType::iterator pendingSelection = m_aPendingSelection.find( _eType );
1758         if ( pendingSelection != m_aPendingSelection.end() )
1759         {
1760             Sequence< ::rtl::OUString > aSelected( pendingSelection->second.size() );
1761             ::std::copy( pendingSelection->second.begin(), pendingSelection->second.end(), aSelected.getArray() );
1762             getContainer()->selectElements( aSelected );
1763 
1764             m_aPendingSelection.erase( pendingSelection );
1765         }
1766 
1767         InvalidateAll();
1768     }
1769     m_eCurrentType = _eType;
1770 
1771     return sal_True;
1772 }
1773 // -----------------------------------------------------------------------------
1774 bool OApplicationController::onEntryDoubleClick( SvTreeListBox& _rTree )
1775 {
1776     if ( getContainer() && getContainer()->isLeaf( _rTree.GetHdlEntry() ) )
1777     {
1778         try
1779         {
1780             openElement(
1781                 getContainer()->getQualifiedName( _rTree.GetHdlEntry() ),
1782                 getContainer()->getElementType(),
1783                 E_OPEN_NORMAL
1784             );
1785             return true;    // handled
1786         }
1787         catch(const Exception&)
1788         {
1789             DBG_UNHANDLED_EXCEPTION();
1790         }
1791     }
1792     return false;   // not handled
1793 }
1794 // -----------------------------------------------------------------------------
1795 bool OApplicationController::impl_isAlterableView_nothrow( const ::rtl::OUString& _rTableOrViewName ) const
1796 {
1797     OSL_PRECOND( m_xDataSourceConnection.is(), "OApplicationController::impl_isAlterableView_nothrow: no connection!" );
1798 
1799     bool bIsAlterableView( false );
1800     try
1801     {
1802         Reference< XViewsSupplier > xViewsSupp( m_xDataSourceConnection, UNO_QUERY );
1803         Reference< XNameAccess > xViews;
1804         if ( xViewsSupp.is() )
1805             xViews = xViewsSupp->getViews();
1806 
1807         Reference< XAlterView > xAsAlterableView;
1808         if ( xViews.is() && xViews->hasByName( _rTableOrViewName ) )
1809             xAsAlterableView.set( xViews->getByName( _rTableOrViewName ), UNO_QUERY );
1810 
1811         bIsAlterableView = xAsAlterableView.is();
1812     }
1813     catch( const Exception& )
1814     {
1815         DBG_UNHANDLED_EXCEPTION();
1816     }
1817     return bIsAlterableView;
1818 }
1819 
1820 // -----------------------------------------------------------------------------
1821 Reference< XComponent > OApplicationController::openElement(const ::rtl::OUString& _sName, ElementType _eType,
1822     ElementOpenMode _eOpenMode, sal_uInt16 _nInstigatorCommand )
1823 {
1824     return openElementWithArguments( _sName, _eType, _eOpenMode, _nInstigatorCommand, ::comphelper::NamedValueCollection() );
1825 }
1826 
1827 // -----------------------------------------------------------------------------
1828 Reference< XComponent > OApplicationController::openElementWithArguments( const ::rtl::OUString& _sName, ElementType _eType,
1829     ElementOpenMode _eOpenMode, sal_uInt16 _nInstigatorCommand, const ::comphelper::NamedValueCollection& _rAdditionalArguments )
1830 {
1831     OSL_PRECOND( getContainer(), "OApplicationController::openElementWithArguments: no view!" );
1832     if ( !getContainer() )
1833         return NULL;
1834 
1835     Reference< XComponent > xRet;
1836     if ( _eOpenMode == E_OPEN_DESIGN )
1837     {
1838         // OJ: http://www.openoffice.org/issues/show_bug.cgi?id=30382
1839         getContainer()->showPreview(NULL);
1840     }
1841 
1842     bool isStandaloneDocument = false;
1843     switch ( _eType )
1844     {
1845     case E_REPORT:
1846         if ( _eOpenMode != E_OPEN_DESIGN )
1847         {
1848             // reports which are opened in a mode other than design are no sub components of our application
1849             // component, but standalone documents.
1850             isStandaloneDocument = true;
1851         }
1852         // NO break!
1853     case E_FORM:
1854     {
1855         if ( isStandaloneDocument || !m_pSubComponentManager->activateSubFrame( _sName, _eType, _eOpenMode, xRet ) )
1856         {
1857             ::std::auto_ptr< OLinkedDocumentsAccess > aHelper = getDocumentsAccess( _eType );
1858             if ( !aHelper->isConnected() )
1859                 break;
1860 
1861             Reference< XComponent > xDefinition;
1862             xRet = aHelper->open( _sName, xDefinition, _eOpenMode, _rAdditionalArguments );
1863 
1864             if ( !isStandaloneDocument )
1865                 onDocumentOpened( _sName, _eType, _eOpenMode, xRet, xDefinition );
1866         }
1867     }
1868     break;
1869 
1870     case E_QUERY:
1871     case E_TABLE:
1872     {
1873         if ( !m_pSubComponentManager->activateSubFrame( _sName, _eType, _eOpenMode, xRet ) )
1874         {
1875             SharedConnection xConnection( ensureConnection() );
1876             if ( !xConnection.is() )
1877                 break;
1878 
1879             ::std::auto_ptr< DatabaseObjectView > pDesigner;
1880             ::comphelper::NamedValueCollection aArguments( _rAdditionalArguments );
1881 
1882             Any aDataSource;
1883             if ( _eOpenMode == E_OPEN_DESIGN )
1884             {
1885                 bool bAddViewTypeArg = false;
1886 
1887                 if ( _eType == E_TABLE )
1888                 {
1889                     if ( impl_isAlterableView_nothrow( _sName ) )
1890                     {
1891                         pDesigner.reset( new QueryDesigner( getORB(), this, m_aCurrentFrame.getFrame(), true ) );
1892                         bAddViewTypeArg = true;
1893                     }
1894                     else
1895                     {
1896                         pDesigner.reset( new TableDesigner( getORB(), this, m_aCurrentFrame.getFrame() ) );
1897                     }
1898                 }
1899                 else if ( _eType == E_QUERY )
1900                 {
1901                     pDesigner.reset( new QueryDesigner( getORB(), this, m_aCurrentFrame.getFrame(), false ) );
1902                     bAddViewTypeArg = true;
1903                 }
1904                 aDataSource <<= m_xDataSource;
1905 
1906                 if ( bAddViewTypeArg )
1907                 {
1908                     const bool bQueryGraphicalMode =( _nInstigatorCommand != SID_DB_APP_EDIT_SQL_VIEW );
1909                     aArguments.put( (::rtl::OUString)PROPERTY_GRAPHICAL_DESIGN, bQueryGraphicalMode );
1910                 }
1911 
1912             }
1913             else
1914             {
1915                 pDesigner.reset( new ResultSetBrowser( getORB(), this, m_aCurrentFrame.getFrame(), _eType == E_TABLE ) );
1916 
1917                 if ( !aArguments.has( (::rtl::OUString)PROPERTY_SHOWMENU ) )
1918                     aArguments.put( (::rtl::OUString)PROPERTY_SHOWMENU, makeAny( (sal_Bool)sal_True ) );
1919 
1920                 aDataSource <<= getDatabaseName();
1921             }
1922 
1923             xRet.set( pDesigner->openExisting( aDataSource, _sName, aArguments ) );
1924             onDocumentOpened( _sName, _eType, _eOpenMode, xRet, NULL );
1925         }
1926     }
1927     break;
1928 
1929     default:
1930         OSL_ENSURE( false, "OApplicationController::openElement: illegal object type!" );
1931         break;
1932     }
1933     return xRet;
1934 }
1935 // -----------------------------------------------------------------------------
1936 IMPL_LINK( OApplicationController, OnSelectContainer, void*, _pType )
1937 {
1938     ElementType eType = (ElementType)reinterpret_cast< sal_IntPtr >( _pType );
1939     getContainer()->selectContainer(eType);
1940     return 0L;
1941 }
1942 // -----------------------------------------------------------------------------
1943 IMPL_LINK( OApplicationController, OnCreateWithPilot, void*, _pType )
1944 {
1945     ElementType eType = (ElementType)reinterpret_cast< sal_IntPtr >( _pType );
1946     newElementWithPilot( eType );
1947     return 0L;
1948 }
1949 
1950 // -----------------------------------------------------------------------------
1951 void OApplicationController::newElementWithPilot( ElementType _eType )
1952 {
1953     CloseVeto aKeepDoc( getFrame() );
1954         // prevent the document being closed while the wizard is open
1955 
1956     OSL_ENSURE( getContainer(), "OApplicationController::newElementWithPilot: without a view?" );
1957 
1958     switch ( _eType )
1959     {
1960         case E_REPORT:
1961         case E_FORM:
1962         {
1963             ::std::auto_ptr<OLinkedDocumentsAccess> aHelper = getDocumentsAccess(_eType);
1964             if ( aHelper->isConnected() )
1965             {
1966                 sal_Int32 nCommandType = -1;
1967                 const ::rtl::OUString sCurrentSelected( getCurrentlySelectedName( nCommandType ) );
1968                 if ( E_REPORT == _eType )
1969                     aHelper->newReportWithPilot( nCommandType, sCurrentSelected );
1970                 else
1971                     aHelper->newFormWithPilot( nCommandType, sCurrentSelected );
1972             }
1973         }
1974         break;
1975         case E_QUERY:
1976         case E_TABLE:
1977         {
1978             ::std::auto_ptr<OLinkedDocumentsAccess> aHelper = getDocumentsAccess(_eType);
1979             if ( aHelper->isConnected() )
1980             {
1981                 if ( E_QUERY == _eType )
1982                     aHelper->newQueryWithPilot();
1983                 else
1984                     aHelper->newTableWithPilot();
1985             }
1986         }
1987         break;
1988         case E_NONE:
1989             break;
1990     }
1991 
1992     // no need for onDocumentOpened, the table wizard opens the created table by using
1993     // XDatabaseDocumentUI::loadComponent method.
1994 }
1995 
1996 // -----------------------------------------------------------------------------
1997 Reference< XComponent > OApplicationController::newElement( ElementType _eType, const ::comphelper::NamedValueCollection& i_rAdditionalArguments,
1998                                                            Reference< XComponent >& o_rDocumentDefinition )
1999 {
2000     OSL_ENSURE(getContainer(),"View is NULL! -> GPF");
2001 
2002     Reference< XComponent > xComponent;
2003     o_rDocumentDefinition.clear();
2004 
2005     switch ( _eType )
2006     {
2007         case E_FORM:
2008         case E_REPORT:
2009         {
2010             ::std::auto_ptr<OLinkedDocumentsAccess> aHelper = getDocumentsAccess( _eType );
2011             if ( !aHelper->isConnected() )
2012                 break;
2013 
2014             xComponent = aHelper->newDocument( _eType == E_FORM ? ID_FORM_NEW_TEXT : ID_REPORT_NEW_TEXT, i_rAdditionalArguments, o_rDocumentDefinition );
2015         }
2016         break;
2017 
2018         case E_QUERY:
2019         case E_TABLE:
2020         {
2021             ::std::auto_ptr< DatabaseObjectView > pDesigner;
2022             SharedConnection xConnection( ensureConnection() );
2023             if ( !xConnection.is() )
2024                 break;
2025 
2026             if ( _eType == E_TABLE )
2027             {
2028                 pDesigner.reset( new TableDesigner( getORB(), this, getFrame() ) );
2029             }
2030             else if ( _eType == E_QUERY )
2031             {
2032                 pDesigner.reset( new QueryDesigner( getORB(), this, getFrame(), false ) );
2033             }
2034 
2035             Reference< XDataSource > xDataSource( m_xDataSource, UNO_QUERY );
2036             xComponent.set( pDesigner->createNew( xDataSource, i_rAdditionalArguments ), UNO_QUERY );
2037         }
2038         break;
2039 
2040         default:
2041             OSL_ENSURE( false, "OApplicationController::newElement: illegal type!" );
2042             break;
2043     }
2044 
2045     if ( xComponent.is() )
2046         onDocumentOpened( ::rtl::OUString(), _eType, E_OPEN_DESIGN, xComponent, o_rDocumentDefinition );
2047 
2048     return xComponent;
2049 }
2050 
2051 // -----------------------------------------------------------------------------
2052 void OApplicationController::addContainerListener(const Reference<XNameAccess>& _xCollection)
2053 {
2054     try
2055     {
2056         Reference< XContainer > xCont(_xCollection, UNO_QUERY);
2057         if ( xCont.is() )
2058         {
2059             // add as listener to get notified if elements are inserted or removed
2060             TContainerVector::iterator aFind = ::std::find(m_aCurrentContainers.begin(),m_aCurrentContainers.end(),xCont);
2061             if ( aFind == m_aCurrentContainers.end() )
2062             {
2063                 xCont->addContainerListener(this);
2064                 m_aCurrentContainers.push_back(xCont);
2065             }
2066         }
2067     }
2068     catch( const Exception& )
2069     {
2070         DBG_UNHANDLED_EXCEPTION();
2071     }
2072 }
2073 // -----------------------------------------------------------------------------
2074 void OApplicationController::renameEntry()
2075 {
2076     ::vos::OGuard aSolarGuard(Application::GetSolarMutex());
2077     ::osl::MutexGuard aGuard( getMutex() );
2078 
2079     OSL_ENSURE(getContainer(),"View is NULL! -> GPF");
2080     ::std::vector< ::rtl::OUString> aList;
2081     getSelectionElementNames(aList);
2082 
2083     Reference< XNameAccess > xContainer = getElements(getContainer()->getElementType());
2084     OSL_ENSURE(aList.size() == 1,"Invalid rename call here. More than one element!");
2085     if ( aList.empty() )
2086         return;
2087 
2088     try
2089     {
2090         if ( xContainer.is() )
2091         {
2092             ::std::auto_ptr< IObjectNameCheck > pNameChecker;
2093             ::std::auto_ptr< OSaveAsDlg > aDialog;
2094 
2095             Reference<XRename> xRename;
2096             const ElementType eType = getContainer()->getElementType();
2097             switch( eType )
2098             {
2099                 case E_FORM:
2100                 case E_REPORT:
2101                     {
2102                         Reference<XHierarchicalNameContainer> xHNames(xContainer, UNO_QUERY);
2103                         if ( xHNames.is() )
2104                         {
2105                             String sLabel;
2106                             if ( eType == E_FORM )
2107                                 sLabel = String(ModuleRes( STR_FRM_LABEL ));
2108                             else
2109                                 sLabel = String(ModuleRes( STR_RPT_LABEL ));
2110 
2111                             ::rtl::OUString sName = *aList.begin();
2112                             if ( xHNames->hasByHierarchicalName(sName) )
2113                             {
2114                                 xRename.set(xHNames->getByHierarchicalName(sName),UNO_QUERY);
2115                                 Reference<XChild> xChild(xRename,UNO_QUERY);
2116                                 if ( xChild.is() )
2117                                 {
2118                                     Reference<XHierarchicalNameContainer> xParent(xChild->getParent(),UNO_QUERY);
2119                                     if ( xParent.is() )
2120                                     {
2121                                         xHNames = xParent;
2122                                         Reference<XPropertySet>(xRename,UNO_QUERY)->getPropertyValue(PROPERTY_NAME) >>= sName;
2123                                     }
2124                                 }
2125                                 pNameChecker.reset( new HierarchicalNameCheck( xHNames.get(), String() ) );
2126                                 aDialog.reset( new OSaveAsDlg(
2127                                     getView(), getORB(), sName, sLabel, *pNameChecker, SAD_TITLE_RENAME ) );
2128                             }
2129                         }
2130                     }
2131                     break;
2132                 case E_TABLE:
2133                     ensureConnection();
2134                     if ( !getConnection().is() )
2135                         break;
2136                     // NO break
2137                 case E_QUERY:
2138                     if ( xContainer->hasByName(*aList.begin()) )
2139                     {
2140                         xRename.set(xContainer->getByName(*aList.begin()),UNO_QUERY);
2141                         sal_Int32 nCommandType = eType == E_QUERY ? CommandType::QUERY : CommandType::TABLE;
2142 
2143                         ensureConnection();
2144                         pNameChecker.reset( new DynamicTableOrQueryNameCheck( getConnection(), nCommandType ) );
2145                         aDialog.reset( new OSaveAsDlg(
2146                             getView(), nCommandType, getORB(), getConnection(),
2147                                 *aList.begin(), *pNameChecker, SAD_TITLE_RENAME ) );
2148                     }
2149                     break;
2150                 default:
2151                     break;
2152             }
2153 
2154             if ( xRename.is() && aDialog.get() )
2155             {
2156 
2157                 sal_Bool bTryAgain = sal_True;
2158                 while( bTryAgain )
2159                 {
2160                     if ( aDialog->Execute() == RET_OK )
2161                     {
2162                         try
2163                         {
2164                             ::rtl::OUString sNewName;
2165                             if ( eType == E_TABLE )
2166                             {
2167                                 ::rtl::OUString sName = aDialog->getName();
2168                                 ::rtl::OUString sCatalog = aDialog->getCatalog();
2169                                 ::rtl::OUString sSchema  = aDialog->getSchema();
2170 
2171                                 sNewName = ::dbtools::composeTableName( m_xMetaData, sCatalog, sSchema, sName, sal_False, ::dbtools::eInDataManipulation );
2172                             }
2173                             else
2174                                 sNewName = aDialog->getName();
2175 
2176                             ::rtl::OUString sOldName = *aList.begin();
2177                             if ( eType == E_FORM || eType == E_REPORT )
2178                             {
2179                                 Reference<XContent> xContent(xRename,UNO_QUERY);
2180                                 if ( xContent.is() )
2181                                 {
2182                                     sOldName = xContent->getIdentifier()->getContentIdentifier();
2183                                 }
2184                             }
2185 
2186                             xRename->rename(sNewName);
2187 
2188                             if ( eType == E_TABLE )
2189                             {
2190                                 Reference<XPropertySet> xProp(xRename,UNO_QUERY);
2191                                 sNewName = ::dbaui::composeTableName( m_xMetaData, xProp, ::dbtools::eInDataManipulation, false, false, false );
2192                             }
2193                             getContainer()->elementReplaced( eType , sOldName, sNewName );
2194 
2195                             bTryAgain = sal_False;
2196                         }
2197                         catch(const SQLException& )
2198                         {
2199                             showError( SQLExceptionInfo( ::cppu::getCaughtException() ) );
2200 
2201                         }
2202                         catch(const ElementExistException& e)
2203                         {
2204                             static ::rtl::OUString sStatus = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("S1000"));
2205                             String sMsg = String( ModuleRes( STR_NAME_ALREADY_EXISTS ) );
2206                             sMsg.SearchAndReplace('#',e.Message);
2207                             showError(SQLExceptionInfo(SQLException(sMsg, e.Context, sStatus, 0, Any())));
2208                         }
2209                         catch(const Exception& )
2210                         {
2211                             DBG_UNHANDLED_EXCEPTION();
2212                         }
2213                     }
2214                     else
2215                         bTryAgain = sal_False;
2216                 }
2217             }
2218         }
2219     }
2220     catch(const Exception& )
2221     {
2222         DBG_UNHANDLED_EXCEPTION();
2223     }
2224 }
2225 
2226 // -----------------------------------------------------------------------------
2227 void OApplicationController::onSelectionChanged()
2228 {
2229     InvalidateAll();
2230 
2231     SelectionGuard aSelGuard( *m_pSelectionNotifier );
2232 
2233     OApplicationView* pView = getContainer();
2234     if ( !pView )
2235         return;
2236 
2237     if ( pView->getSelectionCount() == 1 )
2238     {
2239         const ElementType eType = pView->getElementType();
2240         if ( pView->isALeafSelected() )
2241         {
2242             const ::rtl::OUString sName = pView->getQualifiedName( NULL /* means 'first selected' */ );
2243             showPreviewFor( eType, sName );
2244         }
2245     }
2246 }
2247 // -----------------------------------------------------------------------------
2248 void OApplicationController::showPreviewFor(const ElementType _eType,const ::rtl::OUString& _sName)
2249 {
2250     if ( m_ePreviewMode == E_PREVIEWNONE )
2251         return;
2252 
2253     OApplicationView* pView = getContainer();
2254     if ( !pView )
2255         return;
2256 
2257     try
2258     {
2259         switch( _eType )
2260         {
2261             case E_FORM:
2262             case E_REPORT:
2263             {
2264                 Reference< XHierarchicalNameAccess > xContainer( getElements( _eType ), UNO_QUERY_THROW );
2265                 Reference< XContent> xContent( xContainer->getByHierarchicalName( _sName ), UNO_QUERY_THROW );
2266                 pView->showPreview( xContent );
2267             }
2268             break;
2269 
2270             case E_TABLE:
2271             case E_QUERY:
2272                 {
2273                     SharedConnection xConnection( ensureConnection() );
2274                     if ( xConnection.is() )
2275                         pView->showPreview( getDatabaseName(), xConnection, _sName, _eType == E_TABLE );
2276                 }
2277                 return;
2278 
2279             default:
2280                 OSL_ENSURE( false, "OApplicationController::showPreviewFor: unexpected element type!" );
2281                 break;
2282         }
2283     }
2284     catch( const SQLException& )
2285     {
2286         showError( SQLExceptionInfo( ::cppu::getCaughtException() ) );
2287     }
2288     catch(const Exception& )
2289     {
2290         DBG_UNHANDLED_EXCEPTION();
2291     }
2292 }
2293 
2294 //------------------------------------------------------------------------------
2295 IMPL_LINK( OApplicationController, OnClipboardChanged, void*, EMPTYARG )
2296 {
2297     return OnInvalidateClipboard( NULL );
2298 }
2299 //------------------------------------------------------------------------------
2300 IMPL_LINK(OApplicationController, OnInvalidateClipboard, void*, EMPTYARG)
2301 {
2302     InvalidateFeature(ID_BROWSER_CUT);
2303     InvalidateFeature(ID_BROWSER_COPY);
2304     InvalidateFeature(ID_BROWSER_PASTE);
2305     InvalidateFeature(SID_DB_APP_PASTE_SPECIAL);
2306     return 0L;
2307 }
2308 // -----------------------------------------------------------------------------
2309 void OApplicationController::onCutEntry()
2310 {
2311 }
2312 // -----------------------------------------------------------------------------
2313 void OApplicationController::onCopyEntry()
2314 {
2315     Execute(ID_BROWSER_COPY,Sequence<PropertyValue>());
2316 }
2317 // -----------------------------------------------------------------------------
2318 void OApplicationController::onPasteEntry()
2319 {
2320     Execute(ID_BROWSER_PASTE,Sequence<PropertyValue>());
2321 }
2322 // -----------------------------------------------------------------------------
2323 void OApplicationController::onDeleteEntry()
2324 {
2325     ElementType eType = getContainer()->getElementType();
2326     sal_uInt16 nId = 0;
2327     switch(eType)
2328     {
2329         case E_TABLE:
2330             nId = SID_DB_APP_TABLE_DELETE;
2331             break;
2332         case E_QUERY:
2333             nId = SID_DB_APP_QUERY_DELETE;
2334             break;
2335         case E_FORM:
2336             nId = SID_DB_APP_FORM_DELETE;
2337             break;
2338         case E_REPORT:
2339             nId = SID_DB_APP_REPORT_DELETE;
2340             break;
2341         default:
2342             OSL_ENSURE(0,"Invalid ElementType!");
2343             break;
2344     }
2345     executeChecked(nId,Sequence<PropertyValue>());
2346 }
2347 
2348 // -----------------------------------------------------------------------------
2349 void OApplicationController::executeUnChecked(const URL& _rCommand, const Sequence< PropertyValue>& aArgs)
2350 {
2351     OApplicationController_CBASE::executeUnChecked( _rCommand, aArgs );
2352 }
2353 
2354 // -----------------------------------------------------------------------------
2355 void OApplicationController::executeChecked(const URL& _rCommand, const Sequence< PropertyValue>& aArgs)
2356 {
2357     OApplicationController_CBASE::executeChecked( _rCommand, aArgs );
2358 }
2359 
2360 // -----------------------------------------------------------------------------
2361 void OApplicationController::executeUnChecked(sal_uInt16 _nCommandId, const Sequence< PropertyValue>& aArgs)
2362 {
2363     OApplicationController_CBASE::executeUnChecked( _nCommandId, aArgs );
2364 }
2365 
2366 // -----------------------------------------------------------------------------
2367 void OApplicationController::executeChecked(sal_uInt16 _nCommandId, const Sequence< PropertyValue>& aArgs)
2368 {
2369     OApplicationController_CBASE::executeChecked( _nCommandId, aArgs );
2370 }
2371 
2372 // -----------------------------------------------------------------------------
2373 sal_Bool OApplicationController::isCommandEnabled(sal_uInt16 _nCommandId) const
2374 {
2375     return OApplicationController_CBASE::isCommandEnabled( _nCommandId );
2376 }
2377 
2378 // -----------------------------------------------------------------------------
2379 sal_Bool OApplicationController::isCommandEnabled( const ::rtl::OUString& _rCompleteCommandURL ) const
2380 {
2381     return OApplicationController_CBASE::isCommandEnabled( _rCompleteCommandURL );
2382 }
2383 
2384 // -----------------------------------------------------------------------------
2385 sal_uInt16 OApplicationController::registerCommandURL( const ::rtl::OUString& _rCompleteCommandURL )
2386 {
2387     return OApplicationController_CBASE::registerCommandURL( _rCompleteCommandURL );
2388 }
2389 
2390 // -----------------------------------------------------------------------------
2391 void OApplicationController::notifyHiContrastChanged()
2392 {
2393     OApplicationController_CBASE::notifyHiContrastChanged();
2394 }
2395 
2396 // -----------------------------------------------------------------------------
2397 Reference< XController > OApplicationController::getXController() throw( RuntimeException )
2398 {
2399     return OApplicationController_CBASE::getXController();
2400 }
2401 
2402 // -----------------------------------------------------------------------------
2403 bool OApplicationController::interceptUserInput( const NotifyEvent& _rEvent )
2404 {
2405     return OApplicationController_CBASE::interceptUserInput( _rEvent );
2406 }
2407 
2408 // -----------------------------------------------------------------------------
2409 PopupMenu* OApplicationController::getContextMenu( Control& /*_rControl*/ ) const
2410 {
2411     return new PopupMenu( ModuleRes( RID_MENU_APP_EDIT ) );
2412 }
2413 
2414 // -----------------------------------------------------------------------------
2415 IController& OApplicationController::getCommandController()
2416 {
2417     return *static_cast< IApplicationController* >( this );
2418 }
2419 
2420 // -----------------------------------------------------------------------------
2421 ::cppu::OInterfaceContainerHelper* OApplicationController::getContextMenuInterceptors()
2422 {
2423     return &m_aContextMenuInterceptors;
2424 }
2425 
2426 // -----------------------------------------------------------------------------
2427 Any OApplicationController::getCurrentSelection( Control& _rControl ) const
2428 {
2429     Sequence< NamedDatabaseObject > aSelection;
2430     getContainer()->describeCurrentSelectionForControl( _rControl, aSelection );
2431     return makeAny( aSelection );
2432 }
2433 
2434 // -----------------------------------------------------------------------------
2435 sal_Bool OApplicationController::requestQuickHelp( const SvLBoxEntry* /*_pEntry*/, String& /*_rText*/ ) const
2436 {
2437     return sal_False;
2438 }
2439 
2440 // -----------------------------------------------------------------------------
2441 sal_Bool OApplicationController::requestDrag( sal_Int8 /*_nAction*/, const Point& /*_rPosPixel*/ )
2442 {
2443     TransferableHelper* pTransfer = NULL;
2444     if ( getContainer() && getContainer()->getSelectionCount() )
2445     {
2446         try
2447         {
2448             pTransfer = copyObject( );
2449             Reference< XTransferable> xEnsureDelete = pTransfer;
2450 
2451             if ( pTransfer && getContainer()->getDetailView() )
2452             {
2453                 ElementType eType = getContainer()->getElementType();
2454                 pTransfer->StartDrag( getContainer()->getDetailView()->getTreeWindow(), ((eType == E_FORM || eType == E_REPORT) ? DND_ACTION_COPYMOVE : DND_ACTION_COPY) );
2455             }
2456         }
2457         catch(const Exception& )
2458         {
2459             DBG_UNHANDLED_EXCEPTION();
2460         }
2461     }
2462 
2463     return NULL != pTransfer;
2464 }
2465 // -----------------------------------------------------------------------------
2466 sal_Int8 OApplicationController::queryDrop( const AcceptDropEvent& _rEvt, const DataFlavorExVector& _rFlavors )
2467 {
2468     sal_Int8 nActionAskedFor = _rEvt.mnAction;
2469     // check if we're a table or query container
2470     OApplicationView* pView = getContainer();
2471     if ( pView && !isDataSourceReadOnly() )
2472     {
2473         ElementType eType = pView->getElementType();
2474         if ( eType != E_NONE && (eType != E_TABLE || !isConnectionReadOnly()) )
2475         {
2476             // check for the concrete type
2477             if(::std::find_if(_rFlavors.begin(),_rFlavors.end(),TAppSupportedSotFunctor(eType,sal_True)) != _rFlavors.end())
2478                 return DND_ACTION_COPY;
2479             if ( eType == E_FORM || eType == E_REPORT )
2480             {
2481                 sal_Int8 nAction = OComponentTransferable::canExtractComponentDescriptor(_rFlavors,eType == E_FORM) ? DND_ACTION_COPY : DND_ACTION_NONE;
2482                 if ( nAction != DND_ACTION_NONE )
2483                 {
2484                     SvLBoxEntry* pHitEntry = pView->getEntry(_rEvt.maPosPixel);
2485                     ::rtl::OUString sName;
2486                     if ( pHitEntry )
2487                     {
2488                         sName = pView->getQualifiedName( pHitEntry );
2489                         if ( sName.getLength() )
2490                         {
2491                             Reference< XHierarchicalNameAccess > xContainer(getElements(pView->getElementType()),UNO_QUERY);
2492                             if ( xContainer.is() && xContainer->hasByHierarchicalName(sName) )
2493                             {
2494                                 Reference< XHierarchicalNameAccess > xHitObject(xContainer->getByHierarchicalName(sName),UNO_QUERY);
2495                                 if ( xHitObject.is() )
2496                                     nAction = nActionAskedFor & DND_ACTION_COPYMOVE;
2497                             }
2498                             else
2499                                 nAction = DND_ACTION_NONE;
2500                         }
2501                     }
2502                     /*else
2503                         nAction = nActionAskedFor & DND_ACTION_COPYMOVE;
2504                     */
2505                 }
2506                 return nAction;
2507             }
2508         }
2509     }
2510 
2511     return DND_ACTION_NONE;
2512 }
2513 // -----------------------------------------------------------------------------
2514 sal_Int8 OApplicationController::executeDrop( const ExecuteDropEvent& _rEvt )
2515 {
2516     OApplicationView* pView = getContainer();
2517     if ( !pView || pView->getElementType() == E_NONE )
2518     {
2519         DBG_ERROR("OApplicationController::executeDrop: what the hell did queryDrop do?");
2520             // queryDrop shoud not have allowed us to reach this situation ....
2521         return DND_ACTION_NONE;
2522     }
2523 
2524     // a TransferableDataHelper for accessing the dropped data
2525     TransferableDataHelper aDroppedData(_rEvt.maDropEvent.Transferable);
2526 
2527 
2528     // reset the data of the previous async drop (if any)
2529     if ( m_nAsyncDrop )
2530         Application::RemoveUserEvent(m_nAsyncDrop);
2531 
2532 
2533     m_nAsyncDrop = 0;
2534     m_aAsyncDrop.aDroppedData.clear();
2535     m_aAsyncDrop.nType          = pView->getElementType();
2536     m_aAsyncDrop.nAction        = _rEvt.mnAction;
2537     m_aAsyncDrop.bError         = sal_False;
2538     m_aAsyncDrop.bHtml          = sal_False;
2539     m_aAsyncDrop.aUrl           = ::rtl::OUString();
2540 
2541 
2542     // loop through the available formats and see what we can do ...
2543     // first we have to check if it is our own format, if not we have to copy the stream :-(
2544     if ( ODataAccessObjectTransferable::canExtractObjectDescriptor(aDroppedData.GetDataFlavorExVector()) )
2545     {
2546         m_aAsyncDrop.aDroppedData   = ODataAccessObjectTransferable::extractObjectDescriptor(aDroppedData);
2547 
2548         // asyncron because we some dialogs and we aren't allowed to show them while in D&D
2549         m_nAsyncDrop = Application::PostUserEvent(LINK(this, OApplicationController, OnAsyncDrop));
2550         return DND_ACTION_COPY;
2551     }
2552     else if ( OComponentTransferable::canExtractComponentDescriptor(aDroppedData.GetDataFlavorExVector(),m_aAsyncDrop.nType == E_FORM) )
2553     {
2554         m_aAsyncDrop.aDroppedData = OComponentTransferable::extractComponentDescriptor(aDroppedData);
2555         SvLBoxEntry* pHitEntry = pView->getEntry(_rEvt.maPosPixel);
2556         if ( pHitEntry )
2557             m_aAsyncDrop.aUrl = pView->getQualifiedName( pHitEntry );
2558 
2559         sal_Int8 nAction = _rEvt.mnAction;
2560         Reference<XContent> xContent;
2561         m_aAsyncDrop.aDroppedData[daComponent] >>= xContent;
2562         if ( xContent.is() )
2563         {
2564             ::rtl::OUString sName = xContent->getIdentifier()->getContentIdentifier();
2565             sal_Int32 nIndex = 0;
2566             sName = sName.copy(sName.getToken(0,'/',nIndex).getLength() + 1);
2567             if ( m_aAsyncDrop.aUrl.Len() >= sName.getLength() && 0 == sName.compareTo(m_aAsyncDrop.aUrl,sName.getLength()) )
2568             {
2569                 m_aAsyncDrop.aDroppedData.clear();
2570                 return DND_ACTION_NONE;
2571             }
2572 
2573             // check if move is allowed, if another object with the same name exists only copy is allowed
2574             Reference< XHierarchicalNameAccess > xContainer(getElements(m_aAsyncDrop.nType),UNO_QUERY);
2575             Reference<XNameAccess> xNameAccess(xContainer,UNO_QUERY);
2576 
2577             if ( m_aAsyncDrop.aUrl.Len() && xContainer.is() && xContainer->hasByHierarchicalName(m_aAsyncDrop.aUrl) )
2578                 xNameAccess.set(xContainer->getByHierarchicalName(m_aAsyncDrop.aUrl),UNO_QUERY);
2579 
2580             if ( xNameAccess.is() )
2581             {
2582                 Reference<XPropertySet> xProp(xContent,UNO_QUERY);
2583                 if ( xProp.is() )
2584                 {
2585                     xProp->getPropertyValue(PROPERTY_NAME) >>= sName;
2586                     if ( xNameAccess.is() && xNameAccess->hasByName(sName) )
2587                         nAction &= ~DND_ACTION_MOVE;
2588                 }
2589                 else
2590                     nAction &= ~DND_ACTION_MOVE;
2591             }
2592         }
2593         if ( nAction != DND_ACTION_NONE )
2594         {
2595             m_aAsyncDrop.nAction = nAction;
2596             // asyncron because we some dialogs and we aren't allowed to show them while in D&D
2597             m_nAsyncDrop = Application::PostUserEvent(LINK(this, OApplicationController, OnAsyncDrop));
2598         }
2599         else
2600             m_aAsyncDrop.aDroppedData.clear();
2601         return nAction;
2602     }
2603     else
2604     {
2605         SharedConnection xConnection( ensureConnection() );
2606         if ( xConnection.is() && m_aTableCopyHelper.copyTagTable( aDroppedData, m_aAsyncDrop, xConnection ) )
2607         {
2608             // asyncron because we some dialogs and we aren't allowed to show them while in D&D
2609             m_nAsyncDrop = Application::PostUserEvent(LINK(this, OApplicationController, OnAsyncDrop));
2610             return DND_ACTION_COPY;
2611         }
2612     }
2613 
2614     return DND_ACTION_NONE;
2615 }
2616 // -----------------------------------------------------------------------------
2617 Reference< XModel >  SAL_CALL OApplicationController::getModel(void) throw( RuntimeException )
2618 {
2619     return m_xModel;
2620 }
2621 
2622 // -----------------------------------------------------------------------------
2623 void OApplicationController::onAttachedFrame()
2624 {
2625     sal_Int32 nConnectedControllers( 0 );
2626     try
2627     {
2628         Reference< XModel2 > xModel( m_xModel, UNO_QUERY_THROW );
2629         Reference< XEnumeration > xEnumControllers( xModel->getControllers(), UNO_SET_THROW );
2630         while ( xEnumControllers->hasMoreElements() )
2631         {
2632             Reference< XController > xController( xEnumControllers->nextElement(), UNO_QUERY_THROW );
2633             ++nConnectedControllers;
2634         }
2635     }
2636     catch( const Exception& )
2637     {
2638         DBG_UNHANDLED_EXCEPTION();
2639     }
2640 
2641     if ( nConnectedControllers > 1 )
2642     {   // we are not the first connected controller, there were already others
2643         return;
2644     }
2645 
2646     m_aControllerConnectedEvent.Call();
2647 }
2648 
2649 // -----------------------------------------------------------------------------
2650 IMPL_LINK( OApplicationController, OnFirstControllerConnected, void*, /**/ )
2651 {
2652     ::osl::MutexGuard aGuard( getMutex() );
2653 
2654     if ( !m_xModel.is() )
2655     {
2656         OSL_ENSURE( false, "OApplicationController::OnFirstControllerConnected: too late!" );
2657     }
2658 
2659     // if we have forms or reports which contain macros/scripts, then show a warning
2660     // which suggests the user to migrate them to the database document
2661     Reference< XEmbeddedScripts > xDocumentScripts( m_xModel, UNO_QUERY );
2662     if ( xDocumentScripts.is() )
2663     {
2664         // no need to show this warning, obviously the document supports embedding scripts
2665         // into itself, so there are no "old-style" forms/reports which have macros/scripts
2666         // themselves
2667         return 0L;
2668     }
2669 
2670     try
2671     {
2672         // If the migration just happened, but was not successful, the document is reloaded.
2673         // In this case, we should not show the warning, again.
2674         ::comphelper::NamedValueCollection aModelArgs( m_xModel->getArgs() );
2675         if ( aModelArgs.getOrDefault( "SuppressMigrationWarning", sal_False ) )
2676             return 0L;
2677 
2678         // also, if the document is read-only, then no migration is possible, and the
2679         // respective menu entry is hidden. So, don't show the warning in this case, too.
2680         if ( Reference< XStorable >( m_xModel, UNO_QUERY_THROW )->isReadonly() )
2681             return 0L;
2682 
2683         SQLWarning aWarning;
2684         aWarning.Message = String( ModuleRes( STR_SUB_DOCS_WITH_SCRIPTS ) );
2685         SQLException aDetail;
2686         aDetail.Message = String( ModuleRes( STR_SUB_DOCS_WITH_SCRIPTS_DETAIL ) );
2687         aWarning.NextException <<= aDetail;
2688 
2689         ::comphelper::ComponentContext aContext( getORB() );
2690         Sequence< Any > aArgs(1);
2691         aArgs[0] <<= NamedValue( PROPERTY_SQLEXCEPTION, makeAny( aWarning ) );
2692         Reference< XExecutableDialog > xDialog(
2693             aContext.createComponentWithArguments( "com.sun.star.sdb.ErrorMessageDialog", aArgs ),
2694             UNO_QUERY_THROW );
2695         xDialog->execute();
2696     }
2697     catch( const Exception& )
2698     {
2699         DBG_UNHANDLED_EXCEPTION();
2700     }
2701 
2702     return 1L;
2703 }
2704 
2705 // -----------------------------------------------------------------------------
2706 void SAL_CALL OApplicationController::attachFrame( const Reference< XFrame > & i_rxFrame ) throw( RuntimeException )
2707 {
2708     OApplicationController_CBASE::attachFrame( i_rxFrame );
2709     if ( getFrame().is() )
2710         onAttachedFrame();
2711 }
2712 
2713 // -----------------------------------------------------------------------------
2714 sal_Bool SAL_CALL OApplicationController::attachModel(const Reference< XModel > & _rxModel) throw( RuntimeException )
2715 {
2716     ::osl::MutexGuard aGuard( getMutex() );
2717     const Reference< XOfficeDatabaseDocument > xOfficeDoc( _rxModel, UNO_QUERY );
2718     const Reference< XModifiable > xDocModify( _rxModel, UNO_QUERY );
2719     if ( ( !xOfficeDoc.is() || !xDocModify.is() ) && _rxModel.is() )
2720     {
2721         DBG_ERROR( "OApplicationController::attachModel: invalid model!" );
2722         return sal_False;
2723     }
2724 
2725     if ( m_xModel.is() && ( m_xModel != _rxModel ) && ( _rxModel.is() ) )
2726     {
2727         OSL_ENSURE( false, "OApplicationController::attachModel: missing implementation: setting a new model while we have another one!" );
2728         // we'd need to completely update our view here, close sub components, and the like
2729         return sal_False;
2730     }
2731 
2732     const ::rtl::OUString aPropertyNames[] =
2733     {
2734         PROPERTY_URL, PROPERTY_USER
2735     };
2736 
2737     // disconnect from old model
2738     try
2739     {
2740         if ( m_xDataSource.is() )
2741         {
2742             for ( size_t i=0; i < sizeof( aPropertyNames ) / sizeof( aPropertyNames[0] ); ++i )
2743             {
2744                 m_xDataSource->removePropertyChangeListener( aPropertyNames[i], this );
2745             }
2746         }
2747 
2748         Reference< XModifyBroadcaster >  xBroadcaster( m_xModel, UNO_QUERY );
2749         if ( xBroadcaster.is() )
2750             xBroadcaster->removeModifyListener( this );
2751     }
2752     catch( const Exception& )
2753     {
2754         DBG_UNHANDLED_EXCEPTION();
2755     }
2756 
2757     m_xModel = _rxModel;
2758     m_xDocumentModify = xDocModify;
2759     m_xDataSource.set( xOfficeDoc.is() ? xOfficeDoc->getDataSource() : Reference< XDataSource >(), UNO_QUERY );
2760 
2761     // connect to new model
2762     try
2763     {
2764         if ( m_xDataSource.is() )
2765         {
2766             for ( size_t i=0; i < sizeof( aPropertyNames ) / sizeof( aPropertyNames[0] ); ++i )
2767             {
2768                 m_xDataSource->addPropertyChangeListener( aPropertyNames[i], this );
2769             }
2770         }
2771 
2772         Reference< XModifyBroadcaster >  xBroadcaster( m_xModel, UNO_QUERY_THROW );
2773         xBroadcaster->addModifyListener( this );
2774 
2775     }
2776     catch( const Exception& )
2777     {
2778         DBG_UNHANDLED_EXCEPTION();
2779     }
2780 
2781     // initial preview mode
2782     if ( m_xDataSource.is() )
2783     {
2784         try
2785         {
2786             // to get the 'modified' for the data source
2787             ::comphelper::NamedValueCollection aLayoutInfo( m_xDataSource->getPropertyValue( PROPERTY_LAYOUTINFORMATION ) );
2788             if ( aLayoutInfo.has( (rtl::OUString)INFO_PREVIEW ) )
2789             {
2790                 const sal_Int32 nPreviewMode( aLayoutInfo.getOrDefault( (rtl::OUString)INFO_PREVIEW, (sal_Int32)0 ) );
2791                 m_ePreviewMode = static_cast< PreviewMode >( nPreviewMode );
2792                 if ( getView() )
2793                     getContainer()->switchPreview( m_ePreviewMode );
2794             }
2795         }
2796         catch( const Exception& )
2797         {
2798             DBG_UNHANDLED_EXCEPTION();
2799         }
2800     }
2801 
2802     return sal_True;
2803 }
2804 // -----------------------------------------------------------------------------
2805 void OApplicationController::containerFound( const Reference< XContainer >& _xContainer)
2806 {
2807     try
2808     {
2809         if ( _xContainer.is() )
2810         {
2811             m_aCurrentContainers.push_back(_xContainer);
2812             _xContainer->addContainerListener(this);
2813         }
2814     }
2815     catch(const Exception&)
2816     {
2817         DBG_UNHANDLED_EXCEPTION();
2818     }
2819 }
2820 // -----------------------------------------------------------------------------
2821 ::rtl::OUString OApplicationController::getCurrentlySelectedName(sal_Int32& _rnCommandType) const
2822 {
2823     _rnCommandType = ( (getContainer()->getElementType() == E_QUERY)
2824                                 ? CommandType::QUERY : ( (getContainer()->getElementType() == E_TABLE) ? CommandType::TABLE : -1 ));
2825 
2826 
2827     ::rtl::OUString sName;
2828     if ( _rnCommandType != -1 )
2829     {
2830         try
2831         {
2832             sName = getContainer()->getQualifiedName( NULL );
2833             OSL_ENSURE( sName.getLength(), "OApplicationController::getCurrentlySelectedName: no name given!" );
2834         }
2835         catch( const Exception& )
2836         {
2837             DBG_UNHANDLED_EXCEPTION();
2838         }
2839     }
2840     return sName;
2841 }
2842 
2843 // -----------------------------------------------------------------------------
2844 void SAL_CALL OApplicationController::addSelectionChangeListener( const Reference< view::XSelectionChangeListener >& _Listener ) throw (RuntimeException)
2845 {
2846     m_pSelectionNotifier->addListener( _Listener );
2847 }
2848 
2849 // -----------------------------------------------------------------------------
2850 void SAL_CALL OApplicationController::removeSelectionChangeListener( const Reference< view::XSelectionChangeListener >& _Listener ) throw (RuntimeException)
2851 {
2852     m_pSelectionNotifier->removeListener( _Listener );
2853 }
2854 
2855 // -----------------------------------------------------------------------------
2856 ::sal_Bool SAL_CALL OApplicationController::select( const Any& _aSelection ) throw (IllegalArgumentException, RuntimeException)
2857 {
2858     ::vos::OGuard aSolarGuard( Application::GetSolarMutex() );
2859     ::osl::MutexGuard aGuard( getMutex() );
2860     Sequence< ::rtl::OUString> aSelection;
2861     if ( !_aSelection.hasValue() || !getView() )
2862     {
2863         getContainer()->selectElements(aSelection);
2864         return sal_True;
2865     }
2866 
2867     // --------------------------------------------------------------
2868     // BEGIN compatibility
2869     Sequence< NamedValue > aCurrentSelection;
2870     if ( (_aSelection >>= aCurrentSelection) && aCurrentSelection.getLength() )
2871     {
2872         ElementType eType = E_NONE;
2873         const NamedValue* pIter = aCurrentSelection.getConstArray();
2874         const NamedValue* pEnd  = pIter + aCurrentSelection.getLength();
2875         for(;pIter != pEnd;++pIter)
2876         {
2877             if ( pIter->Name.equalsAscii("Type") )
2878             {
2879                 sal_Int32 nType = 0;
2880                 pIter->Value >>= nType;
2881                 if ( nType < DatabaseObject::TABLE || nType > DatabaseObject::REPORT )
2882                     throw IllegalArgumentException();
2883                 eType = static_cast< ElementType >( nType );
2884             }
2885             else if ( pIter->Name.equalsAscii("Selection") )
2886                 pIter->Value >>= aSelection;
2887         }
2888 
2889         m_aSelectContainerEvent.CancelCall();   // just in case the async select request was running
2890         getContainer()->selectContainer(eType);
2891         getContainer()->selectElements(aSelection);
2892         return sal_True;
2893     }
2894     // END compatibility
2895     // --------------------------------------------------------------
2896 
2897     Sequence< NamedDatabaseObject > aSelectedObjects;
2898     if ( !( _aSelection >>= aSelectedObjects ) )
2899     {
2900         aSelectedObjects.realloc( 1 );
2901         if ( !( _aSelection >>= aSelectedObjects[0] ) )
2902             throw IllegalArgumentException();
2903     }
2904 
2905     SelectionByElementType aSelectedElements;
2906     ElementType eSelectedCategory = E_NONE;
2907     for (   const NamedDatabaseObject* pObject = aSelectedObjects.getConstArray();
2908             pObject != aSelectedObjects.getConstArray() + aSelectedObjects.getLength();
2909             ++pObject
2910         )
2911     {
2912         switch ( pObject->Type )
2913         {
2914             case DatabaseObject::TABLE:
2915             case DatabaseObjectContainer::SCHEMA:
2916             case DatabaseObjectContainer::CATALOG:
2917                 aSelectedElements[ E_TABLE ].push_back( pObject->Name );
2918                 break;
2919             case DatabaseObject::QUERY:
2920                 aSelectedElements[ E_QUERY ].push_back( pObject->Name );
2921                 break;
2922             case DatabaseObject::FORM:
2923             case DatabaseObjectContainer::FORMS_FOLDER:
2924                 aSelectedElements[ E_FORM ].push_back( pObject->Name );
2925                 break;
2926             case DatabaseObject::REPORT:
2927             case DatabaseObjectContainer::REPORTS_FOLDER:
2928                 aSelectedElements[ E_REPORT ].push_back( pObject->Name );
2929                 break;
2930             case DatabaseObjectContainer::TABLES:
2931             case DatabaseObjectContainer::QUERIES:
2932             case DatabaseObjectContainer::FORMS:
2933             case DatabaseObjectContainer::REPORTS:
2934                 if ( eSelectedCategory != E_NONE )
2935                     throw IllegalArgumentException(
2936                         String(ModuleRes(RID_STR_NO_DIFF_CAT)),
2937                         *this, sal_Int16( pObject - aSelectedObjects.getConstArray() ) );
2938                 eSelectedCategory =
2939                         ( pObject->Type == DatabaseObjectContainer::TABLES )  ? E_TABLE
2940                     :   ( pObject->Type == DatabaseObjectContainer::QUERIES ) ? E_QUERY
2941                     :   ( pObject->Type == DatabaseObjectContainer::FORMS )   ? E_FORM
2942                     :   ( pObject->Type == DatabaseObjectContainer::REPORTS ) ? E_REPORT
2943                     :   E_NONE;
2944                 break;
2945 
2946             default:
2947             case DatabaseObjectContainer::DATA_SOURCE:
2948             {
2949                 ::rtl::OUString sMessage = String(ModuleRes( RID_STR_UNSUPPORTED_OBJECT_TYPE ));
2950                 ::comphelper::string::searchAndReplaceAsciiI( sMessage, "$type$", ::rtl::OUString::valueOf(sal_Int32( pObject->Type )) );
2951                 throw IllegalArgumentException(sMessage, *this, sal_Int16( pObject - aSelectedObjects.getConstArray() ));
2952             }
2953         }
2954     }
2955 
2956     for (   SelectionByElementType::const_iterator sel = aSelectedElements.begin();
2957             sel != aSelectedElements.end();
2958             ++sel
2959         )
2960     {
2961         if ( sel->first == m_eCurrentType )
2962         {
2963             Sequence< ::rtl::OUString > aSelected( sel->second.size() );
2964             ::std::copy( sel->second.begin(), sel->second.end(), aSelected.getArray() );
2965             getContainer()->selectElements( aSelected );
2966         }
2967         else
2968         {
2969             m_aPendingSelection[ sel->first ] = sel->second;
2970         }
2971     }
2972 
2973     m_aSelectContainerEvent.CancelCall();   // just in case the async select request was running
2974     getContainer()->selectContainer( eSelectedCategory );
2975 
2976     return sal_True;
2977 }
2978 // -----------------------------------------------------------------------------
2979 Any SAL_CALL OApplicationController::getSelection(  ) throw (RuntimeException)
2980 {
2981     ::vos::OGuard aSolarGuard( Application::GetSolarMutex() );
2982     ::osl::MutexGuard aGuard( getMutex() );
2983 
2984     Sequence< NamedDatabaseObject > aCurrentSelection;
2985     const ElementType eType( getContainer()->getElementType() );
2986     if ( eType != E_NONE )
2987     {
2988         getContainer()->describeCurrentSelectionForType( eType, aCurrentSelection );
2989         if ( aCurrentSelection.getLength() == 0 )
2990         {   // if no objects are selected, add an entry to the sequence which describes the overall category
2991             // which is selected currently
2992             aCurrentSelection.realloc(1);
2993             aCurrentSelection[0].Name = getDatabaseName();
2994             switch ( eType )
2995             {
2996             case E_TABLE:   aCurrentSelection[0].Type = DatabaseObjectContainer::TABLES;   break;
2997             case E_QUERY:   aCurrentSelection[0].Type = DatabaseObjectContainer::QUERIES;  break;
2998             case E_FORM:    aCurrentSelection[0].Type = DatabaseObjectContainer::FORMS;    break;
2999             case E_REPORT:  aCurrentSelection[0].Type = DatabaseObjectContainer::REPORTS;  break;
3000             default:
3001                 OSL_ENSURE( false, "OApplicationController::getSelection: unexpected current element type!" );
3002                 break;
3003             }
3004         }
3005     }
3006     return makeAny( aCurrentSelection );
3007 }
3008 // -----------------------------------------------------------------------------
3009 void OApplicationController::impl_migrateScripts_nothrow()
3010 {
3011     try
3012     {
3013         ::rtl::OUString sDialogService( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.sdb.application.MacroMigrationWizard" ) );
3014         ::comphelper::ComponentContext aContext( getORB() );
3015         Sequence< Any > aDialogArgs(1);
3016         aDialogArgs[0] <<= Reference< XOfficeDatabaseDocument >( m_xModel, UNO_QUERY_THROW );
3017         Reference< XExecutableDialog > xDialog(
3018             aContext.createComponentWithArguments( sDialogService, aDialogArgs ),
3019             UNO_QUERY );
3020 
3021         if ( !xDialog.is() )
3022         {
3023             ShowServiceNotAvailableError( getView(), sDialogService, true );
3024             return;
3025         }
3026 
3027         xDialog->execute();
3028     }
3029     catch( const Exception& )
3030     {
3031         DBG_UNHANDLED_EXCEPTION();
3032     }
3033 }
3034 
3035 //........................................................................
3036 }   // namespace dbaui
3037 //........................................................................
3038 
3039