SynEdit: Markup fold color, react to enabled, patch 16 from issue #30421 by Pascal R.

git-svn-id: trunk@54019 -
This commit is contained in:
martin 2017-01-28 02:54:43 +00:00
parent 715527349b
commit ccc7c8c621

View File

@ -92,6 +92,8 @@ type
Colors : array of TColor; Colors : array of TColor;
FPreparedRow: integer; FPreparedRow: integer;
FLastNode: TSynFoldNodeInfo; FLastNode: TSynFoldNodeInfo;
FLastEnabled: Boolean;
procedure DoMarkupParentFoldAtRow(aRow: Integer); procedure DoMarkupParentFoldAtRow(aRow: Integer);
procedure DoMarkupParentCloseFoldAtRow(aRow: Integer); procedure DoMarkupParentCloseFoldAtRow(aRow: Integer);
procedure SetDefaultGroup(AValue: integer); procedure SetDefaultGroup(AValue: integer);
@ -106,6 +108,7 @@ type
procedure SetLines(const AValue: TSynEditStrings); override; procedure SetLines(const AValue: TSynEditStrings); override;
procedure LinesChanged(Sender: TSynEditStrings; aIndex, aCount: Integer); procedure LinesChanged(Sender: TSynEditStrings; aIndex, aCount: Integer);
procedure HighlightChanged(Sender: TSynEditStrings; aIndex, aCount: Integer); procedure HighlightChanged(Sender: TSynEditStrings; aIndex, aCount: Integer);
procedure DoEnabledChanged(Sender: TObject); override;
public public
constructor Create(ASynEdit : TSynEditBase); constructor Create(ASynEdit : TSynEditBase);
destructor Destroy; override; destructor Destroy; override;
@ -124,7 +127,13 @@ type
implementation implementation
uses uses
SynEdit, SynEditTypes, SynEditMiscProcs, Dialogs; SynEdit,
SynEditTypes,
SynEditMiscProcs,
{$IFDEF SynEditMarkupFoldColoringDebug}
SynHighlighterPas,
{$endif}
Dialogs;
{$IFDEF SynEditMarkupFoldColoringDebug} {$IFDEF SynEditMarkupFoldColoringDebug}
@ -271,6 +280,9 @@ end;
procedure TSynEditMarkupFoldColors.TextBufferChanged(Sender: TSynEditStrings; procedure TSynEditMarkupFoldColors.TextBufferChanged(Sender: TSynEditStrings;
aIndex, aCount: Integer); aIndex, aCount: Integer);
begin begin
if not Enabled then
exit;
InitCache; InitCache;
end; end;
@ -535,15 +547,6 @@ begin
//DebugLn('PrepareMarkupForRow %d', [aRow]); //DebugLn('PrepareMarkupForRow %d', [aRow]);
{$ENDIF} {$ENDIF}
if not Assigned(FHighlighter) then exit; if not Assigned(FHighlighter) then exit;
// if length(FFirstCharacterColumnCache) = 0 then begin
// // array should have been initialized due to a call to SetLines before
// // but with a cloned TextBuffer this is not the case
// // therefore init it here
// {$IFDEF SynEditMarkupFoldColoringDebug}
// DebugLn('!!! SetLines not called before PrepareMarkupForRow (cloned TextBuffer)!!!');
// {$ENDIF}
// InitCache;
// end;
FPreparedRow := aRow; FPreparedRow := aRow;
FFoldColorInfosCount := 0; //reset needed to prevent using of invalid area FFoldColorInfosCount := 0; //reset needed to prevent using of invalid area
@ -608,8 +611,6 @@ begin
end; end;
procedure TSynEditMarkupFoldColors.SetFoldColorInfosCount(pNewCount: Integer); procedure TSynEditMarkupFoldColors.SetFoldColorInfosCount(pNewCount: Integer);
var
i: Integer;
begin begin
if pNewCount > FFoldColorInfosCapacity then begin if pNewCount > FFoldColorInfosCapacity then begin
// expand array // expand array
@ -671,8 +672,11 @@ var
i, lMinAnz, lEndLine, j, l: Integer; i, lMinAnz, lEndLine, j, l: Integer;
lStartNestList, lEndNestList: array of TSynFoldNodeInfo; lStartNestList, lEndNestList: array of TSynFoldNodeInfo;
begin begin
if not Enabled then
exit;
{$IFDEF SynEditMarkupFoldColoringDebug} {$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn('DoTextChanged %d-%d: %d', [StartLine, EndLine, ACountDiff]); DebugLn(' DoTextChanged %d-%d: %d', [StartLine, EndLine, ACountDiff]);
{$ENDIF} {$ENDIF}
// lines available? // lines available?
@ -688,6 +692,10 @@ begin
exit; exit;
FHighlighter.CurrentLines := Lines; FHighlighter.CurrentLines := Lines;
// highlighter still scanning
if FHighlighter.NeedScan then
exit;
if EndLine < 0 then if EndLine < 0 then
EndLine := StartLine EndLine := StartLine
else else
@ -700,16 +708,16 @@ begin
FillNestList(lStartNestList, StartLine, FNestList); FillNestList(lStartNestList, StartLine, FNestList);
{$IFDEF SynEditMarkupFoldColoringDebug} {$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn(' Nodes at Start:'); //DebugLn(' Nodes at Start:');
for i := 0 to length(lStartNestList) - 1 do with lStartNestList[i] do //for i := 0 to length(lStartNestList) - 1 do with lStartNestList[i] do
DebugLn(' x=%.03d l=%.5d %s %s %s %s lvl=%d/%d endline=%d (cache) -> %d (HL)', [LogXStart, ToPos(LineIndex), IfThen(sfaOpen in FoldAction, 'O', IfThen(sfaClose in FoldAction, 'C', ' ')), IfThen(sfaOutlineKeepLevel{OnSameLine} in FoldAction ,'K', ' '), IfThen(sfaOutlineForceIndent in FoldAction, '+', IfThen(sfaOutlineMergeParent in FoldAction, '-', ' ')) ,FoldTypeToStr(FoldType), FoldLvlStart, FoldLvlEnd, FEndLine[LineIndex], ToPos(FHighlighter.FoldEndLine(LineIndex, 0))]); // DebugLn(' x=%.03d l=%.5d %s %s %s %s lvl=%d/%d endline=%d (cache) -> %d (HL)', [LogXStart, ToPos(LineIndex), IfThen(sfaOpen in FoldAction, 'O', IfThen(sfaClose in FoldAction, 'C', ' ')), IfThen(sfaOutlineKeepLevel{OnSameLine} in FoldAction ,'K', ' '), IfThen(sfaOutlineForceIndent in FoldAction, '+', IfThen(sfaOutlineMergeParent in FoldAction, '-', ' ')) ,FoldTypeToStr(FoldType), FoldLvlStart, FoldLvlEnd, FEndLine[LineIndex], ToPos(FHighlighter.FoldEndLine(LineIndex, 0))]);
{$ENDIF} {$ENDIF}
FillNestList(lEndNestList, EndLine + 1, FNestList); FillNestList(lEndNestList, EndLine + 1, FNestList);
{$IFDEF SynEditMarkupFoldColoringDebug} {$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn(' Nodes at End:'); //DebugLn(' Nodes at End:');
for i := 0 to length(lEndNestList) - 1 do with lEndNestList[i] do //for i := 0 to length(lEndNestList) - 1 do with lEndNestList[i] do
DebugLn(' x=%.03d l=%.5d %s %s %s %s lvl=%d/%d endline=%d (cache) -> %d (HL)', [LogXStart, ToPos(LineIndex), IfThen(sfaOpen in FoldAction, 'O', IfThen(sfaClose in FoldAction, 'C', ' ')), IfThen(sfaOutlineKeepLevel{OnSameLine} in FoldAction ,'K', ' '), IfThen(sfaOutlineForceIndent in FoldAction, '+', IfThen(sfaOutlineMergeParent in FoldAction, '-', ' ')) ,FoldTypeToStr(FoldType), FoldLvlStart, FoldLvlEnd, FEndLine[LineIndex], ToPos(FHighlighter.FoldEndLine(LineIndex, 0))]); // DebugLn(' x=%.03d l=%.5d %s %s %s %s lvl=%d/%d endline=%d (cache) -> %d (HL)', [LogXStart, ToPos(LineIndex), IfThen(sfaOpen in FoldAction, 'O', IfThen(sfaClose in FoldAction, 'C', ' ')), IfThen(sfaOutlineKeepLevel{OnSameLine} in FoldAction ,'K', ' '), IfThen(sfaOutlineForceIndent in FoldAction, '+', IfThen(sfaOutlineMergeParent in FoldAction, '-', ' ')) ,FoldTypeToStr(FoldType), FoldLvlStart, FoldLvlEnd, FEndLine[LineIndex], ToPos(FHighlighter.FoldEndLine(LineIndex, 0))]);
{$ENDIF} {$ENDIF}
// delete all nodes in lEndNodeList which where active at StartLine // delete all nodes in lEndNodeList which where active at StartLine
@ -733,9 +741,9 @@ begin
// deeper fold group than StartLine: fold group ends after EndLine // deeper fold group than StartLine: fold group ends after EndLine
// find real EndLine (end line of first remaining fold node) // find real EndLine (end line of first remaining fold node)
{$IFDEF SynEditMarkupFoldColoringDebug} {$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn(' Remaining Nodes:'); //DebugLn(' Remaining Nodes:');
for i := 0 to length(lEndNestList) - 1 do with lEndNestList[i] do //for i := 0 to length(lEndNestList) - 1 do with lEndNestList[i] do
DebugLn(' x=%.03d l=%.5d %s %s %s %s lvl=%d/%d endline=%d (cache) -> %d (HL)', [LogXStart, ToPos(LineIndex), IfThen(sfaOpen in FoldAction, 'O', IfThen(sfaClose in FoldAction, 'C', ' ')), IfThen(sfaOutlineKeepLevel{OnSameLine} in FoldAction ,'K', ' '), IfThen(sfaOutlineForceIndent in FoldAction, '+', IfThen(sfaOutlineMergeParent in FoldAction, '-', ' ')) ,FoldTypeToStr(FoldType), FoldLvlStart, FoldLvlEnd, FEndLine[LineIndex], ToPos(FHighlighter.FoldEndLine(LineIndex, 0))]); // DebugLn(' x=%.03d l=%.5d %s %s %s %s lvl=%d/%d endline=%d (cache) -> %d (HL)', [LogXStart, ToPos(LineIndex), IfThen(sfaOpen in FoldAction, 'O', IfThen(sfaClose in FoldAction, 'C', ' ')), IfThen(sfaOutlineKeepLevel{OnSameLine} in FoldAction ,'K', ' '), IfThen(sfaOutlineForceIndent in FoldAction, '+', IfThen(sfaOutlineMergeParent in FoldAction, '-', ' ')) ,FoldTypeToStr(FoldType), FoldLvlStart, FoldLvlEnd, FEndLine[LineIndex], ToPos(FHighlighter.FoldEndLine(LineIndex, 0))]);
{$ENDIF} {$ENDIF}
// does position of first character change for remaining node? // does position of first character change for remaining node?
if FirstCharacterColumn[lEndNestList[0].LineIndex] <> FFirstCharacterColumnCache[lEndNestList[0].LineIndex] then if FirstCharacterColumn[lEndNestList[0].LineIndex] <> FFirstCharacterColumnCache[lEndNestList[0].LineIndex] then
@ -752,7 +760,7 @@ begin
lEndLine := Max(lEndLine, Max(l, FEndLineCache[LineIndex])); lEndLine := Max(lEndLine, Max(l, FEndLineCache[LineIndex]));
FEndLineCache[LineIndex] := l; FEndLineCache[LineIndex] := l;
{$IFDEF SynEditMarkupFoldColoringDebug} {$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn(' ** x=%.03d l=%.5d %s %s %s %s lvl=%d/%d endline=%d -> %d', [LogXStart, ToPos(LineIndex), IfThen(sfaOpen in FoldAction, 'O', IfThen(sfaClose in FoldAction, 'C', ' ')), IfThen(sfaOutlineKeepLevel{OnSameLine} in FoldAction ,'K', ' '), IfThen(sfaOutlineForceIndent in FoldAction, '+', IfThen(sfaOutlineMergeParent in FoldAction, '-', ' ')) ,FoldTypeToStr(FoldType), FoldLvlStart, FoldLvlEnd, FEndLine[LineIndex], ToPos(FHighlighter.FoldEndLine(LineIndex, 0))]); //DebugLn(' ** x=%.03d l=%.5d %s %s %s %s lvl=%d/%d endline=%d -> %d', [LogXStart, ToPos(LineIndex), IfThen(sfaOpen in FoldAction, 'O', IfThen(sfaClose in FoldAction, 'C', ' ')), IfThen(sfaOutlineKeepLevel{OnSameLine} in FoldAction ,'K', ' '), IfThen(sfaOutlineForceIndent in FoldAction, '+', IfThen(sfaOutlineMergeParent in FoldAction, '-', ' ')) ,FoldTypeToStr(FoldType), FoldLvlStart, FoldLvlEnd, FEndLine[LineIndex], ToPos(FHighlighter.FoldEndLine(LineIndex, 0))]);
{$ENDIF} {$ENDIF}
end; end;
end; end;
@ -769,36 +777,42 @@ begin
{$ENDIF} {$ENDIF}
InvalidateSynLines(EndLine + 1 , lEndLine); InvalidateSynLines(EndLine + 1 , lEndLine);
end; end;
FNestList.Clear;
end; end;
procedure TSynEditMarkupFoldColors.SetLines(const AValue: TSynEditStrings); procedure TSynEditMarkupFoldColors.SetLines(const AValue: TSynEditStrings);
var var
old: TSynEditStrings; old: TSynEditStrings;
begin begin
old := Lines; if Enabled then begin
if Assigned(old) old := Lines;
and (AValue <> old) then begin if Assigned(old)
// change: and (AValue <> old) then begin
// remove Changehandler // change:
old.RemoveChangeHandler(senrLineCount, @LinesChanged); // remove Changehandler
old.RemoveChangeHandler(senrHighlightChanged, @HighlightChanged); old.RemoveChangeHandler(senrLineCount, @LinesChanged);
old.RemoveChangeHandler(senrTextBufferChanged, @TextBufferChanged); old.RemoveChangeHandler(senrHighlightChanged, @HighlightChanged);
ClearCache; old.RemoveChangeHandler(senrTextBufferChanged, @TextBufferChanged);
ClearCache;
end;
end; end;
inherited SetLines(AValue); inherited SetLines(AValue);
if (AValue <> old) then begin if Enabled then begin
// change: if (AValue <> old) then begin
if Assigned(AValue) then begin // change:
// add Changehandler if Assigned(AValue) then begin
AValue.AddChangeHandler(senrLineCount, @LinesChanged); // add Changehandler
AValue.AddChangeHandler(senrHighlightChanged, @HighlightChanged); AValue.AddChangeHandler(senrLineCount, @LinesChanged);
AValue.AddChangeHandler(senrTextBufferChanged, @TextBufferChanged); AValue.AddChangeHandler(senrHighlightChanged, @HighlightChanged);
InitCache; AValue.AddChangeHandler(senrTextBufferChanged, @TextBufferChanged);
end else begin InitCache;
// clear cache end else begin
SetCacheCount(0); // clear cache
if Assigned(FNestList) then SetCacheCount(0);
FNestList.Lines := nil; if Assigned(FNestList) then
FNestList.Lines := nil;
end;
end; end;
end; end;
end; end;
@ -809,9 +823,13 @@ var
absCount, absCount,
idx, i: Integer; idx, i: Integer;
begin begin
if not Enabled then
exit;
{$IFDEF SynEditMarkupFoldColoringDebug} {$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn(' LinesChanged: aIndex=%d aCount=%d', [aIndex, aCount]); DebugLn(' LinesChanged: aIndex=%d aCount=%d', [aIndex, aCount]);
{$ENDIF} {$ENDIF}
idx := ToIdx(aIndex); idx := ToIdx(aIndex);
if (aCount < 0) if (aCount < 0)
and (idx >= 0) then begin and (idx >= 0) then begin
@ -849,9 +867,13 @@ procedure TSynEditMarkupFoldColors.HighlightChanged(Sender: TSynEditStrings;
var var
newHighlighter: TSynCustomHighlighter; newHighlighter: TSynCustomHighlighter;
begin begin
if not Enabled then
exit;
{$IFDEF SynEditMarkupFoldColoringDebug} {$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn(' HighlightChanged: aIndex=%d aCount=%d', [aIndex, aCount]); DebugLn(' HighlightChanged: aIndex=%d aCount=%d', [aIndex, aCount]);
{$ENDIF} {$ENDIF}
if (aIndex <> -1) if (aIndex <> -1)
or (aCount <> -1) then or (aCount <> -1) then
exit; exit;
@ -871,6 +893,36 @@ begin
ClearCache; ClearCache;
end; end;
procedure TSynEditMarkupFoldColors.DoEnabledChanged(Sender: TObject);
begin
if Enabled = FLastEnabled then
exit;
FLastEnabled := Enabled;
if FLastEnabled then begin
{$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn(' *** TSynEditMarkupFoldColors Enabled');
{$ENDIF}
if Assigned(Lines) then begin
// add Changehandler
Lines.AddChangeHandler(senrLineCount, @LinesChanged);
Lines.AddChangeHandler(senrHighlightChanged, @HighlightChanged);
Lines.AddChangeHandler(senrTextBufferChanged, @TextBufferChanged);
InitCache;
end;
end else begin
{$IFDEF SynEditMarkupFoldColoringDebug}
DebugLn(' *** TSynEditMarkupFoldColors Disabled');
{$ENDIF}
if Assigned(Lines) then begin
// remove Changehandler
Lines.RemoveChangeHandler(senrLineCount, @LinesChanged);
Lines.RemoveChangeHandler(senrHighlightChanged, @HighlightChanged);
Lines.RemoveChangeHandler(senrTextBufferChanged, @TextBufferChanged);
ClearCache;
end;
end;
end;
end. end.