Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #include <sfx2/sfxstatuslistener.hxx>
21 : #include <svl/poolitem.hxx>
22 : #include <svl/eitem.hxx>
23 : #include <svl/stritem.hxx>
24 : #include <svl/intitem.hxx>
25 : #include <svl/itemset.hxx>
26 : #include <svtools/itemdel.hxx>
27 : #include <svl/visitem.hxx>
28 : #include <cppuhelper/weak.hxx>
29 : #include <comphelper/processfactory.hxx>
30 : #include <osl/mutex.hxx>
31 : #include <vcl/svapp.hxx>
32 : #include <com/sun/star/util/URLTransformer.hpp>
33 : #include <com/sun/star/util/XURLTransformer.hpp>
34 : #include <com/sun/star/lang/XUnoTunnel.hpp>
35 : #include <com/sun/star/frame/status/ItemStatus.hpp>
36 : #include <com/sun/star/frame/status/ItemState.hpp>
37 : #include <com/sun/star/frame/status/Visibility.hpp>
38 :
39 : #include <sfx2/viewfrm.hxx>
40 : #include <sfx2/dispatch.hxx>
41 : #include <sfx2/unoctitm.hxx>
42 : #include <sfx2/msgpool.hxx>
43 :
44 : using ::rtl::OUString;
45 : using namespace ::cppu;
46 : using namespace ::com::sun::star::uno;
47 : using namespace ::com::sun::star::frame;
48 : using namespace ::com::sun::star::frame::status;
49 : using namespace ::com::sun::star::lang;
50 : using namespace ::com::sun::star::util;
51 :
52 0 : SFX_IMPL_XINTERFACE_3( SfxStatusListener, OWeakObject, ::com::sun::star::lang::XComponent, ::com::sun::star::frame::XStatusListener, ::com::sun::star::lang::XEventListener )
53 0 : SFX_IMPL_XTYPEPROVIDER_3( SfxStatusListener, ::com::sun::star::lang::XComponent, ::com::sun::star::frame::XStatusListener, ::com::sun::star::lang::XEventListener )
54 :
55 0 : SfxStatusListener::SfxStatusListener( const Reference< XDispatchProvider >& rDispatchProvider, sal_uInt16 nSlotId, const OUString& rCommand ) :
56 : cppu::OWeakObject(),
57 : m_nSlotID( nSlotId ),
58 0 : m_xDispatchProvider( rDispatchProvider )
59 : {
60 0 : m_aCommand.Complete = rCommand;
61 0 : Reference< XURLTransformer > xTrans( URLTransformer::create( ::comphelper::getProcessComponentContext() ) );
62 0 : xTrans->parseStrict( m_aCommand );
63 0 : if ( rDispatchProvider.is() )
64 0 : m_xDispatch = rDispatchProvider->queryDispatch( m_aCommand, rtl::OUString(), 0 );
65 0 : }
66 :
67 0 : SfxStatusListener::~SfxStatusListener()
68 : {
69 0 : }
70 :
71 : // old sfx controller item C++ API
72 0 : void SfxStatusListener::StateChanged( sal_uInt16, SfxItemState, const SfxPoolItem* )
73 : {
74 : // must be implemented by sub class
75 0 : }
76 :
77 0 : void SfxStatusListener::UnBind()
78 : {
79 0 : if ( m_xDispatch.is() )
80 : {
81 0 : Reference< XStatusListener > aStatusListener( static_cast< OWeakObject* >( this ), UNO_QUERY );
82 0 : m_xDispatch->removeStatusListener( aStatusListener, m_aCommand );
83 0 : m_xDispatch.clear();
84 : }
85 0 : }
86 :
87 0 : void SfxStatusListener::ReBind()
88 : {
89 0 : Reference< XStatusListener > aStatusListener( static_cast< OWeakObject* >( this ), UNO_QUERY );
90 0 : if ( m_xDispatch.is() )
91 0 : m_xDispatch->removeStatusListener( aStatusListener, m_aCommand );
92 0 : if ( m_xDispatchProvider.is() )
93 : {
94 : try
95 : {
96 0 : m_xDispatch = m_xDispatchProvider->queryDispatch( m_aCommand, rtl::OUString(), 0 );
97 0 : if ( m_xDispatch.is() )
98 0 : m_xDispatch->addStatusListener( aStatusListener, m_aCommand );
99 : }
100 0 : catch( Exception& )
101 : {
102 : }
103 0 : }
104 0 : }
105 :
106 : // new UNO API
107 0 : void SAL_CALL SfxStatusListener::dispose() throw( ::com::sun::star::uno::RuntimeException )
108 : {
109 0 : if ( m_xDispatch.is() && !m_aCommand.Complete.isEmpty() )
110 : {
111 : try
112 : {
113 0 : Reference< XStatusListener > aStatusListener( static_cast< OWeakObject* >( this ), UNO_QUERY );
114 0 : m_xDispatch->removeStatusListener( aStatusListener, m_aCommand );
115 : }
116 0 : catch ( Exception& )
117 : {
118 : }
119 : }
120 :
121 0 : m_xDispatch.clear();
122 0 : m_xDispatchProvider.clear();
123 0 : }
124 :
125 0 : void SAL_CALL SfxStatusListener::addEventListener( const Reference< XEventListener >& )
126 : throw ( RuntimeException )
127 : {
128 : // do nothing - this is a wrapper class which does not support listeners
129 0 : }
130 :
131 0 : void SAL_CALL SfxStatusListener::removeEventListener( const Reference< XEventListener >& )
132 : throw ( RuntimeException )
133 : {
134 : // do nothing - this is a wrapper class which does not support listeners
135 0 : }
136 :
137 0 : void SAL_CALL SfxStatusListener::disposing( const EventObject& Source )
138 : throw( RuntimeException )
139 : {
140 0 : SolarMutexGuard aGuard;
141 :
142 0 : if ( Source.Source == Reference< XInterface >( m_xDispatch, UNO_QUERY ))
143 0 : m_xDispatch.clear();
144 0 : else if ( Source.Source == Reference< XInterface >( m_xDispatchProvider, UNO_QUERY ))
145 0 : m_xDispatchProvider.clear();
146 0 : }
147 :
148 0 : void SAL_CALL SfxStatusListener::statusChanged( const FeatureStateEvent& rEvent)
149 : throw( RuntimeException )
150 : {
151 0 : SolarMutexGuard aGuard;
152 :
153 0 : SfxViewFrame* pViewFrame = NULL;
154 0 : if ( m_xDispatch.is() )
155 : {
156 0 : Reference< XUnoTunnel > xTunnel( m_xDispatch, UNO_QUERY );
157 0 : SfxOfficeDispatch* pDisp = NULL;
158 0 : if ( xTunnel.is() )
159 : {
160 0 : sal_Int64 nImplementation = xTunnel->getSomething(SfxOfficeDispatch::impl_getStaticIdentifier());
161 0 : pDisp = reinterpret_cast< SfxOfficeDispatch* >(sal::static_int_cast< sal_IntPtr >( nImplementation ));
162 : }
163 :
164 0 : if ( pDisp )
165 0 : pViewFrame = pDisp->GetDispatcher_Impl()->GetFrame();
166 : }
167 :
168 0 : SfxSlotPool& rPool = SfxSlotPool::GetSlotPool( pViewFrame );
169 0 : const SfxSlot* pSlot = rPool.GetSlot( m_nSlotID );
170 :
171 0 : SfxItemState eState = SFX_ITEM_DISABLED;
172 0 : SfxPoolItem* pItem = NULL;
173 0 : if ( rEvent.IsEnabled )
174 : {
175 0 : eState = SFX_ITEM_AVAILABLE;
176 0 : ::com::sun::star::uno::Type pType = rEvent.State.getValueType();
177 :
178 0 : if ( pType == ::getVoidCppuType() )
179 : {
180 0 : pItem = new SfxVoidItem( m_nSlotID );
181 0 : eState = SFX_ITEM_UNKNOWN;
182 : }
183 0 : else if ( pType == ::getBooleanCppuType() )
184 : {
185 0 : sal_Bool bTemp = false;
186 0 : rEvent.State >>= bTemp ;
187 0 : pItem = new SfxBoolItem( m_nSlotID, bTemp );
188 : }
189 0 : else if ( pType == ::getCppuType((const sal_uInt16*)0) )
190 : {
191 0 : sal_uInt16 nTemp = 0;
192 0 : rEvent.State >>= nTemp ;
193 0 : pItem = new SfxUInt16Item( m_nSlotID, nTemp );
194 : }
195 0 : else if ( pType == ::getCppuType((const sal_uInt32*)0) )
196 : {
197 0 : sal_uInt32 nTemp = 0;
198 0 : rEvent.State >>= nTemp ;
199 0 : pItem = new SfxUInt32Item( m_nSlotID, nTemp );
200 : }
201 0 : else if ( pType == ::getCppuType((const ::rtl::OUString*)0) )
202 : {
203 0 : ::rtl::OUString sTemp ;
204 0 : rEvent.State >>= sTemp ;
205 0 : pItem = new SfxStringItem( m_nSlotID, sTemp );
206 : }
207 0 : else if ( pType == ::getCppuType((const ::com::sun::star::frame::status::ItemStatus*)0) )
208 : {
209 0 : ItemStatus aItemStatus;
210 0 : rEvent.State >>= aItemStatus;
211 0 : eState = aItemStatus.State;
212 0 : pItem = new SfxVoidItem( m_nSlotID );
213 : }
214 0 : else if ( pType == ::getCppuType((const ::com::sun::star::frame::status::Visibility*)0) )
215 : {
216 0 : Visibility aVisibilityStatus;
217 0 : rEvent.State >>= aVisibilityStatus;
218 0 : pItem = new SfxVisibilityItem( m_nSlotID, aVisibilityStatus.bVisible );
219 : }
220 : else
221 : {
222 0 : if ( pSlot )
223 0 : pItem = pSlot->GetType()->CreateItem();
224 0 : if ( pItem )
225 : {
226 0 : pItem->SetWhich( m_nSlotID );
227 0 : pItem->PutValue( rEvent.State );
228 : }
229 : else
230 0 : pItem = new SfxVoidItem( m_nSlotID );
231 0 : }
232 : }
233 :
234 0 : StateChanged( m_nSlotID, eState, pItem );
235 0 : delete pItem;
236 0 : }
237 :
238 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|