1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_starmath.hxx" 30 #include <com/sun/star/accessibility/AccessibleRole.hpp> 31 #include <com/sun/star/accessibility/AccessibleStateType.hpp> 32 #include <com/sun/star/accessibility/AccessibleTextType.hpp> 33 #include <com/sun/star/accessibility/XAccessibleEventListener.hpp> 34 #include <com/sun/star/accessibility/AccessibleEventObject.hpp> 35 #include <com/sun/star/awt/FocusEvent.hpp> 36 #include <com/sun/star/awt/XFocusListener.hpp> 37 #include <unotools/accessiblerelationsethelper.hxx> 38 39 40 #include <com/sun/star/datatransfer/clipboard/XClipboard.hpp> 41 #include <com/sun/star/datatransfer/clipboard/XFlushableClipboard.hpp> 42 #include <com/sun/star/i18n/WordType.hpp> 43 #include <unotools/accessiblestatesethelper.hxx> 44 #include <comphelper/accessibleeventnotifier.hxx> 45 #include <tools/debug.hxx> 46 #include <vcl/svapp.hxx> 47 #include <vcl/window.hxx> 48 #include <vcl/unohelp2.hxx> 49 #include <tools/gen.hxx> 50 #include <vos/mutex.hxx> 51 #include <svl/itemset.hxx> 52 53 #include <editeng/editobj.hxx> 54 #include <editeng/editdata.hxx> 55 #include <editeng/editview.hxx> 56 #include <editeng/eeitem.hxx> 57 #include <editeng/outliner.hxx> 58 #include <editeng/unoedhlp.hxx> 59 60 61 #include "accessibility.hxx" 62 #include <applicat.hxx> 63 #include <document.hxx> 64 #include <view.hxx> 65 66 using namespace rtl; 67 using namespace com::sun::star; 68 using namespace com::sun::star::lang; 69 using namespace com::sun::star::uno; 70 using namespace com::sun::star::accessibility; 71 72 #define A2OU(cChar) rtl::OUString::createFromAscii(cChar) 73 74 ////////////////////////////////////////////////////////////////////// 75 76 static awt::Rectangle lcl_GetBounds( Window *pWin ) 77 { 78 // !! see VCLXAccessibleComponent::implGetBounds() 79 80 //! the coordinates returned are relativ to the parent window ! 81 //! Thus the top-left point may be different from (0, 0) ! 82 83 awt::Rectangle aBounds; 84 if (pWin) 85 { 86 Rectangle aRect = pWin->GetWindowExtentsRelative( NULL ); 87 aBounds.X = aRect.Left(); 88 aBounds.Y = aRect.Top(); 89 aBounds.Width = aRect.GetWidth(); 90 aBounds.Height = aRect.GetHeight(); 91 Window* pParent = pWin->GetAccessibleParentWindow(); 92 if (pParent) 93 { 94 Rectangle aParentRect = pParent->GetWindowExtentsRelative( NULL ); 95 awt::Point aParentScreenLoc( aParentRect.Left(), aParentRect.Top() ); 96 aBounds.X -= aParentScreenLoc.X; 97 aBounds.Y -= aParentScreenLoc.Y; 98 } 99 } 100 return aBounds; 101 } 102 103 static awt::Point lcl_GetLocationOnScreen( Window *pWin ) 104 { 105 // !! see VCLXAccessibleComponent::getLocationOnScreen() 106 107 awt::Point aPos; 108 if (pWin) 109 { 110 Rectangle aRect = pWin->GetWindowExtentsRelative( NULL ); 111 aPos.X = aRect.Left(); 112 aPos.Y = aRect.Top(); 113 } 114 return aPos; 115 } 116 117 ////////////////////////////////////////////////////////////////////// 118 119 SmGraphicAccessible::SmGraphicAccessible( SmGraphicWindow *pGraphicWin ) : 120 aAccName ( String(SmResId(RID_DOCUMENTSTR)) ), 121 nClientId (0), 122 pWin (pGraphicWin) 123 { 124 DBG_ASSERT( pWin, "SmGraphicAccessible: window missing" ); 125 //++aRefCount; 126 } 127 128 129 SmGraphicAccessible::SmGraphicAccessible( const SmGraphicAccessible &rSmAcc ) : 130 SmGraphicAccessibleBaseClass(), 131 aAccName ( String(SmResId(RID_DOCUMENTSTR)) ), 132 nClientId (0) 133 { 134 //vos::OGuard aGuard(Application::GetSolarMutex()); 135 pWin = rSmAcc.pWin; 136 DBG_ASSERT( pWin, "SmGraphicAccessible: window missing" ); 137 //++aRefCount; 138 } 139 140 141 SmGraphicAccessible::~SmGraphicAccessible() 142 { 143 /* 144 vos::OGuard aGuard(Application::GetSolarMutex()); 145 if (--aRefCount == 0) 146 { 147 } 148 */ 149 } 150 151 152 SmDocShell * SmGraphicAccessible::GetDoc_Impl() 153 { 154 SmViewShell *pView = pWin ? pWin->GetView() : 0; 155 return pView ? pView->GetDoc() : 0; 156 } 157 158 String SmGraphicAccessible::GetAccessibleText_Impl() 159 { 160 String aTxt; 161 SmDocShell *pDoc = GetDoc_Impl(); 162 if (pDoc) 163 aTxt = pDoc->GetAccessibleText(); 164 return aTxt; 165 } 166 167 void SmGraphicAccessible::ClearWin() 168 { 169 pWin = 0; // implicitly results in AccessibleStateType::DEFUNC set 170 171 if ( nClientId ) 172 { 173 comphelper::AccessibleEventNotifier::revokeClientNotifyDisposing( nClientId, *this ); 174 nClientId = 0; 175 } 176 } 177 178 void SmGraphicAccessible::LaunchEvent( 179 const sal_Int16 nAccesibleEventId, 180 const uno::Any &rOldVal, 181 const uno::Any &rNewVal) 182 { 183 AccessibleEventObject aEvt; 184 aEvt.Source = (XAccessible *) this; 185 aEvt.EventId = nAccesibleEventId; 186 aEvt.OldValue = rOldVal; 187 aEvt.NewValue = rNewVal ; 188 189 // pass event on to event-listener's 190 if (nClientId) 191 comphelper::AccessibleEventNotifier::addEvent( nClientId, aEvt ); 192 } 193 194 uno::Reference< XAccessibleContext > SAL_CALL SmGraphicAccessible::getAccessibleContext() 195 throw (RuntimeException) 196 { 197 vos::OGuard aGuard(Application::GetSolarMutex()); 198 return this; 199 } 200 201 sal_Bool SAL_CALL SmGraphicAccessible::containsPoint( const awt::Point& aPoint ) 202 throw (RuntimeException) 203 { 204 //! the arguments coordinates are relativ to the current window ! 205 //! Thus the top-left point is (0, 0) 206 207 vos::OGuard aGuard(Application::GetSolarMutex()); 208 if (!pWin) 209 throw RuntimeException(); 210 211 Size aSz( pWin->GetSizePixel() ); 212 return aPoint.X >= 0 && aPoint.Y >= 0 && 213 aPoint.X < aSz.Width() && aPoint.Y < aSz.Height(); 214 } 215 216 uno::Reference< XAccessible > SAL_CALL SmGraphicAccessible::getAccessibleAtPoint( 217 const awt::Point& aPoint ) 218 throw (RuntimeException) 219 { 220 vos::OGuard aGuard(Application::GetSolarMutex()); 221 XAccessible *pRes = 0; 222 if (containsPoint( aPoint )) 223 pRes = this; 224 return pRes; 225 } 226 227 awt::Rectangle SAL_CALL SmGraphicAccessible::getBounds() 228 throw (RuntimeException) 229 { 230 vos::OGuard aGuard(Application::GetSolarMutex()); 231 if (!pWin) 232 throw RuntimeException(); 233 DBG_ASSERT(pWin->GetParent()->GetAccessible() == getAccessibleParent(), 234 "mismatch of window parent and accessible parent" ); 235 return lcl_GetBounds( pWin ); 236 } 237 238 awt::Point SAL_CALL SmGraphicAccessible::getLocation() 239 throw (RuntimeException) 240 { 241 vos::OGuard aGuard(Application::GetSolarMutex()); 242 if (!pWin) 243 throw RuntimeException(); 244 DBG_ASSERT(pWin->GetParent()->GetAccessible() == getAccessibleParent(), 245 "mismatch of window parent and accessible parent" ); 246 awt::Rectangle aRect( lcl_GetBounds( pWin ) ); 247 return awt::Point( aRect.X, aRect.Y ); 248 } 249 250 awt::Point SAL_CALL SmGraphicAccessible::getLocationOnScreen() 251 throw (RuntimeException) 252 { 253 vos::OGuard aGuard(Application::GetSolarMutex()); 254 if (!pWin) 255 throw RuntimeException(); 256 DBG_ASSERT(pWin->GetParent()->GetAccessible() == getAccessibleParent(), 257 "mismatch of window parent and accessible parent" ); 258 return lcl_GetLocationOnScreen( pWin ); 259 } 260 261 awt::Size SAL_CALL SmGraphicAccessible::getSize() 262 throw (RuntimeException) 263 { 264 vos::OGuard aGuard(Application::GetSolarMutex()); 265 if (!pWin) 266 throw RuntimeException(); 267 DBG_ASSERT(pWin->GetParent()->GetAccessible() == getAccessibleParent(), 268 "mismatch of window parent and accessible parent" ); 269 270 Size aSz( pWin->GetSizePixel() ); 271 #if OSL_DEBUG_LEVEL > 1 272 awt::Rectangle aRect( lcl_GetBounds( pWin ) ); 273 Size aSz2( aRect.Width, aRect.Height ); 274 DBG_ASSERT( aSz == aSz2, "mismatch in width" ); 275 #endif 276 return awt::Size( aSz.Width(), aSz.Height() ); 277 } 278 279 void SAL_CALL SmGraphicAccessible::grabFocus() 280 throw (RuntimeException) 281 { 282 vos::OGuard aGuard(Application::GetSolarMutex()); 283 if (!pWin) 284 throw RuntimeException(); 285 286 pWin->GrabFocus(); 287 } 288 289 sal_Int32 SAL_CALL SmGraphicAccessible::getForeground() 290 throw (RuntimeException) 291 { 292 vos::OGuard aGuard(Application::GetSolarMutex()); 293 294 if (!pWin) 295 throw RuntimeException(); 296 return (sal_Int32) pWin->GetTextColor().GetColor(); 297 } 298 299 sal_Int32 SAL_CALL SmGraphicAccessible::getBackground() 300 throw (RuntimeException) 301 { 302 vos::OGuard aGuard(Application::GetSolarMutex()); 303 304 if (!pWin) 305 throw RuntimeException(); 306 Wallpaper aWall( pWin->GetDisplayBackground() ); 307 ColorData nCol; 308 if (aWall.IsBitmap() || aWall.IsGradient()) 309 nCol = pWin->GetSettings().GetStyleSettings().GetWindowColor().GetColor(); 310 else 311 nCol = aWall.GetColor().GetColor(); 312 return (sal_Int32) nCol; 313 } 314 315 sal_Int32 SAL_CALL SmGraphicAccessible::getAccessibleChildCount() 316 throw (RuntimeException) 317 { 318 vos::OGuard aGuard(Application::GetSolarMutex()); 319 return 0; 320 } 321 322 Reference< XAccessible > SAL_CALL SmGraphicAccessible::getAccessibleChild( 323 sal_Int32 /*i*/ ) 324 throw (IndexOutOfBoundsException, RuntimeException) 325 { 326 vos::OGuard aGuard(Application::GetSolarMutex()); 327 throw IndexOutOfBoundsException(); // there is no child... 328 /*return 0;*/ 329 } 330 331 Reference< XAccessible > SAL_CALL SmGraphicAccessible::getAccessibleParent() 332 throw (RuntimeException) 333 { 334 vos::OGuard aGuard(Application::GetSolarMutex()); 335 if (!pWin) 336 throw RuntimeException(); 337 338 Window *pAccParent = pWin->GetAccessibleParentWindow(); 339 DBG_ASSERT( pAccParent, "accessible parent missing" ); 340 return pAccParent ? pAccParent->GetAccessible() : Reference< XAccessible >(); 341 } 342 343 sal_Int32 SAL_CALL SmGraphicAccessible::getAccessibleIndexInParent() 344 throw (RuntimeException) 345 { 346 vos::OGuard aGuard(Application::GetSolarMutex()); 347 sal_Int32 nIdx = -1; 348 Window *pAccParent = pWin ? pWin->GetAccessibleParentWindow() : 0; 349 if (pAccParent) 350 { 351 sal_uInt16 nCnt = pAccParent->GetAccessibleChildWindowCount(); 352 for (sal_uInt16 i = 0; i < nCnt && nIdx == -1; ++i) 353 if (pAccParent->GetAccessibleChildWindow( i ) == pWin) 354 nIdx = i; 355 } 356 return nIdx; 357 } 358 359 sal_Int16 SAL_CALL SmGraphicAccessible::getAccessibleRole() 360 throw (RuntimeException) 361 { 362 vos::OGuard aGuard(Application::GetSolarMutex()); 363 return AccessibleRole::DOCUMENT; 364 } 365 366 OUString SAL_CALL SmGraphicAccessible::getAccessibleDescription() 367 throw (RuntimeException) 368 { 369 vos::OGuard aGuard(Application::GetSolarMutex()); 370 SmDocShell *pDoc = GetDoc_Impl(); 371 return pDoc ? OUString(pDoc->GetText()) : OUString(); 372 } 373 374 OUString SAL_CALL SmGraphicAccessible::getAccessibleName() 375 throw (RuntimeException) 376 { 377 vos::OGuard aGuard(Application::GetSolarMutex()); 378 return aAccName; 379 } 380 381 Reference< XAccessibleRelationSet > SAL_CALL SmGraphicAccessible::getAccessibleRelationSet() 382 throw (RuntimeException) 383 { 384 vos::OGuard aGuard(Application::GetSolarMutex()); 385 Reference< XAccessibleRelationSet > xRelSet = new utl::AccessibleRelationSetHelper(); 386 return xRelSet; // empty relation set 387 } 388 389 Reference< XAccessibleStateSet > SAL_CALL SmGraphicAccessible::getAccessibleStateSet() 390 throw (RuntimeException) 391 { 392 vos::OGuard aGuard(Application::GetSolarMutex()); 393 ::utl::AccessibleStateSetHelper *pStateSet = 394 new ::utl::AccessibleStateSetHelper; 395 396 Reference<XAccessibleStateSet> xStateSet( pStateSet ); 397 398 if (!pWin) 399 pStateSet->AddState( AccessibleStateType::DEFUNC ); 400 else 401 { 402 //pStateSet->AddState( AccessibleStateType::EDITABLE ); 403 //pStateSet->AddState( AccessibleStateType::HORIZONTAL ); 404 //pStateSet->AddState( AccessibleStateType::TRANSIENT ); 405 pStateSet->AddState( AccessibleStateType::ENABLED ); 406 pStateSet->AddState( AccessibleStateType::FOCUSABLE ); 407 if (pWin->HasFocus()) 408 pStateSet->AddState( AccessibleStateType::FOCUSED ); 409 if (pWin->IsActive()) 410 pStateSet->AddState( AccessibleStateType::ACTIVE ); 411 if (pWin->IsVisible()) 412 pStateSet->AddState( AccessibleStateType::SHOWING ); 413 if (pWin->IsReallyVisible()) 414 pStateSet->AddState( AccessibleStateType::VISIBLE ); 415 if (COL_TRANSPARENT != pWin->GetBackground().GetColor().GetColor()) 416 pStateSet->AddState( AccessibleStateType::OPAQUE ); 417 } 418 419 return xStateSet; 420 } 421 422 Locale SAL_CALL SmGraphicAccessible::getLocale() 423 throw (IllegalAccessibleComponentStateException, RuntimeException) 424 { 425 vos::OGuard aGuard(Application::GetSolarMutex()); 426 // should be the document language... 427 // We use the language of the localized symbol names here. 428 return Application::GetSettings().GetUILocale(); 429 } 430 431 432 void SAL_CALL SmGraphicAccessible::addEventListener( 433 const Reference< XAccessibleEventListener >& xListener ) 434 throw (RuntimeException) 435 { 436 if (xListener.is()) 437 { 438 vos::OGuard aGuard(Application::GetSolarMutex()); 439 if (pWin) 440 { 441 if (!nClientId) 442 nClientId = comphelper::AccessibleEventNotifier::registerClient( ); 443 comphelper::AccessibleEventNotifier::addEventListener( nClientId, xListener ); 444 } 445 } 446 } 447 448 void SAL_CALL SmGraphicAccessible::removeEventListener( 449 const Reference< XAccessibleEventListener >& xListener ) 450 throw (RuntimeException) 451 { 452 if (xListener.is()) 453 { 454 vos::OGuard aGuard(Application::GetSolarMutex()); 455 sal_Int32 nListenerCount = comphelper::AccessibleEventNotifier::removeEventListener( nClientId, xListener ); 456 if ( !nListenerCount ) 457 { 458 // no listeners anymore 459 // -> revoke ourself. This may lead to the notifier thread dying (if we were the last client), 460 // and at least to us not firing any events anymore, in case somebody calls 461 // NotifyAccessibleEvent, again 462 comphelper::AccessibleEventNotifier::revokeClient( nClientId ); 463 nClientId = 0; 464 } 465 } 466 } 467 468 sal_Int32 SAL_CALL SmGraphicAccessible::getCaretPosition() 469 throw (RuntimeException) 470 { 471 vos::OGuard aGuard(Application::GetSolarMutex()); 472 return 0; 473 } 474 475 sal_Bool SAL_CALL SmGraphicAccessible::setCaretPosition( sal_Int32 nIndex ) 476 throw (IndexOutOfBoundsException, RuntimeException) 477 { 478 xub_StrLen nIdx = (xub_StrLen) nIndex; 479 String aTxt( GetAccessibleText_Impl() ); 480 if (!(/*0 <= nIdx &&*/ nIdx < aTxt.Len())) 481 throw IndexOutOfBoundsException(); 482 return sal_False; 483 } 484 485 sal_Unicode SAL_CALL SmGraphicAccessible::getCharacter( sal_Int32 nIndex ) 486 throw (IndexOutOfBoundsException, RuntimeException) 487 { 488 vos::OGuard aGuard(Application::GetSolarMutex()); 489 490 xub_StrLen nIdx = (xub_StrLen) nIndex; 491 String aTxt( GetAccessibleText_Impl() ); 492 if (!(/*0 <= nIdx &&*/ nIdx < aTxt.Len())) 493 throw IndexOutOfBoundsException(); 494 return aTxt.GetChar( nIdx ); 495 } 496 497 Sequence< beans::PropertyValue > SAL_CALL SmGraphicAccessible::getCharacterAttributes( 498 sal_Int32 nIndex, 499 const uno::Sequence< ::rtl::OUString > & /*rRequestedAttributes*/ ) 500 throw (IndexOutOfBoundsException, RuntimeException) 501 { 502 vos::OGuard aGuard(Application::GetSolarMutex()); 503 sal_Int32 nLen = GetAccessibleText_Impl().Len(); 504 if (!(0 <= nIndex && nIndex < nLen)) 505 throw IndexOutOfBoundsException(); 506 return Sequence< beans::PropertyValue >(); 507 } 508 509 awt::Rectangle SAL_CALL SmGraphicAccessible::getCharacterBounds( sal_Int32 nIndex ) 510 throw (IndexOutOfBoundsException, RuntimeException) 511 { 512 vos::OGuard aGuard(Application::GetSolarMutex()); 513 514 awt::Rectangle aRes; 515 516 if (!pWin) 517 throw RuntimeException(); 518 else 519 { 520 // get accessible text 521 SmViewShell *pView = pWin->GetView(); 522 SmDocShell *pDoc = pView ? pView->GetDoc() : 0; 523 if (!pDoc) 524 throw RuntimeException(); 525 String aTxt( GetAccessibleText_Impl() ); 526 if (!(0 <= nIndex && nIndex <= aTxt.Len())) // #108812# aTxt.Len() is valid 527 throw IndexOutOfBoundsException(); 528 529 // #108812# find a reasonable rectangle for position aTxt.Len(). 530 bool bWasBehindText = (nIndex == aTxt.Len()); 531 if (bWasBehindText && nIndex) 532 --nIndex; 533 534 const SmNode *pTree = pDoc->GetFormulaTree(); 535 const SmNode *pNode = pTree->FindNodeWithAccessibleIndex( (xub_StrLen) nIndex ); 536 //! pNode may be 0 if the index belongs to a char that was inserted 537 //! only for the accessible text! 538 if (pNode) 539 { 540 sal_Int32 nAccIndex = pNode->GetAccessibleIndex(); 541 DBG_ASSERT( nAccIndex >= 0, "invalid accessible index" ); 542 DBG_ASSERT( nIndex >= nAccIndex, "index out of range" ); 543 544 String aNodeText; 545 pNode->GetAccessibleText( aNodeText ); 546 sal_Int32 nNodeIndex = nIndex - nAccIndex; 547 if (0 <= nNodeIndex && nNodeIndex < aNodeText.Len()) 548 { 549 // get appropriate rectangle 550 Point aOffset(pNode->GetTopLeft() - pTree->GetTopLeft()); 551 Point aTLPos (pWin->GetFormulaDrawPos() + aOffset); 552 // aTLPos.X() -= pNode->GetItalicLeftSpace(); 553 // Size aSize (pNode->GetItalicSize()); 554 aTLPos.X() -= 0; 555 Size aSize (pNode->GetSize()); 556 557 sal_Int32 *pXAry = new sal_Int32[ aNodeText.Len() ]; 558 pWin->SetFont( pNode->GetFont() ); 559 pWin->GetTextArray( aNodeText, pXAry, 0, aNodeText.Len() ); 560 aTLPos.X() += nNodeIndex > 0 ? pXAry[nNodeIndex - 1] : 0; 561 aSize.Width() = nNodeIndex > 0 ? pXAry[nNodeIndex] - pXAry[nNodeIndex - 1] : pXAry[nNodeIndex]; 562 delete[] pXAry; 563 564 #if OSL_DEBUG_LEVEL > 1 565 Point aLP00( pWin->LogicToPixel( Point(0,0)) ); 566 Point aPL00( pWin->PixelToLogic( Point(0,0)) ); 567 #endif 568 aTLPos = pWin->LogicToPixel( aTLPos ); 569 aSize = pWin->LogicToPixel( aSize ); 570 aRes.X = aTLPos.X(); 571 aRes.Y = aTLPos.Y(); 572 aRes.Width = aSize.Width(); 573 aRes.Height = aSize.Height(); 574 } 575 } 576 577 // #108812# take rectangle from last character and move it to the right 578 if (bWasBehindText) 579 aRes.X += aRes.Width; 580 } 581 582 return aRes; 583 } 584 585 sal_Int32 SAL_CALL SmGraphicAccessible::getCharacterCount() 586 throw (RuntimeException) 587 { 588 vos::OGuard aGuard(Application::GetSolarMutex()); 589 return GetAccessibleText_Impl().Len(); 590 } 591 592 sal_Int32 SAL_CALL SmGraphicAccessible::getIndexAtPoint( const awt::Point& aPoint ) 593 throw (RuntimeException) 594 { 595 vos::OGuard aGuard(Application::GetSolarMutex()); 596 597 sal_Int32 nRes = -1; 598 if (pWin) 599 { 600 const SmNode *pTree = pWin->GetView()->GetDoc()->GetFormulaTree(); 601 //! kann NULL sein! ZB wenn bereits beim laden des Dokuments (bevor der 602 //! Parser angeworfen wurde) ins Fenster geklickt wird. 603 if (!pTree) 604 return nRes; 605 606 // get position relativ to formula draw position 607 Point aPos( aPoint.X, aPoint.Y ); 608 aPos = pWin->PixelToLogic( aPos ); 609 aPos -= pWin->GetFormulaDrawPos(); 610 611 // if it was inside the formula then get the appropriate node 612 const SmNode *pNode = 0; 613 if (pTree->OrientedDist(aPos) <= 0) 614 pNode = pTree->FindRectClosestTo(aPos); 615 616 if (pNode) 617 { 618 // get appropriate rectangle 619 Point aOffset( pNode->GetTopLeft() - pTree->GetTopLeft() ); 620 Point aTLPos ( /*pWin->GetFormulaDrawPos() +*/ aOffset ); 621 // aTLPos.X() -= pNode->GetItalicLeftSpace(); 622 // Size aSize( pNode->GetItalicSize() ); 623 aTLPos.X() -= 0; 624 Size aSize( pNode->GetSize() ); 625 #if OSL_DEBUG_LEVEL > 1 626 Point aLP00( pWin->LogicToPixel( Point(0,0)) ); 627 Point aPL00( pWin->PixelToLogic( Point(0,0)) ); 628 #endif 629 630 Rectangle aRect( aTLPos, aSize ); 631 if (aRect.IsInside( aPos )) 632 { 633 DBG_ASSERT( pNode->IsVisible(), "node is not a leaf" ); 634 String aTxt; 635 pNode->GetAccessibleText( aTxt ); 636 DBG_ASSERT( aTxt.Len(), "no accessible text available" ); 637 638 long nNodeX = pNode->GetLeft(); 639 640 sal_Int32 *pXAry = new sal_Int32[ aTxt.Len() ]; 641 pWin->SetFont( pNode->GetFont() ); 642 pWin->GetTextArray( aTxt, pXAry, 0, aTxt.Len() ); 643 for (sal_Int32 i = 0; i < aTxt.Len() && nRes == -1; ++i) 644 { 645 if (pXAry[i] + nNodeX > aPos.X()) 646 nRes = i; 647 } 648 delete[] pXAry; 649 DBG_ASSERT( nRes >= 0 && nRes < aTxt.Len(), "index out of range" ); 650 DBG_ASSERT( pNode->GetAccessibleIndex() >= 0, 651 "invalid accessible index" ); 652 653 nRes = pNode->GetAccessibleIndex() + nRes; 654 } 655 } 656 } 657 return nRes; 658 } 659 660 OUString SAL_CALL SmGraphicAccessible::getSelectedText() 661 throw (RuntimeException) 662 { 663 vos::OGuard aGuard(Application::GetSolarMutex()); 664 return OUString(); 665 } 666 667 sal_Int32 SAL_CALL SmGraphicAccessible::getSelectionStart() 668 throw (RuntimeException) 669 { 670 vos::OGuard aGuard(Application::GetSolarMutex()); 671 return -1; 672 } 673 674 sal_Int32 SAL_CALL SmGraphicAccessible::getSelectionEnd() 675 throw (RuntimeException) 676 { 677 vos::OGuard aGuard(Application::GetSolarMutex()); 678 return -1; 679 } 680 681 sal_Bool SAL_CALL SmGraphicAccessible::setSelection( 682 sal_Int32 nStartIndex, 683 sal_Int32 nEndIndex ) 684 throw (IndexOutOfBoundsException, RuntimeException) 685 { 686 vos::OGuard aGuard(Application::GetSolarMutex()); 687 sal_Int32 nLen = GetAccessibleText_Impl().Len(); 688 if (!(0 <= nStartIndex && nStartIndex < nLen) || 689 !(0 <= nEndIndex && nEndIndex < nLen)) 690 throw IndexOutOfBoundsException(); 691 return sal_False; 692 } 693 694 OUString SAL_CALL SmGraphicAccessible::getText() 695 throw (RuntimeException) 696 { 697 vos::OGuard aGuard(Application::GetSolarMutex()); 698 return GetAccessibleText_Impl(); 699 } 700 701 OUString SAL_CALL SmGraphicAccessible::getTextRange( 702 sal_Int32 nStartIndex, 703 sal_Int32 nEndIndex ) 704 throw (IndexOutOfBoundsException, RuntimeException) 705 { 706 //!! nEndIndex may be the string length per definition of the interface !! 707 //!! text should be copied exclusive that end index though. And arguments 708 //!! may be switched. 709 710 vos::OGuard aGuard(Application::GetSolarMutex()); 711 String aTxt( GetAccessibleText_Impl() ); 712 xub_StrLen nStart = (xub_StrLen) Min(nStartIndex, nEndIndex); 713 xub_StrLen nEnd = (xub_StrLen) Max(nStartIndex, nEndIndex); 714 if (!(/*0 <= nStart &&*/ nStart <= aTxt.Len()) || 715 !(/*0 <= nEnd &&*/ nEnd <= aTxt.Len())) 716 throw IndexOutOfBoundsException(); 717 return aTxt.Copy( nStart, nEnd - nStart ); 718 } 719 720 ::com::sun::star::accessibility::TextSegment SAL_CALL SmGraphicAccessible::getTextAtIndex( sal_Int32 nIndex, sal_Int16 aTextType ) throw (::com::sun::star::lang::IndexOutOfBoundsException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException) 721 { 722 vos::OGuard aGuard(Application::GetSolarMutex()); 723 String aTxt( GetAccessibleText_Impl() ); 724 xub_StrLen nIdx = (xub_StrLen) nIndex; 725 //!! nIndex is allowed to be the string length 726 if (!(/*0 <= nIdx &&*/ nIdx <= aTxt.Len())) 727 throw IndexOutOfBoundsException(); 728 729 ::com::sun::star::accessibility::TextSegment aResult; 730 aResult.SegmentStart = -1; 731 aResult.SegmentEnd = -1; 732 if ( (AccessibleTextType::CHARACTER == aTextType) && (nIdx < aTxt.Len()) ) 733 { 734 aResult.SegmentText = aTxt.Copy(nIdx, 1); 735 aResult.SegmentStart = nIdx; 736 aResult.SegmentEnd = nIdx+1; 737 } 738 return aResult; 739 } 740 741 ::com::sun::star::accessibility::TextSegment SAL_CALL SmGraphicAccessible::getTextBeforeIndex( sal_Int32 nIndex, sal_Int16 aTextType ) throw (::com::sun::star::lang::IndexOutOfBoundsException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException) 742 { 743 vos::OGuard aGuard(Application::GetSolarMutex()); 744 String aTxt( GetAccessibleText_Impl() ); 745 xub_StrLen nIdx = (xub_StrLen) nIndex; 746 //!! nIndex is allowed to be the string length 747 if (!(/*0 <= nIdx &&*/ nIdx <= aTxt.Len())) 748 throw IndexOutOfBoundsException(); 749 750 ::com::sun::star::accessibility::TextSegment aResult; 751 aResult.SegmentStart = -1; 752 aResult.SegmentEnd = -1; 753 754 if ( (AccessibleTextType::CHARACTER == aTextType) && nIdx ) 755 { 756 aResult.SegmentText = aTxt.Copy(nIdx-1, 1); 757 aResult.SegmentStart = nIdx-1; 758 aResult.SegmentEnd = nIdx; 759 } 760 return aResult; 761 } 762 763 ::com::sun::star::accessibility::TextSegment SAL_CALL SmGraphicAccessible::getTextBehindIndex( sal_Int32 nIndex, sal_Int16 aTextType ) throw (::com::sun::star::lang::IndexOutOfBoundsException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException) 764 { 765 vos::OGuard aGuard(Application::GetSolarMutex()); 766 String aTxt( GetAccessibleText_Impl() ); 767 xub_StrLen nIdx = (xub_StrLen) nIndex; 768 //!! nIndex is allowed to be the string length 769 if (!(/*0 <= nIdx &&*/ nIdx <= aTxt.Len())) 770 throw IndexOutOfBoundsException(); 771 772 ::com::sun::star::accessibility::TextSegment aResult; 773 aResult.SegmentStart = -1; 774 aResult.SegmentEnd = -1; 775 776 nIdx++; // text *behind* 777 if ( (AccessibleTextType::CHARACTER == aTextType) && (nIdx < aTxt.Len()) ) 778 { 779 aResult.SegmentText = aTxt.Copy(nIdx, 1); 780 aResult.SegmentStart = nIdx; 781 aResult.SegmentEnd = nIdx+1; 782 } 783 return aResult; 784 } 785 786 sal_Bool SAL_CALL SmGraphicAccessible::copyText( 787 sal_Int32 nStartIndex, 788 sal_Int32 nEndIndex ) 789 throw (IndexOutOfBoundsException, RuntimeException) 790 { 791 vos::OGuard aGuard(Application::GetSolarMutex()); 792 sal_Bool bReturn = sal_False; 793 794 if (!pWin) 795 throw RuntimeException(); 796 else 797 { 798 Reference< datatransfer::clipboard::XClipboard > xClipboard = pWin->GetClipboard(); 799 if ( xClipboard.is() ) 800 { 801 ::rtl::OUString sText( getTextRange(nStartIndex, nEndIndex) ); 802 803 ::vcl::unohelper::TextDataObject* pDataObj = new ::vcl::unohelper::TextDataObject( sText ); 804 const sal_uInt32 nRef = Application::ReleaseSolarMutex(); 805 xClipboard->setContents( pDataObj, NULL ); 806 807 Reference< datatransfer::clipboard::XFlushableClipboard > xFlushableClipboard( xClipboard, uno::UNO_QUERY ); 808 if( xFlushableClipboard.is() ) 809 xFlushableClipboard->flushClipboard(); 810 811 Application::AcquireSolarMutex( nRef ); 812 813 bReturn = sal_True; 814 } 815 } 816 817 return bReturn; 818 } 819 820 OUString SAL_CALL SmGraphicAccessible::getImplementationName() 821 throw (RuntimeException) 822 { 823 //vos::OGuard aGuard(Application::GetSolarMutex()); 824 return A2OU("SmGraphicAccessible"); 825 } 826 827 sal_Bool SAL_CALL SmGraphicAccessible::supportsService( 828 const OUString& rServiceName ) 829 throw (RuntimeException) 830 { 831 //vos::OGuard aGuard(Application::GetSolarMutex()); 832 return rServiceName == A2OU( "com::sun::star::accessibility::Accessible" ) || 833 rServiceName == A2OU( "com::sun::star::accessibility::AccessibleComponent" ) || 834 rServiceName == A2OU( "com::sun::star::accessibility::AccessibleContext" ) || 835 rServiceName == A2OU( "com::sun::star::accessibility::AccessibleText" ); 836 } 837 838 Sequence< OUString > SAL_CALL SmGraphicAccessible::getSupportedServiceNames() 839 throw (RuntimeException) 840 { 841 //vos::OGuard aGuard(Application::GetSolarMutex()); 842 Sequence< OUString > aNames(4); 843 OUString *pNames = aNames.getArray(); 844 pNames[0] = A2OU( "com::sun::star::accessibility::Accessible" ); 845 pNames[1] = A2OU( "com::sun::star::accessibility::AccessibleComponent" ); 846 pNames[2] = A2OU( "com::sun::star::accessibility::AccessibleContext" ); 847 pNames[3] = A2OU( "com::sun::star::accessibility::AccessibleText" ); 848 return aNames; 849 } 850 851 ////////////////////////////////////////////////////////////////////// 852 853 //------------------------------------------------------------------------ 854 855 SmEditSource::SmEditSource( SmEditWindow * /*pWin*/, SmEditAccessible &rAcc ) : 856 aViewFwd (rAcc), 857 aTextFwd (rAcc, *this), 858 aEditViewFwd(rAcc), 859 rEditAcc (rAcc) 860 { 861 } 862 863 SmEditSource::SmEditSource( const SmEditSource &rSrc ) : 864 SvxEditSource(), 865 aViewFwd (rSrc.rEditAcc), 866 aTextFwd (rSrc.rEditAcc, *this), 867 aEditViewFwd(rSrc.rEditAcc), 868 rEditAcc (rSrc.rEditAcc) 869 { 870 //aBroadCaster; can be completely new 871 } 872 873 SmEditSource::~SmEditSource() 874 { 875 } 876 877 SvxEditSource* SmEditSource::Clone() const 878 { 879 return new SmEditSource( *this ); 880 } 881 882 SvxTextForwarder* SmEditSource::GetTextForwarder() 883 { 884 return &aTextFwd; 885 } 886 887 SvxViewForwarder* SmEditSource::GetViewForwarder() 888 { 889 return &aViewFwd; 890 } 891 892 SvxEditViewForwarder* SmEditSource::GetEditViewForwarder( sal_Bool /*bCreate*/ ) 893 { 894 return &aEditViewFwd; 895 } 896 897 void SmEditSource::UpdateData() 898 { 899 // would possibly only by needed if the XText inteface is implemented 900 // and its text needs to be updated. 901 } 902 903 SfxBroadcaster & SmEditSource::GetBroadcaster() const 904 { 905 return ((SmEditSource *) this)->aBroadCaster; 906 } 907 908 //------------------------------------------------------------------------ 909 910 SmViewForwarder::SmViewForwarder( SmEditAccessible &rAcc ) : 911 rEditAcc(rAcc) 912 { 913 } 914 915 SmViewForwarder::~SmViewForwarder() 916 { 917 } 918 919 sal_Bool SmViewForwarder::IsValid() const 920 { 921 return rEditAcc.GetEditView() != 0; 922 } 923 924 Rectangle SmViewForwarder::GetVisArea() const 925 { 926 EditView *pEditView = rEditAcc.GetEditView(); 927 OutputDevice* pOutDev = pEditView ? pEditView->GetWindow() : 0; 928 929 if( pOutDev && pEditView) 930 { 931 Rectangle aVisArea = pEditView->GetVisArea(); 932 933 // figure out map mode from edit engine 934 EditEngine* pEditEngine = pEditView->GetEditEngine(); 935 936 if( pEditEngine ) 937 { 938 MapMode aMapMode(pOutDev->GetMapMode()); 939 aVisArea = OutputDevice::LogicToLogic( aVisArea, 940 pEditEngine->GetRefMapMode(), 941 aMapMode.GetMapUnit() ); 942 aMapMode.SetOrigin(Point()); 943 return pOutDev->LogicToPixel( aVisArea, aMapMode ); 944 } 945 } 946 947 return Rectangle(); 948 } 949 950 Point SmViewForwarder::LogicToPixel( const Point& rPoint, const MapMode& rMapMode ) const 951 { 952 EditView *pEditView = rEditAcc.GetEditView(); 953 OutputDevice* pOutDev = pEditView ? pEditView->GetWindow() : 0; 954 955 if( pOutDev ) 956 { 957 MapMode aMapMode(pOutDev->GetMapMode()); 958 Point aPoint( OutputDevice::LogicToLogic( rPoint, rMapMode, 959 aMapMode.GetMapUnit() ) ); 960 aMapMode.SetOrigin(Point()); 961 return pOutDev->LogicToPixel( aPoint, aMapMode ); 962 } 963 964 return Point(); 965 } 966 967 Point SmViewForwarder::PixelToLogic( const Point& rPoint, const MapMode& rMapMode ) const 968 { 969 EditView *pEditView = rEditAcc.GetEditView(); 970 OutputDevice* pOutDev = pEditView ? pEditView->GetWindow() : 0; 971 972 if( pOutDev ) 973 { 974 MapMode aMapMode(pOutDev->GetMapMode()); 975 aMapMode.SetOrigin(Point()); 976 Point aPoint( pOutDev->PixelToLogic( rPoint, aMapMode ) ); 977 return OutputDevice::LogicToLogic( aPoint, 978 aMapMode.GetMapUnit(), 979 rMapMode ); 980 } 981 982 return Point(); 983 } 984 985 986 //------------------------------------------------------------------------ 987 988 SmTextForwarder::SmTextForwarder( SmEditAccessible& rAcc, SmEditSource & rSource) : 989 rEditAcc ( rAcc ), 990 rEditSource (rSource) 991 { 992 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 993 if (pEditEngine) 994 pEditEngine->SetNotifyHdl( LINK(this, SmTextForwarder, NotifyHdl) ); 995 } 996 997 SmTextForwarder::~SmTextForwarder() 998 { 999 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1000 if (pEditEngine) 1001 pEditEngine->SetNotifyHdl( Link() ); 1002 } 1003 1004 IMPL_LINK(SmTextForwarder, NotifyHdl, EENotify*, aNotify) 1005 { 1006 if (aNotify) 1007 { 1008 ::std::auto_ptr< SfxHint > aHint = SvxEditSourceHelper::EENotification2Hint( aNotify ); 1009 if (aHint.get()) 1010 rEditSource.GetBroadcaster().Broadcast( *aHint.get() ); 1011 } 1012 1013 return 0; 1014 } 1015 1016 sal_uInt16 SmTextForwarder::GetParagraphCount() const 1017 { 1018 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1019 return pEditEngine ? pEditEngine->GetParagraphCount() : 0; 1020 } 1021 1022 sal_uInt16 SmTextForwarder::GetTextLen( sal_uInt16 nParagraph ) const 1023 { 1024 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1025 return pEditEngine ? pEditEngine->GetTextLen( nParagraph ) : 0; 1026 } 1027 1028 String SmTextForwarder::GetText( const ESelection& rSel ) const 1029 { 1030 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1031 String aRet; 1032 if (pEditEngine) 1033 aRet = pEditEngine->GetText( rSel, LINEEND_LF ); 1034 aRet.ConvertLineEnd(); 1035 return aRet; 1036 } 1037 1038 SfxItemSet SmTextForwarder::GetAttribs( const ESelection& rSel, sal_Bool bOnlyHardAttrib ) const 1039 { 1040 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1041 DBG_ASSERT( pEditEngine, "EditEngine missing" ); 1042 if( rSel.nStartPara == rSel.nEndPara ) 1043 { 1044 sal_uInt8 nFlags = 0; 1045 switch( bOnlyHardAttrib ) 1046 { 1047 case EditEngineAttribs_All: 1048 nFlags = GETATTRIBS_ALL; 1049 break; 1050 case EditEngineAttribs_HardAndPara: 1051 nFlags = GETATTRIBS_PARAATTRIBS|GETATTRIBS_CHARATTRIBS; 1052 break; 1053 case EditEngineAttribs_OnlyHard: 1054 nFlags = GETATTRIBS_CHARATTRIBS; 1055 break; 1056 default: 1057 DBG_ERROR("unknown flags for SmTextForwarder::GetAttribs"); 1058 } 1059 1060 return pEditEngine->GetAttribs( rSel.nStartPara, rSel.nStartPos, rSel.nEndPos, nFlags ); 1061 } 1062 else 1063 { 1064 return pEditEngine->GetAttribs( rSel, bOnlyHardAttrib ); 1065 } 1066 } 1067 1068 SfxItemSet SmTextForwarder::GetParaAttribs( sal_uInt16 nPara ) const 1069 { 1070 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1071 DBG_ASSERT( pEditEngine, "EditEngine missing" ); 1072 1073 SfxItemSet aSet( pEditEngine->GetParaAttribs( nPara ) ); 1074 1075 sal_uInt16 nWhich = EE_PARA_START; 1076 while( nWhich <= EE_PARA_END ) 1077 { 1078 if( aSet.GetItemState( nWhich, sal_True ) != SFX_ITEM_ON ) 1079 { 1080 if( pEditEngine->HasParaAttrib( nPara, nWhich ) ) 1081 aSet.Put( pEditEngine->GetParaAttrib( nPara, nWhich ) ); 1082 } 1083 nWhich++; 1084 } 1085 1086 return aSet; 1087 } 1088 1089 void SmTextForwarder::SetParaAttribs( sal_uInt16 nPara, const SfxItemSet& rSet ) 1090 { 1091 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1092 if (pEditEngine) 1093 pEditEngine->SetParaAttribs( nPara, rSet ); 1094 } 1095 1096 SfxItemPool* SmTextForwarder::GetPool() const 1097 { 1098 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1099 return pEditEngine ? pEditEngine->GetEmptyItemSet().GetPool() : 0; 1100 } 1101 1102 void SmTextForwarder::RemoveAttribs( const ESelection& rSelection, sal_Bool bRemoveParaAttribs, sal_uInt16 nWhich ) 1103 { 1104 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1105 if (pEditEngine) 1106 pEditEngine->RemoveAttribs( rSelection, bRemoveParaAttribs, nWhich ); 1107 } 1108 1109 void SmTextForwarder::GetPortions( sal_uInt16 nPara, SvUShorts& rList ) const 1110 { 1111 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1112 if (pEditEngine) 1113 pEditEngine->GetPortions( nPara, rList ); 1114 } 1115 1116 void SmTextForwarder::QuickInsertText( const String& rText, const ESelection& rSel ) 1117 { 1118 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1119 if (pEditEngine) 1120 pEditEngine->QuickInsertText( rText, rSel ); 1121 } 1122 1123 void SmTextForwarder::QuickInsertLineBreak( const ESelection& rSel ) 1124 { 1125 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1126 if (pEditEngine) 1127 pEditEngine->QuickInsertLineBreak( rSel ); 1128 } 1129 1130 void SmTextForwarder::QuickInsertField( const SvxFieldItem& rFld, const ESelection& rSel ) 1131 { 1132 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1133 if (pEditEngine) 1134 pEditEngine->QuickInsertField( rFld, rSel ); 1135 } 1136 1137 void SmTextForwarder::QuickSetAttribs( const SfxItemSet& rSet, const ESelection& rSel ) 1138 { 1139 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1140 if (pEditEngine) 1141 pEditEngine->QuickSetAttribs( rSet, rSel ); 1142 } 1143 1144 sal_Bool SmTextForwarder::IsValid() const 1145 { 1146 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1147 // cannot reliably query EditEngine state 1148 // while in the middle of an update 1149 return pEditEngine ? pEditEngine->GetUpdateMode() : sal_False; 1150 } 1151 1152 XubString SmTextForwarder::CalcFieldValue( const SvxFieldItem& rField, sal_uInt16 nPara, sal_uInt16 nPos, Color*& rpTxtColor, Color*& rpFldColor ) 1153 { 1154 XubString aTxt; 1155 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1156 if (pEditEngine) 1157 aTxt = pEditEngine->CalcFieldValue( rField, nPara, nPos, rpTxtColor, rpFldColor ); 1158 return aTxt; 1159 } 1160 1161 void SmTextForwarder::FieldClicked(const SvxFieldItem&, sal_uInt16, sal_uInt16) 1162 { 1163 } 1164 1165 sal_uInt16 GetSvxEditEngineItemState( EditEngine& rEditEngine, const ESelection& rSel, sal_uInt16 nWhich ) 1166 { 1167 EECharAttribArray aAttribs; 1168 1169 const SfxPoolItem* pLastItem = NULL; 1170 1171 SfxItemState eState = SFX_ITEM_DEFAULT; 1172 1173 // check all paragraphs inside the selection 1174 for( sal_uInt16 nPara = rSel.nStartPara; nPara <= rSel.nEndPara; nPara++ ) 1175 { 1176 SfxItemState eParaState = SFX_ITEM_DEFAULT; 1177 1178 // calculate start and endpos for this paragraph 1179 sal_uInt16 nPos = 0; 1180 if( rSel.nStartPara == nPara ) 1181 nPos = rSel.nStartPos; 1182 1183 sal_uInt16 nEndPos = rSel.nEndPos; 1184 if( rSel.nEndPara != nPara ) 1185 nEndPos = rEditEngine.GetTextLen( nPara ); 1186 1187 1188 // get list of char attribs 1189 rEditEngine.GetCharAttribs( nPara, aAttribs ); 1190 1191 sal_Bool bEmpty = sal_True; // we found no item inside the selektion of this paragraph 1192 sal_Bool bGaps = sal_False; // we found items but theire gaps between them 1193 sal_uInt16 nLastEnd = nPos; 1194 1195 const SfxPoolItem* pParaItem = NULL; 1196 1197 for( sal_uInt16 nAttrib = 0; nAttrib < aAttribs.Count(); nAttrib++ ) 1198 { 1199 struct EECharAttrib aAttrib = aAttribs.GetObject( nAttrib ); 1200 DBG_ASSERT( aAttrib.pAttr, "GetCharAttribs gives corrupt data" ); 1201 1202 const sal_Bool bEmptyPortion = aAttrib.nStart == aAttrib.nEnd; 1203 if( (!bEmptyPortion && (aAttrib.nStart >= nEndPos)) || (bEmptyPortion && (aAttrib.nStart > nEndPos)) ) 1204 break; // break if we are already behind our selektion 1205 1206 if( (!bEmptyPortion && (aAttrib.nEnd <= nPos)) || (bEmptyPortion && (aAttrib.nEnd < nPos)) ) 1207 continue; // or if the attribute ends before our selektion 1208 1209 if( aAttrib.pAttr->Which() != nWhich ) 1210 continue; // skip if is not the searched item 1211 1212 // if we already found an item 1213 if( pParaItem ) 1214 { 1215 // ... and its different to this one than the state is dont care 1216 if( *pParaItem != *aAttrib.pAttr ) 1217 return SFX_ITEM_DONTCARE; 1218 } 1219 else 1220 { 1221 pParaItem = aAttrib.pAttr; 1222 } 1223 1224 if( bEmpty ) 1225 bEmpty = sal_False; 1226 1227 if( !bGaps && aAttrib.nStart > nLastEnd ) 1228 bGaps = sal_True; 1229 1230 nLastEnd = aAttrib.nEnd; 1231 } 1232 1233 if( !bEmpty && !bGaps && nLastEnd < ( nEndPos - 1 ) ) 1234 bGaps = sal_True; 1235 /* 1236 // since we have no portion with our item or if there were gaps 1237 if( bEmpty || bGaps ) 1238 { 1239 // we need to check the paragraph item 1240 const SfxItemSet& rParaSet = rEditEngine.GetParaAttribs( nPara ); 1241 if( rParaSet.GetItemState( nWhich ) == SFX_ITEM_SET ) 1242 { 1243 eState = SFX_ITEM_SET; 1244 // get item from the paragraph 1245 const SfxPoolItem* pTempItem = rParaSet.GetItem( nWhich ); 1246 if( pParaItem ) 1247 { 1248 if( *pParaItem != *pTempItem ) 1249 return SFX_ITEM_DONTCARE; 1250 } 1251 else 1252 { 1253 pParaItem = pTempItem; 1254 } 1255 1256 // set if theres no last item or if its the same 1257 eParaState = SFX_ITEM_SET; 1258 } 1259 else if( bEmpty ) 1260 { 1261 eParaState = SFX_ITEM_DEFAULT; 1262 } 1263 else if( bGaps ) 1264 { 1265 // gaps and item not set in paragraph, thats a dont care 1266 return SFX_ITEM_DONTCARE; 1267 } 1268 } 1269 else 1270 { 1271 eParaState = SFX_ITEM_SET; 1272 } 1273 */ 1274 if( bEmpty ) 1275 eParaState = SFX_ITEM_DEFAULT; 1276 else if( bGaps ) 1277 eParaState = SFX_ITEM_DONTCARE; 1278 else 1279 eParaState = SFX_ITEM_SET; 1280 1281 // if we already found an item check if we found the same 1282 if( pLastItem ) 1283 { 1284 if( (pParaItem == NULL) || (*pLastItem != *pParaItem) ) 1285 return SFX_ITEM_DONTCARE; 1286 } 1287 else 1288 { 1289 pLastItem = pParaItem; 1290 eState = eParaState; 1291 } 1292 } 1293 1294 return eState; 1295 } 1296 1297 sal_uInt16 SmTextForwarder::GetItemState( const ESelection& rSel, sal_uInt16 nWhich ) const 1298 { 1299 sal_uInt16 nState = SFX_ITEM_DISABLED; 1300 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1301 if (pEditEngine) 1302 nState = GetSvxEditEngineItemState( *pEditEngine, rSel, nWhich ); 1303 return nState; 1304 } 1305 1306 sal_uInt16 SmTextForwarder::GetItemState( sal_uInt16 nPara, sal_uInt16 nWhich ) const 1307 { 1308 sal_uInt16 nState = SFX_ITEM_DISABLED; 1309 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1310 if (pEditEngine) 1311 { 1312 const SfxItemSet& rSet = pEditEngine->GetParaAttribs( nPara ); 1313 nState = rSet.GetItemState( nWhich ); 1314 } 1315 return nState; 1316 } 1317 1318 LanguageType SmTextForwarder::GetLanguage( sal_uInt16 nPara, sal_uInt16 nIndex ) const 1319 { 1320 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1321 return pEditEngine ? pEditEngine->GetLanguage(nPara, nIndex) : LANGUAGE_NONE; 1322 } 1323 1324 sal_uInt16 SmTextForwarder::GetFieldCount( sal_uInt16 nPara ) const 1325 { 1326 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1327 return pEditEngine ? pEditEngine->GetFieldCount(nPara) : 0; 1328 } 1329 1330 EFieldInfo SmTextForwarder::GetFieldInfo( sal_uInt16 nPara, sal_uInt16 nField ) const 1331 { 1332 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1333 return pEditEngine ? pEditEngine->GetFieldInfo( nPara, nField ) : EFieldInfo(); 1334 } 1335 1336 EBulletInfo SmTextForwarder::GetBulletInfo( sal_uInt16 /*nPara*/ ) const 1337 { 1338 return EBulletInfo(); 1339 } 1340 1341 Rectangle SmTextForwarder::GetCharBounds( sal_uInt16 nPara, sal_uInt16 nIndex ) const 1342 { 1343 Rectangle aRect(0,0,0,0); 1344 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1345 1346 if (pEditEngine) 1347 { 1348 // #108900# Handle virtual position one-past-the end of the string 1349 if( nIndex >= pEditEngine->GetTextLen(nPara) ) 1350 { 1351 if( nIndex ) 1352 aRect = pEditEngine->GetCharacterBounds( EPosition(nPara, nIndex-1) ); 1353 1354 aRect.Move( aRect.Right() - aRect.Left(), 0 ); 1355 aRect.SetSize( Size(1, pEditEngine->GetTextHeight()) ); 1356 } 1357 else 1358 { 1359 aRect = pEditEngine->GetCharacterBounds( EPosition(nPara, nIndex) ); 1360 } 1361 } 1362 return aRect; 1363 } 1364 1365 Rectangle SmTextForwarder::GetParaBounds( sal_uInt16 nPara ) const 1366 { 1367 Rectangle aRect(0,0,0,0); 1368 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1369 1370 if (pEditEngine) 1371 { 1372 const Point aPnt = pEditEngine->GetDocPosTopLeft( nPara ); 1373 const sal_uLong nWidth = pEditEngine->CalcTextWidth(); 1374 const sal_uLong nHeight = pEditEngine->GetTextHeight( nPara ); 1375 aRect = Rectangle( aPnt.X(), aPnt.Y(), aPnt.X() + nWidth, aPnt.Y() + nHeight ); 1376 } 1377 1378 return aRect; 1379 } 1380 1381 MapMode SmTextForwarder::GetMapMode() const 1382 { 1383 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1384 return pEditEngine ? pEditEngine->GetRefMapMode() : MapMode( MAP_100TH_MM ); 1385 } 1386 1387 OutputDevice* SmTextForwarder::GetRefDevice() const 1388 { 1389 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1390 return pEditEngine ? pEditEngine->GetRefDevice() : 0; 1391 } 1392 1393 sal_Bool SmTextForwarder::GetIndexAtPoint( const Point& rPos, sal_uInt16& nPara, sal_uInt16& nIndex ) const 1394 { 1395 sal_Bool bRes = sal_False; 1396 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1397 if (pEditEngine) 1398 { 1399 EPosition aDocPos = pEditEngine->FindDocPosition( rPos ); 1400 nPara = aDocPos.nPara; 1401 nIndex = aDocPos.nIndex; 1402 bRes = sal_True; 1403 } 1404 return bRes; 1405 } 1406 1407 sal_Bool SmTextForwarder::GetWordIndices( sal_uInt16 nPara, sal_uInt16 nIndex, sal_uInt16& nStart, sal_uInt16& nEnd ) const 1408 { 1409 sal_Bool bRes = sal_False; 1410 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1411 if (pEditEngine) 1412 { 1413 ESelection aRes = pEditEngine->GetWord( ESelection(nPara, nIndex, nPara, nIndex), com::sun::star::i18n::WordType::DICTIONARY_WORD ); 1414 1415 if( aRes.nStartPara == nPara && 1416 aRes.nStartPara == aRes.nEndPara ) 1417 { 1418 nStart = aRes.nStartPos; 1419 nEnd = aRes.nEndPos; 1420 1421 bRes = sal_True; 1422 } 1423 } 1424 1425 return bRes; 1426 } 1427 1428 sal_Bool SmTextForwarder::GetAttributeRun( sal_uInt16& nStartIndex, sal_uInt16& nEndIndex, sal_uInt16 nPara, sal_uInt16 nIndex ) const 1429 { 1430 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1431 return pEditEngine ? 1432 SvxEditSourceHelper::GetAttributeRun( nStartIndex, nEndIndex, *pEditEngine, nPara, nIndex ) 1433 : sal_False; 1434 } 1435 1436 sal_uInt16 SmTextForwarder::GetLineCount( sal_uInt16 nPara ) const 1437 { 1438 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1439 return pEditEngine ? pEditEngine->GetLineCount(nPara) : 0; 1440 } 1441 1442 sal_uInt16 SmTextForwarder::GetLineLen( sal_uInt16 nPara, sal_uInt16 nLine ) const 1443 { 1444 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1445 return pEditEngine ? pEditEngine->GetLineLen(nPara, nLine) : 0; 1446 } 1447 1448 void SmTextForwarder::GetLineBoundaries( /*out*/sal_uInt16 &rStart, /*out*/sal_uInt16 &rEnd, sal_uInt16 nPara, sal_uInt16 nLine ) const 1449 { 1450 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1451 pEditEngine->GetLineBoundaries(rStart, rEnd, nPara, nLine); 1452 } 1453 1454 sal_uInt16 SmTextForwarder::GetLineNumberAtIndex( sal_uInt16 nPara, sal_uInt16 nIndex ) const 1455 { 1456 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1457 return pEditEngine ? pEditEngine->GetLineNumberAtIndex(nPara, nIndex) : 0; 1458 } 1459 1460 sal_Bool SmTextForwarder::QuickFormatDoc( sal_Bool /*bFull*/ ) 1461 { 1462 sal_Bool bRes = sal_False; 1463 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1464 if (pEditEngine) 1465 { 1466 pEditEngine->QuickFormatDoc(); 1467 bRes = sal_True; 1468 } 1469 return bRes; 1470 } 1471 1472 sal_Int16 SmTextForwarder::GetDepth( sal_uInt16 /*nPara*/ ) const 1473 { 1474 // math has no outliner... 1475 return -1; 1476 } 1477 1478 sal_Bool SmTextForwarder::SetDepth( sal_uInt16 /*nPara*/, sal_Int16 nNewDepth ) 1479 { 1480 // math has no outliner... 1481 return -1 == nNewDepth; // is it the value from 'GetDepth' ? 1482 } 1483 1484 sal_Bool SmTextForwarder::Delete( const ESelection& rSelection ) 1485 { 1486 sal_Bool bRes = sal_False; 1487 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1488 if (pEditEngine) 1489 { 1490 pEditEngine->QuickDelete( rSelection ); 1491 pEditEngine->QuickFormatDoc(); 1492 bRes = sal_True; 1493 } 1494 return bRes; 1495 } 1496 1497 sal_Bool SmTextForwarder::InsertText( const String& rStr, const ESelection& rSelection ) 1498 { 1499 sal_Bool bRes = sal_False; 1500 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1501 if (pEditEngine) 1502 { 1503 pEditEngine->QuickInsertText( rStr, rSelection ); 1504 pEditEngine->QuickFormatDoc(); 1505 bRes = sal_True; 1506 } 1507 return bRes; 1508 } 1509 1510 const SfxItemSet* SmTextForwarder::GetEmptyItemSetPtr() 1511 { 1512 const SfxItemSet *pItemSet = 0; 1513 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1514 if (pEditEngine) 1515 { 1516 pItemSet = &pEditEngine->GetEmptyItemSet(); 1517 } 1518 return pItemSet; 1519 } 1520 1521 void SmTextForwarder::AppendParagraph() 1522 { 1523 // append an empty paragraph 1524 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1525 if (pEditEngine) 1526 { 1527 sal_uInt16 nParaCount = pEditEngine->GetParagraphCount(); 1528 pEditEngine->InsertParagraph( nParaCount, String() ); 1529 } 1530 } 1531 1532 xub_StrLen SmTextForwarder::AppendTextPortion( sal_uInt16 nPara, const String &rText, const SfxItemSet &rSet ) 1533 { 1534 xub_StrLen nRes = 0; 1535 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1536 if (pEditEngine && nPara < pEditEngine->GetParagraphCount()) 1537 { 1538 // append text 1539 ESelection aSel( nPara, pEditEngine->GetTextLen( nPara ) ); 1540 pEditEngine->QuickInsertText( rText, aSel ); 1541 1542 // set attributes for new appended text 1543 nRes = aSel.nEndPos = pEditEngine->GetTextLen( nPara ); 1544 pEditEngine->QuickSetAttribs( rSet, aSel ); 1545 } 1546 return nRes; 1547 } 1548 1549 void SmTextForwarder::CopyText(const SvxTextForwarder& rSource) 1550 { 1551 1552 const SmTextForwarder* pSourceForwarder = dynamic_cast< const SmTextForwarder* >( &rSource ); 1553 if( !pSourceForwarder ) 1554 return; 1555 EditEngine* pSourceEditEngine = pSourceForwarder->rEditAcc.GetEditEngine(); 1556 EditEngine *pEditEngine = rEditAcc.GetEditEngine(); 1557 if (pEditEngine && pSourceEditEngine ) 1558 { 1559 EditTextObject* pNewTextObject = pSourceEditEngine->CreateTextObject(); 1560 pEditEngine->SetText( *pNewTextObject ); 1561 delete pNewTextObject; 1562 } 1563 } 1564 1565 //------------------------------------------------------------------------ 1566 1567 SmEditViewForwarder::SmEditViewForwarder( SmEditAccessible& rAcc ) : 1568 rEditAcc( rAcc ) 1569 { 1570 } 1571 1572 SmEditViewForwarder::~SmEditViewForwarder() 1573 { 1574 } 1575 1576 sal_Bool SmEditViewForwarder::IsValid() const 1577 { 1578 return rEditAcc.GetEditView() != 0; 1579 } 1580 1581 Rectangle SmEditViewForwarder::GetVisArea() const 1582 { 1583 Rectangle aRect(0,0,0,0); 1584 1585 EditView *pEditView = rEditAcc.GetEditView(); 1586 OutputDevice* pOutDev = pEditView ? pEditView->GetWindow() : 0; 1587 1588 if( pOutDev && pEditView) 1589 { 1590 Rectangle aVisArea = pEditView->GetVisArea(); 1591 1592 // figure out map mode from edit engine 1593 EditEngine* pEditEngine = pEditView->GetEditEngine(); 1594 1595 if( pEditEngine ) 1596 { 1597 MapMode aMapMode(pOutDev->GetMapMode()); 1598 aVisArea = OutputDevice::LogicToLogic( aVisArea, 1599 pEditEngine->GetRefMapMode(), 1600 aMapMode.GetMapUnit() ); 1601 aMapMode.SetOrigin(Point()); 1602 aRect = pOutDev->LogicToPixel( aVisArea, aMapMode ); 1603 } 1604 } 1605 1606 return aRect; 1607 } 1608 1609 Point SmEditViewForwarder::LogicToPixel( const Point& rPoint, const MapMode& rMapMode ) const 1610 { 1611 EditView *pEditView = rEditAcc.GetEditView(); 1612 OutputDevice* pOutDev = pEditView ? pEditView->GetWindow() : 0; 1613 1614 if( pOutDev ) 1615 { 1616 MapMode aMapMode(pOutDev->GetMapMode()); 1617 Point aPoint( OutputDevice::LogicToLogic( rPoint, rMapMode, 1618 aMapMode.GetMapUnit() ) ); 1619 aMapMode.SetOrigin(Point()); 1620 return pOutDev->LogicToPixel( aPoint, aMapMode ); 1621 } 1622 1623 return Point(); 1624 } 1625 1626 Point SmEditViewForwarder::PixelToLogic( const Point& rPoint, const MapMode& rMapMode ) const 1627 { 1628 EditView *pEditView = rEditAcc.GetEditView(); 1629 OutputDevice* pOutDev = pEditView ? pEditView->GetWindow() : 0; 1630 1631 if( pOutDev ) 1632 { 1633 MapMode aMapMode(pOutDev->GetMapMode()); 1634 aMapMode.SetOrigin(Point()); 1635 Point aPoint( pOutDev->PixelToLogic( rPoint, aMapMode ) ); 1636 return OutputDevice::LogicToLogic( aPoint, 1637 aMapMode.GetMapUnit(), 1638 rMapMode ); 1639 } 1640 1641 return Point(); 1642 } 1643 1644 sal_Bool SmEditViewForwarder::GetSelection( ESelection& rSelection ) const 1645 { 1646 sal_Bool bRes = sal_False; 1647 EditView *pEditView = rEditAcc.GetEditView(); 1648 if (pEditView) 1649 { 1650 rSelection = pEditView->GetSelection(); 1651 bRes = sal_True; 1652 } 1653 return bRes; 1654 } 1655 1656 sal_Bool SmEditViewForwarder::SetSelection( const ESelection& rSelection ) 1657 { 1658 sal_Bool bRes = sal_False; 1659 EditView *pEditView = rEditAcc.GetEditView(); 1660 if (pEditView) 1661 { 1662 pEditView->SetSelection( rSelection ); 1663 bRes = sal_True; 1664 } 1665 return bRes; 1666 } 1667 1668 sal_Bool SmEditViewForwarder::Copy() 1669 { 1670 sal_Bool bRes = sal_False; 1671 EditView *pEditView = rEditAcc.GetEditView(); 1672 if (pEditView) 1673 { 1674 pEditView->Copy(); 1675 bRes = sal_True; 1676 } 1677 return bRes; 1678 } 1679 1680 sal_Bool SmEditViewForwarder::Cut() 1681 { 1682 sal_Bool bRes = sal_False; 1683 EditView *pEditView = rEditAcc.GetEditView(); 1684 if (pEditView) 1685 { 1686 pEditView->Cut(); 1687 bRes = sal_True; 1688 } 1689 return bRes; 1690 } 1691 1692 sal_Bool SmEditViewForwarder::Paste() 1693 { 1694 sal_Bool bRes = sal_False; 1695 EditView *pEditView = rEditAcc.GetEditView(); 1696 if (pEditView) 1697 { 1698 pEditView->Paste(); 1699 bRes = sal_True; 1700 } 1701 return bRes; 1702 } 1703 1704 //------------------------------------------------------------------------ 1705 1706 SmEditAccessible::SmEditAccessible( SmEditWindow *pEditWin ) : 1707 aAccName ( String(SmResId(STR_CMDBOXWINDOW)) ), 1708 pTextHelper (0), 1709 pWin (pEditWin) 1710 { 1711 DBG_ASSERT( pWin, "SmEditAccessible: window missing" ); 1712 //++aRefCount; 1713 } 1714 1715 1716 SmEditAccessible::SmEditAccessible( const SmEditAccessible &rSmAcc ) : 1717 SmEditAccessibleBaseClass(), 1718 aAccName ( String(SmResId(STR_CMDBOXWINDOW)) ) 1719 { 1720 //vos::OGuard aGuard(Application::GetSolarMutex()); 1721 pWin = rSmAcc.pWin; 1722 DBG_ASSERT( pWin, "SmEditAccessible: window missing" ); 1723 //++aRefCount; 1724 } 1725 1726 SmEditAccessible::~SmEditAccessible() 1727 { 1728 delete pTextHelper; 1729 /* 1730 vos::OGuard aGuard(Application::GetSolarMutex()); 1731 if (--aRefCount == 0) 1732 { 1733 } 1734 */ 1735 } 1736 1737 void SmEditAccessible::Init() 1738 { 1739 DBG_ASSERT( pWin, "SmEditAccessible: window missing" ); 1740 if (pWin) 1741 { 1742 EditEngine *pEditEngine = pWin->GetEditEngine(); 1743 EditView *pEditView = pWin->GetEditView(); 1744 if (pEditEngine && pEditView) 1745 { 1746 ::std::auto_ptr< SvxEditSource > pEditSource( 1747 new SmEditSource( pWin, *this ) ); 1748 pTextHelper = new ::accessibility::AccessibleTextHelper( pEditSource ); 1749 pTextHelper->SetEventSource( this ); 1750 } 1751 } 1752 } 1753 1754 #ifdef TL_NOT_YET_USED 1755 SmDocShell * SmEditAccessible::GetDoc_Impl() 1756 { 1757 SmViewShell *pView = pWin ? pWin->GetView() : 0; 1758 return pView ? pView->GetDoc() : 0; 1759 } 1760 #endif // TL_NOT_YET_USED 1761 1762 void SmEditAccessible::ClearWin() 1763 { 1764 // #112565# remove handler before current object gets destroyed 1765 // (avoid handler being called for already dead object) 1766 EditEngine *pEditEngine = GetEditEngine(); 1767 if (pEditEngine) 1768 pEditEngine->SetNotifyHdl( Link() ); 1769 1770 pWin = 0; // implicitly results in AccessibleStateType::DEFUNC set 1771 1772 //! make TextHelper implicitly release C++ references to some core objects 1773 pTextHelper->SetEditSource( ::std::auto_ptr<SvxEditSource>(NULL) ); 1774 //! make TextHelper release references 1775 //! (e.g. the one set by the 'SetEventSource' call) 1776 pTextHelper->Dispose(); 1777 delete pTextHelper; pTextHelper = 0; 1778 } 1779 1780 // XAccessible 1781 uno::Reference< XAccessibleContext > SAL_CALL SmEditAccessible::getAccessibleContext( ) 1782 throw (RuntimeException) 1783 { 1784 vos::OGuard aGuard(Application::GetSolarMutex()); 1785 return this; 1786 } 1787 1788 // XAccessibleComponent 1789 sal_Bool SAL_CALL SmEditAccessible::containsPoint( const awt::Point& aPoint ) 1790 throw (RuntimeException) 1791 { 1792 //! the arguments coordinates are relativ to the current window ! 1793 //! Thus the top left-point is (0, 0) 1794 1795 vos::OGuard aGuard(Application::GetSolarMutex()); 1796 if (!pWin) 1797 throw RuntimeException(); 1798 1799 Size aSz( pWin->GetSizePixel() ); 1800 return aPoint.X >= 0 && aPoint.Y >= 0 && 1801 aPoint.X < aSz.Width() && aPoint.Y < aSz.Height(); 1802 } 1803 1804 uno::Reference< XAccessible > SAL_CALL SmEditAccessible::getAccessibleAtPoint( const awt::Point& aPoint ) 1805 throw (RuntimeException) 1806 { 1807 vos::OGuard aGuard(Application::GetSolarMutex()); 1808 if (!pTextHelper) 1809 throw RuntimeException(); 1810 return pTextHelper->GetAt( aPoint ); 1811 } 1812 1813 awt::Rectangle SAL_CALL SmEditAccessible::getBounds( ) 1814 throw (RuntimeException) 1815 { 1816 vos::OGuard aGuard(Application::GetSolarMutex()); 1817 if (!pWin) 1818 throw RuntimeException(); 1819 DBG_ASSERT(pWin->GetParent()->GetAccessible() == getAccessibleParent(), 1820 "mismatch of window parent and accessible parent" ); 1821 return lcl_GetBounds( pWin ); 1822 } 1823 1824 awt::Point SAL_CALL SmEditAccessible::getLocation( ) 1825 throw (RuntimeException) 1826 { 1827 vos::OGuard aGuard(Application::GetSolarMutex()); 1828 if (!pWin) 1829 throw RuntimeException(); 1830 DBG_ASSERT(pWin->GetParent()->GetAccessible() == getAccessibleParent(), 1831 "mismatch of window parent and accessible parent" ); 1832 awt::Rectangle aRect( lcl_GetBounds( pWin ) ); 1833 return awt::Point( aRect.X, aRect.Y ); 1834 } 1835 1836 awt::Point SAL_CALL SmEditAccessible::getLocationOnScreen( ) 1837 throw (RuntimeException) 1838 { 1839 vos::OGuard aGuard(Application::GetSolarMutex()); 1840 if (!pWin) 1841 throw RuntimeException(); 1842 DBG_ASSERT(pWin->GetParent()->GetAccessible() == getAccessibleParent(), 1843 "mismatch of window parent and accessible parent" ); 1844 return lcl_GetLocationOnScreen( pWin ); 1845 } 1846 1847 awt::Size SAL_CALL SmEditAccessible::getSize( ) 1848 throw (RuntimeException) 1849 { 1850 vos::OGuard aGuard(Application::GetSolarMutex()); 1851 if (!pWin) 1852 throw RuntimeException(); 1853 DBG_ASSERT(pWin->GetParent()->GetAccessible() == getAccessibleParent(), 1854 "mismatch of window parent and accessible parent" ); 1855 1856 Size aSz( pWin->GetSizePixel() ); 1857 #if OSL_DEBUG_LEVEL > 1 1858 awt::Rectangle aRect( lcl_GetBounds( pWin ) ); 1859 Size aSz2( aRect.Width, aRect.Height ); 1860 DBG_ASSERT( aSz == aSz2, "mismatch in width" ); 1861 #endif 1862 return awt::Size( aSz.Width(), aSz.Height() ); 1863 } 1864 1865 void SAL_CALL SmEditAccessible::grabFocus( ) 1866 throw (RuntimeException) 1867 { 1868 vos::OGuard aGuard(Application::GetSolarMutex()); 1869 if (!pWin) 1870 throw RuntimeException(); 1871 1872 pWin->GrabFocus(); 1873 } 1874 1875 sal_Int32 SAL_CALL SmEditAccessible::getForeground() 1876 throw (RuntimeException) 1877 { 1878 vos::OGuard aGuard(Application::GetSolarMutex()); 1879 1880 if (!pWin) 1881 throw RuntimeException(); 1882 return (sal_Int32) pWin->GetTextColor().GetColor(); 1883 } 1884 1885 sal_Int32 SAL_CALL SmEditAccessible::getBackground() 1886 throw (RuntimeException) 1887 { 1888 vos::OGuard aGuard(Application::GetSolarMutex()); 1889 1890 if (!pWin) 1891 throw RuntimeException(); 1892 Wallpaper aWall( pWin->GetDisplayBackground() ); 1893 ColorData nCol; 1894 if (aWall.IsBitmap() || aWall.IsGradient()) 1895 nCol = pWin->GetSettings().GetStyleSettings().GetWindowColor().GetColor(); 1896 else 1897 nCol = aWall.GetColor().GetColor(); 1898 return (sal_Int32) nCol; 1899 } 1900 1901 // XAccessibleContext 1902 sal_Int32 SAL_CALL SmEditAccessible::getAccessibleChildCount( ) 1903 throw (RuntimeException) 1904 { 1905 vos::OGuard aGuard(Application::GetSolarMutex()); 1906 if (!pTextHelper) 1907 throw RuntimeException(); 1908 return pTextHelper->GetChildCount(); 1909 } 1910 1911 uno::Reference< XAccessible > SAL_CALL SmEditAccessible::getAccessibleChild( sal_Int32 i ) 1912 throw (IndexOutOfBoundsException, RuntimeException) 1913 { 1914 vos::OGuard aGuard(Application::GetSolarMutex()); 1915 if (!pTextHelper) 1916 throw RuntimeException(); 1917 return pTextHelper->GetChild( i ); 1918 } 1919 1920 uno::Reference< XAccessible > SAL_CALL SmEditAccessible::getAccessibleParent( ) 1921 throw (RuntimeException) 1922 { 1923 vos::OGuard aGuard(Application::GetSolarMutex()); 1924 if (!pWin) 1925 throw RuntimeException(); 1926 1927 Window *pAccParent = pWin->GetAccessibleParentWindow(); 1928 DBG_ASSERT( pAccParent, "accessible parent missing" ); 1929 return pAccParent ? pAccParent->GetAccessible() : Reference< XAccessible >(); 1930 } 1931 1932 sal_Int32 SAL_CALL SmEditAccessible::getAccessibleIndexInParent( ) 1933 throw (RuntimeException) 1934 { 1935 vos::OGuard aGuard(Application::GetSolarMutex()); 1936 sal_Int32 nIdx = -1; 1937 Window *pAccParent = pWin ? pWin->GetAccessibleParentWindow() : 0; 1938 if (pAccParent) 1939 { 1940 sal_uInt16 nCnt = pAccParent->GetAccessibleChildWindowCount(); 1941 for (sal_uInt16 i = 0; i < nCnt && nIdx == -1; ++i) 1942 if (pAccParent->GetAccessibleChildWindow( i ) == pWin) 1943 nIdx = i; 1944 } 1945 return nIdx; 1946 } 1947 1948 sal_Int16 SAL_CALL SmEditAccessible::getAccessibleRole( ) 1949 throw (RuntimeException) 1950 { 1951 vos::OGuard aGuard(Application::GetSolarMutex()); 1952 return AccessibleRole::PANEL /*TEXT ?*/; 1953 } 1954 1955 rtl::OUString SAL_CALL SmEditAccessible::getAccessibleDescription( ) 1956 throw (RuntimeException) 1957 { 1958 vos::OGuard aGuard(Application::GetSolarMutex()); 1959 return OUString(); // empty as agreed with product-management 1960 } 1961 1962 rtl::OUString SAL_CALL SmEditAccessible::getAccessibleName( ) 1963 throw (RuntimeException) 1964 { 1965 vos::OGuard aGuard(Application::GetSolarMutex()); 1966 // same name as displayed by the window when not docked 1967 return aAccName; 1968 } 1969 1970 uno::Reference< XAccessibleRelationSet > SAL_CALL SmEditAccessible::getAccessibleRelationSet( ) 1971 throw (RuntimeException) 1972 { 1973 vos::OGuard aGuard(Application::GetSolarMutex()); 1974 Reference< XAccessibleRelationSet > xRelSet = new utl::AccessibleRelationSetHelper(); 1975 return xRelSet; // empty relation set 1976 } 1977 1978 uno::Reference< XAccessibleStateSet > SAL_CALL SmEditAccessible::getAccessibleStateSet( ) 1979 throw (RuntimeException) 1980 { 1981 vos::OGuard aGuard(Application::GetSolarMutex()); 1982 ::utl::AccessibleStateSetHelper *pStateSet = 1983 new ::utl::AccessibleStateSetHelper; 1984 1985 Reference<XAccessibleStateSet> xStateSet( pStateSet ); 1986 1987 if (!pWin || !pTextHelper) 1988 pStateSet->AddState( AccessibleStateType::DEFUNC ); 1989 else 1990 { 1991 //pStateSet->AddState( AccessibleStateType::EDITABLE ); 1992 pStateSet->AddState( AccessibleStateType::MULTI_LINE ); 1993 //pStateSet->AddState( AccessibleStateType::HORIZONTAL ); 1994 //pStateSet->AddState( AccessibleStateType::TRANSIENT ); 1995 pStateSet->AddState( AccessibleStateType::ENABLED ); 1996 pStateSet->AddState( AccessibleStateType::FOCUSABLE ); 1997 if (pWin->HasFocus()) 1998 pStateSet->AddState( AccessibleStateType::FOCUSED ); 1999 if (pWin->IsActive()) 2000 pStateSet->AddState( AccessibleStateType::ACTIVE ); 2001 if (pWin->IsVisible()) 2002 pStateSet->AddState( AccessibleStateType::SHOWING ); 2003 if (pWin->IsReallyVisible()) 2004 pStateSet->AddState( AccessibleStateType::VISIBLE ); 2005 if (COL_TRANSPARENT != pWin->GetBackground().GetColor().GetColor()) 2006 pStateSet->AddState( AccessibleStateType::OPAQUE ); 2007 } 2008 2009 return xStateSet; 2010 } 2011 2012 Locale SAL_CALL SmEditAccessible::getLocale( ) 2013 throw (IllegalAccessibleComponentStateException, RuntimeException) 2014 { 2015 vos::OGuard aGuard(Application::GetSolarMutex()); 2016 // should be the document language... 2017 // We use the language of the localized symbol names here. 2018 return Application::GetSettings().GetUILocale(); 2019 } 2020 2021 2022 // XAccessibleEventBroadcaster 2023 void SAL_CALL SmEditAccessible::addEventListener( const uno::Reference< XAccessibleEventListener >& xListener ) 2024 throw (RuntimeException) 2025 { 2026 //vos::OGuard aGuard(Application::GetSolarMutex()); if (pTextHelper) // not disposing (about to destroy view shell) 2027 pTextHelper->AddEventListener( xListener ); 2028 } 2029 2030 void SAL_CALL SmEditAccessible::removeEventListener( const uno::Reference< XAccessibleEventListener >& xListener ) 2031 throw (RuntimeException) 2032 { 2033 //vos::OGuard aGuard(Application::GetSolarMutex()); 2034 if (pTextHelper) // not disposing (about to destroy view shell) 2035 pTextHelper->RemoveEventListener( xListener ); 2036 } 2037 2038 OUString SAL_CALL SmEditAccessible::getImplementationName() 2039 throw (RuntimeException) 2040 { 2041 //vos::OGuard aGuard(Application::GetSolarMutex()); 2042 return A2OU("SmEditAccessible"); 2043 } 2044 2045 sal_Bool SAL_CALL SmEditAccessible::supportsService( 2046 const OUString& rServiceName ) 2047 throw (RuntimeException) 2048 { 2049 //vos::OGuard aGuard(Application::GetSolarMutex()); 2050 return rServiceName == A2OU( "com::sun::star::accessibility::Accessible" ) || 2051 rServiceName == A2OU( "com::sun::star::accessibility::AccessibleComponent" ) || 2052 rServiceName == A2OU( "com::sun::star::accessibility::AccessibleContext" ); 2053 } 2054 2055 Sequence< OUString > SAL_CALL SmEditAccessible::getSupportedServiceNames() 2056 throw (RuntimeException) 2057 { 2058 //vos::OGuard aGuard(Application::GetSolarMutex()); 2059 Sequence< OUString > aNames(3); 2060 OUString *pNames = aNames.getArray(); 2061 pNames[0] = A2OU( "com::sun::star::accessibility::Accessible" ); 2062 pNames[1] = A2OU( "com::sun::star::accessibility::AccessibleComponent" ); 2063 pNames[2] = A2OU( "com::sun::star::accessibility::AccessibleContext" ); 2064 return aNames; 2065 } 2066 2067 ////////////////////////////////////////////////////////////////////// 2068 2069