mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-11-20 22:19:35 +01:00
synedit: started TSynCustomBeautifier
git-svn-id: trunk@15428 -
This commit is contained in:
parent
a779c0af6e
commit
f1f758e093
@ -19,6 +19,7 @@ uses
|
|||||||
SynEdit, SynEditHighlighter, SynCompletion, SynEditAutoComplete,
|
SynEdit, SynEditHighlighter, SynCompletion, SynEditAutoComplete,
|
||||||
SynEditLazDsgn, SynRegExpr, SynEditRegexSearch, SynEditExport,
|
SynEditLazDsgn, SynRegExpr, SynEditRegexSearch, SynEditExport,
|
||||||
SynExportHTML, SynMemo, SynMacroRecorder, SynEditPlugins,
|
SynExportHTML, SynMemo, SynMacroRecorder, SynEditPlugins,
|
||||||
|
SynBeautifierPas,
|
||||||
SynHighlighterAny,
|
SynHighlighterAny,
|
||||||
SynhighlighterCPP,
|
SynhighlighterCPP,
|
||||||
SynHighlighterCss,
|
SynHighlighterCss,
|
||||||
|
|||||||
@ -337,6 +337,17 @@ type
|
|||||||
public
|
public
|
||||||
property Editor: TCustomSynEdit read FEditor write SetEditor;
|
property Editor: TCustomSynEdit read FEditor write SetEditor;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{ TSynCustomBeautifier }
|
||||||
|
|
||||||
|
TSynCustomBeautifier = class(TComponent)
|
||||||
|
public
|
||||||
|
function LeftSpaces(Editor: TCustomSynEdit; const Line: string;
|
||||||
|
Physical: boolean): Integer;
|
||||||
|
// InsertPos is 1 based. e.g. left,top is 1,1
|
||||||
|
function GetIndentForLineBreak(Editor: TCustomSynEdit;
|
||||||
|
InsertPos: TPoint; var NextText: string): integer; virtual;
|
||||||
|
end;
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
|
|
||||||
{ TCustomSynEdit }
|
{ TCustomSynEdit }
|
||||||
@ -393,6 +404,7 @@ type
|
|||||||
fLastCtrlMouseLinkX2: integer; // logical (byte)
|
fLastCtrlMouseLinkX2: integer; // logical (byte)
|
||||||
fHighlighterNeedsUpdateStartLine: integer; // 1 based, 0 means invalid
|
fHighlighterNeedsUpdateStartLine: integer; // 1 based, 0 means invalid
|
||||||
fHighlighterNeedsUpdateEndLine: integer; // 1 based, 0 means invalid
|
fHighlighterNeedsUpdateEndLine: integer; // 1 based, 0 means invalid
|
||||||
|
fBeautifier: TSynCustomBeautifier;
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
fLines: TStrings;
|
fLines: TStrings;
|
||||||
fLinesInWindow: Integer;// MG: fully visible lines in window
|
fLinesInWindow: Integer;// MG: fully visible lines in window
|
||||||
@ -491,6 +503,7 @@ type
|
|||||||
procedure SetCFDividerDrawLevel(const AValue: Integer);
|
procedure SetCFDividerDrawLevel(const AValue: Integer);
|
||||||
procedure SetLineIndenter(const AValue: TSynCustomLineIndenter);
|
procedure SetLineIndenter(const AValue: TSynCustomLineIndenter);
|
||||||
procedure SetLogicalCaretXY(const NewLogCaretXY: TPoint);
|
procedure SetLogicalCaretXY(const NewLogCaretXY: TPoint);
|
||||||
|
procedure SetBeautifier(NewBeautifier: TSynCustomBeautifier);
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
function GetMaxUndo: Integer;
|
function GetMaxUndo: Integer;
|
||||||
function GetSelAvail: Boolean;
|
function GetSelAvail: Boolean;
|
||||||
@ -828,6 +841,7 @@ type
|
|||||||
property CharWidth: integer read fCharWidth;
|
property CharWidth: integer read fCharWidth;
|
||||||
property Color default clWhite;
|
property Color default clWhite;
|
||||||
{$IFDEF SYN_LAZARUS}
|
{$IFDEF SYN_LAZARUS}
|
||||||
|
property Beautifier: TSynCustomBeautifier read fBeautifier write SetBeautifier;
|
||||||
property CtrlMouseActive: boolean read fCtrlMouseActive;
|
property CtrlMouseActive: boolean read fCtrlMouseActive;
|
||||||
property LogicalCaretXY: TPoint read GetLogicalCaretXY write SetLogicalCaretXY;
|
property LogicalCaretXY: TPoint read GetLogicalCaretXY write SetLogicalCaretXY;
|
||||||
property LineIndenter: TSynCustomLineIndenter read fLineIndenter
|
property LineIndenter: TSynCustomLineIndenter read fLineIndenter
|
||||||
@ -934,6 +948,7 @@ type
|
|||||||
// inherited properties
|
// inherited properties
|
||||||
property Align;
|
property Align;
|
||||||
{$IFDEF SYN_LAZARUS}
|
{$IFDEF SYN_LAZARUS}
|
||||||
|
property Beautifier;
|
||||||
property BlockIndent;
|
property BlockIndent;
|
||||||
property BorderSpacing;
|
property BorderSpacing;
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
@ -1732,6 +1747,13 @@ procedure TCustomSynEdit.SetLogicalCaretXY(const NewLogCaretXY: TPoint);
|
|||||||
begin
|
begin
|
||||||
CaretXY:=LogicalToPhysicalPos(NewLogCaretXY);
|
CaretXY:=LogicalToPhysicalPos(NewLogCaretXY);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
procedure TCustomSynEdit.SetBeautifier(NewBeautifier: TSynCustomBeautifier);
|
||||||
|
begin
|
||||||
|
if fBeautifier=NewBeautifier then exit;
|
||||||
|
fBeautifier:=NewBeautifier;
|
||||||
|
end;
|
||||||
|
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
|
|
||||||
function TCustomSynEdit.GetSelAvail: Boolean;
|
function TCustomSynEdit.GetSelAvail: Boolean;
|
||||||
@ -8274,70 +8296,84 @@ begin
|
|||||||
InsDelta := Ord(CaretX = 1);
|
InsDelta := Ord(CaretX = 1);
|
||||||
{$IFDEF SYN_LAZARUS}
|
{$IFDEF SYN_LAZARUS}
|
||||||
LogCaretXY:=PhysicalToLogicalPos(CaretXY);
|
LogCaretXY:=PhysicalToLogicalPos(CaretXY);
|
||||||
{$ENDIF}
|
Len := Length(Temp);
|
||||||
|
if Len >= LogCaretXY.X then begin
|
||||||
|
if LogCaretXY.X > 1 then begin
|
||||||
|
// break line in two
|
||||||
|
SpaceCount1 := LeftSpaces(Temp);
|
||||||
|
Temp := Copy(LineText, 1, LogCaretXY.X - 1);
|
||||||
|
TrimmedSetLine(CaretY - 1, Temp);
|
||||||
|
Delete(Temp2, 1, LogCaretXY.X - 1);
|
||||||
|
if Assigned(Beautifier) then
|
||||||
|
SpaceCount1:=Beautifier.GetIndentForLineBreak(Self,LogCaretXY,Temp2);
|
||||||
|
fUndoList.AddChange(crLineBreak,
|
||||||
|
LogCaretXY, LogCaretXY,
|
||||||
|
Temp2, smNormal);
|
||||||
|
Lines.Insert(CaretY, StringOfChar(' ', SpaceCount1) + Temp2);
|
||||||
|
if Command = ecLineBreak then
|
||||||
|
CaretXY := Point(SpaceCount1 + 1, CaretY + 1);
|
||||||
|
end else begin
|
||||||
|
// move the whole line
|
||||||
|
Lines.Insert(CaretY - 1, '');
|
||||||
|
fUndoList.AddChange(crLineBreak,
|
||||||
|
LogCaretXY, LogCaretXY,
|
||||||
|
Temp2, smNormal);
|
||||||
|
if Command = ecLineBreak then
|
||||||
|
CaretY := CaretY + 1;
|
||||||
|
end;
|
||||||
|
end else begin
|
||||||
|
// linebreak after end of line
|
||||||
|
fUndoList.AddChange(crLineBreak,
|
||||||
|
LogCaretXY, LogCaretXY,
|
||||||
|
'', smNormal);
|
||||||
|
SpaceCount2 := 0;
|
||||||
|
if Assigned(Beautifier) then begin
|
||||||
|
Temp:='';
|
||||||
|
SpaceCount2:=Beautifier.GetIndentForLineBreak(Self,LogCaretXY,Temp);
|
||||||
|
end else if eoAutoIndent in Options then begin
|
||||||
|
BackCounter := CaretY;
|
||||||
|
repeat
|
||||||
|
Dec(BackCounter);
|
||||||
|
Temp := Lines[BackCounter];
|
||||||
|
SpaceCount2 := LeftSpaces(Temp);
|
||||||
|
until (BackCounter = 0) or (Temp <> '');
|
||||||
|
end;
|
||||||
|
Lines.Insert(CaretY, '');
|
||||||
|
if Command = ecLineBreak then begin
|
||||||
|
if SpaceCount2 > 0 then
|
||||||
|
Lines[CaretY] := StringOfChar(' ', SpaceCount2);
|
||||||
|
CaretXY := Point(SpaceCount2 + 1, CaretY + 1);
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
{$ELSE}
|
||||||
Len := Length(Temp);
|
Len := Length(Temp);
|
||||||
if Len > 0 then begin
|
if Len > 0 then begin
|
||||||
if Len >= LogCaretXY.X then begin
|
if Len >= LogCaretXY.X then begin
|
||||||
if LogCaretXY.X > 1 then begin
|
if LogCaretXY.X > 1 then begin
|
||||||
|
// break line in two
|
||||||
SpaceCount1 := LeftSpaces(Temp);
|
SpaceCount1 := LeftSpaces(Temp);
|
||||||
{begin} //JGF 2000-09-23
|
|
||||||
Temp := Copy(LineText, 1, LogCaretXY.X - 1);
|
Temp := Copy(LineText, 1, LogCaretXY.X - 1);
|
||||||
TrimmedSetLine(CaretY - 1, Temp);
|
TrimmedSetLine(CaretY - 1, Temp);
|
||||||
Delete(Temp2, 1, LogCaretXY.X - 1);
|
Delete(Temp2, 1, LogCaretXY.X - 1);
|
||||||
fUndoList.AddChange(crLineBreak,
|
fUndoList.AddChange(crLineBreak,
|
||||||
{$IFDEF SYN_LAZARUS}
|
|
||||||
LogCaretXY, LogCaretXY,
|
|
||||||
{$ELSE}
|
|
||||||
CaretXY, CaretXY,
|
CaretXY, CaretXY,
|
||||||
{$ENDIF}
|
|
||||||
Temp2, smNormal);
|
Temp2, smNormal);
|
||||||
Lines.Insert(CaretY, StringOfChar(' ', SpaceCount1) + Temp2);
|
Lines.Insert(CaretY, StringOfChar(' ', SpaceCount1) + Temp2);
|
||||||
if Command = ecLineBreak then
|
if Command = ecLineBreak then
|
||||||
CaretXY := Point(SpaceCount1 + 1, CaretY + 1);
|
CaretXY := Point(SpaceCount1 + 1, CaretY + 1);
|
||||||
{end} //JGF 2000-09-23
|
|
||||||
end else begin
|
end else begin
|
||||||
|
// move the whole line
|
||||||
Lines.Insert(CaretY - 1, '');
|
Lines.Insert(CaretY - 1, '');
|
||||||
fUndoList.AddChange(crLineBreak,
|
fUndoList.AddChange(crLineBreak,
|
||||||
{$IFDEF SYN_LAZARUS}
|
|
||||||
LogCaretXY, LogCaretXY,
|
|
||||||
{$ELSE}
|
|
||||||
CaretXY, CaretXY,
|
CaretXY, CaretXY,
|
||||||
{$ENDIF}
|
|
||||||
Temp2, smNormal);
|
Temp2, smNormal);
|
||||||
if Command = ecLineBreak then
|
if Command = ecLineBreak then
|
||||||
CaretY := CaretY + 1;
|
CaretY := CaretY + 1;
|
||||||
end;
|
end;
|
||||||
end else begin
|
end else begin
|
||||||
{begin} //mh 2000-10-06
|
// linebreak after end of line
|
||||||
(*
|
|
||||||
BackCounter := CaretY - 1;
|
|
||||||
while BackCounter >= 0 do begin
|
|
||||||
SpaceCount2 := LeftSpaces(Lines[BackCounter]);
|
|
||||||
if Length(Lines[BackCounter]) > 0 then break;
|
|
||||||
dec(BackCounter);
|
|
||||||
end;
|
|
||||||
fUndoList.AddChange(crLineBreak, CaretXY, CaretXY, '', smNormal);
|
|
||||||
if Command = ecLineBreak then
|
|
||||||
CaretX := SpaceCount2 + 1;
|
|
||||||
if (Command = ecInsertLine) or (eoScrollPastEol in fOptions) then
|
|
||||||
Lines.Insert(CaretY, '');
|
|
||||||
if Command = ecLineBreak then begin
|
|
||||||
Inc(fCaretY);
|
|
||||||
StatusChanged([scCaretY]);
|
|
||||||
end;
|
|
||||||
if (Command = ecLineBreak) and
|
|
||||||
(fOptions * [eoAutoIndent, eoScrollPastEol] = [eoAutoIndent])
|
|
||||||
then begin
|
|
||||||
Lines.Insert(CaretY - 1, StringOfChar(' ', SpaceCount2));
|
|
||||||
CaretX := SpaceCount2 + 1;
|
|
||||||
end;
|
|
||||||
*)
|
|
||||||
fUndoList.AddChange(crLineBreak,
|
fUndoList.AddChange(crLineBreak,
|
||||||
{$IFDEF SYN_LAZARUS}
|
|
||||||
LogCaretXY, LogCaretXY,
|
|
||||||
{$ELSE}
|
|
||||||
CaretXY, CaretXY,
|
CaretXY, CaretXY,
|
||||||
{$ENDIF}
|
|
||||||
'', smNormal);
|
'', smNormal);
|
||||||
SpaceCount2 := 0;
|
SpaceCount2 := 0;
|
||||||
if eoAutoIndent in Options then begin
|
if eoAutoIndent in Options then begin
|
||||||
@ -8354,9 +8390,9 @@ begin
|
|||||||
Lines[CaretY] := StringOfChar(' ', SpaceCount2);
|
Lines[CaretY] := StringOfChar(' ', SpaceCount2);
|
||||||
CaretXY := Point(SpaceCount2 + 1, CaretY + 1);
|
CaretXY := Point(SpaceCount2 + 1, CaretY + 1);
|
||||||
end;
|
end;
|
||||||
{end} //mh 2000-10-06
|
|
||||||
end;
|
end;
|
||||||
end else begin
|
end else begin
|
||||||
|
// current line is empty
|
||||||
if fLines.Count = 0 then
|
if fLines.Count = 0 then
|
||||||
fLines.Add('');
|
fLines.Add('');
|
||||||
BackCounter := CaretY - 1;
|
BackCounter := CaretY - 1;
|
||||||
@ -8366,11 +8402,7 @@ begin
|
|||||||
dec(BackCounter);
|
dec(BackCounter);
|
||||||
end;
|
end;
|
||||||
fUndoList.AddChange(crLineBreak,
|
fUndoList.AddChange(crLineBreak,
|
||||||
{$IFDEF SYN_LAZARUS}
|
|
||||||
LogCaretXY, LogCaretXY,
|
|
||||||
{$ELSE}
|
|
||||||
CaretXY, CaretXY,
|
CaretXY, CaretXY,
|
||||||
{$ENDIF}
|
|
||||||
'', smNormal);
|
'', smNormal);
|
||||||
if Command = ecLineBreak then
|
if Command = ecLineBreak then
|
||||||
CaretX := SpaceCount2 + 1;
|
CaretX := SpaceCount2 + 1;
|
||||||
@ -8378,6 +8410,7 @@ begin
|
|||||||
if Command = ecLineBreak then
|
if Command = ecLineBreak then
|
||||||
CaretY := CaretY + 1;
|
CaretY := CaretY + 1;
|
||||||
end;
|
end;
|
||||||
|
{$ENDIF}
|
||||||
DoLinesInserted(CaretY - InsDelta, 1);
|
DoLinesInserted(CaretY - InsDelta, 1);
|
||||||
EnsureCursorPosVisible; //JGF 2000-09-23
|
EnsureCursorPosVisible; //JGF 2000-09-23
|
||||||
fLastCaretX := fCaretX; //mh 2000-10-19
|
fLastCaretX := fCaretX; //mh 2000-10-19
|
||||||
@ -11429,6 +11462,52 @@ begin
|
|||||||
end;
|
end;
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
|
|
||||||
|
{ TSynCustomBeautifier }
|
||||||
|
|
||||||
|
function TSynCustomBeautifier.LeftSpaces(Editor: TCustomSynEdit;
|
||||||
|
const Line: string; Physical: boolean): Integer;
|
||||||
|
var
|
||||||
|
p: PChar;
|
||||||
|
begin
|
||||||
|
p := pointer(Line);
|
||||||
|
if Assigned(p) then begin
|
||||||
|
Result := 0;
|
||||||
|
while p^ in [#1..#32] do begin
|
||||||
|
Inc(p);
|
||||||
|
Inc(Result);
|
||||||
|
end;
|
||||||
|
if Physical and (Result>0) then
|
||||||
|
Result:=Editor.LogicalToPhysicalCol(Line,Result+1)-1;
|
||||||
|
end else
|
||||||
|
Result := 0;
|
||||||
|
end;
|
||||||
|
|
||||||
|
function TSynCustomBeautifier.GetIndentForLineBreak(Editor: TCustomSynEdit;
|
||||||
|
InsertPos: TPoint; var NextText: string): integer;
|
||||||
|
var
|
||||||
|
LastTextY: LongInt;
|
||||||
|
Line: string;
|
||||||
|
Lines: TStrings;
|
||||||
|
begin
|
||||||
|
Result:=0;
|
||||||
|
DebugLn(['TSynCustomBeautifier.GetIndentForLineBreak ',dbgs(InsertPos)]);
|
||||||
|
if InsertPos.Y<1 then exit;
|
||||||
|
LastTextY:=InsertPos.Y;
|
||||||
|
Lines:=Editor.Lines;
|
||||||
|
if LastTextY>Lines.Count then
|
||||||
|
LastTextY:=Lines.Count;
|
||||||
|
while (LastTextY>0) do begin
|
||||||
|
Line:=Lines[LastTextY-1];
|
||||||
|
if LastTextY=InsertPos.Y then
|
||||||
|
Line:=copy(Line,1,InsertPos.X-1);
|
||||||
|
if Line<>'' then begin
|
||||||
|
Result:=LeftSpaces(Editor,Line,false);
|
||||||
|
exit;
|
||||||
|
end;
|
||||||
|
dec(LastTextY);
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
initialization
|
initialization
|
||||||
{$IFNDEF SYN_LAZARUS}
|
{$IFNDEF SYN_LAZARUS}
|
||||||
SynEditClipboardFormat := RegisterClipboardFormat(SYNEDIT_CLIPBOARD_FORMAT);
|
SynEditClipboardFormat := RegisterClipboardFormat(SYNEDIT_CLIPBOARD_FORMAT);
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user