1 /*************************************************************************
2  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
3  *
4  * Copyright 2000, 2010 Oracle and/or its affiliates.
5  *
6  * OpenOffice.org - a multi-platform office productivity suite
7  *
8  * This file is part of OpenOffice.org.
9  *
10  * OpenOffice.org is free software: you can redistribute it and/or modify
11  * it under the terms of the GNU Lesser General Public License version 3
12  * only, as published by the Free Software Foundation.
13  *
14  * OpenOffice.org is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU Lesser General Public License version 3 for more details
18  * (a copy is included in the LICENSE file that accompanied this code).
19  *
20  * You should have received a copy of the GNU Lesser General Public License
21  * version 3 along with OpenOffice.org.  If not, see
22  * <http://www.openoffice.org/license.html>
23  * for a copy of the LGPLv3 License.
24  *
25 ************************************************************************/
26 
27 // MARKER(update_precomp.py): autogen include statement, do not remove
28 #include "precompiled_svtools.hxx"
29 
30 #include "svtools/table/tablecontrol.hxx"
31 
32 #include "tablegeometry.hxx"
33 #include "tablecontrol_impl.hxx"
34 #include "tabledatawindow.hxx"
35 
36 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
37 #include <com/sun/star/accessibility/AccessibleRole.hpp>
38 #include <com/sun/star/accessibility/AccessibleEventId.hpp>
39 
40 #include <tools/diagnose_ex.h>
41 
42 using namespace ::com::sun::star::uno;
43 using ::com::sun::star::accessibility::XAccessible;
44 using namespace ::com::sun::star::accessibility;
45 using namespace ::com::sun::star::lang;
46 using namespace utl;
47 
48 //......................................................................................................................
49 namespace svt { namespace table
50 {
51 //......................................................................................................................
52 
53     namespace AccessibleEventId = ::com::sun::star::accessibility::AccessibleEventId;
54 
55     //==================================================================================================================
56 	//= TableControl
57     //==================================================================================================================
58     // -----------------------------------------------------------------------------------------------------------------
59     TableControl::TableControl( Window* _pParent, WinBits _nStyle )
60         :Control( _pParent, _nStyle )
61         ,m_pImpl( new TableControl_Impl( *this ) )
62     {
63 		TableDataWindow& rDataWindow = m_pImpl->getDataWindow();
64 		rDataWindow.SetSelectHdl( LINK( this, TableControl, ImplSelectHdl ) );
65 
66         // by default, use the background as determined by the style settings
67         const Color aWindowColor( GetSettings().GetStyleSettings().GetFieldColor() );
68 		SetBackground( Wallpaper( aWindowColor ) );
69 		SetFillColor( aWindowColor );
70 
71         SetCompoundControl( true );
72     }
73 
74     // -----------------------------------------------------------------------------------------------------------------
75     TableControl::~TableControl()
76     {
77 		ImplCallEventListeners( VCLEVENT_OBJECT_DYING );
78 
79         m_pImpl->setModel( PTableModel() );
80         m_pImpl->disposeAccessible();
81         m_pImpl.reset();
82     }
83 
84     // -----------------------------------------------------------------------------------------------------------------
85     void TableControl::GetFocus()
86     {
87         if ( !m_pImpl->getInputHandler()->GetFocus( *m_pImpl ) )
88             Control::GetFocus();
89     }
90 
91     // -----------------------------------------------------------------------------------------------------------------
92     void TableControl::LoseFocus()
93     {
94         if ( !m_pImpl->getInputHandler()->LoseFocus( *m_pImpl ) )
95             Control::LoseFocus();
96     }
97 
98     // -----------------------------------------------------------------------------------------------------------------
99     void TableControl::KeyInput( const KeyEvent& rKEvt )
100     {
101         if ( !m_pImpl->getInputHandler()->KeyInput( *m_pImpl, rKEvt ) )
102             Control::KeyInput( rKEvt );
103         else
104         {
105             if ( m_pImpl->isAccessibleAlive() )
106             {
107                 m_pImpl->commitCellEvent( AccessibleEventId::STATE_CHANGED,
108                                           makeAny( AccessibleStateType::FOCUSED ),
109                                           Any()
110                                         );
111                     // Huh? What the heck? Why do we unconditionally notify a STATE_CHANGE/FOCUSED after each and every
112                     // (handled) key stroke?
113 
114                 m_pImpl->commitTableEvent( AccessibleEventId::ACTIVE_DESCENDANT_CHANGED,
115                                            Any(),
116                                            Any()
117                                          );
118                     // ditto: Why do we notify this unconditionally? We should find the right place to notify the
119                     // ACTIVE_DESCENDANT_CHANGED event.
120                     // Also, we should check if STATE_CHANGED/FOCUSED is really necessary: finally, the children are
121                     // transient, aren't they?
122             }
123         }
124     }
125 
126 
127     // -----------------------------------------------------------------------------------------------------------------
128     void TableControl::StateChanged( StateChangedType i_nStateChange )
129     {
130         Control::StateChanged( i_nStateChange );
131 
132         // forward certain settings to the data window
133         switch ( i_nStateChange )
134         {
135         case STATE_CHANGE_CONTROL_FOCUS:
136             m_pImpl->invalidateSelectedRows();
137             break;
138 
139         case STATE_CHANGE_CONTROLBACKGROUND:
140             if ( IsControlBackground() )
141                 getDataWindow().SetControlBackground( GetControlBackground() );
142             else
143                 getDataWindow().SetControlBackground();
144             break;
145 
146         case STATE_CHANGE_CONTROLFOREGROUND:
147             if ( IsControlForeground() )
148                 getDataWindow().SetControlForeground( GetControlForeground() );
149             else
150                 getDataWindow().SetControlForeground();
151             break;
152 
153         case STATE_CHANGE_CONTROLFONT:
154             if ( IsControlFont() )
155                 getDataWindow().SetControlFont( GetControlFont() );
156             else
157                 getDataWindow().SetControlFont();
158             break;
159         }
160     }
161 
162     // -----------------------------------------------------------------------------------------------------------------
163     void TableControl::Resize()
164     {
165         Control::Resize();
166         m_pImpl->onResize();
167     }
168 
169     // -----------------------------------------------------------------------------------------------------------------
170     void TableControl::SetModel( PTableModel _pModel )
171     {
172         m_pImpl->setModel( _pModel );
173     }
174 
175     // -----------------------------------------------------------------------------------------------------------------
176     PTableModel TableControl::GetModel() const
177     {
178         return m_pImpl->getModel();
179     }
180 
181     // -----------------------------------------------------------------------------------------------------------------
182     RowPos TableControl::GetTopRow() const
183     {
184         return m_pImpl->getTopRow();
185     }
186 
187     // -----------------------------------------------------------------------------------------------------------------
188     void TableControl::SetTopRow( RowPos _nRow )
189     {
190         OSL_ENSURE( false, "TableControl::SetTopRow: not implemented!" );
191         OSL_UNUSED( _nRow );
192     }
193 
194     // -----------------------------------------------------------------------------------------------------------------
195     sal_Int32 TableControl::GetCurrentRow() const
196     {
197         return m_pImpl->getCurrentRow();
198     }
199 
200     // -----------------------------------------------------------------------------------------------------------------
201     sal_Int32 TableControl::GetCurrentColumn() const
202     {
203         return m_pImpl->getCurrentColumn();
204     }
205 
206     // -----------------------------------------------------------------------------------------------------------------
207     bool TableControl::GoTo( ColPos _nColumn, RowPos _nRow )
208     {
209         return m_pImpl->goTo( _nColumn, _nRow );
210     }
211 
212 	// -----------------------------------------------------------------------------------------------------------------
213 	sal_Bool TableControl::GoToCell(sal_Int32 _nColPos, sal_Int32 _nRowPos)
214 	{
215 		return m_pImpl->goTo( _nColPos, _nRowPos );
216 	}
217 
218     //------------------------------------------------------------------------------------------------------------------
219     sal_Int32 TableControl::GetSelectedRowCount() const
220     {
221 	    return sal_Int32( m_pImpl->getSelectedRowCount() );
222     }
223 
224     //------------------------------------------------------------------------------------------------------------------
225     sal_Int32 TableControl::GetSelectedRowIndex( sal_Int32 const i_selectionIndex ) const
226     {
227 	    return sal_Int32( m_pImpl->getSelectedRowIndex( i_selectionIndex ) );
228     }
229 
230     //------------------------------------------------------------------------------------------------------------------
231     bool TableControl::IsRowSelected( sal_Int32 const i_rowIndex ) const
232     {
233 	    return m_pImpl->isRowSelected( i_rowIndex );
234     }
235 
236     // -----------------------------------------------------------------------------------------------------------------
237     void TableControl::SelectRow( RowPos const i_rowIndex, bool const i_select )
238     {
239         ENSURE_OR_RETURN_VOID( ( i_rowIndex >= 0 ) && ( i_rowIndex < m_pImpl->getModel()->getRowCount() ),
240             "TableControl::SelectRow: invalid row index!" );
241 
242         if ( i_select )
243         {
244             if ( !m_pImpl->markRowAsSelected( i_rowIndex ) )
245                 // nothing to do
246                 return;
247         }
248         else
249         {
250             m_pImpl->markRowAsDeselected( i_rowIndex );
251         }
252 
253 		m_pImpl->invalidateRowRange( i_rowIndex, i_rowIndex );
254 	    Select();
255     }
256 
257     // -----------------------------------------------------------------------------------------------------------------
258     void TableControl::SelectAllRows( bool const i_select )
259     {
260         if ( i_select )
261         {
262             if ( !m_pImpl->markAllRowsAsSelected() )
263                 // nothing to do
264                 return;
265         }
266         else
267         {
268             if ( !m_pImpl->markAllRowsAsDeselected() )
269                 // nothing to do
270                 return;
271         }
272 
273 
274         Invalidate();
275             // TODO: can't we do better than this, and invalidate only the rows which changed?
276         Select();
277     }
278 
279     // -----------------------------------------------------------------------------------------------------------------
280     ITableControl& TableControl::getTableControlInterface()
281     {
282         return *m_pImpl;
283     }
284 
285     // -----------------------------------------------------------------------------------------------------------------
286 	SelectionEngine* TableControl::getSelEngine()
287 	{
288 		return m_pImpl->getSelEngine();
289 	}
290 
291     // -----------------------------------------------------------------------------------------------------------------
292 	Window& TableControl::getDataWindow()
293 	{
294 		return m_pImpl->getDataWindow();
295 	}
296 
297     // -----------------------------------------------------------------------------------------------------------------
298 	Reference< XAccessible > TableControl::CreateAccessible()
299 	{
300 		Window* pParent = GetAccessibleParentWindow();
301 		ENSURE_OR_RETURN( pParent, "TableControl::CreateAccessible - parent not found", NULL );
302 
303         return m_pImpl->getAccessible( *pParent );
304 	}
305 
306     // -----------------------------------------------------------------------------------------------------------------
307 	Reference<XAccessible> TableControl::CreateAccessibleControl( sal_Int32 _nIndex )
308 	{
309 		(void)_nIndex;
310 		DBG_ASSERT( sal_False, "TableControl::CreateAccessibleControl: to be overwritten!" );
311 		return NULL;
312 	}
313 
314     // -----------------------------------------------------------------------------------------------------------------
315 	::rtl::OUString TableControl::GetAccessibleObjectName( AccessibleTableControlObjType eObjType, sal_Int32 _nRow, sal_Int32 _nCol) const
316 	{
317 		::rtl::OUString aRetText;
318 		//Window* pWin;
319 		switch( eObjType )
320 		{
321 			case TCTYPE_GRIDCONTROL:
322 				aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Grid control" ) );
323 				break;
324 			case TCTYPE_TABLE:
325 				aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Grid conrol" ) );
326 				break;
327 			case TCTYPE_ROWHEADERBAR:
328 				aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "RowHeaderBar" ) );
329 				break;
330 			case TCTYPE_COLUMNHEADERBAR:
331 				aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ColumnHeaderBar" ) );
332 				break;
333 			case TCTYPE_TABLECELL:
334 				//the name of the cell constists of column name and row name if defined
335 				//if the name is equal to cell content, it'll be read twice
336 				if(GetModel()->hasColumnHeaders())
337 				{
338 					aRetText = GetColumnName(_nCol);
339 					aRetText += rtl::OUString::createFromAscii(" , ");
340 				}
341 				if(GetModel()->hasRowHeaders())
342 				{
343 					aRetText += GetRowName(_nRow);
344 					aRetText += rtl::OUString::createFromAscii(" , ");
345 				}
346 				//aRetText = GetAccessibleCellText(_nRow, _nCol);
347 				break;
348 			case TCTYPE_ROWHEADERCELL:
349 				aRetText = GetRowName(_nRow);
350 				break;
351 			case TCTYPE_COLUMNHEADERCELL:
352 				aRetText = GetColumnName(_nCol);
353 				break;
354 			default:
355 				OSL_ENSURE(0,"GridControl::GetAccessibleName: invalid enum!");
356 		}
357 		return aRetText;
358 	}
359 
360     //------------------------------------------------------------------------------------------------------------------
361     ::rtl::OUString TableControl::GetAccessibleObjectDescription( AccessibleTableControlObjType eObjType, sal_Int32 ) const
362     {
363         ::rtl::OUString aRetText;
364         switch( eObjType )
365         {
366             case TCTYPE_GRIDCONTROL:
367 			    aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Grid control description" ) );
368 			    break;
369             case TCTYPE_TABLE:
370 				    aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "TABLE description" ) );
371 			    break;
372             case TCTYPE_ROWHEADERBAR:
373 				    aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ROWHEADERBAR description" ) );
374 			    break;
375             case TCTYPE_COLUMNHEADERBAR:
376 				    aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "COLUMNHEADERBAR description" ) );
377 			    break;
378             case TCTYPE_TABLECELL:
379                 // the description of the cell consists of column name and row name if defined
380                 // if the name is equal to cell content, it'll be read twice
381                 if ( GetModel()->hasColumnHeaders() )
382                 {
383                     aRetText = GetColumnName( GetCurrentColumn() );
384                     aRetText += rtl::OUString::createFromAscii( " , " );
385                 }
386                 if ( GetModel()->hasRowHeaders() )
387                 {
388                     aRetText += GetRowName( GetCurrentRow() );
389                 }
390                 break;
391             case TCTYPE_ROWHEADERCELL:
392 				    aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ROWHEADERCELL description" ) );
393 			    break;
394             case TCTYPE_COLUMNHEADERCELL:
395 				    aRetText = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "COLUMNHEADERCELL description" ) );
396 			    break;
397         }
398         return aRetText;
399     }
400 
401     //------------------------------------------------------------------------------------------------------------------
402     ::rtl::OUString TableControl::GetRowDescription( sal_Int32 _nRow) const
403     {
404 	    (void)_nRow;
405 	    return rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "row description" ) );
406     }
407 
408     //------------------------------------------------------------------------------------------------------------------
409     ::rtl::OUString TableControl::GetRowName( sal_Int32 _nIndex) const
410     {
411         ::rtl::OUString sRowName;
412         GetModel()->getRowHeading( _nIndex ) >>= sRowName;
413         return sRowName;
414     }
415 
416     //------------------------------------------------------------------------------------------------------------------
417     ::rtl::OUString TableControl::GetColumnDescription( sal_uInt16 _nColumn) const
418     {
419 	    (void)_nColumn;
420 	    return rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "col description" ) );
421     }
422 
423     //------------------------------------------------------------------------------------------------------------------
424     ::rtl::OUString TableControl::GetColumnName( sal_Int32 _nIndex) const
425     {
426 	    return GetModel()->getColumnModel(_nIndex)->getName();
427     }
428 
429     //------------------------------------------------------------------------------------------------------------------
430     ::com::sun::star::uno::Any TableControl::GetCellContent( sal_Int32 _nRowPos, sal_Int32 _nColPos ) const
431     {
432         Any aCellContent;
433         GetModel()->getCellContent( _nColPos, _nRowPos, aCellContent );
434         return aCellContent;
435     }
436 
437     //------------------------------------------------------------------------------------------------------------------
438     ::rtl::OUString TableControl::GetAccessibleCellText( sal_Int32 _nRowPos, sal_Int32 _nColPos) const
439     {
440 	    return m_pImpl->getCellContentAsString( _nRowPos, _nColPos );
441     }
442 
443     //------------------------------------------------------------------------------------------------------------------
444     void TableControl::FillAccessibleStateSet(
445             ::utl::AccessibleStateSetHelper& rStateSet,
446             AccessibleTableControlObjType eObjType ) const
447     {
448 	    switch( eObjType )
449         {
450             case TCTYPE_GRIDCONTROL:
451 		    case TCTYPE_TABLE:
452 
453 			    rStateSet.AddState( AccessibleStateType::FOCUSABLE );
454 
455                 if ( m_pImpl->getSelEngine()->GetSelectionMode() == MULTIPLE_SELECTION )
456 			        rStateSet.AddState( AccessibleStateType::MULTI_SELECTABLE);
457 
458                 if ( HasChildPathFocus() )
459 				    rStateSet.AddState( AccessibleStateType::FOCUSED );
460 
461                 if ( IsActive() )
462 				    rStateSet.AddState( AccessibleStateType::ACTIVE );
463 
464                 if ( m_pImpl->getDataWindow().IsEnabled() )
465                 {
466                     rStateSet.AddState( AccessibleStateType::ENABLED );
467                     rStateSet.AddState( AccessibleStateType::SENSITIVE );
468                 }
469 
470                 if ( IsReallyVisible() )
471 				    rStateSet.AddState( AccessibleStateType::VISIBLE );
472 
473                 if ( eObjType == TCTYPE_TABLE )
474 			        rStateSet.AddState( AccessibleStateType::MANAGES_DESCENDANTS );
475 			    break;
476 
477             case TCTYPE_ROWHEADERBAR:
478 			    rStateSet.AddState( AccessibleStateType::VISIBLE );
479 			    rStateSet.AddState( AccessibleStateType::MANAGES_DESCENDANTS );
480 			    break;
481 
482             case TCTYPE_COLUMNHEADERBAR:
483 			    rStateSet.AddState( AccessibleStateType::VISIBLE );
484 			    rStateSet.AddState( AccessibleStateType::MANAGES_DESCENDANTS );
485 			    break;
486 
487             case TCTYPE_TABLECELL:
488 			    {
489                     rStateSet.AddState( AccessibleStateType::FOCUSABLE );
490                     if ( HasChildPathFocus() )
491 	                    rStateSet.AddState( AccessibleStateType::FOCUSED );
492                     rStateSet.AddState( AccessibleStateType::ACTIVE );
493 				    rStateSet.AddState( AccessibleStateType::TRANSIENT );
494 				    rStateSet.AddState( AccessibleStateType::SELECTABLE);
495                     rStateSet.AddState( AccessibleStateType::VISIBLE );
496                     rStateSet.AddState( AccessibleStateType::SHOWING );
497                     if ( IsRowSelected( GetCurrentRow() ) )
498                         // Hmm? Wouldn't we expect the affected row to be a parameter to this function?
499 					    rStateSet.AddState( AccessibleStateType::SELECTED );
500 			    }
501 			    break;
502 
503             case TCTYPE_ROWHEADERCELL:
504 			    rStateSet.AddState( AccessibleStateType::VISIBLE );
505 			    rStateSet.AddState( AccessibleStateType::TRANSIENT );
506 			    break;
507 
508             case TCTYPE_COLUMNHEADERCELL:
509 			    rStateSet.AddState( AccessibleStateType::VISIBLE );
510 			    break;
511 	    }
512     }
513 
514     //------------------------------------------------------------------------------------------------------------------
515     void TableControl::commitCellEventIfAccessibleAlive( sal_Int16 const i_eventID, const Any& i_newValue, const Any& i_oldValue )
516     {
517         if ( m_pImpl->isAccessibleAlive() )
518             m_pImpl->commitCellEvent( i_eventID, i_newValue, i_oldValue );
519     }
520 
521     //------------------------------------------------------------------------------------------------------------------
522     void TableControl::commitTableEventIfAccessibleAlive( sal_Int16 const i_eventID, const Any& i_newValue, const Any& i_oldValue )
523     {
524         if ( m_pImpl->isAccessibleAlive() )
525             m_pImpl->commitTableEvent( i_eventID, i_newValue, i_oldValue );
526     }
527 
528     //------------------------------------------------------------------------------------------------------------------
529     Rectangle TableControl::GetWindowExtentsRelative( Window *pRelativeWindow ) const
530     {
531 	    return Control::GetWindowExtentsRelative( pRelativeWindow );
532     }
533 
534     //------------------------------------------------------------------------------------------------------------------
535     void TableControl::GrabFocus()
536     {
537 	    Control::GrabFocus();
538     }
539 
540     //------------------------------------------------------------------------------------------------------------------
541     Reference< XAccessible > TableControl::GetAccessible( sal_Bool bCreate )
542     {
543 	    return Control::GetAccessible( bCreate );
544     }
545 
546     //------------------------------------------------------------------------------------------------------------------
547     Window* TableControl::GetAccessibleParentWindow() const
548     {
549 	    return Control::GetAccessibleParentWindow();
550     }
551 
552     //------------------------------------------------------------------------------------------------------------------
553     Window* TableControl::GetWindowInstance()
554     {
555 	    return this;
556     }
557 
558     //------------------------------------------------------------------------------------------------------------------
559     sal_Bool TableControl::HasRowHeader()
560     {
561 	    return GetModel()->hasRowHeaders();
562     }
563 
564     //------------------------------------------------------------------------------------------------------------------
565     sal_Bool TableControl::HasColHeader()
566     {
567 	    return GetModel()->hasColumnHeaders();
568     }
569 
570     //------------------------------------------------------------------------------------------------------------------
571     sal_Int32 TableControl::GetAccessibleControlCount() const
572     {
573         // TC_TABLE is always defined, no matter whether empty or not
574         sal_Int32 count = 1;
575 	    if ( GetModel()->hasRowHeaders() )
576 		    ++count;
577 	    if ( GetModel()->hasColumnHeaders() )
578 		    ++count;
579 	    return count;
580     }
581 
582     //------------------------------------------------------------------------------------------------------------------
583     sal_Bool TableControl::ConvertPointToControlIndex( sal_Int32& _rnIndex, const Point& _rPoint )
584     {
585 	    sal_Int32 nRow = m_pImpl->getRowAtPoint( _rPoint );
586 	    sal_Int32 nCol = m_pImpl->getColAtPoint( _rPoint );
587 	    _rnIndex = nRow * GetColumnCount() + nCol;
588         return nRow >= 0 ? sal_True : sal_False;
589     }
590 
591     //------------------------------------------------------------------------------------------------------------------
592     long TableControl::GetRowCount() const
593     {
594 	    return GetModel()->getRowCount();
595     }
596 
597     //------------------------------------------------------------------------------------------------------------------
598     long TableControl::GetColumnCount() const
599     {
600 	    return GetModel()->getColumnCount();
601     }
602 
603     //------------------------------------------------------------------------------------------------------------------
604     sal_Bool TableControl::HasRowHeader() const
605     {
606 	    return GetModel()->hasRowHeaders();
607     }
608 
609     //------------------------------------------------------------------------------------------------------------------
610     sal_Bool TableControl::ConvertPointToCellAddress( sal_Int32& _rnRow, sal_Int32& _rnColPos, const Point& _rPoint )
611     {
612 	    _rnRow = m_pImpl->getRowAtPoint( _rPoint );
613 	    _rnColPos = m_pImpl->getColAtPoint( _rPoint );
614 	    return _rnRow >= 0 ? sal_True : sal_False;
615     }
616 
617     //------------------------------------------------------------------------------------------------------------------
618     void TableControl::FillAccessibleStateSetForCell( ::utl::AccessibleStateSetHelper& _rStateSet, sal_Int32 _nRow, sal_uInt16 _nColumnPos ) const
619     {
620         if ( IsRowSelected( _nRow ) )
621             _rStateSet.AddState( AccessibleStateType::SELECTED );
622 	    if ( HasChildPathFocus() )
623 		    _rStateSet.AddState( AccessibleStateType::FOCUSED );
624 	    else // only transient when column is not focused
625 		    _rStateSet.AddState( AccessibleStateType::TRANSIENT );
626 
627         _rStateSet.AddState( AccessibleStateType::VISIBLE );
628         _rStateSet.AddState( AccessibleStateType::SHOWING );
629         _rStateSet.AddState( AccessibleStateType::ENABLED );
630         _rStateSet.AddState( AccessibleStateType::SENSITIVE );
631         _rStateSet.AddState( AccessibleStateType::ACTIVE );
632 
633         (void)_nColumnPos;
634     }
635 
636     //------------------------------------------------------------------------------------------------------------------
637     Rectangle TableControl::GetFieldCharacterBounds(sal_Int32 _nRow,sal_Int32 _nColumnPos,sal_Int32 nIndex)
638     {
639 	    (void)_nRow;
640 	    (void)_nColumnPos;
641 	    return GetCharacterBounds(nIndex);
642     }
643 
644     //------------------------------------------------------------------------------------------------------------------
645     sal_Int32 TableControl::GetFieldIndexAtPoint(sal_Int32 _nRow,sal_Int32 _nColumnPos,const Point& _rPoint)
646     {
647 	    (void)_nRow;
648 	    (void)_nColumnPos;
649 	    return GetIndexForPoint(_rPoint);
650     }
651 
652     //------------------------------------------------------------------------------------------------------------------
653     Rectangle TableControl::calcHeaderRect(sal_Bool _bIsColumnBar,sal_Bool _bOnScreen)
654     {
655 	    (void)_bOnScreen;
656         return m_pImpl->calcHeaderRect( _bIsColumnBar ? false : true );
657     }
658 
659     //------------------------------------------------------------------------------------------------------------------
660     Rectangle TableControl::calcHeaderCellRect( sal_Bool _bIsColumnBar, sal_Int32 nPos )
661     {
662         return m_pImpl->calcHeaderCellRect( _bIsColumnBar, nPos );
663     }
664 
665     //------------------------------------------------------------------------------------------------------------------
666     Rectangle TableControl::calcTableRect(sal_Bool _bOnScreen)
667     {
668 	    (void)_bOnScreen;
669 	    return m_pImpl->calcTableRect();
670     }
671 
672     //------------------------------------------------------------------------------------------------------------------
673     Rectangle TableControl::calcCellRect( sal_Int32 _nRowPos, sal_Int32 _nColPos )
674     {
675         return m_pImpl->calcCellRect( _nRowPos, _nColPos );
676     }
677     //------------------------------------------------------------------------------------------------------------------
678     IMPL_LINK( TableControl, ImplSelectHdl, void*, EMPTYARG )
679     {
680 	    Select();
681 	    return 1;
682     }
683 
684     //------------------------------------------------------------------------------------------------------------------
685     void TableControl::Select()
686     {
687         ImplCallEventListenersAndHandler( VCLEVENT_TABLEROW_SELECT, m_pImpl->getSelectHandler(), this );
688 
689         if ( m_pImpl->isAccessibleAlive() )
690         {
691             m_pImpl->commitAccessibleEvent( AccessibleEventId::SELECTION_CHANGED, Any(), Any() );
692 
693             m_pImpl->commitTableEvent( AccessibleEventId::ACTIVE_DESCENDANT_CHANGED, Any(), Any() );
694                 // TODO: why do we notify this when the *selection* changed? Shouldn't we find a better place for this,
695                 // actually, when the active descendant, i.e. the current cell, *really* changed?
696         }
697     }
698 
699     //------------------------------------------------------------------------------------------------------------------
700     void TableControl::SetSelectHdl( const Link& i_selectHandler )
701     {
702         m_pImpl->setSelectHandler( i_selectHandler );
703     }
704 
705     //------------------------------------------------------------------------------------------------------------------
706     const Link& TableControl::GetSelectHdl() const
707     {
708         return m_pImpl->getSelectHandler();
709     }
710 
711 //......................................................................................................................
712 }} // namespace svt::table
713 //......................................................................................................................
714