1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: statusindicator.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 //____________________________________________________________________________________________________________
33 //____________________________________________________________________________________________________________
35 #include "statusindicator.hxx"
37 //____________________________________________________________________________________________________________
38 // includes of other projects
39 //____________________________________________________________________________________________________________
40 #include <com/sun/star/awt/InvalidateStyle.hpp>
41 #include <com/sun/star/awt/WindowAttribute.hpp>
42 #include <cppuhelper/typeprovider.hxx>
43 #include <tools/debug.hxx>
45 //____________________________________________________________________________________________________________
46 // includes of my project
47 //____________________________________________________________________________________________________________
48 #include "progressbar.hxx"
50 //____________________________________________________________________________________________________________
52 //____________________________________________________________________________________________________________
54 using namespace ::cppu
;
55 using namespace ::osl
;
56 using namespace ::rtl
;
57 using namespace ::com::sun::star::uno
;
58 using namespace ::com::sun::star::lang
;
59 using namespace ::com::sun::star::awt
;
60 using namespace ::com::sun::star::task
;
62 namespace unocontrols
{
64 //____________________________________________________________________________________________________________
66 //____________________________________________________________________________________________________________
68 StatusIndicator::StatusIndicator( const Reference
< XMultiServiceFactory
>& xFactory
)
69 : BaseContainerControl ( xFactory
)
71 // Its not allowed to work with member in this method (refcounter !!!)
72 // But with a HACK (++refcount) its "OK" :-(
75 // Create instances for fixedtext and progress ...
76 m_xText
= Reference
< XFixedText
> ( xFactory
->createInstance( OUString::createFromAscii( FIXEDTEXT_SERVICENAME
) ), UNO_QUERY
);
77 m_xProgressBar
= Reference
< XProgressBar
> ( xFactory
->createInstance( OUString::createFromAscii( SERVICENAME_PROGRESSBAR
) ), UNO_QUERY
);
78 // ... cast controls to Reference< XControl > and set model ...
79 // ( ProgressBar has no model !!! )
80 Reference
< XControl
> xTextControl ( m_xText
, UNO_QUERY
);
81 Reference
< XControl
> xProgressControl ( m_xProgressBar
, UNO_QUERY
);
82 xTextControl
->setModel( Reference
< XControlModel
>( xFactory
->createInstance( OUString::createFromAscii( FIXEDTEXT_MODELNAME
) ), UNO_QUERY
) );
83 // ... and add controls to basecontainercontrol!
84 addControl( OUString::createFromAscii( CONTROLNAME_TEXT
), xTextControl
);
85 addControl( OUString::createFromAscii( CONTROLNAME_PROGRESSBAR
), xProgressControl
);
86 // FixedText make it automaticly visible by himself ... but not the progressbar !!!
87 // it must be set explicitly
88 Reference
< XWindow
> xProgressWindow( m_xProgressBar
, UNO_QUERY
);
89 xProgressWindow
->setVisible( sal_True
);
90 // Reset to defaults !!!
91 // (progressbar take automaticly its own defaults)
92 m_xText
->setText( OUString::createFromAscii( DEFAULT_TEXT
) );
97 StatusIndicator::~StatusIndicator()
99 // Release all references
100 m_xText
= Reference
< XFixedText
>();
101 m_xProgressBar
= Reference
< XProgressBar
>();
104 //____________________________________________________________________________________________________________
106 //____________________________________________________________________________________________________________
108 Any SAL_CALL
StatusIndicator::queryInterface( const Type
& rType
) throw( RuntimeException
)
111 // Don't use mutex or guard in this method!!! Is a method of XInterface.
113 Reference
< XInterface
> xDel
= BaseContainerControl::impl_getDelegator();
116 // If an delegator exist, forward question to his queryInterface.
117 // Delegator will ask his own queryAggregation!
118 aReturn
= xDel
->queryInterface( rType
);
122 // If an delegator unknown, forward question to own queryAggregation.
123 aReturn
= queryAggregation( rType
);
129 //____________________________________________________________________________________________________________
131 //____________________________________________________________________________________________________________
133 void SAL_CALL
StatusIndicator::acquire() throw()
136 // Don't use mutex or guard in this method!!! Is a method of XInterface.
138 // Forward to baseclass
139 BaseControl::acquire();
142 //____________________________________________________________________________________________________________
144 //____________________________________________________________________________________________________________
146 void SAL_CALL
StatusIndicator::release() throw()
149 // Don't use mutex or guard in this method!!! Is a method of XInterface.
151 // Forward to baseclass
152 BaseControl::release();
155 //____________________________________________________________________________________________________________
157 //____________________________________________________________________________________________________________
159 Sequence
< Type
> SAL_CALL
StatusIndicator::getTypes() throw( RuntimeException
)
161 // Optimize this method !
162 // We initialize a static variable only one time. And we don't must use a mutex at every call!
163 // For the first call; pTypeCollection is NULL - for the second call pTypeCollection is different from NULL!
164 static OTypeCollection
* pTypeCollection
= NULL
;
166 if ( pTypeCollection
== NULL
)
168 // Ready for multithreading; get global mutex for first call of this method only! see before
169 MutexGuard
aGuard( Mutex::getGlobalMutex() );
171 // Control these pointer again ... it can be, that another instance will be faster then these!
172 if ( pTypeCollection
== NULL
)
174 // Create a static typecollection ...
175 static OTypeCollection
aTypeCollection ( ::getCppuType(( const Reference
< XLayoutConstrains
>*)NULL
) ,
176 ::getCppuType(( const Reference
< XStatusIndicator
>*)NULL
) ,
177 BaseContainerControl::getTypes()
179 // ... and set his address to static pointer!
180 pTypeCollection
= &aTypeCollection
;
184 return pTypeCollection
->getTypes();
187 //____________________________________________________________________________________________________________
189 //____________________________________________________________________________________________________________
191 Any SAL_CALL
StatusIndicator::queryAggregation( const Type
& aType
) throw( RuntimeException
)
193 // Ask for my own supported interfaces ...
194 // Attention: XTypeProvider and XInterface are supported by OComponentHelper!
195 Any
aReturn ( ::cppu::queryInterface( aType
,
196 static_cast< XLayoutConstrains
* > ( this ) ,
197 static_cast< XStatusIndicator
* > ( this )
201 // If searched interface not supported by this class ...
202 if ( aReturn
.hasValue() == sal_False
)
204 // ... ask baseclasses.
205 aReturn
= BaseControl::queryAggregation( aType
);
211 //____________________________________________________________________________________________________________
213 //____________________________________________________________________________________________________________
215 void SAL_CALL
StatusIndicator::start( const OUString
& sText
, sal_Int32 nRange
) throw( RuntimeException
)
217 // Ready for multithreading
218 MutexGuard
aGuard( m_aMutex
);
220 // Initialize status controls with given values.
221 m_xText
->setText( sText
);
222 m_xProgressBar
->setRange( 0, nRange
);
223 // force repaint ... fixedtext has changed !
224 impl_recalcLayout ( WindowEvent(static_cast< OWeakObject
* >(this),0,0,impl_getWidth(),impl_getHeight(),0,0,0,0) ) ;
227 //____________________________________________________________________________________________________________
229 //____________________________________________________________________________________________________________
231 void SAL_CALL
StatusIndicator::end() throw( RuntimeException
)
233 // Ready for multithreading
234 MutexGuard
aGuard( m_aMutex
);
236 // Clear values of status controls.
237 m_xText
->setText( OUString() );
238 m_xProgressBar
->setValue( 0 );
239 setVisible( sal_False
);
242 //____________________________________________________________________________________________________________
244 //____________________________________________________________________________________________________________
246 void SAL_CALL
StatusIndicator::setText( const OUString
& sText
) throw( RuntimeException
)
248 // Ready for multithreading
249 MutexGuard
aGuard( m_aMutex
);
251 // Take text on right control
252 m_xText
->setText( sText
);
255 //____________________________________________________________________________________________________________
257 //____________________________________________________________________________________________________________
259 void SAL_CALL
StatusIndicator::setValue( sal_Int32 nValue
) throw( RuntimeException
)
261 // Ready for multithreading
262 MutexGuard
aGuard( m_aMutex
);
264 // Take value on right control
265 m_xProgressBar
->setValue( nValue
);
268 //____________________________________________________________________________________________________________
270 //____________________________________________________________________________________________________________
272 void SAL_CALL
StatusIndicator::reset() throw( RuntimeException
)
274 // Ready for multithreading
275 MutexGuard
aGuard( m_aMutex
);
277 // Clear values of status controls.
278 // (Don't hide the window! User will reset current values ... but he will not finish using of indicator!)
279 m_xText
->setText( OUString() );
280 m_xProgressBar
->setValue( 0 );
283 //____________________________________________________________________________________________________________
285 //____________________________________________________________________________________________________________
287 Size SAL_CALL
StatusIndicator::getMinimumSize () throw( RuntimeException
)
289 return Size (DEFAULT_WIDTH
, DEFAULT_HEIGHT
) ;
292 //____________________________________________________________________________________________________________
294 //____________________________________________________________________________________________________________
296 Size SAL_CALL
StatusIndicator::getPreferredSize () throw( RuntimeException
)
298 // Ready for multithreading
299 ClearableMutexGuard
aGuard ( m_aMutex
) ;
301 // get information about required place of child controls
302 Reference
< XLayoutConstrains
> xTextLayout ( m_xText
, UNO_QUERY
);
303 Size aTextSize
= xTextLayout
->getPreferredSize();
307 // calc preferred size of status indicator
308 sal_Int32 nWidth
= impl_getWidth() ;
309 sal_Int32 nHeight
= (2*FREEBORDER
)+aTextSize
.Height
;
312 if ( nWidth
<DEFAULT_WIDTH
)
314 nWidth
= DEFAULT_WIDTH
;
316 if ( nHeight
<DEFAULT_HEIGHT
)
318 nHeight
= DEFAULT_HEIGHT
;
322 return Size ( nWidth
, nHeight
) ;
325 //____________________________________________________________________________________________________________
327 //____________________________________________________________________________________________________________
329 Size SAL_CALL
StatusIndicator::calcAdjustedSize ( const Size
& /*rNewSize*/ ) throw( RuntimeException
)
331 return getPreferredSize () ;
334 //____________________________________________________________________________________________________________
336 //____________________________________________________________________________________________________________
338 void SAL_CALL
StatusIndicator::createPeer ( const Reference
< XToolkit
> & rToolkit
, const Reference
< XWindowPeer
> & rParent
) throw( RuntimeException
)
340 if( getPeer().is() == sal_False
)
342 BaseContainerControl::createPeer( rToolkit
, rParent
);
344 // If user forget to call "setPosSize()", we have still a correct size.
345 // And a "MinimumSize" IS A "MinimumSize"!
346 // We change not the position of control at this point.
347 Size aDefaultSize
= getMinimumSize () ;
348 setPosSize ( 0, 0, aDefaultSize
.Width
, aDefaultSize
.Height
, PosSize::SIZE
) ;
352 //____________________________________________________________________________________________________________
354 //____________________________________________________________________________________________________________
356 sal_Bool SAL_CALL
StatusIndicator::setModel ( const Reference
< XControlModel
> & /*rModel*/ ) throw( RuntimeException
)
362 //____________________________________________________________________________________________________________
364 //____________________________________________________________________________________________________________
366 Reference
< XControlModel
> SAL_CALL
StatusIndicator::getModel () throw( RuntimeException
)
369 // return (XControlModel*)this ;
370 return Reference
< XControlModel
> () ;
373 //____________________________________________________________________________________________________________
375 //____________________________________________________________________________________________________________
377 void SAL_CALL
StatusIndicator::dispose () throw( RuntimeException
)
379 // Ready for multithreading
380 MutexGuard
aGuard ( m_aMutex
) ;
382 // "removeControl()" control the state of a reference
383 Reference
< XControl
> xTextControl ( m_xText
, UNO_QUERY
);
384 Reference
< XControl
> xProgressControl ( m_xProgressBar
, UNO_QUERY
);
386 removeControl( xTextControl
);
387 removeControl( xProgressControl
);
389 // do'nt use "...->clear ()" or "... = XFixedText ()"
390 // when other hold a reference at this object !!!
391 xTextControl
->dispose();
392 xProgressControl
->dispose();
393 BaseContainerControl::dispose();
396 //____________________________________________________________________________________________________________
398 //____________________________________________________________________________________________________________
400 void SAL_CALL
StatusIndicator::setPosSize ( sal_Int32 nX
, sal_Int32 nY
, sal_Int32 nWidth
, sal_Int32 nHeight
, sal_Int16 nFlags
) throw( RuntimeException
)
402 Rectangle aBasePosSize
= getPosSize () ;
403 BaseContainerControl::setPosSize (nX
, nY
, nWidth
, nHeight
, nFlags
) ;
405 // if position or size changed
407 ( nWidth
!= aBasePosSize
.Width
) ||
408 ( nHeight
!= aBasePosSize
.Height
)
411 // calc new layout for controls
412 impl_recalcLayout ( WindowEvent(static_cast< OWeakObject
* >(this),0,0,nWidth
,nHeight
,0,0,0,0) ) ;
413 // clear background (!)
414 // [Childs was repainted in "recalcLayout" by setPosSize() automaticly!]
415 getPeer()->invalidate(2);
416 // and repaint the control
417 impl_paint ( 0, 0, impl_getGraphicsPeer() ) ;
421 //____________________________________________________________________________________________________________
422 // impl but public method to register service
423 //____________________________________________________________________________________________________________
425 const Sequence
< OUString
> StatusIndicator::impl_getStaticSupportedServiceNames()
427 MutexGuard
aGuard( Mutex::getGlobalMutex() );
428 Sequence
< OUString
> seqServiceNames( 1 );
429 seqServiceNames
.getArray() [0] = OUString::createFromAscii( SERVICENAME_STATUSINDICATOR
);
430 return seqServiceNames
;
433 //____________________________________________________________________________________________________________
434 // impl but public method to register service
435 //____________________________________________________________________________________________________________
437 const OUString
StatusIndicator::impl_getStaticImplementationName()
439 return OUString::createFromAscii( IMPLEMENTATIONNAME_STATUSINDICATOR
);
442 //____________________________________________________________________________________________________________
444 //____________________________________________________________________________________________________________
446 WindowDescriptor
* StatusIndicator::impl_getWindowDescriptor( const Reference
< XWindowPeer
>& xParentPeer
)
448 // - used from "createPeer()" to set the values of an ::com::sun::star::awt::WindowDescriptor !!!
449 // - if you will change the descriptor-values, you must override this virtuell function
450 // - the caller must release the memory for this dynamical descriptor !!!
452 WindowDescriptor
* pDescriptor
= new WindowDescriptor
;
454 pDescriptor
->Type
= WindowClass_SIMPLE
;
455 pDescriptor
->WindowServiceName
= OUString::createFromAscii( "floatingwindow" ) ;
456 pDescriptor
->ParentIndex
= -1 ;
457 pDescriptor
->Parent
= xParentPeer
;
458 pDescriptor
->Bounds
= getPosSize () ;
463 //____________________________________________________________________________________________________________
465 //____________________________________________________________________________________________________________
467 void StatusIndicator::impl_paint ( sal_Int32 nX
, sal_Int32 nY
, const Reference
< XGraphics
> & rGraphics
)
469 // This paint method ist not buffered !!
470 // Every request paint the completely control. ( but only, if peer exist )
471 if ( rGraphics
.is () )
473 MutexGuard
aGuard (m_aMutex
) ;
476 Reference
< XWindowPeer
> xPeer( impl_getPeerWindow(), UNO_QUERY
);
477 if( xPeer
.is() == sal_True
)
478 xPeer
->setBackground( BACKGROUNDCOLOR
);
480 // FixedText background = gray
481 Reference
< XControl
> xTextControl( m_xText
, UNO_QUERY
);
482 xPeer
= xTextControl
->getPeer();
483 if( xPeer
.is() == sal_True
)
484 xPeer
->setBackground( BACKGROUNDCOLOR
);
486 // Progress background = gray
487 xPeer
= Reference
< XWindowPeer
>( m_xProgressBar
, UNO_QUERY
);
488 if( xPeer
.is() == sal_True
)
489 xPeer
->setBackground( BACKGROUNDCOLOR
);
491 // paint shadow border
492 rGraphics
->setLineColor ( LINECOLOR_BRIGHT
);
493 rGraphics
->drawLine ( nX
, nY
, impl_getWidth(), nY
);
494 rGraphics
->drawLine ( nX
, nY
, nX
, impl_getHeight() );
496 rGraphics
->setLineColor ( LINECOLOR_SHADOW
);
497 rGraphics
->drawLine ( impl_getWidth()-1, impl_getHeight()-1, impl_getWidth()-1, nY
);
498 rGraphics
->drawLine ( impl_getWidth()-1, impl_getHeight()-1, nX
, impl_getHeight()-1 );
502 //____________________________________________________________________________________________________________
504 //____________________________________________________________________________________________________________
506 void StatusIndicator::impl_recalcLayout ( const WindowEvent
& aEvent
)
508 sal_Int32 nX_ProgressBar
;
509 sal_Int32 nY_ProgressBar
;
510 sal_Int32 nWidth_ProgressBar
;
511 sal_Int32 nHeight_ProgressBar
;
514 sal_Int32 nWidth_Text
;
515 sal_Int32 nHeight_Text
;
517 // Ready for multithreading
518 MutexGuard
aGuard ( m_aMutex
) ;
520 // get information about required place of child controls
521 Size
aWindowSize ( aEvent
.Width
, aEvent
.Height
);
522 Reference
< XLayoutConstrains
> xTextLayout ( m_xText
, UNO_QUERY
);
523 Size aTextSize
= xTextLayout
->getPreferredSize();
525 if( aWindowSize
.Width
< DEFAULT_WIDTH
)
527 aWindowSize
.Width
= DEFAULT_WIDTH
;
529 if( aWindowSize
.Height
< DEFAULT_HEIGHT
)
531 aWindowSize
.Height
= DEFAULT_HEIGHT
;
534 // calc position and size of child controls
535 nX_Text
= FREEBORDER
;
536 nY_Text
= FREEBORDER
;
537 nWidth_Text
= aTextSize
.Width
;
538 nHeight_Text
= aTextSize
.Height
;
540 nX_ProgressBar
= nX_Text
+nWidth_Text
+FREEBORDER
;
541 nY_ProgressBar
= nY_Text
;
542 nWidth_ProgressBar
= aWindowSize
.Width
-nWidth_Text
-(3*FREEBORDER
) ;
543 nHeight_ProgressBar
= nHeight_Text
;
545 // Set new position and size on all controls
546 Reference
< XWindow
> xTextWindow ( m_xText
, UNO_QUERY
);
547 Reference
< XWindow
> xProgressWindow ( m_xProgressBar
, UNO_QUERY
);
549 xTextWindow
->setPosSize ( nX_Text
, nY_Text
, nWidth_Text
, nHeight_Text
, 15 ) ;
550 xProgressWindow
->setPosSize ( nX_ProgressBar
, nY_ProgressBar
, nWidth_ProgressBar
, nHeight_ProgressBar
, 15 ) ;
553 //____________________________________________________________________________________________________________
555 //____________________________________________________________________________________________________________
557 #if OSL_DEBUG_LEVEL > 1
559 #endif // #if OSL_DEBUG_LEVEL > 1
561 } // namespace unocontrols