📄 uparameterstostate.pas
字号:
//create editor of the texts
EditTexts := TDocumentationTextOptionWrapper.Create;
try
EditTexts.LoadIniOptions(Ini); //load from project file
finally
EditTexts.Free; //free the editor
end;
finally
Ini.Free; //close the project file
end;
Result := DoParse; //parse the new data
end;
{Tries to select the source code of an executable and parses it.
~param FileName the name of the executable file
~result whether the source code files could be parsed }
function TJADDParameterOptions.HandleExecutable(FileName: String): Boolean;
begin
//project file available? then use it
if FileExists(ChangeFileExt(FileName, '.' + DDPDefaultExtension)) then
Result := LoadSourceProjectFile(ChangeFileExt(FileName,
'.' + DDPDefaultExtension))
else
begin
//Delphi project file available?
if FileExists(ChangeFileExt(FileName, '.dpr')) then
FileName := ChangeFileExt(FileName, '.dpr')
else //Delphi package file available?
if FileExists(ChangeFileExt(FileName, '.dpk')) then
FileName := ChangeFileExt(FileName, '.dpk')
else //just use the whole directory
FileName := ExtractFileDir(FileName);
FJADDState.FilesToParse.Clear; //clear the lists of files to be parsed
FJADDState.FilesToExclude.Clear;
FJADDState.FilesOfLibrary.Clear;
FJADDState.FilesToParse.Add(FileName); //add the one file
Result := DoParse; //parse the new data
end;
end;
{Loads already parsed data from a file.
~param FileName the name of the file to load the parsed data from }
procedure TJADDParameterOptions.LoadParsedData(FileName: String);
var Errors :TParsedDataReadErrors; //errors while reading data
Msg :String; //the error message
Error :TParsedDataReadError; //each possible error
begin
if not FileExists(FileName) then //check whether file exists
begin
FileName := FileName + '.' + DDDDefaultExtension;
if not FileExists(FileName) then
raise EParameterException.CreateFmt('File with parsed data "%s" not found!',
[FileName]);
end;
Errors := FJADDState.ReadDataFromFile(FileName); //load parsed data from file
if Errors <> [] then //errors encountered?
begin
Msg := '';
for Error := Low(Error) to High(Error) do //get message of all errors
if Error in Errors then
Msg := Msg + ParsedDataReadErrorMessages(.Error.) + LineDelimiter;
if IsConsole then //show the errors
begin
WriteLn('Errors occurred while reading the data:');
Write(Msg);
end
else
MessageDlg('Errors occurred while reading the data:' + LineDelimiter + Msg,
mtWarning, [mbOK], 0);
end;
end;
{Sets a text in the documentation to be generated to the specified value.
~param NameValue the name of the text to be localized and its new value
separated by an equals sign }
procedure TJADDParameterOptions.SetLocalizationOption(const NameValue: String);
//to edit the language texts
var EditTexts :TDocumentationTextOptionWrapper;
i :Integer; //position of the equals sign
begin
//create editor of the texts
EditTexts := TDocumentationTextOptionWrapper.Create;
try
i := pos('=', NameValue); //search the equals sign
assert(not (i in [0, 1]));
//try to set the new text
EditTexts.SetOptionByName(Copy(NameValue, 1, i - 1),
Copy(NameValue, i + 1, High(Length(NameValue))));
finally
EditTexts.Free; //free the editor
end;
end;
{Changes the filter on messages of the generator.
Syntax of a part: GroupName=[01][01]*|(+|-)number[,number]*|-
~param Value the string to change the filter
~result whether the string was valid and the filter has been changed }
function TJADDParameterOptions.ChangeFilter(Value: String): Boolean;
{Extracts the next part from the string Value.
~result the next part from the string }
function ExtractPart: String;
var Index :Integer; //index of the delimiter
begin
Index := pos(PathsSeparator, Value); //search separator
if Index = 0 then //separator found?
begin
Result := Value; //return the whole (last) part
Value := ''; //nothing left
end
else
begin
Result := Copy(Value, 1, Index - 1); //extract the first part
Delete(Value, 1, Index); //and remove it
end;
Result := Trim(Result);
end;
{Sets the filter for a group by the specified numbers.
~param Group the group of messages to set
~param Filter whether the specified messages are filtered or not
~param Numbers the string containing the message numbers within the group }
function SetFilterByNumber(const Group: String; Filter: Boolean;
Numbers: String): Boolean;
{Returns the next number from the string.
~result the next number from the string or -1 in case of an error }
function GetNumber: Integer;
var Index :Integer; //index of the first faulty character
begin
Val(Numbers, Result, Index); //get the first number
if Index = 1 then //no number found?
Result := -1 //error
else
if Index = 0 then //last number?
Numbers := '' //none left
else
begin
Delete(Numbers, 1, Index - 1); //remove the number
Numbers := TrimLeft(Numbers);
//not the end of the string, neither a separator?
if (Numbers <> '') and (Numbers[1] <> ',') then
Result := -1 //error
else
begin
Delete(Numbers, 1, 1); //remove separator
Numbers := TrimLeft(Numbers);
end;
end;
end;
var Number :Integer; //the numbers from the string
begin
Result := True;
while Result and (Numbers <> '') do //for each number
begin
Number := GetNumber; //get the next number
Result := Number >= 0;
if Result then //no error and valid number?
FFilter.IsFiltered[Group, Number] := Filter; //set filter for the message
end;
end;
//mapping from characters ('+'/'-') to the filter value
const FilterMap: array[Boolean] of TMessageFilterStatus =
(mfsNotFiltered, mfsFiltered);
var Part :String; //each part of the string
Index :Integer; //index in the part
Group :String; //the name of the group
begin
Result := True;
Value := Trim(Value);
while Result and (Value <> '') do //for each part
begin
Part := ExtractPart; //get next part
Result := Part <> '';
if Result then //not empty?
begin
Index := pos('=', Part); //search separator
Result := Index <> 0;
if Result then //separator found?
begin
Group := Copy(Part, 1, Index - 1); //extract the first part
Delete(Part, 1, Index); //and remove it
Result := (Part <> '') and (Part[1] in ['0', '1', '+', '-']);
if Result then //valid characters?
if Part[1] in ['0', '1'] then //bit mask for messages?
FFilter.SetFilterForGroup(Group, Part) //set it
else
if Length(Part) = 1 then //filter for complete group?
begin
Result := Part[1] = '-'; //can only remove filter
if Result then //requested?
FFilter.AllFiltered[Group] := FilterMap[Part[1] = '+'] //set it
end
else
//set messages by numbers
Result := SetFilterByNumber(Group, Part[1] = '+',
Copy(Part, 2, High(Length(Part))));
end; //if Result
end; //if Result
end; //while Result and Value <> ''
end;
{Sets what topics the program should be verbose about.
~param Modes the modes to be set
~param LongModes whether the modes are expressed with their long names and
not each with a single indicating character
~param DefaultEnable whether the modes should be enabled instead of disabled
when not otherwise indicated
~todo implement long verbose modes and switching enabled/disabled }
procedure TJADDParameterOptions.SetVerboseMode(const Modes: String;
LongModes,
DefaultEnable: Boolean);
{Sets the topics to be verbose about.
~param Verbose whether it should be verbose or quiet about the topics
~param Topics the topics to be verbose or quiet about
~result whether all topics were valid }
function SetVerboseTopics(Verbose: Boolean; const Topics: String): Boolean;
//the characters used to represent topics to be verbose or quiet about
const TopicCharacters: array[TVerboseAbout] of Char = ('P', 'I', 'G');
var Topic :TVerboseAbout; //for each possible topic
Index :Integer; //counter through the string
Character :Char; //current character
begin
Result := True; //no invalid character so far
Index := 1; //run through whole string
while (Index <= Length(Topics)) and Result do
begin
Character := UpCase(Topics[Index]); //get current character
Topic := High(Topic); //search the topic it represents
while (Topic > Low(Topic)) and (Character <> TopicCharacters[Topic]) do
dec(Topic);
Result := Character = TopicCharacters[Topic]; //topic found?
if Result then //character was valid?
if Verbose then //set verbose- or quiet-mode
Include(FVerboseOutput, Topic)
else
Exclude(FVerboseOutput, Topic);
inc(Index); //next character
end;
end;
begin
if Modes = '' then //no parameter defined?
begin
if DefaultEnable then //enable or disable all modes
//be verbose on all topics
FVerboseOutput := [Low(TVerboseAbout)..High(TVerboseAbout)]
else
//be quiet on all topics
FVerboseOutput := [];
end
else
if LongModes then
begin
if not SetVerboseTopics(DefaultEnable, Modes) then
raise EParameterException.CreateFmt('Invalid long verbose modes: "%s"!',
[Modes]);
end
else
if not SetVerboseTopics(DefaultEnable, Modes) then
raise EParameterException.CreateFmt('Invalid short verbose modes: "%s"!',
[Modes]);
end;
{Loads a file with a list of GUI log files to generate a help about.
~param FileName the name of the project file to load }
procedure TJADDParameterOptions.LoadGUIHelpProjectFile(FileName: String);
var Ini :TCustomIniFile; //the project ini file to load
//to edit the language texts
EditTexts :TDocumentationTextOptionWrapper;
begin
//Input should be used and is supported?
if (FileName = '-') and SupportsStdInput then
Ini := ReadStdInProject //create ini from stdin
else
begin
if not FileExists(FileName) then
FileName := FileName + '.' + DDGHDefaultExtension;
if not FileExists(FileName) then
raise EParameterException.CreateFmt('GUI Help project file "%s" not found!',
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -