|
|
1.1 ! root 1: /****************************** Module Header *********************************/ ! 2: /* */ ! 3: /* Module Name: calc.c - Calc application */ ! 4: /* */ ! 5: /* OS/2 Presentation Manager version of Calc, ported from Windows version */ ! 6: /* */ ! 7: /* Created by Microsoft, IBM Corporation, 1990 */ ! 8: /* */ ! 9: /* DISCLAIMER OF WARRANTIES. The following [enclosed] code is */ ! 10: /* sample code created by Microsoft Corporation and/or IBM */ ! 11: /* Corporation. This sample code is not part of any standard */ ! 12: /* Microsoft or IBM product and is provided to you solely for */ ! 13: /* the purpose of assisting you in the development of your */ ! 14: /* applications. The code is provided "AS IS", without */ ! 15: /* warranty of any kind. Neither Microsoft nor IBM shall be */ ! 16: /* liable for any damages arising out of your use of the sample */ ! 17: /* code, even if they have been advised of the possibility of */ ! 18: /* such damages. */ ! 19: /* */ ! 20: /******************************************************************************/ ! 21: ! 22: #define INCL_WININPUT ! 23: #define INCL_WINPOINTERS ! 24: #define INCL_WINMENUS ! 25: #define INCL_WINSYS ! 26: #define INCL_WINCLIPBOARD ! 27: #define INCL_GPIPRIMITIVES ! 28: #define INCL_GPIBITMAPS ! 29: #define INCL_GPILCIDS ! 30: #define INCL_DEV ! 31: #define INCL_ERRORS ! 32: #define INCL_DOSPROCESS ! 33: #define INCL_DOSSEMAPHORES ! 34: #define INCL_DOSNLS ! 35: #include <os2.h> ! 36: #include <string.h> ! 37: #include <stdlib.h> ! 38: #include <stdio.h> ! 39: #include "calc.h" ! 40: ! 41: /******************************************************************************/ ! 42: /* */ ! 43: /* GLOBAL VARIABLES */ ! 44: /* */ ! 45: /******************************************************************************/ ! 46: ! 47: CHAR chLastKey, chCurrKey; ! 48: CHAR szreg1[20], szreg2[20], szmem[20], szregx[20]; ! 49: CHAR szTitle[30], szErrorString[20], szPlusMinus[2]; ! 50: SHORT sCharWidth, sCharHeight; ! 51: extern BOOL fError; ! 52: BOOL fValueInMemory = FALSE; ! 53: BOOL fMDown = FALSE; /* TRUE iff 'm' key depressed */ ! 54: UCHAR uchMScan = 0; /* scan code for 'm' key */ ! 55: ! 56: #define TOLOWER(x) ( (((x) >= 'A') && ((x) <= 'Z')) ? (x)|0x20 : (x)) ! 57: #define WIDTHCONST 28 ! 58: #define CXCHARS 37 ! 59: #define CYCHARS 13 ! 60: ! 61: HAB hab; ! 62: HDC hdcLocal; /* Local used for button bitmap */ ! 63: HPS hpsLocal; ! 64: HDC hdcSqr; /* Sqr used for square-root bitmap */ ! 65: HPS hpsSqr; ! 66: HBITMAP hbmLocal, hbmSqr; ! 67: HMQ hmqCalc; ! 68: HWND hwndCalc, hwndMenu; ! 69: HWND hwndCalcFrame; ! 70: HPS hpsCalc; ! 71: HDC hdcCalc; ! 72: HPOINTER hptrFinger; ! 73: ! 74: DEVOPENSTRUC dop = /* used by DevOpenDC */ ! 75: { ! 76: NULL, "DISPLAY", NULL, NULL, NULL, NULL, NULL, NULL, NULL ! 77: }; ! 78: ! 79: static char achKeys[25] = /* keyboard keys */ ! 80: { ! 81: '\271', '0', '.', '\261', '+', '=', ! 82: '\272', '1', '2', '3', '-', 'c', ! 83: '\273', '4', '5', '6', '*', '%', ! 84: '\274', '7', '8', '9', '/', 'q', ! 85: NULL ! 86: }; ! 87: ! 88: static CHAR achDKeys[25] = /* 4th key is plusminus */ ! 89: { ! 90: ' ', '0', '.', '+', '+', '=', ! 91: ' ', '1', '2', '3', '-', 'C', ! 92: ' ', '4', '5', '6', '*', '%', ! 93: ' ', '7', '8', '9', '/', ' ', ! 94: NULL ! 95: }; ! 96: ! 97: /******************************************************************************/ ! 98: /* */ ! 99: /* PROCEDURE DECLARATIONS */ ! 100: /* */ ! 101: /******************************************************************************/ ! 102: ! 103: VOID FarStrcpy( PSZ, PSZ); ! 104: MPARAM EXPENTRY AboutDlgProc( HWND, USHORT, MPARAM, MPARAM); ! 105: BOOL CalcInit(VOID); ! 106: VOID CalcPaint( HWND, HPS); ! 107: VOID CalcTextOut( HPS, INT, INT, PCH, INT); ! 108: MRESULT EXPENTRY CalcWndProc( HWND, USHORT, MPARAM, MPARAM); ! 109: VOID cdecl main(VOID); ! 110: VOID DataXCopy( VOID); ! 111: VOID DataXPaste( VOID); ! 112: VOID DrawNumbers( HPS); ! 113: VOID Evaluate(BYTE); ! 114: BOOL FlashSqr( HPS, PWPOINT); ! 115: VOID FlipKey( HPS, INT, INT); ! 116: VOID FrameKey( HPS, INT, INT); ! 117: VOID InitCalc( VOID); ! 118: BOOL InterpretChar( CHAR); ! 119: VOID ProcessKey( PWPOINT); ! 120: BOOL PSInit( VOID); ! 121: CHAR Translate( PWPOINT); ! 122: VOID UpdateDisplay( VOID); ! 123: ! 124: ! 125: /******************************************************************************/ ! 126: /******************************************************************************/ ! 127: VOID CalcTextOut( hps, iX, iY, pch, iCount) ! 128: ! 129: HPS hps; ! 130: INT iX, iY; ! 131: PCH pch; ! 132: INT iCount; ! 133: { ! 134: POINTL ptl; ! 135: ! 136: ptl.x = iX; ! 137: ptl.y = iY; ! 138: ! 139: GpiSetColor( hps, CLR_BLACK); ! 140: GpiCharStringAt( hps, (PPOINTL)&ptl, (LONG)iCount, (PSZ)pch); ! 141: } ! 142: ! 143: ! 144: /******************************************************************************/ ! 145: /* Write the appropriate number or error string to the display area */ ! 146: /* and mark memory-in-use if appropriate. */ ! 147: /******************************************************************************/ ! 148: VOID ! 149: UpdateDisplay() ! 150: { ! 151: RECTL rcl; ! 152: ! 153: rcl.xLeft = (6 * sCharWidth); ! 154: rcl.yBottom = 1050 * sCharHeight / 100; ! 155: rcl.xRight = rcl.xLeft + (12 * sCharWidth); ! 156: rcl.yTop = rcl.yBottom + (3 * sCharHeight) / 2; ! 157: ! 158: WinFillRect( hpsCalc, &rcl, CLR_WHITE); /* paint display area white */ ! 159: if( fError) ! 160: WinDrawText( hpsCalc ! 161: , -1 ! 162: , szErrorString ! 163: , &rcl ! 164: , CLR_BLACK ! 165: , CLR_WHITE ! 166: , DT_RIGHT | DT_VCENTER ); ! 167: else ! 168: WinDrawText( hpsCalc ! 169: , -1 ! 170: , szreg1 ! 171: , &rcl ! 172: , CLR_BLACK ! 173: , CLR_WHITE ! 174: , DT_RIGHT | DT_VCENTER ); ! 175: ! 176: if (fValueInMemory) /* little black square shows mem use */ ! 177: { ! 178: rcl.xLeft = (6 * sCharWidth); ! 179: rcl.yBottom = 1050 * sCharHeight / 100; ! 180: rcl.xRight = rcl.xLeft + (sCharWidth / 2); ! 181: rcl.yTop = rcl.yBottom + (sCharHeight / 2); ! 182: WinFillRect( hpsCalc, &rcl, CLR_BLACK); ! 183: } ! 184: } ! 185: ! 186: ! 187: /******************************************************************************/ ! 188: /* Display helpful info */ ! 189: /******************************************************************************/ ! 190: MPARAM EXPENTRY ! 191: AboutDlgProc( hwnd, msg, mp1, mp2) ! 192: ! 193: HWND hwnd; ! 194: USHORT msg; ! 195: MPARAM mp1; ! 196: MPARAM mp2; ! 197: { ! 198: if (msg == WM_COMMAND) ! 199: { ! 200: WinDismissDlg(hwnd, TRUE); ! 201: return(MPFROMSHORT(TRUE)); ! 202: } ! 203: else return(WinDefDlgProc( hwnd, msg, mp1, mp2)); ! 204: } ! 205: ! 206: ! 207: /******************************************************************************/ ! 208: /* General initialization */ ! 209: /******************************************************************************/ ! 210: BOOL ! 211: CalcInit() ! 212: { ! 213: hab = WinInitialize( NULL); ! 214: ! 215: hmqCalc = WinCreateMsgQueue( hab, 0); ! 216: if( !hmqCalc) ! 217: return(FALSE); ! 218: ! 219: WinLoadString( NULL, NULL, 1, 30, (PSZ)szTitle); ! 220: WinLoadString( NULL, NULL, 2, 20, (PSZ)szErrorString); ! 221: WinLoadString( NULL, NULL, 3, 2, (PSZ)szPlusMinus); ! 222: ! 223: if (!WinRegisterClass( hab, szTitle, CalcWndProc, CS_SIZEREDRAW, 0)) ! 224: return(FALSE); ! 225: ! 226: hptrFinger = WinLoadPointer( HWND_DESKTOP, (HMODULE)NULL, IDP_FINGER); ! 227: ! 228: InitCalc(); /* arithmetic initialization */ ! 229: ! 230: return(TRUE); ! 231: } ! 232: ! 233: /******************************************************************************/ ! 234: /* main procedure */ ! 235: /******************************************************************************/ ! 236: VOID cdecl ! 237: main() ! 238: { ! 239: QMSG qmsg; ! 240: ULONG ulFCF; ! 241: ! 242: if (!CalcInit()) { /* general initialization */ ! 243: WinAlarm(HWND_DESKTOP, WA_ERROR); ! 244: goto exit; ! 245: } ! 246: ! 247: if (!PSInit()) { /* presentation spaces & bitmaps */ ! 248: WinAlarm(HWND_DESKTOP, WA_ERROR); ! 249: goto exit; ! 250: } ! 251: ! 252: ulFCF = FCF_STANDARD & ~(LONG)(FCF_SIZEBORDER | FCF_MAXBUTTON); ! 253: hwndCalcFrame = WinCreateStdWindow( HWND_DESKTOP ! 254: , WS_VISIBLE | FS_BORDER ! 255: , &ulFCF ! 256: , szTitle ! 257: , NULL ! 258: , 0L ! 259: , NULL ! 260: , IDR_CALC ! 261: , &hwndCalc); ! 262: ! 263: WinSetWindowPos( hwndCalcFrame ! 264: , (HWND)NULL ! 265: , 2 ! 266: , 2 ! 267: , CXCHARS * sCharWidth ! 268: , CYCHARS * sCharHeight ! 269: + (SHORT)WinQuerySysValue( HWND_DESKTOP ! 270: , SV_CYTITLEBAR ) ! 271: + (SHORT)WinQuerySysValue( HWND_DESKTOP ! 272: , SV_CYMENU ) ! 273: , SWP_MOVE | SWP_SIZE ); ! 274: ! 275: while (WinGetMsg( hab, &qmsg, NULL, 0, 0)) ! 276: WinDispatchMsg( hab, &qmsg); ! 277: ! 278: exit: /* clean up */ ! 279: if (hdcSqr) /* square-root bitmap */ ! 280: { ! 281: GpiDestroyPS( hpsSqr); ! 282: if (hbmSqr) ! 283: GpiDeleteBitmap( hbmSqr); ! 284: } ! 285: ! 286: if (hdcLocal) /* keypad button */ ! 287: { ! 288: GpiDestroyPS( hpsLocal); ! 289: if (hbmLocal) ! 290: GpiDeleteBitmap( hbmLocal); ! 291: } ! 292: ! 293: WinDestroyWindow(hwndCalcFrame); ! 294: ! 295: WinDestroyMsgQueue(hmqCalc); ! 296: WinTerminate(hab); ! 297: ! 298: DosExit(EXIT_PROCESS, 0); /* exit without error */ ! 299: } ! 300: ! 301: ! 302: /******************************************************************************/ ! 303: /* Calc Window Procedure */ ! 304: /******************************************************************************/ ! 305: MRESULT EXPENTRY ! 306: CalcWndProc(hwnd, msg, mp1, mp2) ! 307: ! 308: HWND hwnd; ! 309: USHORT msg; ! 310: MPARAM mp1; ! 311: MPARAM mp2; ! 312: { ! 313: HPS hps; ! 314: RECTL rclPaint; ! 315: WPOINT wpt; ! 316: BOOL fClip; ! 317: USHORT usFmtInfo; ! 318: RECTL rcl; ! 319: SIZEL sizl; ! 320: ! 321: switch (msg) ! 322: { ! 323: case WM_CREATE: ! 324: hdcCalc = WinOpenWindowDC( hwnd); ! 325: WinQueryWindowRect( hwnd, &rcl); ! 326: sizl.cx = rcl.xRight - rcl.xLeft; ! 327: sizl.cy = rcl.yTop - rcl.yBottom; ! 328: hpsCalc = GpiCreatePS( hab ! 329: , hdcCalc ! 330: , &sizl ! 331: , GPIA_ASSOC | PU_PELS ); ! 332: break; ! 333: ! 334: case WM_DESTROY: ! 335: WinDestroyPointer(hptrFinger); ! 336: GpiDestroyPS( hpsSqr); ! 337: GpiDeleteBitmap( hbmSqr); ! 338: GpiDestroyPS( hpsLocal); ! 339: GpiDeleteBitmap( hbmLocal); ! 340: break; ! 341: ! 342: case WM_INITMENU: ! 343: fClip = FALSE; ! 344: if (WinOpenClipbrd( hab)) ! 345: { ! 346: fClip = WinQueryClipbrdFmtInfo( hab, CF_TEXT, &usFmtInfo); ! 347: WinCloseClipbrd( hab); ! 348: } ! 349: WinSendMsg((HWND)mp2, MM_SETITEMATTR, ! 350: (MPARAM) MAKELONG(CMD_PASTE, TRUE), ! 351: (MPARAM) MAKELONG(MIA_DISABLED, fClip ? 0 : MIA_DISABLED)); ! 352: break; ! 353: ! 354: case WM_PAINT: ! 355: hps = WinBeginPaint(hwnd, NULL, &rclPaint); ! 356: CalcPaint( hwnd, hps); /* re-draw calculator */ ! 357: WinEndPaint(hps); ! 358: break; ! 359: ! 360: case WM_COMMAND: ! 361: if (fError) ! 362: break; ! 363: switch(LOUSHORT(mp1)) ! 364: { ! 365: case CMD_COPY: ! 366: DataXCopy(); /* copy to clipboard */ ! 367: break; ! 368: case CMD_PASTE: ! 369: DataXPaste(); /* paste from clipboard */ ! 370: break; ! 371: case CMD_EXIT: ! 372: WinPostMsg( hwndCalcFrame, WM_QUIT, 0L, 0L); ! 373: break; ! 374: case CMD_ABOUT: ! 375: WinDlgBox( HWND_DESKTOP ! 376: , hwndCalcFrame ! 377: , (PFNWP)AboutDlgProc ! 378: , NULL ! 379: , 1 ! 380: , (PSZ)NULL ); ! 381: break; ! 382: } ! 383: break; ! 384: ! 385: case WM_CLOSE: ! 386: WinPostMsg(hwndCalcFrame, WM_QUIT, 0L, 0L); ! 387: break; ! 388: ! 389: case WM_MOUSEMOVE: ! 390: WinSetPointer( HWND_DESKTOP, hptrFinger); ! 391: break; ! 392: ! 393: case WM_BUTTON1DOWN: ! 394: wpt.x = LOUSHORT(mp1); ! 395: wpt.y = HIUSHORT(mp1); ! 396: ProcessKey( &wpt); ! 397: goto dwp; ! 398: break; ! 399: ! 400: case WM_CHAR: ! 401: if (SHORT1FROMMP(mp1) & KC_KEYUP) ! 402: { ! 403: if (CHAR4FROMMP(mp1) == uchMScan) ! 404: fMDown = FALSE; /* 'm' key went up */ ! 405: } ! 406: else if (SHORT1FROMMP(mp1) & KC_CHAR) ! 407: { ! 408: if (InterpretChar(CHAR1FROMMP(mp2))) ! 409: UpdateDisplay(); ! 410: else if ((CHAR1FROMMP(mp2)=='m') || (CHAR1FROMMP(mp2)=='M')) ! 411: { ! 412: uchMScan = CHAR4FROMMP(mp1); /* save 'm' key scan code */ ! 413: fMDown = TRUE; /* 'm' key went down */ ! 414: } ! 415: } ! 416: break; ! 417: ! 418: case WM_ACTIVATE: ! 419: if (HIUSHORT(mp1)) ! 420: WinSetFocus( HWND_DESKTOP, hwndCalc); ! 421: break; ! 422: ! 423: case WM_SETFOCUS: ! 424: if ((HWNDFROMMP(mp1)==hwndCalc) && !mp2); ! 425: fMDown = FALSE; /* since we are losing focus */ ! 426: break; ! 427: ! 428: dwp: ! 429: default: ! 430: return(WinDefWindowProc(hwnd, msg, mp1, mp2)); ! 431: break; ! 432: } ! 433: return(0L); ! 434: } ! 435: ! 436: ! 437: /******************************************************************************/ ! 438: /* translate & interpret keys (ie. locate in logical keyboard) */ ! 439: /******************************************************************************/ ! 440: BOOL ! 441: InterpretChar( ch) ! 442: ! 443: CHAR ch; ! 444: { ! 445: BOOL fDone; ! 446: NPCH pchStep; ! 447: INT i; ! 448: ! 449: fDone = FALSE; ! 450: pchStep = achKeys; ! 451: switch (ch) ! 452: { ! 453: case 'n': ! 454: ch = szPlusMinus[0]; ! 455: break; ! 456: case 27: /* xlate Escape into 'c' */ ! 457: ch = 'c'; ! 458: break; ! 459: case '\r': /* xlate Enter into '=' */ ! 460: ch = '='; ! 461: break; ! 462: } ! 463: ! 464: if (fMDown) /* Do memory keys */ ! 465: { ! 466: switch (ch) ! 467: { ! 468: case 'c': ! 469: case 'C': ! 470: ch = '\274'; ! 471: break; ! 472: case 'r': ! 473: case 'R': ! 474: ch = '\273'; ! 475: break; ! 476: case '+': ! 477: ch = '\272'; ! 478: break; ! 479: case '-': ! 480: ch = '\271'; ! 481: break; ! 482: } ! 483: } ! 484: ! 485: while (!fDone && *pchStep) ! 486: { ! 487: if (*pchStep++ == ch) ! 488: fDone = TRUE; /* char found in logical keyboard */ ! 489: } ! 490: if (fDone) ! 491: { ! 492: chLastKey = chCurrKey; ! 493: i = pchStep - achKeys - 1; ! 494: FlipKey( hpsCalc, i/6, i%6); ! 495: Evaluate( achKeys[i]); ! 496: } ! 497: return (fDone); ! 498: } ! 499: ! 500: ! 501: /******************************************************************************/ ! 502: /* briefly reverse the shading on one of the keys */ ! 503: /******************************************************************************/ ! 504: VOID ! 505: FlipKey( hps, iRow, iCol) ! 506: ! 507: HPS hps; ! 508: INT iRow, iCol; ! 509: { ! 510: RECTL rcl; ! 511: ! 512: rcl.xLeft = (iCol * 6 * sCharWidth) + (14 * sCharWidth / 10); ! 513: rcl.yBottom = (165 * sCharHeight / 100) + (2 * iRow * sCharHeight); ! 514: rcl.xRight = rcl.xLeft + (11 * sCharWidth / 3); ! 515: rcl.yTop = rcl.yBottom + (7 * sCharHeight / 4); ! 516: WinInvertRect( hps, &rcl); ! 517: DosSleep( 50L); ! 518: WinInvertRect( hps, &rcl); ! 519: } ! 520: ! 521: ! 522: /******************************************************************************/ ! 523: /* compute whether a point is over a button and flash the button if so */ ! 524: /******************************************************************************/ ! 525: BOOL ! 526: FlashSqr( hps, pwpt) ! 527: ! 528: HPS hps; ! 529: PWPOINT pwpt; ! 530: { ! 531: INT iRow, iCol; ! 532: BOOL fDone; ! 533: ! 534: /* find x range */ ! 535: fDone = FALSE; ! 536: iCol = 0; ! 537: iRow = 3; ! 538: while (!fDone && iCol<6) ! 539: { ! 540: if (pwpt->x < (iCol * 6 * sCharWidth) ! 541: + (14 * sCharWidth / 10) ! 542: + (11*sCharWidth/3) ) ! 543: { ! 544: if (pwpt->x > (iCol * 6 * sCharWidth) + (14 * sCharWidth / 10)) ! 545: fDone = TRUE; ! 546: else ! 547: return FALSE; ! 548: } ! 549: else ! 550: iCol++; ! 551: } ! 552: if (!fDone) ! 553: return FALSE; ! 554: fDone = FALSE; ! 555: while (!fDone && iRow >= 0) ! 556: { ! 557: if (pwpt->y > ((165 * sCharHeight / 100) + (2 * iRow * sCharHeight))) ! 558: { ! 559: if (pwpt->y < (165 * sCharHeight / 100) ! 560: + (2 * iRow * sCharHeight) ! 561: + (7 * sCharHeight / 4) ) ! 562: fDone = TRUE; ! 563: else ! 564: return FALSE; ! 565: } ! 566: else ! 567: iRow--; ! 568: } ! 569: if (!fDone) ! 570: return FALSE; ! 571: pwpt->x = iCol; ! 572: pwpt->y = iRow; ! 573: FlipKey( hps, iRow, iCol); ! 574: return TRUE; ! 575: } ! 576: ! 577: ! 578: /******************************************************************************/ ! 579: /* which key is point on? */ ! 580: /******************************************************************************/ ! 581: CHAR ! 582: Translate( pwpt) ! 583: ! 584: PWPOINT pwpt; ! 585: { ! 586: return( achKeys[ pwpt->y * 6 + pwpt->x]); ! 587: } ! 588: ! 589: ! 590: /******************************************************************************/ ! 591: /* invoke flashing, point-to-key translation, and result-display update */ ! 592: /******************************************************************************/ ! 593: VOID ! 594: ProcessKey( pwpt) ! 595: ! 596: PWPOINT pwpt; ! 597: { ! 598: BOOL fFlashed; ! 599: ! 600: chLastKey = chCurrKey; ! 601: fFlashed = FlashSqr( hpsCalc, pwpt); ! 602: ! 603: if (fFlashed) ! 604: Evaluate( (BYTE)Translate( pwpt)); ! 605: UpdateDisplay(); ! 606: } ! 607: ! 608: ! 609: /******************************************************************************/ ! 610: /* draw a blank key */ ! 611: /******************************************************************************/ ! 612: VOID ! 613: FrameKey(hps, iRow, iCol) ! 614: ! 615: HPS hps; ! 616: INT iRow, iCol; ! 617: { ! 618: POINTL aptl[3]; ! 619: ! 620: aptl[0].x = (iCol * 6 * sCharWidth) + (14 * sCharWidth / 10); ! 621: aptl[0].y = (165 * sCharHeight / 100) + (2 * iRow * sCharHeight); ! 622: aptl[1].x = (11 * sCharWidth / 3) + (aptl[0].x); ! 623: aptl[1].y = (7 * sCharHeight / 4) + (aptl[0].y); ! 624: aptl[2].x = 0; ! 625: aptl[2].y = 0; ! 626: GpiBitBlt( hps, hpsLocal, 3L, aptl, ROP_SRCCOPY, BBO_IGNORE); ! 627: } ! 628: ! 629: ! 630: /******************************************************************************/ ! 631: /* draw the keys and fill in numbers */ ! 632: /******************************************************************************/ ! 633: VOID ! 634: DrawNumbers(hps) ! 635: ! 636: HPS hps; ! 637: { ! 638: INT iRow, iCol; ! 639: ! 640: /* Draw the keys and fill in the numbers we can */ ! 641: for (iRow = 0; iRow < 4; iRow++) ! 642: { ! 643: for (iCol = 0; iCol < 6; iCol++) ! 644: { ! 645: FrameKey( hps, iRow, iCol); ! 646: CalcTextOut( hps ! 647: , (iCol * 6 * sCharWidth) ! 648: + (WIDTHCONST * sCharWidth / 10) ! 649: , (iRow + 1) * 2 * sCharHeight ! 650: , (PSZ)(achDKeys + (iRow * 6) + iCol) ! 651: , 1 ); ! 652: } ! 653: } ! 654: } ! 655: ! 656: ! 657: /******************************************************************************/ ! 658: /* redraw the whole calculator */ ! 659: /******************************************************************************/ ! 660: VOID ! 661: CalcPaint( hwnd, hps) ! 662: ! 663: HWND hwnd; ! 664: HPS hps; ! 665: { ! 666: RECTL rclDst; ! 667: CHARBUNDLE cbnd; ! 668: INT iX, iY; ! 669: ! 670: WinQueryWindowRect( hwnd, &rclDst); ! 671: WinFillRect( hps, &rclDst, CLR_GREEN); ! 672: ! 673: DrawNumbers(hps); ! 674: CalcTextOut(hps, iX = (11 * sCharWidth / 5) + 1, iY = 2 * sCharHeight, ! 675: (PSZ)"M-", 2); ! 676: CalcTextOut(hps, iX, iY + 2 * sCharHeight, (PSZ)"M+", 2); ! 677: CalcTextOut(hps, iX, iY + 4 * sCharHeight, (PSZ)"MR", 2); ! 678: CalcTextOut(hps, iX, iY + 6 * sCharHeight, (PSZ)"MC", 2); ! 679: ! 680: /* Draw the minus of the plus/minus button */ ! 681: cbnd.usBackMixMode = FM_LEAVEALONE; ! 682: GpiSetAttrs( hps, PRIM_CHAR, CBB_BACK_MIX_MODE, 0L, &cbnd); ! 683: iX = (3 * 6 * sCharWidth) + (WIDTHCONST * sCharWidth / 10); ! 684: CalcTextOut( hps, iX, iY + sCharHeight / 4, (PSZ)"_", 1); ! 685: ! 686: /* Draw the square root bitmap */ ! 687: rclDst.xLeft = 160 * sCharWidth / 5; ! 688: rclDst.yBottom = 31 * sCharHeight / 4; ! 689: rclDst.xRight = rclDst.xLeft + 2 * sCharWidth; ! 690: rclDst.yTop = rclDst.yBottom + (3 * sCharHeight / 2); ! 691: WinDrawBitmap( hps ! 692: , hbmSqr ! 693: , NULL ! 694: , (PPOINTL)&rclDst ! 695: , CLR_WHITE ! 696: , CLR_BLACK ! 697: , DBM_STRETCH ); ! 698: ! 699: UpdateDisplay(); ! 700: } ! 701: ! 702: ! 703: /******************************************************************************/ ! 704: /* initialize the bitmaps for a blank key and for the square-root sign */ ! 705: /******************************************************************************/ ! 706: BOOL ! 707: PSInit() ! 708: { ! 709: HPS hps; ! 710: FONTMETRICS fm; ! 711: POINTL ptl; ! 712: SIZEL sizl; ! 713: BITMAPINFOHEADER bmp; ! 714: POINTL aptl[4]; ! 715: LONG alCaps[2]; ! 716: ! 717: /**************************************************************************/ ! 718: /* compute the units of horizontal and vertical distance based on font */ ! 719: /**************************************************************************/ ! 720: hps = WinGetPS( HWND_DESKTOP); ! 721: GpiQueryFontMetrics( hps, (LONG)sizeof(FONTMETRICS), &fm); ! 722: sCharHeight = (SHORT)(fm.lEmHeight); /* avg height of uppercase character */ ! 723: sCharWidth = (SHORT)(fm.lEmInc); /* usually 'M' increment */ ! 724: WinReleasePS( hps); ! 725: ! 726: /**************************************************************************/ ! 727: /* prepare the square root bitmap */ ! 728: /**************************************************************************/ ! 729: hdcSqr = DevOpenDC( hab, OD_MEMORY, "*", 3L, (PDEVOPENDATA)&dop, NULL); ! 730: if( !hdcSqr) ! 731: return(FALSE); ! 732: ! 733: sizl.cx = sizl.cy = 0L; ! 734: hpsSqr = GpiCreatePS( hab ! 735: , hdcSqr ! 736: , &sizl ! 737: , PU_PELS | GPIT_MICRO | GPIA_ASSOC ); ! 738: hbmSqr = GpiLoadBitmap( hpsSqr, NULL, IDB_SQR, 0L, 0L); ! 739: ! 740: /**************************************************************************/ ! 741: /* prepare the bitmap of a blank key */ ! 742: /**************************************************************************/ ! 743: hdcLocal = DevOpenDC( hab, OD_MEMORY, "*", 3L, (PDEVOPENDATA)&dop, NULL); ! 744: if( !hdcLocal) ! 745: return(FALSE); ! 746: ! 747: sizl.cx = sizl.cy = 0L; ! 748: hpsLocal = GpiCreatePS( hab ! 749: , hdcLocal ! 750: , &sizl ! 751: , PU_PELS | GPIT_MICRO | GPIA_ASSOC ); ! 752: bmp.cbFix = 12; ! 753: bmp.cx = 11 * sCharWidth / 3; ! 754: bmp.cy = sCharHeight * 2; ! 755: DevQueryCaps( hdcLocal, CAPS_COLOR_PLANES, 2L, alCaps); ! 756: bmp.cPlanes = (USHORT)alCaps[0]; ! 757: bmp.cBitCount = (USHORT)alCaps[1]; ! 758: hbmLocal = GpiCreateBitmap( hpsLocal, (PBITMAPINFOHEADER2)&bmp, 0L, NULL, NULL); ! 759: if( !hbmLocal ) ! 760: return(FALSE); ! 761: GpiSetBitmap( hpsLocal, hbmLocal); ! 762: ! 763: aptl[0].x = aptl[0].y = 0; ! 764: aptl[1].x = 11 * sCharWidth / 3; ! 765: aptl[1].y = 7 * sCharHeight / 4; ! 766: aptl[2].x = aptl[2].y = 0; ! 767: aptl[3].x = aptl[1].x; ! 768: aptl[3].y = aptl[1].y; ! 769: GpiSetColor( hpsLocal, CLR_GREEN); /* match the background to client */ ! 770: GpiBitBlt( hpsLocal, NULL, 2L, aptl, ROP_PATCOPY, BBO_IGNORE); ! 771: ! 772: /* Draw the rounded rect */ ! 773: ptl.x = 0; ! 774: ptl.y = 0; ! 775: GpiSetCurrentPosition( hpsLocal, &ptl); ! 776: ptl.x = (11 * sCharWidth / 3) - 1; ! 777: ptl.y = (7 * sCharHeight / 4) - 1; ! 778: GpiSetColor( hpsLocal, CLR_WHITE); /* white interior */ ! 779: GpiBox( hpsLocal ! 780: , DRO_FILL ! 781: , &ptl ! 782: , (LONG)sCharWidth ! 783: , (LONG)(sCharHeight / 2) ); ! 784: ptl.x = 0; ! 785: ptl.y = 0; ! 786: GpiSetCurrentPosition( hpsLocal, &ptl); ! 787: ptl.x = (11 * sCharWidth / 3) - 1; ! 788: ptl.y = (7 * sCharHeight / 4) - 1; ! 789: GpiSetColor( hpsLocal, CLR_BLACK); /* black border */ ! 790: GpiBox( hpsLocal ! 791: , DRO_OUTLINE ! 792: , &ptl ! 793: , (LONG)sCharWidth ! 794: , (LONG)(sCharHeight / 2) ); ! 795: return( TRUE); ! 796: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.