/src/libreoffice/embeddedobj/source/general/intercept.cxx
Line | Count | Source |
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 <com/sun/star/embed/EmbedStates.hpp> |
21 | | #include <comphelper/multiinterfacecontainer3.hxx> |
22 | | |
23 | | #include <intercept.hxx> |
24 | | #include <docholder.hxx> |
25 | | #include <commonembobj.hxx> |
26 | | |
27 | | using namespace ::com::sun::star; |
28 | | |
29 | | constexpr OUString IU0 = u".uno:Save"_ustr; |
30 | | constexpr OUString IU1 = u".uno:SaveAll"_ustr; |
31 | | constexpr OUString IU2 = u".uno:CloseDoc"_ustr; |
32 | | constexpr OUString IU3 = u".uno:CloseWin"_ustr; |
33 | | constexpr OUString IU4 = u".uno:CloseFrame"_ustr; |
34 | | constexpr OUString IU5 = u".uno:SaveAs"_ustr; |
35 | | |
36 | | class StatusChangeListenerContainer |
37 | | : public comphelper::OMultiTypeInterfaceContainerHelperVar3<frame::XStatusListener, OUString> |
38 | | { |
39 | | public: |
40 | | explicit StatusChangeListenerContainer(osl::Mutex& aMutex) |
41 | 0 | : comphelper::OMultiTypeInterfaceContainerHelperVar3<frame::XStatusListener, OUString>(aMutex) |
42 | 0 | { |
43 | 0 | } |
44 | | }; |
45 | | |
46 | | namespace embeddedobj |
47 | | { |
48 | | const uno::Sequence< OUString > Interceptor::m_aInterceptedURL{ IU0, IU1, IU2, IU3, IU4, IU5 }; |
49 | | |
50 | | void Interceptor::DisconnectDocHolder() |
51 | 0 | { |
52 | 0 | osl::MutexGuard aGuard( m_aMutex ); |
53 | 0 | m_pDocHolder = nullptr; |
54 | 0 | } |
55 | | |
56 | | Interceptor::Interceptor( embeddedobj::DocumentHolder* pDocHolder ) |
57 | 0 | : m_pDocHolder( pDocHolder ) |
58 | 0 | { |
59 | 0 | } |
60 | | |
61 | | Interceptor::~Interceptor() |
62 | 0 | { |
63 | 0 | } |
64 | | |
65 | | //XDispatch |
66 | | void SAL_CALL |
67 | | Interceptor::dispatch( |
68 | | const util::URL& URL, |
69 | | const uno::Sequence< |
70 | | beans::PropertyValue >& Arguments ) |
71 | 0 | { |
72 | 0 | osl::MutexGuard aGuard(m_aMutex); |
73 | 0 | if( !m_pDocHolder ) |
74 | 0 | return; |
75 | | |
76 | 0 | if(URL.Complete == m_aInterceptedURL[0]) |
77 | 0 | m_pDocHolder->GetEmbedObject().SaveObject_Impl(); |
78 | 0 | else if(URL.Complete == m_aInterceptedURL[2] || |
79 | 0 | URL.Complete == m_aInterceptedURL[3] || |
80 | 0 | URL.Complete == m_aInterceptedURL[4]) |
81 | 0 | { |
82 | 0 | try { |
83 | 0 | m_pDocHolder->GetEmbedObject().changeState( embed::EmbedStates::RUNNING ); |
84 | 0 | } |
85 | 0 | catch( const uno::Exception& ) |
86 | 0 | { |
87 | 0 | } |
88 | 0 | } |
89 | 0 | else if ( URL.Complete == m_aInterceptedURL[5] ) |
90 | 0 | { |
91 | 0 | uno::Sequence< beans::PropertyValue > aNewArgs = Arguments; |
92 | 0 | sal_Int32 nInd = 0; |
93 | |
|
94 | 0 | while( nInd < aNewArgs.getLength() ) |
95 | 0 | { |
96 | 0 | if ( aNewArgs[nInd].Name == "SaveTo" ) |
97 | 0 | { |
98 | 0 | aNewArgs.getArray()[nInd].Value <<= true; |
99 | 0 | break; |
100 | 0 | } |
101 | 0 | nInd++; |
102 | 0 | } |
103 | |
|
104 | 0 | if ( nInd == aNewArgs.getLength() ) |
105 | 0 | { |
106 | 0 | aNewArgs.realloc( nInd + 1 ); |
107 | 0 | auto pNewArgs = aNewArgs.getArray(); |
108 | 0 | pNewArgs[nInd].Name = "SaveTo"; |
109 | 0 | pNewArgs[nInd].Value <<= true; |
110 | 0 | } |
111 | |
|
112 | 0 | uno::Reference< frame::XDispatch > xDispatch = m_xSlaveDispatchProvider->queryDispatch( |
113 | 0 | URL, u"_self"_ustr, 0 ); |
114 | 0 | if ( xDispatch.is() ) |
115 | 0 | xDispatch->dispatch( URL, aNewArgs ); |
116 | 0 | } |
117 | 0 | } |
118 | | |
119 | | void SAL_CALL |
120 | | Interceptor::addStatusListener( |
121 | | const uno::Reference< |
122 | | frame::XStatusListener >& Control, |
123 | | const util::URL& URL ) |
124 | 0 | { |
125 | 0 | if(!Control.is()) |
126 | 0 | return; |
127 | | |
128 | 0 | if(URL.Complete == m_aInterceptedURL[0]) |
129 | 0 | { // Save |
130 | 0 | frame::FeatureStateEvent aStateEvent; |
131 | 0 | aStateEvent.FeatureURL.Complete = m_aInterceptedURL[0]; |
132 | 0 | aStateEvent.FeatureDescriptor = "Update"; |
133 | 0 | aStateEvent.IsEnabled = true; |
134 | 0 | aStateEvent.Requery = false; |
135 | 0 | aStateEvent.State <<= "($1) " + m_pDocHolder->GetTitle(); |
136 | 0 | Control->statusChanged(aStateEvent); |
137 | |
|
138 | 0 | { |
139 | 0 | osl::MutexGuard aGuard(m_aMutex); |
140 | 0 | if(!m_pStatCL) |
141 | 0 | m_pStatCL.reset(new StatusChangeListenerContainer(m_aMutex)); |
142 | 0 | } |
143 | |
|
144 | 0 | m_pStatCL->addInterface(URL.Complete,Control); |
145 | 0 | return; |
146 | 0 | } |
147 | | |
148 | 0 | sal_Int32 i = 2; |
149 | 0 | if(URL.Complete == m_aInterceptedURL[i] || |
150 | 0 | URL.Complete == m_aInterceptedURL[++i] || |
151 | 0 | URL.Complete == m_aInterceptedURL[++i] ) |
152 | 0 | { // Close and return |
153 | 0 | frame::FeatureStateEvent aStateEvent; |
154 | 0 | aStateEvent.FeatureURL.Complete = m_aInterceptedURL[i]; |
155 | 0 | aStateEvent.FeatureDescriptor = "Close and Return"; |
156 | 0 | aStateEvent.IsEnabled = true; |
157 | 0 | aStateEvent.Requery = false; |
158 | 0 | aStateEvent.State <<= "($2)" + m_pDocHolder->GetContainerName(); |
159 | 0 | Control->statusChanged(aStateEvent); |
160 | | |
161 | |
|
162 | 0 | { |
163 | 0 | osl::MutexGuard aGuard(m_aMutex); |
164 | 0 | if(!m_pStatCL) |
165 | 0 | m_pStatCL.reset(new StatusChangeListenerContainer(m_aMutex)); |
166 | 0 | } |
167 | |
|
168 | 0 | m_pStatCL->addInterface(URL.Complete,Control); |
169 | 0 | return; |
170 | 0 | } |
171 | | |
172 | 0 | if(URL.Complete != m_aInterceptedURL[5]) |
173 | 0 | return; |
174 | | |
175 | | // SaveAs |
176 | 0 | frame::FeatureStateEvent aStateEvent; |
177 | 0 | aStateEvent.FeatureURL.Complete = m_aInterceptedURL[5]; |
178 | 0 | aStateEvent.FeatureDescriptor = "SaveCopyTo"; |
179 | 0 | aStateEvent.IsEnabled = true; |
180 | 0 | aStateEvent.Requery = false; |
181 | 0 | aStateEvent.State <<= u"($3)"_ustr; |
182 | 0 | Control->statusChanged(aStateEvent); |
183 | |
|
184 | 0 | { |
185 | 0 | osl::MutexGuard aGuard(m_aMutex); |
186 | 0 | if(!m_pStatCL) |
187 | 0 | m_pStatCL.reset(new StatusChangeListenerContainer(m_aMutex)); |
188 | 0 | } |
189 | |
|
190 | 0 | m_pStatCL->addInterface(URL.Complete,Control); |
191 | 0 | return; |
192 | |
|
193 | 0 | } |
194 | | |
195 | | |
196 | | void SAL_CALL |
197 | | Interceptor::removeStatusListener( |
198 | | const uno::Reference< |
199 | | frame::XStatusListener >& Control, |
200 | | const util::URL& URL ) |
201 | 0 | { |
202 | 0 | if(!(Control.is() && m_pStatCL)) |
203 | 0 | return; |
204 | 0 | else { |
205 | 0 | m_pStatCL->removeInterface(URL.Complete,Control); |
206 | 0 | return; |
207 | 0 | } |
208 | 0 | } |
209 | | |
210 | | |
211 | | //XInterceptorInfo |
212 | | uno::Sequence< OUString > |
213 | | SAL_CALL |
214 | | Interceptor::getInterceptedURLs( ) |
215 | 0 | { |
216 | | // now implemented as update |
217 | |
|
218 | 0 | return m_aInterceptedURL; |
219 | 0 | } |
220 | | |
221 | | |
222 | | // XDispatchProvider |
223 | | |
224 | | uno::Reference< frame::XDispatch > SAL_CALL |
225 | | Interceptor::queryDispatch( |
226 | | const util::URL& URL, |
227 | | const OUString& TargetFrameName, |
228 | | sal_Int32 SearchFlags ) |
229 | 0 | { |
230 | 0 | osl::MutexGuard aGuard(m_aMutex); |
231 | 0 | if(URL.Complete == m_aInterceptedURL[0]) |
232 | 0 | return static_cast<frame::XDispatch*>(this); |
233 | 0 | else if(URL.Complete == m_aInterceptedURL[1]) |
234 | 0 | return nullptr ; |
235 | 0 | else if(URL.Complete == m_aInterceptedURL[2]) |
236 | 0 | return static_cast<frame::XDispatch*>(this); |
237 | 0 | else if(URL.Complete == m_aInterceptedURL[3]) |
238 | 0 | return static_cast<frame::XDispatch*>(this); |
239 | 0 | else if(URL.Complete == m_aInterceptedURL[4]) |
240 | 0 | return static_cast<frame::XDispatch*>(this); |
241 | 0 | else if(URL.Complete == m_aInterceptedURL[5]) |
242 | 0 | return static_cast<frame::XDispatch*>(this); |
243 | 0 | else { |
244 | 0 | if(m_xSlaveDispatchProvider.is()) |
245 | 0 | return m_xSlaveDispatchProvider->queryDispatch( |
246 | 0 | URL,TargetFrameName,SearchFlags); |
247 | 0 | else |
248 | 0 | return uno::Reference<frame::XDispatch>(nullptr); |
249 | 0 | } |
250 | 0 | } |
251 | | |
252 | | uno::Sequence< uno::Reference< frame::XDispatch > > SAL_CALL |
253 | | Interceptor::queryDispatches( |
254 | | const uno::Sequence<frame::DispatchDescriptor >& Requests ) |
255 | 0 | { |
256 | 0 | osl::MutexGuard aGuard(m_aMutex); |
257 | 0 | typedef uno::Sequence<uno::Reference<frame::XDispatch>> DispatchSeq; |
258 | 0 | DispatchSeq aRet = m_xSlaveDispatchProvider.is() |
259 | 0 | ? m_xSlaveDispatchProvider->queryDispatches(Requests) |
260 | 0 | : DispatchSeq(Requests.getLength()); |
261 | |
|
262 | 0 | auto aRetRange = asNonConstRange(aRet); |
263 | 0 | for(sal_Int32 i = 0; i < Requests.getLength(); ++i) |
264 | 0 | if(m_aInterceptedURL[0] == Requests[i].FeatureURL.Complete) |
265 | 0 | aRetRange[i] = static_cast<frame::XDispatch*>(this); |
266 | 0 | else if(m_aInterceptedURL[1] == Requests[i].FeatureURL.Complete) |
267 | 0 | aRetRange[i] = nullptr; |
268 | 0 | else if(m_aInterceptedURL[2] == Requests[i].FeatureURL.Complete) |
269 | 0 | aRetRange[i] = static_cast<frame::XDispatch*>(this); |
270 | 0 | else if(m_aInterceptedURL[3] == Requests[i].FeatureURL.Complete) |
271 | 0 | aRetRange[i] = static_cast<frame::XDispatch*>(this); |
272 | 0 | else if(m_aInterceptedURL[4] == Requests[i].FeatureURL.Complete) |
273 | 0 | aRetRange[i] = static_cast<frame::XDispatch*>(this); |
274 | 0 | else if(m_aInterceptedURL[5] == Requests[i].FeatureURL.Complete) |
275 | 0 | aRetRange[i] = static_cast<frame::XDispatch*>(this); |
276 | |
|
277 | 0 | return aRet; |
278 | 0 | } |
279 | | |
280 | | |
281 | | //XDispatchProviderInterceptor |
282 | | |
283 | | uno::Reference< frame::XDispatchProvider > SAL_CALL |
284 | | Interceptor::getSlaveDispatchProvider( ) |
285 | 0 | { |
286 | 0 | osl::MutexGuard aGuard(m_aMutex); |
287 | 0 | return m_xSlaveDispatchProvider; |
288 | 0 | } |
289 | | |
290 | | void SAL_CALL |
291 | | Interceptor::setSlaveDispatchProvider( |
292 | | const uno::Reference< frame::XDispatchProvider >& NewDispatchProvider ) |
293 | 0 | { |
294 | 0 | osl::MutexGuard aGuard(m_aMutex); |
295 | 0 | m_xSlaveDispatchProvider = NewDispatchProvider; |
296 | 0 | } |
297 | | |
298 | | |
299 | | uno::Reference< frame::XDispatchProvider > SAL_CALL |
300 | | Interceptor::getMasterDispatchProvider( ) |
301 | 0 | { |
302 | 0 | osl::MutexGuard aGuard(m_aMutex); |
303 | 0 | return m_xMasterDispatchProvider; |
304 | 0 | } |
305 | | |
306 | | |
307 | | void SAL_CALL |
308 | | Interceptor::setMasterDispatchProvider( |
309 | | const uno::Reference< frame::XDispatchProvider >& NewSupplier ) |
310 | 0 | { |
311 | 0 | osl::MutexGuard aGuard(m_aMutex); |
312 | 0 | m_xMasterDispatchProvider = NewSupplier; |
313 | 0 | } |
314 | | |
315 | | } // namespace embeddedobj |
316 | | |
317 | | /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |