1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 #include "precompiled_svtools.hxx"
25 
26 #include "toolpaneldrawer.hxx"
27 #include "toolpaneldrawerpeer.hxx"
28 #include "svtools/svtdata.hxx"
29 #include "svtools/svtools.hrc"
30 
31 #include <com/sun/star/accessibility/AccessibleRole.hpp>
32 
33 #include <vcl/lineinfo.hxx>
34 #include <vcl/image.hxx>
35 #include <vcl/svapp.hxx>
36 #include <vcl/vclevent.hxx>
37 
38 //......................................................................................................................
39 namespace svt
40 {
41 //......................................................................................................................
42 
43     using ::com::sun::star::uno::Reference;
44     using ::com::sun::star::awt::XWindowPeer;
45     namespace AccessibleRole = ::com::sun::star::accessibility::AccessibleRole;
46 
47     static const int s_nIndentationWidth = 16;
48 
49 	//==================================================================================================================
50 	//= DrawerVisualization
51 	//==================================================================================================================
52 	//------------------------------------------------------------------------------------------------------------------
DrawerVisualization(ToolPanelDrawer & i_rParent)53     DrawerVisualization::DrawerVisualization( ToolPanelDrawer& i_rParent )
54         :Window( &i_rParent )
55         ,m_rDrawer( i_rParent )
56     {
57         SetMouseTransparent( sal_True );
58         Show();
59         SetAccessibleRole( AccessibleRole::LABEL );
60     }
61 
62 	//------------------------------------------------------------------------------------------------------------------
~DrawerVisualization()63     DrawerVisualization::~DrawerVisualization()
64     {
65     }
66 
67 	//------------------------------------------------------------------------------------------------------------------
Paint(const Rectangle & i_rBoundingBox)68     void DrawerVisualization::Paint( const Rectangle& i_rBoundingBox )
69     {
70         Window::Paint( i_rBoundingBox );
71         m_rDrawer.Paint();
72     }
73 
74 	//==================================================================================================================
75 	//= ToolPanelDrawer
76 	//==================================================================================================================
77 	//------------------------------------------------------------------------------------------------------------------
ToolPanelDrawer(Window & i_rParent,const::rtl::OUString & i_rTitle)78     ToolPanelDrawer::ToolPanelDrawer( Window& i_rParent, const ::rtl::OUString& i_rTitle )
79         :Window( &i_rParent, WB_TABSTOP )
80         ,m_pPaintDevice( new VirtualDevice( *this ) )
81         ,m_aVisualization( *this )
82         ,m_bFocused( false )
83         ,m_bExpanded( false )
84     {
85         EnableMapMode( sal_False );
86         SetBackground( Wallpaper() );
87         SetPointer( POINTER_REFHAND );
88 
89         SetAccessibleRole( AccessibleRole::LIST_ITEM );
90 
91         SetText( i_rTitle );
92         SetAccessibleName( i_rTitle );
93         SetAccessibleDescription( i_rTitle );
94 
95         m_aVisualization.SetAccessibleName( i_rTitle );
96         m_aVisualization.SetAccessibleDescription( i_rTitle );
97     }
98 
99 	//------------------------------------------------------------------------------------------------------------------
~ToolPanelDrawer()100     ToolPanelDrawer::~ToolPanelDrawer()
101     {
102     }
103 
104 	//------------------------------------------------------------------------------------------------------------------
GetPreferredHeightPixel() const105     long ToolPanelDrawer::GetPreferredHeightPixel() const
106     {
107         Rectangle aTitleBarBox( impl_calcTitleBarBox( impl_calcTextBoundingBox() ) );
108         return aTitleBarBox.GetHeight();
109     }
110 
111 	//------------------------------------------------------------------------------------------------------------------
Paint()112     void ToolPanelDrawer::Paint()
113     {
114         m_pPaintDevice->SetMapMode( GetMapMode() );
115         m_pPaintDevice->SetOutputSize( GetOutputSizePixel() );
116         m_pPaintDevice->SetSettings( GetSettings() );
117         m_pPaintDevice->SetDrawMode( GetDrawMode() );
118 
119         const Rectangle aTextBox( impl_calcTextBoundingBox() );
120         impl_paintBackground( impl_calcTitleBarBox( aTextBox ) );
121 
122         Rectangle aFocusBox( impl_paintExpansionIndicator( aTextBox ) );
123 
124         m_pPaintDevice->DrawText( aTextBox, GetText(), impl_getTextStyle() );
125 
126         aFocusBox.Union( aTextBox );
127         aFocusBox.Left() += 2;
128         impl_paintFocusIndicator( aFocusBox );
129 
130         m_aVisualization.DrawOutDev(
131             Point(), GetOutputSizePixel(),
132             Point(), GetOutputSizePixel(),
133             *m_pPaintDevice
134         );
135     }
136 
137     //------------------------------------------------------------------------------------------------------------------
impl_paintExpansionIndicator(const Rectangle & i_rTextBox)138     Rectangle ToolPanelDrawer::impl_paintExpansionIndicator( const Rectangle& i_rTextBox )
139     {
140         Rectangle aExpansionIndicatorArea;
141 
142         Image aImage( impl_getExpansionIndicator() );
143         const int nHeight( aImage.GetSizePixel().Height() );
144         if ( nHeight > 0 )
145         {
146             Point aPosition(
147                 0,
148                 i_rTextBox.Top() + ( GetTextHeight() - nHeight ) / 2
149             );
150             m_pPaintDevice->DrawImage( aPosition, aImage );
151 
152             aExpansionIndicatorArea = Rectangle( aPosition, aImage.GetSizePixel() );
153         }
154 
155         return aExpansionIndicatorArea;
156     }
157 
158     //------------------------------------------------------------------------------------------------------------------
impl_getExpansionIndicator() const159     Image ToolPanelDrawer::impl_getExpansionIndicator() const
160     {
161         const bool bHighContrastMode( GetSettings().GetStyleSettings().GetHighContrastMode() != 0 );
162         sal_uInt16 nResourceId = 0;
163         if ( m_bExpanded )
164             if ( bHighContrastMode )
165                 nResourceId = IMG_TRIANGLE_DOWN_HC;
166             else
167                 nResourceId = IMG_TRIANGLE_DOWN;
168         else
169             if ( bHighContrastMode )
170                 nResourceId = IMG_TRIANGLE_RIGHT_HC;
171             else
172                 nResourceId = IMG_TRIANGLE_RIGHT;
173         return Image( SvtResId( nResourceId ) );
174     }
175 
176     //------------------------------------------------------------------------------------------------------------------
impl_getTextStyle() const177     sal_uInt16 ToolPanelDrawer::impl_getTextStyle() const
178     {
179         const sal_uInt16 nBasicStyle =  TEXT_DRAW_LEFT
180                                 |   TEXT_DRAW_TOP
181                                 |   TEXT_DRAW_WORDBREAK;
182 
183         if ( IsEnabled() )
184             return nBasicStyle;
185 
186         return nBasicStyle | TEXT_DRAW_DISABLE;
187     }
188 
189     //------------------------------------------------------------------------------------------------------------------
impl_paintBackground(const Rectangle & i_rTitleBarBox)190     void ToolPanelDrawer::impl_paintBackground( const Rectangle& i_rTitleBarBox )
191     {
192         m_pPaintDevice->SetFillColor( GetSettings().GetStyleSettings().GetDialogColor() );
193         m_pPaintDevice->DrawRect( i_rTitleBarBox );
194 
195         m_pPaintDevice->SetFillColor();
196         m_pPaintDevice->SetLineColor( GetSettings().GetStyleSettings().GetLightColor() );
197         m_pPaintDevice->DrawLine( i_rTitleBarBox.TopLeft(), i_rTitleBarBox.TopRight() );
198         m_pPaintDevice->DrawLine( i_rTitleBarBox.TopLeft(), i_rTitleBarBox.BottomLeft() );
199 
200         m_pPaintDevice->SetLineColor( GetSettings().GetStyleSettings().GetShadowColor() );
201         m_pPaintDevice->DrawLine( i_rTitleBarBox.BottomLeft(), i_rTitleBarBox.BottomRight() );
202         m_pPaintDevice->DrawLine( i_rTitleBarBox.TopRight(), i_rTitleBarBox.BottomRight() );
203     }
204 
205     //------------------------------------------------------------------------------------------------------------------
impl_paintFocusIndicator(const Rectangle & i_rTextBox)206     void ToolPanelDrawer::impl_paintFocusIndicator( const Rectangle& i_rTextBox )
207     {
208         if ( m_bFocused )
209         {
210             const Rectangle aTextPixelBox( m_pPaintDevice->LogicToPixel( i_rTextBox ) );
211 
212             m_pPaintDevice->EnableMapMode( sal_False );
213             m_pPaintDevice->SetFillColor();
214 
215             Rectangle aBox( i_rTextBox );
216             aBox.Top() -= 1;
217             aBox.Bottom() += 1;
218 
219             m_pPaintDevice->DrawRect( aTextPixelBox );
220 
221             LineInfo aDottedStyle( LINE_DASH );
222             aDottedStyle.SetDashCount( 0 );
223             aDottedStyle.SetDotCount( 1 );
224             aDottedStyle.SetDotLen( 1 );
225             aDottedStyle.SetDistance( 1 );
226 
227             m_pPaintDevice->SetLineColor( COL_BLACK );
228             m_pPaintDevice->DrawPolyLine( Polygon( aTextPixelBox ), aDottedStyle );
229             m_pPaintDevice->EnableMapMode( sal_False );
230         }
231         else
232             HideFocus();
233     }
234 
235     //------------------------------------------------------------------------------------------------------------------
GetFocus()236     void ToolPanelDrawer::GetFocus()
237     {
238         m_bFocused = true;
239         Invalidate();
240     }
241 
242     //------------------------------------------------------------------------------------------------------------------
LoseFocus()243     void ToolPanelDrawer::LoseFocus()
244     {
245         m_bFocused = false;
246         Invalidate();
247     }
248 
249     //------------------------------------------------------------------------------------------------------------------
Resize()250     void ToolPanelDrawer::Resize()
251     {
252         Window::Resize();
253         m_aVisualization.SetPosSizePixel( Point(), GetOutputSizePixel() );
254     }
255 
256     //------------------------------------------------------------------------------------------------------------------
MouseButtonDown(const MouseEvent & i_rMouseEvent)257     void ToolPanelDrawer::MouseButtonDown( const MouseEvent& i_rMouseEvent )
258     {
259         // consume this event, and do not forward to the base class - it would sent a NotifyEvent, which in turn, when
260         // we live in a DockingWindow, would start undocking
261         (void)i_rMouseEvent;
262     }
263 
264     //------------------------------------------------------------------------------------------------------------------
DataChanged(const DataChangedEvent & i_rEvent)265     void ToolPanelDrawer::DataChanged( const DataChangedEvent& i_rEvent )
266     {
267         Window::DataChanged( i_rEvent );
268 
269         switch ( i_rEvent.GetType() )
270         {
271             case DATACHANGED_SETTINGS:
272                 if ( ( i_rEvent.GetFlags() & SETTINGS_STYLE ) == 0 )
273                     break;
274                 SetSettings( Application::GetSettings() );
275                 m_pPaintDevice.reset( new VirtualDevice( *this ) );
276 
277                 // fall through.
278 
279             case DATACHANGED_FONTS:
280             case DATACHANGED_FONTSUBSTITUTION:
281             {
282                 const StyleSettings& rStyleSettings( GetSettings().GetStyleSettings() );
283 
284                 // Font.
285                 Font aFont = rStyleSettings.GetAppFont();
286                 if ( IsControlFont() )
287                     aFont.Merge( GetControlFont() );
288                 SetZoomedPointFont( aFont );
289 
290                 // Color.
291                 Color aColor;
292                 if ( IsControlForeground() )
293                     aColor = GetControlForeground();
294                 else
295                     aColor = rStyleSettings.GetButtonTextColor();
296                 SetTextColor( aColor );
297                 SetTextFillColor();
298 
299                 Invalidate();
300             }
301             break;
302         }
303     }
304 
305     //------------------------------------------------------------------------------------------------------------------
GetComponentInterface(sal_Bool i_bCreate)306     Reference< XWindowPeer > ToolPanelDrawer::GetComponentInterface( sal_Bool i_bCreate )
307     {
308         Reference< XWindowPeer > xWindowPeer( Window::GetComponentInterface( sal_False ) );
309         if ( !xWindowPeer.is() && i_bCreate )
310         {
311             xWindowPeer.set( new ToolPanelDrawerPeer() );
312             SetComponentInterface( xWindowPeer );
313         }
314         return xWindowPeer;
315     }
316 
317     //------------------------------------------------------------------------------------------------------------------
impl_calcTextBoundingBox() const318     Rectangle ToolPanelDrawer::impl_calcTextBoundingBox() const
319     {
320         Font aFont( GetFont() );
321         if ( m_bExpanded )
322             aFont.SetWeight( m_bExpanded ? WEIGHT_BOLD : WEIGHT_NORMAL );
323         m_pPaintDevice->SetFont( aFont );
324 
325         int nAvailableWidth = m_pPaintDevice->GetTextWidth( GetText() );
326 
327         Rectangle aTextBox(
328             Point(),
329             Size(
330                 nAvailableWidth,
331                 GetSettings().GetStyleSettings().GetTitleHeight()
332             )
333         );
334         aTextBox.Top() += ( aTextBox.GetHeight() - GetTextHeight() ) / 2;
335         aTextBox.Left() += s_nIndentationWidth;
336         aTextBox.Right() -= 1;
337 
338         aTextBox = m_pPaintDevice->GetTextRect( aTextBox, GetText(), impl_getTextStyle() );
339         return aTextBox;
340     }
341 
342     //------------------------------------------------------------------------------------------------------------------
impl_calcTitleBarBox(const Rectangle & i_rTextBox) const343     Rectangle ToolPanelDrawer::impl_calcTitleBarBox( const Rectangle& i_rTextBox ) const
344     {
345         Rectangle aTitleBarBox( i_rTextBox );
346         aTitleBarBox.Bottom() += aTitleBarBox.Top();
347         aTitleBarBox.Top() = 0;
348         aTitleBarBox.Left() = 0;
349 
350         const long nWidth = GetOutputSizePixel().Width();
351         if ( aTitleBarBox.GetWidth() < nWidth )
352             aTitleBarBox.Right() = nWidth - 1;
353 
354         return aTitleBarBox;
355     }
356 
357     //------------------------------------------------------------------------------------------------------------------
SetExpanded(const bool i_bExpanded)358     void ToolPanelDrawer::SetExpanded( const bool i_bExpanded )
359     {
360         if ( m_bExpanded != i_bExpanded )
361         {
362             m_bExpanded = i_bExpanded;
363             CallEventListeners( m_bExpanded ? VCLEVENT_ITEM_EXPANDED : VCLEVENT_ITEM_COLLAPSED );
364             Invalidate();
365         }
366     }
367 
368 //......................................................................................................................
369 } // namespace svt
370 //......................................................................................................................
371