Line data Source code
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 <roadmap.hxx>
21 :
22 : #include <vector>
23 : #include <algorithm>
24 : #include <vcl/bitmap.hxx>
25 : #include <vcl/settings.hxx>
26 : #include <tools/color.hxx>
27 : #include <rtl/ustring.hxx>
28 : #include <boost/scoped_ptr.hpp>
29 :
30 : #define ROADMAP_INDENT_X 4
31 : #define ROADMAP_INDENT_Y 27
32 : #define ROADMAP_ITEM_DISTANCE_Y 6
33 :
34 :
35 : namespace svt
36 : {
37 :
38 :
39 : typedef std::vector< RoadmapItem* > HL_Vector;
40 :
41 :
42 : //= ColorChanger
43 :
44 : class IDLabel : public FixedText
45 : {
46 : public:
47 : IDLabel( vcl::Window* _pParent, WinBits _nWinStyle = 0 );
48 : virtual ~IDLabel( );
49 : virtual void DataChanged( const DataChangedEvent& rDCEvt ) SAL_OVERRIDE;
50 : };
51 :
52 : class RoadmapItem : public RoadmapTypes
53 : {
54 : private:
55 : IDLabel* mpID;
56 : HyperLabel* mpDescription;
57 : const Size m_aItemPlayground;
58 :
59 : public:
60 : RoadmapItem( ORoadmap& _rParent, const Size& _rItemPlayground );
61 : ~RoadmapItem( );
62 :
63 : void SetID( sal_Int16 _ID );
64 : sal_Int16 GetID() const;
65 :
66 : void SetIndex( ItemIndex _Index );
67 : ItemIndex GetIndex() const;
68 :
69 : void Update( ItemIndex _RMIndex, const OUString& _rText );
70 :
71 : void SetPosition( RoadmapItem* OldHyperLabel );
72 :
73 : void ToggleBackgroundColor( const Color& _rGBColor );
74 : void SetInteractive( bool _bInteractive );
75 :
76 : void SetClickHdl( const Link& rLink );
77 : void Enable( bool bEnable = true);
78 : bool IsEnabled() const;
79 : void GrabFocus();
80 :
81 : bool Contains( const vcl::Window* _pWindow ) const;
82 :
83 0 : HyperLabel* GetDescriptionHyperLabel() const { return mpDescription; }
84 :
85 : private:
86 : void ImplUpdateIndex( const ItemIndex _nIndex );
87 : void ImplUpdatePosSize();
88 : };
89 :
90 :
91 : //= RoadmapImpl
92 :
93 0 : class RoadmapImpl : public RoadmapTypes
94 : {
95 : protected:
96 : const ORoadmap& m_rAntiImpl;
97 : Link m_aSelectHdl;
98 : BitmapEx m_aPicture;
99 : HL_Vector m_aRoadmapSteps;
100 : ItemId m_iCurItemID;
101 : bool m_bInteractive;
102 : bool m_bComplete;
103 : Size m_aItemSizePixel;
104 :
105 : public:
106 0 : RoadmapImpl( const ORoadmap& _rAntiImpl )
107 : :m_rAntiImpl( _rAntiImpl )
108 : ,m_iCurItemID( -1 )
109 : ,m_bInteractive( true )
110 : ,m_bComplete( true )
111 0 : ,InCompleteHyperLabel ( NULL )
112 : {
113 0 : }
114 :
115 : RoadmapItem* InCompleteHyperLabel;
116 :
117 0 : HL_Vector& getHyperLabels() { return m_aRoadmapSteps; }
118 :
119 0 : void insertHyperLabel( ItemIndex _Index, RoadmapItem* _rRoadmapStep ) { m_aRoadmapSteps.insert( m_aRoadmapSteps.begin() + _Index, _rRoadmapStep ); }
120 :
121 0 : ItemIndex getItemCount() const { return m_aRoadmapSteps.size();}
122 :
123 0 : void setCurItemID( ItemId i ) {m_iCurItemID = i; }
124 0 : ItemId getCurItemID() const { return m_iCurItemID; }
125 :
126 0 : void setInteractive(const bool _bInteractive) {m_bInteractive = _bInteractive; }
127 0 : bool isInteractive() const { return m_bInteractive; };
128 :
129 0 : void setComplete(const bool _bComplete) {m_bComplete = _bComplete; }
130 0 : bool isComplete() const { return m_bComplete; };
131 :
132 0 : void setPicture( const BitmapEx& _rPic ) { m_aPicture = _rPic; }
133 0 : const BitmapEx& getPicture( ) const { return m_aPicture; }
134 :
135 0 : void setSelectHdl( const Link& _rHdl ) { m_aSelectHdl = _rHdl; }
136 0 : const Link& getSelectHdl( ) const { return m_aSelectHdl; }
137 :
138 : void initItemSize();
139 0 : const Size& getItemSize() const { return m_aItemSizePixel; }
140 :
141 0 : void removeHyperLabel( ItemIndex _Index )
142 : {
143 0 : if ( ( _Index > -1 ) && ( _Index < getItemCount() ) )
144 : {
145 0 : delete m_aRoadmapSteps[_Index];
146 0 : m_aRoadmapSteps.erase( m_aRoadmapSteps.begin() + _Index);
147 : }
148 0 : }
149 : };
150 :
151 :
152 0 : void RoadmapImpl::initItemSize()
153 : {
154 0 : Size aLabelSize( m_rAntiImpl.GetOutputSizePixel() );
155 0 : aLabelSize.Height() = m_rAntiImpl.LogicToPixel( Size( 0, LABELBASEMAPHEIGHT ), MAP_APPFONT ).Height();
156 0 : aLabelSize.Width() -= m_rAntiImpl.LogicToPixel( Size( 2 * ROADMAP_INDENT_X, 0 ), MAP_APPFONT ).Width();
157 0 : m_aItemSizePixel = aLabelSize;
158 0 : }
159 :
160 :
161 : //= Roadmap
162 :
163 :
164 0 : ORoadmap::ORoadmap( vcl::Window* _pParent, WinBits _nWinStyle )
165 : :Control( _pParent, _nWinStyle )
166 0 : ,m_pImpl( new RoadmapImpl( *this ) )
167 :
168 : {
169 0 : implInit();
170 0 : }
171 :
172 :
173 0 : void ORoadmap::implInit()
174 : {
175 0 : const StyleSettings& rStyleSettings = GetSettings().GetStyleSettings();
176 0 : Color aTextColor = rStyleSettings.GetFieldTextColor();
177 0 : vcl::Font aFont = GetFont( );
178 0 : aFont.SetColor( aTextColor );
179 0 : aFont.SetWeight( WEIGHT_BOLD );
180 0 : aFont.SetUnderline( UNDERLINE_SINGLE );
181 0 : SetFont( aFont );
182 0 : SetBackground( Wallpaper( rStyleSettings.GetFieldColor() ) );
183 0 : m_pImpl->InCompleteHyperLabel = NULL;
184 0 : m_pImpl->setCurItemID(-1 );
185 0 : m_pImpl->setComplete( true );
186 :
187 : // Roadmap control should be reachable as one unit with a Tab key
188 : // the next Tab key should spring out of the control.
189 : // To reach it the control itself should get focus and set it
190 : // on entries. The entries themself should not be reachable with
191 : // the Tab key directly. So each entry should have WB_NOTABSTOP.
192 :
193 : // In other words the creator should create the control with the following
194 : // flags:
195 : // SetStyle( ( GetStyle() | WB_TABSTOP ) & ~WB_DIALOGCONTROL );
196 :
197 : // TODO: if somebody sets a new font from outside (OutputDevice::SetFont), we would have to react
198 : // on this with calculating a new bold font.
199 : // Unfortunately, the OutputDevice does not offer a notify mechanism for a changed font.
200 : // So settings the font from outside is simply a forbidded scenario at the moment
201 0 : EnableMapMode( false );
202 0 : }
203 :
204 :
205 0 : ORoadmap::~ORoadmap( )
206 : {
207 0 : HL_Vector aItemsCopy = m_pImpl->getHyperLabels();
208 0 : m_pImpl->getHyperLabels().clear();
209 0 : for ( HL_Vector::iterator i = aItemsCopy.begin(); i != aItemsCopy.end(); ++i )
210 : {
211 0 : delete *i;
212 : }
213 0 : if ( ! m_pImpl->isComplete() )
214 0 : delete m_pImpl->InCompleteHyperLabel;
215 0 : delete m_pImpl;
216 0 : m_pImpl = NULL;
217 0 : }
218 :
219 :
220 0 : RoadmapTypes::ItemId ORoadmap::GetCurrentRoadmapItemID() const
221 : {
222 0 : return m_pImpl->getCurItemID();
223 : }
224 :
225 :
226 0 : RoadmapItem* ORoadmap::GetPreviousHyperLabel( ItemIndex _Index)
227 : {
228 0 : RoadmapItem* pOldItem = NULL;
229 0 : if ( _Index > 0 )
230 0 : pOldItem = m_pImpl->getHyperLabels().at( _Index - 1 );
231 0 : return pOldItem;
232 : }
233 :
234 :
235 :
236 :
237 0 : RoadmapItem* ORoadmap::InsertHyperLabel( ItemIndex _Index, const OUString& _sLabel, ItemId _RMID, bool _bEnabled, bool _bIncomplete)
238 : {
239 0 : if ( m_pImpl->getItemCount() == 0 )
240 0 : m_pImpl->initItemSize();
241 :
242 0 : RoadmapItem* pItem = NULL;
243 0 : RoadmapItem* pOldItem = GetPreviousHyperLabel( _Index );
244 :
245 0 : pItem = new RoadmapItem( *this, m_pImpl->getItemSize() );
246 0 : if ( _bIncomplete )
247 : {
248 0 : pItem->SetInteractive( false );
249 : }
250 : else
251 : {
252 0 : pItem->SetInteractive( m_pImpl->isInteractive() );
253 0 : m_pImpl->insertHyperLabel( _Index, pItem );
254 : }
255 0 : pItem->SetPosition( pOldItem );
256 0 : pItem->Update( _Index, _sLabel );
257 0 : pItem->SetClickHdl(LINK( this, ORoadmap, ImplClickHdl ) );
258 0 : pItem->SetID( _RMID );
259 0 : pItem->SetIndex( _Index );
260 0 : if (!_bEnabled)
261 0 : pItem->Enable( _bEnabled );
262 0 : return pItem;
263 : }
264 :
265 :
266 0 : void ORoadmap::SetRoadmapBitmap( const BitmapEx& _rBmp, bool _bInvalidate )
267 : {
268 0 : m_pImpl->setPicture( _rBmp );
269 0 : if ( _bInvalidate )
270 0 : Invalidate( );
271 0 : }
272 :
273 :
274 0 : void ORoadmap::SetRoadmapInteractive( bool _bInteractive )
275 : {
276 0 : m_pImpl->setInteractive( _bInteractive );
277 :
278 0 : const HL_Vector& rItems = m_pImpl->getHyperLabels();
279 0 : for ( HL_Vector::const_iterator i = rItems.begin();
280 0 : i != rItems.end();
281 : ++i
282 : )
283 : {
284 0 : (*i)->SetInteractive( _bInteractive );
285 : }
286 0 : }
287 :
288 :
289 0 : bool ORoadmap::IsRoadmapInteractive()
290 : {
291 0 : return m_pImpl->isInteractive();
292 : }
293 :
294 :
295 0 : void ORoadmap::SetRoadmapComplete( bool _bComplete )
296 : {
297 0 : bool bWasComplete = m_pImpl->isComplete();
298 0 : m_pImpl->setComplete( _bComplete );
299 0 : if ( _bComplete )
300 : {
301 0 : if ( m_pImpl->InCompleteHyperLabel != NULL)
302 : {
303 0 : delete m_pImpl->InCompleteHyperLabel;
304 0 : m_pImpl->InCompleteHyperLabel = NULL;
305 : }
306 : }
307 0 : else if ( bWasComplete )
308 0 : m_pImpl->InCompleteHyperLabel = InsertHyperLabel( m_pImpl->getItemCount(), OUString("..."), -1, true/*bEnabled*/, true/*bIncomplete*/ );
309 0 : }
310 :
311 :
312 0 : void ORoadmap::UpdatefollowingHyperLabels( ItemIndex _nIndex )
313 : {
314 0 : const HL_Vector& rItems = m_pImpl->getHyperLabels();
315 0 : if ( _nIndex < (ItemIndex)rItems.size() )
316 : {
317 0 : RoadmapItem* pItem = NULL;
318 0 : for ( HL_Vector::const_iterator i = rItems.begin() + _nIndex;
319 0 : i != rItems.end();
320 : ++i, ++_nIndex
321 : )
322 : {
323 0 : pItem = *i;
324 :
325 0 : pItem->SetIndex( _nIndex );
326 0 : pItem->SetPosition( GetPreviousHyperLabel( _nIndex ) );
327 : }
328 : }
329 0 : if ( ! m_pImpl->isComplete() )
330 : {
331 0 : RoadmapItem* pOldItem = GetPreviousHyperLabel( m_pImpl->getItemCount() );
332 0 : m_pImpl->InCompleteHyperLabel->SetPosition( pOldItem );
333 0 : m_pImpl->InCompleteHyperLabel->Update( m_pImpl->getItemCount(), OUString("...") );
334 : }
335 0 : }
336 :
337 :
338 0 : void ORoadmap::ReplaceRoadmapItem( ItemIndex _Index, const OUString& _RoadmapItem, ItemId _RMID, bool _bEnabled )
339 : {
340 0 : RoadmapItem* pItem = GetByIndex( _Index);
341 0 : if ( pItem != NULL )
342 : {
343 0 : pItem->Update( _Index, _RoadmapItem );
344 0 : pItem->SetID( _RMID );
345 0 : pItem->Enable( _bEnabled );
346 : }
347 0 : }
348 :
349 :
350 0 : RoadmapTypes::ItemIndex ORoadmap::GetItemCount() const
351 : {
352 0 : return m_pImpl->getItemCount();
353 : }
354 :
355 :
356 0 : RoadmapTypes::ItemId ORoadmap::GetItemID( ItemIndex _nIndex ) const
357 : {
358 0 : const RoadmapItem* pHyperLabel = GetByIndex( _nIndex );
359 0 : if ( pHyperLabel )
360 0 : return pHyperLabel->GetID();
361 0 : return -1;
362 : }
363 :
364 :
365 0 : void ORoadmap::InsertRoadmapItem( ItemIndex _Index, const OUString& _RoadmapItem, ItemId _nUniqueId, bool _bEnabled )
366 : {
367 0 : InsertHyperLabel( _Index, _RoadmapItem, _nUniqueId, _bEnabled, false/*bIncomplete*/ );
368 : // TODO YPos is superfluous, if items are always appended
369 0 : UpdatefollowingHyperLabels( _Index + 1 );
370 0 : }
371 :
372 :
373 0 : void ORoadmap::DeleteRoadmapItem( ItemIndex _Index )
374 : {
375 0 : if ( m_pImpl->getItemCount() > 0 && ( _Index > -1) && ( _Index < m_pImpl->getItemCount() ) )
376 : {
377 0 : m_pImpl->removeHyperLabel( _Index );
378 0 : UpdatefollowingHyperLabels( _Index );
379 : }
380 0 : }
381 :
382 :
383 0 : bool ORoadmap::IsRoadmapComplete( ) const
384 : {
385 0 : return m_pImpl->isComplete();
386 : }
387 :
388 :
389 0 : void ORoadmap::EnableRoadmapItem( ItemId _nItemId, bool _bEnable, ItemIndex _nStartIndex )
390 : {
391 0 : RoadmapItem* pItem = GetByID( _nItemId, _nStartIndex );
392 0 : if ( pItem != NULL )
393 0 : pItem->Enable( _bEnable );
394 0 : }
395 :
396 :
397 0 : void ORoadmap::ChangeRoadmapItemLabel( ItemId _nID, const OUString& _sLabel, ItemIndex _nStartIndex )
398 : {
399 0 : RoadmapItem* pItem = GetByID( _nID, _nStartIndex );
400 0 : if ( pItem != NULL )
401 : {
402 0 : pItem->Update( pItem->GetIndex(), _sLabel );
403 :
404 0 : const HL_Vector& rItems = m_pImpl->getHyperLabels();
405 0 : for ( HL_Vector::const_iterator i = rItems.begin() + _nStartIndex;
406 0 : i != rItems.end();
407 : ++i
408 : )
409 : {
410 0 : (*i)->SetPosition( GetPreviousHyperLabel( i - rItems.begin() ) );
411 : }
412 : }
413 0 : }
414 :
415 :
416 0 : void ORoadmap::ChangeRoadmapItemID( ItemId _nID, ItemId _NewID, ItemIndex _nStartIndex )
417 : {
418 0 : RoadmapItem* pItem = GetByID( _nID, _nStartIndex );
419 0 : if ( pItem != NULL )
420 0 : pItem->SetID( _NewID );
421 0 : }
422 :
423 :
424 0 : RoadmapItem* ORoadmap::GetByID( ItemId _nID, ItemIndex _nStartIndex)
425 : {
426 0 : ItemId nLocID = 0;
427 0 : const HL_Vector& rItems = m_pImpl->getHyperLabels();
428 0 : for ( HL_Vector::const_iterator i = rItems.begin() + _nStartIndex;
429 0 : i != rItems.end();
430 : ++i
431 : )
432 : {
433 0 : nLocID = (*i)->GetID();
434 0 : if ( nLocID == _nID )
435 0 : return *i;
436 : }
437 0 : return NULL;
438 : }
439 :
440 :
441 0 : const RoadmapItem* ORoadmap::GetByID( ItemId _nID, ItemIndex _nStartIndex ) const
442 : {
443 0 : return const_cast< ORoadmap* >( this )->GetByID( _nID, _nStartIndex );
444 : }
445 :
446 :
447 0 : RoadmapItem* ORoadmap::GetByIndex( ItemIndex _nItemIndex)
448 : {
449 0 : const HL_Vector& rItems = m_pImpl->getHyperLabels();
450 0 : if ( ( _nItemIndex > -1 ) && ( _nItemIndex < (ItemIndex)rItems.size() ) )
451 : {
452 0 : return rItems.at( _nItemIndex );
453 : }
454 0 : return NULL;
455 : }
456 :
457 :
458 0 : const RoadmapItem* ORoadmap::GetByIndex( ItemIndex _nItemIndex ) const
459 : {
460 0 : return const_cast< ORoadmap* >( this )->GetByIndex( _nItemIndex );
461 : }
462 :
463 :
464 0 : RoadmapTypes::ItemId ORoadmap::GetNextAvailableItemId( ItemIndex _nNewIndex )
465 : {
466 0 : RoadmapItem* pItem = NULL;
467 :
468 0 : ItemIndex searchIndex = ++_nNewIndex;
469 0 : while ( searchIndex < m_pImpl->getItemCount() )
470 : {
471 0 : pItem = GetByIndex( searchIndex );
472 0 : if ( pItem->IsEnabled() )
473 0 : return pItem->GetID( );
474 :
475 0 : ++searchIndex;
476 : }
477 0 : return -1;
478 : }
479 :
480 :
481 0 : RoadmapTypes::ItemId ORoadmap::GetPreviousAvailableItemId( ItemIndex _nNewIndex )
482 : {
483 0 : RoadmapItem* pItem = NULL;
484 0 : ItemIndex searchIndex = --_nNewIndex;
485 0 : while ( searchIndex > -1 )
486 : {
487 0 : pItem = GetByIndex( searchIndex );
488 0 : if ( pItem->IsEnabled() )
489 0 : return pItem->GetID( );
490 :
491 0 : searchIndex--;
492 : }
493 0 : return -1;
494 : }
495 :
496 :
497 0 : void ORoadmap::DeselectOldRoadmapItems()
498 : {
499 0 : const HL_Vector& rItems = m_pImpl->getHyperLabels();
500 0 : for ( HL_Vector::const_iterator i = rItems.begin();
501 0 : i != rItems.end();
502 : ++i
503 : )
504 : {
505 0 : (*i)->ToggleBackgroundColor( COL_TRANSPARENT );
506 : }
507 0 : }
508 :
509 :
510 0 : void ORoadmap::SetItemSelectHdl( const Link& _rHdl )
511 : {
512 0 : m_pImpl->setSelectHdl( _rHdl );
513 0 : }
514 :
515 :
516 0 : Link ORoadmap::GetItemSelectHdl( ) const
517 : {
518 0 : return m_pImpl->getSelectHdl();
519 : }
520 :
521 :
522 0 : void ORoadmap::Select()
523 : {
524 0 : GetItemSelectHdl().Call( this );
525 0 : CallEventListeners( VCLEVENT_ROADMAP_ITEMSELECTED );
526 0 : }
527 :
528 :
529 0 : void ORoadmap::GetFocus()
530 : {
531 0 : RoadmapItem* pCurHyperLabel = GetByID( GetCurrentRoadmapItemID() );
532 0 : if ( pCurHyperLabel != NULL )
533 0 : pCurHyperLabel->GrabFocus();
534 0 : }
535 :
536 :
537 0 : bool ORoadmap::SelectRoadmapItemByID( ItemId _nNewID )
538 : {
539 0 : DeselectOldRoadmapItems();
540 0 : RoadmapItem* pItem = GetByID( _nNewID );
541 0 : if ( pItem != NULL )
542 : {
543 0 : if ( pItem->IsEnabled() )
544 : {
545 0 : const StyleSettings& rStyleSettings = GetSettings().GetStyleSettings();
546 0 : pItem->ToggleBackgroundColor( rStyleSettings.GetHighlightColor() ); //HighlightColor
547 :
548 0 : pItem->GrabFocus();
549 0 : m_pImpl->setCurItemID(_nNewID);
550 :
551 0 : Select();
552 0 : return true;
553 : }
554 : }
555 0 : return false;
556 : }
557 :
558 :
559 0 : void ORoadmap::Paint( const Rectangle& _rRect )
560 : {
561 0 : Control::Paint( _rRect );
562 :
563 :
564 : // draw the bitmap
565 0 : if ( !!m_pImpl->getPicture() )
566 : {
567 0 : Size aBitmapSize = m_pImpl->getPicture().GetSizePixel();
568 0 : Size aMySize = GetOutputSizePixel();
569 :
570 0 : Point aBitmapPos( aMySize.Width() - aBitmapSize.Width(), aMySize.Height() - aBitmapSize.Height() );
571 :
572 : // draw it
573 0 : DrawBitmapEx( aBitmapPos, m_pImpl->getPicture() );
574 : }
575 :
576 :
577 : // draw the headline
578 0 : DrawHeadline();
579 0 : }
580 :
581 :
582 0 : void ORoadmap::DrawHeadline()
583 : {
584 0 : Point aTextPos = LogicToPixel( Point( ROADMAP_INDENT_X, 8 ), MAP_APPFONT );
585 :
586 0 : Size aOutputSize( GetOutputSizePixel() );
587 :
588 : // draw it
589 0 : DrawText( Rectangle( aTextPos, aOutputSize ), GetText(), TEXT_DRAW_LEFT | TEXT_DRAW_TOP | TEXT_DRAW_MULTILINE | TEXT_DRAW_WORDBREAK );
590 0 : DrawTextLine( aTextPos, aOutputSize.Width(), STRIKEOUT_NONE, UNDERLINE_SINGLE, UNDERLINE_NONE, false );
591 0 : const StyleSettings& rStyleSettings = GetSettings().GetStyleSettings();
592 0 : SetLineColor( rStyleSettings.GetFieldTextColor());
593 0 : SetTextColor(rStyleSettings.GetFieldTextColor());
594 0 : }
595 :
596 :
597 0 : RoadmapItem* ORoadmap::GetByPointer(vcl::Window* pWindow)
598 : {
599 0 : const HL_Vector& rItems = m_pImpl->getHyperLabels();
600 0 : for ( HL_Vector::const_iterator i = rItems.begin();
601 0 : i != rItems.end();
602 : ++i
603 : )
604 : {
605 0 : if ( (*i)->Contains( pWindow ) )
606 0 : return *i;
607 : }
608 0 : return NULL;
609 : }
610 :
611 :
612 0 : bool ORoadmap::PreNotify( NotifyEvent& _rNEvt )
613 : {
614 : // capture KeyEvents for taskpane cycling
615 0 : if ( _rNEvt.GetType() == EVENT_KEYINPUT )
616 : {
617 0 : vcl::Window* pWindow = _rNEvt.GetWindow();
618 0 : RoadmapItem* pItem = GetByPointer( pWindow );
619 0 : if ( pItem != NULL )
620 : {
621 0 : sal_Int16 nKeyCode = _rNEvt.GetKeyEvent()->GetKeyCode().GetCode();
622 0 : switch( nKeyCode )
623 : {
624 : case KEY_UP:
625 : { // Note: Performancewise this is not optimal, because we search for an ID in the labels
626 : // and afterwards we search again for a label with the appropriate ID ->
627 : // unnecessarily we search twice!!!
628 0 : ItemId nPrevItemID = GetPreviousAvailableItemId( pItem->GetIndex() );
629 0 : if ( nPrevItemID != -1 )
630 0 : return SelectRoadmapItemByID( nPrevItemID );
631 : }
632 0 : break;
633 : case KEY_DOWN:
634 : {
635 0 : ItemId nNextItemID = GetNextAvailableItemId( pItem->GetIndex() );
636 0 : if ( nNextItemID != -1 )
637 0 : return SelectRoadmapItemByID( nNextItemID );
638 : }
639 0 : break;
640 : case KEY_SPACE:
641 0 : return SelectRoadmapItemByID( pItem->GetID() );
642 : }
643 : }
644 : }
645 0 : return Window::PreNotify( _rNEvt );
646 : }
647 :
648 :
649 0 : IMPL_LINK(ORoadmap, ImplClickHdl, HyperLabel*, _CurHyperLabel)
650 : {
651 0 : return SelectRoadmapItemByID( _CurHyperLabel->GetID() ) ? 1 : 0;
652 : }
653 :
654 :
655 :
656 :
657 0 : void ORoadmap::DataChanged( const DataChangedEvent& rDCEvt )
658 : {
659 0 : if ((( rDCEvt.GetType() == DATACHANGED_SETTINGS ) ||
660 0 : ( rDCEvt.GetType() == DATACHANGED_DISPLAY )) &&
661 0 : ( rDCEvt.GetFlags() & SETTINGS_STYLE ))
662 : {
663 0 : const StyleSettings& rStyleSettings = GetSettings().GetStyleSettings();
664 0 : SetBackground( Wallpaper( rStyleSettings.GetFieldColor() ) );
665 0 : Color aTextColor = rStyleSettings.GetFieldTextColor();
666 0 : vcl::Font aFont = GetFont();
667 0 : aFont.SetColor( aTextColor );
668 0 : SetFont( aFont );
669 0 : RoadmapTypes::ItemId curItemID = GetCurrentRoadmapItemID();
670 0 : RoadmapItem* pLabelItem = GetByID( curItemID );
671 0 : if (pLabelItem != NULL)
672 : {
673 0 : pLabelItem->ToggleBackgroundColor(rStyleSettings.GetHighlightColor());
674 : }
675 0 : Invalidate();
676 : }
677 0 : }
678 :
679 :
680 :
681 0 : RoadmapItem::RoadmapItem( ORoadmap& _rParent, const Size& _rItemPlayground )
682 0 : :m_aItemPlayground( _rItemPlayground )
683 : {
684 0 : mpID = new IDLabel( &_rParent, WB_WORDBREAK );
685 0 : mpID->SetTextColor( mpID->GetSettings().GetStyleSettings().GetFieldTextColor( ) );
686 0 : mpID->Show();
687 0 : mpDescription = new HyperLabel( &_rParent, WB_NOTABSTOP | WB_WORDBREAK );
688 0 : mpDescription->Show();
689 0 : }
690 :
691 :
692 0 : bool RoadmapItem::Contains( const vcl::Window* _pWindow ) const
693 : {
694 0 : return ( mpID == _pWindow ) || ( mpDescription == _pWindow );
695 : }
696 :
697 :
698 0 : void RoadmapItem::GrabFocus()
699 : {
700 0 : if ( mpDescription )
701 0 : mpDescription->GrabFocus();
702 0 : }
703 :
704 :
705 0 : void RoadmapItem::SetInteractive( bool _bInteractive )
706 : {
707 0 : if ( mpDescription )
708 0 : mpDescription->SetInteractive(_bInteractive);
709 0 : }
710 :
711 :
712 0 : void RoadmapItem::SetID( sal_Int16 _ID )
713 : {
714 0 : if ( mpDescription )
715 0 : mpDescription->SetID(_ID);
716 0 : }
717 :
718 :
719 0 : sal_Int16 RoadmapItem::GetID() const
720 : {
721 0 : return mpDescription ? mpDescription->GetID() : sal_Int16(-1);
722 : }
723 :
724 :
725 0 : void RoadmapItem::ImplUpdateIndex( const ItemIndex _nIndex )
726 : {
727 0 : mpDescription->SetIndex( _nIndex );
728 :
729 0 : OUString aIDText = OUString::number( _nIndex + 1 ) + ".";
730 0 : mpID->SetText( aIDText );
731 :
732 : // update the geometry of both controls
733 0 : ImplUpdatePosSize();
734 0 : }
735 :
736 :
737 0 : void RoadmapItem::SetIndex( ItemIndex _Index )
738 : {
739 0 : ImplUpdateIndex( _Index );
740 0 : }
741 :
742 :
743 0 : RoadmapTypes::ItemIndex RoadmapItem::GetIndex() const
744 : {
745 0 : return mpDescription ? mpDescription->GetIndex() : ItemIndex(-1);
746 : }
747 :
748 :
749 0 : void RoadmapItem::SetPosition( RoadmapItem* _pOldItem )
750 : {
751 0 : Point aIDPos;
752 0 : if ( _pOldItem == NULL )
753 : {
754 0 : aIDPos = mpID->LogicToPixel( Point( ROADMAP_INDENT_X, ROADMAP_INDENT_Y ), MAP_APPFONT );
755 : }
756 : else
757 : {
758 0 : Size aOldSize = _pOldItem->GetDescriptionHyperLabel()->GetSizePixel();
759 :
760 0 : aIDPos = _pOldItem->mpID->GetPosPixel();
761 0 : aIDPos.Y() += aOldSize.Height();
762 0 : aIDPos.Y() += mpID->GetParent()->LogicToPixel( Size( 0, ROADMAP_ITEM_DISTANCE_Y ) ).Height();
763 : }
764 0 : mpID->SetPosPixel( aIDPos );
765 :
766 0 : sal_Int32 nDescPos = aIDPos.X() + mpID->GetSizePixel().Width();
767 0 : mpDescription->SetPosPixel( Point( nDescPos, aIDPos.Y() ) );
768 0 : }
769 :
770 :
771 0 : void RoadmapItem::Enable( bool _bEnable)
772 : {
773 0 : mpID->Enable(_bEnable);
774 0 : mpDescription->Enable(_bEnable);
775 0 : }
776 :
777 :
778 0 : bool RoadmapItem::IsEnabled() const
779 : {
780 0 : return mpID->IsEnabled();
781 : }
782 :
783 :
784 0 : void RoadmapItem::ToggleBackgroundColor( const Color& _rGBColor )
785 : {
786 0 : if (_rGBColor == COL_TRANSPARENT)
787 : {
788 0 : mpID->SetTextColor( mpID->GetSettings().GetStyleSettings().GetFieldTextColor( ) );
789 0 : mpID->SetControlBackground( COL_TRANSPARENT );
790 : }
791 : else
792 : {
793 0 : mpID->SetControlBackground( mpID->GetSettings().GetStyleSettings().GetHighlightColor() );
794 0 : mpID->SetTextColor( mpID->GetSettings().GetStyleSettings().GetHighlightTextColor( ) );
795 : }
796 0 : mpDescription->ToggleBackgroundColor(_rGBColor);
797 0 : }
798 :
799 :
800 0 : void RoadmapItem::ImplUpdatePosSize()
801 : {
802 : // calculate widths
803 0 : long nIDWidth = mpID->GetTextWidth( mpID->GetText() );
804 0 : long nMaxIDWidth = mpID->GetTextWidth( OUString( "100." ) );
805 0 : nIDWidth = ::std::min( nIDWidth, nMaxIDWidth );
806 :
807 : // check how many space the description would need
808 0 : Size aDescriptionSize = mpDescription->CalcMinimumSize( m_aItemPlayground.Width() - nIDWidth );
809 :
810 : // position and size both controls
811 0 : Size aIDSize( nIDWidth, aDescriptionSize.Height() );
812 0 : mpID->SetSizePixel( aIDSize );
813 :
814 0 : Point aIDPos = mpID->GetPosPixel();
815 0 : mpDescription->SetPosPixel( Point( aIDPos.X() + nIDWidth, aIDPos.Y() ) );
816 0 : mpDescription->SetSizePixel( aDescriptionSize );
817 0 : }
818 :
819 :
820 0 : void RoadmapItem::Update( ItemIndex _RMIndex, const OUString& _rText )
821 : {
822 : // update description label
823 0 : mpDescription->SetLabel( _rText );
824 :
825 : // update the index in both controls, which triggers updating the geometry of both
826 0 : ImplUpdateIndex( _RMIndex );
827 0 : }
828 :
829 :
830 0 : RoadmapItem::~RoadmapItem( )
831 : {
832 : {
833 0 : boost::scoped_ptr<Control> xTakeOnership(mpID);
834 0 : mpID = NULL;
835 : }
836 : {
837 0 : boost::scoped_ptr<Control> xTakeOnership(mpDescription);
838 0 : mpDescription = NULL;
839 : }
840 0 : }
841 :
842 :
843 0 : void RoadmapItem::SetClickHdl( const Link& rLink )
844 : {
845 0 : if ( mpDescription )
846 0 : mpDescription->SetClickHdl( rLink);
847 0 : }
848 :
849 :
850 0 : IDLabel::IDLabel( vcl::Window* _pParent, WinBits _nWinStyle )
851 0 : :FixedText( _pParent, _nWinStyle )
852 : {
853 :
854 0 : }
855 :
856 :
857 0 : IDLabel::~IDLabel( )
858 : {
859 0 : }
860 :
861 :
862 0 : void IDLabel::DataChanged( const DataChangedEvent& rDCEvt )
863 : {
864 0 : const StyleSettings& rStyleSettings = GetSettings().GetStyleSettings();
865 0 : FixedText::DataChanged( rDCEvt );
866 0 : if ((( rDCEvt.GetType() == DATACHANGED_SETTINGS ) ||
867 0 : ( rDCEvt.GetType() == DATACHANGED_DISPLAY )) &&
868 0 : ( rDCEvt.GetFlags() & SETTINGS_STYLE ))
869 : {
870 0 : const Color& rGBColor = GetControlBackground();
871 0 : if (rGBColor == COL_TRANSPARENT)
872 0 : SetTextColor( rStyleSettings.GetFieldTextColor( ) );
873 : else
874 : {
875 0 : SetControlBackground(rStyleSettings.GetHighlightColor());
876 0 : SetTextColor( rStyleSettings.GetHighlightTextColor( ) );
877 : }
878 0 : Invalidate();
879 : }
880 0 : }
881 :
882 :
883 :
884 :
885 :
886 1227 : } // namespace svt
887 :
888 :
889 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|