1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
21 #include <hintids.hxx>
22 #include <sfx2/bindings.hxx>
23 #include <sfx2/viewfrm.hxx>
24 #include <svl/eitem.hxx>
25 #include <svl/macitem.hxx>
26 #include <unotools/charclass.hxx>
27 #include <sfx2/event.hxx>
28 #include <osl/diagnose.h>
37 #include <swdtflvr.hxx>
39 #include <wordcountdialog.hxx>
41 #include <vcl/uitest/logger.hxx>
42 #include <vcl/uitest/eventdescription.hxx>
44 namespace com::sun::star::util
{
45 struct SearchOptions2
;
48 using namespace ::com::sun::star::util
;
50 static tools::Long nStartDragX
= 0, nStartDragY
= 0;
51 static bool bStartDrag
= false;
53 void SwWrtShell::Invalidate()
55 // to avoid making the slot volatile, invalidate it every time if something could have been changed
56 // this is still much cheaper than asking for the state every 200 ms (and avoid background processing)
57 GetView().GetViewFrame().GetBindings().Invalidate( FN_STAT_SELMODE
);
58 GetView().GetViewFrame().GetBindings().Update(FN_STAT_SELMODE
); // make selection mode control icon update immediately
59 SwWordCountWrapper
*pWrdCnt
= static_cast<SwWordCountWrapper
*>(GetView().GetViewFrame().GetChildWindow(SwWordCountWrapper::GetChildWindowId()));
61 pWrdCnt
->UpdateCounts();
64 bool SwWrtShell::SelNearestWrd()
66 SwMvContext
aMvContext(this);
67 if( !IsInWord() && !IsEndWrd() && !IsStartWord() )
70 Left(SwCursorSkipMode::Cells
, false, 1, false );
74 bool SwWrtShell::SelWrd(const Point
*pPt
)
78 SwMvContext
aMvContext(this);
80 bRet
= SwCursorShell::SelectWord( pPt
);
92 void SwWrtShell::SelSentence(const Point
*pPt
)
95 SwMvContext
aMvContext(this);
97 SwCursorShell::GoStartSentence();
99 SwCursorShell::GoEndSentence();
105 m_bSelWrd
= false; // disable SelWord, otherwise no SelLine goes on
108 void SwWrtShell::SelPara(const Point
*pPt
)
111 SwMvContext
aMvContext(this);
113 SwCursorShell::MovePara( GoCurrPara
, fnParaStart
);
115 SwCursorShell::MovePara( GoCurrPara
, fnParaEnd
);
121 m_bSelWrd
= false; // disable SelWord, otherwise no SelLine goes on
124 void SwWrtShell::SelAll()
126 const bool bLockedView
= IsViewLocked();
131 SwMvContext
aMvContext(this);
132 bool bMoveTable
= false;
133 std::optional
<SwPosition
> oStartPos
;
134 std::optional
<SwPosition
> oEndPos
;
135 SwShellCursor
* pTmpCursor
= nullptr;
137 // Query these early, before we move the cursor.
138 bool bHasWholeTabSelection
= HasWholeTabSelection();
139 bool bIsCursorInTable
= IsCursorInTable();
141 if (!bHasWholeTabSelection
142 && ( !bIsCursorInTable
143 || getShellCursor(false)->GetMarkNode().FindTableNode() == nullptr
144 || !ExtendedSelectedAll())) // ESA inside table -> else branch
146 if ( IsSelection() && IsCursorPtAtEnd() )
148 pTmpCursor
= getShellCursor( false );
151 oStartPos
.emplace( *pTmpCursor
->GetPoint() );
152 oEndPos
.emplace( *pTmpCursor
->GetMark() );
155 bool bIsFullSel
= !MoveSection( GoCurrSection
, fnSectionStart
);
157 bIsFullSel
&= !MoveSection( GoCurrSection
, fnSectionEnd
);
158 Pop(SwCursorShell::PopMode::DeleteCurrent
);
159 GoStart(true, &bMoveTable
, false, !bIsFullSel
);
161 GoEnd(true, &bMoveTable
);
165 if (MoveOutOfTable())
166 { // select outer text
167 EnterStdMode(); // delete m_pTableCursor
168 // GoStart(true, &bMoveTable, false, true);
169 MoveSection(GoCurrSection
, fnSectionStart
); // don't move into prev table
171 MoveSection(GoCurrSection
, fnSectionEnd
); // don't move to different cell
175 TrySelectOuterTable();
179 bool bNeedsExtendedSelectAll
= StartsWith_() != StartsWith::None
;
181 // the GoEnd() could have created a table selection, if so avoid ESA.
182 if (bNeedsExtendedSelectAll
&& bIsCursorInTable
)
184 bNeedsExtendedSelectAll
= !HasWholeTabSelection();
187 if (bNeedsExtendedSelectAll
)
189 ExtendedSelectAll(/*bFootnotes =*/ false);
192 SwDoc
*pDoc
= GetDoc();
195 pDoc
->SetPrepareSelAll();
200 pTmpCursor
= getShellCursor( false );
203 // Some special handling for sections (e.g. TOC) at the beginning of the document body
204 // to avoid the selection of the first section
205 // if the last selection was behind the first section or
206 // if the last selection was already the first section
207 // In this both cases we select to the end of document
208 if( ( *pTmpCursor
->GetPoint() < *oEndPos
||
209 ( *oStartPos
== *pTmpCursor
->GetMark() &&
210 *oEndPos
== *pTmpCursor
->GetPoint() ) ) && !bNeedsExtendedSelectAll
)
211 SwCursorShell::SttEndDoc(false);
216 LockView( bLockedView
);
219 // Description: Text search
221 sal_Int32
SwWrtShell::SearchPattern( const i18nutil::SearchOptions2
& rSearchOpt
, bool bSearchInNotes
,
222 SwDocPositions eStt
, SwDocPositions eEnd
,
223 FindRanges eFlags
, bool bReplace
)
225 // no enhancement of existing selections
226 if(!(eFlags
& FindRanges::InSel
))
228 bool bCancel
= false;
229 sal_Int32 nRet
= Find_Text(rSearchOpt
, bSearchInNotes
, eStt
, eEnd
, bCancel
, eFlags
, bReplace
);
233 nRet
= SAL_MAX_INT32
;
238 // Description: search for templates
240 sal_Int32
SwWrtShell::SearchTempl( const OUString
&rTempl
,
241 SwDocPositions eStt
, SwDocPositions eEnd
,
242 FindRanges eFlags
, const OUString
* pReplTempl
)
244 // no enhancement of existing selections
245 if(!(eFlags
& FindRanges::InSel
))
247 SwTextFormatColl
*pColl
= GetParaStyle(rTempl
, SwWrtShell::GETSTYLE_CREATESOME
);
248 SwTextFormatColl
*pReplaceColl
= nullptr;
250 pReplaceColl
= GetParaStyle(*pReplTempl
, SwWrtShell::GETSTYLE_CREATESOME
);
252 bool bCancel
= false;
253 sal_Int32 nRet
= FindFormat(pColl
? *pColl
: GetDfltTextFormatColl(),
254 eStt
,eEnd
, bCancel
, eFlags
, pReplaceColl
);
258 nRet
= SAL_MAX_INT32
;
263 // search for attributes
265 sal_Int32
SwWrtShell::SearchAttr( const SfxItemSet
& rFindSet
, bool bNoColls
,
266 SwDocPositions eStart
, SwDocPositions eEnd
,
267 FindRanges eFlags
, const i18nutil::SearchOptions2
* pSearchOpt
,
268 const SfxItemSet
* pReplaceSet
)
270 // no enhancement of existing selections
271 if (!(eFlags
& FindRanges::InSel
))
275 bool bCancel
= false;
276 sal_Int32 nRet
= FindAttrs(rFindSet
, bNoColls
, eStart
, eEnd
, bCancel
, eFlags
, pSearchOpt
, pReplaceSet
);
281 nRet
= SAL_MAX_INT32
;
288 void SwWrtShell::PushMode()
290 m_pModeStack
= new ModeStack( m_pModeStack
, m_bIns
, m_bExtMode
, m_bAddMode
, m_bBlockMode
);
293 void SwWrtShell::PopMode()
295 if ( nullptr == m_pModeStack
)
298 if ( m_bExtMode
&& !m_pModeStack
->bExt
)
300 if ( m_bAddMode
&& !m_pModeStack
->bAdd
)
302 if ( m_bBlockMode
&& !m_pModeStack
->bBlock
)
304 m_bIns
= m_pModeStack
->bIns
;
306 m_pModeStack
= std::move(m_pModeStack
->pNext
);
309 // Two methods for setting cursors: the first maps at the
310 // eponymous methods in the CursorShell, the second removes
311 // all selections at first.
313 tools::Long
SwWrtShell::SetCursor(const Point
*pPt
, bool bTextOnly
)
315 // Remove a possibly present selection at the position
318 if(!IsInSelect() && TestCurrPam(*pPt
)) {
322 return SwCursorShell::SetCursor(*pPt
, bTextOnly
);
325 tools::Long
SwWrtShell::SetCursorKillSel(const Point
*pPt
, bool bTextOnly
)
327 SwActContext
aActContext(this);
328 ResetSelect(pPt
,false);
329 return SwCursorShell::SetCursor(*pPt
, bTextOnly
);
332 void SwWrtShell::UnSelectFrame()
334 // Remove Frame selection with guaranteed invalid position
335 Point
aPt(LONG_MIN
, LONG_MIN
);
337 SwTransferable::ClearSelection( *this );
340 // Remove of all selections
342 tools::Long
SwWrtShell::ResetSelect(const Point
*,bool)
351 // SwActContext opens an Action -
352 // to avoid problems in the basic process with the
353 // shell switching, GetChgLnk().Call() may be called
354 // after EndAction().
356 SwActContext
aActContext(this);
357 m_bSelWrd
= m_bSelLn
= false;
360 m_fnKillSel
= &SwWrtShell::Ignore
;
361 m_fnSetCursor
= &SwWrtShell::SetCursor
;
364 // After canceling of all selections an update of Attr-Controls
365 // could be necessary.
366 GetChgLnk().Call(nullptr);
368 if ( GetEnhancedTableSelection() != SwTable::SEARCH_NONE
)
369 UnsetEnhancedTableSelection();
372 SwTransferable::ClearSelection( *this );
376 bool SwWrtShell::IsSplitVerticalByDefault() const
378 return GetDoc()->IsSplitVerticalByDefault();
381 void SwWrtShell::SetSplitVerticalByDefault(bool value
)
383 GetDoc()->SetSplitVerticalByDefault(value
);
388 tools::Long
SwWrtShell::Ignore(const Point
*, bool ) {
392 // Begin of a selection process.
394 void SwWrtShell::SttSelect()
402 SwShellCursor
* pTmp
= getShellCursor( true );
403 if( !pTmp
->HasMark() )
406 m_fnKillSel
= &SwWrtShell::Ignore
;
407 m_fnSetCursor
= &SwWrtShell::SetCursor
;
410 SwTransferable::CreateSelection( *this );
415 void collectUIInformation(SwShellCursor
* pCursor
)
417 EventDescription aDescription
;
418 OUString aSelStart
= OUString::number(pCursor
->Start()->GetContentIndex());
419 OUString aSelEnd
= OUString::number(pCursor
->End()->GetContentIndex());
421 aDescription
.aParameters
= {{"START_POS", aSelStart
}, {"END_POS", aSelEnd
}};
422 aDescription
.aAction
= "SELECT";
423 aDescription
.aID
= "writer_edit";
424 aDescription
.aKeyWord
= "SwEditWinUIObject";
425 aDescription
.aParent
= "MainWindow";
427 UITestLogger::getInstance().logEvent(aDescription
);
432 // End of a selection process.
434 void SwWrtShell::EndSelect()
436 if(m_bInSelect
&& !m_bExtMode
)
446 m_fnSetCursor
= &SwWrtShell::SetCursorKillSel
;
447 m_fnKillSel
= &SwWrtShell::ResetSelect
;
450 SwWordCountWrapper
*pWrdCnt
= static_cast<SwWordCountWrapper
*>(GetView().GetViewFrame().GetChildWindow(SwWordCountWrapper::GetChildWindowId()));
452 pWrdCnt
->UpdateCounts();
454 collectUIInformation(GetCursor_());
457 void SwWrtShell::ExtSelWrd(const Point
*pPt
, bool )
459 SwMvContext
aMvContext(this);
463 // Bug 66823: actual crsr has in additional mode no selection?
464 // Then destroy the actual and go to prev, this will be expand
465 if( !HasMark() && GoPrevCursor() )
467 bool bHasMark
= HasMark(); // that's wrong!
476 // check the direction of the selection with the new point
477 bool bMoveCursor
= true, bToTop
= false;
478 SwCursorShell::SelectWord( &m_aStart
); // select the startword
479 SwCursorShell::Push(); // save the cursor
480 SwCursorShell::SetCursor( *pPt
); // and check the direction
482 switch( SwCursorShell::CompareCursorStackMkCurrPt())
484 case -1: bToTop
= false; break;
485 case 1: bToTop
= true; break;
486 default: bMoveCursor
= false; break;
489 SwCursorShell::Pop(SwCursorShell::PopMode::DeleteCurrent
); // restore the saved cursor
494 // select to Top but cursor select to Bottom? or
495 // select to Bottom but cursor select to Top? --> swap the cursor
499 SwCursorShell::Push(); // save cur cursor
500 if( SwCursorShell::SelectWord( pPt
)) // select the current word
508 SwCursorShell::Pop(SwCursorShell::PopMode::DeleteCurrent
);
514 void SwWrtShell::ExtSelLn(const Point
*pPt
, bool )
516 SwMvContext
aMvContext(this);
517 SwCursorShell::SetCursor(*pPt
);
521 // Bug 66823: actual crsr has in additional mode no selection?
522 // Then destroy the actual and go to prev, this will be expand
523 if( !HasMark() && GoPrevCursor() )
525 bool bHasMark
= HasMark(); // that's wrong!
534 // if applicable fit the selection to the "Mark"
535 bool bToTop
= !IsCursorPtAtEnd();
538 // The "Mark" has to be at the end or the beginning of the line.
539 if( bToTop
? !IsEndSentence() : !IsStartSentence() )
544 SwCursorShell::Right(1,SwCursorSkipMode::Chars
);
545 SwCursorShell::GoEndSentence();
548 SwCursorShell::GoStartSentence();
553 SwCursorShell::GoStartSentence();
555 SwCursorShell::GoEndSentence();
558 // Back into the standard mode: no mode, no selections.
560 void SwWrtShell::EnterStdMode()
566 m_bBlockMode
= false;
576 // SwActContext opens and action which has to be
577 // closed prior to the call of
578 // GetChgLnk().Call()
579 SwActContext
aActContext(this);
580 m_bSelWrd
= m_bSelLn
= false;
581 if( !IsRetainSelection() )
584 m_fnSetCursor
= &SwWrtShell::SetCursorKillSel
;
585 m_fnKillSel
= &SwWrtShell::ResetSelect
;
588 SwTransferable::ClearSelection( *this );
593 void SwWrtShell::EnterExtMode()
603 m_bBlockMode
= false;
607 void SwWrtShell::LeaveExtMode()
613 // End of a selection; if the selection is empty,
616 void SwWrtShell::SttLeaveSelect()
618 if(SwCursorShell::HasSelection() && !IsSelTableCells() && m_bClearMark
) {
624 // Leaving of the selection mode in additional mode
626 void SwWrtShell::AddLeaveSelect()
628 if(IsTableMode()) LeaveAddMode();
629 else if(SwCursorShell::HasSelection())
635 void SwWrtShell::EnterAddMode()
637 if(IsTableMode()) return;
640 m_fnKillSel
= &SwWrtShell::Ignore
;
641 m_fnSetCursor
= &SwWrtShell::SetCursor
;
643 m_bBlockMode
= false;
645 if(SwCursorShell::HasSelection())
650 void SwWrtShell::LeaveAddMode()
652 m_fnKillSel
= &SwWrtShell::ResetSelect
;
653 m_fnSetCursor
= &SwWrtShell::SetCursorKillSel
;
660 void SwWrtShell::EnterBlockMode()
662 m_bBlockMode
= false;
665 CursorToBlockCursor();
669 void SwWrtShell::LeaveBlockMode()
671 m_bBlockMode
= false;
672 BlockCursorToCursor();
679 void SwWrtShell::SetInsMode( bool bOn
)
682 SwCursorShell::SetOverwriteCursor( !m_bIns
);
683 const SfxBoolItem
aTmp( SID_ATTR_INSERT
, m_bIns
);
684 GetView().GetViewFrame().GetBindings().SetState( aTmp
);
689 //Overwrite mode is incompatible with red-lining
690 void SwWrtShell::SetRedlineFlagsAndCheckInsMode( RedlineFlags eMode
)
692 SetRedlineFlags( eMode
);
699 void SwWrtShell::BeginFrameDrag(const Point
*pPt
, bool bIsShift
)
701 m_fnDrag
= &SwFEShell::Drag
;
704 Point
aTmp( nStartDragX
, nStartDragY
);
705 SwFEShell::BeginDrag( &aTmp
, bIsShift
);
708 SwFEShell::BeginDrag( pPt
, bIsShift
);
711 void SwWrtShell::EnterSelFrameMode(const Point
*pPos
)
715 nStartDragX
= pPos
->X();
716 nStartDragY
= pPos
->Y();
719 m_bLayoutMode
= true;
722 // equal call of BeginDrag in the SwFEShell
723 m_fnDrag
= &SwWrtShell::BeginFrameDrag
;
724 m_fnEndDrag
= &SwWrtShell::UpdateLayoutFrame
;
725 SwBaseShell::SetFrameMode( FLY_DRAG_START
, this );
729 void SwWrtShell::LeaveSelFrameMode()
731 m_fnDrag
= &SwWrtShell::BeginDrag
;
732 m_fnEndDrag
= &SwWrtShell::DefaultEndDrag
;
733 m_bLayoutMode
= false;
736 SwBaseShell::SetFrameMode( FLY_DRAG_END
, this );
740 // Description: execute framebound macro
742 IMPL_LINK( SwWrtShell
, ExecFlyMac
, const SwFlyFrameFormat
*, pFlyFormat
, void )
744 const SwFrameFormat
*pFormat
= pFlyFormat
? static_cast<const SwFrameFormat
*>(pFlyFormat
) : GetFlyFrameFormat();
745 OSL_ENSURE(pFormat
, "no frame format");
746 const SvxMacroItem
&rFormatMac
= pFormat
->GetMacro();
748 if(rFormatMac
.HasMacro(SvMacroItemId::SwObjectSelect
))
750 const SvxMacro
&rMac
= rFormatMac
.GetMacro(SvMacroItemId::SwObjectSelect
);
751 if( IsFrameSelected() )
752 m_bLayoutMode
= true;
758 void SwWrtShell::UpdateLayoutFrame(const Point
*, bool )
761 SwFEShell::EndDrag();
762 m_fnDrag
= &SwWrtShell::BeginFrameDrag
;
765 // Handler for toggling the modes. Returns back the old mode.
767 void SwWrtShell::ToggleAddMode()
769 m_bAddMode
? LeaveAddMode(): EnterAddMode();
773 void SwWrtShell::ToggleBlockMode()
775 m_bBlockMode
? LeaveBlockMode(): EnterBlockMode();
779 void SwWrtShell::ToggleExtMode()
781 m_bExtMode
? LeaveExtMode() : EnterExtMode();
785 // Dragging in standard mode (Selecting of content)
787 void SwWrtShell::BeginDrag(const Point
* /*pPt*/, bool )
792 if( !IsCursorPtAtEnd() )
795 m_fnDrag
= &SwWrtShell::ExtSelWrd
;
796 m_fnSetCursor
= &SwWrtShell::Ignore
;
801 m_fnDrag
= &SwWrtShell::ExtSelLn
;
802 m_fnSetCursor
= &SwWrtShell::Ignore
;
806 m_fnDrag
= &SwWrtShell::DefaultDrag
;
811 void SwWrtShell::DefaultDrag(const Point
*, bool )
813 if( IsSelTableCells() )
814 m_aSelTableLink
.Call(*this);
817 void SwWrtShell::DefaultEndDrag(const Point
* /*pPt*/, bool )
819 m_fnDrag
= &SwWrtShell::BeginDrag
;
823 if( IsSelTableCells() )
824 m_aSelTableLink
.Call(*this);
828 // #i32329# Enhanced table selection
829 bool SwWrtShell::SelectTableRowCol( const Point
& rPt
, const Point
* pEnd
, bool bRowDrag
)
831 SwMvContext
aMvContext(this);
833 if(SelTableRowCol( rPt
, pEnd
, bRowDrag
))
835 m_fnSetCursor
= &SwWrtShell::SetCursorKillSel
;
836 m_fnKillSel
= &SwWrtShell::ResetSelect
;
842 // Description: Selection of a table line or column
844 void SwWrtShell::SelectTableRow()
848 m_fnSetCursor
= &SwWrtShell::SetCursorKillSel
;
849 m_fnKillSel
= &SwWrtShell::ResetSelect
;
853 void SwWrtShell::SelectTableCol()
857 m_fnSetCursor
= &SwWrtShell::SetCursorKillSel
;
858 m_fnKillSel
= &SwWrtShell::ResetSelect
;
862 void SwWrtShell::SelectTableCell()
866 m_fnSetCursor
= &SwWrtShell::SetCursorKillSel
;
867 m_fnKillSel
= &SwWrtShell::ResetSelect
;
871 // Description: Check if a word selection is present.
872 // According to the rules for intelligent cut / paste
873 // surrounding spaces are cut out.
874 // Return: Delivers the type of the word selection.
876 int SwWrtShell::IntelligentCut(SelectionType nSelection
, bool bCut
)
878 // On multiple selection no intelligent drag and drop
879 // there are multiple cursors, since a second was placed
880 // already at the target position.
881 if( IsAddMode() || !(nSelection
& SelectionType::Text
) )
885 CharClass
& rCC
= GetAppCharClass();
887 // If the first character is no word character,
889 sal_Unicode cPrev
= GetChar(false);
890 sal_Unicode cNext
= GetChar(true, -1);
891 if( !cPrev
|| !cNext
||
892 !rCC
.isLetterNumeric( ( sText
= OUString(cPrev
) ), 0 ) ||
893 !rCC
.isLetterNumeric( ( sText
= OUString(cNext
) ), 0 ) )
896 cPrev
= GetChar(false, -1);
900 // is a word selected?
901 if (cPrev
&& cNext
&&
902 CH_TXTATR_BREAKWORD
!= cPrev
&& CH_TXTATR_INWORD
!= cPrev
&&
903 CH_TXTATR_BREAKWORD
!= cNext
&& CH_TXTATR_INWORD
!= cNext
&&
904 !rCC
.isLetterNumeric( ( sText
= OUString(cPrev
) ), 0 ) &&
905 !rCC
.isLetterNumeric( ( sText
= OUString(cNext
) ), 0 ) )
906 cWord
= WORD_NO_SPACE
;
908 if(cWord
== WORD_NO_SPACE
&& ' ' == cPrev
)
910 cWord
= WORD_SPACE_BEFORE
;
911 // delete the space before
915 if(IsCursorPtAtEnd())
919 SwCursorShell::Left(1,SwCursorSkipMode::Chars
);
920 SwFEShell::Delete(true);
921 Pop(SwCursorShell::PopMode::DeleteCurrent
);
924 else if(cWord
== WORD_NO_SPACE
&& cNext
== ' ')
926 cWord
= WORD_SPACE_AFTER
;
927 // delete the space behind
930 if(!IsCursorPtAtEnd()) SwapPam();
933 SwCursorShell::Right(1,SwCursorSkipMode::Chars
);
934 SwFEShell::Delete(true);
935 Pop(SwCursorShell::PopMode::DeleteCurrent
);
941 // jump to the next / previous hyperlink - inside text and also
943 void SwWrtShell::SelectNextPrevHyperlink( bool bNext
)
946 bool bRet
= SwCursorShell::SelectNxtPrvHyperlink( bNext
);
947 if( !bRet
) // didn't find? wrap and check again
949 SwShellCursor
* pCursor
= GetCursor_();
950 SwCursorSaveState
aSaveState(*pCursor
);
956 bRet
= SwCursorShell::SelectNxtPrvHyperlink(bNext
);
957 if (!bRet
) // didn't find again? restore cursor position and bail
959 pCursor
->RestoreSavePos();
960 EndAction(true); // don't scroll to restored cursor position
966 bool bCreateXSelection
= false;
967 const bool bFrameSelected
= IsFrameSelected() || IsObjSelected();
970 if ( bFrameSelected
)
973 // Set the function pointer for the canceling of the selection
975 m_fnKillSel
= &SwWrtShell::ResetSelect
;
976 m_fnSetCursor
= &SwWrtShell::SetCursorKillSel
;
977 bCreateXSelection
= true;
979 else if( bFrameSelected
)
982 bCreateXSelection
= true;
984 else if( (CNT_GRF
| CNT_OLE
) & GetCntType() )
986 SelectObj( GetCharRect().Pos() );
988 bCreateXSelection
= true;
991 if( bCreateXSelection
)
992 SwTransferable::CreateSelection( *this );
995 // For the preservation of the selection the cursor will be moved left
996 // after SetMark(), so that the cursor is not moved by inserting text.
997 // Because a present selection at the CORE page is cleared at the
998 // current cursor position, the cursor will be pushed on the stack.
999 // After moving, they will again resummarized.
1001 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */