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_editeng.hxx"
26
27 #include <eeng_pch.hxx>
28
29 #include <impedit.hxx>
30 #include <editundo.hxx>
31 #include <editeng/editview.hxx>
32 #include <editeng/editeng.hxx>
33
34 DBG_NAME( EditUndo )
35
36 #define MAX_UNDOS 100 // ab dieser Menge darf geloescht werden....
37 #define MIN_UNDOS 50 // soviel muss stehen bleiben...
38
39 #define NO_UNDO 0xFFFF
40 #define GROUP_NOTFOUND 0xFFFF
41
42 TYPEINIT1( EditUndo, SfxUndoAction );
43 TYPEINIT1( EditUndoDelContent, EditUndo );
44 TYPEINIT1( EditUndoConnectParas, EditUndo );
45 TYPEINIT1( EditUndoSplitPara, EditUndo );
46 TYPEINIT1( EditUndoInsertChars, EditUndo );
47 TYPEINIT1( EditUndoRemoveChars, EditUndo );
48 TYPEINIT1( EditUndoInsertFeature, EditUndo );
49 TYPEINIT1( EditUndoMoveParagraphs, EditUndo );
50 TYPEINIT1( EditUndoSetStyleSheet, EditUndo );
51 TYPEINIT1( EditUndoSetParaAttribs, EditUndo );
52 TYPEINIT1( EditUndoSetAttribs, EditUndo );
53 TYPEINIT1( EditUndoTransliteration, EditUndo );
54 TYPEINIT1( EditUndoMarkSelection, EditUndo );
55
lcl_DoSetSelection(EditView * pView,sal_uInt32 nPara)56 void lcl_DoSetSelection( EditView* pView, sal_uInt32 nPara )
57 {
58 EPaM aEPaM( nPara, 0 );
59 EditPaM aPaM( pView->GetImpEditEngine()->CreateEditPaM( aEPaM ) );
60 aPaM.SetIndex( aPaM.GetNode()->Len() );
61 EditSelection aSel( aPaM, aPaM );
62 pView->GetImpEditView()->SetEditSelection( aSel );
63 }
64
65 // -----------------------------------------------------------------------
66 // EditUndoManager
67 // ------------------------------------------------------------------------
EditUndoManager(sal_uInt16 nMaxUndoActionCount)68 EditUndoManager::EditUndoManager(sal_uInt16 nMaxUndoActionCount )
69 : SfxUndoManager(nMaxUndoActionCount),
70 mpImpEE(0)
71 {
72 }
73
SetImpEditEngine(ImpEditEngine * pNew)74 void EditUndoManager::SetImpEditEngine(ImpEditEngine* pNew)
75 {
76 mpImpEE = pNew;
77 }
78
Undo()79 sal_Bool __EXPORT EditUndoManager::Undo()
80 {
81 if ( !mpImpEE || GetUndoActionCount() == 0 )
82 return sal_False;
83
84 DBG_ASSERT( mpImpEE->GetActiveView(), "Active View?" );
85
86 if ( !mpImpEE->GetActiveView() )
87 {
88 if ( mpImpEE->GetEditViews().Count() )
89 mpImpEE->SetActiveView( mpImpEE->GetEditViews().GetObject(0) );
90 else
91 {
92 DBG_ERROR( "Undo in Engine ohne View nicht moeglich!" );
93 return sal_False;
94 }
95 }
96
97 mpImpEE->GetActiveView()->GetImpEditView()->DrawSelection(); // alte Selektion entfernen
98
99 mpImpEE->SetUndoMode( sal_True );
100 sal_Bool bDone = SfxUndoManager::Undo();
101 mpImpEE->SetUndoMode( sal_False );
102
103 EditSelection aNewSel( mpImpEE->GetActiveView()->GetImpEditView()->GetEditSelection() );
104 DBG_ASSERT( !aNewSel.IsInvalid(), "Ungueltige Selektion nach Undo()" );
105 DBG_ASSERT( !aNewSel.DbgIsBuggy( mpImpEE->GetEditDoc() ), "Kaputte Selektion nach Undo()" );
106
107 aNewSel.Min() = aNewSel.Max();
108 mpImpEE->GetActiveView()->GetImpEditView()->SetEditSelection( aNewSel );
109 mpImpEE->FormatAndUpdate( mpImpEE->GetActiveView() );
110
111 return bDone;
112 }
113
Redo()114 sal_Bool __EXPORT EditUndoManager::Redo()
115 {
116 if ( !mpImpEE || GetRedoActionCount() == 0 )
117 return sal_False;
118
119 DBG_ASSERT( mpImpEE->GetActiveView(), "Active View?" );
120
121 if ( !mpImpEE->GetActiveView() )
122 {
123 if ( mpImpEE->GetEditViews().Count() )
124 mpImpEE->SetActiveView( mpImpEE->GetEditViews().GetObject(0) );
125 else
126 {
127 DBG_ERROR( "Redo in Engine ohne View nicht moeglich!" );
128 return sal_False;
129 }
130 }
131
132 mpImpEE->GetActiveView()->GetImpEditView()->DrawSelection(); // alte Selektion entfernen
133
134 mpImpEE->SetUndoMode( sal_True );
135 sal_Bool bDone = SfxUndoManager::Redo();
136 mpImpEE->SetUndoMode( sal_False );
137
138 EditSelection aNewSel( mpImpEE->GetActiveView()->GetImpEditView()->GetEditSelection() );
139 DBG_ASSERT( !aNewSel.IsInvalid(), "Ungueltige Selektion nach Undo()" );
140 DBG_ASSERT( !aNewSel.DbgIsBuggy( mpImpEE->GetEditDoc() ), "Kaputte Selektion nach Redo()" );
141
142 aNewSel.Min() = aNewSel.Max();
143 mpImpEE->GetActiveView()->GetImpEditView()->SetEditSelection( aNewSel );
144 mpImpEE->FormatAndUpdate( mpImpEE->GetActiveView() );
145
146 return bDone;
147 }
148
149 // -----------------------------------------------------------------------
150 // EditUndo
151 // ------------------------------------------------------------------------
EditUndo(sal_uInt16 nI,ImpEditEngine * p)152 EditUndo::EditUndo( sal_uInt16 nI, ImpEditEngine* p )
153 {
154 DBG_CTOR( EditUndo, 0 );
155 nId = nI;
156 pImpEE = p;
157 }
158
~EditUndo()159 EditUndo::~EditUndo()
160 {
161 DBG_DTOR( EditUndo, 0 );
162 }
163
GetId() const164 sal_uInt16 __EXPORT EditUndo::GetId() const
165 {
166 DBG_CHKTHIS( EditUndo, 0 );
167 return nId;
168 }
169
CanRepeat(SfxRepeatTarget &) const170 sal_Bool __EXPORT EditUndo::CanRepeat(SfxRepeatTarget&) const
171 {
172 return sal_False;
173 }
174
GetComment() const175 XubString __EXPORT EditUndo::GetComment() const
176 {
177 XubString aComment;
178 if ( pImpEE )
179 {
180 EditEngine* pEditEng = pImpEE->GetEditEnginePtr();
181 aComment = pEditEng->GetUndoComment( GetId() );
182 }
183 return aComment;
184 }
185
186 // -----------------------------------------------------------------------
187 // EditUndoDelContent
188 // ------------------------------------------------------------------------
EditUndoDelContent(ImpEditEngine * _pImpEE,ContentNode * pNode,sal_uInt32 n)189 EditUndoDelContent::EditUndoDelContent( ImpEditEngine* _pImpEE, ContentNode* pNode, sal_uInt32 n )
190 : EditUndo( EDITUNDO_DELCONTENT, _pImpEE )
191 {
192 pContentNode = pNode;
193 nNode = n;
194 bDelObject = sal_True;
195 }
196
~EditUndoDelContent()197 EditUndoDelContent::~EditUndoDelContent()
198 {
199 if ( bDelObject )
200 delete pContentNode;
201 }
202
Undo()203 void __EXPORT EditUndoDelContent::Undo()
204 {
205 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
206 GetImpEditEngine()->InsertContent( pContentNode, nNode );
207 bDelObject = sal_False; // gehoert wieder der Engine
208 EditSelection aSel( EditPaM( pContentNode, 0 ), EditPaM( pContentNode, pContentNode->Len() ) );
209 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aSel );
210 }
211
Redo()212 void __EXPORT EditUndoDelContent::Redo()
213 {
214 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
215
216 ImpEditEngine* _pImpEE = GetImpEditEngine();
217
218 // pNode stimmt nicht mehr, falls zwischendurch Undos, in denen
219 // Absaetze verschmolzen sind.
220 pContentNode = _pImpEE->GetEditDoc().SaveGetObject( nNode );
221 DBG_ASSERT( pContentNode, "EditUndoDelContent::Redo(): Node?!" );
222
223 delete _pImpEE->GetParaPortions()[nNode];
224 _pImpEE->GetParaPortions().Remove( nNode );
225
226 // Node nicht loeschen, haengt im Undo!
227 _pImpEE->GetEditDoc().Remove( nNode );
228 if( _pImpEE->IsCallParaInsertedOrDeleted() )
229 _pImpEE->GetEditEnginePtr()->ParagraphDeleted( nNode );
230
231 DeletedNodeInfo* pInf = new DeletedNodeInfo( (sal_uLong)pContentNode, nNode );
232 _pImpEE->aDeletedNodes.Insert( pInf, _pImpEE->aDeletedNodes.Count() );
233 _pImpEE->UpdateSelections();
234
235 ContentNode* pN = ( nNode < _pImpEE->GetEditDoc().Count() )
236 ? _pImpEE->GetEditDoc().SaveGetObject( nNode )
237 : _pImpEE->GetEditDoc().SaveGetObject( nNode-1 );
238 DBG_ASSERT( pN && ( pN != pContentNode ), "?! RemoveContent !? " );
239 EditPaM aPaM( pN, pN->Len() );
240
241 bDelObject = sal_True; // gehoert wieder dem Undo
242
243 _pImpEE->GetActiveView()->GetImpEditView()->SetEditSelection( EditSelection( aPaM, aPaM ) );
244 }
245
246 // -----------------------------------------------------------------------
247 // EditUndoConnectParas
248 // ------------------------------------------------------------------------
EditUndoConnectParas(ImpEditEngine * _pImpEE,sal_uInt32 nN,sal_uInt16 nSP,const SfxItemSet & rLeftParaAttribs,const SfxItemSet & rRightParaAttribs,const SfxStyleSheet * pLeftStyle,const SfxStyleSheet * pRightStyle,sal_Bool bBkwrd)249 EditUndoConnectParas::EditUndoConnectParas( ImpEditEngine* _pImpEE, sal_uInt32 nN, sal_uInt16 nSP,
250 const SfxItemSet& rLeftParaAttribs, const SfxItemSet& rRightParaAttribs,
251 const SfxStyleSheet* pLeftStyle, const SfxStyleSheet* pRightStyle, sal_Bool bBkwrd )
252 : EditUndo( EDITUNDO_CONNECTPARAS, _pImpEE ),
253 aLeftParaAttribs( rLeftParaAttribs ),
254 aRightParaAttribs( rRightParaAttribs )
255 {
256 nNode = nN;
257 nSepPos = nSP;
258
259 if ( pLeftStyle )
260 {
261 aLeftStyleName = pLeftStyle->GetName();
262 eLeftStyleFamily = pLeftStyle->GetFamily();
263 }
264 if ( pRightStyle )
265 {
266 aRightStyleName = pRightStyle->GetName();
267 eRightStyleFamily = pRightStyle->GetFamily();
268 }
269
270 bBackward = bBkwrd;
271 }
272
~EditUndoConnectParas()273 EditUndoConnectParas::~EditUndoConnectParas()
274 {
275 }
276
Undo()277 void __EXPORT EditUndoConnectParas::Undo()
278 {
279 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
280
281 // Bei SplitContent darf noch kein ParagraphInserted gerufen werden,
282 // weil der Outliner sich auf die Attribute verlaesst um die Tiefe
283 // des Absatzes zu initialisieren
284
285 sal_Bool bCall = GetImpEditEngine()->IsCallParaInsertedOrDeleted();
286 GetImpEditEngine()->SetCallParaInsertedOrDeleted( sal_False );
287
288 EditPaM aPaM = GetImpEditEngine()->SplitContent( nNode, nSepPos );
289 GetImpEditEngine()->SetParaAttribs( nNode, aLeftParaAttribs );
290 GetImpEditEngine()->SetParaAttribs( nNode+1, aRightParaAttribs );
291
292 GetImpEditEngine()->SetCallParaInsertedOrDeleted( bCall );
293 if ( GetImpEditEngine()->IsCallParaInsertedOrDeleted() )
294 GetImpEditEngine()->GetEditEnginePtr()->ParagraphInserted( nNode+1 );
295
296 if ( GetImpEditEngine()->GetStyleSheetPool() )
297 {
298 if ( aLeftStyleName.Len() )
299 GetImpEditEngine()->SetStyleSheet( nNode, (SfxStyleSheet*)GetImpEditEngine()->GetStyleSheetPool()->Find( aLeftStyleName, eLeftStyleFamily ) );
300 if ( aRightStyleName.Len() )
301 GetImpEditEngine()->SetStyleSheet( nNode+1, (SfxStyleSheet*)GetImpEditEngine()->GetStyleSheetPool()->Find( aRightStyleName, eRightStyleFamily ) );
302 }
303
304 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( EditSelection( aPaM, aPaM ) );
305 }
306
Redo()307 void __EXPORT EditUndoConnectParas::Redo()
308 {
309 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
310 EditPaM aPaM = GetImpEditEngine()->ConnectContents( nNode, bBackward );
311
312 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( EditSelection( aPaM, aPaM ) );
313 }
314
315 // -----------------------------------------------------------------------
316 // EditUndoSplitPara
317 // ------------------------------------------------------------------------
EditUndoSplitPara(ImpEditEngine * _pImpEE,sal_uInt32 nN,sal_uInt16 nSP)318 EditUndoSplitPara::EditUndoSplitPara( ImpEditEngine* _pImpEE, sal_uInt32 nN, sal_uInt16 nSP )
319 : EditUndo( EDITUNDO_SPLITPARA, _pImpEE )
320 {
321 nNode = nN;
322 nSepPos = nSP;
323 }
324
~EditUndoSplitPara()325 EditUndoSplitPara::~EditUndoSplitPara()
326 {
327 }
328
Undo()329 void __EXPORT EditUndoSplitPara::Undo()
330 {
331 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
332 EditPaM aPaM = GetImpEditEngine()->ConnectContents( nNode, sal_False );
333 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( EditSelection( aPaM, aPaM ) );
334 }
335
Redo()336 void __EXPORT EditUndoSplitPara::Redo()
337 {
338 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
339 EditPaM aPaM = GetImpEditEngine()->SplitContent( nNode, nSepPos );
340 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( EditSelection( aPaM, aPaM ) );
341 }
342
343 // -----------------------------------------------------------------------
344 // EditUndoInsertChars
345 // ------------------------------------------------------------------------
EditUndoInsertChars(ImpEditEngine * _pImpEE,const EPaM & rEPaM,const XubString & rStr)346 EditUndoInsertChars::EditUndoInsertChars( ImpEditEngine* _pImpEE, const EPaM& rEPaM, const XubString& rStr )
347 : EditUndo( EDITUNDO_INSERTCHARS, _pImpEE ),
348 aEPaM( rEPaM ), aText( rStr )
349 {
350 }
351
Undo()352 void __EXPORT EditUndoInsertChars::Undo()
353 {
354 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
355 EditPaM aPaM( GetImpEditEngine()->CreateEditPaM( aEPaM ) );
356 EditSelection aSel( aPaM, aPaM );
357 aSel.Max().GetIndex() = aSel.Max().GetIndex() + aText.Len();
358 EditPaM aNewPaM( GetImpEditEngine()->ImpDeleteSelection( aSel ) );
359 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( EditSelection( aNewPaM, aNewPaM ) );
360 }
361
Redo()362 void __EXPORT EditUndoInsertChars::Redo()
363 {
364 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
365 EditPaM aPaM( GetImpEditEngine()->CreateEditPaM( aEPaM ) );
366 GetImpEditEngine()->ImpInsertText( EditSelection( aPaM, aPaM ), aText );
367 EditPaM aNewPaM( aPaM );
368 aNewPaM.GetIndex() = aNewPaM.GetIndex() + aText.Len();
369 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( EditSelection( aPaM, aNewPaM ) );
370 }
371
Merge(SfxUndoAction * pNextAction)372 sal_Bool __EXPORT EditUndoInsertChars::Merge( SfxUndoAction* pNextAction )
373 {
374 if ( !pNextAction->ISA( EditUndoInsertChars ) )
375 return sal_False;
376
377 EditUndoInsertChars* pNext = (EditUndoInsertChars*)pNextAction;
378
379 if ( aEPaM.nPara != pNext->aEPaM.nPara )
380 return sal_False;
381
382 if ( ( aEPaM.nIndex + aText.Len() ) == pNext->aEPaM.nIndex )
383 {
384 aText += pNext->aText;
385 return sal_True;
386 }
387 return sal_False;
388 }
389
390 // -----------------------------------------------------------------------
391 // EditUndoRemoveChars
392 // ------------------------------------------------------------------------
EditUndoRemoveChars(ImpEditEngine * _pImpEE,const EPaM & rEPaM,const XubString & rStr)393 EditUndoRemoveChars::EditUndoRemoveChars( ImpEditEngine* _pImpEE, const EPaM& rEPaM, const XubString& rStr )
394 : EditUndo( EDITUNDO_REMOVECHARS, _pImpEE ),
395 aEPaM( rEPaM ), aText( rStr )
396 {
397 }
398
Undo()399 void __EXPORT EditUndoRemoveChars::Undo()
400 {
401 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
402 EditPaM aPaM( GetImpEditEngine()->CreateEditPaM( aEPaM ) );
403 EditSelection aSel( aPaM, aPaM );
404 GetImpEditEngine()->ImpInsertText( aSel, aText );
405 aSel.Max().GetIndex() = aSel.Max().GetIndex() + aText.Len();
406 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aSel );
407 }
408
Redo()409 void __EXPORT EditUndoRemoveChars::Redo()
410 {
411 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
412 EditPaM aPaM( GetImpEditEngine()->CreateEditPaM( aEPaM ) );
413 EditSelection aSel( aPaM, aPaM );
414 aSel.Max().GetIndex() = aSel.Max().GetIndex() + aText.Len();
415 EditPaM aNewPaM = GetImpEditEngine()->ImpDeleteSelection( aSel );
416 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aNewPaM );
417 }
418
419 // -----------------------------------------------------------------------
420 // EditUndoInsertFeature
421 // ------------------------------------------------------------------------
EditUndoInsertFeature(ImpEditEngine * _pImpEE,const EPaM & rEPaM,const SfxPoolItem & rFeature)422 EditUndoInsertFeature::EditUndoInsertFeature( ImpEditEngine* _pImpEE, const EPaM& rEPaM, const SfxPoolItem& rFeature)
423 : EditUndo( EDITUNDO_INSERTFEATURE, _pImpEE ), aEPaM( rEPaM )
424 {
425 pFeature = rFeature.Clone();
426 DBG_ASSERT( pFeature, "Feature konnte nicht dupliziert werden: EditUndoInsertFeature" );
427 }
428
~EditUndoInsertFeature()429 EditUndoInsertFeature::~EditUndoInsertFeature()
430 {
431 delete pFeature;
432 }
433
Undo()434 void __EXPORT EditUndoInsertFeature::Undo()
435 {
436 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
437 EditPaM aPaM( GetImpEditEngine()->CreateEditPaM( aEPaM ) );
438 EditSelection aSel( aPaM, aPaM );
439 // Attribute werden dort implizit vom Dokument korrigiert...
440 aSel.Max().GetIndex()++;
441 EditPaM aNewPaM = GetImpEditEngine()->ImpDeleteSelection( aSel );
442 aSel.Max().GetIndex()--; // Fuer Selektion
443 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aSel );
444 }
445
Redo()446 void __EXPORT EditUndoInsertFeature::Redo()
447 {
448 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
449 EditPaM aPaM( GetImpEditEngine()->CreateEditPaM( aEPaM ) );
450 EditSelection aSel( aPaM, aPaM );
451 GetImpEditEngine()->ImpInsertFeature( aSel, *pFeature );
452 if ( pFeature->Which() == EE_FEATURE_FIELD )
453 GetImpEditEngine()->UpdateFields();
454 aSel.Max().GetIndex()++;
455 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aSel );
456 }
457
458 // -----------------------------------------------------------------------
459 // EditUndoMoveParagraphs
460 // ------------------------------------------------------------------------
EditUndoMoveParagraphs(ImpEditEngine * _pImpEE,const Range & rParas,sal_uInt32 n)461 EditUndoMoveParagraphs::EditUndoMoveParagraphs
462 ( ImpEditEngine* _pImpEE, const Range& rParas, sal_uInt32 n )
463 : EditUndo( EDITUNDO_MOVEPARAGRAPHS, _pImpEE ),
464 nParagraphs( rParas )
465 {
466 nDest = n;
467 }
468
~EditUndoMoveParagraphs()469 EditUndoMoveParagraphs::~EditUndoMoveParagraphs()
470 {
471 }
472
Undo()473 void __EXPORT EditUndoMoveParagraphs::Undo()
474 {
475 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
476 Range aTmpRange( nParagraphs );
477 long nTmpDest = aTmpRange.Min();
478
479 long nDiff = ( nDest - aTmpRange.Min() );
480 aTmpRange.Min() += nDiff;
481 aTmpRange.Max() += nDiff;
482
483 if ( nParagraphs.Min() < (long)nDest )
484 {
485 long nLen = aTmpRange.Len();
486 aTmpRange.Min() -= nLen;
487 aTmpRange.Max() -= nLen;
488 }
489 else
490 nTmpDest += aTmpRange.Len();
491
492 EditSelection aNewSel( GetImpEditEngine()->MoveParagraphs( aTmpRange, (sal_uInt32)nTmpDest, 0 ) );
493 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aNewSel );
494 }
495
Redo()496 void __EXPORT EditUndoMoveParagraphs::Redo()
497 {
498 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
499 EditSelection aNewSel( GetImpEditEngine()->MoveParagraphs( nParagraphs, nDest, 0 ) );
500 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aNewSel );
501 }
502
503 // -----------------------------------------------------------------------
504 // EditUndoSetStyleSheet
505 // ------------------------------------------------------------------------
EditUndoSetStyleSheet(ImpEditEngine * _pImpEE,sal_uInt32 nP,const XubString & rPrevName,SfxStyleFamily ePrevFam,const XubString & rNewName,SfxStyleFamily eNewFam,const SfxItemSet & rPrevParaAttribs)506 EditUndoSetStyleSheet::EditUndoSetStyleSheet( ImpEditEngine* _pImpEE, sal_uInt32 nP,
507 const XubString& rPrevName, SfxStyleFamily ePrevFam,
508 const XubString& rNewName, SfxStyleFamily eNewFam,
509 const SfxItemSet& rPrevParaAttribs )
510 : EditUndo( EDITUNDO_STYLESHEET, _pImpEE ), aPrevName( rPrevName ), aNewName( rNewName ),
511 aPrevParaAttribs( rPrevParaAttribs )
512 {
513 ePrevFamily = ePrevFam;
514 eNewFamily = eNewFam;
515 nPara = nP;
516 }
517
~EditUndoSetStyleSheet()518 EditUndoSetStyleSheet::~EditUndoSetStyleSheet()
519 {
520 }
521
Undo()522 void __EXPORT EditUndoSetStyleSheet::Undo()
523 {
524 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
525 GetImpEditEngine()->SetStyleSheet( nPara, (SfxStyleSheet*)GetImpEditEngine()->GetStyleSheetPool()->Find( aPrevName, ePrevFamily ) );
526 GetImpEditEngine()->SetParaAttribs( nPara, aPrevParaAttribs );
527 lcl_DoSetSelection( GetImpEditEngine()->GetActiveView(), nPara );
528 }
529
Redo()530 void __EXPORT EditUndoSetStyleSheet::Redo()
531 {
532 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
533 GetImpEditEngine()->SetStyleSheet( nPara, (SfxStyleSheet*)GetImpEditEngine()->GetStyleSheetPool()->Find( aNewName, eNewFamily ) );
534 lcl_DoSetSelection( GetImpEditEngine()->GetActiveView(), nPara );
535 }
536
537 // -----------------------------------------------------------------------
538 // EditUndoSetParaAttribs
539 // ------------------------------------------------------------------------
EditUndoSetParaAttribs(ImpEditEngine * _pImpEE,sal_uInt32 nP,const SfxItemSet & rPrevItems,const SfxItemSet & rNewItems)540 EditUndoSetParaAttribs::EditUndoSetParaAttribs( ImpEditEngine* _pImpEE, sal_uInt32 nP, const SfxItemSet& rPrevItems, const SfxItemSet& rNewItems )
541 : EditUndo( EDITUNDO_PARAATTRIBS, _pImpEE ),
542 aPrevItems( rPrevItems ),
543 aNewItems(rNewItems )
544 {
545 nPara = nP;
546 }
547
~EditUndoSetParaAttribs()548 EditUndoSetParaAttribs::~EditUndoSetParaAttribs()
549 {
550 }
551
Undo()552 void __EXPORT EditUndoSetParaAttribs::Undo()
553 {
554 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
555 GetImpEditEngine()->SetParaAttribs( nPara, aPrevItems );
556 lcl_DoSetSelection( GetImpEditEngine()->GetActiveView(), nPara );
557 }
558
Redo()559 void __EXPORT EditUndoSetParaAttribs::Redo()
560 {
561 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
562 GetImpEditEngine()->SetParaAttribs( nPara, aNewItems );
563 lcl_DoSetSelection( GetImpEditEngine()->GetActiveView(), nPara );
564 }
565
566 // -----------------------------------------------------------------------
567 // EditUndoSetAttribs
568 // ------------------------------------------------------------------------
EditUndoSetAttribs(ImpEditEngine * _pImpEE,const ESelection & rESel,const SfxItemSet & rNewItems)569 EditUndoSetAttribs::EditUndoSetAttribs( ImpEditEngine* _pImpEE, const ESelection& rESel, const SfxItemSet& rNewItems )
570 : EditUndo( EDITUNDO_ATTRIBS, _pImpEE ),
571 aESel( rESel ),
572 aNewAttribs( rNewItems )
573 {
574 // Wenn das EditUndoSetAttribs eigentlich ein RemoveAttribs ist, koennte
575 // man das eigentlich an einem leeren ItemSet erkennen, aber dann muesste
576 // an einigen Stellen abgefangen werden, das ggf. ein SetAttribs mit einem
577 // leeren ItemSet gemacht wird.
578 // => Ich habe lieber diesen Member spendiert...
579 bSetIsRemove = sal_False;
580 bRemoveParaAttribs = sal_False;
581 nRemoveWhich = 0;
582 nSpecial = 0;
583 }
584
~EditUndoSetAttribs()585 EditUndoSetAttribs::~EditUndoSetAttribs()
586 {
587 // Items aus Pool holen...
588 SfxItemPool* pPool = aNewAttribs.GetPool();
589 sal_uInt16 nContents = aPrevAttribs.Count();
590 for ( sal_uInt16 n = 0; n < nContents; n++ )
591 {
592 ContentAttribsInfo* pInf = aPrevAttribs[n];
593 DBG_ASSERT( pInf, "Undo_DTOR (SetAttribs): pInf = NULL!" );
594 for ( sal_uInt16 nAttr = 0; nAttr < pInf->GetPrevCharAttribs().Count(); nAttr++ )
595 {
596 EditCharAttrib* pX = pInf->GetPrevCharAttribs()[nAttr];
597 DBG_ASSERT( pX, "Undo_DTOR (SetAttribs): pX = NULL!" );
598 pPool->Remove( *pX->GetItem() );
599 delete pX;
600 }
601 delete pInf;
602 }
603 }
604
Undo()605 void __EXPORT EditUndoSetAttribs::Undo()
606 {
607 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
608 ImpEditEngine* _pImpEE = GetImpEditEngine();
609 sal_Bool bFields = sal_False;
610 for ( sal_uInt32 nPara = aESel.nStartPara; nPara <= aESel.nEndPara; nPara++ )
611 {
612 ContentAttribsInfo* pInf = aPrevAttribs[ (sal_uInt16)(nPara-aESel.nStartPara) ];
613 DBG_ASSERT( pInf, "Undo (SetAttribs): pInf = NULL!" );
614
615 // erstmal die Absatzattribute...
616 _pImpEE->SetParaAttribs( nPara, pInf->GetPrevParaAttribs() );
617
618 // Dann die Zeichenattribute...
619 // Alle Attribute inkl. Features entfernen, werden wieder neu eingestellt.
620 _pImpEE->RemoveCharAttribs( nPara, 0, sal_True );
621 DBG_ASSERT( _pImpEE->GetEditDoc().SaveGetObject( nPara ), "Undo (SetAttribs): pNode = NULL!" );
622 ContentNode* pNode = _pImpEE->GetEditDoc().GetObject( nPara );
623 for ( sal_uInt16 nAttr = 0; nAttr < pInf->GetPrevCharAttribs().Count(); nAttr++ )
624 {
625 EditCharAttrib* pX = pInf->GetPrevCharAttribs()[nAttr];
626 DBG_ASSERT( pX, "Redo (SetAttribs): pX = NULL!" );
627 // wird autom. 'eingepoolt'.
628 _pImpEE->GetEditDoc().InsertAttrib( pNode, pX->GetStart(), pX->GetEnd(), *pX->GetItem() );
629 if ( pX->Which() == EE_FEATURE_FIELD )
630 bFields = sal_True;
631 }
632 }
633 if ( bFields )
634 _pImpEE->UpdateFields();
635 ImpSetSelection( GetImpEditEngine()->GetActiveView() );
636 }
637
Redo()638 void __EXPORT EditUndoSetAttribs::Redo()
639 {
640 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
641 ImpEditEngine* _pImpEE = GetImpEditEngine();
642
643 EditSelection aSel( _pImpEE->CreateSel( aESel ) );
644 if ( !bSetIsRemove )
645 _pImpEE->SetAttribs( aSel, aNewAttribs, nSpecial );
646 else
647 _pImpEE->RemoveCharAttribs( aSel, bRemoveParaAttribs, nRemoveWhich );
648
649 ImpSetSelection( GetImpEditEngine()->GetActiveView() );
650 }
651
ImpSetSelection(EditView *)652 void EditUndoSetAttribs::ImpSetSelection( EditView* /*pView*/ )
653 {
654 ImpEditEngine* _pImpEE = GetImpEditEngine();
655 EditSelection aSel( _pImpEE->CreateSel( aESel ) );
656 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aSel );
657 }
658
659 // -----------------------------------------------------------------------
660 // EditUndoTransliteration
661 // ------------------------------------------------------------------------
EditUndoTransliteration(ImpEditEngine * _pImpEE,const ESelection & rESel,sal_Int32 nM)662 EditUndoTransliteration::EditUndoTransliteration( ImpEditEngine* _pImpEE, const ESelection& rESel, sal_Int32 nM )
663 : EditUndo( EDITUNDO_TRANSLITERATE, _pImpEE ), aOldESel( rESel )
664 {
665 nMode = nM;
666 pTxtObj = NULL;
667 }
668
~EditUndoTransliteration()669 EditUndoTransliteration::~EditUndoTransliteration()
670 {
671 delete pTxtObj;
672 }
673
Undo()674 void __EXPORT EditUndoTransliteration::Undo()
675 {
676 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
677
678 ImpEditEngine* _pImpEE = GetImpEditEngine();
679
680 EditSelection aSel( _pImpEE->CreateSel( aNewESel ) );
681
682 // Insert text, but don't expand Atribs at the current position:
683 aSel = _pImpEE->DeleteSelected( aSel );
684 EditSelection aDelSel( aSel );
685 aSel = _pImpEE->InsertParaBreak( aSel );
686 aDelSel.Max() = aSel.Min();
687 aDelSel.Max().GetNode()->GetCharAttribs().DeleteEmptyAttribs( _pImpEE->GetEditDoc().GetItemPool() );
688 EditSelection aNewSel;
689 if ( pTxtObj )
690 {
691 aNewSel = _pImpEE->InsertText( *pTxtObj, aSel );
692 }
693 else
694 {
695 aNewSel = _pImpEE->InsertText( aSel, aText );
696 }
697 if ( aNewSel.Min().GetNode() == aDelSel.Max().GetNode() )
698 {
699 aNewSel.Min().SetNode( aDelSel.Min().GetNode() );
700 aNewSel.Min().GetIndex() =
701 aNewSel.Min().GetIndex() + aDelSel.Min().GetIndex();
702 }
703 if ( aNewSel.Max().GetNode() == aDelSel.Max().GetNode() )
704 {
705 aNewSel.Max().SetNode( aDelSel.Min().GetNode() );
706 aNewSel.Max().GetIndex() =
707 aNewSel.Max().GetIndex() + aDelSel.Min().GetIndex();
708 }
709 _pImpEE->DeleteSelected( aDelSel );
710
711 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aNewSel );
712 }
713
Redo()714 void __EXPORT EditUndoTransliteration::Redo()
715 {
716 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
717 ImpEditEngine* _pImpEE = GetImpEditEngine();
718
719 EditSelection aSel( _pImpEE->CreateSel( aOldESel ) );
720 EditSelection aNewSel = _pImpEE->TransliterateText( aSel, nMode );
721 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( aNewSel );
722 }
723
724 // -----------------------------------------------------------------------
725 // EditUndoMarkSelection
726 // ------------------------------------------------------------------------
EditUndoMarkSelection(ImpEditEngine * _pImpEE,const ESelection & rSel)727 EditUndoMarkSelection::EditUndoMarkSelection( ImpEditEngine* _pImpEE, const ESelection& rSel )
728 : EditUndo( EDITUNDO_MARKSELECTION, _pImpEE ), aSelection( rSel )
729 {
730 }
731
~EditUndoMarkSelection()732 EditUndoMarkSelection::~EditUndoMarkSelection()
733 {
734 }
735
Undo()736 void __EXPORT EditUndoMarkSelection::Undo()
737 {
738 DBG_ASSERT( GetImpEditEngine()->GetActiveView(), "Undo/Redo: Keine Active View!" );
739 if ( GetImpEditEngine()->GetActiveView() )
740 {
741 if ( GetImpEditEngine()->IsFormatted() )
742 GetImpEditEngine()->GetActiveView()->SetSelection( aSelection );
743 else
744 GetImpEditEngine()->GetActiveView()->GetImpEditView()->SetEditSelection( GetImpEditEngine()->CreateSel( aSelection ) );
745 }
746 }
747
Redo()748 void __EXPORT EditUndoMarkSelection::Redo()
749 {
750 // Fuer Redo unwichtig, weil am Anfang der Undo-Klammerung
751 }
752
753