Initial import
This commit is contained in:
parent
44908433fb
commit
37c48d3182
|
@ -0,0 +1,448 @@
|
|||
Unit m_MenuHelp;
|
||||
|
||||
{$I M_OPS.PAS}
|
||||
|
||||
Interface
|
||||
|
||||
Uses
|
||||
m_Input,
|
||||
m_Output;
|
||||
|
||||
Const
|
||||
mMaxHelpTest = 200;
|
||||
mMaxHelpKeyLen = 20;
|
||||
mMaxHelpLineLinks = 10;
|
||||
|
||||
Type
|
||||
TLinkInfoRec = Record
|
||||
Key : String[mMaxHelpKeyLen];
|
||||
LinkPos : Byte;
|
||||
LinkLen : Byte;
|
||||
End;
|
||||
|
||||
TLineInfoRec = Record
|
||||
Text : String;
|
||||
Links : Byte;
|
||||
Link : Array[1..mMaxHelpLineLinks] of TLinkInfoRec
|
||||
End;
|
||||
|
||||
TMenuHelp = Class
|
||||
HelpFile : Text;
|
||||
CurKey : String[mMaxHelpKeyLen];
|
||||
Text : Array[1..mMaxHelpTest] of TLineInfoRec;
|
||||
Lines : Word;
|
||||
Console : TOutput;
|
||||
Input : TInput;
|
||||
WinX1 : Byte;
|
||||
WinY1 : Byte;
|
||||
WinX2 : Byte;
|
||||
WinY2 : Byte;
|
||||
|
||||
Constructor Create (Var C: TOutput; Var I: TInput);
|
||||
Destructor Destroy; Override;
|
||||
|
||||
Function ReadKeywordData : Boolean;
|
||||
Procedure OpenHelp (Str: String);
|
||||
Function StripLinks (Str: String) : String;
|
||||
End;
|
||||
|
||||
Implementation
|
||||
|
||||
Uses
|
||||
m_Strings;
|
||||
|
||||
Constructor TMenuHelp.Create (Var C: TOutput; Var I: TInput);
|
||||
Begin
|
||||
Inherited Create;
|
||||
|
||||
Console := C;
|
||||
Input := I;
|
||||
WinX1 := 1;
|
||||
WinY1 := 11;
|
||||
WinX2 := 79;
|
||||
WinY2 := 23;
|
||||
End;
|
||||
|
||||
Destructor TMenuHelp.Destroy;
|
||||
Begin
|
||||
Inherited Destroy;
|
||||
End;
|
||||
|
||||
Function TMenuHelp.StripLinks (Str: String) : String;
|
||||
Var
|
||||
A : Byte;
|
||||
B : Byte;
|
||||
Begin
|
||||
A := 255;
|
||||
|
||||
While A > 0 Do Begin
|
||||
A := Pos('<link=', Str);
|
||||
|
||||
If A > 0 Then Begin
|
||||
B := 1;
|
||||
While Str[A + 6 + B] <> '>' Do Inc(B);
|
||||
Delete (Str, A, 7 + B);
|
||||
|
||||
A := Pos('</link>', Str);
|
||||
If A = 0 Then A := Length(Str);
|
||||
Delete (Str, A, 7);
|
||||
End;
|
||||
End;
|
||||
|
||||
Result := Str;
|
||||
End;
|
||||
|
||||
Function TMenuHelp.ReadKeywordData : Boolean;
|
||||
Var
|
||||
Str : String;
|
||||
Key : String;
|
||||
Temp1 : Byte;
|
||||
Temp2 : Byte;
|
||||
Done : Boolean;
|
||||
Buffer : Array[1..4 * 1024] of Char;
|
||||
Begin
|
||||
SetTextBuf (HelpFile, Buffer);
|
||||
Reset (HelpFile);
|
||||
|
||||
Done := False;
|
||||
|
||||
While Not Eof(HelpFile) And Not Done Do Begin
|
||||
ReadLn (HelpFile, Str);
|
||||
|
||||
Temp1 := Pos('<keyword> ', Str);
|
||||
|
||||
If Temp1 = 0 Then Continue;
|
||||
|
||||
Key := Copy(Str, Temp1 + 10, Length(Str));
|
||||
|
||||
If Key <> CurKey Then Continue;
|
||||
|
||||
Lines := 0;
|
||||
|
||||
While Not Eof(HelpFile) Do Begin
|
||||
ReadLn (HelpFile, Str);
|
||||
|
||||
If Pos('<end>', Str) > 0 Then Begin
|
||||
Done := True;
|
||||
Break;
|
||||
End;
|
||||
|
||||
Inc (Lines);
|
||||
|
||||
Text[Lines].Text := StripLinks(Str);
|
||||
Text[Lines].Links := 0;
|
||||
Str := strStripPipe(Str);
|
||||
|
||||
Repeat
|
||||
Temp1 := Pos('<link=', Str);
|
||||
|
||||
If Temp1 = 0 Then Break;
|
||||
|
||||
Inc (Text[Lines].Links);
|
||||
|
||||
Text[Lines].Link[Text[Lines].Links].LinkPos := Temp1;
|
||||
|
||||
Temp2 := 0;
|
||||
Key := '';
|
||||
|
||||
While Str[Temp1 + 6 + Temp2] <> '>' Do Begin
|
||||
Key := Key + Str[Temp1 + 6 + Temp2];
|
||||
Inc (Temp2);
|
||||
End;
|
||||
|
||||
Delete (Str, Temp1, 7 + Temp2);
|
||||
Temp2 := Pos('</link>', Str);
|
||||
Delete (Str, Temp2, 7);
|
||||
|
||||
Text[Lines].Link[Text[Lines].Links].LinkLen := Temp2 - Temp1;
|
||||
Text[Lines].Link[Text[Lines].Links].Key := Key;
|
||||
Until False;
|
||||
End;
|
||||
End;
|
||||
|
||||
Close (HelpFile);
|
||||
|
||||
Result := Done And (Lines > 0);
|
||||
End;
|
||||
|
||||
Procedure TMenuHelp.OpenHelp (Str: String);
|
||||
Var
|
||||
FN : String;
|
||||
Keyword : String;
|
||||
TopPage : Integer;
|
||||
CurLine : Integer;
|
||||
CurLPos : Byte = 1;
|
||||
WinSize : Integer;
|
||||
LastPos : Byte;
|
||||
LastKey : Array[1..10] of String[mMaxHelpKeyLen];
|
||||
|
||||
Procedure LinkOFF (LineNum: Word; YPos, LPos: Byte);
|
||||
Var
|
||||
S : String;
|
||||
Begin
|
||||
If Text[LineNum].Links = 0 Then Exit;
|
||||
|
||||
With Text[LineNum] Do
|
||||
S := Copy(strStripPipe(Text), Link[LPos].LinkPos, Link[LPos].LinkLen);
|
||||
|
||||
Console.WriteXY (WinX1 + Text[LineNum].Link[LPos].LinkPos - 1, YPos, 9, S);
|
||||
End;
|
||||
|
||||
Procedure DrawPage;
|
||||
Var
|
||||
Count1 : Byte;
|
||||
Count2 : Byte;
|
||||
Begin
|
||||
For Count1 := 1 to WinSize Do Begin
|
||||
If TopPage + Count1 - 1 <= Lines Then Begin
|
||||
Console.WriteXYPipe (WinX1, Count1 + WinY1 - 1, 7, WinX2 - WinX1 + 1, Text[TopPage + Count1 - 1].Text);
|
||||
|
||||
For Count2 := 1 to Text[TopPage + Count1 - 1].Links Do
|
||||
LinkOFF (TopPage + Count1 - 1, Count1 + WinY1 - 1, Count2);
|
||||
End Else
|
||||
Console.WriteXYPipe (WinX1, Count1 + WinY1 - 1, 7, WinX2 - WinX1 + 1, '');
|
||||
End;
|
||||
End;
|
||||
|
||||
Procedure LinkON;
|
||||
Var
|
||||
S : String;
|
||||
Begin
|
||||
With Text[TopPage + CurLine - 1] Do
|
||||
S := Copy(strStripPipe(Text), Link[CurLPos].LinkPos, Link[CurLPos].LinkLen);
|
||||
|
||||
Console.WriteXY (WinX1 + Text[TopPage + CurLine - 1].Link[CurLPos].LinkPos - 1, WinY1 + CurLine - 1, 30, S);
|
||||
Console.CursorXY (WinX1 + Text[TopPage + CurLine - 1].Link[CurLPos].LinkPos - 1, WinY1 + CurLine - 1);
|
||||
End;
|
||||
|
||||
Procedure UpdateCursor;
|
||||
Begin
|
||||
If Text[TopPage + CurLine - 1].Links > 0 Then Begin
|
||||
If CurLPos > Text[TopPage + CurLine - 1].Links Then CurLPos := Text[TopPage + CurLine - 1].Links;
|
||||
If CurLPos < 1 Then CurLPos := 1;
|
||||
|
||||
LinkON;
|
||||
End Else Begin
|
||||
CurLPos := 1;
|
||||
|
||||
Console.CursorXY (WinX1, WinY1 + CurLine - 1);
|
||||
End;
|
||||
End;
|
||||
|
||||
Procedure PageDown;
|
||||
Begin
|
||||
If Lines > WinSize Then Begin
|
||||
If TopPage + WinSize <= Lines - WinSize Then Begin
|
||||
Inc (TopPage, WinSize);
|
||||
End Else Begin
|
||||
TopPage := Lines - WinSize + 1;
|
||||
CurLine := WinSize;
|
||||
End;
|
||||
End Else
|
||||
CurLine := Lines;
|
||||
End;
|
||||
|
||||
Var
|
||||
OK : Boolean;
|
||||
Count : Byte;
|
||||
Ch : Char;
|
||||
Begin
|
||||
FillChar(LastKey, SizeOf(LastKey), 0);
|
||||
|
||||
FN := strWordGet(1, Str, ';');
|
||||
Keyword := strWordGet(2, Str, ';');
|
||||
|
||||
Assign (HelpFile, FN + '.hlp');
|
||||
{$I-} Reset (HelpFile); {$I+}
|
||||
|
||||
If IoResult <> 0 Then Exit;
|
||||
|
||||
Close (HelpFile);
|
||||
|
||||
TopPage := 1;
|
||||
CurLine := 1;
|
||||
LastPos := 0;
|
||||
WinSize := WinY2 - WinY1 + 1;
|
||||
CurKey := Keyword;
|
||||
OK := ReadKeywordData;
|
||||
|
||||
If Not OK and (CurKey <> 'INDEX') Then Begin
|
||||
CurKey := 'INDEX';
|
||||
OK := ReadKeywordData;
|
||||
End;
|
||||
|
||||
If Not OK Then Exit;
|
||||
|
||||
While OK Do Begin
|
||||
TopPage := 1;
|
||||
CurLine := 1;
|
||||
|
||||
DrawPage;
|
||||
|
||||
For Count := 1 to WinSize Do
|
||||
If Text[Count].Links > 0 Then Begin
|
||||
CurLine := Count;
|
||||
Break;
|
||||
End;
|
||||
|
||||
UpdateCursor;
|
||||
|
||||
Repeat
|
||||
Ch := Input.ReadKey;
|
||||
|
||||
Case Ch of
|
||||
#00 : Case Input.ReadKey of
|
||||
#71 : If (TopPage > 1) or (CurLine > 1) Then Begin
|
||||
TopPage := 1;
|
||||
CurLine := 1;
|
||||
|
||||
DrawPage;
|
||||
UpdateCursor;
|
||||
End;
|
||||
#72 : Begin
|
||||
If (CurLine = 1) and (TopPage > 1) Then Begin
|
||||
Dec (TopPage);
|
||||
|
||||
DrawPage;
|
||||
|
||||
UpdateCursor;
|
||||
End Else If CurLine > 1 Then Begin
|
||||
LinkOFF(TopPage + CurLine - 1, WinY1 + CurLine - 1, CurLPos);
|
||||
|
||||
Dec (CurLine);
|
||||
|
||||
UpdateCursor;
|
||||
End;
|
||||
End;
|
||||
#73 : Begin
|
||||
If TopPage - WinSize > 0 Then Begin
|
||||
Dec (TopPage, WinSize);
|
||||
|
||||
DrawPage;
|
||||
UpdateCursor;
|
||||
End Else If CurLine > 1 Then Begin
|
||||
TopPage := 1;
|
||||
CurLine := 1;
|
||||
|
||||
DrawPage;
|
||||
UpdateCursor;
|
||||
End;
|
||||
End;
|
||||
#75 : If (CurLPos > 1) and (Text[TopPage + CurLine - 1].Links > 0) Then Begin
|
||||
LinkOFF(TopPage + CurLine - 1, WinY1 + CurLine - 1, CurLPos);
|
||||
|
||||
Dec(CurLPos);
|
||||
|
||||
LinkON;
|
||||
End;
|
||||
#77 : If CurLPos < Text[TopPage + CurLine - 1].Links Then Begin
|
||||
LinkOFF(TopPage + CurLine - 1, WinY1 + CurLine - 1, CurLPos);
|
||||
|
||||
Inc(CurLPos);
|
||||
|
||||
LinkON;
|
||||
End;
|
||||
#79 : If TopPage + WinSize <= Lines Then Begin
|
||||
Repeat
|
||||
PageDown;
|
||||
Until TopPage >= Lines - WinSize - 1;
|
||||
|
||||
DrawPage;
|
||||
UpdateCursor;
|
||||
End Else
|
||||
If TopPage + CurLine <= Lines Then Begin
|
||||
LinkOFF (TopPage + CurLine - 1, WinY1 + CurLine - 1, CurLPos);
|
||||
|
||||
CurLine := Lines - TopPage + 1;
|
||||
|
||||
UpdateCursor;
|
||||
End;
|
||||
#80 : Begin
|
||||
If (CurLine = WinSize) and (TopPage + WinSize <= Lines) Then Begin
|
||||
Inc(TopPage);
|
||||
|
||||
DrawPage;
|
||||
|
||||
UpdateCursor;
|
||||
End Else
|
||||
If (CurLine < WinSize) And (TopPage + CurLine <= Lines) Then Begin
|
||||
LinkOFF(TopPage + CurLine - 1, WinY1 + CurLine - 1, CurLPos);
|
||||
|
||||
Inc(CurLine);
|
||||
|
||||
UpdateCursor;
|
||||
End;
|
||||
End;
|
||||
#81 : If TopPage + WinSize <= Lines Then Begin
|
||||
PageDown;
|
||||
|
||||
DrawPage;
|
||||
|
||||
UpdateCursor;
|
||||
End Else
|
||||
If TopPage + CurLine <= Lines Then Begin
|
||||
LinkOFF (TopPage + CurLine - 1, WinY1 + CurLine - 1, CurLPos);
|
||||
|
||||
CurLine := Lines - TopPage + 1;
|
||||
|
||||
UpdateCursor;
|
||||
End;
|
||||
End;
|
||||
#08 : Begin
|
||||
If LastPos = 0 Then
|
||||
CurKey := Keyword
|
||||
Else Begin
|
||||
CurKey := LastKey[LastPos];
|
||||
|
||||
Dec (LastPos);
|
||||
End;
|
||||
|
||||
OK := ReadKeywordData;
|
||||
|
||||
If Not OK Then Begin
|
||||
CurKey := 'INDEX';
|
||||
OK := ReadKeywordData;
|
||||
End;
|
||||
|
||||
Break;
|
||||
End;
|
||||
#13 : If Text[TopPage + CurLine - 1].Links > 0 Then Begin
|
||||
If Text[TopPage + CurLine - 1].Link[CurLPos].Key = '@PREV' Then Begin
|
||||
If LastPos = 0 Then
|
||||
CurKey := Keyword
|
||||
Else Begin
|
||||
CurKey := LastKey[LastPos];
|
||||
|
||||
Dec (LastPos);
|
||||
End;
|
||||
End Else Begin
|
||||
If LastPos < 10 Then
|
||||
Inc (LastPos)
|
||||
Else
|
||||
For Count := 1 to 9 Do LastKey[Count] := LastKey[Count + 1];
|
||||
|
||||
LastKey[LastPos] := CurKey;
|
||||
|
||||
CurKey := Text[TopPage + CurLine - 1].Link[CurLPos].Key;
|
||||
End;
|
||||
|
||||
OK := ReadKeywordData;
|
||||
|
||||
If Not OK Then Begin
|
||||
CurKey := 'INDEX';
|
||||
OK := ReadKeywordData;
|
||||
End;
|
||||
|
||||
Break;
|
||||
End;
|
||||
#27 : Begin
|
||||
OK := False;
|
||||
|
||||
Break;
|
||||
End;
|
||||
End;
|
||||
Until False;
|
||||
End;
|
||||
End;
|
||||
|
||||
End.
|
Loading…
Reference in New Issue