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 #ifndef SVX_SOURCE_INC_FMCONTROLBORDERMANAGER_HXX
29 #define SVX_SOURCE_INC_FMCONTROLBORDERMANAGER_HXX
30 
31 /** === begin UNO includes === **/
32 #include <com/sun/star/awt/VisualEffect.hpp>
33 #include <com/sun/star/awt/FontUnderline.hpp>
34 #include <com/sun/star/awt/XControl.hpp>
35 #include <com/sun/star/awt/XVclWindowPeer.hpp>
36 /** === end UNO includes === **/
37 #include <comphelper/stl_types.hxx>
38 #include <comphelper/stl_types.hxx>
39 
40 #include <set>
41 
42 namespace com { namespace sun { namespace star { namespace form { namespace validation {
43     class XValidatableFormComponent;
44 } } } } }
45 
46 //........................................................................
47 namespace svxform
48 {
49 //........................................................................
50 
51     typedef sal_Int16 ControlStatus;
52 
53     #define CONTROL_STATUS_NONE         0x00
54     #define CONTROL_STATUS_FOCUSED      0x01
55     #define CONTROL_STATUS_MOUSE_HOVER  0x02
56     #define CONTROL_STATUS_INVALID      0x04
57 
58     //====================================================================
59 	//= BorderDescriptor
60 	//====================================================================
61     struct BorderDescriptor
62     {
63         sal_Int16   nBorderType;
64         sal_Int32   nBorderColor;
65 
66         BorderDescriptor()
67             :nBorderType( ::com::sun::star::awt::VisualEffect::FLAT )
68             ,nBorderColor( 0x00000000 )
69         {
70         }
71 		inline void clear()
72 		{
73 			nBorderType = ::com::sun::star::awt::VisualEffect::FLAT;
74 			nBorderColor = 0x00000000;
75 		}
76     };
77 
78     //====================================================================
79 	//= UnderlineDescriptor
80 	//====================================================================
81     struct UnderlineDescriptor
82     {
83         sal_Int16 nUnderlineType;
84         sal_Int32 nUnderlineColor;
85 
86         UnderlineDescriptor()
87             :nUnderlineType( ::com::sun::star::awt::FontUnderline::NONE )
88             ,nUnderlineColor( 0x00000000 )
89         {
90         }
91 
92         UnderlineDescriptor( sal_Int16 _nUnderlineType, sal_Int32 _nUnderlineColor )
93             :nUnderlineType( _nUnderlineType )
94             ,nUnderlineColor( _nUnderlineColor )
95         {
96         }
97 
98 		inline void clear()
99 		{
100 			nUnderlineType = ::com::sun::star::awt::FontUnderline::NONE;
101 			nUnderlineColor = 0x00000000;
102 		}
103     };
104 
105     //====================================================================
106     //= ControlData
107     //====================================================================
108     struct ControlData : public BorderDescriptor, UnderlineDescriptor
109     {
110         ::com::sun::star::uno::Reference< ::com::sun::star::awt::XControl > xControl;
111         ::rtl::OUString                                                     sOriginalHelpText;
112 
113         ControlData() : BorderDescriptor() { }
114         ControlData( const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XControl >& _rxControl )
115             :xControl( _rxControl )
116         {
117         }
118 		void clear()
119 		{
120 			BorderDescriptor::clear();
121 			UnderlineDescriptor::clear();
122 			xControl.clear();
123 			sOriginalHelpText = ::rtl::OUString();
124 		}
125     };
126 
127     //====================================================================
128 	//= ControlBorderManager
129 	//====================================================================
130     /** manages the dynamic border color for form controls
131 
132         Used by the <type>FormController</type>, this class manages the dynamic changes in the
133         border color of form controls. For this a set of events have to be forwarded to the manager
134         instance, which then will switch the border color depending on the mouse and focus status
135         of the controls.
136     */
137 	class ControlBorderManager
138 	{
139     private:
140         struct ControlDataCompare : public ::std::binary_function< ControlData, ControlData, bool >
141         {
142            bool operator()( const ControlData& _rLHS, const ControlData& _rRHS ) const
143            {
144                return _rLHS.xControl.get() < _rRHS.xControl.get();
145            }
146         };
147 
148         typedef ::std::set< ControlData, ControlDataCompare > ControlBag;
149         typedef ::com::sun::star::awt::XVclWindowPeer                                       WindowPeer;
150         typedef ::com::sun::star::uno::Reference< ::com::sun::star::awt::XVclWindowPeer >   WindowPeerRef;
151         typedef ::std::set< WindowPeerRef, ::comphelper::OInterfaceCompare< WindowPeer > >  PeerBag;
152 
153         PeerBag     m_aColorableControls;
154         PeerBag     m_aNonColorableControls;
155 
156         ControlData m_aFocusControl;
157         ControlData m_aMouseHoverControl;
158         ControlBag  m_aInvalidControls;
159 
160         // ----------------
161         // attributes
162         sal_Int32   m_nFocusColor;
163         sal_Int32   m_nMouseHoveColor;
164         sal_Int32   m_nInvalidColor;
165         bool        m_bDynamicBorderColors;
166 
167     public:
168         ControlBorderManager();
169         ~ControlBorderManager();
170 
171     public:
172         void    focusGained( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface >& _rxControl ) SAL_THROW(());
173         void    focusLost( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface >& _rxControl ) SAL_THROW(());
174         void    mouseEntered( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface >& _rxControl ) SAL_THROW(());
175         void    mouseExited( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface >& _rxControl ) SAL_THROW(());
176 
177         void    validityChanged(
178                     const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XControl >& _rxControl,
179                     const ::com::sun::star::uno::Reference< ::com::sun::star::form::validation::XValidatableFormComponent >& _rxValidatable
180                 ) SAL_THROW(());
181 
182         /// enables dynamic border color for the controls
183         void    enableDynamicBorderColor( );
184         /// disables dynamic border color for the controls
185         void    disableDynamicBorderColor( );
186 
187         /** sets a color to be used for a given status
188             @param _nStatus
189                 the status which the color should be applied for. Must not be CONTROL_STATUS_NONE
190             @param _nColor
191                 the color to apply for the given status
192         */
193         void    setStatusColor( ControlStatus _nStatus, sal_Int32 _nColor );
194 
195         /** restores all colors of all controls where we possibly changed them
196         */
197         void    restoreAll();
198 
199     private:
200         /** called when a control got one of the two possible stati (focused, and hovered with the mouse)
201             @param _rxControl
202                 the control which gained the status
203             @param _rControlData
204                 the control's status data, as a reference to our respective member
205         */
206         void    controlStatusGained(
207                     const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface >& _rxControl,
208                     ControlData& _rControlData
209                 ) SAL_THROW(());
210 
211         /** called when a control lost one of the two possible stati (focused, and hovered with the mouse)
212             @param _rxControl
213                 the control which lost the status
214             @param _rControlData
215                 the control's status data, as a reference to our respective member
216         */
217         void    controlStatusLost( const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface >& _rxControl, ControlData& _rControlData ) SAL_THROW(());
218 
219         /** determines whether the border of a given peer can be colored
220             @param _rxPeer
221                 the peer to examine. Must not be <NULL/>
222         */
223         bool    canColorBorder( const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XVclWindowPeer >& _rxPeer );
224 
225         /** determines the status of the given control
226         */
227         ControlStatus   getControlStatus( const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XControl >& _rxControl ) SAL_THROW(());
228 
229         /** retrieves the color associated with a given ControlStatus
230             @param _eStatus
231                 the status of the control. Must not be <member>ControlStatus::none</member>
232         */
233         sal_Int32       getControlColorByStatus( ControlStatus _eStatus );
234 
235         /** sets the border color for a given control, depending on its status
236             @param _rxControl
237                 the control to set the border color for. Must not be <NULL/>
238             @param _rxPeer
239                 the peer of the control, to be passed herein for optimization the caller usually needs it, anyway).
240                 Must not be <NULL/>
241             @param _rFallback
242                 the color/type to use when the control has the status CONTROL_STATUS_NONE
243         */
244         void            updateBorderStyle(
245                             const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XControl >& _rxControl,
246                             const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XVclWindowPeer >& _rxPeer,
247                             const BorderDescriptor& _rFallback
248                         ) SAL_THROW(());
249 
250         /** determines the to-be-remembered original border color and type for a control
251 
252             The method also takes into account that the control may currently have an overwritten
253             border style
254 
255             @param _rxControl
256                 the control to examine. Must not be <NULL/>, and have a non-<NULL/> peer
257         */
258         void determineOriginalBorderStyle(
259                     const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XControl >& _rxControl,
260                     BorderDescriptor& _rData
261                 ) const;
262 	};
263 
264 //........................................................................
265 } // namespace svxform
266 //........................................................................
267 
268 #endif // SVX_SOURCE_INC_FMCONTROLBORDERMANAGER_HXX
269