help.c
来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 1,490 行 · 第 1/3 页
C
1,490 行
if( *field == tabFilter.curr ) {
tabFilter.curr = NULL;
}
if( changecurr && count < helpStack->cur ) {
helpStack->cur -= 1;
}
next = (*field)->next;
HelpMemFree( *field );
*field = next;
tabFilter.first = helpTab;
}
static void display_fields( void )
{
a_field *p;
for( p = helpTab; p != NULL; p = p->next ) {
uivattribute( &helpScreen, p->area, AT( ATTR_EDIT ) );
}
}
static void free_fields( a_field **ht )
{
while( *ht != NULL ) {
del_field( *ht, ht, FALSE );
}
}
static a_field *field_find( a_field *table, int count )
{
for( ; count > 0 && table != NULL; --count, table = table->next )
;
return( table );
}
static void vscroll_fields( a_field **ht, SAREA use, int incr )
{
a_field **p;
a_field **next;
if( incr == 0 ) return;
for( p=ht; *p && (*p)->area.row < use.row+use.height ; p = next ) {
next = &((*p)->next);
if( (*p)->area.row >= use.row ) {
if((incr > 0 && (*p)->area.row < use.row + incr )
|| (incr < 0 && (*p)->area.row - incr >= use.row + use.height) ) {
next = p;
del_field( *ht, p, TRUE );
} else {
(*p)->area.row -= incr;
}
}
}
}
a_tab_field *help_next_field( a_field *fld, a_field *table )
{
_unused( table );
if( fld != NULL ) {
fld = fld->next;
}
return( fld );
}
static void nexttopic( char *word )
{
a_hstackent *h;
unsigned len;
len = strlen( word );
if( word == NULL ) {
h = HelpMemAlloc( sizeof( a_hstackent ) + 1 );
} else {
h = HelpMemAlloc( sizeof( a_hstackent ) + strlen( word ) );
}
if( helpStack != NULL ) {
helpStack->cur = field_count( helpTab, helpCur );
helpStack->line = currLine;
}
h->next = helpStack;
h->type = HSTCK_NAME;
h->cur = 0;
h->line = 0;
strcpy( h->helpfname, curFile );
if( word != NULL ) {
strcpy( h->word, word );
h->word[strlen( word )] = '\0';
} else {
h->word[0] = '\0';
}
helpStack = h;
free_fields( &helpTab );
}
static void prevtopic( void )
{
a_hstackent *h;
if( helpStack->next != NULL ) {
h = helpStack;
helpStack = helpStack->next;
HelpMemFree( h );
}
free_fields( &helpTab );
}
static void replacetopic( char *word )
{
if( helpStack->next == NULL ) {
HelpMemFree( helpStack );
helpStack = NULL;
} else {
prevtopic();
}
nexttopic( word );
}
void Free_Stack( void )
{
while( helpStack->next != NULL ) {
prevtopic();
}
HelpMemFree( helpStack );
}
unsigned help_in_tab( a_field *fld, void *dummy )
{
_unused( fld );
_unused( dummy );
return( TRUE );
}
static EVENT hlpwait( VTAB *tab )
{
int done;
static EVENT bumpev = EV_NO_EVENT;
char *next_name;
unsigned len1;
unsigned len2;
helpCur = field_find( helpTab, helpStack->cur );
if( helpTab != NULL && helpCur == NULL ) {
helpCur = helpTab;
}
tab->other = helpCur;
tab->curr = helpCur;
if( helpCur != NULL ) {
tab->home = helpCur->area.col;
}
uipushlist( helpEventList );
if( bumpev != EV_NO_EVENT ) {
uitabfilter( bumpev, tab );
helpCur = tab->curr;
bumpev = EV_NO_EVENT;
}
done = FALSE;
while( !done ) {
if( helpTab != NULL ) {
uivattribute( &helpScreen, helpCur->area, AT( ATTR_CURR_EDIT ) );
}
do {
uipushlist( keyShift );
curEvent = uivget( &helpScreen );
if( curEvent == EV_MOUSE_PRESS ) {
ignoreMouseRelease = FALSE;
}
uipoplist();
curEvent = uigadgetfilter( curEvent, &vGadget );
curEvent = uitabfilter( curEvent, tab );
} while( curEvent == EV_NO_EVENT );
if( eventMapFn != NULL ) {
curEvent = (*eventMapFn)( curEvent );
}
curEvent = uihotspotfilter( &helpScreen, hotSpotFields, curEvent );
if( helpTab != NULL ) {
uivattribute( &helpScreen, helpCur->area, AT( ATTR_EDIT ) );
}
switch( curEvent ) {
case EV_HELP:
nexttopic( helpWord );
done = TRUE;
break;
case EV_BOTTOM:
case E_UP:
case EV_PAGE_UP:
case EV_PAGE_DOWN:
case EV_CURSOR_UP:
case EV_CURSOR_DOWN:
case EV_TOP:
case E_DOWN:
case EV_SCROLL_VERTICAL:
if( curEvent == EV_BOTTOM ) {
bumpev = EV_CURSOR_DOWN;
} else if( curEvent == EV_TOP ) {
bumpev = EV_CURSOR_UP;
}
helpStack->cur = field_count( helpTab, helpCur );
done = TRUE;
break;
case '-':
case EV_MOUSE_RELEASE_R:
case EV_ALT_B:
case 'b':
case 'B':
case EV_FUNC(8):
case EV_FUNC(4):
prevtopic();
if( strcmp( helpStack->helpfname, curFile ) ) {
len1 = strlen( helpStack->word );
len2 = strlen( helpStack->helpfname );
helpCur = HelpMemAlloc( sizeof( a_field ) + len1 + len2 );
memcpy( helpCur->keyword, helpStack->word, len1 );
memcpy( helpCur->keyword + len1, helpStack->helpfname, len2 );
helpCur->keyword[ len1 + len2 ] = '\0';
helpCur->key1_len = len1;
helpCur->key2_len = len2;
helpCur->next = NULL;
// prevtopic();
helpTab = helpCur;
}
done = TRUE;
break;
case EV_ALT_S:
case 'S':
case 's':
if( helpSearchHdl != NULL ) {
uipoplist();
next_name = HelpSearch( helpSearchHdl );
if( next_name != NULL ) {
nexttopic( next_name );
HelpMemFree( next_name );
done = 1;
}
uipushlist( helpEventList );
}
break;
case EV_FIELD_CHANGE:
helpCur = tab->curr;
break;
case EV_MOUSE_RELEASE:
if( tab->other == NULL ) break;
if( ignoreMouseRelease ) {
/* this mouse release is for a mouse press that occured
* before this help topic was opened */
ignoreMouseRelease = FALSE;
break;
}
tab->other = tab->curr;
/* fall through */
case EV_ENTER: /*same as page-down if there are other topics*/
case EV_FUNC(7):
case '+':
// DEN 90/04/12 - next line necessary for mouse release kludge
helpCur = tab->curr;
if( helpTab != NULL ) {
if( helpCur->key2_len == 0 ) {
nexttopic( helpCur->keyword );
}
done = TRUE;
}
break;
case EV_KILL_UI:
uiforceevadd( EV_KILL_UI );
/* fall through */
case EV_ESCAPE:
done = TRUE;
break;
}
}
uipoplist();
return( curEvent );
}
static int getline( void )
{
int l;
if( helpGetString( helpInBuf, BUF_LEN, helpFileHdl ) == NULL ) {
return( FALSE );
}
l = strlen( helpInBuf );
if( l >= RSEP_LEN ) {
helpInBuf[l - RSEP_LEN] = '\0'; /* ignore record sep */
}
return( TRUE );
}
static void clearline( void )
{
helpInBuf[0] = '\0';
helpOutBuf[0] = '\0';
}
static void scanCallBack( TokenType type, void *info, ScanInfo *myinfo )
{
TextInfo *text;
HyperLinkInfo *link;
TextInfoBlock *block;
bool goofy;
unsigned cnt;
a_field *ht;
goofy = TRUE;
switch( type ) {
case TK_TEXT:
text = info;
switch( text->type ) {
case TT_LEFT_ARROW:
myinfo->buf[0] = REAL_LEFT_ARROW;
myinfo->buf++;
myinfo->pos++;
break;
case TT_RIGHT_ARROW:
myinfo->buf[0] = REAL_RIGHT_ARROW;
myinfo->buf++;
myinfo->pos++;
break;
case TT_END_OF_LINE:
myinfo->buf[0] = '\0';
myinfo->buf++;
myinfo->pos++;
break;
case TT_CTRL_SEQ:
memcpy( myinfo->buf, text->str, text->len );
myinfo->buf += text->len;
break;
case TT_ESC_SEQ:
memcpy( myinfo->buf, text->str, text->len );
myinfo->buf += text->len;
myinfo->pos += 1;
break;
default:
memcpy( myinfo->buf, text->str, text->len );
myinfo->buf += text->len;
myinfo->pos += text->len;
break;
}
break;
case TK_PLAIN_LINK:
myinfo->buf[0] = '<';
myinfo->buf ++;
myinfo->pos ++;
goofy = FALSE;
/* fall through */
case TK_GOOFY_LINK:
link = info;
block = &( link->block1 );
cnt = 0;
ht = HelpMemAlloc( sizeof( a_field ) + link->topic_len
+ link->hfname_len );
ht->area.width = 0;
ht->area.row = myinfo->line;
ht->area.height = 1;
ht->area.col = myinfo->pos;
memcpy( ht->keyword, link->topic, link->topic_len );
if( link->hfname_len != 0 ) {
memcpy( ht->keyword + link->topic_len, link->hfname,
link->hfname_len );
ht->keyword[ link->topic_len + link->hfname_len ] = '\0';
} else {
ht->keyword[ link->topic_len ] = '\0';
}
ht->key1_len = link->topic_len;
ht->key2_len = link->hfname_len;
while( block != NULL ) {
while( cnt < block->cnt ) {
text = &( block->info[cnt] );
switch( text->type ) {
case TT_ESC_SEQ:
memcpy( myinfo->buf, text->str, text->len );
myinfo->buf += text->len;
myinfo->pos ++;
ht->area.width ++;
break;
case TT_PLAIN:
memcpy( myinfo->buf, text->str, text->len );
myinfo->buf += text->len;
myinfo->pos += text->len;
ht->area.width += text->len;
break;
}
cnt++;
}
block = block->next;
cnt = 0;
}
if( ht->area.col + ht->area.width > helpScreen.area.width ) {
ht->area.width = helpScreen.area.width - ht->area.col;
}
add_field( ht, myinfo->changecurr );
if( !goofy ) {
myinfo->buf[0] = '>';
myinfo->buf ++;
myinfo->pos ++;
}
break;
}
}
/*
* processLine
*/
static int processLine( char *bufin, char *bufout, int line, bool changecurr )
{
ScanInfo info;
info.buf = bufout;
info.line = line;
info.changecurr = changecurr;
info.pos = 0;
ScanLine( bufin, scanCallBack, &info );
return( TRUE );
}
/*
* helpSet - set the help window title bar and its size
* - assumes helpInbuf contains the topic line for this topic
*/
static void helpSet( char *str, char *helpname, unsigned buflen )
{
int nums[5];
int i;
char *srcptr;
char *dstptr;
helpScreen.name = NULL;
helpLines = 0;
if( str != NULL ) {
strcpy( helpname, str );
srcptr = str;
dstptr = helpname;
while( *srcptr != '\0' ) {
if( *srcptr == HELP_ESCAPE ) srcptr ++;
*dstptr = *srcptr;
srcptr++;
dstptr++;
buflen--;
if( buflen == 0 ) {
dstptr --;
*dstptr = '\0';
break;
}
}
*dstptr = '\0';
helpScreen.name = helpname;
scanTopic( helpInBuf, &str );
str++;
str = strtok( str, " " );
}
for( i = 0; i < 5; ++i ) {
nums[i] = 0;
if( str != NULL ) {
nums[i] = atoi( str );
str = strtok( NULL, " " );
}
}
helpScreen.area.height = (nums[0] == 0) ? UIData->height - 3 : nums[0] + 3;
helpScreen.area.width = (nums[1] == 0) ? UIData->width - 2 : nums[1];
helpLines = nums[4];
if( helpScreen.area.height > UIData->height - 2 ) {
helpScreen.area.height = UIData->height - 2;
}
if( helpScreen.area.width > UIData->width - 2 ) {
helpScreen.area.width = UIData->width - 2;
} else if( helpScreen.area.width < HELP_MIN_WIDTH ) {
helpScreen.area.width = HELP_MIN_WIDTH;
}
if( strlen( helpScreen.name ) > helpScreen.area.width ) {
helpScreen.name[ helpScreen.area.width ] = '\0';
}
hlp_ut_position( &helpScreen.area, helpScreen.area.height, helpScreen.area.width,
nums[2], nums[3], TRUE );
}
static void putline( char *buffer, int line )
{
int i;
int start;
helpScreen.col = 0;
i = 0;
while( buffer[i] && helpScreen.col < helpScreen.area.width ) {
start = i;
while( buffer[i] && buffer[i] != HELP_ESCAPE &&
helpScreen.col+i-start<=helpScreen.area.width ) {
if( buffer[i] == 0xFF )
buffer[i] = 0x20;
++i;
}
if( i - start > 0 ) {
uivtextput( &helpScreen, line, helpScreen.col, currentAttr,
&buffer[start], i - start );
}
helpScreen.col += i-start;
if( buffer[i] == HELP_ESCAPE ) {
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?