[BACK]Return to gclient.c CVS log [TXT][DIR] Up to [local] / OpenXM_contrib / gnuplot / os2

Annotation of OpenXM_contrib/gnuplot/os2/gclient.c, Revision 1.1

1.1     ! maekawa     1: #ifdef INCRCSDATA
        !             2: static char RCSid[]="$Id: gclient.c,v 1.15 1998/03/22 22:34:21 drd Exp $" ;
        !             3: #endif
        !             4:
        !             5: /****************************************************************************
        !             6:
        !             7:     PROGRAM: Gnupmdrv
        !             8:
        !             9:     MODULE:  gclient.c
        !            10:
        !            11:     This file contains the client window procedures for Gnupmdrv
        !            12:
        !            13: ****************************************************************************/
        !            14:
        !            15: /* PM driver for GNUPLOT */
        !            16:
        !            17: /*[
        !            18:  * Copyright 1992, 1993, 1998   Roger Fearick
        !            19:  *
        !            20:  * Permission to use, copy, and distribute this software and its
        !            21:  * documentation for any purpose with or without fee is hereby granted,
        !            22:  * provided that the above copyright notice appear in all copies and
        !            23:  * that both that copyright notice and this permission notice appear
        !            24:  * in supporting documentation.
        !            25:  *
        !            26:  * Permission to modify the software is granted, but not the right to
        !            27:  * distribute the complete modified source code.  Modifications are to
        !            28:  * be distributed as patches to the released version.  Permission to
        !            29:  * distribute binaries produced by compiling modified sources is granted,
        !            30:  * provided you
        !            31:  *   1. distribute the corresponding source modifications from the
        !            32:  *    released version in the form of a patch file along with the binaries,
        !            33:  *   2. add special version identification to distinguish your version
        !            34:  *    in addition to the base release version number,
        !            35:  *   3. provide your name and address as the primary contact for the
        !            36:  *    support of your modified version, and
        !            37:  *   4. retain our contact information in regard to use of the base
        !            38:  *    software.
        !            39:  * Permission to distribute the released version of the source code along
        !            40:  * with corresponding source modifications in the form of a patch file is
        !            41:  * granted with same provisions 2 through 4 for binary distributions.
        !            42:  *
        !            43:  * This software is provided "as is" without express or implied warranty
        !            44:  * to the extent permitted by applicable law.
        !            45: ]*/
        !            46:
        !            47: /*
        !            48:  * AUTHOR
        !            49:  *
        !            50:  *   Gnuplot driver for OS/2:  Roger Fearick
        !            51:  *
        !            52:  * Send your comments or suggestions to
        !            53:  *  info-gnuplot@dartmouth.edu.
        !            54:  * This is a mailing list; to join it send a note to
        !            55:  *  majordomo@dartmouth.edu.
        !            56:  * Send bug reports to
        !            57:  *  bug-gnuplot@dartmouth.edu.
        !            58: **/
        !            59:
        !            60: #define INCL_PM
        !            61: #define INCL_WIN
        !            62: #define INCL_SPL
        !            63: #define INCL_SPLDOSPRINT
        !            64: #define INCL_WINSTDFONT
        !            65: #define INCL_DOSMEMMGR
        !            66: #define INCL_DOSPROCESS
        !            67: #define INCL_DOSERRORS
        !            68: #define INCL_DOSFILEMGR
        !            69: #define INCL_DOSNMPIPES
        !            70: #define INCL_DOSSESMGR
        !            71: #define INCL_DOSSEMAPHORES
        !            72: #define INCL_DOSMISC
        !            73: #define INCL_DOSQUEUES
        !            74: #define INCL_WINSWITCHLIST
        !            75: #include <os2.h>
        !            76: #include <string.h>
        !            77: #include <stdio.h>
        !            78: #include <io.h>
        !            79: #include <fcntl.h>
        !            80: #include <math.h>
        !            81: #include <stdlib.h>
        !            82: #include <unistd.h>
        !            83: #include <process.h>
        !            84: #include <signal.h>
        !            85: #include "gnupmdrv.h"
        !            86:
        !            87: /*==== g l o b a l    d a t a ================================================*/
        !            88:
        !            89: extern char szIPCName[] ;       /* name used in IPC with gnuplot */
        !            90: extern char szIniFile[256] ;    /* full path of ini file */
        !            91: extern int  bServer ;
        !            92: extern int  bPersist ;
        !            93: extern int  bEnhanced ;
        !            94:
        !            95: /*==== l o c a l    d a t a ==================================================*/
        !            96:
        !            97: static long lLineTypes[7] = { LINETYPE_SOLID,
        !            98:                               LINETYPE_SHORTDASH,
        !            99:                               LINETYPE_DOT,
        !           100:                               LINETYPE_DASHDOT,
        !           101:                               LINETYPE_LONGDASH,
        !           102:                               LINETYPE_DOUBLEDOT,
        !           103:                               LINETYPE_DASHDOUBLEDOT } ;
        !           104: static long lCols[16] =     { CLR_BLACK,
        !           105:                               CLR_DARKGRAY,
        !           106:                               CLR_BLUE,
        !           107:                               CLR_RED,
        !           108:                               CLR_GREEN,
        !           109:                               CLR_CYAN,
        !           110:                               CLR_PINK,
        !           111:                               CLR_YELLOW,
        !           112:                               CLR_DARKBLUE,
        !           113:                               CLR_DARKRED,
        !           114:                               CLR_DARKGREEN,
        !           115:                               CLR_DARKCYAN,
        !           116:                               CLR_DARKPINK,
        !           117:                               CLR_BROWN,
        !           118:                               CLR_PALEGRAY,
        !           119:                               CLR_WHITE } ;
        !           120:
        !           121: static LONG alColourTable[ 16 ] ;
        !           122:
        !           123: #define   GNUBUF    1024        /* buffer for gnuplot commands */
        !           124: #define   PIPEBUF   4096        /* size of pipe buffers */
        !           125: #define   CMDALLOC  4096        /* command buffer allocation increment (ints) */
        !           126: #define   ENVSIZE   2048        /* size of environment */
        !           127:
        !           128: #define   PAUSE_DLG 1           /* pause handled in dialog box */
        !           129: #define   PAUSE_BTN 2           /* pause handled by menu item */
        !           130: #define   PAUSE_GNU 3           /* pause handled by Gnuplot */
        !           131:
        !           132: #define   DEFLW     50
        !           133:
        !           134: static ULONG    ppidGnu=0L ;      /* gnuplot pid */
        !           135: static HPS      hpsScreen ;     /* screen pres. space */
        !           136: static int      iSeg = 1 ;
        !           137:
        !           138: static HSWITCH hSwitch = 0 ;    /* switching between windows */
        !           139: static SWCNTRL swGnu ;
        !           140:
        !           141: static BOOL     bLineTypes = FALSE ;    // true if use dashed linetypes
        !           142: BOOL     bWideLines ;
        !           143: static BOOL     bColours = TRUE ;
        !           144: static BOOL     bShellPos = FALSE ;
        !           145: static BOOL     bPlotPos = FALSE ;
        !           146: static BOOL     bPopFront = TRUE ;
        !           147: static BOOL     bNewFont = FALSE ;
        !           148: static BOOL     bHorz = TRUE ;
        !           149:
        !           150: static ULONG    ulPlotPos[4] ;
        !           151: static ULONG    ulShellPos[4] ;
        !           152: static PAUSEDATA pausedata = {sizeof(PAUSEDATA), NULL, NULL} ;
        !           153: static char     szFontNameSize[FONTBUF] ;
        !           154: static PRQINFO3 infPrinter = { "" } ;
        !           155: static QPRINT   qPrintData = { sizeof(QPRINT), 0.0, 0.0, 1.0, 1.0, 0,
        !           156:                                "", "", &infPrinter, 0, NULL } ;
        !           157: //static HEV      semStartSeq ;   /* semaphore to start things in right sequence */
        !           158: static HEV      semPause ;
        !           159: static HMTX     semHpsAccess ;
        !           160: static ULONG    ulPauseReply = 1 ;
        !           161: static ULONG    ulPauseMode  = PAUSE_DLG ;
        !           162:
        !           163: static HWND     hSysMenu ;
        !           164:             /* stuff for screen-draw thread control */
        !           165:
        !           166: static BOOL     bExist ;
        !           167: //static HEV      semDrawDone ;
        !           168:
        !           169:             /* thread control */
        !           170:
        !           171: static TID     tidDraw, tidSpawn ;
        !           172:
        !           173:             /* font data */
        !           174:
        !           175: static int lSupOffset = 0 ;
        !           176: static int lSubOffset = 0 ;
        !           177: static int lBaseSupOffset = 0 ;
        !           178: static int lBaseSubOffset = 0 ;
        !           179: static int lCharWidth = 217 ;
        !           180: static int lCharHeight = 465 ;
        !           181:
        !           182:
        !           183: /*==== f u n c t i o n s =====================================================*/
        !           184:
        !           185: int             DoPrint( HWND ) ;
        !           186: HBITMAP         CopyToBitmap( HPS ) ;
        !           187: HMF             CopyToMetaFile( HPS ) ;
        !           188: MRESULT         WmClientCmdProc( HWND , ULONG, MPARAM, MPARAM ) ;
        !           189: void            ChangeCheck( HWND, USHORT, USHORT ) ;
        !           190: BOOL            QueryIni( HAB ) ;
        !           191: static void     SaveIni( HWND ) ;
        !           192: static void     ThreadDraw( void* ) ;
        !           193: static void     DoPaint( HWND, HPS ) ;
        !           194: static void     Display( HPS ) ;
        !           195: void            SelectFont( HPS, char * );
        !           196: void            SwapFont( HPS, char * );
        !           197: static void     CopyToClipBrd( HWND ) ;
        !           198: static void     ReadGnu( void* ) ;
        !           199: static void     EditLineTypes( HWND, HPS, BOOL ) ;
        !           200: static void     EditCharCell( HPS, SIZEF* ) ;
        !           201: static HPS      InitScreenPS( void ) ;
        !           202: static int      BufRead( HFILE, void*, int, PULONG ) ;
        !           203: int             GetNewFont( HWND, HPS ) ;
        !           204: void            SigHandler( int ) ;
        !           205: void            FontExpand( char * ) ;
        !           206: static char    *ParseText(HPS, char *, BOOL, char *,
        !           207:                        int, int, BOOL, BOOL ) ;
        !           208: static void     CharStringAt(HPS, int, int, int, char *) ;
        !           209: static int      QueryTextBox( HPS, int, char * ) ;
        !           210: static void      LMove( HPS hps, POINTL *p ) ;
        !           211: static void      LLine( HPS hps, POINTL *p ) ;
        !           212: static void      LType( int iType ) ;
        !           213:
        !           214: /*==== c o d e ===============================================================*/
        !           215:
        !           216: MRESULT EXPENTRY DisplayClientWndProc(HWND hWnd, ULONG message, MPARAM mp1, MPARAM mp2)
        !           217: /*
        !           218: **  Window proc for main window
        !           219: **  -- passes most stuff to active child window via WmClientCmdProc
        !           220: **  -- passes DDE messages to DDEProc
        !           221: */
        !           222: {
        !           223:     static BOOL    bSw = FALSE ;
        !           224:     static BOOL    bFirst = TRUE ;
        !           225:     static RECTL   rectlPaint = { 0, 0, 0, 0 } ;
        !           226:     static int     iPaintCount = 0 ;
        !           227:     static int     firstcall = 1 ;
        !           228:
        !           229:     switch (message) {
        !           230:
        !           231:         case WM_CREATE:
        !           232:             {
        !           233:             HDC     hdcScreen ;
        !           234:             SIZEL   sizlPage ;
        !           235:                 // set initial values
        !           236:             ChangeCheck( hWnd, IDM_LINES_THICK, bWideLines?IDM_LINES_THICK:0 ) ;
        !           237:             ChangeCheck( hWnd, IDM_LINES_SOLID, bLineTypes?0:IDM_LINES_SOLID ) ;
        !           238:             ChangeCheck( hWnd, IDM_COLOURS, bColours?IDM_COLOURS:0 ) ;
        !           239:             ChangeCheck( hWnd, IDM_FRONT, bPopFront?IDM_FRONT:0 ) ;
        !           240:                 // disable close from system menu (close only from gnuplot)
        !           241:             hApp = WinQueryWindow( hWnd, QW_PARENT ) ; /* temporary assignment.. */
        !           242:             hSysMenu = WinWindowFromID( hApp, FID_SYSMENU ) ;
        !           243:                 // setup semaphores
        !           244: //            DosCreateEventSem( NULL, &semDrawDone, 0L, 0L ) ;
        !           245: //            DosCreateEventSem( NULL, &semStartSeq, 0L, 0L ) ;
        !           246:             DosCreateEventSem( NULL, &semPause, 0L, 0L ) ;
        !           247:             DosCreateMutexSem( NULL, &semHpsAccess, 0L, 1L ) ;
        !           248:             bExist = TRUE ;
        !           249:                 // create a dc and hps to draw on the screen
        !           250:             hdcScreen = WinOpenWindowDC( hWnd ) ;
        !           251:             sizlPage.cx = 0 ; sizlPage.cy = 0 ;
        !           252:             sizlPage.cx = 19500 ; sizlPage.cy = 12500 ;
        !           253:             hpsScreen = GpiCreatePS( hab, hdcScreen, &sizlPage,
        !           254:                            PU_HIMETRIC|GPIT_NORMAL|GPIA_ASSOC) ;
        !           255:                 // spawn server for GNUPLOT ...
        !           256:             tidSpawn = _beginthread( ReadGnu, NULL, 32768, NULL ) ;
        !           257:             }
        !           258:             break ;
        !           259:
        !           260:         case WM_GPSTART:
        !           261:
        !           262:                 // get details of command-line window
        !           263:             hSwitch = WinQuerySwitchHandle( 0, ppidGnu ) ;
        !           264:             WinQuerySwitchEntry( hSwitch, &swGnu ) ;
        !           265:             if( firstcall ) {
        !           266:                 // set size of this window
        !           267:             WinSetWindowPos( WinQueryWindow( hWnd, QW_PARENT ),
        !           268:                              bPopFront?HWND_TOP:swGnu.hwnd,
        !           269:                              ulShellPos[0],
        !           270:                              ulShellPos[1],
        !           271:                              ulShellPos[2],
        !           272:                              ulShellPos[3],
        !           273:                              bShellPos?(bPopFront?SWP_SIZE|SWP_MOVE|SWP_SHOW|SWP_ACTIVATE
        !           274:                                                  :SWP_SIZE|SWP_MOVE|SWP_SHOW|SWP_ZORDER)
        !           275:                                       :(bPopFront?SWP_SHOW|SWP_ACTIVATE:SWP_SHOW|SWP_ZORDER) ) ;
        !           276:             signal( SIGTERM, SigHandler ) ;
        !           277:                 firstcall = 0 ;
        !           278:                 }
        !           279:             if( !bPopFront ) WinSwitchToProgram( hSwitch ) ;
        !           280: //            DosPostEventSem( semDrawDone ) ;
        !           281:             DosReleaseMutexSem( semHpsAccess ) ;
        !           282:             return 0 ;
        !           283:
        !           284:         case WM_COMMAND:
        !           285:
        !           286:             return WmClientCmdProc( hWnd , message , mp1 , mp2 ) ;
        !           287:
        !           288:         case WM_CHAR:
        !           289:                     /* If the user types a command in the driver window,
        !           290:                        we route it to the gnuplot window and switch that
        !           291:                        to the front. Doesn't work for full-screen
        !           292:                        sessions, though (but does switch).  */
        !           293:             {
        !           294:             USHORT  usFlag ;
        !           295:             usFlag = SHORT1FROMMP( mp1 ) ;
        !           296:             if(  !(usFlag & (KC_KEYUP|KC_ALT|KC_CTRL)) ) {
        !           297:                 USHORT uc = SHORT1FROMMP( mp2 ) ;
        !           298:                     HWND hw = WinQueryWindow( swGnu.hwnd, QW_BOTTOM ) ;
        !           299:                     WinSetFocus( HWND_DESKTOP, hw ) ;
        !           300:                 WinSendMsg( hw, message,
        !           301:                             MPFROM2SHORT((USHORT)(KC_SCANCODE), 1),
        !           302:                             MPFROMSHORT(uc) ) ;
        !           303:                     WinSwitchToProgram( hSwitch ) ;
        !           304:                     }
        !           305:             }
        !           306:             break ;
        !           307:
        !           308:         case WM_DESTROY:
        !           309:
        !           310:             if( WinSendMsg( hWnd, WM_USER_PRINT_QBUSY, 0L, 0L ) != 0L ) {
        !           311:                 WinMessageBox( HWND_DESKTOP,
        !           312:                                hWnd,
        !           313:                                "Still printing - not closed",
        !           314:                                APP_NAME,
        !           315:                                0,
        !           316:                                MB_OK | MB_ICONEXCLAMATION ) ;
        !           317:                 return 0L ;
        !           318:                 }
        !           319:            return (WinDefWindowProc(hWnd, message, mp1, mp2));
        !           320:
        !           321:         case WM_PAINT:
        !           322:             {
        !           323:             ULONG ulCount ;
        !           324:             PID pid; TID tid;
        !           325:             HPS hps_tmp;
        !           326:             RECTL rectl_tmp;
        !           327:               DosQueryMutexSem( semHpsAccess, &pid, &tid, &ulCount ) ;
        !           328:             if (( ulCount > 0 ) && (tid != tidDraw)) {
        !           329:                 /* simple repaint while building plot or metafile */
        !           330:                 /* use temporary PS                   */
        !           331:               hps_tmp = WinBeginPaint(hWnd,0,&rectl_tmp );
        !           332:               WinFillRect(hps_tmp,&rectl_tmp,CLR_BACKGROUND);
        !           333:               WinEndPaint(hps_tmp);
        !           334:                 /* add dirty rectangle to saved rectangle     */
        !           335:                 /* to be repainted when PS is available again */
        !           336:               WinUnionRect(hab,&rectlPaint,&rectl_tmp,&rectlPaint);
        !           337:                 iPaintCount ++ ;
        !           338:                 break ;
        !           339:                 }
        !           340:             WinInvalidateRect( hWnd, &rectlPaint, TRUE ) ;
        !           341:             DoPaint( hWnd, hpsScreen ) ;
        !           342:             WinSetRectEmpty( hab, &rectlPaint ) ;
        !           343:             }
        !           344:             break ;
        !           345:
        !           346:         case WM_SIZE :
        !           347:
        !           348:             {
        !           349:             WinInvalidateRect( hWnd, NULL, TRUE ) ;
        !           350:             }
        !           351:             break ;
        !           352:
        !           353:         case WM_PRESPARAMCHANGED:
        !           354:             {
        !           355:             char *pp ;
        !           356:             ULONG ulID ;
        !           357:             pp = malloc(FONTBUF) ;
        !           358:             if( WinQueryPresParam( hWnd,
        !           359:                                    PP_FONTNAMESIZE,
        !           360:                                    0,
        !           361:                                    &ulID,
        !           362:                                    FONTBUF,
        !           363:                                    pp,
        !           364:                                    QPF_NOINHERIT ) != 0L ) {
        !           365:                 strcpy( szFontNameSize, pp ) ;
        !           366:                 bNewFont = TRUE ;
        !           367:                 WinInvalidateRect( hWnd, NULL, TRUE ) ;
        !           368:                 }
        !           369:             free(pp) ;
        !           370:             }
        !           371:             break ;
        !           372:
        !           373:         case WM_USER_PRINT_BEGIN:
        !           374:         case WM_USER_PRINT_OK :
        !           375:         case WM_USER_DEV_ERROR :
        !           376:         case WM_USER_PRINT_ERROR :
        !           377:         case WM_USER_PRINT_QBUSY :
        !           378:
        !           379:             return( PrintCmdProc( hWnd, message, mp1, mp2 ) ) ;
        !           380:
        !           381:         case WM_GNUPLOT:
        !           382:                 // display the plot
        !           383:             if( bPopFront )
        !           384:                 WinSetWindowPos( hwndFrame, HWND_TOP, 0,0,0,0, SWP_ACTIVATE|SWP_ZORDER ) ;
        !           385:             if( iPaintCount > 0 ) { /* if outstanding paint messages, repaint */
        !           386:                 WinInvalidateRect( hWnd, &rectlPaint, TRUE ) ;
        !           387:                 iPaintCount = 0 ;
        !           388:                 }
        !           389:             return 0L ;
        !           390:
        !           391:         case WM_PAUSEPLOT:
        !           392:                 /* put pause message on screen, or enable 'continue' button */
        !           393:             if( ulPauseMode == PAUSE_DLG ) {
        !           394:                 pausedata.pszMessage = (char*)mp1 ;
        !           395:                 WinLoadDlg( HWND_DESKTOP,
        !           396:                             hWnd,
        !           397:                             (PFNWP)PauseMsgDlgProc,
        !           398:                             0L,
        !           399:                             IDD_PAUSEBOX,
        !           400:                             &pausedata ) ;
        !           401:                 }
        !           402:             else {
        !           403:                 WinEnableMenuItem( WinWindowFromID(
        !           404:                                    WinQueryWindow( hWnd, QW_PARENT ), FID_MENU ),
        !           405:                                    IDM_CONTINUE,
        !           406:                                    TRUE ) ;
        !           407:                 }
        !           408:             return 0L ;
        !           409:
        !           410:         case WM_PAUSEEND:
        !           411:             /* resume plotting */
        !           412:             ulPauseReply = (ULONG) mp1 ;
        !           413:             DosPostEventSem( semPause ) ;
        !           414:             return 0L ;
        !           415:
        !           416:        default:         /* Passes it on if unproccessed    */
        !           417:            return (WinDefWindowProc(hWnd, message, mp1, mp2));
        !           418:     }
        !           419:     return (NULL);
        !           420: }
        !           421:
        !           422: MRESULT WmClientCmdProc(HWND hWnd, ULONG message, MPARAM mp1, MPARAM mp2)
        !           423: /*
        !           424: **   Handle client window command (menu) messages
        !           425: */
        !           426:     {
        !           427:     extern HWND hApp ;
        !           428:     static ulPauseItem = IDM_PAUSEDLG ;
        !           429:
        !           430:     switch( (USHORT) SHORT1FROMMP( mp1 ) ) {
        !           431:
        !           432:         case IDM_ABOUT :    /* show the 'About' box */
        !           433:
        !           434:             WinDlgBox( HWND_DESKTOP,
        !           435:                        hWnd ,
        !           436:                        (PFNWP)About ,
        !           437:                        0L,
        !           438:                        ID_ABOUT,
        !           439:                        NULL ) ;
        !           440:             break ;
        !           441:
        !           442:
        !           443:         case IDM_GPLOTINF:  /* view gnuplot.inf */
        !           444:             {
        !           445:             char path[256] ;
        !           446:             char *p ;
        !           447:             strcpy( path, "start view " ) ;
        !           448:             if( (p=getenv("GNUPLOT")) != NULL ) {
        !           449:                 strcat( path, p ) ;
        !           450:                 strcat( path, "/" ) ;
        !           451:                 }
        !           452:             strcat( path, "gnuplot" ) ;
        !           453:             system( path ) ;
        !           454:             }
        !           455:             break ;
        !           456:
        !           457:         case IDM_PRINT :    /* print plot */
        !           458:
        !           459:             if( SetupPrinter( hWnd, &qPrintData ) ) {
        !           460:                             WinPostMsg( hWnd,
        !           461:                             WM_USER_PRINT_BEGIN,
        !           462:                             (MPARAM) &qPrintData,
        !           463:                             (MPARAM) hpsScreen ) ;
        !           464:                             }
        !           465:             break ;
        !           466:
        !           467:         case IDM_PRINTSETUP :    /* select printer */
        !           468:
        !           469:             WinDlgBox( HWND_DESKTOP,
        !           470:                        hWnd ,
        !           471:                        (PFNWP)QPrintersDlgProc,
        !           472:                        0L,
        !           473:                        IDD_QUERYPRINT,
        !           474:                        qPrintData.szPrinterName ) ;
        !           475:             break ;
        !           476:
        !           477:         case IDM_LINES_THICK:
        !           478:                 // change line setting
        !           479:             bWideLines = !bWideLines ;
        !           480:             ChangeCheck( hWnd, IDM_LINES_THICK, bWideLines?IDM_LINES_THICK:0 ) ;
        !           481:             WinInvalidateRect( hWnd, NULL, TRUE ) ;
        !           482:             break ;
        !           483:
        !           484:         case IDM_LINES_SOLID:
        !           485:                 // change line setting
        !           486:             bLineTypes = !bLineTypes ;
        !           487:             ChangeCheck( hWnd, IDM_LINES_SOLID, bLineTypes?0:IDM_LINES_SOLID ) ;
        !           488:             EditLineTypes( hWnd, hpsScreen, bLineTypes ) ;
        !           489:             WinInvalidateRect( hWnd, NULL, TRUE ) ;
        !           490:             break ;
        !           491:
        !           492:         case IDM_COLOURS:
        !           493:                 // change colour setting
        !           494:             bColours = !bColours ;
        !           495:             ChangeCheck( hWnd, IDM_COLOURS, bColours?IDM_COLOURS:0 ) ;
        !           496:             WinInvalidateRect( hWnd, NULL, TRUE ) ;
        !           497:             break ;
        !           498:
        !           499:         case IDM_FRONT:
        !           500:                 /* toggle z-order forcing */
        !           501:             bPopFront = !bPopFront ;
        !           502:             ChangeCheck( hWnd, IDM_FRONT, bPopFront?IDM_FRONT:0 ) ;
        !           503:             break ;
        !           504:
        !           505:         case IDM_FONTS:
        !           506:
        !           507:             if( GetNewFont( hWnd, hpsScreen ) ) {
        !           508:                 bNewFont = TRUE ;
        !           509:                 WinInvalidateRect( hWnd, NULL, TRUE ) ;
        !           510:                 }
        !           511:             break ;
        !           512:
        !           513:         case IDM_SAVE :
        !           514:             SaveIni( hWnd ) ;
        !           515:             break ;
        !           516:
        !           517:         case IDM_COPY :         /* copy to clipboard */
        !           518:             if( WinOpenClipbrd( hab ) ) {
        !           519:                 CopyToClipBrd( hWnd ) ;
        !           520:                 }
        !           521:             else {
        !           522:                 WinMessageBox( HWND_DESKTOP,
        !           523:                                hWnd,
        !           524:                                "Can't open clipboard",
        !           525:                                APP_NAME,
        !           526:                                0,
        !           527:                                MB_OK | MB_ICONEXCLAMATION ) ;
        !           528:                 }
        !           529:             break ;
        !           530:
        !           531:         case IDM_CLEARCLIP :         /* clear clipboard */
        !           532:             if( WinOpenClipbrd( hab ) ) {
        !           533:                 WinEmptyClipbrd( hab ) ;
        !           534:                 WinCloseClipbrd( hab ) ;
        !           535:                 }
        !           536:             else {
        !           537:                 WinMessageBox( HWND_DESKTOP,
        !           538:                                hWnd,
        !           539:                                "Can't open clipboard",
        !           540:                                APP_NAME,
        !           541:                                0,
        !           542:                                MB_OK | MB_ICONEXCLAMATION ) ;
        !           543:                 }
        !           544:             break ;
        !           545:
        !           546:         case IDM_COMMAND:       /* go back to GNUPLOT command window */
        !           547:             WinSwitchToProgram( hSwitch ) ;
        !           548:             break ;
        !           549:
        !           550:         case IDM_CONTINUE:
        !           551:             WinPostMsg( hWnd, WM_PAUSEEND, (MPARAM)1L, (MPARAM)0L ) ;
        !           552:             WinEnableMenuItem( WinWindowFromID(
        !           553:                                WinQueryWindow( hWnd, QW_PARENT ), FID_MENU ),
        !           554:                                IDM_CONTINUE,
        !           555:                                FALSE ) ;
        !           556:             break ;
        !           557:
        !           558:         case IDM_PAUSEGNU:  /* gnuplot handles pause */
        !           559:             ChangeCheck( hWnd, ulPauseItem, IDM_PAUSEGNU ) ;
        !           560:             ulPauseItem = IDM_PAUSEGNU ;
        !           561:             ulPauseMode = PAUSE_GNU ;
        !           562:             break ;
        !           563:
        !           564:         case IDM_PAUSEDLG:  /* pause message in dlg box */
        !           565:             ChangeCheck( hWnd, ulPauseItem, IDM_PAUSEDLG ) ;
        !           566:             ulPauseItem = IDM_PAUSEDLG ;
        !           567:             ulPauseMode = PAUSE_DLG ;
        !           568:             break ;
        !           569:
        !           570:         case IDM_PAUSEBTN:  /* pause uses menu button, no message */
        !           571:             ChangeCheck( hWnd, ulPauseItem, IDM_PAUSEBTN ) ;
        !           572:             ulPauseItem = IDM_PAUSEBTN ;
        !           573:             ulPauseMode = PAUSE_BTN ;
        !           574:             break ;
        !           575:
        !           576:         case IDM_HELPFORHELP:
        !           577:             WinSendMsg(WinQueryHelpInstance(hWnd),
        !           578:                        HM_DISPLAY_HELP, 0L, 0L ) ;
        !           579:             return 0L ;
        !           580:
        !           581:         case IDM_EXTENDEDHELP:
        !           582:             WinSendMsg(WinQueryHelpInstance(hWnd),
        !           583:                         HM_EXT_HELP, 0L, 0L);
        !           584:             return 0L ;
        !           585:
        !           586:         case IDM_KEYSHELP:
        !           587:             WinSendMsg(WinQueryHelpInstance(hWnd),
        !           588:                        HM_KEYS_HELP, 0L, 0L);
        !           589:             return 0L ;
        !           590:
        !           591:         case IDM_HELPINDEX:
        !           592:             WinSendMsg(WinQueryHelpInstance(hWnd),
        !           593:                        HM_HELP_INDEX, 0L, 0L);
        !           594:             return 0L ;
        !           595:
        !           596:         default :
        !           597:
        !           598:             return WinDefWindowProc( hWnd, message, mp1, mp2 ) ;
        !           599:
        !           600:         }
        !           601:     return( NULL ) ;
        !           602:     }
        !           603:
        !           604: void ChangeCheck( HWND hWnd , USHORT wItem1 , USHORT wItem2 )
        !           605: /*
        !           606: **  Utility function:
        !           607: **
        !           608: **  move check mark from menu item 1 to item 2
        !           609: */
        !           610:     {
        !           611:     HWND hMenu ;
        !           612:
        !           613:     hMenu = WinWindowFromID( WinQueryWindow( hWnd, QW_PARENT ),
        !           614:                              FID_MENU ) ;
        !           615:     if( wItem1 != 0 )
        !           616:         WinSendMsg( hMenu,
        !           617:                     MM_SETITEMATTR,
        !           618:                     MPFROM2SHORT( wItem1, TRUE ),
        !           619:                     MPFROM2SHORT( MIA_CHECKED, 0 ) ) ;
        !           620:     if( wItem2 != 0 )
        !           621:         WinSendMsg( hMenu,
        !           622:                     MM_SETITEMATTR,
        !           623:                     MPFROM2SHORT( wItem2, TRUE ),
        !           624:                     MPFROM2SHORT( MIA_CHECKED, MIA_CHECKED ) ) ;
        !           625:     }
        !           626:
        !           627: static void CopyToClipBrd( HWND hWnd )
        !           628: /*
        !           629: **  Copy window to clipboard as bitmap.
        !           630: */
        !           631:     {
        !           632:     HAB hab ;
        !           633:     HBITMAP hbm ;
        !           634:     HMF     hmf ;
        !           635:
        !           636:     hab = WinQueryAnchorBlock( hWnd ) ;
        !           637:     WinEmptyClipbrd( hab ) ;
        !           638:     hbm = CopyToBitmap( hpsScreen ) ;
        !           639:     WinSetClipbrdData( hab, (ULONG) hbm, CF_BITMAP, CFI_HANDLE) ;
        !           640:     hmf = CopyToMetaFile( hpsScreen ) ;
        !           641:     WinSetClipbrdData( hab, (ULONG) hmf, CF_METAFILE, CFI_HANDLE) ;
        !           642:     WinCloseClipbrd( hab ) ;
        !           643:     }
        !           644:
        !           645: HBITMAP CopyToBitmap( HPS hps )
        !           646: /*
        !           647: **  Copy ps to a bitmap.
        !           648: */
        !           649:     {
        !           650:     HPS     hpsMem ;
        !           651:     HWND    hwnd ;
        !           652:     HAB     hab ;
        !           653:     PSZ     psz[4] = {NULL,"Display",NULL,NULL} ;
        !           654:     HDC     hdcMem, hdcScr ;
        !           655:     SIZEL   sizel ;
        !           656:     BITMAPINFOHEADER2 bmp ;
        !           657:     PBITMAPINFO2 pbmi ;
        !           658:     HBITMAP hbm ;
        !           659:     BYTE    abBmp[80] ;
        !           660:     LONG    alData[2] ;
        !           661:     RECTL   rectl ;
        !           662:     POINTL  aptl[6] ;
        !           663:     HMF     hmf ;
        !           664:
        !           665:     hdcScr = GpiQueryDevice( hps ) ;
        !           666:     hwnd = WinWindowFromDC( hdcScr ) ;
        !           667:     hab = WinQueryAnchorBlock( hwnd ) ;
        !           668:     hdcMem = DevOpenDC( hab,
        !           669:                         OD_MEMORY,
        !           670:                         "*",
        !           671:                         4L,
        !           672:                         (PDEVOPENDATA) psz,
        !           673:                         hdcScr ) ;
        !           674:     sizel.cx = 0/*GNUPAGE*/ ; sizel.cy = 0/*GNUPAGE*/ ;
        !           675:     hpsMem = GpiCreatePS( hab, hdcMem, &sizel, PU_PELS|GPIA_ASSOC|GPIT_MICRO ) ;
        !           676:     GpiQueryDeviceBitmapFormats( hpsMem, 2L, alData ) ;
        !           677:     WinQueryWindowRect( hwnd, &rectl ) ;
        !           678:     memset( &bmp, 0, sizeof(bmp) ) ;
        !           679:     bmp.cbFix = (ULONG) sizeof( bmp ) ;
        !           680:     bmp.cx = (SHORT) (rectl.xRight-rectl.xLeft) ;
        !           681:     bmp.cy = (SHORT) (rectl.yTop-rectl.yBottom) ;
        !           682:     bmp.cPlanes = alData[0] ;
        !           683:     bmp.cBitCount = alData[1] ;
        !           684:     hbm = GpiCreateBitmap( hpsMem, &bmp, 0, NULL, NULL ) ;
        !           685:     GpiSetBitmap( hpsMem, hbm ) ;
        !           686:     aptl[0].x = 0 ; aptl[0].y = 0 ;
        !           687:     aptl[1].x = (LONG)bmp.cx ; aptl[1].y = (LONG)bmp.cy ;
        !           688:     aptl[2].x = 0 ; aptl[2].y = 0 ;
        !           689:     GpiBitBlt( hpsMem, hps, 3L, aptl, ROP_SRCCOPY, BBO_IGNORE ) ;
        !           690:     GpiDestroyPS( hpsMem ) ;
        !           691:     DevCloseDC( hdcMem ) ;
        !           692:     return hbm ;
        !           693:     }
        !           694:
        !           695: HMF CopyToMetaFile( HPS hps )
        !           696: /*
        !           697: **  Copy ps to a mteafile.
        !           698: */
        !           699:     {
        !           700:     HDC hdcMF, hdcOld ;
        !           701:     HAB hab ;
        !           702:     HWND hwnd ;
        !           703:     PSZ psz[4] = {NULL,"Display",NULL,NULL} ;
        !           704:     HMF hmf ;
        !           705:     hdcOld = GpiQueryDevice( hps ) ;
        !           706:     hwnd = WinWindowFromDC( hdcOld ) ;
        !           707:     hab = WinQueryAnchorBlock( hwnd ) ;
        !           708:     hdcMF = DevOpenDC( hab, OD_METAFILE, "*", 4L, psz, hdcOld ) ;
        !           709:     DosRequestMutexSem( semHpsAccess, (ULONG) SEM_INDEFINITE_WAIT ) ;
        !           710:     GpiSetDrawingMode( hps, DM_DRAW ) ;
        !           711:     GpiAssociate( hps, 0 ) ;
        !           712:     GpiAssociate( hps, hdcMF ) ;
        !           713:     ScalePS( hps ) ;
        !           714:     GpiDrawChain( hps ) ;
        !           715:     GpiAssociate( hps, 0 ) ;
        !           716:     GpiAssociate( hps, hdcOld ) ;
        !           717:     DosReleaseMutexSem( semHpsAccess ) ;
        !           718:     hmf = DevCloseDC( hdcMF ) ;
        !           719:     return hmf ;
        !           720:     }
        !           721:
        !           722: BOOL QueryIni( HAB hab )
        !           723: /*
        !           724: ** Query INI file
        !           725: */
        !           726:     {
        !           727:     BOOL         bPos, bData, bSwp  ;
        !           728:     ULONG        ulOpts[5] ;
        !           729:     HINI         hini ;
        !           730:     ULONG        ulCB ;
        !           731:     char         *p ;
        !           732:     static SWP   pauseswp ;
        !           733:
        !           734:             // read gnuplot ini file
        !           735:
        !           736:     hini = PrfOpenProfile( hab, szIniFile ) ;
        !           737:     ulCB = sizeof( ulShellPos ) ;
        !           738:     bPos = PrfQueryProfileData( hini, APP_NAME, INISHELLPOS, &ulShellPos, &ulCB ) ;
        !           739:     ulCB = sizeof( SWP ) ;
        !           740:     bSwp = PrfQueryProfileData( hini, APP_NAME, INIPAUSEPOS, &pauseswp, &ulCB ) ;
        !           741:     if( bSwp ) pausedata.pswp = &pauseswp ;
        !           742:     ulCB = sizeof( ulOpts ) ;
        !           743:     bData = PrfQueryProfileData( hini, APP_NAME, INIOPTS, &ulOpts, &ulCB ) ;
        !           744:     if( bData ) {
        !           745:         bLineTypes = (BOOL)ulOpts[0] ;
        !           746:         bWideLines = (BOOL)ulOpts[1] ;
        !           747:         bColours = (BOOL)ulOpts[2] ;
        !           748:         ulPauseMode = ulOpts[3] ;
        !           749:         bPopFront = (BOOL)ulOpts[4] ;
        !           750:         }
        !           751:     else {
        !           752:         bLineTypes = FALSE ;  /* default values */
        !           753:      /*   bWideLines = FALSE ; */
        !           754:         bColours = TRUE ;
        !           755:         bPopFront = TRUE ;
        !           756:         ulPauseMode = 1 ;
        !           757:         }
        !           758:     ulCB = 4*sizeof(float) ;
        !           759:     PrfQueryProfileData( hini, APP_NAME, INIFRAC, &qPrintData.xsize, &ulCB ) ;
        !           760:     if( PrfQueryProfileSize( hini, APP_NAME, INIPRDRIV, &ulCB ) ) {
        !           761:         PDRIVDATA pdriv = (PDRIVDATA) malloc( ulCB ) ;
        !           762:         if( pdriv != NULL ) {
        !           763:             PrfQueryProfileData( hini, APP_NAME, INIPRDRIV, pdriv, &ulCB ) ;
        !           764:             qPrintData.pdriv = pdriv ;
        !           765:             qPrintData.cbpdriv = ulCB ;
        !           766:             }
        !           767:         }
        !           768:     PrfQueryProfileString( hini, APP_NAME, INIPRPR, "",
        !           769:                            qPrintData.szPrinterName,
        !           770:                            (long) sizeof qPrintData.szPrinterName ) ;
        !           771:     PrfQueryProfileString( hini, APP_NAME, INIFONT, INITIAL_FONT,
        !           772:                              szFontNameSize, FONTBUF ) ;
        !           773:     ulCB = sizeof( ulOpts ) ;
        !           774:     bData = PrfQueryProfileData( hini, APP_NAME, INICHAR, &ulOpts, &ulCB ) ;
        !           775:     if( bData ) {
        !           776:         lCharWidth = ulOpts[0] ;
        !           777:         lCharHeight = ulOpts[1] ;
        !           778:         }
        !           779:     else {
        !           780:         lCharWidth = 217 ;
        !           781:         lCharHeight = 465 ;
        !           782:         }
        !           783:     PrfCloseProfile( hini ) ;
        !           784:
        !           785:     if( qPrintData.szPrinterName[0] == '\0' ) {
        !           786:             // get default printer name
        !           787:         PrfQueryProfileString( HINI_PROFILE,
        !           788:                                "PM_SPOOLER",
        !           789:                                "PRINTER",
        !           790:                                ";",
        !           791:                                qPrintData.szPrinterName,
        !           792:                                (long) sizeof qPrintData.szPrinterName ) ;
        !           793:         if( (p=strchr( qPrintData.szPrinterName, ';' )) != NULL ) *p = '\0' ;
        !           794:         }
        !           795:     bShellPos = bPos ;
        !           796:     return bPos ;
        !           797:     }
        !           798:
        !           799: static void SaveIni( HWND hWnd )
        !           800: /*
        !           801: ** save data in ini file
        !           802: */
        !           803:     {
        !           804:     SWP     swp ;
        !           805:     HINI    hini ;
        !           806:     ULONG   ulOpts[5] ;
        !           807:     HFILE   hfile ;
        !           808:     ULONG   ulAct ;
        !           809:     ERRORID errid ;
        !           810:     char    achErr[64] ;
        !           811:     HAB     hab ;
        !           812:
        !           813:     hab = WinQueryAnchorBlock( hWnd ) ;
        !           814:     hini = PrfOpenProfile( hab, szIniFile ) ;
        !           815:     if( hini != NULLHANDLE ) {
        !           816:         WinQueryWindowPos( hwndFrame, &swp ) ;
        !           817:         ulPlotPos[0] = swp.x ;
        !           818:         ulPlotPos[1] = swp.y ;
        !           819:         ulPlotPos[2] = swp.cx ;
        !           820:         ulPlotPos[3] = swp.cy ;
        !           821:         PrfWriteProfileData( hini, APP_NAME, INISHELLPOS, &ulPlotPos, sizeof(ulPlotPos) ) ;
        !           822:         if( pausedata.pswp != NULL )
        !           823:             PrfWriteProfileData( hini, APP_NAME, INIPAUSEPOS,
        !           824:                                  pausedata.pswp, sizeof(SWP) ) ;
        !           825:         ulOpts[0] = (ULONG)bLineTypes ;
        !           826:         ulOpts[1] = (ULONG)bWideLines ;
        !           827:         ulOpts[2] = (ULONG)bColours ;
        !           828:         ulOpts[3] = ulPauseMode ;
        !           829:         ulOpts[4] = (ULONG)bPopFront ;
        !           830:         PrfWriteProfileData( hini, APP_NAME, INIOPTS, &ulOpts, sizeof(ulOpts) ) ;
        !           831:         PrfWriteProfileData( hini, APP_NAME, INIFRAC, &qPrintData.xsize, 4*sizeof(float) ) ;
        !           832:         if( qPrintData.pdriv != NULL )
        !           833:             PrfWriteProfileData( hini, APP_NAME, INIPRDRIV, qPrintData.pdriv,
        !           834:                                  qPrintData.cbpdriv ) ;
        !           835:         PrfWriteProfileString( hini, APP_NAME, INIPRPR,
        !           836:                                qPrintData.szPrinterName[0] == '\0'? NULL:
        !           837:                                qPrintData.szPrinterName ) ;
        !           838:         PrfWriteProfileString( hini, APP_NAME, INIFONT, szFontNameSize ) ;
        !           839:         ulOpts[0] = (ULONG)lCharWidth ;
        !           840:         ulOpts[1] = (ULONG)lCharHeight ;
        !           841:         PrfWriteProfileData( hini, APP_NAME, INICHAR, &ulOpts, sizeof(ulOpts) ) ;
        !           842:         PrfCloseProfile( hini ) ;
        !           843:         }
        !           844:     else {
        !           845:         WinMessageBox( HWND_DESKTOP,
        !           846:                        HWND_DESKTOP,
        !           847:                        "Can't write ini file",
        !           848:                        APP_NAME,
        !           849:                        0,
        !           850:                        MB_OK | MB_ICONEXCLAMATION ) ;
        !           851:         }
        !           852:     }
        !           853:
        !           854: static void DoPaint( HWND hWnd, HPS hps  )
        !           855: /*
        !           856: **  Paint the screen with current data
        !           857: */
        !           858:     {
        !           859:     ULONG ulCount ;
        !           860:
        !           861:     static RECTL rectl ;
        !           862:     if( tidDraw != 0 ) {
        !           863:             /* already drawing - stop it; include the rectl now
        !           864:                being drawn in, in the update region; and return
        !           865:                without calling beginpaint so that the paint
        !           866:                message is resent */
        !           867:         GpiSetStopDraw( hpsScreen, SDW_ON ) ;
        !           868:         DosSleep(1) ;
        !           869:         WinInvalidateRect( hWnd, &rectl, TRUE ) ;
        !           870:         return ;
        !           871:         }
        !           872:             /* winbeginpaint here, so paint message is
        !           873:                not resent when we return, then spawn a
        !           874:                thread to do the drawing */
        !           875:     WinBeginPaint( hWnd, hps, &rectl ) ;                 //rl
        !           876:     tidDraw = _beginthread( ThreadDraw, NULL, 32768, NULL ) ;
        !           877:     }
        !           878:
        !           879: static void ThreadDraw( void* arg )
        !           880: /*
        !           881: **  Thread to draw plot on screen
        !           882: */
        !           883:     {
        !           884:     HAB     hab ;
        !           885:
        !           886:     hab = WinInitialize( 0 ) ;
        !           887:
        !           888:     InitScreenPS() ;
        !           889:
        !           890:     DosRequestMutexSem( semHpsAccess, (ULONG) SEM_INDEFINITE_WAIT ) ;
        !           891:     ScalePS( hpsScreen ) ;
        !           892:     GpiSetStopDraw( hpsScreen, SDW_OFF ) ;
        !           893:     GpiSetDrawingMode( hpsScreen, DM_DRAW ) ;
        !           894:     GpiDrawChain( hpsScreen ) ;
        !           895:     WinEndPaint( hpsScreen ) ;
        !           896:     DosReleaseMutexSem( semHpsAccess ) ;
        !           897:     WinTerminate( hab ) ;
        !           898:     tidDraw = 0 ;
        !           899:     }
        !           900:
        !           901: HPS InitScreenPS()
        !           902: /*
        !           903: ** Initialise the screen ps for drawing
        !           904: */
        !           905:     {
        !           906:     RECTL   rectClient ;
        !           907:     int     nColour = 0 ;
        !           908:
        !           909:     GpiResetPS( hpsScreen, GRES_ATTRS ) ;
        !           910:     GpiErase(hpsScreen);
        !           911:
        !           912:     WinQueryWindowRect( hApp, (PRECTL)&rectClient ) ;
        !           913:     {
        !           914:     double ratio = 1.560 ;
        !           915:     double xs = rectClient.xRight - rectClient.xLeft ;
        !           916:     double ys = rectClient.yTop - rectClient.yBottom ;
        !           917:     if( ys > xs/ratio ) { /* reduce ys to fit */
        !           918:         rectClient.yTop = rectClient.yBottom + (int)(xs/ratio) ;
        !           919:         }
        !           920:     else if( ys < xs/ratio ) { /* reduce xs to fit */
        !           921:         rectClient.xRight = rectClient.xLeft + (int)(ys*ratio) ;
        !           922:         }
        !           923:     }
        !           924:
        !           925:     GpiSetPageViewport( hpsScreen, &rectClient ) ;
        !           926:     if( !bColours ) {
        !           927:         int i ;
        !           928:         for( i=0; i<8; i++ ) alColourTable[i] = 0 ;
        !           929:         for( i=8; i<16; i++ ) alColourTable[i] = 0 ;
        !           930:         alColourTable[0] = 0xFFFFFF ;
        !           931:         nColour = 16 ;
        !           932:         }
        !           933:     GpiCreateLogColorTable( hpsScreen,
        !           934:                             LCOL_RESET,
        !           935:                             LCOLF_CONSECRGB,
        !           936:                             0, nColour, alColourTable ) ;
        !           937:     return hpsScreen ;
        !           938:     }
        !           939:
        !           940: enum JUSTIFY { LEFT, CENTRE, RIGHT } jmode;
        !           941:
        !           942:
        !           943: short ScalePS( HPS hps )
        !           944: /*
        !           945: **  Get a font to use
        !           946: **  Scale the plot area to world coords for subsequent plotting
        !           947: */
        !           948:     {
        !           949:     RECTL rectView ;
        !           950:
        !           951:     SelectFont( hps, szFontNameSize ) ;
        !           952:     return 0 ;
        !           953:     }
        !           954:
        !           955: static SIZEF sizBaseSubSup ;
        !           956: static SIZEF sizCurSubSup ;
        !           957: static SIZEF sizCurFont ;
        !           958: static long lVOffset = 0 ;
        !           959: static SIZEF sizBaseFont ;
        !           960: static struct _ft {
        !           961:     char *name ;
        !           962:     LONG  lcid ;
        !           963:     } tabFont[256] = {{NULL,0L}, {NULL}};
        !           964:
        !           965: void SelectFont( HPS hps, char *szFontNameSize )
        !           966: /*
        !           967: **  Select a named and sized outline (adobe) font
        !           968: */
        !           969:     {
        !           970:      HDC    hdc ;
        !           971:      FATTRS  fat ;
        !           972:      LONG   xDeviceRes, yDeviceRes ;
        !           973:      POINTL ptlFont ;
        !           974:      SIZEF  sizfx ;
        !           975:      static LONG lcid = 0L ;
        !           976:      static char *szFontName ;
        !           977:      static short shPointSize ;
        !           978:
        !           979:      sscanf( szFontNameSize, "%hd", &shPointSize ) ;
        !           980:      szFontName = strchr( szFontNameSize, '.' ) + 1 ;
        !           981:
        !           982:      fat.usRecordLength  = sizeof fat ;
        !           983:      fat.fsSelection     = 0 ;
        !           984:      fat.lMatch          = 0 ;
        !           985:      fat.idRegistry      = 0 ;
        !           986:      fat.usCodePage      = 0 ; //GpiQueryCp (hps) ;
        !           987:      fat.lMaxBaselineExt = 0 ;
        !           988:      fat.lAveCharWidth   = 0 ;
        !           989:      fat.fsType          = 0 ;
        !           990:      fat.fsFontUse       = FATTR_FONTUSE_OUTLINE |
        !           991:                            FATTR_FONTUSE_TRANSFORMABLE ;
        !           992:
        !           993:      strcpy (fat.szFacename, szFontName) ;
        !           994:
        !           995:      if(tabFont[0].name !=NULL) free( tabFont[0].name ) ;
        !           996:      tabFont[0].name = strdup( szFontName ) ;
        !           997:      tabFont[0].lcid = 10L ;
        !           998:
        !           999:      lcid = GpiQueryCharSet( hps ) ;
        !          1000:      if( lcid != 10L ) lcid = 10L ;
        !          1001:      else {
        !          1002:         GpiSetCharSet( hps, 0L) ;
        !          1003:         GpiDeleteSetId( hps, lcid ) ;
        !          1004:         }
        !          1005:      GpiCreateLogFont (hps, NULL, lcid, &fat) ;
        !          1006:      GpiSetCharSet( hps, lcid ) ;
        !          1007:
        !          1008:      hdc = GpiQueryDevice (hps) ;
        !          1009:
        !          1010:      DevQueryCaps (hdc, CAPS_HORIZONTAL_RESOLUTION, 1L, &xDeviceRes) ;
        !          1011:      DevQueryCaps (hdc, CAPS_VERTICAL_RESOLUTION,   1L, &yDeviceRes) ;
        !          1012:
        !          1013:                          // Find desired font size in pixels
        !          1014:
        !          1015:      ptlFont.x = 2540L * (long)shPointSize / 72L ;
        !          1016:      ptlFont.y = 2540L * (long)shPointSize / 72L ;
        !          1017:
        !          1018:                          // Set the character box
        !          1019:
        !          1020:      sizfx.cx = MAKEFIXED (ptlFont.x, 0) ;
        !          1021:      sizfx.cy = MAKEFIXED (ptlFont.y, 0) ;
        !          1022:      lVOffset = ptlFont.y ;
        !          1023:
        !          1024:      sizBaseFont = sizfx ;
        !          1025:      GpiSetCharBox (hps, &sizfx) ;
        !          1026:
        !          1027:                         // set up some useful globals
        !          1028:      {
        !          1029:      FONTMETRICS fm ;
        !          1030:      GpiQueryFontMetrics( hps, sizeof(FONTMETRICS), &fm ) ;
        !          1031:      lBaseSubOffset = -fm.lSubscriptYOffset ;
        !          1032:      lBaseSupOffset = fm.lSuperscriptYOffset ;
        !          1033:      lSubOffset = lBaseSubOffset ;
        !          1034:      lSupOffset = lBaseSupOffset ;
        !          1035:      lCharHeight = fm.lMaxAscender*1.2 ;
        !          1036:      lCharWidth  = fm.lAveCharWidth ;
        !          1037:      sizBaseSubSup.cx = MAKEFIXED( ptlFont.x*0.7, 0 ) ;
        !          1038:      sizBaseSubSup.cy = MAKEFIXED( ptlFont.y*0.7, 0 ) ;
        !          1039:      }
        !          1040:      sizCurFont = sizBaseFont ;
        !          1041:      sizCurSubSup = sizBaseSubSup ;
        !          1042:     if( bNewFont ) {
        !          1043: //        EditCharCell( hps, &sizfx ) ;
        !          1044:         bNewFont = FALSE ;
        !          1045:         }
        !          1046:     }
        !          1047:
        !          1048: void SwapFont( HPS hps, char *szFNS )
        !          1049: /*
        !          1050: **  Select a named and sized outline (adobe) font
        !          1051: */
        !          1052:     {
        !          1053:      HDC    hdc ;
        !          1054:      FATTRS  fat ;
        !          1055:      LONG   xDeviceRes, yDeviceRes ;
        !          1056:      POINTL ptlFont ;
        !          1057:      SIZEF  sizfx ;
        !          1058:      static LONG lcid = 0L ;
        !          1059:      static int itab = 1 ;
        !          1060:      static char *szFontName ;
        !          1061:      static short shPointSize ;
        !          1062:
        !          1063:      if( szFNS == NULL ) {    /* restore base font */
        !          1064:          sizCurFont = sizBaseFont ;
        !          1065:          sizCurSubSup = sizBaseSubSup ;
        !          1066:          lSubOffset = lBaseSubOffset ;
        !          1067:          lSupOffset = lBaseSupOffset ;
        !          1068:          GpiSetCharSet( hps, 10 ) ;
        !          1069:          GpiSetCharBox (hps, &sizBaseFont) ;
        !          1070:         }
        !          1071:      else {
        !          1072:         sscanf( szFNS, "%hd", &shPointSize ) ;
        !          1073:         szFontName = strchr( szFNS, '.' ) + 1 ;
        !          1074:
        !          1075:         {
        !          1076:             int i ;
        !          1077:             lcid = 0 ;
        !          1078:             for(i=0;i<itab;i++) {
        !          1079:                 if( strcmp( szFontName, tabFont[i].name ) == 0 ) {
        !          1080:                     lcid = tabFont[i].lcid ;
        !          1081:                     break ;
        !          1082:                     }
        !          1083:                 }
        !          1084:         }
        !          1085:         if( lcid == 0 ) {
        !          1086:
        !          1087:         fat.usRecordLength  = sizeof fat ;
        !          1088:         fat.fsSelection     = 0 ;
        !          1089:         fat.lMatch          = 0 ;
        !          1090:         fat.idRegistry      = 0 ;
        !          1091:         fat.usCodePage      = 0 ; //GpiQueryCp (hps) ;
        !          1092:         fat.lMaxBaselineExt = 0 ;
        !          1093:         fat.lAveCharWidth   = 0 ;
        !          1094:         fat.fsType          = 0 ;
        !          1095:         fat.fsFontUse       = FATTR_FONTUSE_OUTLINE |
        !          1096:                                FATTR_FONTUSE_TRANSFORMABLE ;
        !          1097:
        !          1098:         strcpy (fat.szFacename, szFontName) ;
        !          1099:
        !          1100:
        !          1101:         tabFont[itab].name = strdup( szFontName ) ;
        !          1102:         lcid = itab+10 ;
        !          1103:         tabFont[itab].lcid = lcid ;
        !          1104:         ++itab ;
        !          1105:
        !          1106: //        lcid = 11L ;
        !          1107:         GpiSetCharSet( hps, 0L) ;
        !          1108:         GpiDeleteSetId( hps, lcid ) ;
        !          1109:         GpiCreateLogFont (hps, NULL, lcid, &fat) ;
        !          1110:         }
        !          1111:         GpiSetCharSet( hps, lcid ) ;
        !          1112:      hdc = GpiQueryDevice (hps) ;
        !          1113:
        !          1114:      DevQueryCaps (hdc, CAPS_HORIZONTAL_RESOLUTION, 1L, &xDeviceRes) ;
        !          1115:      DevQueryCaps (hdc, CAPS_VERTICAL_RESOLUTION,   1L, &yDeviceRes) ;
        !          1116:
        !          1117:                          // Find desired font size in pixels
        !          1118:
        !          1119:      ptlFont.x = 2540L * (long)shPointSize / 72L ;
        !          1120:      ptlFont.y = 2540L * (long)shPointSize / 72L ;
        !          1121:
        !          1122:                          // Set the character box
        !          1123:
        !          1124:      sizCurFont.cx = MAKEFIXED (ptlFont.x, 0) ;
        !          1125:      sizCurFont.cy = MAKEFIXED (ptlFont.y, 0) ;
        !          1126: //     lVOffset = ptlFont.y ;
        !          1127:
        !          1128:      GpiSetCharBox (hps, &sizCurFont) ;
        !          1129:      sizCurSubSup.cx = MAKEFIXED( ptlFont.x*0.7, 0 ) ;
        !          1130:      sizCurSubSup.cy = MAKEFIXED( ptlFont.y*0.7, 0 ) ;
        !          1131:
        !          1132:                         // set up some useful globals
        !          1133:      {
        !          1134:      FONTMETRICS fm ;
        !          1135:      GpiQueryFontMetrics( hps, sizeof(FONTMETRICS), &fm ) ;
        !          1136:      lSubOffset = -fm.lSubscriptYOffset ;
        !          1137:      lSupOffset = fm.lSuperscriptYOffset ;
        !          1138:      }
        !          1139:         }
        !          1140:
        !          1141:      }
        !          1142:
        !          1143: static void ReadGnu( void* arg )
        !          1144: /*
        !          1145: ** Thread to read plot commands from  GNUPLOT pm driver.
        !          1146: ** Opens named pipe, then clears semaphore to allow GNUPLOT driver to proceed.
        !          1147: ** Reads commands and builds a command list.
        !          1148: */
        !          1149:     {
        !          1150:     HPIPE    hRead = 0L ;
        !          1151:     POINTL ptl ;
        !          1152:     POINTL aptl[4] ;
        !          1153:     long lCurCol ;
        !          1154:     long lOldLine = 0 ;
        !          1155:     BOOL bBW = FALSE ; /* passed frpm print.c ?? */
        !          1156:     BOOL bPath = FALSE ;
        !          1157:     BOOL bDots = FALSE ;
        !          1158:     char *szEnv ;
        !          1159:     char *szFileBuf ;
        !          1160:     ULONG rc;
        !          1161:     USHORT usErr ;
        !          1162:     ULONG cbR ;
        !          1163:     USHORT i ;
        !          1164:     PID ppid ;
        !          1165:     unsigned char buff[2] ;
        !          1166:     HEV hev ;
        !          1167:     static char *szPauseText = NULL ;
        !          1168:     ULONG ulPause ;
        !          1169:     char *pszPipeName, *pszSemName ;
        !          1170:     LONG  commands[4] ;
        !          1171:     HPS hps ;
        !          1172:     HAB hab ;
        !          1173:     int linewidth = DEFLW ;
        !          1174:
        !          1175:     hab = WinInitialize( 0 ) ;
        !          1176:     DosEnterCritSec() ;
        !          1177:     pszPipeName = malloc( 256 ) ;
        !          1178:     pszSemName  = malloc( 256 ) ;
        !          1179:     DosExitCritSec() ;
        !          1180:     strcpy( pszPipeName, "\\pipe\\" ) ;
        !          1181:     strcpy( pszSemName, "\\sem32\\" ) ;
        !          1182:     strcat( pszPipeName, szIPCName ) ;
        !          1183:     strcat( pszSemName, szIPCName ) ;
        !          1184:
        !          1185:             /* open a named pipe for communication with gnuplot */
        !          1186:
        !          1187:     rc = DosCreateNPipe( pszPipeName,
        !          1188:                          &hRead,
        !          1189:                          NP_ACCESS_DUPLEX|NP_NOINHERIT|NP_NOWRITEBEHIND ,
        !          1190:                          1|NP_WAIT|NP_READMODE_MESSAGE|NP_TYPE_MESSAGE,
        !          1191:                          PIPEBUF,
        !          1192:                          PIPEBUF,
        !          1193:                          0xFFFFFFFF) ;
        !          1194:     hev = 0 ;       /* OK, gnuplot can try to open npipe ... */
        !          1195:     DosOpenEventSem( pszSemName, &hev ) ;
        !          1196:     DosPostEventSem( hev ) ;
        !          1197:
        !          1198:
        !          1199:
        !          1200:         /* attach to gnuplot */
        !          1201:
        !          1202: server:
        !          1203:
        !          1204:     if( DosConnectNPipe( hRead ) == 0L ) {
        !          1205:
        !          1206:         WinPostMsg( hSysMenu,
        !          1207:                     MM_SETITEMATTR,
        !          1208:                     MPFROM2SHORT(SC_CLOSE, TRUE ),
        !          1209:                     MPFROM2SHORT(MIA_DISABLED, MIA_DISABLED) ) ;
        !          1210:
        !          1211:         /* store graphics commands */
        !          1212:         /* use semaphore to prevent problems with drawing while reallocating
        !          1213:            the command buffers */
        !          1214:
        !          1215:         DosRead( hRead, &ppidGnu, 4, &cbR ) ;
        !          1216: //        DosPostEventSem( semStartSeq ) ;         /* once we've got pidGnu */
        !          1217:         WinPostMsg( hApp, WM_GPSTART, 0, 0 ) ;
        !          1218:
        !          1219:
        !          1220:         hps = hpsScreen ;
        !          1221:    InitScreenPS() ;
        !          1222:         while (1) {
        !          1223:
        !          1224:             usErr=BufRead(hRead,buff, 1, &cbR) ;
        !          1225:             if( usErr != 0 ) break ;
        !          1226:
        !          1227:             switch( *buff ) {
        !          1228:                 case 'G' :    /* enter graphics mode */
        !          1229:                     {
        !          1230:                     ULONG ulCount ;
        !          1231:
        !          1232:                     if( tidDraw != 0 ) {
        !          1233:                       /* already drawing - stop it */
        !          1234:                         GpiSetStopDraw( hpsScreen, SDW_ON ) ;
        !          1235:                         while(tidDraw != 0) DosSleep(1) ;
        !          1236:                         }
        !          1237:                    /* wait for access to command list and lock it */
        !          1238: //                    DosWaitEventSem( semDrawDone, SEM_INDEFINITE_WAIT ) ;
        !          1239: //                    DosEnterCritSec() ;
        !          1240:                     DosRequestMutexSem( semHpsAccess, (ULONG) SEM_INDEFINITE_WAIT ) ;
        !          1241:                     InitScreenPS() ;
        !          1242:                     ScalePS( hps ) ;
        !          1243: //                    DosResetEventSem( semDrawDone, &ulCount ) ;
        !          1244:                     GpiSetDrawingMode( hps, DM_DRAWANDRETAIN ) ;
        !          1245:                     for(i=1;i<=iSeg;i++)
        !          1246:                         GpiDeleteSegment( hps, i ) ;
        !          1247:                     iSeg = 1 ;
        !          1248:                     GpiOpenSegment( hps, iSeg ) ;
        !          1249: //                    DosExitCritSec() ;
        !          1250:                     GpiSetLineEnd( hps, LINEEND_ROUND ) ;
        !          1251:                     GpiSetLineWidthGeom( hps, linewidth ) ;
        !          1252:                     GpiSetCharBox (hps, &sizBaseFont) ;
        !          1253:                     }
        !          1254:                     break ;
        !          1255:
        !          1256:                 case 'Q' :     /* query terminal info */
        !          1257:                     DosWrite( hRead, &lCharWidth, sizeof(int), &cbR ) ;
        !          1258:                     DosWrite( hRead, &lCharHeight, sizeof(int), &cbR ) ;
        !          1259:                     break ;
        !          1260:
        !          1261:                 case 'E' :     /* leave graphics mode (graph completed) */
        !          1262:                     if( bPath ) {
        !          1263:                         GpiEndPath( hps ) ;
        !          1264:                         GpiStrokePath( hps, 1, 0 ) ;
        !          1265:                         bPath = FALSE ;
        !          1266:                         }
        !          1267:                     GpiCloseSegment( hps ) ;
        !          1268: //                    DosPostEventSem( semDrawDone ) ;
        !          1269:                     DosReleaseMutexSem( semHpsAccess ) ;
        !          1270:                     WinPostMsg( hApp, WM_GNUPLOT, 0L, 0L ) ;
        !          1271:                     break ;
        !          1272:
        !          1273:                 case 'R' :
        !          1274:                     /* gnuplot has reset drivers, allow user to kill this */
        !          1275:                     WinPostMsg( hSysMenu,
        !          1276:                                 MM_SETITEMATTR,
        !          1277:                                 MPFROM2SHORT(SC_CLOSE, TRUE ),
        !          1278:                                 MPFROM2SHORT(MIA_DISABLED, (USHORT)0 ) ) ;
        !          1279:                     /* if we are keeping us on the screen, wait for new connection */
        !          1280:                     if( bServer||bPersist ) {
        !          1281:                         DosDisConnectNPipe( hRead ) ;
        !          1282:                         goto server ;
        !          1283:                         }
        !          1284:                     break ;
        !          1285:
        !          1286:                 case 'r' :
        !          1287:                     /* resume after multiplot */
        !          1288:                     {
        !          1289:                     ULONG ulCount ;
        !          1290:                     DosRequestMutexSem( semHpsAccess, (ULONG) SEM_INDEFINITE_WAIT ) ;
        !          1291: //                    DosWaitEventSem( semDrawDone, SEM_INDEFINITE_WAIT ) ;
        !          1292:                     iSeg++ ;
        !          1293: //                    DosResetEventSem( semDrawDone, &ulCount ) ;
        !          1294:                     GpiSetDrawingMode( hps, DM_DRAWANDRETAIN ) ;
        !          1295:                     GpiOpenSegment( hps, iSeg ) ;
        !          1296:                     }
        !          1297:                     break ;
        !          1298:
        !          1299:                 case 's' :
        !          1300:                     /* suspend after multiplot */
        !          1301:                     break ;
        !          1302:
        !          1303:                 case 'M' :   /* move */
        !          1304:                 case 'V' :   /* draw vector */
        !          1305:                     if( *buff=='M' ) {
        !          1306:                         if( bPath ) {
        !          1307:                             GpiEndPath( hps ) ;
        !          1308:                             GpiStrokePath( hps, 1, 0 ) ;
        !          1309:                             bPath = FALSE ;
        !          1310:                             }
        !          1311:                         }
        !          1312:                     else {
        !          1313:                         if( bWideLines/*bWideLines*/ && !bPath ) {
        !          1314:                             GpiBeginPath( hps, 1 ) ;
        !          1315:                             bPath = TRUE ;
        !          1316:                             }
        !          1317:                         }
        !          1318:                     BufRead(hRead,&ptl.x, 2*sizeof(int), &cbR) ;
        !          1319:                     if( (*buff=='V') && bDots ) ptl.x += 5 ;
        !          1320:                     else if( (*buff=='M') && bDots ) ptl.x -= 5 ;
        !          1321:                     if( *buff == 'M' ) LMove( hps, &ptl ) ;
        !          1322:                     else LLine( hps, &ptl ) ;
        !          1323:                     break ;
        !          1324:
        !          1325:                 case 'P' :   /* pause */
        !          1326:                     {
        !          1327:                     int len ;
        !          1328:                     BufRead(hRead,&len, sizeof(int), &cbR) ;
        !          1329:                     len = (len+sizeof(int)-1)/sizeof(int) ;
        !          1330:                     if( len > 0 ){  /* get pause text */
        !          1331:                         DosEnterCritSec() ;
        !          1332:                         szPauseText = malloc( len*sizeof(int) ) ;
        !          1333:                         DosExitCritSec() ;
        !          1334:                         BufRead(hRead,szPauseText, len*sizeof(int), &cbR) ;
        !          1335:                         }
        !          1336:                     if( ulPauseMode != PAUSE_GNU ) {
        !          1337:                              /* pause and wait for semaphore to be cleared */
        !          1338:                         DosResetEventSem( semPause, &ulPause ) ;
        !          1339:                         WinPostMsg( hApp, WM_PAUSEPLOT, (MPARAM) szPauseText, 0L ) ;
        !          1340:                         DosWaitEventSem( semPause, SEM_INDEFINITE_WAIT ) ;
        !          1341:                         }
        !          1342:                     else { /* gnuplot handles pause */
        !          1343:                         ulPauseReply = 2 ;
        !          1344:                         }
        !          1345:                     DosEnterCritSec() ;
        !          1346:                     if( szPauseText != NULL ) free( szPauseText ) ;
        !          1347:                     szPauseText = NULL ;
        !          1348:                     DosExitCritSec() ;
        !          1349:                              /* reply to gnuplot so it can continue */
        !          1350:                     DosWrite( hRead, &ulPauseReply, sizeof(int), &cbR ) ;
        !          1351:                     }
        !          1352:                     break ;
        !          1353:
        !          1354:                 case 'T' :   /* write text */
        !          1355:                         /* read x, y, len */
        !          1356:                     if( bPath ) {
        !          1357:                         GpiEndPath( hps ) ;
        !          1358:                         GpiStrokePath( hps, 1, 0 ) ;
        !          1359:                         bPath = FALSE ;
        !          1360:                         }
        !          1361:                     {
        !          1362:                     int x, y, len, sw ;
        !          1363:                     char *str ;
        !          1364:                     BufRead(hRead,&x, sizeof(int), &cbR) ;
        !          1365:                     BufRead(hRead,&y, sizeof(int), &cbR) ;
        !          1366:                     BufRead(hRead,&len, sizeof(int), &cbR) ;
        !          1367:
        !          1368:                     DosEnterCritSec() ;
        !          1369:                     len = (len+sizeof(int)-1)/sizeof(int) ;
        !          1370:                     if( len == 0 ) len = 1 ; //?? how about read
        !          1371:                     str = malloc( len*sizeof(int) ) ;
        !          1372:                     *str = '\0' ;
        !          1373:                     DosExitCritSec() ;
        !          1374:                     BufRead(hRead, str, len*sizeof(int), &cbR) ;
        !          1375:                     lCurCol = GpiQueryColor( hps ) ;
        !          1376:                     GpiSetColor( hps, CLR_BLACK ) ;
        !          1377:                     sw = QueryTextBox( hps, strlen(str), str ) ;
        !          1378:                     switch(jmode) {
        !          1379:                        case LEFT:   sw = 0;     break;
        !          1380:                        case CENTRE: sw = -sw/2; break;
        !          1381:                        case RIGHT:  sw = -sw;   break;
        !          1382:                         }
        !          1383:                     if( bHorz ) {
        !          1384:                         ptl.x = (LONG)(x+sw) ; ptl.y = (LONG)(y-lVOffset/4) ;
        !          1385:                         }
        !          1386:                     else {
        !          1387:                         ptl.x = (LONG)x ; ptl.y = (LONG)(y+sw) ;
        !          1388:                         }
        !          1389:                     if(bEnhanced)
        !          1390:                         CharStringAt( hps, ptl.x, ptl.y, strlen( str ) , str ) ;
        !          1391:                     else
        !          1392:                         GpiCharStringAt( hps, &ptl, strlen( str ), str ) ;
        !          1393:                     GpiSetColor( hps, lCurCol ) ;
        !          1394:                     DosEnterCritSec() ;
        !          1395:                     free(str) ;
        !          1396:                     DosExitCritSec() ;
        !          1397:                     }
        !          1398:                     break ;
        !          1399:
        !          1400:                 case 'J' :   /* justify */
        !          1401:                     BufRead(hRead,&jmode, sizeof(int), &cbR) ;
        !          1402:                     break ;
        !          1403:
        !          1404:                 case 'A' :   /* text angle */
        !          1405:                     {
        !          1406:                     int ta ;
        !          1407:                     GRADIENTL grdl ;
        !          1408:                     SIZEF sizHor, sizVer ;
        !          1409:                     if( bPath ) {
        !          1410:                         GpiEndPath( hps ) ;
        !          1411:                         GpiStrokePath( hps, 1, 0 ) ;
        !          1412:                         bPath = FALSE ;
        !          1413:                         }
        !          1414:                     BufRead(hRead,&ta, sizeof(int), &cbR) ;
        !          1415:                     if( ta == 0 ) {
        !          1416:                         grdl.x = 0L ; grdl.y = 0L ;
        !          1417:                         GpiSetCharAngle( hps, &grdl ) ;
        !          1418:                         if( !bHorz ) {
        !          1419:                             bHorz = TRUE ;
        !          1420:                             }
        !          1421:                         }
        !          1422:                     else if( ta == 1 ) {
        !          1423:                         grdl.x = 0L ; grdl.y = 1L ;
        !          1424:                         GpiSetCharAngle( hps, &grdl ) ;
        !          1425:                         if( bHorz ) {
        !          1426:                             bHorz = FALSE ;
        !          1427:                             }
        !          1428:                         }
        !          1429:                     }
        !          1430:                     break ;
        !          1431:
        !          1432:                 case 'L' :   /* line type */
        !          1433:                     {
        !          1434:                     int lt, col ;
        !          1435:                     if( bPath ) {
        !          1436:                         GpiEndPath( hps ) ;
        !          1437:                         GpiStrokePath( hps, 1, 0 ) ;
        !          1438:                         bPath = FALSE ;
        !          1439:                         }
        !          1440:                     BufRead(hRead,&lt, sizeof(int), &cbR) ;
        !          1441:                    /* linetype = -2 axes, -1 border, 0 arrows, all to 0 */
        !          1442:                    col = lt ;
        !          1443:                     if( lt == -2 )     GpiSetLineWidthGeom( hps, DEFLW*0.85 ) ;
        !          1444:                     else if( lt == -1 ) GpiSetLineWidthGeom( hps, DEFLW*0.6 ) ;
        !          1445:                     else GpiSetLineWidthGeom( hps, linewidth ) ;
        !          1446:                     if( lt < 0 ) lt = 0 ;
        !          1447:                    lt = (lt%8);
        !          1448:                    col = (col+2)%16 ;
        !          1449:                     GpiLabel( hps, lLineTypes[lt] ) ;
        !          1450: lOldLine=lt ;
        !          1451:                     LType( (bLineTypes||bBW)?lt:0 ) ;
        !          1452: //                    GpiSetLineType( hps, (bLineTypes||bBW)?lLineTypes[lt]:lLineTypes[0] ) ;
        !          1453:                     if( !bBW ) { /* maintain some flexibility here in case we don't want
        !          1454:                            the model T option */
        !          1455:                         if( bColours ) GpiSetColor( hps, lCols[col] ) ;
        !          1456:                         else GpiSetColor( hps, CLR_BLACK ) ;
        !          1457:                         }
        !          1458:                     }
        !          1459:                     break ;
        !          1460:
        !          1461:                 case 'W' :   /* line width */
        !          1462:                     {
        !          1463:                     int lw ;
        !          1464:                     if( bPath ) {
        !          1465:                         GpiEndPath( hps ) ;
        !          1466:                         GpiStrokePath( hps, 1, 0 ) ;
        !          1467:                         bPath = FALSE ;
        !          1468:                         }
        !          1469:                     BufRead(hRead,&lw, sizeof(int), &cbR) ;
        !          1470:                     GpiSetLineWidthGeom( hps, DEFLW*lw/100 ) ;
        !          1471:                     linewidth = DEFLW*lw/100 ;
        !          1472:                     }
        !          1473:                     break ;
        !          1474:
        !          1475:                  case 'D' :   /* points mode */
        !          1476:                     {
        !          1477:                     int lt ;
        !          1478:                     BufRead(hRead,&lt, sizeof(int), &cbR) ;
        !          1479:                      /* 1: enter point mode, 0: exit */
        !          1480:                     if( bLineTypes || bBW ) {
        !          1481:                         if( lt==1) LType(0) ;
        !          1482:                         else LType( lOldLine ) ;
        !          1483: //                        if( lt == 1 ) lOldLine = GpiSetLineType( hps, lLineTypes[0] ) ;
        !          1484: //                        else GpiSetLineType( hps, lOldLine ) ;
        !          1485:                         }
        !          1486: //                    if( lt == 1 ) GpiSetLineWidthGeom( hps, 20 ) ;
        !          1487: //                    else GpiSetLineWidthGeom( hps, 50 ) ;
        !          1488:                     bDots = lt ;
        !          1489:                     }
        !          1490:                     break ;
        !          1491:
        !          1492:                 case 'F' :   /* set font */
        !          1493:
        !          1494:                     {
        !          1495:                     int len ;
        !          1496:                     char *str ;
        !          1497:                     char font[FONTBUF] ;
        !          1498:                     BufRead(hRead,&len, sizeof(int), &cbR) ;
        !          1499:                     len = (len+sizeof(int)-1)/sizeof(int) ;
        !          1500:                     if( len == 0 ) {
        !          1501:                         SwapFont( hps, NULL ) ;
        !          1502:                         }
        !          1503:                     else {
        !          1504:                         char *p ;
        !          1505:                         str = malloc( len*sizeof(int) ) ;
        !          1506:                         BufRead(hRead, str, len*sizeof(int), &cbR) ;
        !          1507:                         p = strchr(str, ',') ;
        !          1508:                         if( p==NULL ) strcpy( font, "14" ) ;
        !          1509:                         else {
        !          1510:                             *p = '\0' ;
        !          1511:                             strcpy( font, p+1 ) ;
        !          1512:                             }
        !          1513:                         strcat( font,"." ) ;
        !          1514:                         strcat( font, str ) ;
        !          1515:                         free( str ) ;
        !          1516:                         SwapFont( hps, font ) ;
        !          1517:                         }
        !          1518:                     }
        !          1519:                     break ;
        !          1520:
        !          1521:                 case 'O' :   /* set options */
        !          1522:
        !          1523:                     {
        !          1524:                     int len ;
        !          1525:                     char *str ;
        !          1526:                     BufRead(hRead,&len, sizeof(int), &cbR) ;
        !          1527:                     len = (len+sizeof(int)-1)/sizeof(int) ;
        !          1528:                     bWideLines = FALSE ; /* reset options */
        !          1529:                     bEnhanced = FALSE ;
        !          1530:
        !          1531:                     if( len > 0 ) {
        !          1532:                         char *p ;
        !          1533:                         p = str = malloc( len*sizeof(int) ) ;
        !          1534:                         BufRead(hRead, str, len*sizeof(int), &cbR) ;
        !          1535:                         while( (p=strchr(p,'-')) != NULL ) {
        !          1536:                             ++p ;
        !          1537:                             if( *p == 'w' ) bWideLines = TRUE ;
        !          1538:                             if( *p == 'e' ) bEnhanced = TRUE ;
        !          1539:                             ++p ;
        !          1540:                             }
        !          1541:                         free( str ) ;
        !          1542:                         }
        !          1543:                     }
        !          1544:                     break ;
        !          1545:
        !          1546:
        !          1547:                  default :  /* should handle error */
        !          1548:                     break ;
        !          1549:                  }
        !          1550:              }
        !          1551:         }
        !          1552: exitserver:
        !          1553:     DosDisConnectNPipe( hRead ) ;
        !          1554:     WinPostMsg( hApp, WM_CLOSE, 0L, 0L ) ;
        !          1555:     }
        !          1556:
        !          1557: static void EditLineTypes( HWND hwnd, HPS hps, BOOL bDashed )
        !          1558: /*
        !          1559: */
        !          1560:     {
        !          1561:     int i, rc ;
        !          1562:     char buf[64] ;
        !          1563:     GpiSetDrawingMode( hps, DM_RETAIN ) ;
        !          1564:     GpiOpenSegment( hps, iSeg ) ;
        !          1565:     GpiSetEditMode( hps, SEGEM_REPLACE ) ;
        !          1566:     for( i=0; i<7; i++ ) {
        !          1567:         while( GpiSetElementPointerAtLabel( hps, lLineTypes[i] ) ) {
        !          1568:             GpiOffsetElementPointer( hps, 1 ) ;
        !          1569:             GpiSetLineType( hps, bDashed?lLineTypes[i]:lLineTypes[0] ) ;
        !          1570:             }
        !          1571:         GpiSetElementPointer( hps, 0 ) ;
        !          1572:         }
        !          1573:     GpiSetEditMode( hps, SEGEM_INSERT ) ;
        !          1574:     GpiCloseSegment( hps ) ;
        !          1575:     }
        !          1576:
        !          1577: static void EditCharCell( HPS hps, SIZEF *psize )
        !          1578: /*
        !          1579: ** Edit segment to change char cell (font size)
        !          1580: */
        !          1581:     {
        !          1582:     int i ;
        !          1583:     LONG rl, rc ;
        !          1584:     SIZEF sizH, sizV ;
        !          1585:     char buf[64] ;
        !          1586:     int iVert = 0 ;
        !          1587:
        !          1588:     sizH = *psize ;
        !          1589:     sizV.cx = sizH.cy ;
        !          1590:     sizV.cy = sizH.cx ;
        !          1591:     GpiSetDrawingMode( hps, DM_RETAIN ) ;
        !          1592:     GpiOpenSegment( hps, iSeg ) ;
        !          1593:     GpiSetEditMode( hps, SEGEM_REPLACE ) ;
        !          1594:     i=0 ;
        !          1595:     while( GpiSetElementPointer( hps, i ) ) {
        !          1596:         rc = GpiQueryElementPointer( hps) ;
        !          1597:         if( rc != i ) break ;
        !          1598:         rl = GpiQueryElementType( hps, &rc, 0, NULL ) ;
        !          1599:         if( rc == 0x34 || rc == 0x74 ) {
        !          1600:             LONG gdata ;
        !          1601:             GpiQueryElement( hps, 5, 4, (PBYTE)&gdata ) ;
        !          1602:             if( gdata == 0 ) iVert = 0 ;
        !          1603:             else iVert = 1 ;
        !          1604:             }
        !          1605:         else if( rc==0x33 || rc==0x03 ) GpiSetCharBox(hps, iVert?&sizV:&sizH ) ;
        !          1606:         ++i ;
        !          1607:         }
        !          1608:     GpiSetEditMode( hps, SEGEM_INSERT ) ;
        !          1609:     GpiCloseSegment( hps ) ;
        !          1610:     }
        !          1611:
        !          1612: static int BufRead( HFILE hfile, void *buf, int nBytes, ULONG *pcbR )
        !          1613: /*
        !          1614: ** pull next plot command out of buffer read from GNUPLOT
        !          1615: */
        !          1616:     {
        !          1617:     ULONG ulR, ulRR ;
        !          1618:     int rc ;
        !          1619:     static char buffer[GNUBUF] ;
        !          1620:     static char *pbuffer = buffer+GNUBUF, *ebuffer = buffer+GNUBUF ;
        !          1621:
        !          1622:     for( ; nBytes > 0 ; nBytes-- ) {
        !          1623:         if( pbuffer >= ebuffer ) {
        !          1624:             ulR = GNUBUF ;
        !          1625:             rc = DosRead( hfile, buffer, ulR, &ulRR ) ;
        !          1626:             if( rc != 0 ) return rc ;
        !          1627:             if( ulRR == 0 ) return 1 ;
        !          1628:             pbuffer = buffer ;
        !          1629:             ebuffer = pbuffer+ulRR ;
        !          1630:             }
        !          1631:         *(char*)buf++ = *pbuffer++ ;
        !          1632:         }
        !          1633:     return 0L ;
        !          1634:     }
        !          1635:
        !          1636:
        !          1637: int GetNewFont( HWND hwnd, HPS hps )
        !          1638: /*
        !          1639: ** Get a new font using standard font dialog
        !          1640: */
        !          1641:     {
        !          1642:     static FONTDLG pfdFontdlg;      /* Font dialog info structure */
        !          1643:     static int i1 =1 ;
        !          1644:     static int     iSize ;
        !          1645:     char szPtList[64] ;
        !          1646:     HWND    hwndFontDlg;     /* Font dialog window handle */
        !          1647:     char    *p ;
        !          1648:     char szFamilyname[FACESIZE];
        !          1649:
        !          1650:     if( i1 ) {
        !          1651:         strcpy( pfdFontdlg.fAttrs.szFacename, strchr( szFontNameSize, '.' ) + 1 ) ;
        !          1652:         strcpy( szFamilyname, strchr( szFontNameSize, '.' ) + 1 ) ;
        !          1653:         sscanf( szFontNameSize, "%d", &iSize ) ;
        !          1654:         memset(&pfdFontdlg, 0, sizeof(FONTDLG));
        !          1655:
        !          1656:         pfdFontdlg.cbSize = sizeof(FONTDLG);
        !          1657:         pfdFontdlg.hpsScreen = hps;
        !          1658:  /*   szFamilyname[0] = 0;*/
        !          1659:         pfdFontdlg.pszFamilyname = szFamilyname;
        !          1660:         pfdFontdlg.usFamilyBufLen = FACESIZE;
        !          1661:         pfdFontdlg.fl = FNTS_HELPBUTTON |
        !          1662:                         FNTS_CENTER | FNTS_VECTORONLY |
        !          1663:                         FNTS_OWNERDRAWPREVIEW ;
        !          1664:         pfdFontdlg.clrFore = CLR_BLACK;
        !          1665:         pfdFontdlg.clrBack = CLR_WHITE;
        !          1666:         pfdFontdlg.usWeight = FWEIGHT_NORMAL ; //5 ;
        !          1667:         pfdFontdlg.fAttrs.usCodePage = 0;
        !          1668:         pfdFontdlg.fAttrs.usRecordLength = sizeof(FATTRS) ;
        !          1669:         }
        !          1670:     sprintf( szPtList, "%d 8 10 12 14 18 24", iSize ) ;
        !          1671:     pfdFontdlg.pszPtSizeList = szPtList ;
        !          1672:     pfdFontdlg.fxPointSize = MAKEFIXED(iSize,0);
        !          1673:     hwndFontDlg = WinFontDlg(HWND_DESKTOP, hwnd, &pfdFontdlg);
        !          1674:     if( i1 ) {
        !          1675:         pfdFontdlg.fl = FNTS_HELPBUTTON |
        !          1676:                         FNTS_CENTER | FNTS_VECTORONLY |
        !          1677:                         FNTS_INITFROMFATTRS ;
        !          1678:         i1=0;
        !          1679:         }
        !          1680:     if (hwndFontDlg && (pfdFontdlg.lReturn == DID_OK)) {
        !          1681:         iSize = FIXEDINT( pfdFontdlg.fxPointSize ) ;
        !          1682:         sprintf( szFontNameSize, "%d.%s", iSize, pfdFontdlg.fAttrs.szFacename ) ;
        !          1683:         return 1 ;
        !          1684:         }
        !          1685:     else return 0 ;
        !          1686:     }
        !          1687:
        !          1688: void SigHandler( int sig )
        !          1689: /*
        !          1690: **  Handle termination signal to free up resources before
        !          1691: **  termination.
        !          1692: */
        !          1693:     {
        !          1694:     if( sig == SIGTERM ) {
        !          1695:         if( bPersist ) {
        !          1696:             DosKillThread( tidSpawn ) ;
        !          1697:             signal( SIGTERM, SIG_ACK ) ;
        !          1698:             return ;
        !          1699:             }
        !          1700:         DosEnterCritSec() ;
        !          1701:         DosKillThread( tidSpawn ) ;
        !          1702:         DosKillThread( tidDraw ) ;
        !          1703:         DosExitCritSec() ;
        !          1704:         exit(0) ;
        !          1705:         }
        !          1706:     }
        !          1707:
        !          1708: /* disable debugging info */
        !          1709: #define TEXT_DEBUG(x) /* fprintf x; */
        !          1710:
        !          1711: /* used in determining height of processed text */
        !          1712:
        !          1713: //static float max_height, min_height;
        !          1714:
        !          1715: /* process a bit of string, and return the last character used.
        !          1716:  * p is start of string
        !          1717:  * brace is TRUE to keep processing to }, FALSE for do one character
        !          1718:  * fontname & fontsize are obvious
        !          1719:  * base is the current baseline
        !          1720:  * widthflag is TRUE if the width of this should count,
        !          1721:  *              FALSE for zero width boxes
        !          1722:  * showflag is TRUE if this should be shown,
        !          1723:  *             FALSE if it should not be shown (like TeX \phantom)
        !          1724:  */
        !          1725:
        !          1726: static char *starttext = NULL ;
        !          1727: static int  textlen = 0 ;
        !          1728: static BOOL bText = FALSE ;
        !          1729: static int  textwidth = 0 ;
        !          1730: static POINTL ptlText ;
        !          1731: static FILE *ff ;
        !          1732: static char *ParseText(HPS hps, char *p, BOOL brace, char *fontname,
        !          1733:                        int fontsize, int base, BOOL widthflag, BOOL showflag)
        !          1734: {
        !          1735:     POINTL aptl[TXTBOX_COUNT] ;
        !          1736:     BOOL bChangeFont = FALSE ;
        !          1737:        TEXT_DEBUG((ff,"RECURSE WITH [%p] %s, %d %s %.1f %.1f %d %d\n", p, p, brace, fontname, fontsize, base, widthflag, showflag))
        !          1738:
        !          1739:     /* Start each recursion with a clean string */
        !          1740:
        !          1741: //{FILE *ff;int i=textlen;ff=fopen("deb","a");
        !          1742: //for(i=0;i<textlen;i++)fputc(starttext[i], ff);fputc('\n',ff) ; fclose(ff);}
        !          1743:         if( textlen > 0 ) {
        !          1744:             GpiQueryTextBox( hps, textlen, starttext, TXTBOX_COUNT, aptl ) ;
        !          1745:             if( bHorz ) textwidth += aptl[TXTBOX_BOTTOMRIGHT].x ;
        !          1746:             else        textwidth += aptl[TXTBOX_BOTTOMRIGHT].y ;
        !          1747:             }
        !          1748:         if( bText ) {
        !          1749:             if(textlen > 0 ) {
        !          1750:                 GpiCharStringAt( hps, &ptlText, textlen, starttext ) ;
        !          1751:                 ptlText.x += aptl[TXTBOX_CONCAT].x + (bHorz?0:(-base)) ;
        !          1752:                 ptlText.y += aptl[TXTBOX_CONCAT].y + (bHorz?base:0) ;
        !          1753:                 }
        !          1754:             else {
        !          1755:                 ptlText.x += (bHorz?0:(-base)) ;
        !          1756:                 ptlText.y += (bHorz?base:0) ;
        !          1757:                 }
        !          1758:             }
        !          1759:         textlen = 0 ;
        !          1760:         starttext = p ;
        !          1761:         if( fontname != NULL ) {
        !          1762:             char szFont[FONTBUF] ;
        !          1763:             sprintf(szFont, "%d.%s", fontsize, fontname ) ;
        !          1764:             SwapFont( hps, szFont ) ;
        !          1765:             bChangeFont = TRUE ;
        !          1766:             }
        !          1767:     if( base != 0 ) GpiSetCharBox( hps, &sizCurSubSup ) ;
        !          1768:
        !          1769:     for ( ; *p; ++p)
        !          1770:     {    int shift;
        !          1771:
        !          1772:         switch (*p)
        !          1773:         {
        !          1774:             case '}'  :
        !          1775:                 /*{{{  deal with it*/
        !          1776:                 if (brace) {
        !          1777:                     brace = 0 ;
        !          1778:                     break ;
        !          1779:                     }
        !          1780:
        !          1781:                 break;
        !          1782:                 /*}}}*/
        !          1783:
        !          1784:             case '_'  :
        !          1785:             case '^'  :
        !          1786:                 /*{{{  deal with super/sub script*/
        !          1787:
        !          1788:                 shift = (*p == '^') ? lSupOffset : lSubOffset;
        !          1789:                 p = ParseText(hps, p+1, FALSE, NULL/*fontname*/, fontsize*0.7, base+shift, widthflag, showflag);
        !          1790:                 break;
        !          1791:                 /*}}}*/
        !          1792:
        !          1793:             case '{'  :
        !          1794:             {
        !          1795:                 char *savepos=NULL, save=0;
        !          1796:                 char *localfontname=fontname, ch;
        !          1797:                 char localfontbuf[FONTBUF] ;
        !          1798:                 int recode=1;
        !          1799:                 int f=fontsize;
        !          1800:                 BOOL bChangeFont = FALSE ;
        !          1801:                 char *q=localfontbuf ;
        !          1802:
        !          1803:                 /*{{{  recurse (possibly with a new font) */
        !          1804:
        !          1805:                 TEXT_DEBUG((ff,"Dealing with {\n"))
        !          1806:
        !          1807:                 if (*++p == '/')
        !          1808:                 {    /* then parse a fontname, optional fontsize */
        !          1809:                     while (*++p == ' ');
        !          1810:                     if (*p=='-')
        !          1811:                     {
        !          1812:                         recode=0;
        !          1813:                         while (*++p == ' ');
        !          1814:                     }
        !          1815:                     localfontname = p;
        !          1816:                     while ((ch = *p) > ' ' && ch != '=') {
        !          1817:                             localfontname=localfontbuf ;
        !          1818:                             if(*p=='_') *q=' ' ;
        !          1819:                             else *q=*p ;
        !          1820:                         ++p;++q;
        !          1821:                         }
        !          1822:                     *q = '\0' ;
        !          1823:                     FontExpand( localfontbuf ) ;
        !          1824:                     save = *(savepos=p);
        !          1825:                     if (ch == '=')
        !          1826:                     {
        !          1827:                         *p++ = '\0';
        !          1828:                         /*{{{  get optional font size*/
        !          1829:                         TEXT_DEBUG((ff,"Calling strtod(%s) ...", p))
        !          1830:                         f = strtod(p, &p);
        !          1831:                         TEXT_DEBUG((ff,"Retured %.1f and %s\n", f, p))
        !          1832:
        !          1833:                         if (!f) f = fontsize;
        !          1834:
        !          1835:                         TEXT_DEBUG((ff,"Font size %.1f\n", f))
        !          1836:                         /*}}}*/
        !          1837:                     }
        !          1838:                     else
        !          1839:                     {
        !          1840:                         *p++ = '\0';
        !          1841:                         f = fontsize;
        !          1842:                     }
        !          1843:
        !          1844:                     while (*p == ' ')
        !          1845:                         ++p;
        !          1846:                     if (! (*localfontname)) {
        !          1847:                         localfontname = fontname;
        !          1848:                         if( f != fontsize )
        !          1849:                             localfontname = strchr( szFontNameSize, '.' ) + 1 ;
        !          1850:                         }
        !          1851:                 }
        !          1852:                 /*}}}*/
        !          1853:
        !          1854:                 TEXT_DEBUG((ff,"Before recursing, we are at [%p] %s\n", p, p))
        !          1855:
        !          1856:                 p = ParseText(hps,p, TRUE, localfontname, f, base, widthflag, showflag);
        !          1857:
        !          1858:                 TEXT_DEBUG((ff,"BACK WITH %s\n", p));
        !          1859:                 if (savepos)
        !          1860:                     /* restore overwritten character */
        !          1861:                     *savepos = save;
        !          1862:
        !          1863:                 break;
        !          1864:             }
        !          1865:
        !          1866:             case '@' :
        !          1867:                 /*{{{  phantom box - prints next 'char', then restores currentpoint */
        !          1868:
        !          1869:                 p = ParseText(hps,++p, FALSE, NULL/*fontname*/, fontsize, base, FALSE, showflag);
        !          1870:
        !          1871:                 break;
        !          1872:                 /*}}}*/
        !          1873:
        !          1874:             case '&' :
        !          1875:                 /*{{{  character skip - skips space equal to length of character(s) */
        !          1876:
        !          1877:                 p = ParseText(hps,++p, FALSE, NULL/*fontname*/, fontsize, base, widthflag, FALSE);
        !          1878:
        !          1879:                 break;
        !          1880:                 /*}}}*/
        !          1881:
        !          1882:             case '\\'  :
        !          1883:                 {
        !          1884:                 char buffer[4] ; /* should need only one char.. */
        !          1885:                 char *q = buffer ;
        !          1886:                 *q = '\0' ;
        !          1887:                 ParseText(hps,q, FALSE, NULL, fontsize, base, widthflag, showflag);
        !          1888:                 /*{{{  is it an escape */
        !          1889:                 /* special cases */
        !          1890:
        !          1891:                 if (p[1]=='\\' || p[1]=='{' || p[1]=='}')
        !          1892:                 {
        !          1893:                     *q++=p[1] ;
        !          1894:                     ++p ;
        !          1895:                 }
        !          1896: #if 0
        !          1897:                 else if (p[1] >= '0' && p[1] <= '7')
        !          1898:                 {
        !          1899:                     /* up to 3 octal digits */
        !          1900:                     int c = 0 ;
        !          1901:                     c+=p[1];
        !          1902:                     ++p;
        !          1903:                     if (p[1] >= '0' && p[1] <= '7')
        !          1904:                     {
        !          1905:                         c*=8; c+=p[1];
        !          1906:                         ++p;
        !          1907:                         if (p[1] >= '0' && p[1] <= '7')
        !          1908:                         {
        !          1909:                             c*=8; c+=p[1];
        !          1910:                             ++p;
        !          1911:                         }
        !          1912:                     }
        !          1913:                     *q++ = c ;
        !          1914:                     break;
        !          1915:                 }
        !          1916: #endif
        !          1917:                 *q = '\0' ;
        !          1918:                 textlen = 1 ;
        !          1919:                 starttext=buffer ;
        !          1920:                 ParseText(hps,q, FALSE, NULL/*fontname*/, fontsize, base, widthflag, showflag);
        !          1921:                 starttext=p+1 ;
        !          1922:                 textlen = 0 ;
        !          1923:                 /*}}}*/
        !          1924:                 }
        !          1925:                 break ;
        !          1926:
        !          1927:             default:
        !          1928:                 ++textlen ;
        !          1929:
        !          1930:             /*}}}*/
        !          1931:
        !          1932:         }
        !          1933:
        !          1934:         /* like TeX, we only do one character in a recursion, unless it's
        !          1935:          * in braces
        !          1936:          */
        !          1937:
        !          1938:         if (!brace) break ;
        !          1939:         }
        !          1940:         if( textlen > 0 ) {
        !          1941:             GpiQueryTextBox( hps, textlen, starttext, TXTBOX_COUNT, aptl ) ;
        !          1942:             if( widthflag ) {
        !          1943:                 if( bHorz ) textwidth += aptl[TXTBOX_BOTTOMRIGHT].x ;
        !          1944:                 else        textwidth += aptl[TXTBOX_BOTTOMRIGHT].y ;
        !          1945:                 }
        !          1946:             }
        !          1947:         if( bText ) {
        !          1948:             if( textlen > 0 ) {
        !          1949:                 if( showflag)
        !          1950:                     GpiCharStringAt( hps, &ptlText, textlen, starttext ) ;
        !          1951:                 if( widthflag ) {
        !          1952:                     ptlText.x += aptl[TXTBOX_CONCAT].x ;
        !          1953:                     ptlText.y += aptl[TXTBOX_CONCAT].y ;
        !          1954:                     }
        !          1955:                 }
        !          1956:             if( base != 0 ) {
        !          1957:                 ptlText.x -= (bHorz?0:(-base)) ;
        !          1958:                 ptlText.y -= (bHorz?base:0) ;
        !          1959:                 }
        !          1960:             }
        !          1961:         if( bChangeFont ) {
        !          1962:             SwapFont( hps, NULL ) ;
        !          1963:             bChangeFont = FALSE ;
        !          1964:             }
        !          1965:     if( base != 0 ) GpiSetCharBox( hps, &sizBaseFont ) ;
        !          1966:
        !          1967:
        !          1968:         textlen = 0 ;
        !          1969:         starttext = p+1 ;
        !          1970:     return p;
        !          1971: }
        !          1972:
        !          1973: static void CharStringAt(HPS hps, int x, int y, int len, char *str)
        !          1974: {
        !          1975:     /* flush any pending graphics (all the XShow routines do this...) */
        !          1976:
        !          1977:      char *fontname ;
        !          1978:      int fontsize ;
        !          1979:
        !          1980:     if (!strlen(str))
        !          1981:         return;
        !          1982:
        !          1983:     /* set up the globals */
        !          1984:
        !          1985:         ptlText.x = x ;
        !          1986:         ptlText.y = y ;
        !          1987:         bText = TRUE ;
        !          1988:         starttext = NULL ;
        !          1989:         textlen = 0 ;
        !          1990:         textwidth = 0 ;
        !          1991:         sscanf( szFontNameSize, "%d", &fontsize ) ;
        !          1992:         fontname = strchr( szFontNameSize, '.' ) + 1 ;
        !          1993:
        !          1994:     while (*(str = ParseText(hps, str, TRUE, NULL,
        !          1995:                      fontsize,
        !          1996:                      0.0, TRUE, TRUE)));
        !          1997:
        !          1998: }
        !          1999:
        !          2000: static int QueryTextBox( HPS hps, int len, char *str )
        !          2001: {
        !          2002:      char *fontname ;
        !          2003:      int fontsize ;
        !          2004:     if (!strlen(str))
        !          2005:         return 0 ;
        !          2006:
        !          2007:
        !          2008:     /* set up the globals */
        !          2009:
        !          2010:         bText = FALSE ;
        !          2011:         starttext = NULL ;
        !          2012:         textlen = 0 ;
        !          2013:         textwidth = 0 ;
        !          2014:         sscanf( szFontNameSize, "%d", &fontsize ) ;
        !          2015:         fontname = strchr( szFontNameSize, '.' ) + 1 ;
        !          2016:
        !          2017:     while (*(str = ParseText(hps, str, TRUE, NULL,
        !          2018:                      fontsize,
        !          2019:                      0.0, TRUE, TRUE)));
        !          2020:
        !          2021:     return textwidth ;
        !          2022: }
        !          2023:
        !          2024: void FontExpand( char *name )
        !          2025:     {
        !          2026:     if     ( strcmp(name,"S")==0 ) strcpy( name, "Symbol Set" ) ;
        !          2027:     else if( strcmp(name,"H")==0 ) strcpy( name, "Helvetica" ) ;
        !          2028:     else if( strcmp(name,"T")==0 ) strcpy( name, "Times New Roman" ) ;
        !          2029:     else if( strcmp(name,"C")==0 ) strcpy( name, "Courier" ) ;
        !          2030:     }
        !          2031:
        !          2032: /*=======================================*/
        !          2033: static POINTL pCur ;
        !          2034: static int iLinebegin = 1 ;
        !          2035: static int iLtype = 0 ;
        !          2036: static int iState = 0 ;
        !          2037: static double togo = 0.0 ;
        !          2038: static int iPatt[8][9]
        !          2039:   = {
        !          2040:     {   0,   0,   0,   0,   0,   0,   0,   0,  0 },
        !          2041:     { 300, 200,  -1,   0,   0,   0,   0,   0,  0 },
        !          2042:     { 150, 150,  -1,   0,   0,   0,   0,   0,  0 },
        !          2043:     { 300, 200, 150, 200,  -1,   0,   0,   0,  0 },
        !          2044:     { 500, 200,  -1,   0,   0,   0,   0,   0,  0 },
        !          2045:     { 300, 200, 150, 200, 150, 200,  -1,   0,  0 },
        !          2046:     { 300, 200, 150, 200, 150, 200, 150, 200, -1 },
        !          2047:     { 500, 200, 150, 200,  -1,   0,   0,   0,  0 }
        !          2048:     } ;
        !          2049:
        !          2050: void LMove( HPS hps, POINTL *p )
        !          2051:     {
        !          2052:     double ds, dx, dy ;
        !          2053:     if( iLinebegin ) {
        !          2054:         pCur = *p ;
        !          2055:         GpiMove( hps, p ) ;
        !          2056:         }
        !          2057:     else if( iLtype == 0 ) GpiMove( hps, p ) ;
        !          2058:     else {
        !          2059:         dx = p->x - pCur.x ;
        !          2060:         dy = p->y - pCur.y ;
        !          2061:         ds = sqrt( dx*dx + dy*dy ) ;
        !          2062:         dx /= ds ; dy /= ds ;
        !          2063:         while( ds > 0.0 ) {
        !          2064:             if( ds < togo ) {
        !          2065:                 togo -= ds ;
        !          2066:                 ds = 0.0 ;
        !          2067:                 GpiMove( hps, p ) ;
        !          2068:                 pCur = *p ;
        !          2069:                 }
        !          2070:             else {
        !          2071:                 POINTL pn ;
        !          2072:                 pn.x = pCur.x + togo * dx ;
        !          2073:                 pn.y = pCur.y + togo * dy ;
        !          2074:                 GpiMove( hps, &pn ) ;
        !          2075:                 pCur = pn ;
        !          2076:                 ds -= togo ;
        !          2077:                 iState++ ;
        !          2078:                 if( iPatt[iLtype][iState] < 0 ) {
        !          2079:                     togo = iPatt[iLtype][0] ;
        !          2080:                     iState = 0 ;
        !          2081:         }
        !          2082:                 else togo = iPatt[iLtype][iState] ;
        !          2083:     }
        !          2084:             }
        !          2085:         }
        !          2086:     }
        !          2087:
        !          2088: void LLine( HPS hps, POINTL *p )
        !          2089:     {
        !          2090:     double ds, dx, dy ;
        !          2091:     if( iLinebegin ) iLinebegin = 0 ;
        !          2092:
        !          2093:     if( iLtype == 0 ) GpiLine( hps, p ) ;
        !          2094:     else {
        !          2095:         dx = p->x - pCur.x ;
        !          2096:         dy = p->y - pCur.y ;
        !          2097:         ds = sqrt( dx*dx + dy*dy ) ;
        !          2098:         dx /= ds ; dy /= ds ;
        !          2099:         while( ds > 0.0 ) {
        !          2100:             if( ds < togo ) {
        !          2101:                 togo -= ds ;
        !          2102:                 ds = 0.0 ;
        !          2103:                 if( iState&1 ) GpiMove( hps, p ) ;
        !          2104:                 else GpiLine( hps, p ) ;
        !          2105:                 pCur = *p ;
        !          2106:                 }
        !          2107:             else {
        !          2108:                 POINTL pn ;
        !          2109:                 pn.x = pCur.x + togo * dx ;
        !          2110:                 pn.y = pCur.y + togo * dy ;
        !          2111:                 if( iState&1 ) GpiMove( hps, &pn ) ;
        !          2112:                 else GpiLine( hps, &pn ) ;
        !          2113:                 pCur = pn ;
        !          2114:                 ds -= togo ;
        !          2115:                 iState++ ;
        !          2116:                 if( iPatt[iLtype][iState] < 0 ) {
        !          2117:                     togo = iPatt[iLtype][0] ;
        !          2118:                     iState = 0 ;
        !          2119:                     }
        !          2120:                 else togo = iPatt[iLtype][iState] ;
        !          2121:                 }
        !          2122:             }
        !          2123:         }
        !          2124:     }
        !          2125:
        !          2126: void LType( int iType )
        !          2127:     {
        !          2128:     iLinebegin = 1 ;
        !          2129:     if( iType > 7 ) iType = 0 ;
        !          2130:     iLtype = iType ;
        !          2131:     iState = 0 ;
        !          2132:     togo = iPatt[iLtype][0] ;
        !          2133:     }
        !          2134:

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>