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_svtools.hxx"
30 #include <svtools/generictoolboxcontroller.hxx>
31 
32 //_________________________________________________________________________________________________________________
33 //	my own includes
34 //_________________________________________________________________________________________________________________
35 
36 //_________________________________________________________________________________________________________________
37 //	interface includes
38 //_________________________________________________________________________________________________________________
39 #include <com/sun/star/util/XURLTransformer.hpp>
40 #include <com/sun/star/frame/XDispatchProvider.hpp>
41 #include <com/sun/star/beans/PropertyValue.hpp>
42 #include <com/sun/star/lang/DisposedException.hpp>
43 #include <com/sun/star/frame/status/ItemStatus.hpp>
44 #include <com/sun/star/frame/status/ItemState.hpp>
45 
46 //_________________________________________________________________________________________________________________
47 //	other includes
48 //_________________________________________________________________________________________________________________
49 #include <vos/mutex.hxx>
50 #include <vcl/svapp.hxx>
51 
52 using namespace ::com::sun::star::awt;
53 using namespace ::com::sun::star::uno;
54 using namespace ::com::sun::star::beans;
55 using namespace ::com::sun::star::lang;
56 using namespace ::com::sun::star::frame;
57 using namespace ::com::sun::star::frame::status;
58 using namespace ::com::sun::star::util;
59 
60 namespace svt
61 {
62 
63 struct ExecuteInfo
64 {
65     ::com::sun::star::uno::Reference< ::com::sun::star::frame::XDispatch >     xDispatch;
66     ::com::sun::star::util::URL                                                aTargetURL;
67     ::com::sun::star::uno::Sequence< ::com::sun::star::beans::PropertyValue >  aArgs;
68 };
69 
70 GenericToolboxController::GenericToolboxController( const Reference< XMultiServiceFactory >& rServiceManager,
71                                                     const Reference< XFrame >&               rFrame,
72                                                     ToolBox*                                 pToolbox,
73                                                     sal_uInt16                                   nID,
74                                                     const ::rtl::OUString&                          aCommand ) :
75     svt::ToolboxController( rServiceManager, rFrame, aCommand )
76     ,   m_pToolbox( pToolbox )
77     ,   m_nID( nID )
78 {
79     // Initialization is done through ctor
80     m_bInitialized = sal_True;
81 
82     // insert main command to our listener map
83     if ( m_aCommandURL.getLength() )
84         m_aListenerMap.insert( URLToDispatchMap::value_type( aCommand, Reference< XDispatch >() ));
85 }
86 
87 GenericToolboxController::~GenericToolboxController()
88 {
89 }
90 
91 void SAL_CALL GenericToolboxController::dispose()
92 throw ( RuntimeException )
93 {
94     vos::OGuard aSolarMutexGuard( Application::GetSolarMutex() );
95 
96     svt::ToolboxController::dispose();
97 
98     m_pToolbox = 0;
99     m_nID = 0;
100 }
101 
102 void SAL_CALL GenericToolboxController::execute( sal_Int16 /*KeyModifier*/ )
103 throw ( RuntimeException )
104 {
105     Reference< XDispatch >       xDispatch;
106     Reference< XURLTransformer > xURLTransformer;
107     ::rtl::OUString                     aCommandURL;
108 
109     {
110         vos::OGuard aSolarMutexGuard( Application::GetSolarMutex() );
111 
112         if ( m_bDisposed )
113             throw DisposedException();
114 
115         if ( m_bInitialized &&
116              m_xFrame.is() &&
117              m_xServiceManager.is() &&
118              m_aCommandURL.getLength() )
119         {
120             xURLTransformer = Reference< XURLTransformer >( m_xServiceManager->createInstance(
121                                                                 rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.util.URLTransformer" ))),
122                                                             UNO_QUERY );
123 
124             aCommandURL = m_aCommandURL;
125             URLToDispatchMap::iterator pIter = m_aListenerMap.find( m_aCommandURL );
126             if ( pIter != m_aListenerMap.end() )
127                 xDispatch = pIter->second;
128         }
129     }
130 
131     if ( xDispatch.is() && xURLTransformer.is() )
132     {
133         com::sun::star::util::URL aTargetURL;
134         Sequence<PropertyValue>   aArgs;
135 
136         aTargetURL.Complete = aCommandURL;
137         xURLTransformer->parseStrict( aTargetURL );
138 
139         // Execute dispatch asynchronously
140         ExecuteInfo* pExecuteInfo = new ExecuteInfo;
141         pExecuteInfo->xDispatch     = xDispatch;
142         pExecuteInfo->aTargetURL    = aTargetURL;
143         pExecuteInfo->aArgs         = aArgs;
144         Application::PostUserEvent( STATIC_LINK(0, GenericToolboxController , ExecuteHdl_Impl), pExecuteInfo );
145     }
146 }
147 
148 void GenericToolboxController::statusChanged( const FeatureStateEvent& Event )
149 throw ( RuntimeException )
150 {
151     vos::OGuard aSolarMutexGuard( Application::GetSolarMutex() );
152 
153     if ( m_bDisposed )
154         return;
155 
156     if ( m_pToolbox )
157     {
158         m_pToolbox->EnableItem( m_nID, Event.IsEnabled );
159 
160         sal_uInt16 nItemBits = m_pToolbox->GetItemBits( m_nID );
161         nItemBits &= ~TIB_CHECKABLE;
162 	    TriState eTri = STATE_NOCHECK;
163 
164         sal_Bool        bValue = sal_Bool();
165         rtl::OUString   aStrValue;
166         ItemStatus      aItemState;
167 
168         if ( Event.State >>= bValue )
169         {
170             // Boolean, treat it as checked/unchecked
171             m_pToolbox->SetItemBits( m_nID, nItemBits );
172             m_pToolbox->CheckItem( m_nID, bValue );
173             if ( bValue )
174                 eTri = STATE_CHECK;
175 		    nItemBits |= TIB_CHECKABLE;
176         }
177         else if ( Event.State >>= aStrValue )
178         {
179             m_pToolbox->SetItemText( m_nID, aStrValue );
180         }
181         else if ( Event.State >>= aItemState )
182         {
183 			eTri = STATE_DONTKNOW;
184             nItemBits |= TIB_CHECKABLE;
185         }
186 
187         m_pToolbox->SetItemState( m_nID, eTri );
188 	    m_pToolbox->SetItemBits( m_nID, nItemBits );
189     }
190 }
191 
192 IMPL_STATIC_LINK_NOINSTANCE( GenericToolboxController, ExecuteHdl_Impl, ExecuteInfo*, pExecuteInfo )
193 {
194    try
195    {
196        // Asynchronous execution as this can lead to our own destruction!
197        // Framework can recycle our current frame and the layout manager disposes all user interface
198        // elements if a component gets detached from its frame!
199        pExecuteInfo->xDispatch->dispatch( pExecuteInfo->aTargetURL, pExecuteInfo->aArgs );
200    }
201    catch ( Exception& )
202    {
203    }
204    delete pExecuteInfo;
205    return 0;
206 }
207 
208 } // namespace
209