1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_sc.hxx" 26 27 28 #include "AccessibleDocument.hxx" 29 #include "AccessibleSpreadsheet.hxx" 30 #include "tabvwsh.hxx" 31 #include "AccessibilityHints.hxx" 32 #include "document.hxx" 33 #include "drwlayer.hxx" 34 #include "unoguard.hxx" 35 #include "shapeuno.hxx" 36 #include "DrawModelBroadcaster.hxx" 37 #include "drawview.hxx" 38 #include "gridwin.hxx" 39 #include "AccessibleEditObject.hxx" 40 #include "scresid.hxx" 41 #ifndef SC_SC_HRC 42 #include "sc.hrc" 43 #endif 44 #include <com/sun/star/accessibility/AccessibleEventId.hpp> 45 #ifndef _COM_SUN_STAR_ACCESSIBILITY_XACCESSIBLESTATETYPE_HPP_ 46 #include <com/sun/star/accessibility/AccessibleStateType.hpp> 47 #endif 48 #ifndef _COM_SUN_STAR_ACCESSIBILITY_XACCESSIBLERELATIONTYPE_HPP_ 49 #include <com/sun/star/accessibility/AccessibleRelationType.hpp> 50 #endif 51 #include <com/sun/star/view/XSelectionSupplier.hpp> 52 #include <com/sun/star/drawing/XShape.hpp> 53 #include <com/sun/star/drawing/XShapes.hpp> 54 55 #ifndef _UTL_ACCESSIBLESTATESETHELPER_HXX 56 #include <unotools/accessiblestatesethelper.hxx> 57 #endif 58 #include <tools/debug.hxx> 59 #include <tools/gen.hxx> 60 #include <svx/svdpage.hxx> 61 #include <svx/svdobj.hxx> 62 #include <svx/ShapeTypeHandler.hxx> 63 #include <svx/AccessibleShape.hxx> 64 #include <svx/AccessibleShapeTreeInfo.hxx> 65 #include <svx/AccessibleShapeInfo.hxx> 66 #include <comphelper/sequence.hxx> 67 #include <sfx2/viewfrm.hxx> 68 #include <svx/unoshcol.hxx> 69 #include <svx/unoshape.hxx> 70 #include <unotools/accessiblerelationsethelper.hxx> 71 #include <toolkit/helper/convert.hxx> 72 73 //IAccessibility2 Implementation 2009----- 74 #include <svx/AccessibleControlShape.hxx> 75 #include <svx/AccessibleShape.hxx> 76 #include <svx/ShapeTypeHandler.hxx> 77 #include <svx/SvxShapeTypes.hxx> 78 #include <sfx2/objsh.hxx> 79 #include <editeng/editview.hxx> 80 #include <editeng/editeng.hxx> 81 //-----IAccessibility2 Implementation 2009 82 #include <list> 83 #include <algorithm> 84 //IAccessibility2 Implementation 2009----- 85 #include "AccessibleCell.hxx" 86 87 #include "svx/unoapi.hxx" 88 #include "scmod.hxx" 89 //-----IAccessibility2 Implementation 2009 90 using namespace ::com::sun::star; 91 using namespace ::com::sun::star::accessibility; 92 using ::std::for_each; 93 94 //===== internal ======================================================== 95 96 struct ScAccessibleShapeData 97 { 98 ScAccessibleShapeData() : pAccShape(NULL), pRelationCell(NULL), bSelected(sal_False), bSelectable(sal_True) {} 99 ~ScAccessibleShapeData(); 100 mutable ::accessibility::AccessibleShape* pAccShape; 101 mutable ScAddress* pRelationCell; // if it is NULL this shape is anchored on the table 102 // SdrObject* pShape; 103 com::sun::star::uno::Reference< com::sun::star::drawing::XShape > xShape; 104 mutable sal_Bool bSelected; 105 sal_Bool bSelectable; 106 }; 107 108 ScAccessibleShapeData::~ScAccessibleShapeData() 109 { 110 if (pAccShape) 111 { 112 pAccShape->dispose(); 113 pAccShape->release(); 114 } 115 } 116 117 struct ScShapeDataLess 118 { 119 rtl::OUString msLayerId; 120 rtl::OUString msZOrder; 121 ScShapeDataLess() 122 : msLayerId(RTL_CONSTASCII_USTRINGPARAM( "LayerID" )), 123 msZOrder(RTL_CONSTASCII_USTRINGPARAM( "ZOrder" )) 124 { 125 } 126 void ConvertLayerId(sal_Int16& rLayerID) const // changes the number of the LayerId so it the accessibility order 127 { 128 switch (rLayerID) 129 { 130 case SC_LAYER_FRONT: 131 rLayerID = 1; 132 break; 133 case SC_LAYER_BACK: 134 rLayerID = 0; 135 break; 136 case SC_LAYER_INTERN: 137 rLayerID = 2; 138 break; 139 case SC_LAYER_CONTROLS: 140 rLayerID = 3; 141 break; 142 } 143 } 144 sal_Bool LessThanSheet(const ScAccessibleShapeData* pData) const 145 { 146 sal_Bool bResult(sal_False); 147 uno::Reference< beans::XPropertySet> xProps(pData->xShape, uno::UNO_QUERY); 148 if (xProps.is()) 149 { 150 uno::Any aPropAny = xProps->getPropertyValue(msLayerId); 151 sal_Int16 nLayerID = 0; 152 if( (aPropAny >>= nLayerID) ) 153 { 154 if (nLayerID == SC_LAYER_BACK) 155 bResult = sal_True; 156 } 157 } 158 return bResult; 159 } 160 sal_Bool operator()(const ScAccessibleShapeData* pData1, const ScAccessibleShapeData* pData2) const 161 { 162 sal_Bool bResult(sal_False); 163 if (pData1 && pData2) 164 { 165 uno::Reference< beans::XPropertySet> xProps1(pData1->xShape, uno::UNO_QUERY); 166 uno::Reference< beans::XPropertySet> xProps2(pData2->xShape, uno::UNO_QUERY); 167 if (xProps1.is() && xProps2.is()) 168 { 169 uno::Any aPropAny1 = xProps1->getPropertyValue(msLayerId); 170 uno::Any aPropAny2 = xProps2->getPropertyValue(msLayerId); 171 sal_Int16 nLayerID1(0); 172 sal_Int16 nLayerID2(0); 173 if( (aPropAny1 >>= nLayerID1) && (aPropAny2 >>= nLayerID2) ) 174 { 175 if (nLayerID1 == nLayerID2) 176 { 177 uno::Any aAny1 = xProps1->getPropertyValue(msZOrder); 178 sal_Int32 nZOrder1 = 0; 179 uno::Any aAny2 = xProps2->getPropertyValue(msZOrder); 180 sal_Int32 nZOrder2 = 0; 181 if ( (aAny1 >>= nZOrder1) && (aAny2 >>= nZOrder2) ) 182 bResult = (nZOrder1 < nZOrder2); 183 } 184 else 185 { 186 ConvertLayerId(nLayerID1); 187 ConvertLayerId(nLayerID2); 188 bResult = (nLayerID1 < nLayerID2); 189 } 190 } 191 } 192 } 193 else if (pData1 && !pData2) 194 bResult = LessThanSheet(pData1); 195 else if (!pData1 && pData2) 196 bResult = !LessThanSheet(pData2); 197 else 198 bResult = sal_False; 199 return bResult; 200 } 201 }; 202 203 struct DeselectShape 204 { 205 void operator() (const ScAccessibleShapeData* pAccShapeData) const 206 { 207 if (pAccShapeData) 208 { 209 pAccShapeData->bSelected = sal_False; 210 if (pAccShapeData->pAccShape) 211 pAccShapeData->pAccShape->ResetState(AccessibleStateType::SELECTED); 212 } 213 } 214 }; 215 216 struct SelectShape 217 { 218 uno::Reference < drawing::XShapes > xShapes; 219 SelectShape(uno::Reference<drawing::XShapes>& xTemp) : xShapes(xTemp) {} 220 void operator() (const ScAccessibleShapeData* pAccShapeData) const 221 { 222 if (pAccShapeData && pAccShapeData->bSelectable) 223 { 224 pAccShapeData->bSelected = sal_True; 225 if (pAccShapeData->pAccShape) 226 pAccShapeData->pAccShape->SetState(AccessibleStateType::SELECTED); 227 if (xShapes.is()) 228 xShapes->add(pAccShapeData->xShape); 229 } 230 } 231 }; 232 233 struct Destroy 234 { 235 void operator() (ScAccessibleShapeData* pData) 236 { 237 if (pData) 238 DELETEZ(pData); 239 } 240 }; 241 242 class ScChildrenShapes : public SfxListener, 243 public ::accessibility::IAccessibleParent 244 { 245 public: 246 ScChildrenShapes(ScAccessibleDocument* pAccessibleDocument, ScTabViewShell* pViewShell, ScSplitPos eSplitPos); 247 ~ScChildrenShapes(); 248 249 ///===== SfxListener ===================================================== 250 251 virtual void Notify( SfxBroadcaster& rBC, const SfxHint& rHint ); 252 253 ///===== IAccessibleParent =============================================== 254 255 virtual sal_Bool ReplaceChild ( 256 ::accessibility::AccessibleShape* pCurrentChild, 257 const ::com::sun::star::uno::Reference< ::com::sun::star::drawing::XShape >& _rxShape, 258 const long _nIndex, 259 const ::accessibility::AccessibleShapeTreeInfo& _rShapeTreeInfo 260 ) throw (::com::sun::star::uno::RuntimeException); 261 262 //IAccessibility2 Implementation 2009----- 263 virtual ::accessibility::AccessibleControlShape* GetAccControlShapeFromModel 264 (::com::sun::star::beans::XPropertySet* pSet) 265 throw (::com::sun::star::uno::RuntimeException); 266 virtual ::com::sun::star::uno::Reference< 267 ::com::sun::star::accessibility::XAccessible> 268 GetAccessibleCaption (const ::com::sun::star::uno::Reference< 269 ::com::sun::star::drawing::XShape>& xShape) 270 throw (::com::sun::star::uno::RuntimeException); 271 //-----IAccessibility2 Implementation 2009 272 ///===== Internal ======================================================== 273 void SetDrawBroadcaster(); 274 275 sal_Int32 GetCount() const; 276 uno::Reference< XAccessible > Get(const ScAccessibleShapeData* pData) const; 277 uno::Reference< XAccessible > Get(sal_Int32 nIndex) const; 278 uno::Reference< XAccessible > GetAt(const awt::Point& rPoint) const; 279 280 // gets the index of the shape starting on 0 (without the index of the table) 281 // returns the selected shape 282 sal_Bool IsSelected(sal_Int32 nIndex, 283 com::sun::star::uno::Reference<com::sun::star::drawing::XShape>& rShape) const; 284 285 sal_Bool SelectionChanged(); 286 287 void Select(sal_Int32 nIndex); 288 void DeselectAll(); // deselect also the table 289 void SelectAll(); 290 sal_Int32 GetSelectedCount() const; 291 uno::Reference< XAccessible > GetSelected(sal_Int32 nSelectedChildIndex, sal_Bool bTabSelected) const; 292 void Deselect(sal_Int32 nChildIndex); 293 294 SdrPage* GetDrawPage() const; 295 296 utl::AccessibleRelationSetHelper* GetRelationSet(const ScAddress* pAddress) const; 297 298 void VisAreaChanged() const; 299 private: 300 typedef std::vector<ScAccessibleShapeData*> SortedShapes; 301 302 mutable SortedShapes maZOrderedShapes; // a null pointer represents the sheet in the correct order 303 304 mutable ::accessibility::AccessibleShapeTreeInfo maShapeTreeInfo; 305 mutable com::sun::star::uno::Reference<com::sun::star::view::XSelectionSupplier> xSelectionSupplier; 306 mutable sal_uInt32 mnSdrObjCount; 307 mutable sal_uInt32 mnShapesSelected; 308 ScTabViewShell* mpViewShell; 309 ScAccessibleDocument* mpAccessibleDocument; 310 ScSplitPos meSplitPos; 311 312 void FillShapes(std::vector < uno::Reference < drawing::XShape > >& rShapes) const; 313 sal_Bool FindSelectedShapesChanges(const com::sun::star::uno::Reference<com::sun::star::drawing::XShapes>& xShapes, sal_Bool bCommitChange) const; 314 void FillSelectionSupplier() const; 315 316 ScAddress* GetAnchor(const uno::Reference<drawing::XShape>& xShape) const; 317 uno::Reference<XAccessibleRelationSet> GetRelationSet(const ScAccessibleShapeData* pData) const; 318 void CheckWhetherAnchorChanged(const uno::Reference<drawing::XShape>& xShape) const; 319 void SetAnchor(const uno::Reference<drawing::XShape>& xShape, ScAccessibleShapeData* pData) const; 320 void AddShape(const uno::Reference<drawing::XShape>& xShape, sal_Bool bCommitChange) const; 321 void RemoveShape(const uno::Reference<drawing::XShape>& xShape) const; 322 323 sal_Bool FindShape(const uno::Reference<drawing::XShape>& xShape, SortedShapes::iterator& rItr) const; 324 325 sal_Int8 Compare(const ScAccessibleShapeData* pData1, 326 const ScAccessibleShapeData* pData2) const; 327 }; 328 329 ScChildrenShapes::ScChildrenShapes(ScAccessibleDocument* pAccessibleDocument, ScTabViewShell* pViewShell, ScSplitPos eSplitPos) 330 : 331 mnShapesSelected(0), 332 mpViewShell(pViewShell), 333 mpAccessibleDocument(pAccessibleDocument), 334 meSplitPos(eSplitPos) 335 { 336 FillSelectionSupplier(); 337 maZOrderedShapes.push_back(NULL); // add an element which represents the table 338 339 GetCount(); // fill list with filtered shapes (no internal shapes) 340 341 if (mnShapesSelected) 342 { 343 //set flag on every selected shape 344 if (!xSelectionSupplier.is()) 345 throw uno::RuntimeException(); 346 347 uno::Reference<drawing::XShapes> xShapes(xSelectionSupplier->getSelection(), uno::UNO_QUERY); 348 if (xShapes.is()) 349 FindSelectedShapesChanges(xShapes, sal_False); 350 } 351 if (pViewShell) 352 { 353 SfxBroadcaster* pDrawBC = pViewShell->GetViewData()->GetDocument()->GetDrawBroadcaster(); 354 if (pDrawBC) 355 { 356 StartListening(*pDrawBC); 357 358 maShapeTreeInfo.SetModelBroadcaster( new ScDrawModelBroadcaster(pViewShell->GetViewData()->GetDocument()->GetDrawLayer()) ); 359 maShapeTreeInfo.SetSdrView(pViewShell->GetViewData()->GetScDrawView()); 360 maShapeTreeInfo.SetController(NULL); 361 maShapeTreeInfo.SetWindow(pViewShell->GetWindowByPos(meSplitPos)); 362 maShapeTreeInfo.SetViewForwarder(mpAccessibleDocument); 363 } 364 } 365 } 366 367 ScChildrenShapes::~ScChildrenShapes() 368 { 369 std::for_each(maZOrderedShapes.begin(), maZOrderedShapes.end(), Destroy()); 370 if (mpViewShell) 371 { 372 SfxBroadcaster* pDrawBC = mpViewShell->GetViewData()->GetDocument()->GetDrawBroadcaster(); 373 if (pDrawBC) 374 EndListening(*pDrawBC); 375 } 376 } 377 378 void ScChildrenShapes::SetDrawBroadcaster() 379 { 380 if (mpViewShell) 381 { 382 SfxBroadcaster* pDrawBC = mpViewShell->GetViewData()->GetDocument()->GetDrawBroadcaster(); 383 if (pDrawBC) 384 { 385 StartListening(*pDrawBC, sal_True); 386 387 maShapeTreeInfo.SetModelBroadcaster( new ScDrawModelBroadcaster(mpViewShell->GetViewData()->GetDocument()->GetDrawLayer()) ); 388 maShapeTreeInfo.SetSdrView(mpViewShell->GetViewData()->GetScDrawView()); 389 maShapeTreeInfo.SetController(NULL); 390 maShapeTreeInfo.SetWindow(mpViewShell->GetWindowByPos(meSplitPos)); 391 maShapeTreeInfo.SetViewForwarder(mpAccessibleDocument); 392 } 393 } 394 } 395 396 void ScChildrenShapes::Notify(SfxBroadcaster&, const SfxHint& rHint) 397 { 398 if ( rHint.ISA( SdrHint ) ) 399 { 400 const SdrHint* pSdrHint = PTR_CAST( SdrHint, &rHint ); 401 if (pSdrHint) 402 { 403 SdrObject* pObj = const_cast<SdrObject*>(pSdrHint->GetObject()); 404 if (pObj && /*(pObj->GetLayer() != SC_LAYER_INTERN) && */(pObj->GetPage() == GetDrawPage()) && 405 (pObj->GetPage() == pObj->GetObjList()) ) //#108480# only do something if the object lies direct on the page 406 { 407 switch (pSdrHint->GetKind()) 408 { 409 case HINT_OBJCHG : // Objekt geaendert 410 { 411 uno::Reference<drawing::XShape> xShape (pObj->getUnoShape(), uno::UNO_QUERY); 412 if (xShape.is()) 413 { 414 ScShapeDataLess aLess; 415 std::sort(maZOrderedShapes.begin(), maZOrderedShapes.end(), aLess); // sort, because the z index or layer could be changed 416 CheckWhetherAnchorChanged(xShape); 417 } 418 } 419 break; 420 case HINT_OBJINSERTED : // Neues Zeichenobjekt eingefuegt 421 { 422 uno::Reference<drawing::XShape> xShape (pObj->getUnoShape(), uno::UNO_QUERY); 423 if (xShape.is()) 424 AddShape(xShape, sal_True); 425 } 426 break; 427 case HINT_OBJREMOVED : // Zeichenobjekt aus Liste entfernt 428 { 429 uno::Reference<drawing::XShape> xShape (pObj->getUnoShape(), uno::UNO_QUERY); 430 if (xShape.is()) 431 RemoveShape(xShape); 432 } 433 break; 434 default : 435 { 436 // other events are not interesting 437 } 438 break; 439 } 440 } 441 } 442 } 443 } 444 445 sal_Bool ScChildrenShapes::ReplaceChild (::accessibility::AccessibleShape* pCurrentChild, 446 const ::com::sun::star::uno::Reference< ::com::sun::star::drawing::XShape >& _rxShape, 447 const long _nIndex, const ::accessibility::AccessibleShapeTreeInfo& _rShapeTreeInfo) 448 throw (uno::RuntimeException) 449 { 450 // create the new child 451 ::accessibility::AccessibleShape* pReplacement = ::accessibility::ShapeTypeHandler::Instance().CreateAccessibleObject ( 452 ::accessibility::AccessibleShapeInfo ( _rxShape, pCurrentChild->getAccessibleParent(), this, _nIndex ), 453 _rShapeTreeInfo 454 ); 455 ::com::sun::star::uno::Reference< ::com::sun::star::accessibility::XAccessible > xNewChild( pReplacement ); // keep this alive (do this before calling Init!) 456 if ( pReplacement ) 457 pReplacement->Init(); 458 459 sal_Bool bResult(sal_False); 460 if (pCurrentChild && pReplacement) 461 { 462 DBG_ASSERT(pCurrentChild->GetXShape().get() == pReplacement->GetXShape().get(), "XShape changes and should be inserted sorted"); 463 SortedShapes::iterator aItr; 464 FindShape(pCurrentChild->GetXShape(), aItr); 465 if (aItr != maZOrderedShapes.end() && (*aItr)) 466 { 467 if ((*aItr)->pAccShape) 468 { 469 DBG_ASSERT((*aItr)->pAccShape == pCurrentChild, "wrong child found"); 470 AccessibleEventObject aEvent; 471 aEvent.EventId = AccessibleEventId::CHILD; 472 aEvent.Source = uno::Reference< XAccessibleContext >(mpAccessibleDocument); 473 aEvent.OldValue <<= uno::makeAny(uno::Reference<XAccessible>(pCurrentChild)); 474 475 mpAccessibleDocument->CommitChange(aEvent); // child is gone - event 476 477 pCurrentChild->dispose(); 478 } 479 (*aItr)->pAccShape = pReplacement; 480 AccessibleEventObject aEvent; 481 aEvent.EventId = AccessibleEventId::CHILD; 482 aEvent.Source = uno::Reference< XAccessibleContext >(mpAccessibleDocument); 483 aEvent.NewValue <<= uno::makeAny(uno::Reference<XAccessible>(pReplacement)); 484 485 mpAccessibleDocument->CommitChange(aEvent); // child is new - event 486 bResult = sal_True; 487 } 488 } 489 return bResult; 490 } 491 492 //IAccessibility2 Implementation 2009----- 493 ::accessibility::AccessibleControlShape * ScChildrenShapes::GetAccControlShapeFromModel(::com::sun::star::beans::XPropertySet* pSet) throw (::com::sun::star::uno::RuntimeException) 494 { 495 sal_Int32 count = GetCount(); 496 for (sal_Int32 index=0;index<count;index++) 497 { 498 ScAccessibleShapeData* pShape = maZOrderedShapes[index]; 499 if (pShape) 500 { 501 ::accessibility::AccessibleShape* pAccShape = pShape->pAccShape; 502 if (pAccShape && ::accessibility::ShapeTypeHandler::Instance().GetTypeId (pAccShape->GetXShape()) == ::accessibility::DRAWING_CONTROL) 503 { 504 ::accessibility::AccessibleControlShape *pCtlAccShape = static_cast < ::accessibility::AccessibleControlShape* >(pAccShape); 505 if (pCtlAccShape && pCtlAccShape->GetControlModel() == pSet) 506 return pCtlAccShape; 507 } 508 } 509 } 510 return NULL; 511 } 512 ::com::sun::star::uno::Reference < ::com::sun::star::accessibility::XAccessible > 513 ScChildrenShapes::GetAccessibleCaption (const ::com::sun::star::uno::Reference < ::com::sun::star::drawing::XShape>& xShape) 514 throw (::com::sun::star::uno::RuntimeException) 515 { 516 sal_Int32 count = GetCount(); 517 for (sal_Int32 index=0;index<count;index++) 518 { 519 ScAccessibleShapeData* pShape = maZOrderedShapes[index]; 520 if (pShape && pShape->xShape == xShape ) 521 { 522 ::com::sun::star::uno::Reference< ::com::sun::star::accessibility::XAccessible > xNewChild( pShape->pAccShape ); 523 // uno::Reference<XAccessible> xNewChild( pShape->pAccShape , uno::UNO_QUERY ); 524 if(xNewChild.get()) 525 return xNewChild; 526 } 527 } 528 return NULL; 529 } 530 //-----IAccessibility2 Implementation 2009 531 sal_Int32 ScChildrenShapes::GetCount() const 532 { 533 SdrPage* pDrawPage = GetDrawPage(); 534 if (pDrawPage && (maZOrderedShapes.size() == 1)) // the table is always in 535 { 536 mnSdrObjCount = pDrawPage->GetObjCount(); 537 maZOrderedShapes.reserve(mnSdrObjCount + 1); // the table is always in 538 for (sal_uInt32 i = 0; i < mnSdrObjCount; ++i) 539 { 540 SdrObject* pObj = pDrawPage->GetObj(i); 541 if (pObj/* && (pObj->GetLayer() != SC_LAYER_INTERN)*/) 542 { 543 uno::Reference< drawing::XShape > xShape (pObj->getUnoShape(), uno::UNO_QUERY); 544 AddShape(xShape, sal_False); //inserts in the correct order 545 } 546 } 547 } 548 return maZOrderedShapes.size(); 549 } 550 551 uno::Reference< XAccessible > ScChildrenShapes::Get(const ScAccessibleShapeData* pData) const 552 { 553 if (!pData) 554 return NULL; 555 556 if (!pData->pAccShape) 557 { 558 ::accessibility::ShapeTypeHandler& rShapeHandler = ::accessibility::ShapeTypeHandler::Instance(); 559 ::accessibility::AccessibleShapeInfo aShapeInfo(pData->xShape, mpAccessibleDocument, const_cast<ScChildrenShapes*>(this)); 560 pData->pAccShape = rShapeHandler.CreateAccessibleObject( 561 aShapeInfo, maShapeTreeInfo); 562 if (pData->pAccShape) 563 { 564 pData->pAccShape->acquire(); 565 pData->pAccShape->Init(); 566 if (pData->bSelected) 567 pData->pAccShape->SetState(AccessibleStateType::SELECTED); 568 if (!pData->bSelectable) 569 pData->pAccShape->ResetState(AccessibleStateType::SELECTABLE); 570 pData->pAccShape->SetRelationSet(GetRelationSet(pData)); 571 } 572 } 573 return pData->pAccShape; 574 } 575 576 uno::Reference< XAccessible > ScChildrenShapes::Get(sal_Int32 nIndex) const 577 { 578 if (maZOrderedShapes.size() <= 1) 579 GetCount(); // fill list with filtered shapes (no internal shapes) 580 581 if (static_cast<sal_uInt32>(nIndex) >= maZOrderedShapes.size()) 582 return NULL; 583 584 return Get(maZOrderedShapes[nIndex]); 585 } 586 587 uno::Reference< XAccessible > ScChildrenShapes::GetAt(const awt::Point& rPoint) const 588 { 589 uno::Reference<XAccessible> xAccessible; 590 if(mpViewShell) 591 { 592 sal_Int32 i(maZOrderedShapes.size() - 1); 593 sal_Bool bFound(sal_False); 594 while (!bFound && i >= 0) 595 { 596 ScAccessibleShapeData* pShape = maZOrderedShapes[i]; 597 if (pShape) 598 { 599 if (!pShape->pAccShape) 600 Get(pShape); 601 602 if (pShape->pAccShape) 603 { 604 Point aPoint(VCLPoint(rPoint)); 605 aPoint -= VCLRectangle(pShape->pAccShape->getBounds()).TopLeft(); 606 if (pShape->pAccShape->containsPoint(AWTPoint(aPoint))) 607 { 608 xAccessible = pShape->pAccShape; 609 bFound = sal_True; 610 } 611 } 612 else 613 { 614 DBG_ERRORFILE("I should have an accessible shape now!"); 615 } 616 } 617 else 618 bFound = sal_True; // this is the sheet and it lies before the rest of the shapes which are background shapes 619 620 --i; 621 } 622 } 623 return xAccessible; 624 } 625 626 sal_Bool ScChildrenShapes::IsSelected(sal_Int32 nIndex, 627 uno::Reference<drawing::XShape>& rShape) const 628 { 629 sal_Bool bResult (sal_False); 630 if (maZOrderedShapes.size() <= 1) 631 GetCount(); // fill list with filtered shapes (no internal shapes) 632 633 if (!xSelectionSupplier.is()) 634 throw uno::RuntimeException(); 635 636 if (!maZOrderedShapes[nIndex]) 637 return sal_False; 638 639 bResult = maZOrderedShapes[nIndex]->bSelected; 640 rShape = maZOrderedShapes[nIndex]->xShape; 641 642 #ifdef DBG_UTIL // test whether it is truly selected by a slower method 643 uno::Reference< drawing::XShape > xReturnShape; 644 sal_Bool bDebugResult(sal_False); 645 uno::Reference<container::XIndexAccess> xIndexAccess; 646 xSelectionSupplier->getSelection() >>= xIndexAccess; 647 648 if (xIndexAccess.is()) 649 { 650 sal_Int32 nCount(xIndexAccess->getCount()); 651 if (nCount) 652 { 653 uno::Reference< drawing::XShape > xShape; 654 uno::Reference< drawing::XShape > xIndexShape = maZOrderedShapes[nIndex]->xShape; 655 sal_Int32 i(0); 656 while (!bDebugResult && (i < nCount)) 657 { 658 xIndexAccess->getByIndex(i) >>= xShape; 659 if (xShape.is() && (xIndexShape.get() == xShape.get())) 660 { 661 bDebugResult = sal_True; 662 xReturnShape = xShape; 663 } 664 else 665 ++i; 666 } 667 } 668 } 669 DBG_ASSERT((bResult == bDebugResult) && ((bResult && (rShape.get() == xReturnShape.get())) || !bResult), "found the wrong shape or result"); 670 #endif 671 672 return bResult; 673 } 674 675 sal_Bool ScChildrenShapes::SelectionChanged() 676 { 677 sal_Bool bResult(sal_False); 678 if (!xSelectionSupplier.is()) 679 throw uno::RuntimeException(); 680 681 uno::Reference<drawing::XShapes> xShapes(xSelectionSupplier->getSelection(), uno::UNO_QUERY); 682 683 bResult = FindSelectedShapesChanges(xShapes, sal_True); 684 685 return bResult; 686 } 687 688 void ScChildrenShapes::Select(sal_Int32 nIndex) 689 { 690 if (maZOrderedShapes.size() <= 1) 691 GetCount(); // fill list with filtered shapes (no internal shapes) 692 693 if (!xSelectionSupplier.is()) 694 throw uno::RuntimeException(); 695 696 if (!maZOrderedShapes[nIndex]) 697 return; 698 699 uno::Reference<drawing::XShape> xShape; 700 if (!IsSelected(nIndex, xShape) && maZOrderedShapes[nIndex]->bSelectable) 701 { 702 uno::Reference<drawing::XShapes> xShapes; 703 xSelectionSupplier->getSelection() >>= xShapes; 704 705 if (!xShapes.is()) 706 xShapes = new SvxShapeCollection(); 707 708 xShapes->add(maZOrderedShapes[nIndex]->xShape); 709 710 try 711 { 712 xSelectionSupplier->select(uno::makeAny(xShapes)); 713 maZOrderedShapes[nIndex]->bSelected = sal_True; 714 if (maZOrderedShapes[nIndex]->pAccShape) 715 maZOrderedShapes[nIndex]->pAccShape->SetState(AccessibleStateType::SELECTED); 716 } 717 catch (lang::IllegalArgumentException&) 718 { 719 } 720 } 721 } 722 723 void ScChildrenShapes::DeselectAll() 724 { 725 if (!xSelectionSupplier.is()) 726 throw uno::RuntimeException(); 727 728 sal_Bool bSomethingSelected(sal_True); 729 try 730 { 731 xSelectionSupplier->select(uno::Any()); //deselects all 732 } 733 catch (lang::IllegalArgumentException&) 734 { 735 DBG_ERRORFILE("nothing selected before"); 736 bSomethingSelected = sal_False; 737 } 738 739 if (bSomethingSelected) 740 std::for_each(maZOrderedShapes.begin(), maZOrderedShapes.end(), DeselectShape()); 741 } 742 743 void ScChildrenShapes::SelectAll() 744 { 745 if (!xSelectionSupplier.is()) 746 throw uno::RuntimeException(); 747 748 if (maZOrderedShapes.size() <= 1) 749 GetCount(); // fill list with filtered shapes (no internal shapes) 750 751 if (maZOrderedShapes.size() > 1) 752 { 753 uno::Reference<drawing::XShapes> xShapes; 754 xShapes = new SvxShapeCollection(); 755 756 try 757 { 758 std::for_each(maZOrderedShapes.begin(), maZOrderedShapes.end(), SelectShape(xShapes)); 759 xSelectionSupplier->select(uno::makeAny(xShapes)); 760 } 761 catch (lang::IllegalArgumentException&) 762 { 763 SelectionChanged(); // find all selected shapes and set the flags 764 } 765 } 766 } 767 768 void ScChildrenShapes::FillShapes(std::vector < uno::Reference < drawing::XShape > >& rShapes) const 769 { 770 uno::Reference<container::XIndexAccess> xIndexAccess; 771 xSelectionSupplier->getSelection() >>= xIndexAccess; 772 773 if (xIndexAccess.is()) 774 { 775 sal_uInt32 nCount(xIndexAccess->getCount()); 776 for (sal_uInt32 i = 0; i < nCount; ++i) 777 { 778 uno::Reference<drawing::XShape> xShape; 779 xIndexAccess->getByIndex(i) >>= xShape; 780 if (xShape.is()) 781 rShapes.push_back(xShape); 782 } 783 } 784 } 785 786 sal_Int32 ScChildrenShapes::GetSelectedCount() const 787 { 788 if (!xSelectionSupplier.is()) 789 throw uno::RuntimeException(); 790 791 std::vector < uno::Reference < drawing::XShape > > aShapes; 792 FillShapes(aShapes); 793 794 return aShapes.size(); 795 } 796 797 uno::Reference< XAccessible > ScChildrenShapes::GetSelected(sal_Int32 nSelectedChildIndex, sal_Bool bTabSelected) const 798 { 799 uno::Reference< XAccessible > xAccessible; 800 801 if (maZOrderedShapes.size() <= 1) 802 GetCount(); // fill list with shapes 803 804 if (!bTabSelected) 805 { 806 std::vector < uno::Reference < drawing::XShape > > aShapes; 807 FillShapes(aShapes); 808 809 //IAccessibility2 Implementation 2009----- 810 if(aShapes.size()<=0) return xAccessible; 811 //-----IAccessibility2 Implementation 2009 812 SortedShapes::iterator aItr; 813 if (FindShape(aShapes[nSelectedChildIndex], aItr)) 814 xAccessible = Get(aItr - maZOrderedShapes.begin()); 815 } 816 else 817 { 818 SortedShapes::iterator aItr = maZOrderedShapes.begin(); 819 SortedShapes::iterator aEndItr = maZOrderedShapes.end(); 820 sal_Bool bFound(sal_False); 821 while(!bFound && aItr != aEndItr) 822 { 823 if (*aItr) 824 { 825 if ((*aItr)->bSelected) 826 { 827 if (nSelectedChildIndex == 0) 828 bFound = sal_True; 829 else 830 --nSelectedChildIndex; 831 } 832 } 833 else 834 { 835 if (nSelectedChildIndex == 0) 836 bFound = sal_True; 837 else 838 --nSelectedChildIndex; 839 } 840 if (!bFound) 841 ++aItr; 842 } 843 if (bFound && *aItr) 844 xAccessible = (*aItr)->pAccShape; 845 } 846 847 return xAccessible; 848 } 849 850 void ScChildrenShapes::Deselect(sal_Int32 nChildIndex) 851 { 852 uno::Reference<drawing::XShape> xShape; 853 if (IsSelected(nChildIndex, xShape)) // returns false if it is the sheet 854 { 855 if (xShape.is()) 856 { 857 uno::Reference<drawing::XShapes> xShapes; 858 xSelectionSupplier->getSelection() >>= xShapes; 859 if (xShapes.is()) 860 xShapes->remove(xShape); 861 862 try 863 { 864 xSelectionSupplier->select(uno::makeAny(xShapes)); 865 } 866 catch (lang::IllegalArgumentException&) 867 { 868 DBG_ERRORFILE("something not selectable"); 869 } 870 871 maZOrderedShapes[nChildIndex]->bSelected = sal_False; 872 if (maZOrderedShapes[nChildIndex]->pAccShape) 873 maZOrderedShapes[nChildIndex]->pAccShape->ResetState(AccessibleStateType::SELECTED); 874 } 875 } 876 } 877 878 879 SdrPage* ScChildrenShapes::GetDrawPage() const 880 { 881 SCTAB nTab(mpAccessibleDocument->getVisibleTable()); 882 SdrPage* pDrawPage = NULL; 883 if (mpViewShell) 884 { 885 ScDocument* pDoc = mpViewShell->GetViewData()->GetDocument(); 886 if (pDoc && pDoc->GetDrawLayer()) 887 { 888 ScDrawLayer* pDrawLayer = pDoc->GetDrawLayer(); 889 if (pDrawLayer->HasObjects() && (pDrawLayer->GetPageCount() > nTab)) 890 pDrawPage = pDrawLayer->GetPage(static_cast<sal_uInt16>(static_cast<sal_Int16>(nTab))); 891 } 892 } 893 return pDrawPage; 894 } 895 896 struct SetRelation 897 { 898 const ScChildrenShapes* mpChildrenShapes; 899 mutable utl::AccessibleRelationSetHelper* mpRelationSet; 900 const ScAddress* mpAddress; 901 SetRelation(const ScChildrenShapes* pChildrenShapes, const ScAddress* pAddress) 902 : 903 mpChildrenShapes(pChildrenShapes), 904 mpRelationSet(NULL), 905 mpAddress(pAddress) 906 { 907 } 908 void operator() (const ScAccessibleShapeData* pAccShapeData) const 909 { 910 if (pAccShapeData && 911 ((!pAccShapeData->pRelationCell && !mpAddress) || 912 (pAccShapeData->pRelationCell && mpAddress && (*(pAccShapeData->pRelationCell) == *mpAddress)))) 913 { 914 if (!mpRelationSet) 915 mpRelationSet = new utl::AccessibleRelationSetHelper(); 916 917 AccessibleRelation aRelation; 918 aRelation.TargetSet.realloc(1); 919 aRelation.TargetSet[0] = mpChildrenShapes->Get(pAccShapeData); 920 aRelation.RelationType = AccessibleRelationType::CONTROLLER_FOR; 921 922 mpRelationSet->AddRelation(aRelation); 923 } 924 } 925 }; 926 927 utl::AccessibleRelationSetHelper* ScChildrenShapes::GetRelationSet(const ScAddress* pAddress) const 928 { 929 SetRelation aSetRelation(this, pAddress); 930 ::std::for_each(maZOrderedShapes.begin(), maZOrderedShapes.end(), aSetRelation); 931 return aSetRelation.mpRelationSet; 932 } 933 934 sal_Bool ScChildrenShapes::FindSelectedShapesChanges(const uno::Reference<drawing::XShapes>& xShapes, sal_Bool /* bCommitChange */) const 935 { 936 sal_Bool bResult(sal_False); 937 SortedShapes aShapesList; 938 uno::Reference<container::XIndexAccess> xIndexAcc(xShapes, uno::UNO_QUERY); 939 if (xIndexAcc.is()) 940 { 941 mnShapesSelected = xIndexAcc->getCount(); 942 for (sal_uInt32 i = 0; i < mnShapesSelected; ++i) 943 { 944 uno::Reference< drawing::XShape > xShape; 945 xIndexAcc->getByIndex(i) >>= xShape; 946 if (xShape.is()) 947 { 948 ScAccessibleShapeData* pShapeData = new ScAccessibleShapeData(); 949 pShapeData->xShape = xShape; 950 aShapesList.push_back(pShapeData); 951 } 952 } 953 } 954 else 955 mnShapesSelected = 0; 956 //IAccessibility2 Implementation 2009----- 957 SdrObject *pFocusedObj = NULL; 958 if( mnShapesSelected == 1 && aShapesList.size() == 1) 959 { 960 pFocusedObj = GetSdrObjectFromXShape(aShapesList[0]->xShape); 961 } 962 //-----IAccessibility2 Implementation 2009 963 ScShapeDataLess aLess; 964 std::sort(aShapesList.begin(), aShapesList.end(), aLess); 965 //IAccessibility2 Implementation 2009----- 966 SortedShapes vecSelectedShapeAdd; 967 SortedShapes vecSelectedShapeRemove; 968 sal_Bool bHasSelect=sal_False; 969 //-----IAccessibility2 Implementation 2009 970 SortedShapes::iterator aXShapesItr(aShapesList.begin()); 971 SortedShapes::const_iterator aXShapesEndItr(aShapesList.end()); 972 SortedShapes::iterator aDataItr(maZOrderedShapes.begin()); 973 SortedShapes::const_iterator aDataEndItr(maZOrderedShapes.end()); 974 SortedShapes::const_iterator aFocusedItr = aDataEndItr; 975 while((aDataItr != aDataEndItr)) 976 { 977 if (*aDataItr) // is it realy a shape or only the sheet 978 { 979 sal_Int8 nComp(0); 980 if (aXShapesItr == aXShapesEndItr) 981 nComp = -1; // simulate that the Shape is lower, so the selction state will be removed 982 else 983 nComp = Compare(*aDataItr, *aXShapesItr); 984 if (nComp == 0) 985 { 986 if (!(*aDataItr)->bSelected) 987 { 988 (*aDataItr)->bSelected = sal_True; 989 if ((*aDataItr)->pAccShape) 990 { 991 (*aDataItr)->pAccShape->SetState(AccessibleStateType::SELECTED); 992 (*aDataItr)->pAccShape->ResetState(AccessibleStateType::FOCUSED); 993 bResult = sal_True; 994 //IAccessibility2 Implementation 2009----- 995 vecSelectedShapeAdd.push_back((*aDataItr)); 996 //-----IAccessibility2 Implementation 2009 997 } 998 aFocusedItr = aDataItr; 999 } 1000 //IAccessibility2 Implementation 2009----- 1001 else 1002 { 1003 bHasSelect = sal_True; 1004 } 1005 //-----IAccessibility2 Implementation 2009 1006 ++aDataItr; 1007 ++aXShapesItr; 1008 } 1009 else if (nComp < 0) 1010 { 1011 if ((*aDataItr)->bSelected) 1012 { 1013 (*aDataItr)->bSelected = sal_False; 1014 if ((*aDataItr)->pAccShape) 1015 { 1016 (*aDataItr)->pAccShape->ResetState(AccessibleStateType::SELECTED); 1017 (*aDataItr)->pAccShape->ResetState(AccessibleStateType::FOCUSED); 1018 bResult = sal_True; 1019 //IAccessibility2 Implementation 2009----- 1020 vecSelectedShapeRemove.push_back(*aDataItr); 1021 //-----IAccessibility2 Implementation 2009 1022 } 1023 } 1024 ++aDataItr; 1025 } 1026 else 1027 { 1028 DBG_ERRORFILE("here is a selected shape which is not in the childlist"); 1029 ++aXShapesItr; 1030 --mnShapesSelected; 1031 } 1032 } 1033 else 1034 ++aDataItr; 1035 } 1036 //IAccessibility2 Implementation 2009----- 1037 bool bWinFocus=false; 1038 ScGridWindow* pWin = static_cast<ScGridWindow*>(mpViewShell->GetWindowByPos(meSplitPos)); 1039 if (pWin) 1040 { 1041 bWinFocus = pWin->HasFocus(); 1042 } 1043 const SdrMarkList* pMarkList = NULL; 1044 SdrObject* pMarkedObj = NULL; 1045 SdrObject* pUpObj = NULL; 1046 sal_Bool bIsFocuseMarked = sal_True; 1047 if( mpViewShell && mnShapesSelected == 1 && bWinFocus) 1048 { 1049 ScDrawView* pScDrawView = mpViewShell->GetViewData()->GetScDrawView(); 1050 if( pScDrawView ) 1051 { 1052 if( pScDrawView->GetMarkedObjectList().GetMarkCount() == 1 ) 1053 { 1054 pMarkList = &(pScDrawView->GetMarkedObjectList()); 1055 pMarkedObj = pMarkList->GetMark(0)->GetMarkedSdrObj(); 1056 uno::Reference< drawing::XShape > xMarkedXShape (pMarkedObj->getUnoShape(), uno::UNO_QUERY); 1057 if( aFocusedItr != aDataEndItr && 1058 (*aFocusedItr)->xShape.is() && 1059 xMarkedXShape.is() && 1060 (*aFocusedItr)->xShape != xMarkedXShape ) 1061 bIsFocuseMarked = sal_False; 1062 } 1063 } 1064 } 1065 //if ((aFocusedItr != aDataEndItr) && (*aFocusedItr)->pAccShape && (mnShapesSelected == 1)) 1066 if ( bIsFocuseMarked && (aFocusedItr != aDataEndItr) && (*aFocusedItr)->pAccShape && (mnShapesSelected == 1) && bWinFocus) 1067 { 1068 (*aFocusedItr)->pAccShape->SetState(AccessibleStateType::FOCUSED); 1069 } 1070 else if( pFocusedObj && bWinFocus && pMarkList && pMarkList->GetMarkCount() == 1 && mnShapesSelected == 1 ) 1071 { 1072 if( pMarkedObj ) 1073 { 1074 uno::Reference< drawing::XShape > xMarkedXShape (pMarkedObj->getUnoShape(), uno::UNO_QUERY); 1075 pUpObj = pMarkedObj->GetUpGroup(); 1076 1077 if( pMarkedObj == pFocusedObj ) 1078 { 1079 if( pUpObj ) 1080 { 1081 uno::Reference< drawing::XShape > xUpGroupXShape (pUpObj->getUnoShape(), uno::UNO_QUERY); 1082 uno::Reference < XAccessible > xAccGroupShape = 1083 const_cast<ScChildrenShapes*>(this)->GetAccessibleCaption( xUpGroupXShape ); 1084 if( xAccGroupShape.is() ) 1085 { 1086 ::accessibility::AccessibleShape* pAccGroupShape = 1087 static_cast< ::accessibility::AccessibleShape* >(xAccGroupShape.get()); 1088 if( pAccGroupShape ) 1089 { 1090 sal_Int32 nCount = pAccGroupShape->getAccessibleChildCount(); 1091 for( sal_Int32 i = 0; i < nCount; i++ ) 1092 { 1093 uno::Reference<XAccessible> xAccShape = pAccGroupShape->getAccessibleChild(i); 1094 if (xAccShape.is()) 1095 { 1096 ::accessibility::AccessibleShape* pChildAccShape = static_cast< ::accessibility::AccessibleShape* >(xAccShape.get()); 1097 uno::Reference< drawing::XShape > xChildShape = pChildAccShape->GetXShape(); 1098 if (xChildShape == xMarkedXShape) 1099 { 1100 pChildAccShape->SetState(AccessibleStateType::FOCUSED); 1101 } 1102 else 1103 { 1104 pChildAccShape->ResetState(AccessibleStateType::FOCUSED); 1105 } 1106 } 1107 } 1108 } 1109 } 1110 } 1111 } 1112 } 1113 } 1114 if (vecSelectedShapeAdd.size() >= 10 ) 1115 { 1116 AccessibleEventObject aEvent; 1117 aEvent.EventId = AccessibleEventId::SELECTION_CHANGED_WITHIN; 1118 aEvent.Source = uno::Reference< XAccessible >(mpAccessibleDocument); 1119 mpAccessibleDocument->CommitChange(aEvent); 1120 } 1121 else 1122 { 1123 SortedShapes::iterator vi = vecSelectedShapeAdd.begin(); 1124 for (; vi != vecSelectedShapeAdd.end() ; ++vi ) 1125 { 1126 AccessibleEventObject aEvent; 1127 if (bHasSelect) 1128 { 1129 aEvent.EventId = AccessibleEventId::SELECTION_CHANGED_ADD; 1130 } 1131 else 1132 { 1133 aEvent.EventId = AccessibleEventId::SELECTION_CHANGED; 1134 } 1135 aEvent.Source = uno::Reference< XAccessible >(mpAccessibleDocument); 1136 uno::Reference< XAccessible > xChild( (*vi)->pAccShape); 1137 aEvent.NewValue <<= xChild; 1138 mpAccessibleDocument->CommitChange(aEvent); 1139 } 1140 } 1141 SortedShapes::iterator vi = vecSelectedShapeRemove.begin(); 1142 for (; vi != vecSelectedShapeRemove.end() ; ++vi ) 1143 { 1144 AccessibleEventObject aEvent; 1145 aEvent.EventId = AccessibleEventId::SELECTION_CHANGED_REMOVE; 1146 aEvent.Source = uno::Reference< XAccessible >(mpAccessibleDocument); 1147 uno::Reference< XAccessible > xChild( (*vi)->pAccShape); 1148 aEvent.NewValue <<= xChild; 1149 mpAccessibleDocument->CommitChange(aEvent); 1150 } 1151 //-----IAccessibility2 Implementation 2009 1152 std::for_each(aShapesList.begin(), aShapesList.end(), Destroy()); 1153 1154 return bResult; 1155 } 1156 1157 void ScChildrenShapes::FillSelectionSupplier() const 1158 { 1159 if (!xSelectionSupplier.is() && mpViewShell) 1160 { 1161 SfxViewFrame* pViewFrame = mpViewShell->GetViewFrame(); 1162 if (pViewFrame) 1163 { 1164 xSelectionSupplier = uno::Reference<view::XSelectionSupplier>(pViewFrame->GetFrame().GetController(), uno::UNO_QUERY); 1165 if (xSelectionSupplier.is()) 1166 { 1167 if (mpAccessibleDocument) 1168 xSelectionSupplier->addSelectionChangeListener(mpAccessibleDocument); 1169 uno::Reference<drawing::XShapes> xShapes (xSelectionSupplier->getSelection(), uno::UNO_QUERY); 1170 if (xShapes.is()) 1171 mnShapesSelected = xShapes->getCount(); 1172 } 1173 } 1174 } 1175 } 1176 1177 ScAddress* ScChildrenShapes::GetAnchor(const uno::Reference<drawing::XShape>& xShape) const 1178 { 1179 ScAddress* pAddress = NULL; 1180 if (mpViewShell) 1181 { 1182 SvxShape* pShapeImp = SvxShape::getImplementation(xShape); 1183 uno::Reference<beans::XPropertySet> xShapeProp(xShape, uno::UNO_QUERY); 1184 if (pShapeImp && xShapeProp.is()) 1185 { 1186 SdrObject *pSdrObj = pShapeImp->GetSdrObject(); 1187 if (pSdrObj) 1188 { 1189 if (ScDrawLayer::GetAnchor(pSdrObj) == SCA_CELL) 1190 { 1191 ScDocument* pDoc = mpViewShell->GetViewData()->GetDocument(); 1192 if (pDoc) 1193 { 1194 rtl::OUString sCaptionShape(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.drawing.CaptionShape")); 1195 awt::Point aPoint(xShape->getPosition()); 1196 awt::Size aSize(xShape->getSize()); 1197 rtl::OUString sType(xShape->getShapeType()); 1198 Rectangle aRectangle(aPoint.X, aPoint.Y, aPoint.X + aSize.Width, aPoint.Y + aSize.Height); 1199 if ( sType.equals(sCaptionShape) ) 1200 { 1201 awt::Point aRelativeCaptionPoint; 1202 rtl::OUString sCaptionPoint( RTL_CONSTASCII_USTRINGPARAM( "CaptionPoint" )); 1203 xShapeProp->getPropertyValue( sCaptionPoint ) >>= aRelativeCaptionPoint; 1204 Point aCoreRelativeCaptionPoint(aRelativeCaptionPoint.X, aRelativeCaptionPoint.Y); 1205 Point aCoreAbsoluteCaptionPoint(aPoint.X, aPoint.Y); 1206 aCoreAbsoluteCaptionPoint += aCoreRelativeCaptionPoint; 1207 aRectangle.Union(Rectangle(aCoreAbsoluteCaptionPoint, aCoreAbsoluteCaptionPoint)); 1208 } 1209 ScRange aRange = pDoc->GetRange(mpAccessibleDocument->getVisibleTable(), aRectangle); 1210 pAddress = new ScAddress(aRange.aStart); 1211 } 1212 } 1213 // else 1214 // do nothing, because it is always a NULL Pointer 1215 } 1216 } 1217 } 1218 1219 return pAddress; 1220 } 1221 1222 uno::Reference<XAccessibleRelationSet> ScChildrenShapes::GetRelationSet(const ScAccessibleShapeData* pData) const 1223 { 1224 utl::AccessibleRelationSetHelper* pRelationSet = new utl::AccessibleRelationSetHelper(); 1225 1226 if(pData && pRelationSet && mpAccessibleDocument) 1227 { 1228 uno::Reference<XAccessible> xAccessible = mpAccessibleDocument->GetAccessibleSpreadsheet(); // should be the current table 1229 if (pData->pRelationCell && xAccessible.is()) 1230 { 1231 uno::Reference<XAccessibleTable> xAccTable (xAccessible->getAccessibleContext(), uno::UNO_QUERY); 1232 if (xAccTable.is()) 1233 xAccessible = xAccTable->getAccessibleCellAt(pData->pRelationCell->Row(), pData->pRelationCell->Col()); 1234 } 1235 AccessibleRelation aRelation; 1236 aRelation.TargetSet.realloc(1); 1237 aRelation.TargetSet[0] = xAccessible; 1238 aRelation.RelationType = AccessibleRelationType::CONTROLLED_BY; 1239 pRelationSet->AddRelation(aRelation); 1240 } 1241 1242 return pRelationSet; 1243 } 1244 1245 void ScChildrenShapes::CheckWhetherAnchorChanged(const uno::Reference<drawing::XShape>& xShape) const 1246 { 1247 SortedShapes::iterator aItr; 1248 if (FindShape(xShape, aItr)) 1249 SetAnchor(xShape, *aItr); 1250 } 1251 1252 void ScChildrenShapes::SetAnchor(const uno::Reference<drawing::XShape>& xShape, ScAccessibleShapeData* pData) const 1253 { 1254 if (pData) 1255 { 1256 ScAddress* pAddress = GetAnchor(xShape); 1257 if ((pAddress && pData->pRelationCell && (*pAddress != *(pData->pRelationCell))) || 1258 (!pAddress && pData->pRelationCell) || (pAddress && !pData->pRelationCell)) 1259 { 1260 if (pData->pRelationCell) 1261 delete pData->pRelationCell; 1262 pData->pRelationCell = pAddress; 1263 if (pData->pAccShape) 1264 pData->pAccShape->SetRelationSet(GetRelationSet(pData)); 1265 } 1266 } 1267 } 1268 1269 void ScChildrenShapes::AddShape(const uno::Reference<drawing::XShape>& xShape, sal_Bool bCommitChange) const 1270 { 1271 SortedShapes::iterator aFindItr; 1272 if (!FindShape(xShape, aFindItr)) 1273 { 1274 ScAccessibleShapeData* pShape = new ScAccessibleShapeData(); 1275 pShape->xShape = xShape; 1276 SortedShapes::iterator aNewItr = maZOrderedShapes.insert(aFindItr, pShape); 1277 SetAnchor(xShape, pShape); 1278 1279 uno::Reference< beans::XPropertySet > xShapeProp(xShape, uno::UNO_QUERY); 1280 if (xShapeProp.is()) 1281 { 1282 uno::Any aPropAny = xShapeProp->getPropertyValue(rtl::OUString(RTL_CONSTASCII_USTRINGPARAM( "LayerID" ))); 1283 sal_Int16 nLayerID = 0; 1284 if( aPropAny >>= nLayerID ) 1285 { 1286 if( (nLayerID == SC_LAYER_INTERN) || (nLayerID == SC_LAYER_HIDDEN) ) 1287 pShape->bSelectable = sal_False; 1288 else 1289 pShape->bSelectable = sal_True; 1290 } 1291 } 1292 1293 1294 if (!xSelectionSupplier.is()) 1295 throw uno::RuntimeException(); 1296 1297 uno::Reference<container::XEnumerationAccess> xEnumAcc(xSelectionSupplier->getSelection(), uno::UNO_QUERY); 1298 if (xEnumAcc.is()) 1299 { 1300 uno::Reference<container::XEnumeration> xEnum = xEnumAcc->createEnumeration(); 1301 if (xEnum.is()) 1302 { 1303 uno::Reference<drawing::XShape> xSelectedShape; 1304 sal_Bool bFound(sal_False); 1305 while (!bFound && xEnum->hasMoreElements()) 1306 { 1307 xEnum->nextElement() >>= xSelectedShape; 1308 if (xShape.is() && (xShape.get() == xSelectedShape.get())) 1309 { 1310 pShape->bSelected = sal_True; 1311 bFound = sal_True; 1312 } 1313 } 1314 } 1315 } 1316 if (mpAccessibleDocument && bCommitChange) 1317 { 1318 AccessibleEventObject aEvent; 1319 aEvent.EventId = AccessibleEventId::CHILD; 1320 aEvent.Source = uno::Reference< XAccessibleContext >(mpAccessibleDocument); 1321 aEvent.NewValue <<= Get(aNewItr - maZOrderedShapes.begin()); 1322 1323 mpAccessibleDocument->CommitChange(aEvent); // new child - event 1324 } 1325 } 1326 else 1327 { 1328 DBG_ERRORFILE("shape is always in the list"); 1329 } 1330 } 1331 1332 void ScChildrenShapes::RemoveShape(const uno::Reference<drawing::XShape>& xShape) const 1333 { 1334 SortedShapes::iterator aItr; 1335 if (FindShape(xShape, aItr)) 1336 { 1337 if (mpAccessibleDocument) 1338 { 1339 uno::Reference<XAccessible> xOldAccessible (Get(aItr - maZOrderedShapes.begin())); 1340 1341 delete *aItr; 1342 maZOrderedShapes.erase(aItr); 1343 1344 AccessibleEventObject aEvent; 1345 aEvent.EventId = AccessibleEventId::CHILD; 1346 aEvent.Source = uno::Reference< XAccessibleContext >(mpAccessibleDocument); 1347 aEvent.OldValue <<= uno::makeAny(xOldAccessible); 1348 1349 mpAccessibleDocument->CommitChange(aEvent); // child is gone - event 1350 } 1351 else 1352 { 1353 delete *aItr; 1354 maZOrderedShapes.erase(aItr); 1355 } 1356 } 1357 else 1358 { 1359 DBG_ERRORFILE("shape was not in internal list"); 1360 } 1361 } 1362 1363 sal_Bool ScChildrenShapes::FindShape(const uno::Reference<drawing::XShape>& xShape, ScChildrenShapes::SortedShapes::iterator& rItr) const 1364 { 1365 sal_Bool bResult(sal_False); 1366 ScAccessibleShapeData aShape; 1367 aShape.xShape = xShape; 1368 ScShapeDataLess aLess; 1369 rItr = std::lower_bound(maZOrderedShapes.begin(), maZOrderedShapes.end(), &aShape, aLess); 1370 if ((rItr != maZOrderedShapes.end()) && (*rItr != NULL) && ((*rItr)->xShape.get() == xShape.get())) 1371 bResult = sal_True; // if the shape is found 1372 1373 #ifdef DBG_UTIL // test whether it finds truly the correct shape (perhaps it is not really sorted) 1374 SortedShapes::iterator aDebugItr = maZOrderedShapes.begin(); 1375 SortedShapes::iterator aEndItr = maZOrderedShapes.end(); 1376 sal_Bool bFound(sal_False); 1377 while (!bFound && aDebugItr != aEndItr) 1378 { 1379 if (*aDebugItr && ((*aDebugItr)->xShape.get() == xShape.get())) 1380 bFound = sal_True; 1381 else 1382 ++aDebugItr; 1383 } 1384 sal_Bool bResult2 = (aDebugItr != maZOrderedShapes.end()); 1385 DBG_ASSERT((bResult == bResult2) && ((bResult && (rItr == aDebugItr)) || !bResult), "wrong Shape found"); 1386 #endif 1387 return bResult; 1388 } 1389 1390 sal_Int8 ScChildrenShapes::Compare(const ScAccessibleShapeData* pData1, 1391 const ScAccessibleShapeData* pData2) const 1392 { 1393 ScShapeDataLess aLess; 1394 1395 sal_Bool bResult1(aLess(pData1, pData2)); 1396 sal_Bool bResult2(aLess(pData2, pData1)); 1397 1398 sal_Int8 nResult(0); 1399 if (!bResult1 && bResult2) 1400 nResult = 1; 1401 else if (bResult1 && !bResult2) 1402 nResult = -1; 1403 1404 return nResult; 1405 } 1406 1407 struct ScVisAreaChanged 1408 { 1409 ScAccessibleDocument* mpAccDoc; 1410 ScVisAreaChanged(ScAccessibleDocument* pAccDoc) : mpAccDoc(pAccDoc) {} 1411 void operator() (const ScAccessibleShapeData* pAccShapeData) const 1412 { 1413 if (pAccShapeData && pAccShapeData->pAccShape) 1414 { 1415 pAccShapeData->pAccShape->ViewForwarderChanged(::accessibility::IAccessibleViewForwarderListener::VISIBLE_AREA, mpAccDoc); 1416 } 1417 } 1418 }; 1419 1420 void ScChildrenShapes::VisAreaChanged() const 1421 { 1422 ScVisAreaChanged aVisAreaChanged(mpAccessibleDocument); 1423 std::for_each(maZOrderedShapes.begin(), maZOrderedShapes.end(), aVisAreaChanged); 1424 } 1425 1426 // ============================================================================ 1427 1428 ScAccessibleDocument::ScAccessibleDocument( 1429 const uno::Reference<XAccessible>& rxParent, 1430 ScTabViewShell* pViewShell, 1431 ScSplitPos eSplitPos) 1432 : ScAccessibleDocumentBase(rxParent), 1433 mpViewShell(pViewShell), 1434 meSplitPos(eSplitPos), 1435 mpAccessibleSpreadsheet(NULL), 1436 mpChildrenShapes(NULL), 1437 mpTempAccEdit(NULL), 1438 mbCompleteSheetSelected(sal_False) 1439 { 1440 if (pViewShell) 1441 { 1442 pViewShell->AddAccessibilityObject(*this); 1443 Window *pWin = pViewShell->GetWindowByPos(eSplitPos); 1444 if( pWin ) 1445 { 1446 pWin->AddChildEventListener( LINK( this, ScAccessibleDocument, WindowChildEventListener )); 1447 sal_uInt16 nCount = pWin->GetChildCount(); 1448 for( sal_uInt16 i=0; i < nCount; ++i ) 1449 { 1450 Window *pChildWin = pWin->GetChild( i ); 1451 if( pChildWin && 1452 AccessibleRole::EMBEDDED_OBJECT == pChildWin->GetAccessibleRole() ) 1453 AddChild( pChildWin->GetAccessible(), sal_False ); 1454 } 1455 } 1456 if (pViewShell->GetViewData()->HasEditView( eSplitPos )) 1457 { 1458 uno::Reference<XAccessible> xAcc = new ScAccessibleEditObject(this, pViewShell->GetViewData()->GetEditView(eSplitPos), 1459 pViewShell->GetWindowByPos(eSplitPos), GetCurrentCellName(), GetCurrentCellDescription(), 1460 CellInEditMode); 1461 AddChild(xAcc, sal_False); 1462 } 1463 } 1464 maVisArea = GetVisibleArea_Impl(); 1465 } 1466 1467 void ScAccessibleDocument::Init() 1468 { 1469 if(!mpChildrenShapes) 1470 mpChildrenShapes = new ScChildrenShapes(this, mpViewShell, meSplitPos); 1471 } 1472 1473 ScAccessibleDocument::~ScAccessibleDocument(void) 1474 { 1475 if (!ScAccessibleContextBase::IsDefunc() && !rBHelper.bInDispose) 1476 { 1477 // increment refcount to prevent double call off dtor 1478 osl_incrementInterlockedCount( &m_refCount ); 1479 dispose(); 1480 } 1481 } 1482 1483 void SAL_CALL ScAccessibleDocument::disposing() 1484 { 1485 ScUnoGuard aGuard; 1486 FreeAccessibleSpreadsheet(); 1487 if (mpViewShell) 1488 { 1489 Window *pWin = mpViewShell->GetWindowByPos(meSplitPos); 1490 if( pWin ) 1491 pWin->RemoveChildEventListener( LINK( this, ScAccessibleDocument, WindowChildEventListener )); 1492 1493 mpViewShell->RemoveAccessibilityObject(*this); 1494 mpViewShell = NULL; 1495 } 1496 if (mpChildrenShapes) 1497 DELETEZ(mpChildrenShapes); 1498 1499 ScAccessibleDocumentBase::disposing(); 1500 } 1501 1502 void SAL_CALL ScAccessibleDocument::disposing( const lang::EventObject& /* Source */ ) 1503 throw (uno::RuntimeException) 1504 { 1505 disposing(); 1506 } 1507 1508 //===== SfxListener ===================================================== 1509 1510 IMPL_LINK( ScAccessibleDocument, WindowChildEventListener, VclSimpleEvent*, pEvent ) 1511 { 1512 DBG_ASSERT( pEvent && pEvent->ISA( VclWindowEvent ), "Unknown WindowEvent!" ); 1513 if ( pEvent && pEvent->ISA( VclWindowEvent ) ) 1514 { 1515 VclWindowEvent *pVclEvent = static_cast< VclWindowEvent * >( pEvent ); 1516 DBG_ASSERT( pVclEvent->GetWindow(), "Window???" ); 1517 switch ( pVclEvent->GetId() ) 1518 { 1519 case VCLEVENT_WINDOW_SHOW: // send create on show for direct accessible children 1520 { 1521 Window* pChildWin = static_cast < Window * >( pVclEvent->GetData() ); 1522 if( pChildWin && AccessibleRole::EMBEDDED_OBJECT == pChildWin->GetAccessibleRole() ) 1523 { 1524 AddChild( pChildWin->GetAccessible(), sal_True ); 1525 } 1526 } 1527 break; 1528 case VCLEVENT_WINDOW_HIDE: // send destroy on hide for direct accessible children 1529 { 1530 Window* pChildWin = static_cast < Window * >( pVclEvent->GetData() ); 1531 if( pChildWin && AccessibleRole::EMBEDDED_OBJECT == pChildWin->GetAccessibleRole() ) 1532 { 1533 RemoveChild( pChildWin->GetAccessible(), sal_True ); 1534 } 1535 } 1536 break; 1537 } 1538 } 1539 return 0; 1540 } 1541 1542 void ScAccessibleDocument::Notify( SfxBroadcaster& rBC, const SfxHint& rHint ) 1543 { 1544 if (rHint.ISA( ScAccGridWinFocusLostHint ) ) 1545 { 1546 const ScAccGridWinFocusLostHint& rRef = (const ScAccGridWinFocusLostHint&)rHint; 1547 if (rRef.GetOldGridWin() == meSplitPos) 1548 { 1549 if (mxTempAcc.is() && mpTempAccEdit) 1550 mpTempAccEdit->LostFocus(); 1551 else if (mpAccessibleSpreadsheet) 1552 mpAccessibleSpreadsheet->LostFocus(); 1553 else 1554 CommitFocusLost(); 1555 } 1556 } 1557 else if (rHint.ISA( ScAccGridWinFocusGotHint ) ) 1558 { 1559 const ScAccGridWinFocusGotHint& rRef = (const ScAccGridWinFocusGotHint&)rHint; 1560 if (rRef.GetNewGridWin() == meSplitPos) 1561 { 1562 //IAccessibility2 Implementation 2009----- 1563 uno::Reference<XAccessible> xAccessible; 1564 if (mpChildrenShapes) 1565 { 1566 sal_Bool bTabMarked(IsTableSelected()); 1567 xAccessible = mpChildrenShapes->GetSelected(0, bTabMarked); 1568 } 1569 if( xAccessible.is() ) 1570 { 1571 uno::Any aNewValue; 1572 aNewValue<<=AccessibleStateType::FOCUSED; 1573 static_cast< ::accessibility::AccessibleShape* >(xAccessible.get())-> 1574 CommitChange(AccessibleEventId::STATE_CHANGED, 1575 aNewValue, 1576 uno::Any() ); 1577 } 1578 else 1579 { 1580 if (mxTempAcc.is() && mpTempAccEdit) 1581 mpTempAccEdit->GotFocus(); 1582 else if (mpAccessibleSpreadsheet) 1583 mpAccessibleSpreadsheet->GotFocus(); 1584 else 1585 CommitFocusGained(); 1586 } 1587 //-----IAccessibility2 Implementation 2009 1588 } 1589 } 1590 else if (rHint.ISA( SfxSimpleHint )) 1591 { 1592 const SfxSimpleHint& rRef = (const SfxSimpleHint&)rHint; 1593 // only notify if child exist, otherwise it is not necessary 1594 if ((rRef.GetId() == SC_HINT_ACC_TABLECHANGED) && 1595 mpAccessibleSpreadsheet) 1596 { 1597 FreeAccessibleSpreadsheet(); 1598 if (mpChildrenShapes) 1599 DELETEZ(mpChildrenShapes); 1600 1601 // #124567# Accessibility: Shapes / form controls after reload not accessible 1602 if ( !mpChildrenShapes ) 1603 { 1604 mpChildrenShapes = new ScChildrenShapes( this, mpViewShell, meSplitPos ); 1605 } 1606 //IAccessibility2 Implementation 2009----- 1607 //Invoke Init() to rebuild the mpChildrenShapes variable 1608 this->Init(); 1609 //-----IAccessibility2 Implementation 2009 1610 AccessibleEventObject aEvent; 1611 aEvent.EventId = AccessibleEventId::INVALIDATE_ALL_CHILDREN; 1612 aEvent.Source = uno::Reference< XAccessibleContext >(this); 1613 CommitChange(aEvent); // all childs changed 1614 //IAccessibility2 Implementation 2009----- 1615 if (mpAccessibleSpreadsheet) 1616 mpAccessibleSpreadsheet->FireFirstCellFocus(); 1617 //-----IAccessibility2 Implementation 2009 1618 } 1619 else if (rRef.GetId() == SC_HINT_ACC_MAKEDRAWLAYER) 1620 { 1621 if (mpChildrenShapes) 1622 mpChildrenShapes->SetDrawBroadcaster(); 1623 } 1624 else if ((rRef.GetId() == SC_HINT_ACC_ENTEREDITMODE)) // this event comes only on creating edit field of a cell 1625 { 1626 if (mpViewShell && mpViewShell->GetViewData()->HasEditView(meSplitPos)) 1627 { 1628 //IAccessibility2 Implementation 2009------ 1629 EditEngine* pEditEng = mpViewShell->GetViewData()->GetEditView(meSplitPos)->GetEditEngine(); 1630 if (pEditEng && pEditEng->GetUpdateMode()) 1631 { 1632 mpTempAccEdit = new ScAccessibleEditObject(this, mpViewShell->GetViewData()->GetEditView(meSplitPos), 1633 mpViewShell->GetWindowByPos(meSplitPos), GetCurrentCellName(), 1634 rtl::OUString(String(ScResId(STR_ACC_EDITLINE_DESCR))), CellInEditMode); 1635 uno::Reference<XAccessible> xAcc = mpTempAccEdit; 1636 1637 AddChild(xAcc, sal_True); 1638 1639 if (mpAccessibleSpreadsheet) 1640 mpAccessibleSpreadsheet->LostFocus(); 1641 else 1642 CommitFocusLost(); 1643 1644 mpTempAccEdit->GotFocus(); 1645 } 1646 //------IAccessibility2 Implementation 2009 1647 } 1648 } 1649 else if (rRef.GetId() == SC_HINT_ACC_LEAVEEDITMODE) 1650 { 1651 if (mxTempAcc.is()) 1652 { 1653 if (mpTempAccEdit) 1654 mpTempAccEdit->LostFocus(); 1655 1656 mpTempAccEdit = NULL; 1657 RemoveChild(mxTempAcc, sal_True); 1658 //IAccessibility2 Implementation 2009----- 1659 //if (mpAccessibleSpreadsheet) 1660 if (mpAccessibleSpreadsheet && mpViewShell->IsActive()) 1661 //-----IAccessibility2 Implementation 2009 1662 mpAccessibleSpreadsheet->GotFocus(); 1663 //IAccessibility2 Implementation 2009----- 1664 //else 1665 else if( mpViewShell->IsActive()) 1666 //-----IAccessibility2 Implementation 2009 1667 CommitFocusGained(); 1668 } 1669 } 1670 else if ((rRef.GetId() == SC_HINT_ACC_VISAREACHANGED) || (rRef.GetId() == SC_HINT_ACC_WINDOWRESIZED)) 1671 { 1672 Rectangle aOldVisArea(maVisArea); 1673 maVisArea = GetVisibleArea_Impl(); 1674 1675 if (maVisArea != aOldVisArea) 1676 { 1677 if (maVisArea.GetSize() != aOldVisArea.GetSize()) 1678 { 1679 AccessibleEventObject aEvent; 1680 aEvent.EventId = AccessibleEventId::BOUNDRECT_CHANGED; 1681 aEvent.Source = uno::Reference< XAccessibleContext >(this); 1682 1683 CommitChange(aEvent); 1684 1685 if (mpAccessibleSpreadsheet) 1686 mpAccessibleSpreadsheet->BoundingBoxChanged(); 1687 } 1688 else if (mpAccessibleSpreadsheet) 1689 { 1690 mpAccessibleSpreadsheet->VisAreaChanged(); 1691 } 1692 if (mpChildrenShapes) 1693 mpChildrenShapes->VisAreaChanged(); 1694 } 1695 } 1696 } 1697 1698 ScAccessibleDocumentBase::Notify(rBC, rHint); 1699 } 1700 1701 void SAL_CALL ScAccessibleDocument::selectionChanged( const lang::EventObject& /* aEvent */ ) 1702 throw (uno::RuntimeException) 1703 { 1704 sal_Bool bSelectionChanged(sal_False); 1705 if (mpAccessibleSpreadsheet) 1706 { 1707 sal_Bool bOldSelected(mbCompleteSheetSelected); 1708 mbCompleteSheetSelected = IsTableSelected(); 1709 if (bOldSelected != mbCompleteSheetSelected) 1710 { 1711 mpAccessibleSpreadsheet->CompleteSelectionChanged(mbCompleteSheetSelected); 1712 bSelectionChanged = sal_True; 1713 } 1714 } 1715 1716 if (mpChildrenShapes && mpChildrenShapes->SelectionChanged()) 1717 bSelectionChanged = sal_True; 1718 1719 if (bSelectionChanged) 1720 { 1721 AccessibleEventObject aEvent; 1722 aEvent.EventId = AccessibleEventId::SELECTION_CHANGED; 1723 aEvent.Source = uno::Reference< XAccessibleContext >(this); 1724 1725 CommitChange(aEvent); 1726 } 1727 //IAccessibility2 Implementation 2009----- 1728 if(mpChildrenShapes ) 1729 { 1730 mpChildrenShapes->SelectionChanged(); 1731 } 1732 //-----IAccessibility2 Implementation 2009 1733 } 1734 1735 //===== XInterface ===================================================== 1736 1737 uno::Any SAL_CALL ScAccessibleDocument::queryInterface( uno::Type const & rType ) 1738 throw (uno::RuntimeException) 1739 { 1740 //IAccessibility2 Implementation 2009----- 1741 uno::Any aAnyTmp; 1742 if(rType == ::getCppuType((com::sun::star::uno::Reference<XAccessibleGetAccFlowTo> *)NULL) ) 1743 { 1744 com::sun::star::uno::Reference<XAccessibleGetAccFlowTo> AccFromXShape = this; 1745 aAnyTmp <<= AccFromXShape; 1746 return aAnyTmp; 1747 } 1748 //-----IAccessibility2 Implementation 2009 1749 uno::Any aAny (ScAccessibleDocumentImpl::queryInterface(rType)); 1750 return aAny.hasValue() ? aAny : ScAccessibleContextBase::queryInterface(rType); 1751 } 1752 1753 void SAL_CALL ScAccessibleDocument::acquire() 1754 throw () 1755 { 1756 ScAccessibleContextBase::acquire(); 1757 } 1758 1759 void SAL_CALL ScAccessibleDocument::release() 1760 throw () 1761 { 1762 ScAccessibleContextBase::release(); 1763 } 1764 1765 //===== XAccessibleComponent ============================================ 1766 1767 uno::Reference< XAccessible > SAL_CALL ScAccessibleDocument::getAccessibleAtPoint( 1768 const awt::Point& rPoint ) 1769 throw (uno::RuntimeException) 1770 { 1771 uno::Reference<XAccessible> xAccessible = NULL; 1772 if (containsPoint(rPoint)) 1773 { 1774 ScUnoGuard aGuard; 1775 IsObjectValid(); 1776 if (mpChildrenShapes) 1777 xAccessible = mpChildrenShapes->GetAt(rPoint); 1778 if(!xAccessible.is()) 1779 { 1780 if (mxTempAcc.is()) 1781 { 1782 uno::Reference< XAccessibleContext > xCont(mxTempAcc->getAccessibleContext()); 1783 uno::Reference< XAccessibleComponent > xComp(xCont, uno::UNO_QUERY); 1784 if (xComp.is()) 1785 { 1786 Rectangle aBound(VCLRectangle(xComp->getBounds())); 1787 if (aBound.IsInside(VCLPoint(rPoint))) 1788 xAccessible = mxTempAcc; 1789 } 1790 } 1791 if (!xAccessible.is()) 1792 xAccessible = GetAccessibleSpreadsheet(); 1793 } 1794 } 1795 return xAccessible; 1796 } 1797 1798 void SAL_CALL ScAccessibleDocument::grabFocus( ) 1799 throw (uno::RuntimeException) 1800 { 1801 ScUnoGuard aGuard; 1802 IsObjectValid(); 1803 if (getAccessibleParent().is()) 1804 { 1805 uno::Reference<XAccessibleComponent> xAccessibleComponent(getAccessibleParent()->getAccessibleContext(), uno::UNO_QUERY); 1806 if (xAccessibleComponent.is()) 1807 { 1808 xAccessibleComponent->grabFocus(); 1809 // grab only focus if it does not have the focus and it is not hidden 1810 if (mpViewShell && mpViewShell->GetViewData() && 1811 (mpViewShell->GetViewData()->GetActivePart() != meSplitPos) && 1812 mpViewShell->GetWindowByPos(meSplitPos)->IsVisible()) 1813 { 1814 mpViewShell->ActivatePart(meSplitPos); 1815 } 1816 } 1817 } 1818 } 1819 1820 //===== XAccessibleContext ============================================== 1821 1822 /// Return the number of currently visible children. 1823 sal_Int32 SAL_CALL 1824 ScAccessibleDocument::getAccessibleChildCount(void) 1825 throw (uno::RuntimeException) 1826 { 1827 ScUnoGuard aGuard; 1828 IsObjectValid(); 1829 sal_Int32 nCount(1); 1830 if (mpChildrenShapes) 1831 nCount = mpChildrenShapes->GetCount(); // returns the count of the shapes inclusive the table 1832 1833 if (mxTempAcc.is()) 1834 ++nCount; 1835 1836 return nCount; 1837 } 1838 1839 /// Return the specified child or NULL if index is invalid. 1840 uno::Reference<XAccessible> SAL_CALL 1841 ScAccessibleDocument::getAccessibleChild(sal_Int32 nIndex) 1842 throw (uno::RuntimeException, 1843 lang::IndexOutOfBoundsException) 1844 { 1845 ScUnoGuard aGuard; 1846 IsObjectValid(); 1847 uno::Reference<XAccessible> xAccessible; 1848 if (nIndex >= 0) 1849 { 1850 sal_Int32 nCount(1); 1851 if (mpChildrenShapes) 1852 { 1853 xAccessible = mpChildrenShapes->Get(nIndex); // returns NULL if it is the table or out of range 1854 nCount = mpChildrenShapes->GetCount(); //there is always a table 1855 } 1856 if (!xAccessible.is()) 1857 { 1858 if (nIndex < nCount) 1859 xAccessible = GetAccessibleSpreadsheet(); 1860 else if (nIndex == nCount && mxTempAcc.is()) 1861 xAccessible = mxTempAcc; 1862 } 1863 } 1864 1865 if (!xAccessible.is()) 1866 throw lang::IndexOutOfBoundsException(); 1867 1868 return xAccessible; 1869 } 1870 1871 /// Return the set of current states. 1872 uno::Reference<XAccessibleStateSet> SAL_CALL 1873 ScAccessibleDocument::getAccessibleStateSet(void) 1874 throw (uno::RuntimeException) 1875 { 1876 ScUnoGuard aGuard; 1877 uno::Reference<XAccessibleStateSet> xParentStates; 1878 if (getAccessibleParent().is()) 1879 { 1880 uno::Reference<XAccessibleContext> xParentContext = getAccessibleParent()->getAccessibleContext(); 1881 xParentStates = xParentContext->getAccessibleStateSet(); 1882 } 1883 utl::AccessibleStateSetHelper* pStateSet = new utl::AccessibleStateSetHelper(); 1884 if (IsDefunc(xParentStates)) 1885 pStateSet->AddState(AccessibleStateType::DEFUNC); 1886 else 1887 { 1888 if (IsEditable(xParentStates)) 1889 pStateSet->AddState(AccessibleStateType::EDITABLE); 1890 pStateSet->AddState(AccessibleStateType::ENABLED); 1891 pStateSet->AddState(AccessibleStateType::OPAQUE); 1892 if (isShowing()) 1893 pStateSet->AddState(AccessibleStateType::SHOWING); 1894 if (isVisible()) 1895 pStateSet->AddState(AccessibleStateType::VISIBLE); 1896 } 1897 return pStateSet; 1898 } 1899 1900 //IAccessibility2 Implementation 2009----- 1901 ::rtl::OUString SAL_CALL 1902 ScAccessibleDocument::getAccessibleName(void) 1903 throw (::com::sun::star::uno::RuntimeException) 1904 { 1905 rtl::OUString sName = String(ScResId(STR_ACC_DOC_SPREADSHEET)); 1906 ScDocument* pScDoc = GetDocument(); 1907 if ( pScDoc ) 1908 { 1909 rtl::OUString sFileName = pScDoc->getDocAccTitle(); 1910 if ( !sFileName.getLength() ) 1911 { 1912 SfxObjectShell* pObjSh = pScDoc->GetDocumentShell(); 1913 if ( pObjSh ) 1914 { 1915 sFileName = pObjSh->GetTitle( SFX_TITLE_APINAME ); 1916 } 1917 } 1918 rtl::OUString sReadOnly; 1919 if (pScDoc->getDocReadOnly()) 1920 { 1921 sReadOnly = String(ScResId(STR_ACC_DOC_SPREADSHEET_READONLY)); 1922 } 1923 if ( sFileName.getLength() ) 1924 { 1925 sName = sFileName + sReadOnly + rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(" - ")) + sName; 1926 } 1927 } 1928 return sName; 1929 } 1930 //-----IAccessibility2 Implementation 2009 1931 ///===== XAccessibleSelection =========================================== 1932 1933 void SAL_CALL 1934 ScAccessibleDocument::selectAccessibleChild( sal_Int32 nChildIndex ) 1935 throw (lang::IndexOutOfBoundsException, uno::RuntimeException) 1936 { 1937 ScUnoGuard aGuard; 1938 IsObjectValid(); 1939 1940 if (mpChildrenShapes) 1941 { 1942 sal_Int32 nCount(mpChildrenShapes->GetCount()); //all shapes and the table 1943 if (mxTempAcc.is()) 1944 ++nCount; 1945 if (nChildIndex < 0 || nChildIndex >= nCount) 1946 throw lang::IndexOutOfBoundsException(); 1947 1948 uno::Reference < XAccessible > xAccessible = mpChildrenShapes->Get(nChildIndex); 1949 if (xAccessible.is()) 1950 { 1951 sal_Bool bWasTableSelected(IsTableSelected()); 1952 1953 if (mpChildrenShapes) 1954 mpChildrenShapes->Select(nChildIndex); // throws no lang::IndexOutOfBoundsException if Index is to high 1955 1956 if (bWasTableSelected) 1957 mpViewShell->SelectAll(); 1958 } 1959 else 1960 { 1961 if (mpViewShell) 1962 mpViewShell->SelectAll(); 1963 } 1964 } 1965 } 1966 1967 sal_Bool SAL_CALL 1968 ScAccessibleDocument::isAccessibleChildSelected( sal_Int32 nChildIndex ) 1969 throw (lang::IndexOutOfBoundsException, uno::RuntimeException) 1970 { 1971 ScUnoGuard aGuard; 1972 IsObjectValid(); 1973 sal_Bool bResult(sal_False); 1974 1975 if (mpChildrenShapes) 1976 { 1977 sal_Int32 nCount(mpChildrenShapes->GetCount()); //all shapes and the table 1978 if (mxTempAcc.is()) 1979 ++nCount; 1980 if (nChildIndex < 0 || nChildIndex >= nCount) 1981 throw lang::IndexOutOfBoundsException(); 1982 1983 uno::Reference < XAccessible > xAccessible = mpChildrenShapes->Get(nChildIndex); 1984 if (xAccessible.is()) 1985 { 1986 uno::Reference<drawing::XShape> xShape; 1987 bResult = mpChildrenShapes->IsSelected(nChildIndex, xShape); // throws no lang::IndexOutOfBoundsException if Index is to high 1988 } 1989 else 1990 { 1991 if (mxTempAcc.is() && nChildIndex == nCount) 1992 bResult = sal_True; 1993 else 1994 bResult = IsTableSelected(); 1995 } 1996 } 1997 return bResult; 1998 } 1999 2000 void SAL_CALL 2001 ScAccessibleDocument::clearAccessibleSelection( ) 2002 throw (uno::RuntimeException) 2003 { 2004 ScUnoGuard aGuard; 2005 IsObjectValid(); 2006 2007 if (mpChildrenShapes) 2008 mpChildrenShapes->DeselectAll(); //deselects all (also the table) 2009 } 2010 2011 void SAL_CALL 2012 ScAccessibleDocument::selectAllAccessibleChildren( ) 2013 throw (uno::RuntimeException) 2014 { 2015 ScUnoGuard aGuard; 2016 IsObjectValid(); 2017 2018 if (mpChildrenShapes) 2019 mpChildrenShapes->SelectAll(); 2020 2021 // select table after shapes, because while selecting shapes the table will be deselected 2022 if (mpViewShell) 2023 { 2024 mpViewShell->SelectAll(); 2025 } 2026 } 2027 2028 sal_Int32 SAL_CALL 2029 ScAccessibleDocument::getSelectedAccessibleChildCount( ) 2030 throw (uno::RuntimeException) 2031 { 2032 ScUnoGuard aGuard; 2033 IsObjectValid(); 2034 sal_Int32 nCount(0); 2035 2036 if (mpChildrenShapes) 2037 nCount = mpChildrenShapes->GetSelectedCount(); 2038 2039 if (IsTableSelected()) 2040 ++nCount; 2041 2042 if (mxTempAcc.is()) 2043 ++nCount; 2044 2045 return nCount; 2046 } 2047 2048 uno::Reference<XAccessible > SAL_CALL 2049 ScAccessibleDocument::getSelectedAccessibleChild( sal_Int32 nSelectedChildIndex ) 2050 throw (lang::IndexOutOfBoundsException, uno::RuntimeException) 2051 { 2052 ScUnoGuard aGuard; 2053 IsObjectValid(); 2054 uno::Reference<XAccessible> xAccessible; 2055 if (mpChildrenShapes) 2056 { 2057 sal_Int32 nCount(getSelectedAccessibleChildCount()); //all shapes and the table 2058 if (nSelectedChildIndex < 0 || nSelectedChildIndex >= nCount) 2059 throw lang::IndexOutOfBoundsException(); 2060 2061 sal_Bool bTabMarked(IsTableSelected()); 2062 2063 if (mpChildrenShapes) 2064 xAccessible = mpChildrenShapes->GetSelected(nSelectedChildIndex, bTabMarked); // throws no lang::IndexOutOfBoundsException if Index is to high 2065 if (mxTempAcc.is() && nSelectedChildIndex == nCount - 1) 2066 xAccessible = mxTempAcc; 2067 else if (bTabMarked) 2068 xAccessible = GetAccessibleSpreadsheet(); 2069 } 2070 2071 DBG_ASSERT(xAccessible.is(), "here should always be an accessible object or a exception throwed"); 2072 2073 return xAccessible; 2074 } 2075 2076 void SAL_CALL 2077 ScAccessibleDocument::deselectAccessibleChild( sal_Int32 nChildIndex ) 2078 throw (lang::IndexOutOfBoundsException, uno::RuntimeException) 2079 { 2080 ScUnoGuard aGuard; 2081 IsObjectValid(); 2082 2083 if (mpChildrenShapes) 2084 { 2085 sal_Int32 nCount(mpChildrenShapes->GetCount()); //all shapes and the table 2086 if (mxTempAcc.is()) 2087 ++nCount; 2088 if (nChildIndex < 0 || nChildIndex >= nCount) 2089 throw lang::IndexOutOfBoundsException(); 2090 2091 sal_Bool bTabMarked(IsTableSelected()); 2092 2093 uno::Reference < XAccessible > xAccessible = mpChildrenShapes->Get(nChildIndex); 2094 if (xAccessible.is()) 2095 { 2096 if (mpChildrenShapes) 2097 mpChildrenShapes->Deselect(nChildIndex); // throws no lang::IndexOutOfBoundsException if Index is to high 2098 2099 if (bTabMarked) 2100 mpViewShell->SelectAll(); // select the table again 2101 } 2102 else if (bTabMarked) 2103 mpViewShell->Unmark(); 2104 } 2105 } 2106 2107 //===== XServiceInfo ==================================================== 2108 2109 ::rtl::OUString SAL_CALL 2110 ScAccessibleDocument::getImplementationName(void) 2111 throw (uno::RuntimeException) 2112 { 2113 return ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM ("ScAccessibleDocument")); 2114 } 2115 2116 uno::Sequence< ::rtl::OUString> SAL_CALL 2117 ScAccessibleDocument::getSupportedServiceNames(void) 2118 throw (uno::RuntimeException) 2119 { 2120 uno::Sequence< ::rtl::OUString > aSequence = ScAccessibleContextBase::getSupportedServiceNames(); 2121 sal_Int32 nOldSize(aSequence.getLength()); 2122 aSequence.realloc(nOldSize + 1); 2123 ::rtl::OUString* pNames = aSequence.getArray(); 2124 2125 pNames[nOldSize] = rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.AccessibleSpreadsheetDocumentView")); 2126 2127 return aSequence; 2128 } 2129 2130 //===== XTypeProvider ======================================================= 2131 2132 uno::Sequence< uno::Type > SAL_CALL ScAccessibleDocument::getTypes() 2133 throw (uno::RuntimeException) 2134 { 2135 return comphelper::concatSequences(ScAccessibleDocumentImpl::getTypes(), ScAccessibleContextBase::getTypes()); 2136 } 2137 2138 uno::Sequence<sal_Int8> SAL_CALL 2139 ScAccessibleDocument::getImplementationId(void) 2140 throw (uno::RuntimeException) 2141 { 2142 ScUnoGuard aGuard; 2143 IsObjectValid(); 2144 static uno::Sequence<sal_Int8> aId; 2145 if (aId.getLength() == 0) 2146 { 2147 aId.realloc (16); 2148 rtl_createUuid (reinterpret_cast<sal_uInt8 *>(aId.getArray()), 0, sal_True); 2149 } 2150 return aId; 2151 } 2152 2153 ///===== IAccessibleViewForwarder ======================================== 2154 2155 sal_Bool ScAccessibleDocument::IsValid (void) const 2156 { 2157 ScUnoGuard aGuard; 2158 IsObjectValid(); 2159 return (!ScAccessibleContextBase::IsDefunc() && !rBHelper.bInDispose); 2160 } 2161 2162 Rectangle ScAccessibleDocument::GetVisibleArea_Impl() const 2163 { 2164 Rectangle aVisRect(GetBoundingBox()); 2165 2166 Point aPoint(mpViewShell->GetViewData()->GetPixPos(meSplitPos)); // returns a negative Point 2167 aPoint.setX(-aPoint.getX()); 2168 aPoint.setY(-aPoint.getY()); 2169 aVisRect.SetPos(aPoint); 2170 2171 ScGridWindow* pWin = static_cast<ScGridWindow*>(mpViewShell->GetWindowByPos(meSplitPos)); 2172 if (pWin) 2173 aVisRect = pWin->PixelToLogic(aVisRect, pWin->GetDrawMapMode()); 2174 2175 return aVisRect; 2176 } 2177 2178 Rectangle ScAccessibleDocument::GetVisibleArea() const 2179 { 2180 ScUnoGuard aGuard; 2181 IsObjectValid(); 2182 return maVisArea; 2183 } 2184 2185 Point ScAccessibleDocument::LogicToPixel (const Point& rPoint) const 2186 { 2187 ScUnoGuard aGuard; 2188 IsObjectValid(); 2189 Point aPoint; 2190 ScGridWindow* pWin = static_cast<ScGridWindow*>(mpViewShell->GetWindowByPos(meSplitPos)); 2191 if (pWin) 2192 { 2193 aPoint = pWin->LogicToPixel(rPoint, pWin->GetDrawMapMode()); 2194 aPoint += pWin->GetWindowExtentsRelative(NULL).TopLeft(); 2195 } 2196 return aPoint; 2197 } 2198 2199 Size ScAccessibleDocument::LogicToPixel (const Size& rSize) const 2200 { 2201 ScUnoGuard aGuard; 2202 IsObjectValid(); 2203 Size aSize; 2204 ScGridWindow* pWin = static_cast<ScGridWindow*>(mpViewShell->GetWindowByPos(meSplitPos)); 2205 if (pWin) 2206 aSize = pWin->LogicToPixel(rSize, pWin->GetDrawMapMode()); 2207 return aSize; 2208 } 2209 2210 Point ScAccessibleDocument::PixelToLogic (const Point& rPoint) const 2211 { 2212 ScUnoGuard aGuard; 2213 IsObjectValid(); 2214 Point aPoint; 2215 ScGridWindow* pWin = static_cast<ScGridWindow*>(mpViewShell->GetWindowByPos(meSplitPos)); 2216 if (pWin) 2217 { 2218 aPoint -= pWin->GetWindowExtentsRelative(NULL).TopLeft(); 2219 aPoint = pWin->PixelToLogic(rPoint, pWin->GetDrawMapMode()); 2220 } 2221 return aPoint; 2222 } 2223 2224 Size ScAccessibleDocument::PixelToLogic (const Size& rSize) const 2225 { 2226 ScUnoGuard aGuard; 2227 IsObjectValid(); 2228 Size aSize; 2229 ScGridWindow* pWin = static_cast<ScGridWindow*>(mpViewShell->GetWindowByPos(meSplitPos)); 2230 if (pWin) 2231 aSize = pWin->PixelToLogic(rSize, pWin->GetDrawMapMode()); 2232 return aSize; 2233 } 2234 2235 //===== internal ======================================================== 2236 2237 utl::AccessibleRelationSetHelper* ScAccessibleDocument::GetRelationSet(const ScAddress* pAddress) const 2238 { 2239 utl::AccessibleRelationSetHelper* pRelationSet = NULL; 2240 if (mpChildrenShapes) 2241 pRelationSet = mpChildrenShapes->GetRelationSet(pAddress); 2242 return pRelationSet; 2243 } 2244 2245 ::rtl::OUString SAL_CALL 2246 ScAccessibleDocument::createAccessibleDescription(void) 2247 throw (uno::RuntimeException) 2248 { 2249 rtl::OUString sDescription = String(ScResId(STR_ACC_DOC_DESCR)); 2250 return sDescription; 2251 } 2252 2253 ::rtl::OUString SAL_CALL 2254 ScAccessibleDocument::createAccessibleName(void) 2255 throw (uno::RuntimeException) 2256 { 2257 ScUnoGuard aGuard; 2258 IsObjectValid(); 2259 rtl::OUString sName = String(ScResId(STR_ACC_DOC_NAME)); 2260 sal_Int32 nNumber(sal_Int32(meSplitPos) + 1); 2261 sName += rtl::OUString::valueOf(nNumber); 2262 return sName; 2263 } 2264 2265 Rectangle ScAccessibleDocument::GetBoundingBoxOnScreen() const 2266 throw (uno::RuntimeException) 2267 { 2268 Rectangle aRect; 2269 if (mpViewShell) 2270 { 2271 Window* pWindow = mpViewShell->GetWindowByPos(meSplitPos); 2272 if (pWindow) 2273 aRect = pWindow->GetWindowExtentsRelative(NULL); 2274 } 2275 return aRect; 2276 } 2277 2278 Rectangle ScAccessibleDocument::GetBoundingBox() const 2279 throw (uno::RuntimeException) 2280 { 2281 Rectangle aRect; 2282 if (mpViewShell) 2283 { 2284 Window* pWindow = mpViewShell->GetWindowByPos(meSplitPos); 2285 if (pWindow) 2286 aRect = pWindow->GetWindowExtentsRelative(pWindow->GetAccessibleParentWindow()); 2287 } 2288 return aRect; 2289 } 2290 2291 SCTAB ScAccessibleDocument::getVisibleTable() const 2292 { 2293 SCTAB nVisibleTable(0); 2294 if (mpViewShell && mpViewShell->GetViewData()) 2295 nVisibleTable = mpViewShell->GetViewData()->GetTabNo(); 2296 return nVisibleTable; 2297 } 2298 2299 uno::Reference < XAccessible > 2300 ScAccessibleDocument::GetAccessibleSpreadsheet() 2301 { 2302 if (!mpAccessibleSpreadsheet && mpViewShell) 2303 { 2304 mpAccessibleSpreadsheet = new ScAccessibleSpreadsheet(this, mpViewShell, getVisibleTable(), meSplitPos); 2305 mpAccessibleSpreadsheet->acquire(); 2306 mpAccessibleSpreadsheet->Init(); 2307 mbCompleteSheetSelected = IsTableSelected(); 2308 } 2309 return mpAccessibleSpreadsheet; 2310 } 2311 2312 void ScAccessibleDocument::FreeAccessibleSpreadsheet() 2313 { 2314 if (mpAccessibleSpreadsheet) 2315 { 2316 mpAccessibleSpreadsheet->dispose(); 2317 mpAccessibleSpreadsheet->release(); 2318 mpAccessibleSpreadsheet = NULL; 2319 } 2320 } 2321 2322 sal_Bool ScAccessibleDocument::IsTableSelected() const 2323 { 2324 sal_Bool bResult (sal_False); 2325 if(mpViewShell) 2326 { 2327 SCTAB nTab(getVisibleTable()); 2328 //#103800#; use a copy of MarkData 2329 ScMarkData aMarkData(mpViewShell->GetViewData()->GetMarkData()); 2330 aMarkData.MarkToMulti(); 2331 if (aMarkData.IsAllMarked(ScRange(ScAddress(0, 0, nTab),ScAddress(MAXCOL, MAXROW, nTab)))) 2332 bResult = sal_True; 2333 } 2334 return bResult; 2335 } 2336 2337 sal_Bool ScAccessibleDocument::IsDefunc( 2338 const uno::Reference<XAccessibleStateSet>& rxParentStates) 2339 { 2340 return ScAccessibleContextBase::IsDefunc() || (mpViewShell == NULL) || !getAccessibleParent().is() || 2341 (rxParentStates.is() && rxParentStates->contains(AccessibleStateType::DEFUNC)); 2342 } 2343 2344 sal_Bool ScAccessibleDocument::IsEditable( 2345 const uno::Reference<XAccessibleStateSet>& /* rxParentStates */) 2346 { 2347 // what is with document protection or readonly documents? 2348 return sal_True; 2349 } 2350 2351 void ScAccessibleDocument::AddChild(const uno::Reference<XAccessible>& xAcc, sal_Bool bFireEvent) 2352 { 2353 DBG_ASSERT(!mxTempAcc.is(), "this object should be removed before"); 2354 if (xAcc.is()) 2355 { 2356 mxTempAcc = xAcc; 2357 if( bFireEvent ) 2358 { 2359 AccessibleEventObject aEvent; 2360 aEvent.Source = uno::Reference<XAccessibleContext>(this); 2361 aEvent.EventId = AccessibleEventId::CHILD; 2362 aEvent.NewValue <<= mxTempAcc; 2363 CommitChange( aEvent ); 2364 } 2365 } 2366 } 2367 2368 void ScAccessibleDocument::RemoveChild(const uno::Reference<XAccessible>& xAcc, sal_Bool bFireEvent) 2369 { 2370 DBG_ASSERT(mxTempAcc.is(), "this object should be added before"); 2371 if (xAcc.is()) 2372 { 2373 DBG_ASSERT(xAcc.get() == mxTempAcc.get(), "only the same object should be removed"); 2374 if( bFireEvent ) 2375 { 2376 AccessibleEventObject aEvent; 2377 aEvent.Source = uno::Reference<XAccessibleContext>(this); 2378 aEvent.EventId = AccessibleEventId::CHILD; 2379 aEvent.OldValue <<= mxTempAcc; 2380 CommitChange( aEvent ); 2381 } 2382 mxTempAcc = NULL; 2383 } 2384 } 2385 2386 rtl::OUString ScAccessibleDocument::GetCurrentCellName() const 2387 { 2388 String sName( ScResId(STR_ACC_CELL_NAME) ); 2389 if (mpViewShell) 2390 { 2391 String sAddress; 2392 // Document not needed, because only the cell address, but not the tablename is needed 2393 mpViewShell->GetViewData()->GetCurPos().Format( sAddress, SCA_VALID, NULL ); 2394 sName.SearchAndReplaceAscii("%1", sAddress); 2395 } 2396 return rtl::OUString(sName); 2397 } 2398 2399 rtl::OUString ScAccessibleDocument::GetCurrentCellDescription() const 2400 { 2401 return rtl::OUString(); 2402 } 2403 //IAccessibility2 Implementation 2009----- 2404 ScDocument *ScAccessibleDocument::GetDocument() const 2405 { 2406 return mpViewShell ? mpViewShell->GetViewData()->GetDocument() : NULL; 2407 } 2408 ScAddress ScAccessibleDocument::GetCurCellAddress() const 2409 { 2410 return mpViewShell ? mpViewShell->GetViewData()->GetCurPos() :ScAddress(); 2411 } 2412 uno::Any SAL_CALL ScAccessibleDocument::getExtendedAttributes() 2413 throw (::com::sun::star::lang::IndexOutOfBoundsException, ::com::sun::star::uno::RuntimeException) 2414 { 2415 2416 uno::Any anyAtrribute; 2417 2418 rtl::OUString sName; 2419 rtl::OUString sValue; 2420 sal_uInt16 sheetIndex; 2421 String sSheetName; 2422 sheetIndex = getVisibleTable(); 2423 if(GetDocument()==NULL) 2424 return anyAtrribute; 2425 GetDocument()->GetName(sheetIndex,sSheetName); 2426 sName = rtl::OUString::createFromAscii("page-name:"); 2427 sValue = sName + sSheetName ; 2428 sName = rtl::OUString::createFromAscii(";page-number:"); 2429 sValue += sName; 2430 sValue += String::CreateFromInt32(sheetIndex+1) ; 2431 sName = rtl::OUString::createFromAscii(";total-pages:"); 2432 sValue += sName; 2433 sValue += String::CreateFromInt32(GetDocument()->GetTableCount()); 2434 sValue += rtl::OUString::createFromAscii(";"); 2435 anyAtrribute <<= sValue; 2436 return anyAtrribute; 2437 } 2438 com::sun::star::uno::Sequence< com::sun::star::uno::Any > ScAccessibleDocument::GetScAccFlowToSequence() 2439 { 2440 if ( getAccessibleChildCount() ) 2441 { 2442 uno::Reference < XAccessible > xSCTableAcc = getAccessibleChild( 0 ); // table 2443 if ( xSCTableAcc.is() ) 2444 { 2445 uno::Reference < XAccessibleSelection > xAccSelection( xSCTableAcc, uno::UNO_QUERY ); 2446 sal_Int32 nSelCount = xAccSelection->getSelectedAccessibleChildCount(); 2447 if( nSelCount ) 2448 { 2449 uno::Reference < XAccessible > xSel = xAccSelection->getSelectedAccessibleChild( 0 ); // selected cell 2450 if ( xSel.is() ) 2451 { 2452 uno::Reference < XAccessibleContext > xSelContext( xSel->getAccessibleContext() ); 2453 if ( xSelContext.is() ) 2454 { 2455 if ( xSelContext->getAccessibleRole() == AccessibleRole::TABLE_CELL ) 2456 { 2457 sal_Int32 nParaCount = 0; 2458 uno::Sequence <uno::Any> aSequence(nSelCount); 2459 for ( sal_Int32 i = 0; i < nSelCount; i++ ) 2460 { 2461 xSel = xAccSelection->getSelectedAccessibleChild( i ) ; 2462 if ( xSel.is() ) 2463 { 2464 xSelContext = xSel->getAccessibleContext(); 2465 if ( xSelContext.is() ) 2466 { 2467 if ( xSelContext->getAccessibleRole() == AccessibleRole::TABLE_CELL ) 2468 { 2469 aSequence[nParaCount] = uno::makeAny( xSel ); 2470 nParaCount++; 2471 } 2472 } 2473 } 2474 } 2475 return aSequence; 2476 } 2477 } 2478 } 2479 } 2480 } 2481 } 2482 uno::Sequence <uno::Any> aEmpty; 2483 return aEmpty; 2484 } 2485 ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Any > 2486 SAL_CALL ScAccessibleDocument::get_AccFlowTo(const ::com::sun::star::uno::Any& rAny, sal_Int32 nType) 2487 throw ( ::com::sun::star::uno::RuntimeException ) 2488 { 2489 const sal_Int32 SPELLCHECKFLOWTO = 1; 2490 const sal_Int32 FINDREPLACEFLOWTO = 2; 2491 if ( nType == SPELLCHECKFLOWTO ) 2492 { 2493 uno::Reference< ::com::sun::star::drawing::XShape > xShape; 2494 rAny >>= xShape; 2495 if ( xShape.is() ) 2496 { 2497 uno::Reference < XAccessible > xAcc = mpChildrenShapes->GetAccessibleCaption(xShape); 2498 uno::Reference < XAccessibleSelection > xAccSelection( xAcc, uno::UNO_QUERY ); 2499 if ( xAccSelection.is() ) 2500 { 2501 if ( xAccSelection->getSelectedAccessibleChildCount() ) 2502 { 2503 uno::Reference < XAccessible > xSel = xAccSelection->getSelectedAccessibleChild( 0 ); 2504 if ( xSel.is() ) 2505 { 2506 uno::Reference < XAccessibleContext > xSelContext( xSel->getAccessibleContext() ); 2507 if ( xSelContext.is() ) 2508 { 2509 //if in sw we find the selected paragraph here 2510 if ( xSelContext->getAccessibleRole() == AccessibleRole::PARAGRAPH ) 2511 { 2512 uno::Sequence<uno::Any> aRet( 1 ); 2513 aRet[0] = uno::makeAny( xSel ); 2514 return aRet; 2515 } 2516 } 2517 } 2518 } 2519 } 2520 } 2521 else 2522 { 2523 if ( getSelectedAccessibleChildCount() ) 2524 { 2525 uno::Reference < XAccessible > xSel = getSelectedAccessibleChild( 0 ); 2526 if ( xSel.is() ) 2527 { 2528 uno::Reference < XAccessibleContext > xSelContext( xSel->getAccessibleContext() ); 2529 if ( xSelContext.is() ) 2530 { 2531 uno::Reference < XAccessibleSelection > xAccChildSelection( xSel, uno::UNO_QUERY ); 2532 if ( xAccChildSelection.is() ) 2533 { 2534 if ( xAccChildSelection->getSelectedAccessibleChildCount() ) 2535 { 2536 uno::Reference < XAccessible > xChildSel = xAccChildSelection->getSelectedAccessibleChild( 0 ); 2537 if ( xChildSel.is() ) 2538 { 2539 uno::Reference < ::com::sun::star::accessibility::XAccessibleContext > xChildSelContext( xChildSel->getAccessibleContext() ); 2540 if ( xChildSelContext.is() && 2541 xChildSelContext->getAccessibleRole() == ::com::sun::star::accessibility::AccessibleRole::PARAGRAPH ) 2542 { 2543 uno::Sequence<uno::Any> aRet( 1 ); 2544 aRet[0] = uno::makeAny( xChildSel ); 2545 return aRet; 2546 } 2547 } 2548 } 2549 } 2550 } 2551 } 2552 } 2553 } 2554 } 2555 else if ( nType == FINDREPLACEFLOWTO ) 2556 { 2557 sal_Bool bSuccess; 2558 rAny >>= bSuccess; 2559 if ( bSuccess ) 2560 { 2561 uno::Sequence< uno::Any> aSeq = GetScAccFlowToSequence(); 2562 if ( aSeq.getLength() ) 2563 { 2564 return aSeq; 2565 } 2566 else if( mpAccessibleSpreadsheet ) 2567 { 2568 uno::Reference < XAccessible > xFindCellAcc = mpAccessibleSpreadsheet->GetActiveCell(); 2569 // add xFindCellAcc to the return the Sequence 2570 uno::Sequence< uno::Any> aSeq2(1); 2571 aSeq2[0] = uno::makeAny( xFindCellAcc ); 2572 return aSeq2; 2573 } 2574 } 2575 } 2576 uno::Sequence< uno::Any> aEmpty; 2577 return aEmpty; 2578 } 2579 void ScAccessibleDocument::SwitchViewFireFocus() 2580 { 2581 if (mpAccessibleSpreadsheet) 2582 { 2583 mpAccessibleSpreadsheet->FireFirstCellFocus(); 2584 } 2585 } 2586 2587 sal_Int32 SAL_CALL ScAccessibleDocument::getForeground( ) 2588 throw (uno::RuntimeException) 2589 { 2590 return COL_BLACK; 2591 } 2592 2593 sal_Int32 SAL_CALL ScAccessibleDocument::getBackground( ) 2594 throw (uno::RuntimeException) 2595 { 2596 ScUnoGuard aGuard; 2597 IsObjectValid(); 2598 return SC_MOD()->GetColorConfig().GetColorValue( ::svtools::DOCCOLOR ).nColor; 2599 } 2600 //-----IAccessibility2 Implementation 2009 2601 2602