⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 textwind.cpp

📁 DOS下采用中断接收数据的串口通讯的例子,很难找到的好东西!
💻 CPP
📖 第 1 页 / 共 2 页
字号:
            for ( rpos.h.dl = start_col ;
                  rpos.h.dl < (unsigned char) (start_col+width);
                  rpos.h.dl++ ) {
                int86( 0x10, &rpos, &rout );
                int86( 0x10, &rread, &rout );
                save_buffer[ i++ ] = rout.x.ax;
            }
    }
}

// When a popup window is destroyed, the area under it is
// restored.  This function restores the text under the window,
// but doesn't do anything about the border.

void TextWindow::restore_window( void )
{
    union REGS rpos;
    union REGS rwrite;
    union REGS rout;
    int i;
    SaveCursor save_it;

    if ( !save_buffer )
        return;
    i = 0;
    rpos.h.ah = 2;
    rpos.h.bh = 0;
    rwrite.h.ah = 9;
    rwrite.h.bh = 0;
    rwrite.x.cx = 1;
    for ( rpos.h.dh = start_row ;
          rpos.h.dh < (unsigned char) ( start_row + height );
          rpos.h.dh++ )
        for ( rpos.h.dl = start_col ;
              rpos.h.dl < (unsigned char) ( start_col + width );
              rpos.h.dl++ ) {
            int86( 0x10, &rpos, &rout );
            rwrite.h.al = (unsigned char) save_buffer[ i ];
            rwrite.h.bl = (unsigned char)(save_buffer[i++]>>8);
            int86( 0x10, &rwrite, &rout );
        }
}

// When a popup window is saved, the border has to be saved as
// well.  The main window is saved in a standard row by column
// order in the save buffer.  The border area is stored somewhat
// more haphazardly, right here.

void TextWindow::save_border( void )
{
    union REGS rpos;
    union REGS rread;
    union REGS rout;
    int i;
    SaveCursor save_it;

    if ( save_buffer == 0 )
        return;
    i = width * height;
    rpos.h.ah = 2;
    rpos.h.bh = 0;
    rread.h.ah = 8;
    rread.h.bh = 0;
    for ( rpos.h.dl = (unsigned char) ( start_col - 1 );
          rpos.h.dl < (unsigned char) ( start_col + width + 1 ) ;
          rpos.h.dl++ ) {
        rpos.h.dh = (unsigned char) ( start_row - 1 );
        int86( 0x10, &rpos, &rout );
        int86( 0x10, &rread, &rout );
        save_buffer[ i++ ] = rout.x.ax;
        rpos.h.dh = (unsigned char) ( start_row + height );
        int86( 0x10, &rpos, &rout );
        int86( 0x10, &rread, &rout );
        save_buffer[ i++ ] = rout.x.ax;
    }
    for ( rpos.h.dh = start_row ;
          rpos.h.dh < (unsigned char) ( start_row + height ) ;
          rpos.h.dh++ ) {
        rpos.h.dl = (unsigned char) ( start_col - 1 );
        int86( 0x10, &rpos, &rout );
        int86( 0x10, &rread, &rout );
        save_buffer[ i++ ] = rout.x.ax;
        rpos.h.dl = start_col;
        rpos.h.dl = (unsigned char)( rpos.h.dl + width );
        int86( 0x10, &rpos, &rout );
        int86( 0x10, &rread, &rout );
        save_buffer[ i++ ] = rout.x.ax;
    }
}

// This protected function restores the border in the same odd
// order that it was saved.

void TextWindow::restore_border( void )
{
    union REGS rpos;
    union REGS rwrite;
    union REGS rout;
    int i;
    SaveCursor save_it;

    if ( save_buffer == 0 )
        return;
    i = width * height;
    rpos.h.ah = 2;
    rpos.h.bh = 0;
    rwrite.h.ah = 9;
    rwrite.h.bh = 0;
    rwrite.x.cx = 1;
    for ( rpos.h.dl = (unsigned char) ( start_col - 1 );
          rpos.h.dl < (unsigned char)( start_col + width + 1 );
          rpos.h.dl++ ) {
        rpos.h.dh = (unsigned char) ( start_row - 1 );
        int86( 0x10, &rpos, &rout );
        rwrite.h.al = (unsigned char) save_buffer[ i ];
        rwrite.h.bl = (unsigned char)( save_buffer[ i++ ] >> 8 );
        int86( 0x10, &rwrite, &rout );
        rpos.h.dh = (unsigned char) ( start_row + height );
        int86( 0x10, &rpos, &rout );
        rwrite.h.al = (unsigned char) save_buffer[ i ];
        rwrite.h.bl = (unsigned char)( save_buffer[ i++ ] >> 8 );
        int86( 0x10, &rwrite, &rout );
    }
    for ( rpos.h.dh = start_row;
          rpos.h.dh < (unsigned char) ( start_row + height ) ;
          rpos.h.dh++ ) {
        rpos.h.dl = (unsigned char) ( start_col - 1 );
        int86( 0x10, &rpos, &rout );
        rwrite.h.al = (unsigned char) save_buffer[ i ];
        rwrite.h.bl = (unsigned char) ( save_buffer[ i++ ] >> 8 );
        int86( 0x10, &rwrite, &rout );
        rpos.h.dl = (unsigned char) ( start_col + width );
        int86( 0x10, &rpos, &rout );
        rwrite.h.al = (unsigned char) save_buffer[ i ];
        rwrite.h.bl = (unsigned char) ( save_buffer[ i++ ] >> 8 );
        int86( 0x10, &rwrite, &rout );
    }
}

// A popup window is just like a text window except that it
// has an automatic save buffer and save cursor.  The constructor
// doesn't do anything except make a text window and then save
// it.

PopupWindow::PopupWindow( int r, int c, int w, int h )
         : TextWindow( r, c, w, h )
{
    save_window();
}

// This internal utility routine hides the cursor by moving it
// off the screen.  It is used when in the menu code.

inline void hide_cursor( void )
{
    union REGS r;
    r.h.ah = 2;
    r.h.dh = 25;
    r.h.dl = 0;
    r.h.bh = 0;
    int86( 0x10, &r, &r );
}

int Menu( char *menu[] )
{
    int items;
    int maxlen;
    int length;
    int i;
    int c;
    int selection;

    items = 0;
    maxlen = 0;
    while ( ( length = strlen( menu[ items ] ) ) != 0 ) {
        items++;
        if ( length > maxlen )
            maxlen = length;
    }
    if ( items == 0 )
        return -1;
    PopupWindow w( 5, 25, maxlen + 2, items );
    w.Clear();
    w.AddBorder();
    for ( i = 0 ; i < items ; i++ ) {
        w.SetPosition( i, 1 );
        w << menu[ i ];
    }
    selection = 0;
    for ( ; ; ) {
        w.SetAttribute( REVERSE_ATTRIBUTE );
        w.SetPosition( selection, 1 );
        w << menu[ selection ];
        hide_cursor();
        while ( ( c = w.ReadKey() ) == 0 )
            ;
        w.SetAttribute( NORMAL_ATTRIBUTE );
        w.SetPosition( selection, 1 );
        w << menu[ selection ];
        switch ( c ) {
            case 27 : //Escape
                return( -1 );
            case 13 : // CR
                return( selection );
            case HOME :
                selection = 0;
                break;
            case END :
                selection = items - 1;
                break;
            case DOWN :
                if ( selection < ( items - 1 ) )
                   selection++;
                break;
            case UP :
                if ( selection > 0 )
                    selection--;
                break;
            default :
                for ( i = ( selection + 1 ) % items ;
                      i != selection ;
                      i = ( i + 1 ) % items ) {
                    if (toupper(c)==toupper(menu[i][0]))
                    {
                        selection = i;
                        break;
                    }
                }
                break;
        }
    }
#ifdef _MSC_VER
    return -1;// To pass /W4 under Microsoft, not really needed
#endif
}

int ReadLine( char *prompt, char *buffer, int length )
{
    int c;
    int count;

    PopupWindow w( 5, 10, 60, 1 );
    w.Clear();
    w.AddBorder();
    w << prompt << ' ';
    count = 0;

    for ( ; ; ) {
        while ( ( c = w.ReadKey() ) == 0 )
            ;
        switch ( c ) {
            case ESC :
                return 0;
            case CR :
                buffer[ count ] = '\0';
                return 1;
            case BS :
                if ( count > 0 ) {
                    count--;
                    w << BS;
                    w << ' ';
                    w << BS;
                }
                break;
            default :
               if ( c >= ' ' && c <= 0x7f ) {
                   if ( count < length ) {
                       buffer[ count++ ] = (char) c;
                       w << c;
                   }
               }
        }
    }
#ifdef _MSC_VER
    return -1; // To pass /W4 under Microsoft, not really needed
#endif
}

// ReadKey returns a 0 if no key is ready.  The _bios_keybrd()
// routine under Borland C++ has trouble if a Ctrl-Break has been
// pressed, so I replace it with the equivalet int86() function
// call for that compiler only.

int TextWindow::ReadKey( void )
{
#ifdef __TURBOC__
    union REGS r;
    r.h.ah = 1;
    int86( 0x16, &r, &r );
    if ( r.x.flags & 0x40 )  // Test for the zero flag
        return 0;
    r.h.ah = 0;
    int86( 0x16, &r, &r );
    if ( r.h.al != 0 )
        return r.h.al;
    else
        return r.x.ax;
#else  // #ifdef __TURBOC__
    int c;

// Under Borland C, this function will never return true if CTRL-BREAK
// has been pressed, effectively closing the keyboard.

    if ( _bios_keybrd( _KEYBRD_READY ) == 0 )
       return 0;
    c = _bios_keybrd( _KEYBRD_READ );
    if ( ( c & 0xff ) == 0 )  // A normal ASCII key
        return c;
    else
        return c & 0xff;      // A function or other extended key
#endif // #ifdef __TURBOC__ ... #else
}

// This is an unsophisticated way to change to 43 line mode, or 50
// line mode on a VGA.  Note that it doesn't disable EGA cursor
// emulation, so if you try to change the cursor size, strange things
// might happen.  All this routine does to change modes is select the
// appropriate size font, 8x8 for 43 line mode, else 8x14 or 8x16.

void Set43LineMode( int control )
{
    union REGS r;

    if ( control ) {
        r.h.ah = 0x11;
        r.h.al = 0x12;
        r.h.bl = 0;
        int86( 0x10, &r, &r );
    } else {
        r.h.ah = 0x14;  // Change to 11 for EGA
        r.h.al = 0x12;
        r.h.bl = 0;
        int86( 0x10, &r, &r );
        r.h.ah = 0;
        r.h.al = 3; // Change to 2 for BW80
        int86( 0x10, &r, &r );
    }
}

// ****************** END OF TEXTWIND.CPP ******************

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -