support for DDOC ranges

This commit is contained in:
Basile Burg 2014-07-07 04:17:41 +02:00
parent 1ce5f8f65f
commit 7e42d6afbd
1 changed files with 113 additions and 106 deletions

View File

@ -81,9 +81,9 @@ type
{$ENDIF} {$ENDIF}
{$ENDIF} {$ENDIF}
TTokenKind = (tkCommt, tkIdent, tkKeywd, tkStrng, tkBlank, tkSymbl, tkNumbr, tkCurrI); TTokenKind = (tkCommt, tkIdent, tkKeywd, tkStrng, tkBlank, tkSymbl, tkNumbr, tkCurrI, tkDDocs);
TRangeKind = (rkNone, rkString1, rkString2, rkBlockCom1, rkBlockCom2, rkAsm); TRangeKind = (rkNone, rkString1, rkString2, rkBlockCom1, rkBlockCom2, rkBlockDoc1, rkBlockDoc2, rkAsm);
TFoldKind = (fkBrackets, fkComments1, fkComments2); TFoldKind = (fkBrackets, fkComments1, fkComments2);
TFoldKinds = set of TFoldKind; TFoldKinds = set of TFoldKind;
@ -98,6 +98,7 @@ type
fStrngAttrib: TSynHighlighterAttributes; fStrngAttrib: TSynHighlighterAttributes;
fKeywdAttrib: TSynHighlighterAttributes; fKeywdAttrib: TSynHighlighterAttributes;
fCurrIAttrib: TSynHighlighterAttributes; fCurrIAttrib: TSynHighlighterAttributes;
fDDocsAttrib: TSynHighlighterAttributes;
fKeyWords: TD2Dictionary; fKeyWords: TD2Dictionary;
fCurrIdent: string; fCurrIdent: string;
fLineBuf: string; fLineBuf: string;
@ -119,6 +120,7 @@ type
procedure setStrngAttrib(aValue: TSynHighlighterAttributes); procedure setStrngAttrib(aValue: TSynHighlighterAttributes);
procedure setKeywdAttrib(aValue: TSynHighlighterAttributes); procedure setKeywdAttrib(aValue: TSynHighlighterAttributes);
procedure setCurrIAttrib(aValue: TSynHighlighterAttributes); procedure setCurrIAttrib(aValue: TSynHighlighterAttributes);
procedure setDDocsAttrib(aValue: TSynHighlighterAttributes);
procedure doAttribChange(sender: TObject); procedure doAttribChange(sender: TObject);
procedure setCurrIdent(const aValue: string); procedure setCurrIdent(const aValue: string);
procedure doChanged; procedure doChanged;
@ -133,6 +135,7 @@ type
property StrngAttrib: TSynHighlighterAttributes read fStrngAttrib write setStrngAttrib; property StrngAttrib: TSynHighlighterAttributes read fStrngAttrib write setStrngAttrib;
property KeywdAttrib: TSynHighlighterAttributes read fKeywdAttrib write setKeywdAttrib; property KeywdAttrib: TSynHighlighterAttributes read fKeywdAttrib write setKeywdAttrib;
property CurrIAttrib: TSynHighlighterAttributes read fCurrIAttrib write setCurrIAttrib; property CurrIAttrib: TSynHighlighterAttributes read fCurrIAttrib write setCurrIAttrib;
property DDocsAttrib: TSynHighlighterAttributes read fDDocsAttrib write setDDocsAttrib;
public public
constructor create(aOwner: TComponent); override; constructor create(aOwner: TComponent); override;
destructor destroy; override; destructor destroy; override;
@ -286,6 +289,7 @@ begin
fStrngAttrib := TSynHighlighterAttributes.Create('String','String'); fStrngAttrib := TSynHighlighterAttributes.Create('String','String');
fKeywdAttrib := TSynHighlighterAttributes.Create('Keyword','Keyword'); fKeywdAttrib := TSynHighlighterAttributes.Create('Keyword','Keyword');
fCurrIAttrib := TSynHighlighterAttributes.Create('CurrentIdentifier','CurrentIdentifier'); fCurrIAttrib := TSynHighlighterAttributes.Create('CurrentIdentifier','CurrentIdentifier');
fDDocsAttrib := TSynHighlighterAttributes.Create('DDoc','DDoc');
fNumbrAttrib.Foreground := $000079F2; fNumbrAttrib.Foreground := $000079F2;
fSymblAttrib.Foreground := clMaroon; fSymblAttrib.Foreground := clMaroon;
@ -299,6 +303,8 @@ begin
fCurrIAttrib.FrameColor := clGray; fCurrIAttrib.FrameColor := clGray;
fCurrIAttrib.Background := cl3dlight; fCurrIAttrib.Background := cl3dlight;
fDDocsAttrib.Foreground := clTeal;
fCommtAttrib.Style := [fsItalic]; fCommtAttrib.Style := [fsItalic];
fKeywdAttrib.Style := [fsBold]; fKeywdAttrib.Style := [fsBold];
@ -310,6 +316,7 @@ begin
AddAttribute(fStrngAttrib); AddAttribute(fStrngAttrib);
AddAttribute(fKeywdAttrib); AddAttribute(fKeywdAttrib);
AddAttribute(fCurrIAttrib); AddAttribute(fCurrIAttrib);
AddAttribute(fDDocsAttrib);
fAttribLut[TTokenKind.tkident] := fIdentAttrib; fAttribLut[TTokenKind.tkident] := fIdentAttrib;
fAttribLut[TTokenKind.tkBlank] := fWhiteAttrib; fAttribLut[TTokenKind.tkBlank] := fWhiteAttrib;
@ -319,6 +326,7 @@ begin
fAttribLut[TTokenKind.tkStrng] := fStrngAttrib; fAttribLut[TTokenKind.tkStrng] := fStrngAttrib;
fAttribLut[TTokenKind.tksymbl] := fSymblAttrib; fAttribLut[TTokenKind.tksymbl] := fSymblAttrib;
fAttribLut[TTokenKind.tkCurrI] := fCurrIAttrib; fAttribLut[TTokenKind.tkCurrI] := fCurrIAttrib;
fAttribLut[TTokenKind.tkDDocs] := fDDocsAttrib;
SetAttributesOnChange(@doAttribChange); SetAttributesOnChange(@doAttribChange);
fTokStop := 1; fTokStop := 1;
@ -392,6 +400,11 @@ begin
fCurrIAttrib.Assign(aValue); fCurrIAttrib.Assign(aValue);
end; end;
procedure TSynD2Syn.setDDocsAttrib(aValue: TSynHighlighterAttributes);
begin
fDDocsAttrib.Assign(aValue);
end;
procedure TSynD2Syn.setCurrIdent(const aValue: string); procedure TSynD2Syn.setCurrIdent(const aValue: string);
begin begin
if aValue = '' then exit; if aValue = '' then exit;
@ -427,17 +440,15 @@ begin
result := fLineBuf[fTokStop-1]; result := fLineBuf[fTokStop-1];
end; end;
{
TODO: //TODO-crange: asm range.
- alternative attributes for ddoc comments. //TODO-cnumber literals: stricter.
- range: asm range. //TODO-cnumber literals: binary.
- number literals: stricter. //TODO-cstring literals: delimited strings.
- number literals: binary. //TODO-cstring literals: token strings.
- string literals: delimited strings. //TODO-cstring literals: escape bug: std.path/std.regex: "\\"
- string literals: token strings. //TODO-ccomments: correct nested comments handling.
- string literals: escape bug: std.path/std.regex: "\\"
- comments: correct nested comments handling.
}
{$BOOLEVAL ON} {$BOOLEVAL ON}
procedure TSynD2Syn.next; procedure TSynD2Syn.next;
label label
@ -463,8 +474,12 @@ begin
begin begin
if (readNext = '/') then if (readNext = '/') then
begin begin
while readNext <> #10 do (*!*);
fTokKind := tkCommt; fTokKind := tkCommt;
if readNext <> #10 then if readCurr = '/' then
begin
fTokKind := tkDDocs;
end;
while readCurr <> #10 do readNext(*!*);
exit; exit;
end end
else else
@ -472,7 +487,28 @@ begin
end; end;
// block comments 1 // block comments 1
if fRange = rkBlockCom1 then if fRange = rkNone then if (readCurr = '/') then if (readNext = '*') then
begin
if (readNext = '*') then fTokKind := tkDDocs
else fTokKind := tkCommt;
while(true) do
begin
if readCurr = #10 then break;
if readNext = #10 then break;
if (readPrev = '*') and (readCurr = '/') then break;
end;
if (readCurr = #10) then
begin
if fTokKind = tkDDocs then fRange := rkBlockDoc1
else fRange := rkBlockCom1;
if fkComments1 in fFoldKinds then
StartCodeFoldBlock(nil);
end
else readNext;
exit;
end
else Dec(fTokStop);
if (fRange = rkBlockCom1) or (fRange = rkBlockDoc1) then
begin begin
while(true) do while(true) do
begin begin
@ -482,13 +518,14 @@ begin
end; end;
if (readCurr = #10) then if (readCurr = #10) then
begin begin
fRange := rkBlockCom1; if fRange = rkBlockDoc1 then fTokKind := tkDDocs
fTokKind := tkCommt; else fTokKind := tkCommt;
exit; exit;
end; end;
if (readCurr = '/') then if (readCurr = '/') then
begin begin
fTokKind := tkCommt; if fRange = rkBlockDoc1 then fTokKind := tkDDocs
else fTokKind := tkCommt;
fRange := rkNone; fRange := rkNone;
readNext; readNext;
if fkComments1 in fFoldKinds then if fkComments1 in fFoldKinds then
@ -496,31 +533,30 @@ begin
exit; exit;
end; end;
end; end;
if fRange <> rkBlockCom2 then if (readCurr <> #10) and (readCurr = '/') then if (readNext = '*') then
begin // block comments 2
if fRange = rkNone then if fRange = rkNone then if (readCurr = '/') then if (readNext = '+') then
begin begin
if (readNext = '+') then fTokKind := tkDDocs
else fTokKind := tkCommt;
while(true) do while(true) do
begin begin
if readCurr = #10 then break; if readCurr = #10 then break;
if readNext = #10 then break; if readNext = #10 then break;
if (readPrev = '*') and (readCurr = '/') then break; if (readPrev = '+') and (readCurr = '/') then break;
end; end;
if (readCurr = #10) then if (readCurr = #10) then
begin begin
fRange := rkBlockCom1; if fTokKind = tkDDocs then fRange := rkBlockDoc2
if fkComments1 in fFoldKinds then else fRange := rkBlockCom2;
StartCodeFoldBlock(nil); if fkComments2 in fFoldKinds then
end StartCodeFoldBlock(nil);
end
else readNext; else readNext;
fTokKind := tkCommt;
exit; exit;
end; end
end else Dec(fTokStop);
else Dec(fTokStop); if (fRange = rkBlockCom2) or (fRange = rkBlockDoc2) then
// block comments 2
if fRange = rkBlockCom2 then
begin begin
while(true) do while(true) do
begin begin
@ -530,13 +566,14 @@ begin
end; end;
if (readCurr = #10) then if (readCurr = #10) then
begin begin
fRange := rkBlockCom2; if fRange = rkBlockDoc2 then fTokKind := tkDDocs
fTokKind := tkCommt; else fTokKind := tkCommt;
exit; exit;
end; end;
if (readCurr = '/') then if (readCurr = '/') then
begin begin
fTokKind := tkCommt; if fRange = rkBlockDoc2 then fTokKind := tkDDocs
else fTokKind := tkCommt;
fRange := rkNone; fRange := rkNone;
readNext; readNext;
if fkComments2 in fFoldKinds then if fkComments2 in fFoldKinds then
@ -544,36 +581,37 @@ begin
exit; exit;
end; end;
end; end;
if fRange <> rkBlockCom1 then if (readCurr <> #10) and (readCurr = '/') then if (readNext = '+') then
begin
if fRange = rkNone then
begin
while(true) do
begin
if readCurr = #10 then break;
if readNext = #10 then break;
if (readPrev = '+') and (readCurr = '/') then break;
end;
if (readCurr = #10) then
begin
fRange := rkBlockCom2;
if fkComments2 in fFoldKinds then
StartCodeFoldBlock(nil);
end
else readNext;
fTokKind := tkCommt;
exit;
end;
end
else Dec(fTokStop);
// string 1 // string 1
if fRange = rkNone then if (readCurr in ['r','x','"']) then
begin
// check WYSIWYG/hex prefix
if readCurr in ['r','x'] then
begin
if not (readNext = '"') then
begin
Dec(fTokStop);
goto _postString1;
end;
end;
// go to end of string/eol
while (((readNext <> '"') or (readPrev = '\')) and (not (readCurr = #10))) do (*!*);
if (readCurr = #10) then fRange := rkString1
else
begin
readNext;
// check postfix
if isStringPostfix(readCurr) then
readNext;
end;
fTokKind := tkStrng;
exit;
end;
if fRange = rkString1 then if fRange = rkString1 then
begin begin
if (readCurr <> '"') then while (((readNext <> '"') or (readPrev = '\')) and (not (readCurr = #10))) do (*!*); if (readCurr <> '"') then while (((readNext <> '"') or (readPrev = '\')) and (not (readCurr = #10))) do (*!*);
if (readCurr = #10) then if (readCurr = #10) then
begin begin
fRange := rkString1;
fTokKind := tkStrng; fTokKind := tkStrng;
exit; exit;
end; end;
@ -588,42 +626,29 @@ begin
exit; exit;
end; end;
end; end;
if fRange <> rkString2 then if (readCurr in ['r','x','"']) then
begin
if fRange = rkNone then
begin
// check WYSIWYG/hex prefix
if readCurr in ['r','x'] then
begin
if not (readNext = '"') then
begin
Dec(fTokStop);
goto _postString1;
end;
end;
// go to end of string/eol
while (((readNext <> '"') or (readPrev = '\')) and (not (readCurr = #10))) do (*!*);
if (readCurr = #10) then fRange := rkString1
else
begin
readNext;
// check postfix
if isStringPostfix(readCurr) then
readNext;
end;
fTokKind := tkStrng;
exit;
end;
end;
_postString1: _postString1:
// string 2 // string 2
if fRange = rkNone then if (readCurr = '`') then
begin
// go to end of string/eol
while ((readNext <> '`') and (not (readCurr = #10))) do (*!*);
if (readCurr = #10) then fRange := rkString2
else
begin
readNext;
// check postfix
if isStringPostfix(readCurr) then
readNext;
end;
fTokKind := tkStrng;
exit;
end;
if fRange = rkString2 then if fRange = rkString2 then
begin begin
if (readCurr <> '`') then while ((readNext <> '`') and (not (readCurr = #10))) do (*!*); if (readCurr <> '`') then while ((readNext <> '`') and (not (readCurr = #10))) do (*!*);
if (readCurr = #10) then if (readCurr = #10) then
begin begin
fRange := rkString2;
fTokKind := tkStrng; fTokKind := tkStrng;
exit; exit;
end; end;
@ -638,24 +663,6 @@ begin
exit; exit;
end; end;
end; end;
if fRange <> rkString1 then if (readCurr = '`') then
begin
if fRange = rkNone then
begin
// go to end of string/eol
while ((readNext <> '`') and (not (readCurr = #10))) do (*!*);
if (readCurr = #10) then fRange := rkString2
else
begin
readNext;
// check postfix
if isStringPostfix(readCurr) then
readNext;
end;
fTokKind := tkStrng;
exit;
end;
end;
// char literals // char literals
if fRange = rkNone then if (readCurr = #39) then if fRange = rkNone then if (readCurr = #39) then