📄 synhighlighterpython.pas
字号:
{-------------------------------------------------------------------------------
The contents of this file are subject to the Mozilla Public License
Version 1.1 (the "License"); you may not use this file except in compliance
with the License. You may obtain a copy of the License at
http://www.mozilla.org/MPL/
Software distributed under the License is distributed on an "AS IS" basis,
WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License for
the specific language governing rights and limitations under the License.
The Original Code is: SynHighlighterPython.pas, released 2000-06-23.
The Original Code is based on the odPySyn.pas file from the
mwEdit component suite by Martin Waldenburg and other developers, the Initial
Author of this file is Olivier Deckmyn.
Portions created by M.Utku Karatas and Dennis Chuah.
All Rights Reserved.
Contributors to the SynEdit and mwEdit projects are listed in the
Contributors.txt file.
Alternatively, the contents of this file may be used under the terms of the
GNU General Public License Version 2 or later (the "GPL"), in which case
the provisions of the GPL are applicable instead of those above.
If you wish to allow use of your version of this file only under the terms
of the GPL and not to allow others to use your version of this file
under the MPL, indicate your decision by deleting the provisions above and
replace them with the notice and other provisions required by the GPL.
If you do not delete the provisions above, a recipient may use your version
of this file under either the MPL or the GPL.
$Id: SynHighlighterPython.pas,v 1.19 2005/01/28 16:53:24 maelh Exp $
You may retrieve the latest version of this file at the SynEdit home page,
located at http://SynEdit.SourceForge.net
Known Issues:
-------------------------------------------------------------------------------}
{
@abstract(A Python language highlighter for SynEdit)
@author(Olivier Deckmyn, converted to SynEdit by David Muir <dhmn@dmsoftware.co.uk>)
@created(unknown, converted to SynEdit on 2000-06-23)
@lastmod(2003-02-13)
The SynHighlighterPython implements a highlighter for Python for the SynEdit projects.
}
{$IFNDEF QSYNHIGHLIGHTERPYTHON}
unit SynHighlighterPython;
{$ENDIF}
{$I SynEdit.inc}
interface
uses
{$IFDEF SYN_COMPILER_6_UP}
IniFiles, //THashedStringList
{$ENDIF}
{$IFDEF SYN_CLX}
QGraphics,
QSynEditHighlighter,
QSynEditTypes,
{$ELSE}
Graphics,
SynEditHighlighter,
SynEditTypes,
{$ENDIF}
SysUtils,
Classes;
const
ALPHA_CHARS = ['_', 'a'..'z', 'A'..'Z'];
IDENTIFIER_CHARS = ['0'..'9'] + ALPHA_CHARS;
type
TtkTokenKind = (tkComment, tkIdentifier, tkKey, tkNull, tkNumber, tkSpace,
tkString, tkSymbol, tkNonKeyword, tkTrippleQuotedString,
tkSystemDefined, tkHex, tkOct, tkFloat, tkUnknown);
TRangeState = (rsANil, rsComment, rsUnKnown, rsMultilineString, rsMultilineString2,
rsMultilineString3 //this is to indicate if a string is made multiline by backslash char at line end (as in C++ highlighter)
);
TProcTableProc = procedure of object;
type
TSynPythonSyn = class(TSynCustomHighLighter)
private
fStringStarter: char; // used only for rsMultilineString3 stuff
fRange: TRangeState;
fLine: PChar;
fLineNumber: Integer;
fProcTable: array[#0..#255] of TProcTableProc;
fToIdent: PChar;
fTokenPos: Integer;
FTokenID: TtkTokenKind;
FKeywords: TStringList;
fStringAttri: TSynHighlighterAttributes;
fDocStringAttri: TSynHighlighterAttributes;
fNumberAttri: TSynHighlighterAttributes;
fHexAttri: TSynHighlighterAttributes;
fOctalAttri: TSynHighlighterAttributes;
fFloatAttri: TSynHighlighterAttributes;
fKeyAttri: TSynHighlighterAttributes;
fNonKeyAttri: TSynHighlighterAttributes;
fSystemAttri: TSynHighlighterAttributes;
fSymbolAttri: TSynHighlighterAttributes;
fCommentAttri: TSynHighlighterAttributes;
fIdentifierAttri: TSynHighlighterAttributes;
fSpaceAttri: TSynHighlighterAttributes;
fErrorAttri: TSynHighlighterAttributes;
procedure SymbolProc;
procedure CRProc;
procedure CommentProc;
procedure GreaterProc;
procedure IdentProc;
procedure LFProc;
procedure LowerProc;
procedure NullProc;
procedure NumberProc;
procedure SpaceProc;
procedure PreStringProc;
procedure UnicodeStringProc;
procedure StringProc;
procedure String2Proc;
procedure StringEndProc(EndChar:char);
procedure UnknownProc;
procedure MakeMethodTables;
protected
Run: LongInt;
fStringLen: Integer;
function GetIdentChars: TSynIdentChars; override;
function GetSampleSource: string; override;
function IsFilterStored: Boolean; override;
function IdentKind(MayBe: PChar): TtkTokenKind; virtual;
function GetKeywordIdentifiers: TStringList; virtual;
property Keywords: TStringlist read FKeywords;
property TokenID: TtkTokenKind read FTokenID;
public
class function GetLanguageName: string; override;
public
constructor Create(AOwner: TComponent); override;
destructor Destroy; override;
function GetDefaultAttribute(Index: integer): TSynHighlighterAttributes;
override;
function GetEol: Boolean; override;
function GetRange: Pointer; override;
function GetTokenID: TtkTokenKind;
procedure SetLine(NewValue: string; LineNumber: Integer); override;
function GetToken: string; override;
function GetTokenAttribute: TSynHighlighterAttributes; override;
function GetTokenKind: integer; override;
function GetTokenPos: Integer; override;
procedure Next; override;
property IdentChars;
procedure SetRange(Value: Pointer); override;
procedure ResetRange; override;
published
property CommentAttri: TSynHighlighterAttributes read fCommentAttri
write fCommentAttri;
property IdentifierAttri: TSynHighlighterAttributes read fIdentifierAttri
write fIdentifierAttri;
property KeyAttri: TSynHighlighterAttributes read fKeyAttri write fKeyAttri;
property NonKeyAttri: TSynHighlighterAttributes read fNonKeyAttri
write fNonKeyAttri;
property SystemAttri: TSynHighlighterAttributes read fSystemAttri
write fSystemAttri;
property NumberAttri: TSynHighlighterAttributes read fNumberAttri
write fNumberAttri;
property HexAttri: TSynHighlighterAttributes read fHexAttri
write fHexAttri;
property OctalAttri: TSynHighlighterAttributes read fOctalAttri
write fOctalAttri;
property FloatAttri: TSynHighlighterAttributes read fFloatAttri
write fFloatAttri;
property SpaceAttri: TSynHighlighterAttributes read fSpaceAttri
write fSpaceAttri;
property StringAttri: TSynHighlighterAttributes read fStringAttri
write fStringAttri;
property DocStringAttri: TSynHighlighterAttributes read fDocStringAttri
write fDocStringAttri;
property SymbolAttri: TSynHighlighterAttributes read fSymbolAttri
write fSymbolAttri;
property ErrorAttri: TSynHighlighterAttributes read fErrorAttri
write fErrorAttri;
end;
implementation
uses
{$IFDEF SYN_CLX}
QSynEditStrConst;
{$ELSE}
SynEditStrConst;
{$ENDIF}
var
GlobalKeywords: TStringList;
function TSynPythonSyn.GetKeywordIdentifiers: TStringList;
const
// No need to localise keywords!
// List of keywords
KEYWORDCOUNT = 29;
KEYWORDS: array [1..KEYWORDCOUNT] of string =
(
'and',
'assert',
'break',
'class',
'continue',
'def',
'del',
'elif',
'else',
'except',
'exec',
'finally',
'for',
'from',
'global',
'if',
'import',
'in',
'is',
'lambda',
'not',
'or',
'pass',
'print',
'raise',
'return',
'try',
'while',
'yield'
);
// List of non-keyword identifiers
NONKEYWORDCOUNT = 66;
NONKEYWORDS: array [1..NONKEYWORDCOUNT] of string =
(
'__future__',
'__import__',
'abs',
'apply',
'as',
'buffer',
'callable',
'chr',
'cmp',
'coerce',
'compile',
'complex',
'delattr',
'dict',
'dir',
'divmod',
'eval',
'execfile',
'False',
'file',
'filter',
'float',
'getattr',
'globals',
'hasattr',
'hash',
'help',
'hex',
'id',
'input',
'int',
'intern',
'isinstance',
'issubclass',
'iter',
'len',
'list',
'locals',
'long',
'None',
'NotImplemented',
'map',
'max',
'min',
'oct',
'open',
'ord',
'pow',
'range',
'raw_input',
'reduce',
'reload',
'repr',
'round',
'self',
'setattr',
'slice',
'str',
'True',
'tuple',
'type',
'unichr',
'unicode',
'vars',
'xrange',
'zip'
);
var
f: Integer;
begin
if not Assigned (GlobalKeywords) then begin
// Create the string list of keywords - only once
GlobalKeywords := TStringList.Create;
for f := 1 to KEYWORDCOUNT do
GlobalKeywords.AddObject (KEYWORDS[f], Pointer (Ord(tkKey)));
for f := 1 to NONKEYWORDCOUNT do
GlobalKeywords.AddObject (NONKEYWORDS[f], Pointer (Ord(tkNonKeyword)));
end; // if
Result := GlobalKeywords;
end;
function TSynPythonSyn.IdentKind(MayBe: PChar): TtkTokenKind;
var
index: Integer;
temp: PChar;
s: string;
begin
// Extract the identifier out - it is assumed to terminate in a
// non-alphanumeric character
fToIdent := MayBe;
temp := MayBe;
while temp^ in IDENTIFIER_CHARS do
Inc (temp);
fStringLen := temp - fToIdent;
// Check to see if it is a keyword
SetString (s, fToIdent, fStringLen);
{$IFDEF SYN_COMPILER_6_UP}
index := FKeywords.IndexOf (s);
{$ELSE}
if FKeywords.Find (s, index) then begin
// TStringList is not case sensitive!
if s <> FKeywords[index] then
index := -1;
end else begin
index := -1;
end; // if
{$ENDIF}
if index <> -1 then
Result := TtkTokenKind (FKeywords.Objects[index])
// Check if it is a system identifier (__*__)
else if (fStringLen >= 5) and
(MayBe[0] = '_') and (MayBe[1] = '_') and (MayBe[2] <> '_') and
(MayBe[fStringLen-1] = '_') and (MayBe[fStringLen-2] = '_') and
(MayBe[fStringLen-3] <> '_') then
Result := tkSystemDefined
// Else, hey, it is an ordinary run-of-the-mill identifier!
else
Result := tkIdentifier;
end;
procedure TSynPythonSyn.MakeMethodTables;
var
I: Char;
begin
for I := #0 to #255 do
case I of
'&', '}', '{', ':', ',', ']', '[', '*', '`',
'^', ')', '(', ';', '/', '=', '-', '+', '!', '\',
'%', '|', '~' :
fProcTable[I] := SymbolProc;
#13: fProcTable[I] := CRProc;
'#': fProcTable[I] := CommentProc;
'>': fProcTable[I] := GreaterProc;
'A'..'Q', 'S', 'T', 'V'..'Z', 'a'..'q', 's', 't', 'v'..'z', '_': fProcTable[I] := IdentProc;
#10: fProcTable[I] := LFProc;
'<': fProcTable[I] := LowerProc;
#0: fProcTable[I] := NullProc;
'.', '0'..'9': fProcTable[I] := NumberProc;
#1..#9, #11, #12, #14..#32:
fProcTable[I] := SpaceProc;
'r', 'R': fProcTable[I] := PreStringProc;
'u', 'U': fProcTable[I] := UnicodeStringProc;
'''': fProcTable[I] := StringProc;
'"': fProcTable[I] := String2Proc;
else
fProcTable[I] := UnknownProc;
end;
end;
constructor TSynPythonSyn.Create(AOwner: TComponent);
begin
inherited Create(AOwner);
{$IFDEF SYN_COMPILER_6_UP}
FKeywords := THashedStringList.Create;
FKeywords.CaseSensitive := True;
{$ELSE}
// Older compilers do not ave hashed string list - so use less efficient
// TStringList instead - but keep it sorted
FKeywords := TStringList.Create;
FKeywords.Sorted := True;
{$ENDIF}
FKeywords.Duplicates := dupError;
FKeywords.Assign (GetKeywordIdentifiers);
fRange := rsUnknown;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -