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: ObjectHierarchy.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 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_chart2.hxx"
34 #include "ObjectHierarchy.hxx"
35 #include "ObjectIdentifier.hxx"
36 #include "ChartModelHelper.hxx"
37 #include "DiagramHelper.hxx"
38 #include "RegressionCurveHelper.hxx"
39 #include "AxisHelper.hxx"
40 #include "chartview/ExplicitValueProvider.hxx"
42 #include "LineProperties.hxx"
43 #include "ChartTypeHelper.hxx"
48 #include <com/sun/star/chart2/XTitled.hpp>
49 #include <com/sun/star/chart2/XCoordinateSystemContainer.hpp>
50 #include <com/sun/star/chart2/XChartTypeContainer.hpp>
51 #include <com/sun/star/chart2/XDataSeriesContainer.hpp>
52 #include <com/sun/star/chart/ErrorBarStyle.hpp>
54 #include <com/sun/star/container/XIndexAccess.hpp>
55 #include <com/sun/star/awt/Key.hpp>
56 #include <com/sun/star/awt/KeyModifier.hpp>
58 using namespace ::com::sun::star
;
59 using namespace ::com::sun::star::chart2
;
61 using ::com::sun::star::uno::Reference
;
62 using ::com::sun::star::uno::Sequence
;
63 using ::rtl::OUString
;
67 struct lcl_ObjectToCID
: public ::std::unary_function
< Reference
< uno::XInterface
>, OUString
>
69 explicit lcl_ObjectToCID( const Reference
< chart2::XChartDocument
> & xChartDoc
) :
70 m_xModel( xChartDoc
, uno::UNO_QUERY
)
73 OUString
operator() ( const Reference
< uno::XInterface
> & xObj
)
75 return ::chart::ObjectIdentifier::createClassifiedIdentifierForObject( xObj
, m_xModel
);
79 Reference
< frame::XModel
> m_xModel
;
82 void lcl_getChildCIDs(
83 ::chart::ObjectHierarchy::tChildContainer
& rOutChildren
,
84 const Reference
< container::XIndexAccess
> & xShapes
)
88 sal_Int32 nCount
= xShapes
->getCount();
89 for( sal_Int32 i
=0; i
<nCount
; ++i
)
91 Reference
< beans::XPropertySet
> xShapeProp( xShapes
->getByIndex( i
), uno::UNO_QUERY
);
94 Reference
< beans::XPropertySetInfo
> xInfo( xShapeProp
->getPropertySetInfo());
97 xInfo
->hasPropertyByName( C2U("Name")) &&
98 (xShapeProp
->getPropertyValue( C2U("Name")) >>= aName
) &&
99 aName
.getLength() > 0 &&
100 ::chart::ObjectIdentifier::isCID( aName
))
102 rOutChildren
.push_back( aName
);
104 Reference
< container::XIndexAccess
> xNewShapes( xShapeProp
, uno::UNO_QUERY
);
106 lcl_getChildCIDs( rOutChildren
, xNewShapes
);
112 } // anonymous namespace
120 class ImplObjectHierarchy
123 explicit ImplObjectHierarchy(
124 const Reference
< XChartDocument
> & xChartDocument
,
125 ExplicitValueProvider
* pExplicitValueProvider
,
126 bool bFlattenDiagram
);
128 bool hasChildren( const OUString
& rParent
);
129 ObjectHierarchy::tChildContainer
getChildren( const OUString
& rParent
);
130 ObjectHierarchy::tChildContainer
getSiblings( const OUString
& rNode
);
132 ObjectHierarchy::tCID
getParent( const ObjectHierarchy::tCID
& rCID
);
135 void createTree( const Reference
< XChartDocument
> & xChartDocument
);
136 void createDiagramTree(
137 ObjectHierarchy::tChildContainer
& rContainer
,
138 const Reference
< XChartDocument
> & xChartDoc
,
139 const Reference
< XDiagram
> & xDiagram
);
140 void createDataSeriesTree(
141 ObjectHierarchy::tChildContainer
& rOutDiagramSubContainer
,
142 const Reference
< XCoordinateSystemContainer
> & xCooSysCnt
);
143 ObjectHierarchy::tCID
getParentImpl(
144 const ObjectHierarchy::tCID
& rParentCID
,
145 const ObjectHierarchy::tCID
& rCID
);
147 typedef ::std::map
< OUString
, ObjectHierarchy::tChildContainer
>
149 tChildMap m_aChildMap
;
150 ExplicitValueProvider
* m_pExplicitValueProvider
;
151 bool m_bFlattenDiagram
;
154 ImplObjectHierarchy::ImplObjectHierarchy(
155 const Reference
< XChartDocument
> & xChartDocument
,
156 ExplicitValueProvider
* pExplicitValueProvider
,
157 bool bFlattenDiagram
) :
158 m_pExplicitValueProvider( pExplicitValueProvider
),
159 m_bFlattenDiagram( bFlattenDiagram
)
161 createTree( xChartDocument
);
162 // don't remember this helper to avoid access after lifetime
163 m_pExplicitValueProvider
= 0;
166 void ImplObjectHierarchy::createTree( const Reference
< XChartDocument
> & xChartDocument
)
168 if( !xChartDocument
.is())
171 //@todo: change ObjectIdentifier to take an XChartDocument rather than XModel
172 Reference
< frame::XModel
> xModel( xChartDocument
, uno::UNO_QUERY
);
173 ObjectHierarchy::tChildContainer aTopLevelContainer
;
178 Reference
< XTitled
> xDocTitled( xChartDocument
, uno::UNO_QUERY
);
181 Reference
< XTitle
> xMainTitle( xDocTitled
->getTitleObject());
183 aTopLevelContainer
.push_back(
184 ObjectIdentifier::createClassifiedIdentifierForObject( xMainTitle
, xModel
));
187 Reference
< XDiagram
> xDiagram( ChartModelHelper::findDiagram( xChartDocument
));
190 // Sub Title. Note: This is interpreted of being top level
191 Reference
< XTitled
> xDiaTitled( xDiagram
, uno::UNO_QUERY
);
194 Reference
< XTitle
> xSubTitle( xDiaTitled
->getTitleObject());
196 aTopLevelContainer
.push_back(
197 ObjectIdentifier::createClassifiedIdentifierForObject( xSubTitle
, xModel
));
200 // Axis Titles. Note: These are interpreted of being top level
201 Sequence
< Reference
< XAxis
> > aAxes( AxisHelper::getAllAxesOfDiagram( xDiagram
) );
202 for( sal_Int32 i
=0; i
<aAxes
.getLength(); ++i
)
204 Reference
< XTitled
> xAxisTitled( aAxes
[i
], uno::UNO_QUERY
);
205 if( xAxisTitled
.is())
207 Reference
< XTitle
> xAxisTitle( xAxisTitled
->getTitleObject());
209 aTopLevelContainer
.push_back(
210 ObjectIdentifier::createClassifiedIdentifierForObject( xAxisTitle
, xModel
));
215 OUString
aDiaCID( ObjectIdentifier::createClassifiedIdentifierForObject( xDiagram
, xModel
));
216 OSL_ASSERT( aDiaCID
.getLength());
217 aTopLevelContainer
.push_back( aDiaCID
);
218 if( m_bFlattenDiagram
)
219 createDiagramTree( aTopLevelContainer
, xChartDocument
, xDiagram
);
222 ObjectHierarchy::tChildContainer aSubContainer
;
223 createDiagramTree( aSubContainer
, xChartDocument
, xDiagram
);
224 if( ! aSubContainer
.empty())
225 m_aChildMap
[ aDiaCID
] = aSubContainer
;
229 // Legend. Note: This is interpreted of being top level
230 Reference
< XLegend
> xLegend( xDiagram
->getLegend());
233 Reference
< beans::XPropertySet
> xLegendProp( xLegend
, uno::UNO_QUERY
);
235 if( xLegendProp
.is() &&
236 (xLegendProp
->getPropertyValue( C2U("Show")) >>= bShow
) &&
239 OUString
aLegendCID( ObjectIdentifier::createClassifiedIdentifierForObject( xLegend
, xModel
));
240 aTopLevelContainer
.push_back( aLegendCID
);
242 // iterate over child shapes of legend and search for matching CIDs
243 if( m_pExplicitValueProvider
)
245 Reference
< container::XIndexAccess
> xLegendShapeContainer(
246 m_pExplicitValueProvider
->getShapeForCID( aLegendCID
), uno::UNO_QUERY
);
247 ObjectHierarchy::tChildContainer aLegendEntryCIDs
;
248 lcl_getChildCIDs( aLegendEntryCIDs
, xLegendShapeContainer
);
250 m_aChildMap
[ aLegendCID
] = aLegendEntryCIDs
;
257 aTopLevelContainer
.push_back(
258 ObjectIdentifier::createClassifiedIdentifier( OBJECTTYPE_PAGE
, OUString() ) );
260 if( ! aTopLevelContainer
.empty())
261 m_aChildMap
[ ObjectHierarchy::getRootNodeCID() ] = aTopLevelContainer
;
264 void ImplObjectHierarchy::createDiagramTree(
265 ObjectHierarchy::tChildContainer
& rContainer
,
266 const Reference
< XChartDocument
> & xChartDoc
,
267 const Reference
< XDiagram
> & xDiagram
)
270 Reference
< XCoordinateSystemContainer
> xCooSysCnt( xDiagram
, uno::UNO_QUERY_THROW
);
271 createDataSeriesTree( rContainer
, xCooSysCnt
);
274 sal_Int32 nDimensionCount
= DiagramHelper::getDimension( xDiagram
);
275 uno::Reference
< chart2::XChartType
> xChartType( DiagramHelper::getChartTypeByIndex( xDiagram
, 0 ) );
276 bool bSupportsAxesGrids
= ChartTypeHelper::isSupportingMainAxis( xChartType
, nDimensionCount
, 0 );
277 bool bIsThreeD
= ( nDimensionCount
== 3 );
278 bool bHasWall
= DiagramHelper::isSupportingFloorAndWall( xDiagram
);
279 if( bSupportsAxesGrids
)
281 Sequence
< Reference
< XAxis
> > aAxes( AxisHelper::getAllAxesOfDiagram( xDiagram
, /* bOnlyVisible = */ true ) );
282 ::std::transform( aAxes
.getConstArray(), aAxes
.getConstArray() + aAxes
.getLength(),
283 ::std::back_inserter( rContainer
),
284 lcl_ObjectToCID( xChartDoc
));
286 // get all axes, also invisible ones
287 aAxes
= AxisHelper::getAllAxesOfDiagram( xDiagram
, /* bOnlyVisible = */ false );
289 Reference
< frame::XModel
> xChartModel( xChartDoc
, uno::UNO_QUERY
);
290 for( sal_Int32 nA
=0; nA
<aAxes
.getLength(); ++nA
)
292 Reference
< XAxis
> xAxis( aAxes
[nA
] );
296 Reference
< beans::XPropertySet
> xGridProperties( xAxis
->getGridProperties() );
297 if( AxisHelper::isGridVisible( xGridProperties
) )
300 rContainer
.push_back(
301 ObjectIdentifier::createClassifiedIdentifierForGrid( xAxis
, xChartModel
) );
304 Sequence
< Reference
< beans::XPropertySet
> > aSubGrids( xAxis
->getSubGridProperties() );;
305 sal_Int32 nSubGrid
= 0;
306 for( nSubGrid
= 0; nSubGrid
< aSubGrids
.getLength(); ++nSubGrid
)
308 Reference
< beans::XPropertySet
> xSubGridProperties( aSubGrids
[nSubGrid
] );
309 if( AxisHelper::isGridVisible( xSubGridProperties
) )
312 rContainer
.push_back(
313 ObjectIdentifier::createClassifiedIdentifierForGrid( xAxis
, xChartModel
, nSubGrid
) );
322 rContainer
.push_back(
323 ObjectIdentifier::createClassifiedIdentifier( OBJECTTYPE_DIAGRAM_WALL
, rtl::OUString()));
327 if( bHasWall
&& bIsThreeD
)
329 Reference
< beans::XPropertySet
> xFloor( xDiagram
->getFloor());
331 rContainer
.push_back(
332 ObjectIdentifier::createClassifiedIdentifier( OBJECTTYPE_DIAGRAM_FLOOR
, rtl::OUString()));
336 void ImplObjectHierarchy::createDataSeriesTree(
337 ObjectHierarchy::tChildContainer
& rOutDiagramSubContainer
,
338 const Reference
< XCoordinateSystemContainer
> & xCooSysCnt
)
342 sal_Int32 nDiagramIndex
= 0;
343 Sequence
< Reference
< XCoordinateSystem
> > aCooSysSeq(
344 xCooSysCnt
->getCoordinateSystems());
345 for( sal_Int32 nCooSysIdx
=0; nCooSysIdx
<aCooSysSeq
.getLength(); ++nCooSysIdx
)
347 Reference
< XChartTypeContainer
> xCTCnt( aCooSysSeq
[nCooSysIdx
], uno::UNO_QUERY_THROW
);
348 Sequence
< Reference
< XChartType
> > aChartTypeSeq( xCTCnt
->getChartTypes());
349 for( sal_Int32 nCTIdx
=0; nCTIdx
<aChartTypeSeq
.getLength(); ++nCTIdx
)
351 Reference
< XDataSeriesContainer
> xDSCnt( aChartTypeSeq
[nCTIdx
], uno::UNO_QUERY_THROW
);
352 Sequence
< Reference
< XDataSeries
> > aSeriesSeq( xDSCnt
->getDataSeries() );
353 const sal_Int32 nNumberOfSeries
=
354 ChartTypeHelper::getNumberOfDisplayedSeries( aChartTypeSeq
[nCTIdx
], aSeriesSeq
.getLength());
356 for( sal_Int32 nSeriesIdx
=0; nSeriesIdx
<nNumberOfSeries
; ++nSeriesIdx
)
358 OUString
aSeriesParticle(
359 ObjectIdentifier::createParticleForSeries(
360 nDiagramIndex
, nCooSysIdx
, nCTIdx
, nSeriesIdx
));
361 ObjectHierarchy::tCID
aSeriesCID(
362 ObjectIdentifier::createClassifiedIdentifierForParticle( aSeriesParticle
));
363 rOutDiagramSubContainer
.push_back( aSeriesCID
);
365 ObjectHierarchy::tChildContainer aSeriesSubContainer
;
368 Reference
< chart2::XRegressionCurveContainer
> xCurveCnt( aSeriesSeq
[nSeriesIdx
], uno::UNO_QUERY
);
371 Sequence
< Reference
< chart2::XRegressionCurve
> > aCurves( xCurveCnt
->getRegressionCurves());
372 for( sal_Int32 nCurveIdx
=0; nCurveIdx
<aCurves
.getLength(); ++nCurveIdx
)
374 bool bIsAverageLine
= RegressionCurveHelper::isMeanValueLine( aCurves
[nCurveIdx
] );
375 aSeriesSubContainer
.push_back(
376 ObjectIdentifier::createDataCurveCID( aSeriesParticle
, nCurveIdx
, bIsAverageLine
));
377 Reference
< beans::XPropertySet
> xEqProp( aCurves
[nCurveIdx
]->getEquationProperties());
378 bool bShowEq
= false;
379 bool bShowCoeff
= false;
381 ( (xEqProp
->getPropertyValue( C2U("ShowEquation")) >>= bShowEq
) ||
382 (xEqProp
->getPropertyValue( C2U("ShowCorrelationCoefficient")) >>= bShowCoeff
) ) &&
383 ( bShowEq
|| bShowCoeff
) )
385 aSeriesSubContainer
.push_back(
386 ObjectIdentifier::createDataCurveEquationCID( aSeriesParticle
, nCurveIdx
));
389 Reference
< beans::XPropertySet
> xSeriesProp( aSeriesSeq
[nSeriesIdx
], uno::UNO_QUERY
);
390 Reference
< beans::XPropertySet
> xErrorBarProp
;
391 if( xSeriesProp
.is() &&
392 (xSeriesProp
->getPropertyValue( C2U("ErrorBarY")) >>= xErrorBarProp
) &&
395 sal_Int32 nStyle
= ::com::sun::star::chart::ErrorBarStyle::NONE
;
396 if( ( xErrorBarProp
->getPropertyValue( C2U("ErrorBarStyle")) >>= nStyle
) &&
397 ( nStyle
!= ::com::sun::star::chart::ErrorBarStyle::NONE
) )
399 aSeriesSubContainer
.push_back(
400 ObjectIdentifier::createClassifiedIdentifierWithParent(
401 OBJECTTYPE_DATA_ERRORS
, OUString(), aSeriesParticle
));
407 // iterate over child shapes of legend and search for matching CIDs
408 if( m_pExplicitValueProvider
)
410 Reference
< container::XIndexAccess
> xSeriesShapeContainer(
411 m_pExplicitValueProvider
->getShapeForCID( aSeriesCID
), uno::UNO_QUERY
);
412 lcl_getChildCIDs( aSeriesSubContainer
, xSeriesShapeContainer
);
415 if( ! aSeriesSubContainer
.empty())
416 m_aChildMap
[ aSeriesCID
] = aSeriesSubContainer
;
421 catch( uno::Exception
& ex
)
423 ASSERT_EXCEPTION( ex
);
427 bool ImplObjectHierarchy::hasChildren( const OUString
& rParent
)
429 if( rParent
.getLength())
431 tChildMap::const_iterator
aIt( m_aChildMap
.find( rParent
));
432 if( aIt
!= m_aChildMap
.end())
433 return ! (aIt
->second
.empty());
438 ObjectHierarchy::tChildContainer
ImplObjectHierarchy::getChildren( const OUString
& rParent
)
440 if( rParent
.getLength())
442 tChildMap::const_iterator
aIt( m_aChildMap
.find( rParent
));
443 if( aIt
!= m_aChildMap
.end())
446 return ObjectHierarchy::tChildContainer();
449 ObjectHierarchy::tChildContainer
ImplObjectHierarchy::getSiblings( const OUString
& rNode
)
451 if( rNode
.getLength() && !ObjectHierarchy::isRootNode( rNode
))
453 for( tChildMap::const_iterator
aIt( m_aChildMap
.begin());
454 aIt
!= m_aChildMap
.end(); ++aIt
)
456 ObjectHierarchy::tChildContainer::const_iterator
aElemIt(
457 ::std::find( aIt
->second
.begin(), aIt
->second
.end(), rNode
));
458 if( aElemIt
!= aIt
->second
.end())
462 return ObjectHierarchy::tChildContainer();
465 ObjectHierarchy::tCID
ImplObjectHierarchy::getParentImpl(
466 const ObjectHierarchy::tCID
& rParentCID
,
467 const ObjectHierarchy::tCID
& rCID
)
470 ObjectHierarchy::tChildContainer
aChildren( getChildren( rParentCID
));
471 ObjectHierarchy::tChildContainer::const_iterator
aIt(
472 ::std::find( aChildren
.begin(), aChildren
.end(), rCID
));
474 if( aIt
!= aChildren
.end())
477 for( aIt
= aChildren
.begin(); aIt
!= aChildren
.end(); ++aIt
)
480 ObjectHierarchy::tCID
aTempParent( getParentImpl( *aIt
, rCID
));
481 if( aTempParent
.getLength())
489 return ObjectHierarchy::tCID();
492 ObjectHierarchy::tCID
ImplObjectHierarchy::getParent(
493 const ObjectHierarchy::tCID
& rCID
)
495 return getParentImpl( ObjectHierarchy::getRootNodeCID(), rCID
);
500 ObjectHierarchy::ObjectHierarchy(
501 const Reference
< XChartDocument
> & xChartDocument
,
502 ExplicitValueProvider
* pExplicitValueProvider
/* = 0 */,
503 bool bFlattenDiagram
/* = false */ ) :
504 m_apImpl( new impl::ImplObjectHierarchy( xChartDocument
, pExplicitValueProvider
, bFlattenDiagram
))
507 ObjectHierarchy::~ObjectHierarchy()
511 ObjectHierarchy::tCID
ObjectHierarchy::getRootNodeCID()
517 bool ObjectHierarchy::isRootNode( const ObjectHierarchy::tCID
& rCID
)
519 return rCID
.equals( ObjectHierarchy::getRootNodeCID());
522 ObjectHierarchy::tChildContainer
ObjectHierarchy::getTopLevelChildren() const
524 return m_apImpl
->getChildren( ObjectHierarchy::getRootNodeCID());
527 bool ObjectHierarchy::hasChildren( const tCID
& rParent
) const
529 return m_apImpl
->hasChildren( rParent
);
532 ObjectHierarchy::tChildContainer
ObjectHierarchy::getChildren(
533 const ObjectHierarchy::tCID
& rParent
) const
535 if( rParent
.getLength())
536 return m_apImpl
->getChildren( rParent
);
538 return ObjectHierarchy::tChildContainer();
541 ObjectHierarchy::tChildContainer
ObjectHierarchy::getSiblings(
542 const ObjectHierarchy::tCID
& rNode
) const
544 if( rNode
.getLength() && !isRootNode( rNode
))
545 return m_apImpl
->getSiblings( rNode
);
547 return ObjectHierarchy::tChildContainer();
550 ObjectHierarchy::tCID
ObjectHierarchy::getParent(
551 const ObjectHierarchy::tCID
& rNode
) const
553 return m_apImpl
->getParent( rNode
);
556 sal_Int32
ObjectHierarchy::getIndexInParent(
557 const ObjectHierarchy::tCID
& rNode
) const
559 tCID
aParentCID( m_apImpl
->getParent( rNode
));
560 tChildContainer
aChildren( m_apImpl
->getChildren( aParentCID
));
561 tChildContainer::const_iterator
aIt( aChildren
.begin());
562 for( sal_Int32 nIndex
= 0; aIt
!= aChildren
.end(); ++nIndex
, ++aIt
)
564 if( aIt
->equals( rNode
))
570 // ================================================================================
572 ObjectKeyNavigation::ObjectKeyNavigation(
573 const ObjectHierarchy::tCID
& rCurrentCID
,
574 const Reference
< chart2::XChartDocument
> & xChartDocument
,
575 ExplicitValueProvider
* pExplicitValueProvider
/* = 0 */ ) :
576 m_aCurrentCID( rCurrentCID
),
577 m_xChartDocument( xChartDocument
),
578 m_pExplicitValueProvider( pExplicitValueProvider
),
579 m_bStepDownInDiagram( true )
581 if( m_aCurrentCID
.getLength() == 0 )
582 setCurrentSelection( ObjectHierarchy::getRootNodeCID());
585 bool ObjectKeyNavigation::handleKeyEvent(
586 const awt::KeyEvent
& rEvent
)
588 bool bResult
= false;
590 switch( rEvent
.KeyCode
)
593 if( rEvent
.Modifiers
& awt::KeyModifier::SHIFT
)
594 bResult
= previous();
605 if( rEvent
.Modifiers
& awt::KeyModifier::SHIFT
)
610 case awt::Key::ESCAPE
:
611 setCurrentSelection( OUString());
621 void ObjectKeyNavigation::setCurrentSelection( const ObjectHierarchy::tCID
& rCID
)
623 m_aCurrentCID
= rCID
;
626 ObjectHierarchy::tCID
ObjectKeyNavigation::getCurrentSelection() const
628 return m_aCurrentCID
;
631 bool ObjectKeyNavigation::first()
633 ObjectHierarchy
aHierarchy( m_xChartDocument
, m_pExplicitValueProvider
, m_bStepDownInDiagram
);
634 ObjectHierarchy::tChildContainer
aSiblings( aHierarchy
.getSiblings( getCurrentSelection()));
635 bool bResult
= !aSiblings
.empty();
637 setCurrentSelection( aSiblings
.front());
639 bResult
= veryFirst();
643 bool ObjectKeyNavigation::last()
645 ObjectHierarchy
aHierarchy( m_xChartDocument
, m_pExplicitValueProvider
, m_bStepDownInDiagram
);
646 ObjectHierarchy::tChildContainer
aSiblings( aHierarchy
.getSiblings( getCurrentSelection()));
647 bool bResult
= !aSiblings
.empty();
649 setCurrentSelection( aSiblings
.back());
651 bResult
= veryLast();
655 bool ObjectKeyNavigation::next()
657 ObjectHierarchy
aHierarchy( m_xChartDocument
, m_pExplicitValueProvider
, m_bStepDownInDiagram
);
658 ObjectHierarchy::tChildContainer
aSiblings( aHierarchy
.getSiblings( getCurrentSelection()));
659 bool bResult
= !aSiblings
.empty();
662 ObjectHierarchy::tChildContainer::const_iterator
aIt(
663 ::std::find( aSiblings
.begin(), aSiblings
.end(), getCurrentSelection()));
664 OSL_ASSERT( aIt
!= aSiblings
.end());
665 if( ++aIt
== aSiblings
.end())
666 aIt
= aSiblings
.begin();
667 setCurrentSelection( *aIt
);
670 bResult
= veryFirst();
675 bool ObjectKeyNavigation::previous()
677 ObjectHierarchy
aHierarchy( m_xChartDocument
, m_pExplicitValueProvider
, m_bStepDownInDiagram
);
678 ObjectHierarchy::tChildContainer
aSiblings( aHierarchy
.getSiblings( getCurrentSelection()));
679 bool bResult
= !aSiblings
.empty();
682 ObjectHierarchy::tChildContainer::const_iterator
aIt(
683 ::std::find( aSiblings
.begin(), aSiblings
.end(), getCurrentSelection()));
684 OSL_ASSERT( aIt
!= aSiblings
.end());
685 if( aIt
== aSiblings
.begin())
686 aIt
= aSiblings
.end();
688 setCurrentSelection( *aIt
);
691 bResult
= veryLast();
695 bool ObjectKeyNavigation::up()
697 ObjectHierarchy
aHierarchy( m_xChartDocument
, m_pExplicitValueProvider
, m_bStepDownInDiagram
);
698 bool bResult
= !ObjectHierarchy::isRootNode( getCurrentSelection());
700 setCurrentSelection( aHierarchy
.getParent( getCurrentSelection()));
704 bool ObjectKeyNavigation::down()
706 ObjectHierarchy
aHierarchy( m_xChartDocument
, m_pExplicitValueProvider
, m_bStepDownInDiagram
);
707 bool bResult
= aHierarchy
.hasChildren( getCurrentSelection());
710 ObjectHierarchy::tChildContainer aChildren
= aHierarchy
.getChildren( getCurrentSelection());
711 OSL_ASSERT( !aChildren
.empty());
712 setCurrentSelection( aChildren
.front());
717 bool ObjectKeyNavigation::veryFirst()
719 ObjectHierarchy
aHierarchy( m_xChartDocument
, m_pExplicitValueProvider
, m_bStepDownInDiagram
);
720 ObjectHierarchy::tChildContainer
aChildren( aHierarchy
.getTopLevelChildren());
721 bool bResult
= !aChildren
.empty();
723 setCurrentSelection( aChildren
.front());
727 bool ObjectKeyNavigation::veryLast()
729 ObjectHierarchy
aHierarchy( m_xChartDocument
, m_pExplicitValueProvider
, m_bStepDownInDiagram
);
730 ObjectHierarchy::tChildContainer
aChildren( aHierarchy
.getTopLevelChildren());
731 bool bResult
= !aChildren
.empty();
733 setCurrentSelection( aChildren
.back());