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: AccessibleEditObject.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_sc.hxx"
33 #include "AccessibleEditObject.hxx"
34 #include "scitems.hxx"
35 #include <svx/eeitem.hxx>
36 #include "unoguard.hxx"
37 #include "AccessibleText.hxx"
38 #include "editsrc.hxx"
40 #include "inputhdl.hxx"
42 #ifndef _UTL_ACCESSIBLESTATESETHELPER_HXX
43 #include <unotools/accessiblestatesethelper.hxx>
45 #ifndef _COM_SUN_STAR_ACCESSIBILITY_XACCESSIBLEROLE_HPP_
46 #include <com/sun/star/accessibility/AccessibleRole.hpp>
48 #ifndef _COM_SUN_STAR_ACCESSIBILITY_XACCESSIBLESTATETYPE_HPP_
49 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
52 #include <tools/debug.hxx>
53 #include <svx/AccessibleTextHelper.hxx>
54 #include <svx/editview.hxx>
55 #include <svx/editeng.hxx>
56 #include <svx/svdmodel.hxx>
58 using namespace ::com::sun::star
;
59 using namespace ::com::sun::star::accessibility
;
61 //===== internal ============================================================
63 ScAccessibleEditObject::ScAccessibleEditObject(
64 const uno::Reference
<XAccessible
>& rxParent
,
65 EditView
* pEditView
, Window
* pWin
, const rtl::OUString
& rName
,
66 const rtl::OUString
& rDescription
, EditObjectType eObjectType
)
68 ScAccessibleContextBase(rxParent
, AccessibleRole::TEXT_FRAME
),
70 mpEditView(pEditView
),
72 meObjectType(eObjectType
),
77 SetDescription(rDescription
);
80 ScAccessibleEditObject::~ScAccessibleEditObject()
82 if (!ScAccessibleContextBase::IsDefunc() && !rBHelper
.bInDispose
)
84 // increment refcount to prevent double call off dtor
85 osl_incrementInterlockedCount( &m_refCount
);
86 // call dispose to inform object wich have a weak reference to this object
91 void SAL_CALL
ScAccessibleEditObject::disposing()
95 DELETEZ(mpTextHelper
);
97 ScAccessibleContextBase::disposing();
100 void ScAccessibleEditObject::LostFocus()
102 mbHasFocus
= sal_False
;
104 mpTextHelper
->SetFocus(sal_False
);
108 void ScAccessibleEditObject::GotFocus()
110 mbHasFocus
= sal_True
;
113 mpTextHelper
->SetFocus(sal_True
);
116 //===== XAccessibleComponent ============================================
118 uno::Reference
< XAccessible
> SAL_CALL
ScAccessibleEditObject::getAccessibleAtPoint(
119 const awt::Point
& rPoint
)
120 throw (uno::RuntimeException
)
122 uno::Reference
<XAccessible
> xRet
;
123 if (containsPoint(rPoint
))
131 xRet
= mpTextHelper
->GetAt(rPoint
);
137 Rectangle
ScAccessibleEditObject::GetBoundingBoxOnScreen(void) const
138 throw (uno::RuntimeException
)
140 Rectangle aScreenBounds
;
144 if ( meObjectType
== CellInEditMode
)
146 if ( mpEditView
&& mpEditView
->GetEditEngine() )
148 MapMode
aMapMode( mpEditView
->GetEditEngine()->GetRefMapMode() );
149 aScreenBounds
= mpWindow
->LogicToPixel( mpEditView
->GetOutputArea(), aMapMode
);
150 Point aCellLoc
= aScreenBounds
.TopLeft();
151 Rectangle aWindowRect
= mpWindow
->GetWindowExtentsRelative( NULL
);
152 Point aWindowLoc
= aWindowRect
.TopLeft();
153 Point
aPos( aCellLoc
.getX() + aWindowLoc
.getX(), aCellLoc
.getY() + aWindowLoc
.getY() );
154 aScreenBounds
.SetPos( aPos
);
159 aScreenBounds
= mpWindow
->GetWindowExtentsRelative( NULL
);
163 return aScreenBounds
;
166 Rectangle
ScAccessibleEditObject::GetBoundingBox(void) const
167 throw (uno::RuntimeException
)
169 Rectangle
aBounds( GetBoundingBoxOnScreen() );
173 uno::Reference
< XAccessible
> xThis( mpWindow
->GetAccessible() );
176 uno::Reference
< XAccessibleContext
> xContext( xThis
->getAccessibleContext() );
179 uno::Reference
< XAccessible
> xParent( xContext
->getAccessibleParent() );
182 uno::Reference
< XAccessibleComponent
> xParentComponent( xParent
->getAccessibleContext(), uno::UNO_QUERY
);
183 if ( xParentComponent
.is() )
185 Point aScreenLoc
= aBounds
.TopLeft();
186 awt::Point aParentScreenLoc
= xParentComponent
->getLocationOnScreen();
187 Point
aPos( aScreenLoc
.getX() - aParentScreenLoc
.X
, aScreenLoc
.getY() - aParentScreenLoc
.Y
);
188 aBounds
.SetPos( aPos
);
198 //===== XAccessibleContext ==============================================
201 ScAccessibleEditObject::getAccessibleChildCount(void)
202 throw (uno::RuntimeException
)
208 return mpTextHelper
->GetChildCount();
211 uno::Reference
< XAccessible
> SAL_CALL
212 ScAccessibleEditObject::getAccessibleChild(sal_Int32 nIndex
)
213 throw (uno::RuntimeException
,
214 lang::IndexOutOfBoundsException
)
220 return mpTextHelper
->GetChild(nIndex
);
223 uno::Reference
<XAccessibleStateSet
> SAL_CALL
224 ScAccessibleEditObject::getAccessibleStateSet(void)
225 throw (uno::RuntimeException
)
228 uno::Reference
<XAccessibleStateSet
> xParentStates
;
229 if (getAccessibleParent().is())
231 uno::Reference
<XAccessibleContext
> xParentContext
= getAccessibleParent()->getAccessibleContext();
232 xParentStates
= xParentContext
->getAccessibleStateSet();
234 utl::AccessibleStateSetHelper
* pStateSet
= new utl::AccessibleStateSetHelper();
235 if (IsDefunc(xParentStates
))
236 pStateSet
->AddState(AccessibleStateType::DEFUNC
);
239 // all states are const, because this object exists only in one state
240 pStateSet
->AddState(AccessibleStateType::EDITABLE
);
241 pStateSet
->AddState(AccessibleStateType::ENABLED
);
242 pStateSet
->AddState(AccessibleStateType::SENSITIVE
);
243 pStateSet
->AddState(AccessibleStateType::MULTI_LINE
);
244 pStateSet
->AddState(AccessibleStateType::MULTI_SELECTABLE
);
245 pStateSet
->AddState(AccessibleStateType::SHOWING
);
246 pStateSet
->AddState(AccessibleStateType::VISIBLE
);
251 ::rtl::OUString SAL_CALL
252 ScAccessibleEditObject::createAccessibleDescription(void)
253 throw (uno::RuntimeException
)
255 // DBG_ERRORFILE("Should never be called, because is set in the constructor.")
256 return rtl::OUString();
259 ::rtl::OUString SAL_CALL
260 ScAccessibleEditObject::createAccessibleName(void)
261 throw (uno::RuntimeException
)
263 DBG_ERRORFILE("Should never be called, because is set in the constructor.");
264 return rtl::OUString();
267 ///===== XAccessibleEventBroadcaster =====================================
270 ScAccessibleEditObject::addEventListener(const uno::Reference
<XAccessibleEventListener
>& xListener
)
271 throw (uno::RuntimeException
)
276 mpTextHelper
->AddEventListener(xListener
);
278 ScAccessibleContextBase::addEventListener(xListener
);
282 ScAccessibleEditObject::removeEventListener(const uno::Reference
<XAccessibleEventListener
>& xListener
)
283 throw (uno::RuntimeException
)
288 mpTextHelper
->RemoveEventListener(xListener
);
290 ScAccessibleContextBase::removeEventListener(xListener
);
293 //===== XServiceInfo ====================================================
295 ::rtl::OUString SAL_CALL
ScAccessibleEditObject::getImplementationName(void)
296 throw (uno::RuntimeException
)
298 return rtl::OUString(RTL_CONSTASCII_USTRINGPARAM ("ScAccessibleEditObject"));
301 //===== XTypeProvider =======================================================
303 uno::Sequence
<sal_Int8
> SAL_CALL
304 ScAccessibleEditObject::getImplementationId(void)
305 throw (uno::RuntimeException
)
309 static uno::Sequence
<sal_Int8
> aId
;
310 if (aId
.getLength() == 0)
313 rtl_createUuid (reinterpret_cast<sal_uInt8
*>(aId
.getArray()), 0, sal_True
);
318 //==== internal =========================================================
320 sal_Bool
ScAccessibleEditObject::IsDefunc(
321 const uno::Reference
<XAccessibleStateSet
>& rxParentStates
)
323 return ScAccessibleContextBase::IsDefunc() || !getAccessibleParent().is() ||
324 (rxParentStates
.is() && rxParentStates
->contains(AccessibleStateType::DEFUNC
));
327 void ScAccessibleEditObject::CreateTextHelper()
331 ::std::auto_ptr
< ScAccessibleTextData
> pAccessibleTextData
;
332 if (meObjectType
== CellInEditMode
|| meObjectType
== EditControl
)
334 pAccessibleTextData
.reset
335 (new ScAccessibleEditObjectTextData(mpEditView
, mpWindow
));
339 pAccessibleTextData
.reset
340 (new ScAccessibleEditLineTextData(NULL
, mpWindow
));
343 ::std::auto_ptr
< SvxEditSource
> pEditSource (new ScAccessibilityEditSource(pAccessibleTextData
));
344 mpTextHelper
= new ::accessibility::AccessibleTextHelper(pEditSource
);
345 mpTextHelper
->SetEventSource(this);
346 mpTextHelper
->SetFocus(mbHasFocus
);
348 // #i54814# activate cell in edit mode
349 if( meObjectType
== CellInEditMode
)
351 // do not activate cell object, if top edit line is active
352 const ScInputHandler
* pInputHdl
= SC_MOD()->GetInputHdl();
353 if( pInputHdl
&& !pInputHdl
->IsTopMode() )
355 SdrHint
aHint( HINT_BEGEDIT
);
356 mpTextHelper
->GetEditSource().GetBroadcaster().Broadcast( aHint
);