home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Monster Media 1994 #1
/
monster.zip
/
monster
/
CLIPPER
/
NCCLIB.ZIP
/
NCCVIEW.ZIP
/
G_HELP.PRG
< prev
next >
Wrap
Text File
|
1993-12-12
|
24KB
|
789 lines
//═══════════════════════════════════════════════════════╕
// Program .....: G_Help │
// CopyRight ...: 1993 National Computer Consultants │
// All rights are reserved. │
// Author ......: Greg Rice │
//═══════════════════════════════════════════════════════╛
#include "nccview.ch"
#include "g_event.ch"
#include "inkey.ch"
#include "mouse.ch"
#include "fileio.ch"
/*
┌─────────────────────────────────────────────────────┐
│from buildhlp.exe │
│ │
│ Structure │
│ ~~~~~~~~~ │
│ │
│ Offset Id │
│ ------ ------------------- │
│ 0-1 HELPFILE_ID │
│ 2-3 Marker Length │
│ 4-5 Id Length │
│ 6-9 Total Header Length │
│ Id marker │
│ Help id's ... │
│ Text ... │
└─────────────────────────────────────────────────────┘
*/
#define HELPFILE "Nccviews.hlp"
#define HELPFILE_ID 'GR'
#define CRLF chr(13)+chr(10)
#xtranslate ftell( <x> ) => fseek( <x>, 0, FS_RELATIVE )
//--------------------------------------------------------------------------
static H_marker := NIL, ;
H_marker_len := NIL, ;
H_id_len := NIL, ;
H_header_len := NIL
//─────────────┐
// Online Help │
//─────────────┘
Function Gen_Help( xsearch )
local nOffset := -1 , ;
nLen := -1 , ;
nHandle , ;
aId , ;
aView , ;
nKey , ;
i , ;
vBar , ;
a , ;
y , ;
x , ;
xCursor := SetCursor( 0 ) , ;
xScrn := savescreen()
if (nHandle := fopen(HELPFILE, FO_READ+FO_SHARED)) == -1
NccPopUp('\nUnable to open help file\nPress any key to continue.\n', ;
Message_Color(), 5 ;
)
SetCursor( xCursor )
ShowBackGround()
Return( NIL )
endif
aId := HelpLink( nHandle )
if Empty(aId)
NccPopUp('\nInvalid help file\nPress any key to continue.\n', ;
Message_Color(), 5 ;
)
SetCursor( xCursor )
ShowBackGround()
Return( NIL )
endif
if xSearch == NIL
nOffset := aId[1,2] // Offset of Id in help file
nLen := aId[1,3] // Length of help for this Id
ViewHelpIndex( aId, @nOffset, @nLen )
if lastkey() == K_ESC
SetCursor( xCursor )
Return( NIL )
endif
else
a := ascan( aId, { |x| a == uppe(x[1]) } )
if a == 0
a := 1
endif
nOffset := aId[a,2] // Offset of Id in help file
nLen := aId[a,3] // Length of help for this Id
endif
ShowFile( nHandle, aId, nOffset, nLen )
fClose( nHandle )
restscreen(,,,,xScrn)
SetCursor( xCursor )
Return( NIL )
//-----------------------------------------------------------------------------
//───────────────────┐
// Display Help file │
//───────────────────┘
static function ShowFile( nHandle, aId, nOffset, nLen )
local o , ;
vBar , ;
xCursor := SET(_SET_CURSOR,0) , ;
xScrn := savescreen() , ;
xColor := SetColor( Title_Color() ) , ;
row := Row() , ;
col := Col() , ;
linebuf := space(512) , ;
nKey2 , ;
whereami , ;
hLen , ;
xtmp , ;
Mouse := MouseSys() , ;
Button , ;
mRow , ;
mColumn
Showbackground()
whereami := fseek(nHandle,nOffset+1,0)
fread( nHandle, @linebuf, 80 )
whereami := fseek( nHandle, noffset + at( CRLF, linebuf ) + 2, FS_SET )
// save where I am
fseek( nHandle,6, FS_SET) // position at Header Length
xtmp := space(4) // read header length
fread( nHandle, @xtmp, 4 ) //
hLen := bin2l( xtmp ) + 2 // header len + CRLF
fseek(nHandle,whereami,0) // reset to where I was
WinBox(2,,,,,5)
@ Maxrow()-2,1 say replicate('─',maxcol()-1)
@ maxrow()-1,1 say space(maxcol()-1) color Title_Color()
UnGrayLocalMenu()
o := dViewTXT():New(3,2,maxrow()-3,maxcol()-2,nhandle)
o:DataBlock := { || hLine(o) }
o:InverseColor := setcolor( "W+/R" )
o:GoTopBlock := { || o:dvFileSet( hLen+1 ), o:Down(), o:Refresh := .t. }
o:WhileBlock := { || o:FilePos > hLen .and. ! o:AtBottom .and. ! o:AtTop }
o:SkipBlock := { |n| Skipper(o,n) }
o:UserSlot := o:StatusBlock
o:StatusBlock := { |n| helpStat(o, n) }
o:UseStyle := .t.
vBar := NccvBar():New( 3 , ;
maxcol() , ;
maxrow()-3 , ;
maxcol() , ;
o:FileLen ;
)
o:Activate() ; vBar:Activate()
Mouse:Activate()
Mouse:Delay := 0
while .t.
o:Stabilize() ; vBar:Update( if( o:AtBottom, o:FileLen, o:filePos ) )
Mouse:MouseRead()
if Mouse:Ascii # 0
nKey2 := Mouse:Ascii
else
Button := Mouse:Button
mRow := Mouse:Row
mColumn := Mouse:Column
Do Case
Case Button == 2
Exit
Case Button == 1 .and. mRow == 23 .and. mColumn >= 2 .and. mColumn <= 3
keyboard CHR(K_F1)
Case Button == 1 .and. mRow == 23 .and. mColumn >= 19 .and. mColumn <= 21
keyboard CHR(K_ESC)
Case Button == 1 .and. mRow == 23 .and. mColumn >= 30 .and. mColumn <= 33
keyboard CHR(K_PGUP)
Case Button == 1 .and. mRow == 23 .and. mColumn >= 35 .and. mColumn <= 38
keyboard CHR(K_PGDN)
Case Button == 1 .and. mRow == 3 .and. mColumn == maxcol()
o:Home() ; o:Up() ; vBar:Update(o:FilePos)
Case Button == 1 .and. mRow == maxrow()-3 .and. mColumn == maxcol()
o:End() ; o:Down() ; vBar:Update(o:FilePos)
EndCase
LOOP
endif
Do Case
Case nKey2 == K_ESC
exit
Case nKey2 == K_LEFT .or. nKey2 == K_RIGHT // do nothing
Case nKey2 == K_F1
GrayLocalMenu()
whereami := ftell( nHandle )
if whereami >= aId[len(aId),2]
whereami := len(aId)
else
whereami := ascan( aId, { |o| o[2] > whereami } ) - 1
endif
ViewHelpIndex( aId, @nOffset, @nLen, whereami )
UnGrayLocalMenu()
if lastkey() # K_ESC
whereami := fseek(nHandle,nOffset+1,0)
fread( nHandle, @linebuf, 80 )
whereami := fseek( nHandle, noffset + at( CRLF, linebuf ) + 2, FS_SET )
o:dvFileSet( whereami )
o:RefreshAll( 0 )
endif
Otherwise
if nKey2 == K_DOWN .or. nKey2 == K_CTRL_PGDN .or. nKey2 == K_PGDN
o:End()
elseif nKey2 == K_UP .or. nKey2 == K_CTRL_PGUP .or. nKey2 == K_PGUP
o:Home()
endif
o:StandardKeys( nKey2 )
EndCase
enddo
set( _SET_CURSOR, xCursor )
Setcolor( xColor )
restscreen(,,,,xScrn)
setpos( row,col )
Return( NIL )
//-----------------------------------------------------------------------------
//──────────────────────────────────────────┐
// Build an array of Indeces for Help file │
//──────────────────────────────────────────┘
static function HelpLink( nHandle )
local xTmp , ;
nLen , ;
aRetVal := {} , ;
cHeaderBuffer , ;
nTextOffset , ;
nTextLen
xTmp := space(10)
if ! fread( nHandle, @xTmp, 10 ) == 10
* <Invalid Helpfile>
Return( {} )
endif
H_marker_len := bin2i( subs( xTmp,3,2 ) )
H_id_len := bin2i( subs( xTmp,5,2 ) )
H_header_len := bin2l( subs( xTmp,7,4 ) )
if subs(xTmp,1,2) # HELPFILE_ID
* <Invalid Helpfile id>
Return( {} )
endif
xTmp := space( H_marker_len )
if ! fread( nHandle, @xTmp, H_marker_len ) == H_marker_len
* <Invalid Helpfile id>
Return( {} )
endif
H_marker := xTmp
nLen := H_header_len - H_marker_len - 10 // rest of header
// from marker thru id's
if nLen > ( ( memory(1) * 1024 ) - 1 ) // nLen > Character Space
* <Not enough memory to load header>
Return( {} )
endif
cHeaderBuffer := space( nLen )
IF ! fread( nHandle, @cHeaderBuffer, nLen ) == nLen
* <Could not read bytes reported by header length bytes>
Return( {} )
END
nLen := len(cHeaderBuffer)
While .t.
if nLen < H_marker_len
exit
endif
xtmp := subs(cHeaderBuffer,1,H_id_len+8)
nTextOffset := bin2l( subs(xtmp,H_id_len+1,4 ) )
nTextLen := bin2l( subs(xtmp,H_id_len+4+1,4) )
aadd( aRetVal, { subs(xTmp,1,H_id_len), nTextOffset, nTextLen } )
nLen -= (H_id_len+8)
cHeaderBuffer := subs(cHeaderBuffer,(H_id_len+9))
Enddo
Return( aRetVal )
//-----------------------------------------------------------------------------
//────────────────────┐
// Display Help Index │
//────────────────────┘
static Function ViewHelpIndex( aArray, nOffset, nLen, StartPos )
local aView , ;
vBar , ;
nKey , ;
nKey2 , ;
row := row() , ;
col := col() , ;
Top , ;
Left , ;
Bottom , ;
Right , ;
xScrn := savescreen() , ;
xCursor := Set( _SET_CURSOR, 0 ) , ;
nRetVal := 0 , ;
xColor , ;
Mouse := MouseSys() , ;
Button , ;
mRow , ;
mColumn
Top := 04
Left := max( 0, int( (maxcol() - len( aArray[1,1])+2) /2 ) - 2 )
Bottom := min(maxrow()-6,Top+len(aArray) )
Right := Left + len(aArray[1,1])+1
xColor := SetColor( Title_Color() )
StartPos := if( StartPos == NIL, 1, StartPos )
Showbackground()
SetColor( "W+/B,W+/R" )
aView := dViewArray():New( Top+1 , ;
Left , ;
Bottom , ;
Right , ;
aArray ;
)
aView:DataBlock := { |l| if(!l, ;
space(right-left+1), ;
" " + aArray[aView:CurrentItem,1] + " " ;
) ;
}
aView:UseStyle := .t.
aView:StatusBlock := { || "" }
SetColor( "W+/R" )
vBar := NccvBar():New( Top , ;
Right+1 , ;
Bottom , ;
Right+1 , ;
len(aArray) ;
)
SetColor( "W+/B,W+/R" )
WinBox( Top-1 , ;
Left-1 , ;
Bottom+3 , ;
Right+1 , ;
, ;
5 , ;
.t. ;
)
@ Top-1,Left+2 say ' TOPIC INDEX ' color 'R/BG'
@ Bottom+1, Left say replicate("─", Right-Left+1)
SetColor( Title_Color() )
@ Bottom+2, Left say space( Right-Left+1 ) color "N/BG"
@ Bottom+2, Left + int((Right-Left+1-19)/2) say "┘=Select │ Esc=Exit" color "N/BG"
@ Bottom+2, Left + int((Right-Left+1-19)/2) say "┘" color "R/BG"
@ Bottom+2, Left + int((Right-Left+1-19)/2) + 12 say "Esc" color "R/BG"
@ maxrow(), 0 say ' Use mouse or keyboard to make selection.' color 'w+/r'
SetColor( xColor )
if StartPos > 0 .and. StartPos <= len( aArray )
aView:CurrentItem := StartPos
endif
aView:Activate(int((Bottom-Top)/2)) ; vBar:Activate()
Mouse:Activate()
Mouse:Delay := .1
While .T.
aView:Stabilize()
vBar:Update( aView:CurrentItem )
Mouse:MouseRead()
if Mouse:Ascii # 0
nKey2 := Mouse:Ascii
else
Button := Mouse:Button
mRow := Mouse:Row
mColumn := Mouse:Column
Do Case
Case Button == 2
keyboard CHR(K_ESC)
Case Button == 1 .and. mRow == Bottom+2 ;
.and. mColumn >= Left + int((Right-Left+1-19)/2) + 12 ;
.and. mColumn <= Left + int((Right-Left+1-19)/2) + 14
keyboard CHR(K_ESC)
Case Button == 1 .and. mRow == Bottom+2 ;
.and. mColumn >= Left + int((Right-Left+1-19)/2) ;
.and. mColumn <= Left + int((Right-Left+1-19)/2) + 1
keyboard CHR(K_ENTER)
Case Button == 1 .and. mRow == Top .and. mColumn == Right+1
aView:Up()
Case Button == 1 .and. mRow == Bottom .and. mColumn == Right+1
aView:Down()
Case Button == 1 .and. ( Top+1 >= aView:TopRow .and. ;
Bottom <= aView:BottomRow .and. ;
Left >= aView:LeftColumn .and. ;
Right <= aView:RightColumn )
if aView:CurrentRow == mRow
keyboard CHR(K_ENTER)
endif
if aView:CurrentRow > mRow
aView:Up(aView:CurrentRow - mRow)
else
aView:Down(mRow - aView:CurrentRow)
endif
EndCase
LOOP
endif
// nKey := inkey(0)
Do Case
Case nKey2 == K_ESC
exit
Case nKey2 == K_RETURN
nOffset := aArray[aView:CurrentItem,2]
nLen := aArray[aView:CurrentItem,3]
nRetVal := aView:CurrentItem
exit
Otherwise
aView:StandardKeys( nKey2 )
EndCase
enddo
restscreen(,,,,xScrn)
SetColor( xColor )
setpos( row,col )
Set( _SET_CURSOR, xCursor )
Return( nRetVal )
//-----------------------------------------------------------------------------
//────────────────────────────┐
// Line display for Help file │
//────────────────────────────┘
static func hline( o )
local first , ;
i , ;
who , ; // max things to check
marks := { , , } , ;
line := subs(o:Line,o:LeftPosition)
setpos( o:CurrentRow,o:LeftColumn )
While .t.
marks[1] := at( '~',Line )
marks[2] := at( '^',Line )
marks[3] := at( '&',Line )
who := ascan( marks, { |x| x # 0 } )
if who == 0
exit
endif
for i = who+1 to 3
if marks[i] < marks[who] .and. marks[i] # 0
who := i
endif
next
Do Case
Case who == 1
tilde( o, @line, marks[who] )
Case who == 2
hat( o, @line, marks[who] )
Case who == 3
perc( o, @line, marks[who] )
EndCase
enddo
@row(),col() say padr(line,o:RightColumn-col()+1," ") color o:standardcolor
Return( '' )
//-----------------------------------------------------------------------------
static function tilde( o, line, xAt )
@Row(),Col() say subs(line,1,xAt-1)
line := subs(line,xAt+1)
xAt := at( '~', Line )
if xAt # 0
@row(),col() say subs(line,1,min(o:RightColumn-col()+1,xAt-1)) ;
color 'W+/R'
line := subs(line,xAt+1)
endif
Return( NIL )
//-----------------------------------------------------------------------------
static function hat( o, line, xAt )
@Row(),Col() say subs(line,1,xAt-1)
line := subs(line,xAt+1)
xAt := at( '^', Line )
if xAt # 0
@row(),col() say subs(line,1,min(o:RightColumn-col()+1,xAt-1)) ;
color "R/BG"
line := subs(line,xAt+1)
endif
Return( NIL )
//-----------------------------------------------------------------------------
static function perc( o , line, xAt )
@Row(),Col() say subs(line,1,xAt-1)
line := subs(line,xAt+1)
xAt := at( '&', Line )
if xAt # 0
@row(),col() say subs(line,1,min(o:RightColumn-col()+1,xAt-1)) ;
color 'GR+/RB'
line := subs(line,xAt+1)
endif
Return( NIL )
//-----------------------------------------------------------------------------
//───────────────────────┐
// Skipper for Help file │
//───────────────────────┘
static Function Skipper(o,n)
local nSkipped := 0, nDirection := if(n>0,1,-1), ;
savefilepos := o:FilePos
if n == 0
Return( 0 )
endif
While nSkipped # n
if n>0
if o:dvNextLn()
if H_marker $ o:Line
loop
endif
if ! o:while()
o:dvFileSet( savefilepos )
exit
endif
savefilepos := o:FilePos
else
o:dvFileSet( savefilepos )
exit
endif
else
if o:dvPrevLn()
if H_marker $ o:Line
loop
endif
if ! o:while()
o:dvFileSet( savefilepos )
exit
endif
savefilepos := o:FilePos
else
o:dvFileSet( savefilepos )
exit
endif
endif
nSkipped += nDirection
enddo
Return( nSkipped )
//-----------------------------------------------------------------------------
//──────────────────────────────┐
// Status display for Help text │
//──────────────────────────────┘
static Function helpStat( o, n )
local top := o:TopRow , ;
right := o:RightColumn , ;
sColor := o:StandardColor , ;
iColor := o:InverseColor
if n == NIL
n := o:CurrentStatus
endif
if n == DVIEW_IDLE
@ maxrow()-1, 41 say space(7) color Letter_Color()
else
o:TopRow := Maxrow() + 2
o:RightColumn := 47
o:InverseColor := "W+/R+"
o:StandardColor := "W+/R+"
eval( o:UserSlot, n )
o:InverseColor := iColor
o:StandardColor := sColor
o:TopRow := top
o:RightColumn := right
endif
Return( NIL )
//-----------------------------------------------------------------------------
//───────────────────────────────┐
// Gray menu of Help text screen │
//───────────────────────────────┘
static function GrayLocalMenu()
local xColor := SetColor()
@maxrow()-1,01 say " F1=Topic Index │ Esc=Exit │ PgUp/PgDn │" + space(38) color "N+/BG"
SetColor( xColor )
Return( NIL )
//-----------------------------------------------------------------------------
//─────────────────────────────────┐
// UnGray menu of Help text screen │
//─────────────────────────────────┘
static function UnGrayLocalMenu()
local row := maxrow()-1, xColor := SetColor( Title_Color() )
@row,01 say " F1=Topic Index │ Esc=Exit │ PgUp/PgDn │" + space(38) color "N/BG"
SetColor( "R/BG" )
@row,02 say "F1"
@row,19 say "Esc"
@row,30 say "PgUp/PgDn"
SetColor( xColor )
Return( NIL )
//─────────────────────┐
// About NccView │
//─────────────────────┘
Function g_about()
local screen := savescreen(), cColor := SetColor(), Mouse := MouseSys()
SetColor("N/BG")
WinBox(5,13,19,66,0,4,.t.)
@ 05,14 say "╡"
@row(),col() say " National Computer Consultants " color 'W/RB+'
@row(),col() say "╞"
@ 7,30 say 'NccViews Version 1.2'
@ 8,31 say 'Shareware Version'
@ 10,16 say 'Copyright (c) 1993 National Computer Consultants'
@ 12,19 say 'Phone (703) 569-2729 CompuServe 70324,634'
// WinBox(15,37,17,43,,4)
@ 16,38 say ' Esc ' color 'W+/RB+'
@ 16,43 say '▄' color 'n/bg'
@ 17,39 say repl("▀",5) color 'n/bg'
@ maxrow(),0 say ' Press ESC key or click with left mouse button on Esc. Or click right button.' color 'w+/r'
While .t.
Mouse:MouseRead()
if Mouse:Row == 16 .and. ;
Mouse:Column >= 38 .and. ;
Mouse:Column <= 42 .or. ;
Mouse:Ascii == K_ESC .or. ;
Mouse:Button == RIGHT_BUTTON
While Mouse:Button # 0 .and. Mouse:ButtonHold( Mouse:Button )
Enddo
exit
endif
enddo
Mouse:ClearButtons()
SetColor( cColor )
restscreen(,,,,screen)
Return( NIL )