update dev300-m57
[ooovba.git] / chart2 / source / controller / main / ObjectHierarchy.cxx
blob55dbe8aa237b15c53d982b8451bab9c531d8e635
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: ObjectHierarchy.cxx,v $
10 * $Revision: 1.7 $
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"
41 #include "macros.hxx"
42 #include "LineProperties.hxx"
43 #include "ChartTypeHelper.hxx"
45 #include <map>
46 #include <algorithm>
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;
65 namespace
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 );
78 private:
79 Reference< frame::XModel > m_xModel;
82 void lcl_getChildCIDs(
83 ::chart::ObjectHierarchy::tChildContainer & rOutChildren,
84 const Reference< container::XIndexAccess > & xShapes )
86 if( xShapes.is())
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 );
92 if( xShapeProp.is())
94 Reference< beans::XPropertySetInfo > xInfo( xShapeProp->getPropertySetInfo());
95 OUString aName;
96 if( xInfo.is() &&
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 );
105 if( xNewShapes.is())
106 lcl_getChildCIDs( rOutChildren, xNewShapes );
112 } // anonymous namespace
115 namespace chart
118 namespace impl
120 class ImplObjectHierarchy
122 public:
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 );
134 private:
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 >
148 tChildMap;
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())
169 return;
171 //@todo: change ObjectIdentifier to take an XChartDocument rather than XModel
172 Reference< frame::XModel > xModel( xChartDocument, uno::UNO_QUERY );
173 ObjectHierarchy::tChildContainer aTopLevelContainer;
175 // First Level
177 // Main Title
178 Reference< XTitled > xDocTitled( xChartDocument, uno::UNO_QUERY );
179 if( xDocTitled.is())
181 Reference< XTitle > xMainTitle( xDocTitled->getTitleObject());
182 if( xMainTitle.is())
183 aTopLevelContainer.push_back(
184 ObjectIdentifier::createClassifiedIdentifierForObject( xMainTitle, xModel ));
187 Reference< XDiagram > xDiagram( ChartModelHelper::findDiagram( xChartDocument ));
188 if( xDiagram.is())
190 // Sub Title. Note: This is interpreted of being top level
191 Reference< XTitled > xDiaTitled( xDiagram, uno::UNO_QUERY );
192 if( xDiaTitled.is())
194 Reference< XTitle > xSubTitle( xDiaTitled->getTitleObject());
195 if( xSubTitle.is())
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());
208 if( xAxisTitle.is())
209 aTopLevelContainer.push_back(
210 ObjectIdentifier::createClassifiedIdentifierForObject( xAxisTitle, xModel ));
214 // Diagram
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 );
220 else
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());
231 if( xLegend.is())
233 Reference< beans::XPropertySet > xLegendProp( xLegend, uno::UNO_QUERY );
234 bool bShow = false;
235 if( xLegendProp.is() &&
236 (xLegendProp->getPropertyValue( C2U("Show")) >>= bShow) &&
237 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;
256 // Chart Area
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 )
269 // Data Series
270 Reference< XCoordinateSystemContainer > xCooSysCnt( xDiagram, uno::UNO_QUERY_THROW );
271 createDataSeriesTree( rContainer, xCooSysCnt );
273 // Axes
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 );
288 // Grids
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] );
293 if(!xAxis.is())
294 continue;
296 Reference< beans::XPropertySet > xGridProperties( xAxis->getGridProperties() );
297 if( AxisHelper::isGridVisible( xGridProperties ) )
299 //main grid
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 ) )
311 //sub grid
312 rContainer.push_back(
313 ObjectIdentifier::createClassifiedIdentifierForGrid( xAxis, xChartModel, nSubGrid ) );
319 // Wall
320 if( bHasWall )
322 rContainer.push_back(
323 ObjectIdentifier::createClassifiedIdentifier( OBJECTTYPE_DIAGRAM_WALL, rtl::OUString()));
326 // Floor
327 if( bHasWall && bIsThreeD )
329 Reference< beans::XPropertySet > xFloor( xDiagram->getFloor());
330 if( xFloor.is())
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;
367 // Statistics
368 Reference< chart2::XRegressionCurveContainer > xCurveCnt( aSeriesSeq[nSeriesIdx], uno::UNO_QUERY );
369 if( xCurveCnt.is())
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;
380 if( xEqProp.is() &&
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) &&
393 xErrorBarProp.is())
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 ));
406 // Data Points
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());
435 return false;
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())
444 return aIt->second;
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())
459 return aIt->second;
462 return ObjectHierarchy::tChildContainer();
465 ObjectHierarchy::tCID ImplObjectHierarchy::getParentImpl(
466 const ObjectHierarchy::tCID & rParentCID,
467 const ObjectHierarchy::tCID & rCID )
469 // search children
470 ObjectHierarchy::tChildContainer aChildren( getChildren( rParentCID ));
471 ObjectHierarchy::tChildContainer::const_iterator aIt(
472 ::std::find( aChildren.begin(), aChildren.end(), rCID ));
473 // recursion end
474 if( aIt != aChildren.end())
475 return rParentCID;
477 for( aIt = aChildren.begin(); aIt != aChildren.end(); ++aIt )
479 // recursion
480 ObjectHierarchy::tCID aTempParent( getParentImpl( *aIt, rCID ));
481 if( aTempParent.getLength())
483 // exit on success
484 return aTempParent;
488 // exit on fail
489 return ObjectHierarchy::tCID();
492 ObjectHierarchy::tCID ImplObjectHierarchy::getParent(
493 const ObjectHierarchy::tCID & rCID )
495 return getParentImpl( ObjectHierarchy::getRootNodeCID(), rCID );
498 } // namespace impl
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()
510 // static
511 ObjectHierarchy::tCID ObjectHierarchy::getRootNodeCID()
513 return C2U("ROOT");
516 // static
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 ))
565 return nIndex;
567 return -1;
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 )
592 case awt::Key::TAB:
593 if( rEvent.Modifiers & awt::KeyModifier::SHIFT )
594 bResult = previous();
595 else
596 bResult = next();
597 break;
598 case awt::Key::HOME:
599 bResult = first();
600 break;
601 case awt::Key::END:
602 bResult = last();
603 break;
604 case awt::Key::F3:
605 if( rEvent.Modifiers & awt::KeyModifier::SHIFT )
606 bResult = up();
607 else
608 bResult = down();
609 break;
610 case awt::Key::ESCAPE:
611 setCurrentSelection( OUString());
612 bResult = true;
613 break;
614 default:
615 bResult = false;
616 break;
618 return bResult;
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();
636 if( bResult )
637 setCurrentSelection( aSiblings.front());
638 else
639 bResult = veryFirst();
640 return bResult;
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();
648 if( bResult )
649 setCurrentSelection( aSiblings.back());
650 else
651 bResult = veryLast();
652 return bResult;
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();
660 if( bResult )
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 );
669 else
670 bResult = veryFirst();
672 return bResult;
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();
680 if( bResult )
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();
687 --aIt;
688 setCurrentSelection( *aIt );
690 else
691 bResult = veryLast();
692 return bResult;
695 bool ObjectKeyNavigation::up()
697 ObjectHierarchy aHierarchy( m_xChartDocument, m_pExplicitValueProvider, m_bStepDownInDiagram );
698 bool bResult = !ObjectHierarchy::isRootNode( getCurrentSelection());
699 if( bResult )
700 setCurrentSelection( aHierarchy.getParent( getCurrentSelection()));
701 return bResult;
704 bool ObjectKeyNavigation::down()
706 ObjectHierarchy aHierarchy( m_xChartDocument, m_pExplicitValueProvider, m_bStepDownInDiagram );
707 bool bResult = aHierarchy.hasChildren( getCurrentSelection());
708 if( bResult )
710 ObjectHierarchy::tChildContainer aChildren = aHierarchy.getChildren( getCurrentSelection());
711 OSL_ASSERT( !aChildren.empty());
712 setCurrentSelection( aChildren.front());
714 return bResult;
717 bool ObjectKeyNavigation::veryFirst()
719 ObjectHierarchy aHierarchy( m_xChartDocument, m_pExplicitValueProvider, m_bStepDownInDiagram );
720 ObjectHierarchy::tChildContainer aChildren( aHierarchy.getTopLevelChildren());
721 bool bResult = !aChildren.empty();
722 if( bResult )
723 setCurrentSelection( aChildren.front());
724 return bResult;
727 bool ObjectKeyNavigation::veryLast()
729 ObjectHierarchy aHierarchy( m_xChartDocument, m_pExplicitValueProvider, m_bStepDownInDiagram );
730 ObjectHierarchy::tChildContainer aChildren( aHierarchy.getTopLevelChildren());
731 bool bResult = !aChildren.empty();
732 if( bResult )
733 setCurrentSelection( aChildren.back());
734 return bResult;
737 } // namespace chart