SynEdit: Fixed folding broken by undo/redo. issue #21473

git-svn-id: trunk@35912 -
This commit is contained in:
martin 2012-03-13 01:18:33 +00:00
parent a452a818da
commit 6f7c5e1d9b
4 changed files with 109 additions and 2 deletions

View File

@ -250,7 +250,14 @@ type
procedure EditLinesDelete(LogY, ACount: Integer); virtual; abstract;
procedure EditUndo(Item: TSynEditUndoItem); virtual; abstract;
procedure EditRedo(Item: TSynEditUndoItem); virtual; abstract;
property IsInEditAction: Boolean read GetIsInEditAction;
(* IsInEditAction
While in EditAction a "senrEditAction" event is triggerred, that contains
more detailed line-count change info.
Yet senrLineCount is also sent.
IsInEditAction allows to skip senrLineCount, that are sent as senrEditAction
Currently used by FoldView
*)
property IsInEditAction: Boolean read GetIsInEditAction; // Todo: have individual event types instead
property UndoList: TSynEditUndoList read GetUndoList;
property RedoList: TSynEditUndoList read GetRedoList;
property CurUndoList: TSynEditUndoList read GetCurUndoList; // Re or Undo (Redo while undoing)

View File

@ -842,6 +842,25 @@ begin
dec(j);
inc(PWidths);
end;
//j := 0;
//for i := 0 to LineLen-1 do begin
// if j = 0 then begin
// j := UTF8CharacterLength(Line);
// if (j=2) and
// ( ( (Line^ = #$CC) and ((Line+1)^ in [#$80..#$FF]) ) or
// ( (Line^ = #$CD) and ((Line+1)^ in [#$00..#$AF]) ) )
// then
// PWidths^ := 0 // Combining Diacritical Marks
// else
// PWidths^ := 1;
// inc(Line, j);
// end else begin
// PWidths^ := 0;
// end;
// dec(j);
// inc(PWidths);
//end;
end;
function TSynEditStringList.GetDisplayView: TLazSynDisplayView;
@ -1191,7 +1210,9 @@ end;
procedure TSynEditStringList.EditUndo(Item: TSynEditUndoItem);
begin
IncIsInEditAction; // all undo calls edit actions
EditRedo(Item);
DecIsInEditAction;
end;
procedure TSynEditStringList.UndoEditLinesDelete(LogY, ACount: Integer);
@ -1211,7 +1232,9 @@ end;
procedure TSynEditStringList.EditRedo(Item: TSynEditUndoItem);
begin
IncIsInEditAction; // all undo calls edit actions
Item.PerformUndo(self);
DecIsInEditAction;
end;
procedure TSynEditStringList.SendNotification(AReason: TSynEditNotifyReason;

View File

@ -1126,8 +1126,10 @@ end;
procedure TSynEditStringTrimmingList.EditRedo(Item: TSynEditUndoItem);
begin
IncIsInEditAction; // all undo calls edit actions
if not Item.PerformUndo(self) then
inherited EditRedo(Item);
DecIsInEditAction;
end;
end.

View File

@ -47,6 +47,7 @@ type
function TestTextHide3: TStringArray;
function TestTextHide4: TStringArray;
function TestTextPlain: TStringArray;
function TestTextBug21473: TStringArray;
protected
procedure TstSetText(AName: String; AText: Array of String);
procedure TstFold(AName: String; AFoldAtIndex: integer; AExpectedLines: Array of Integer);
@ -545,6 +546,46 @@ begin
end;
function TTestFoldedView.TestTextBug21473: TStringArray;
begin
SetLength(Result, 35);
Result[ 0] := 'program a;';
Result[ 1] := '';
Result[ 2] := '// 1';
Result[ 3] := '// 2';
Result[ 4] := 'procedure Bar;';
Result[ 5] := '';
Result[ 6] := ' procedure BarA;';
Result[ 7] := ' begin';
Result[ 8] := ' end;';
Result[ 9] := '';
Result[10] := ' procedure BarB;';
Result[11] := ' begin';
Result[12] := ' end;';
Result[13] := '';
Result[14] := 'begin';
Result[15] := 'end;';
Result[16] := '';
Result[17] := '// 1';
Result[18] := '// 2';
Result[19] := 'procedure Foo;';
Result[20] := '';
Result[21] := ' procedure FooA;';
Result[22] := ' begin';
Result[23] := ' end;';
Result[24] := '';
Result[25] := ' procedure FooB;';
Result[26] := ' begin';
Result[27] := ' end;';
Result[28] := '';
Result[29] := 'begin';
Result[30] := 'end;';
Result[31] := '';
Result[32] := 'end.';
Result[33] := '';
Result[34] := '';
end;
procedure TTestFoldedView.TestFold;
procedure RunTest;
@ -919,6 +960,7 @@ procedure TTestFoldedView.TestFoldEdit;
var
n: string;
i: integer;
s: String;
begin
{%region simple}
@ -1394,8 +1436,42 @@ begin
TstFold('f2', 3, -1, 1, False, 1, [0, 1, 2, 3, 9, 10, 11]);
TestNodeAtPos('n3', 15, 4);
PopBaseName;
{%endregion}
{%region}
// 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33
TstSetText('TestTextBug21473', TestTextBug21473);
TstFold('FooB', 25, -1, 1, False, 1, [0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25, 28,29,30,31,32,33]);
TstFold('FooA', 21, -1, 1, False, 1, [0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21, 24,25, 28,29,30,31,32,33]);
TstFold('Foo ', 19, -1, 1, False, 1, [0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19, 31,32,33]);
TestNodeAtPos('n1', 1, 20);
s := SynEdit.TextBetweenPoints[point(1,7), point(1,10)];
SynEdit.TextBetweenPoints[point(1,6), point(1,9)] := '';
TestFoldedText('Cut', [0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16, 28,29,30]);
TestNodeAtPos('n1 Cut', 1, 17);
SynEdit.TextBetweenPoints[point(1,7), point(1,7)] := s;
TestFoldedText('Restore', [0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19, 31,32,33]);
TestNodeAtPos('n1 Restore', 1, 20);
SynEdit.Undo;
//debugln('*********AFTER UNDO'); FoldedView.debug;
TestFoldedText('Undone', [0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16, 28,29,30]);
TestNodeAtPos('n1 Undone', 1, 17);
//SetCaretAndSel(1, 4, 1, 8);
//SynEdit.CutToClipboard;
PopBaseName;
{%endregion}
end;
procedure TTestFoldedView.TestFoldStateFromText;
@ -2043,7 +2119,6 @@ begin
CheckNode(TheList.HLNode[0], 0, 0, 0, 7, 0, 1, 0, 1, 10, 10, 1, [sfaOpen,sfaMarkup,sfaFold,sfaFoldFold]);
PopBaseName;
end;
initialization