1*6d739b60SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3*6d739b60SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4*6d739b60SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5*6d739b60SAndrew Rist  * distributed with this work for additional information
6*6d739b60SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7*6d739b60SAndrew Rist  * to you under the Apache License, Version 2.0 (the
8*6d739b60SAndrew Rist  * "License"); you may not use this file except in compliance
9*6d739b60SAndrew Rist  * with the License.  You may obtain a copy of the License at
10*6d739b60SAndrew Rist  *
11*6d739b60SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12*6d739b60SAndrew Rist  *
13*6d739b60SAndrew Rist  * Unless required by applicable law or agreed to in writing,
14*6d739b60SAndrew Rist  * software distributed under the License is distributed on an
15*6d739b60SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*6d739b60SAndrew Rist  * KIND, either express or implied.  See the License for the
17*6d739b60SAndrew Rist  * specific language governing permissions and limitations
18*6d739b60SAndrew Rist  * under the License.
19*6d739b60SAndrew Rist  *
20*6d739b60SAndrew Rist  *************************************************************/
21*6d739b60SAndrew Rist 
22*6d739b60SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_framework.hxx"
26cdf0e10cSrcweir 
27cdf0e10cSrcweir //-----------------------------------------------
28cdf0e10cSrcweir // my own includes
29cdf0e10cSrcweir 
30cdf0e10cSrcweir #include <algorithm>
31cdf0e10cSrcweir #include <helper/statusindicatorfactory.hxx>
32cdf0e10cSrcweir #include <helper/statusindicator.hxx>
33cdf0e10cSrcweir #include <helper/vclstatusindicator.hxx>
34cdf0e10cSrcweir #include <threadhelp/writeguard.hxx>
35cdf0e10cSrcweir #include <threadhelp/readguard.hxx>
36cdf0e10cSrcweir #include <services.h>
37cdf0e10cSrcweir #include <properties.h>
38cdf0e10cSrcweir 
39cdf0e10cSrcweir //-----------------------------------------------
40cdf0e10cSrcweir // interface includes
41cdf0e10cSrcweir #include <com/sun/star/awt/Rectangle.hpp>
42cdf0e10cSrcweir 
43cdf0e10cSrcweir #ifndef _COM_SUN_STAR_AWT_XCONTROLS_HPP_
44cdf0e10cSrcweir #include <com/sun/star/awt/XControl.hpp>
45cdf0e10cSrcweir #endif
46cdf0e10cSrcweir #include <com/sun/star/awt/XLayoutConstrains.hpp>
47cdf0e10cSrcweir #include <com/sun/star/awt/DeviceInfo.hpp>
48cdf0e10cSrcweir #include <com/sun/star/awt/PosSize.hpp>
49cdf0e10cSrcweir #include <com/sun/star/awt/WindowAttribute.hpp>
50cdf0e10cSrcweir #include <com/sun/star/awt/XTopWindow.hpp>
51cdf0e10cSrcweir #include <com/sun/star/awt/XWindow2.hpp>
52cdf0e10cSrcweir #include <com/sun/star/beans/XPropertySet.hpp>
53cdf0e10cSrcweir #include <com/sun/star/frame/XLayoutManager.hpp>
54cdf0e10cSrcweir 
55cdf0e10cSrcweir #ifndef _TOOLKIT_HELPER_VCLUNOHELPER_HXX_
56cdf0e10cSrcweir #include <toolkit/unohlp.hxx>
57cdf0e10cSrcweir #endif
58cdf0e10cSrcweir 
59cdf0e10cSrcweir //-----------------------------------------------
60cdf0e10cSrcweir // includes of other projects
61cdf0e10cSrcweir #include <comphelper/sequenceashashmap.hxx>
62cdf0e10cSrcweir #include <comphelper/mediadescriptor.hxx>
63cdf0e10cSrcweir #include <comphelper/configurationhelper.hxx>
64cdf0e10cSrcweir #include <vcl/svapp.hxx>
65cdf0e10cSrcweir #include <vos/mutex.hxx>
66cdf0e10cSrcweir 
67cdf0e10cSrcweir //-----------------------------------------------
68cdf0e10cSrcweir // namespace
69cdf0e10cSrcweir 
70cdf0e10cSrcweir namespace framework{
71cdf0e10cSrcweir 
72cdf0e10cSrcweir //-----------------------------------------------
73cdf0e10cSrcweir // definitions
74cdf0e10cSrcweir 
75cdf0e10cSrcweir sal_Int32 StatusIndicatorFactory::m_nInReschedule = 0;	///	static counter for rescheduling
76cdf0e10cSrcweir static ::rtl::OUString PROGRESS_RESOURCE = ::rtl::OUString::createFromAscii("private:resource/progressbar/progressbar");
77cdf0e10cSrcweir 
78cdf0e10cSrcweir //-----------------------------------------------
DEFINE_XINTERFACE_5(StatusIndicatorFactory,OWeakObject,DIRECT_INTERFACE (css::lang::XTypeProvider),DIRECT_INTERFACE (css::lang::XServiceInfo),DIRECT_INTERFACE (css::lang::XInitialization),DIRECT_INTERFACE (css::task::XStatusIndicatorFactory),DIRECT_INTERFACE (css::util::XUpdatable))79cdf0e10cSrcweir DEFINE_XINTERFACE_5(StatusIndicatorFactory                              ,
80cdf0e10cSrcweir                     OWeakObject                                         ,
81cdf0e10cSrcweir                     DIRECT_INTERFACE(css::lang::XTypeProvider          ),
82cdf0e10cSrcweir                     DIRECT_INTERFACE(css::lang::XServiceInfo           ),
83cdf0e10cSrcweir                     DIRECT_INTERFACE(css::lang::XInitialization        ),
84cdf0e10cSrcweir                     DIRECT_INTERFACE(css::task::XStatusIndicatorFactory),
85cdf0e10cSrcweir                     DIRECT_INTERFACE(css::util::XUpdatable             ))
86cdf0e10cSrcweir 
87cdf0e10cSrcweir DEFINE_XTYPEPROVIDER_5(StatusIndicatorFactory            ,
88cdf0e10cSrcweir                        css::lang::XTypeProvider          ,
89cdf0e10cSrcweir                        css::lang::XServiceInfo           ,
90cdf0e10cSrcweir                        css::lang::XInitialization        ,
91cdf0e10cSrcweir                        css::task::XStatusIndicatorFactory,
92cdf0e10cSrcweir                        css::util::XUpdatable             )
93cdf0e10cSrcweir 
94cdf0e10cSrcweir DEFINE_XSERVICEINFO_MULTISERVICE(StatusIndicatorFactory                   ,
95cdf0e10cSrcweir                                  ::cppu::OWeakObject                      ,
96cdf0e10cSrcweir                                  SERVICENAME_STATUSINDICATORFACTORY       ,
97cdf0e10cSrcweir                                  IMPLEMENTATIONNAME_STATUSINDICATORFACTORY)
98cdf0e10cSrcweir 
99cdf0e10cSrcweir DEFINE_INIT_SERVICE(StatusIndicatorFactory,
100cdf0e10cSrcweir                     {
101cdf0e10cSrcweir                         /*Attention
102cdf0e10cSrcweir                             I think we don't need any mutex or lock here ... because we are called by our own static method impl_createInstance()
103cdf0e10cSrcweir                             to create a new instance of this class by our own supported service factory.
104cdf0e10cSrcweir                             see macro DEFINE_XSERVICEINFO_MULTISERVICE and "impl_initService()" for further informations!
105cdf0e10cSrcweir                         */
106cdf0e10cSrcweir                     }
107cdf0e10cSrcweir                    )
108cdf0e10cSrcweir 
109cdf0e10cSrcweir //-----------------------------------------------
110cdf0e10cSrcweir StatusIndicatorFactory::StatusIndicatorFactory(const css::uno::Reference< css::lang::XMultiServiceFactory >& xSMGR)
111cdf0e10cSrcweir     : ThreadHelpBase      (         )
112cdf0e10cSrcweir     , ::cppu::OWeakObject (         )
113cdf0e10cSrcweir     , m_xSMGR             (xSMGR    )
114cdf0e10cSrcweir     , m_pWakeUp           (0        )
115cdf0e10cSrcweir     , m_bAllowReschedule  (sal_False)
116cdf0e10cSrcweir     , m_bAllowParentShow  (sal_False)
117cdf0e10cSrcweir     , m_bDisableReschedule(sal_False)
118cdf0e10cSrcweir {
119cdf0e10cSrcweir }
120cdf0e10cSrcweir 
121cdf0e10cSrcweir //-----------------------------------------------
~StatusIndicatorFactory()122cdf0e10cSrcweir StatusIndicatorFactory::~StatusIndicatorFactory()
123cdf0e10cSrcweir {
124cdf0e10cSrcweir     impl_stopWakeUpThread();
125cdf0e10cSrcweir }
126cdf0e10cSrcweir 
127cdf0e10cSrcweir //-----------------------------------------------
initialize(const css::uno::Sequence<css::uno::Any> & lArguments)128cdf0e10cSrcweir void SAL_CALL StatusIndicatorFactory::initialize(const css::uno::Sequence< css::uno::Any >& lArguments)
129cdf0e10cSrcweir     throw(css::uno::Exception       ,
130cdf0e10cSrcweir           css::uno::RuntimeException)
131cdf0e10cSrcweir {
132cdf0e10cSrcweir     ::comphelper::SequenceAsHashMap lArgs(lArguments);
133cdf0e10cSrcweir 
134cdf0e10cSrcweir     // SAFE -> ----------------------------------
135cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
136cdf0e10cSrcweir 
137cdf0e10cSrcweir     m_xFrame             = lArgs.getUnpackedValueOrDefault(STATUSINDICATORFACTORY_PROPNAME_FRAME            , css::uno::Reference< css::frame::XFrame >());
138cdf0e10cSrcweir     m_xPluggWindow       = lArgs.getUnpackedValueOrDefault(STATUSINDICATORFACTORY_PROPNAME_WINDOW           , css::uno::Reference< css::awt::XWindow >() );
139cdf0e10cSrcweir     m_bAllowParentShow   = lArgs.getUnpackedValueOrDefault(STATUSINDICATORFACTORY_PROPNAME_ALLOWPARENTSHOW  , (sal_Bool)sal_False                        );
140cdf0e10cSrcweir     m_bDisableReschedule = lArgs.getUnpackedValueOrDefault(STATUSINDICATORFACTORY_PROPNAME_DISABLERESCHEDULE, (sal_Bool)sal_False                        );
141cdf0e10cSrcweir 
142cdf0e10cSrcweir     aWriteLock.unlock();
143cdf0e10cSrcweir     // <- SAFE ----------------------------------
144cdf0e10cSrcweir 
145cdf0e10cSrcweir     impl_createProgress();
146cdf0e10cSrcweir }
147cdf0e10cSrcweir 
148cdf0e10cSrcweir //-----------------------------------------------
createStatusIndicator()149cdf0e10cSrcweir css::uno::Reference< css::task::XStatusIndicator > SAL_CALL StatusIndicatorFactory::createStatusIndicator()
150cdf0e10cSrcweir     throw(css::uno::RuntimeException)
151cdf0e10cSrcweir {
152cdf0e10cSrcweir     StatusIndicator* pIndicator = new StatusIndicator(this);
153cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xIndicator(static_cast< ::cppu::OWeakObject* >(pIndicator), css::uno::UNO_QUERY_THROW);
154cdf0e10cSrcweir 
155cdf0e10cSrcweir 	return xIndicator;
156cdf0e10cSrcweir }
157cdf0e10cSrcweir 
158cdf0e10cSrcweir //-----------------------------------------------
update()159cdf0e10cSrcweir void SAL_CALL StatusIndicatorFactory::update()
160cdf0e10cSrcweir     throw(css::uno::RuntimeException)
161cdf0e10cSrcweir {
162cdf0e10cSrcweir     // SAFE -> ----------------------------------
163cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
164cdf0e10cSrcweir     m_bAllowReschedule = sal_True;
165cdf0e10cSrcweir     aWriteLock.unlock();
166cdf0e10cSrcweir     // <- SAFE ----------------------------------
167cdf0e10cSrcweir }
168cdf0e10cSrcweir 
169cdf0e10cSrcweir //-----------------------------------------------
start(const css::uno::Reference<css::task::XStatusIndicator> & xChild,const::rtl::OUString & sText,sal_Int32 nRange)170cdf0e10cSrcweir void StatusIndicatorFactory::start(const css::uno::Reference< css::task::XStatusIndicator >& xChild,
171cdf0e10cSrcweir                                    const ::rtl::OUString&                                    sText ,
172cdf0e10cSrcweir                                          sal_Int32                                           nRange)
173cdf0e10cSrcweir {
174cdf0e10cSrcweir     // SAFE -> ----------------------------------
175cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
176cdf0e10cSrcweir 
177cdf0e10cSrcweir     // create new info structure for this child or move it to the front of our stack
178cdf0e10cSrcweir     IndicatorStack::iterator pItem = ::std::find(m_aStack.begin(), m_aStack.end(), xChild);
179cdf0e10cSrcweir     if (pItem != m_aStack.end())
180cdf0e10cSrcweir         m_aStack.erase(pItem);
181cdf0e10cSrcweir     IndicatorInfo aInfo(xChild, sText, nRange);
182cdf0e10cSrcweir     m_aStack.push_back (aInfo                );
183cdf0e10cSrcweir 
184cdf0e10cSrcweir     m_xActiveChild = xChild;
185cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xProgress = m_xProgress;
186cdf0e10cSrcweir 
187cdf0e10cSrcweir     aWriteLock.unlock();
188cdf0e10cSrcweir     // <- SAFE ----------------------------------
189cdf0e10cSrcweir 
190cdf0e10cSrcweir     implts_makeParentVisibleIfAllowed();
191cdf0e10cSrcweir 
192cdf0e10cSrcweir     if (xProgress.is())
193cdf0e10cSrcweir         xProgress->start(sText, nRange);
194cdf0e10cSrcweir 
195cdf0e10cSrcweir     impl_startWakeUpThread();
196cdf0e10cSrcweir     impl_reschedule(sal_True);
197cdf0e10cSrcweir }
198cdf0e10cSrcweir 
199cdf0e10cSrcweir //-----------------------------------------------
reset(const css::uno::Reference<css::task::XStatusIndicator> & xChild)200cdf0e10cSrcweir void StatusIndicatorFactory::reset(const css::uno::Reference< css::task::XStatusIndicator >& xChild)
201cdf0e10cSrcweir {
202cdf0e10cSrcweir     // SAFE -> ----------------------------------
203cdf0e10cSrcweir     ReadGuard aReadLock(m_aLock);
204cdf0e10cSrcweir 
205cdf0e10cSrcweir     // reset the internal info structure related to this child
206cdf0e10cSrcweir     IndicatorStack::iterator pItem = ::std::find(m_aStack.begin(), m_aStack.end(), xChild);
207cdf0e10cSrcweir     if (pItem != m_aStack.end())
208cdf0e10cSrcweir     {
209cdf0e10cSrcweir         pItem->m_nValue = 0;
210cdf0e10cSrcweir         pItem->m_sText  = ::rtl::OUString();
211cdf0e10cSrcweir     }
212cdf0e10cSrcweir 
213cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xActive   = m_xActiveChild;
214cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xProgress = m_xProgress;
215cdf0e10cSrcweir 
216cdf0e10cSrcweir     aReadLock.unlock();
217cdf0e10cSrcweir     // <- SAFE ----------------------------------
218cdf0e10cSrcweir 
219cdf0e10cSrcweir     // not the top most child => dont change UI
220cdf0e10cSrcweir     // But dont forget Reschedule!
221cdf0e10cSrcweir     if (
222cdf0e10cSrcweir         (xChild == xActive) &&
223cdf0e10cSrcweir         (xProgress.is()   )
224cdf0e10cSrcweir        )
225cdf0e10cSrcweir         xProgress->reset();
226cdf0e10cSrcweir 
227cdf0e10cSrcweir     impl_reschedule(sal_True);
228cdf0e10cSrcweir }
229cdf0e10cSrcweir 
230cdf0e10cSrcweir //-----------------------------------------------
end(const css::uno::Reference<css::task::XStatusIndicator> & xChild)231cdf0e10cSrcweir void StatusIndicatorFactory::end(const css::uno::Reference< css::task::XStatusIndicator >& xChild)
232cdf0e10cSrcweir {
233cdf0e10cSrcweir     // SAFE -> ----------------------------------
234cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
235cdf0e10cSrcweir 
236cdf0e10cSrcweir     // remove this child from our stack
237cdf0e10cSrcweir     IndicatorStack::iterator pItem = ::std::find(m_aStack.begin(), m_aStack.end(), xChild);
238cdf0e10cSrcweir     if (pItem != m_aStack.end())
239cdf0e10cSrcweir         m_aStack.erase(pItem);
240cdf0e10cSrcweir 
241cdf0e10cSrcweir     // activate next child ... or finish the progress if there is no further one.
242cdf0e10cSrcweir     m_xActiveChild.clear();
243cdf0e10cSrcweir     ::rtl::OUString                  sText;
244cdf0e10cSrcweir     sal_Int32                        nValue = 0;
245cdf0e10cSrcweir     IndicatorStack::reverse_iterator pNext  = m_aStack.rbegin();
246cdf0e10cSrcweir     if (pNext != m_aStack.rend())
247cdf0e10cSrcweir     {
248cdf0e10cSrcweir         m_xActiveChild = pNext->m_xIndicator;
249cdf0e10cSrcweir         sText          = pNext->m_sText;
250cdf0e10cSrcweir         nValue         = pNext->m_nValue;
251cdf0e10cSrcweir     }
252cdf0e10cSrcweir 
253cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xActive   = m_xActiveChild;
254cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xProgress = m_xProgress;
255cdf0e10cSrcweir 
256cdf0e10cSrcweir     aWriteLock.unlock();
257cdf0e10cSrcweir     // <- SAFE ----------------------------------
258cdf0e10cSrcweir 
259cdf0e10cSrcweir     if (xActive.is())
260cdf0e10cSrcweir     {
261cdf0e10cSrcweir         // There is at least one further child indicator.
262cdf0e10cSrcweir         // Actualize our progress, so it shows these values from now.
263cdf0e10cSrcweir         if (xProgress.is())
264cdf0e10cSrcweir         {
265cdf0e10cSrcweir             xProgress->setText (sText );
266cdf0e10cSrcweir             xProgress->setValue(nValue);
267cdf0e10cSrcweir         }
268cdf0e10cSrcweir     }
269cdf0e10cSrcweir     else
270cdf0e10cSrcweir     {
271cdf0e10cSrcweir         // Our stack is empty. No further child exists.
272cdf0e10cSrcweir         // Se we must "end" our progress realy
273cdf0e10cSrcweir         if (xProgress.is())
274cdf0e10cSrcweir             xProgress->end();
275cdf0e10cSrcweir         // Now hide the progress bar again.
276cdf0e10cSrcweir         impl_hideProgress();
277cdf0e10cSrcweir 
278cdf0e10cSrcweir         impl_stopWakeUpThread();
279cdf0e10cSrcweir     }
280cdf0e10cSrcweir 
281cdf0e10cSrcweir     impl_reschedule(sal_True);
282cdf0e10cSrcweir }
283cdf0e10cSrcweir 
284cdf0e10cSrcweir //-----------------------------------------------
setText(const css::uno::Reference<css::task::XStatusIndicator> & xChild,const::rtl::OUString & sText)285cdf0e10cSrcweir void StatusIndicatorFactory::setText(const css::uno::Reference< css::task::XStatusIndicator >& xChild,
286cdf0e10cSrcweir                                      const ::rtl::OUString&                                    sText )
287cdf0e10cSrcweir {
288cdf0e10cSrcweir     // SAFE -> ----------------------------------
289cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
290cdf0e10cSrcweir 
291cdf0e10cSrcweir     IndicatorStack::iterator pItem = ::std::find(m_aStack.begin(), m_aStack.end(), xChild);
292cdf0e10cSrcweir     if (pItem != m_aStack.end())
293cdf0e10cSrcweir         pItem->m_sText = sText;
294cdf0e10cSrcweir 
295cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xActive   = m_xActiveChild;
296cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xProgress = m_xProgress;
297cdf0e10cSrcweir 
298cdf0e10cSrcweir     aWriteLock.unlock();
299cdf0e10cSrcweir     // SAFE -> ----------------------------------
300cdf0e10cSrcweir 
301cdf0e10cSrcweir     // paint only the top most indicator
302cdf0e10cSrcweir     // but dont forget to Reschedule!
303cdf0e10cSrcweir     if (
304cdf0e10cSrcweir         (xChild == xActive) &&
305cdf0e10cSrcweir         (xProgress.is()   )
306cdf0e10cSrcweir        )
307cdf0e10cSrcweir     {
308cdf0e10cSrcweir         xProgress->setText(sText);
309cdf0e10cSrcweir     }
310cdf0e10cSrcweir 
311cdf0e10cSrcweir     impl_reschedule(sal_True);
312cdf0e10cSrcweir }
313cdf0e10cSrcweir 
314cdf0e10cSrcweir //-----------------------------------------------
setValue(const css::uno::Reference<css::task::XStatusIndicator> & xChild,sal_Int32 nValue)315cdf0e10cSrcweir void StatusIndicatorFactory::setValue( const css::uno::Reference< css::task::XStatusIndicator >& xChild ,
316cdf0e10cSrcweir                                              sal_Int32                                           nValue )
317cdf0e10cSrcweir {
318cdf0e10cSrcweir     // SAFE -> ----------------------------------
319cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
320cdf0e10cSrcweir 
321cdf0e10cSrcweir     sal_Int32 nOldValue = 0;
322cdf0e10cSrcweir     IndicatorStack::iterator pItem = ::std::find(m_aStack.begin(), m_aStack.end(), xChild);
323cdf0e10cSrcweir     if (pItem != m_aStack.end())
324cdf0e10cSrcweir     {
325cdf0e10cSrcweir         nOldValue       = pItem->m_nValue;
326cdf0e10cSrcweir         pItem->m_nValue = nValue;
327cdf0e10cSrcweir     }
328cdf0e10cSrcweir 
329cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xActive    = m_xActiveChild;
330cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xProgress  = m_xProgress;
331cdf0e10cSrcweir 
332cdf0e10cSrcweir     aWriteLock.unlock();
333cdf0e10cSrcweir     // SAFE -> ----------------------------------
334cdf0e10cSrcweir 
335cdf0e10cSrcweir     if (
336cdf0e10cSrcweir         (xChild    == xActive) &&
337cdf0e10cSrcweir         (nOldValue != nValue ) &&
338cdf0e10cSrcweir         (xProgress.is()      )
339cdf0e10cSrcweir        )
340cdf0e10cSrcweir     {
341cdf0e10cSrcweir         xProgress->setValue(nValue);
342cdf0e10cSrcweir     }
343cdf0e10cSrcweir 
344cdf0e10cSrcweir     impl_reschedule(sal_False);
345cdf0e10cSrcweir }
346cdf0e10cSrcweir 
347cdf0e10cSrcweir //-----------------------------------------------
implts_makeParentVisibleIfAllowed()348cdf0e10cSrcweir void StatusIndicatorFactory::implts_makeParentVisibleIfAllowed()
349cdf0e10cSrcweir {
350cdf0e10cSrcweir     // SAFE -> ----------------------------------
351cdf0e10cSrcweir     ReadGuard aReadLock(m_aLock);
352cdf0e10cSrcweir 
353cdf0e10cSrcweir     if (!m_bAllowParentShow)
354cdf0e10cSrcweir         return;
355cdf0e10cSrcweir 
356cdf0e10cSrcweir     css::uno::Reference< css::frame::XFrame > xFrame      (m_xFrame.get()      , css::uno::UNO_QUERY);
357cdf0e10cSrcweir     css::uno::Reference< css::awt::XWindow >  xPluggWindow(m_xPluggWindow.get(), css::uno::UNO_QUERY);
358cdf0e10cSrcweir     css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR( m_xSMGR.get(), css::uno::UNO_QUERY);
359cdf0e10cSrcweir 
360cdf0e10cSrcweir     aReadLock.unlock();
361cdf0e10cSrcweir     // <- SAFE ----------------------------------
362cdf0e10cSrcweir 
363cdf0e10cSrcweir     css::uno::Reference< css::awt::XWindow > xParentWindow;
364cdf0e10cSrcweir     if (xFrame.is())
365cdf0e10cSrcweir         xParentWindow = xFrame->getContainerWindow();
366cdf0e10cSrcweir     else
367cdf0e10cSrcweir         xParentWindow = xPluggWindow;
368cdf0e10cSrcweir 
369cdf0e10cSrcweir     // dont disturb user in case he put the loading document into the background!
370cdf0e10cSrcweir     // Supress any setVisible() or toFront() call in case the initial show was
371cdf0e10cSrcweir     // already made.
372cdf0e10cSrcweir     css::uno::Reference< css::awt::XWindow2 > xVisibleCheck(xParentWindow, css::uno::UNO_QUERY);
373cdf0e10cSrcweir     sal_Bool bIsVisible = sal_False;
374cdf0e10cSrcweir     if (xVisibleCheck.is())
375cdf0e10cSrcweir         bIsVisible = xVisibleCheck->isVisible();
376cdf0e10cSrcweir 
377cdf0e10cSrcweir     if (bIsVisible)
378cdf0e10cSrcweir     {
379cdf0e10cSrcweir         impl_showProgress();
380cdf0e10cSrcweir         return;
381cdf0e10cSrcweir     }
382cdf0e10cSrcweir 
383cdf0e10cSrcweir     // Check if the layout manager has been set to invisible state. It this case we are also
384cdf0e10cSrcweir     // not allowed to set the frame visible!
385cdf0e10cSrcweir     css::uno::Reference< css::beans::XPropertySet > xPropSet(xFrame, css::uno::UNO_QUERY);
386cdf0e10cSrcweir     if (xPropSet.is())
387cdf0e10cSrcweir     {
388cdf0e10cSrcweir         css::uno::Reference< css::frame::XLayoutManager > xLayoutManager;
389cdf0e10cSrcweir         xPropSet->getPropertyValue(FRAME_PROPNAME_LAYOUTMANAGER) >>= xLayoutManager;
390cdf0e10cSrcweir         if (xLayoutManager.is())
391cdf0e10cSrcweir         {
392cdf0e10cSrcweir             if ( !xLayoutManager->isVisible() )
393cdf0e10cSrcweir                 return;
394cdf0e10cSrcweir         }
395cdf0e10cSrcweir     }
396cdf0e10cSrcweir 
397cdf0e10cSrcweir     // Ok the window should be made visible ... becuase it isnt currently visible.
398cdf0e10cSrcweir     // BUT ..!
399cdf0e10cSrcweir     // We need a Hack for our applications: They get her progress from the frame directly
400cdf0e10cSrcweir     // on saving documents. Because there is no progress set on the MediaDescriptor.
401cdf0e10cSrcweir     // But that's wrong. In case the document was opened hidden, they shouldnt use any progress .-(
402cdf0e10cSrcweir     // They only possible workaround: dont show the parent window here, if the document was opened hidden.
403cdf0e10cSrcweir     sal_Bool bHiddenDoc = sal_False;
404cdf0e10cSrcweir     if (xFrame.is())
405cdf0e10cSrcweir     {
406cdf0e10cSrcweir         css::uno::Reference< css::frame::XController > xController;
407cdf0e10cSrcweir         css::uno::Reference< css::frame::XModel >      xModel     ;
408cdf0e10cSrcweir         xController = xFrame->getController();
409cdf0e10cSrcweir         if (xController.is())
410cdf0e10cSrcweir             xModel = xController->getModel();
411cdf0e10cSrcweir         if (xModel.is())
412cdf0e10cSrcweir         {
413cdf0e10cSrcweir             ::comphelper::MediaDescriptor lDocArgs(xModel->getArgs());
414cdf0e10cSrcweir             bHiddenDoc = lDocArgs.getUnpackedValueOrDefault(
415cdf0e10cSrcweir                 ::comphelper::MediaDescriptor::PROP_HIDDEN(),
416cdf0e10cSrcweir                 (sal_Bool)sal_False);
417cdf0e10cSrcweir         }
418cdf0e10cSrcweir     }
419cdf0e10cSrcweir 
420cdf0e10cSrcweir     if (bHiddenDoc)
421cdf0e10cSrcweir         return;
422cdf0e10cSrcweir 
423cdf0e10cSrcweir     // OK: The document was not opened in hidden mode ...
424cdf0e10cSrcweir     // and the window isnt already visible.
425cdf0e10cSrcweir     // Show it and bring it to front.
426cdf0e10cSrcweir     // But before we have to be sure, that our internal used helper progress
427cdf0e10cSrcweir     // is visible too.
428cdf0e10cSrcweir     impl_showProgress();
429cdf0e10cSrcweir 
430cdf0e10cSrcweir     ::vos::OClearableGuard aSolarGuard(Application::GetSolarMutex());
431cdf0e10cSrcweir     Window* pWindow = VCLUnoHelper::GetWindow(xParentWindow);
432cdf0e10cSrcweir     if ( pWindow )
433cdf0e10cSrcweir     {
434cdf0e10cSrcweir         bool bForceFrontAndFocus(false);
435cdf0e10cSrcweir         ::comphelper::ConfigurationHelper::readDirectKey(
436cdf0e10cSrcweir             xSMGR,
437cdf0e10cSrcweir             ::rtl::OUString::createFromAscii("org.openoffice.Office.Common/View"),
438cdf0e10cSrcweir             ::rtl::OUString::createFromAscii("NewDocumentHandling"),
439cdf0e10cSrcweir             ::rtl::OUString::createFromAscii("ForceFocusAndToFront"),
440cdf0e10cSrcweir             ::comphelper::ConfigurationHelper::E_READONLY) >>= bForceFrontAndFocus;
441cdf0e10cSrcweir 
442cdf0e10cSrcweir         pWindow->Show(sal_True, bForceFrontAndFocus ? SHOW_FOREGROUNDTASK : 0 );
443cdf0e10cSrcweir     }
444cdf0e10cSrcweir 
445cdf0e10cSrcweir     /*
446cdf0e10cSrcweir     #i75167# dont disturb window manager handling .-)
447cdf0e10cSrcweir     css::uno::Reference< css::awt::XTopWindow > xParentWindowTop(xParentWindow, css::uno::UNO_QUERY);
448cdf0e10cSrcweir     if (xParentWindowTop.is())
449cdf0e10cSrcweir         xParentWindowTop->toFront();
450cdf0e10cSrcweir     */
451cdf0e10cSrcweir }
452cdf0e10cSrcweir 
453cdf0e10cSrcweir //-----------------------------------------------
impl_createProgress()454cdf0e10cSrcweir void StatusIndicatorFactory::impl_createProgress()
455cdf0e10cSrcweir {
456cdf0e10cSrcweir     // SAFE -> ----------------------------------
457cdf0e10cSrcweir     ReadGuard aReadLock(m_aLock);
458cdf0e10cSrcweir 
459cdf0e10cSrcweir     css::uno::Reference< css::frame::XFrame >              xFrame (m_xFrame.get()      , css::uno::UNO_QUERY);
460cdf0e10cSrcweir     css::uno::Reference< css::awt::XWindow >               xWindow(m_xPluggWindow.get(), css::uno::UNO_QUERY);
461cdf0e10cSrcweir     css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR  = m_xSMGR;
462cdf0e10cSrcweir 
463cdf0e10cSrcweir     aReadLock.lock();
464cdf0e10cSrcweir     // <- SAFE ----------------------------------
465cdf0e10cSrcweir 
466cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xProgress;
467cdf0e10cSrcweir 
468cdf0e10cSrcweir     if (xWindow.is())
469cdf0e10cSrcweir     {
470cdf0e10cSrcweir         // use vcl based progress implementation in plugged mode
471cdf0e10cSrcweir         VCLStatusIndicator* pVCLProgress = new VCLStatusIndicator(xSMGR, xWindow);
472cdf0e10cSrcweir         xProgress = css::uno::Reference< css::task::XStatusIndicator >(static_cast< css::task::XStatusIndicator* >(pVCLProgress), css::uno::UNO_QUERY);
473cdf0e10cSrcweir     }
474cdf0e10cSrcweir     else
475cdf0e10cSrcweir     if (xFrame.is())
476cdf0e10cSrcweir     {
477cdf0e10cSrcweir         // use frame layouted progress implementation
478cdf0e10cSrcweir         css::uno::Reference< css::beans::XPropertySet > xPropSet(xFrame, css::uno::UNO_QUERY);
479cdf0e10cSrcweir         if (xPropSet.is())
480cdf0e10cSrcweir         {
481cdf0e10cSrcweir             css::uno::Reference< css::frame::XLayoutManager > xLayoutManager;
482cdf0e10cSrcweir             xPropSet->getPropertyValue(FRAME_PROPNAME_LAYOUTMANAGER) >>= xLayoutManager;
483cdf0e10cSrcweir             if (xLayoutManager.is())
484cdf0e10cSrcweir             {
485cdf0e10cSrcweir                 xLayoutManager->lock();
486cdf0e10cSrcweir                 xLayoutManager->createElement( PROGRESS_RESOURCE );
487cdf0e10cSrcweir                 xLayoutManager->hideElement( PROGRESS_RESOURCE );
488cdf0e10cSrcweir 
489cdf0e10cSrcweir                 css::uno::Reference< css::ui::XUIElement > xProgressBar = xLayoutManager->getElement(PROGRESS_RESOURCE);
490cdf0e10cSrcweir                 if (xProgressBar.is())
491cdf0e10cSrcweir                     xProgress = css::uno::Reference< css::task::XStatusIndicator >(xProgressBar->getRealInterface(), css::uno::UNO_QUERY);
492cdf0e10cSrcweir                 xLayoutManager->unlock();
493cdf0e10cSrcweir             }
494cdf0e10cSrcweir         }
495cdf0e10cSrcweir     }
496cdf0e10cSrcweir 
497cdf0e10cSrcweir     // SAFE -> ----------------------------------
498cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
499cdf0e10cSrcweir     m_xProgress = xProgress;
500cdf0e10cSrcweir     aWriteLock.lock();
501cdf0e10cSrcweir     // <- SAFE ----------------------------------
502cdf0e10cSrcweir }
503cdf0e10cSrcweir 
504cdf0e10cSrcweir //-----------------------------------------------
impl_showProgress()505cdf0e10cSrcweir void StatusIndicatorFactory::impl_showProgress()
506cdf0e10cSrcweir {
507cdf0e10cSrcweir     // SAFE -> ----------------------------------
508cdf0e10cSrcweir     ReadGuard aReadLock(m_aLock);
509cdf0e10cSrcweir 
510cdf0e10cSrcweir     css::uno::Reference< css::frame::XFrame >              xFrame (m_xFrame.get()      , css::uno::UNO_QUERY);
511cdf0e10cSrcweir     css::uno::Reference< css::awt::XWindow >               xWindow(m_xPluggWindow.get(), css::uno::UNO_QUERY);
512cdf0e10cSrcweir     css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR  = m_xSMGR;
513cdf0e10cSrcweir 
514cdf0e10cSrcweir     aReadLock.lock();
515cdf0e10cSrcweir     // <- SAFE ----------------------------------
516cdf0e10cSrcweir 
517cdf0e10cSrcweir     css::uno::Reference< css::task::XStatusIndicator > xProgress;
518cdf0e10cSrcweir 
519cdf0e10cSrcweir     if (xFrame.is())
520cdf0e10cSrcweir     {
521cdf0e10cSrcweir         // use frame layouted progress implementation
522cdf0e10cSrcweir         css::uno::Reference< css::beans::XPropertySet > xPropSet(xFrame, css::uno::UNO_QUERY);
523cdf0e10cSrcweir         if (xPropSet.is())
524cdf0e10cSrcweir         {
525cdf0e10cSrcweir             css::uno::Reference< css::frame::XLayoutManager > xLayoutManager;
526cdf0e10cSrcweir             xPropSet->getPropertyValue(FRAME_PROPNAME_LAYOUTMANAGER) >>= xLayoutManager;
527cdf0e10cSrcweir             if (xLayoutManager.is())
528cdf0e10cSrcweir             {
529cdf0e10cSrcweir                 // Be sure that we have always a progress. It can be that our frame
530cdf0e10cSrcweir                 // was recycled and therefore the progress was destroyed!
531cdf0e10cSrcweir                 // CreateElement does nothing if there is already a valid progress.
532cdf0e10cSrcweir                 xLayoutManager->createElement( PROGRESS_RESOURCE );
533cdf0e10cSrcweir                 xLayoutManager->showElement( PROGRESS_RESOURCE );
534cdf0e10cSrcweir 
535cdf0e10cSrcweir                 css::uno::Reference< css::ui::XUIElement > xProgressBar = xLayoutManager->getElement(PROGRESS_RESOURCE);
536cdf0e10cSrcweir                 if (xProgressBar.is())
537cdf0e10cSrcweir                     xProgress = css::uno::Reference< css::task::XStatusIndicator >(xProgressBar->getRealInterface(), css::uno::UNO_QUERY);
538cdf0e10cSrcweir             }
539cdf0e10cSrcweir         }
540cdf0e10cSrcweir 
541cdf0e10cSrcweir         // SAFE -> ----------------------------------
542cdf0e10cSrcweir         WriteGuard aWriteLock(m_aLock);
543cdf0e10cSrcweir         m_xProgress = xProgress;
544cdf0e10cSrcweir         aWriteLock.lock();
545cdf0e10cSrcweir         // <- SAFE ----------------------------------
546cdf0e10cSrcweir     }
547cdf0e10cSrcweir }
548cdf0e10cSrcweir 
549cdf0e10cSrcweir //-----------------------------------------------
impl_hideProgress()550cdf0e10cSrcweir void StatusIndicatorFactory::impl_hideProgress()
551cdf0e10cSrcweir {
552cdf0e10cSrcweir     // SAFE -> ----------------------------------
553cdf0e10cSrcweir     ReadGuard aReadLock(m_aLock);
554cdf0e10cSrcweir 
555cdf0e10cSrcweir     css::uno::Reference< css::frame::XFrame >              xFrame (m_xFrame.get()      , css::uno::UNO_QUERY);
556cdf0e10cSrcweir     css::uno::Reference< css::awt::XWindow >               xWindow(m_xPluggWindow.get(), css::uno::UNO_QUERY);
557cdf0e10cSrcweir     css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR  = m_xSMGR;
558cdf0e10cSrcweir 
559cdf0e10cSrcweir     aReadLock.lock();
560cdf0e10cSrcweir     // <- SAFE ----------------------------------
561cdf0e10cSrcweir 
562cdf0e10cSrcweir     if (xFrame.is())
563cdf0e10cSrcweir     {
564cdf0e10cSrcweir         // use frame layouted progress implementation
565cdf0e10cSrcweir         css::uno::Reference< css::beans::XPropertySet > xPropSet(xFrame, css::uno::UNO_QUERY);
566cdf0e10cSrcweir         if (xPropSet.is())
567cdf0e10cSrcweir         {
568cdf0e10cSrcweir             css::uno::Reference< css::frame::XLayoutManager > xLayoutManager;
569cdf0e10cSrcweir             xPropSet->getPropertyValue(FRAME_PROPNAME_LAYOUTMANAGER) >>= xLayoutManager;
570cdf0e10cSrcweir             if (xLayoutManager.is())
571cdf0e10cSrcweir                 xLayoutManager->hideElement( PROGRESS_RESOURCE );
572cdf0e10cSrcweir         }
573cdf0e10cSrcweir     }
574cdf0e10cSrcweir }
575cdf0e10cSrcweir 
576cdf0e10cSrcweir //-----------------------------------------------
impl_reschedule(sal_Bool bForce)577cdf0e10cSrcweir void StatusIndicatorFactory::impl_reschedule(sal_Bool bForce)
578cdf0e10cSrcweir {
579cdf0e10cSrcweir     // SAFE ->
580cdf0e10cSrcweir     ReadGuard aReadLock(m_aLock);
581cdf0e10cSrcweir     if (m_bDisableReschedule)
582cdf0e10cSrcweir         return;
583cdf0e10cSrcweir     aReadLock.unlock();
584cdf0e10cSrcweir     // <- SAFE
585cdf0e10cSrcweir 
586cdf0e10cSrcweir     sal_Bool bReschedule = bForce;
587cdf0e10cSrcweir     if (!bReschedule)
588cdf0e10cSrcweir     {
589cdf0e10cSrcweir         // SAFE ->
590cdf0e10cSrcweir         WriteGuard aWriteLock(m_aLock);
591cdf0e10cSrcweir         bReschedule        = m_bAllowReschedule;
592cdf0e10cSrcweir         m_bAllowReschedule = sal_False;
593cdf0e10cSrcweir         aWriteLock.unlock();
594cdf0e10cSrcweir         // <- SAFE
595cdf0e10cSrcweir     }
596cdf0e10cSrcweir 
597cdf0e10cSrcweir     if (!bReschedule)
598cdf0e10cSrcweir         return;
599cdf0e10cSrcweir 
600cdf0e10cSrcweir     // SAFE ->
601cdf0e10cSrcweir     WriteGuard aGlobalLock(LockHelper::getGlobalLock());
602cdf0e10cSrcweir 
603cdf0e10cSrcweir 	if (m_nInReschedule == 0)
604cdf0e10cSrcweir 	{
605cdf0e10cSrcweir 		++m_nInReschedule;
606cdf0e10cSrcweir         aGlobalLock.unlock();
607cdf0e10cSrcweir         // <- SAFE
608cdf0e10cSrcweir 
609cdf0e10cSrcweir         Application::Reschedule(true);
610cdf0e10cSrcweir 
611cdf0e10cSrcweir         // SAFE ->
612cdf0e10cSrcweir         aGlobalLock.lock();
613cdf0e10cSrcweir 		--m_nInReschedule;
614cdf0e10cSrcweir 	}
615cdf0e10cSrcweir }
616cdf0e10cSrcweir 
617cdf0e10cSrcweir //-----------------------------------------------
impl_startWakeUpThread()618cdf0e10cSrcweir void StatusIndicatorFactory::impl_startWakeUpThread()
619cdf0e10cSrcweir {
620cdf0e10cSrcweir     // SAFE ->
621cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
622cdf0e10cSrcweir 
623cdf0e10cSrcweir     if (m_bDisableReschedule)
624cdf0e10cSrcweir         return;
625cdf0e10cSrcweir 
626cdf0e10cSrcweir     if (!m_pWakeUp)
627cdf0e10cSrcweir     {
628cdf0e10cSrcweir         m_pWakeUp = new WakeUpThread(this);
629cdf0e10cSrcweir         m_pWakeUp->create();
630cdf0e10cSrcweir     }
631cdf0e10cSrcweir     aWriteLock.unlock();
632cdf0e10cSrcweir     // <- SAFE
633cdf0e10cSrcweir }
634cdf0e10cSrcweir 
635cdf0e10cSrcweir //-----------------------------------------------
impl_stopWakeUpThread()636cdf0e10cSrcweir void StatusIndicatorFactory::impl_stopWakeUpThread()
637cdf0e10cSrcweir {
638cdf0e10cSrcweir     // SAFE ->
639cdf0e10cSrcweir     WriteGuard aWriteLock(m_aLock);
640cdf0e10cSrcweir     if (m_pWakeUp)
641cdf0e10cSrcweir     {
642cdf0e10cSrcweir         // Thread kill itself after terminate()!
643cdf0e10cSrcweir         m_pWakeUp->terminate();
644cdf0e10cSrcweir         m_pWakeUp = 0;
645cdf0e10cSrcweir     }
646cdf0e10cSrcweir     aWriteLock.unlock();
647cdf0e10cSrcweir     // <- SAFE
648cdf0e10cSrcweir }
649cdf0e10cSrcweir 
650cdf0e10cSrcweir } // namespace framework
651