|
|
1.1 ! root 1: /*- ! 2: * apolloGC.c -- ! 3: * Functions to support the meddling with GC's we do to preserve ! 4: * the software cursor... ! 5: * ! 6: * Copyright (c) 1987 by the Regents of the University of California ! 7: * ! 8: * Permission to use, copy, modify, and distribute this ! 9: * software and its documentation for any purpose and without ! 10: * fee is hereby granted, provided that the above copyright ! 11: * notice appear in all copies. The University of California ! 12: * makes no representations about the suitability of this ! 13: * software for any purpose. It is provided "as is" without ! 14: * express or implied warranty. ! 15: * ! 16: * ! 17: */ ! 18: ! 19: #include "apollo.h" ! 20: #include "../mi/mifpoly.h" /* for SppPointPtr */ ! 21: ! 22: apProcPtrs apProcs; ! 23: ! 24: /* ! 25: * Overlap BoxPtr and Box elements ! 26: */ ! 27: #define BOX_OVERLAP(pCbox,X1,Y1,X2,Y2) \ ! 28: (((pCbox)->x1 <= (X2)) && ((X1) <= (pCbox)->x2) && \ ! 29: ((pCbox)->y1 <= (Y2)) && ((Y1) <= (pCbox)->y2)) ! 30: ! 31: /* ! 32: * Overlap BoxPtr, origins, and rectangle ! 33: */ ! 34: #define ORG_OVERLAP(pCbox,xorg,yorg,x,y,w,h) \ ! 35: BOX_OVERLAP((pCbox),(x)+(xorg),(y)+(yorg),(x)+(xorg)+(w),(y)+(yorg)+(h)) ! 36: ! 37: /* ! 38: * Overlap BoxPtr, origins and RectPtr ! 39: */ ! 40: #define ORGRECT_OVERLAP(pCbox,xorg,yorg,pRect) \ ! 41: ORG_OVERLAP((pCbox),(xorg),(yorg),(pRect)->x,(pRect)->y,(pRect)->width, \ ! 42: (pRect)->height) ! 43: /* ! 44: * Overlap BoxPtr and horizontal span ! 45: */ ! 46: #define SPN_OVERLAP(pCbox,y,x,w) BOX_OVERLAP((pCbox),(x),(y),(x)+(w),(y)) ! 47: ! 48: ! 49: #ifdef notdef ! 50: #define COMPARE_GCS(g1, g2) compare_gcs(g1, g2) ! 51: ! 52: static ! 53: compare_gcs(g1, g2) ! 54: GCPtr g1, g2; ! 55: { ! 56: if (g1->pScreen != g2->pScreen) FatalError("GC and Shadow mis-match - pScreen\n"); ! 57: if (g1->depth != g2->depth) FatalError("GC and Shadow mis-match - depth\n"); ! 58: #ifdef notdef ! 59: if (g1->serialNumber != g2->serialNumber) FatalError("GC and Shadow mis-match - serialNumber\n"); ! 60: #endif ! 61: if (g1->alu != g2->alu) FatalError("GC and Shadow mis-match - alu\n"); ! 62: if (g1->planemask != g2->planemask) FatalError("GC and Shadow mis-match - planemask\n"); ! 63: if (g1->fgPixel != g2->fgPixel) FatalError("GC and Shadow mis-match - fgPixel\n"); ! 64: if (g1->bgPixel != g2->bgPixel) FatalError("GC and Shadow mis-match - bgPixel\n"); ! 65: if (g1->lineWidth != g2->lineWidth) FatalError("GC and Shadow mis-match - lineWidth\n"); ! 66: if (g1->lineStyle != g2->lineStyle) FatalError("GC and Shadow mis-match - lineStyle\n"); ! 67: if (g1->capStyle != g2->capStyle) FatalError("GC and Shadow mis-match - capStyle\n"); ! 68: if (g1->joinStyle != g2->joinStyle) FatalError("GC and Shadow mis-match - joinStyle\n"); ! 69: if (g1->fillStyle != g2->fillStyle) FatalError("GC and Shadow mis-match - fillStyle\n"); ! 70: if (g1->fillRule != g2->fillRule) FatalError("GC and Shadow mis-match - fillRule\n"); ! 71: if (g1->arcMode != g2->arcMode) FatalError("GC and Shadow mis-match - arcMode\n"); ! 72: if (g1->tile != g2->tile) FatalError("GC and Shadow mis-match - tile\n"); ! 73: if (g1->stipple != g2->stipple) FatalError("GC and Shadow mis-match - stipple\n"); ! 74: if (g1->patOrg.x != g2->patOrg.x) FatalError("GC and Shadow mis-match - patOrg.x\n"); ! 75: if (g1->patOrg.y != g2->patOrg.y) FatalError("GC and Shadow mis-match - patOrg.y\n"); ! 76: if (g1->font != g2->font) FatalError("GC and Shadow mis-match - font\n"); ! 77: if (g1->subWindowMode != g2->subWindowMode) FatalError("GC and Shadow mis-match - subWindowMode\n"); ! 78: if (g1->graphicsExposures != g2->graphicsExposures) FatalError("GC and Shadow mis-match - graphicsExposures\n"); ! 79: if (g1->clipOrg.x != g2->clipOrg.x) FatalError("GC and Shadow mis-match - clipOrg.x\n"); ! 80: if (g1->clipOrg.y != g2->clipOrg.y) FatalError("GC and Shadow mis-match - clipOrg.y\n"); ! 81: #ifdef notdef ! 82: if (g1->clientClip != g2->clientClip) FatalError("GC and Shadow mis-match - clientClip\n"); ! 83: #endif ! 84: if (g1->clientClipType != g2->clientClipType) FatalError("GC and Shadow mis-match - clientClipType\n"); ! 85: if (g1->dashOffset != g2->dashOffset) FatalError("GC and Shadow mis-match - dashOffset\n"); ! 86: if (g1->numInDashList != g2->numInDashList) FatalError("GC and Shadow mis-match - numInDashList\n"); ! 87: #ifdef notdef ! 88: if (g1->dash != g2->dash) FatalError("GC and Shadow mis-match - dash\n"); ! 89: if (g1->stateChanges != g2->stateChanges) FatalError("GC and Shadow mis-match - stateChanges\n"); ! 90: #endif ! 91: if (g1->lastWinOrg.x != g2->lastWinOrg.x) FatalError("GC and Shadow mis-match - lastWinOrg.x\n"); ! 92: if (g1->lastWinOrg.y != g2->lastWinOrg.y) FatalError("GC and Shadow mis-match - lastWinOrg.y\n"); ! 93: if (g1->miTranslate != g2->miTranslate) FatalError("GC and Shadow mis-match - miTranslate\n"); ! 94: ! 95: } ! 96: #else ! 97: #define COMPARE_GCS(g1, g2) ! 98: #endif ! 99: ! 100: ! 101: /*- ! 102: *----------------------------------------------------------------------- ! 103: * apSaveCursorBox -- ! 104: * Given an array of points, figure out the bounding box for the ! 105: * series and remove the cursor if it overlaps that box. ! 106: * ! 107: * Results: ! 108: * ! 109: * Side Effects: ! 110: * ! 111: *----------------------------------------------------------------------- ! 112: */ ! 113: void ! 114: apSaveCursorBox (xorg, yorg, mode, pPts, nPts, pCursorBox) ! 115: register int xorg; /* X-Origin for points */ ! 116: register int yorg; /* Y-Origin for points */ ! 117: int mode; /* CoordModeOrigin or ! 118: * CoordModePrevious */ ! 119: register DDXPointPtr pPts; /* Array of points */ ! 120: int nPts; /* Number of points */ ! 121: register BoxPtr pCursorBox; /* Bounding box for cursor */ ! 122: { ! 123: register int minx, ! 124: miny, ! 125: maxx, ! 126: maxy; ! 127: ! 128: minx = maxx = pPts->x + xorg; ! 129: miny = maxy = pPts->y + yorg; ! 130: ! 131: pPts++; ! 132: nPts--; ! 133: ! 134: if (mode == CoordModeOrigin) { ! 135: while (nPts--) { ! 136: minx = min(minx, pPts->x + xorg); ! 137: maxx = max(maxx, pPts->x + xorg); ! 138: miny = min(miny, pPts->y + yorg); ! 139: maxy = max(maxy, pPts->y + yorg); ! 140: pPts++; ! 141: } ! 142: } else { ! 143: xorg = minx; ! 144: yorg = miny; ! 145: while (nPts--) { ! 146: minx = min(minx, pPts->x + xorg); ! 147: maxx = max(maxx, pPts->x + xorg); ! 148: miny = min(miny, pPts->y + yorg); ! 149: maxy = max(maxy, pPts->y + yorg); ! 150: xorg += pPts->x; ! 151: yorg += pPts->y; ! 152: pPts++; ! 153: } ! 154: } ! 155: if (BOX_OVERLAP(pCursorBox,minx,miny,maxx,maxy)) { ! 156: apRemoveCursor(TRUE); ! 157: } ! 158: } ! 159: ! 160: /*- ! 161: *----------------------------------------------------------------------- ! 162: * apFillSpans -- ! 163: * Remove the cursor if any of the spans overlaps the area covered ! 164: * by the cursor. This assumes the points have been translated ! 165: * already, though perhaps it shouldn't... ! 166: * ! 167: * Results: ! 168: * None. ! 169: * ! 170: * Side Effects: ! 171: * ! 172: *----------------------------------------------------------------------- ! 173: */ ! 174: void ! 175: apFillSpans(pDrawable, pGC, nInit, pptInit, pwidthInit, fSorted) ! 176: DrawablePtr pDrawable; ! 177: GCPtr pGC; ! 178: int nInit; /* number of spans to fill */ ! 179: DDXPointPtr pptInit; /* pointer to list of start points */ ! 180: int *pwidthInit; /* pointer to list of n widths */ ! 181: int fSorted; ! 182: { ! 183: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 184: ! 185: if (pDrawable->type == DRAWABLE_WINDOW) { ! 186: BoxRec cursorBox; ! 187: ! 188: if (apCursorLoc (pDrawable->pScreen, &cursorBox)) { ! 189: register DDXPointPtr pts; ! 190: register int *widths; ! 191: register int nPts; ! 192: ! 193: for (pts = pptInit, widths = pwidthInit, nPts = nInit; ! 194: nPts--; ! 195: pts++, widths++) { ! 196: if (SPN_OVERLAP(&cursorBox,pts->y,pts->x,*widths)) { ! 197: apRemoveCursor(TRUE); ! 198: break; ! 199: } ! 200: } ! 201: } ! 202: } ! 203: ! 204: COMPARE_GCS(pGC,pShadowGC); ! 205: (* pShadowGC->FillSpans)(pDrawable, pShadowGC, nInit, pptInit, ! 206: pwidthInit, fSorted); ! 207: } ! 208: ! 209: /*- ! 210: *----------------------------------------------------------------------- ! 211: * apSetSpans -- ! 212: * Remove the cursor if any of the horizontal segments overlaps ! 213: * the area covered by the cursor. This also assumes the spans ! 214: * have been translated from the window's coordinates to the ! 215: * screen's. ! 216: * Results: ! 217: * None. ! 218: * ! 219: * Side Effects: ! 220: * ! 221: *----------------------------------------------------------------------- ! 222: */ ! 223: void ! 224: apSetSpans(pDrawable, pGC, psrc, ppt, pwidth, nspans, fSorted) ! 225: DrawablePtr pDrawable; ! 226: GCPtr pGC; ! 227: int *psrc; ! 228: register DDXPointPtr ppt; ! 229: int *pwidth; ! 230: int nspans; ! 231: int fSorted; ! 232: { ! 233: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 234: ! 235: if (pDrawable->type == DRAWABLE_WINDOW) { ! 236: BoxRec cursorBox; ! 237: ! 238: if (apCursorLoc (pDrawable->pScreen, &cursorBox)) { ! 239: register DDXPointPtr pts; ! 240: register int *widths; ! 241: register int nPts; ! 242: ! 243: for (pts = ppt, widths = pwidth, nPts = nspans; ! 244: nPts--; ! 245: pts++, widths++) { ! 246: if (SPN_OVERLAP(&cursorBox,pts->y,pts->x,*widths)) { ! 247: apRemoveCursor(TRUE); ! 248: break; ! 249: } ! 250: } ! 251: } ! 252: } ! 253: ! 254: COMPARE_GCS(pGC,pShadowGC); ! 255: (* pShadowGC->SetSpans) (pDrawable, pShadowGC, psrc, ppt, pwidth, ! 256: nspans, fSorted); ! 257: } ! 258: ! 259: /*- ! 260: *----------------------------------------------------------------------- ! 261: * apGetSpans -- ! 262: * Remove the cursor if any of the desired spans overlaps the cursor. ! 263: * ! 264: * Results: ! 265: * ! 266: * Side Effects: ! 267: * ! 268: *----------------------------------------------------------------------- ! 269: */ ! 270: unsigned int * ! 271: apGetSpans(pDrawable, wMax, ppt, pwidth, nspans) ! 272: DrawablePtr pDrawable; /* drawable from which to get bits */ ! 273: int wMax; /* largest value of all *pwidths */ ! 274: register DDXPointPtr ppt; /* points to start copying from */ ! 275: int *pwidth; /* list of number of bits to copy */ ! 276: int nspans; /* number of scanlines to copy */ ! 277: { ! 278: if (pDrawable->type == DRAWABLE_WINDOW) { ! 279: BoxRec cursorBox; ! 280: ! 281: if (apCursorLoc (pDrawable->pScreen, &cursorBox)) { ! 282: register DDXPointPtr pts; ! 283: register int *widths; ! 284: register int nPts; ! 285: register int xorg, ! 286: yorg; ! 287: ! 288: xorg = ((WindowPtr)pDrawable)->absCorner.x; ! 289: yorg = ((WindowPtr)pDrawable)->absCorner.y; ! 290: ! 291: for (pts = ppt, widths = pwidth, nPts = nspans; ! 292: nPts--; ! 293: pts++, widths++) { ! 294: if (SPN_OVERLAP(&cursorBox,pts->y+yorg, ! 295: pts->x+xorg,*widths)) { ! 296: apRemoveCursor(TRUE); ! 297: break; ! 298: } ! 299: } ! 300: } ! 301: } ! 302: ! 303: /* ! 304: * XXX: Because we have no way to get at the GC used to call us, ! 305: * we must rely on the GetSpans vector never changing and stick it ! 306: * in the fbFd structure. Gross. ! 307: */ ! 308: return (* apProcs.GetSpans) (pDrawable, wMax, ppt, pwidth, nspans); ! 309: } ! 310: ! 311: /*- ! 312: *----------------------------------------------------------------------- ! 313: * apPutImage -- ! 314: * Remove the cursor if it is in the way of the image to be ! 315: * put down... ! 316: * ! 317: * Results: ! 318: * None. ! 319: * ! 320: * Side Effects: ! 321: * ! 322: *----------------------------------------------------------------------- ! 323: */ ! 324: void ! 325: apPutImage(pDst, pGC, depth, x, y, w, h, leftPad, format, pBits) ! 326: DrawablePtr pDst; ! 327: GCPtr pGC; ! 328: int depth; ! 329: int x; ! 330: int y; ! 331: int w; ! 332: int h; ! 333: int format; ! 334: char *pBits; ! 335: { ! 336: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 337: ! 338: if (pDst->type == DRAWABLE_WINDOW) { ! 339: BoxRec cursorBox; ! 340: if (apCursorLoc (pDst->pScreen, &cursorBox)) { ! 341: register WindowPtr pWin = (WindowPtr)pDst; ! 342: ! 343: if (ORG_OVERLAP(&cursorBox,pWin->absCorner.x,pWin->absCorner.y, ! 344: x,y,w,h)) { ! 345: apRemoveCursor(TRUE); ! 346: } ! 347: } ! 348: } ! 349: ! 350: COMPARE_GCS(pGC,pShadowGC); ! 351: (* pShadowGC->PutImage) (pDst, pShadowGC, depth, x, y, w, h, ! 352: leftPad, format, pBits); ! 353: } ! 354: ! 355: /*- ! 356: *----------------------------------------------------------------------- ! 357: * apGetImage -- ! 358: * Remove the cursor if it overlaps the image to be gotten. ! 359: * ! 360: * Results: ! 361: * None. ! 362: * ! 363: * Side Effects: ! 364: * ! 365: *----------------------------------------------------------------------- ! 366: */ ! 367: void ! 368: apGetImage (pSrc, x, y, w, h, format, planeMask, pBits) ! 369: DrawablePtr pSrc; ! 370: int x; ! 371: int y; ! 372: int w; ! 373: int h; ! 374: unsigned int format; ! 375: unsigned int planeMask; ! 376: int *pBits; ! 377: { ! 378: if (pSrc->type == DRAWABLE_WINDOW) { ! 379: BoxRec cursorBox; ! 380: ! 381: if (apCursorLoc(pSrc->pScreen, &cursorBox)) { ! 382: register WindowPtr pWin = (WindowPtr)pSrc; ! 383: ! 384: if (ORG_OVERLAP(&cursorBox,pWin->absCorner.x,pWin->absCorner.y, ! 385: x,y,w,h)) { ! 386: apRemoveCursor(TRUE); ! 387: } ! 388: } ! 389: } ! 390: ! 391: (* apProcs.GetImage) (pSrc, x, y, w, h, format, planeMask, pBits); ! 392: } ! 393: ! 394: /*- ! 395: *----------------------------------------------------------------------- ! 396: * apCopyArea -- ! 397: * Remove the cursor if it overlaps either the source or destination ! 398: * drawables, then call the screen-specific CopyArea routine. ! 399: * ! 400: * Results: ! 401: * None. ! 402: * ! 403: * Side Effects: ! 404: * ! 405: *----------------------------------------------------------------------- ! 406: */ ! 407: void ! 408: apCopyArea (pSrc, pDst, pGC, srcx, srcy, w, h, dstx, dsty) ! 409: DrawablePtr pSrc; ! 410: DrawablePtr pDst; ! 411: GCPtr pGC; ! 412: int srcx; ! 413: int srcy; ! 414: int w; ! 415: int h; ! 416: int dstx; ! 417: int dsty; ! 418: { ! 419: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 420: BoxRec cursorBox; ! 421: register WindowPtr pWin; ! 422: int out = FALSE; ! 423: ! 424: if (pSrc->type == DRAWABLE_WINDOW && ! 425: apCursorLoc(pSrc->pScreen, &cursorBox)) { ! 426: pWin = (WindowPtr)pSrc; ! 427: ! 428: if (ORG_OVERLAP(&cursorBox,pWin->absCorner.x,pWin->absCorner.y, ! 429: srcx, srcy, w, h)) { ! 430: apRemoveCursor(TRUE); ! 431: out = TRUE; ! 432: } ! 433: } ! 434: ! 435: if (!out && pDst->type == DRAWABLE_WINDOW && ! 436: apCursorLoc(pDst->pScreen, &cursorBox)) { ! 437: pWin = (WindowPtr)pDst; ! 438: ! 439: if (ORG_OVERLAP(&cursorBox,pWin->absCorner.x,pWin->absCorner.y, ! 440: dstx, dsty, w, h)) { ! 441: apRemoveCursor(TRUE); ! 442: } ! 443: } ! 444: ! 445: COMPARE_GCS(pGC,pShadowGC); ! 446: (* pShadowGC->CopyArea) (pSrc, pDst, pShadowGC, srcx, srcy, ! 447: w, h, dstx, dsty); ! 448: } ! 449: ! 450: /*- ! 451: *----------------------------------------------------------------------- ! 452: * apCopyPlane -- ! 453: * Remove the cursor as necessary and call the screen-specific ! 454: * CopyPlane function. ! 455: * ! 456: * Results: ! 457: * None. ! 458: * ! 459: * Side Effects: ! 460: * ! 461: *----------------------------------------------------------------------- ! 462: */ ! 463: void ! 464: apCopyPlane (pSrc, pDst, pGC, srcx, srcy, w, h, dstx, dsty, plane) ! 465: DrawablePtr pSrc; ! 466: DrawablePtr pDst; ! 467: register GC *pGC; ! 468: int srcx, ! 469: srcy; ! 470: int w, ! 471: h; ! 472: int dstx, ! 473: dsty; ! 474: unsigned int plane; ! 475: { ! 476: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 477: BoxRec cursorBox; ! 478: register WindowPtr pWin; ! 479: int out = FALSE; ! 480: ! 481: if (pSrc->type == DRAWABLE_WINDOW && ! 482: apCursorLoc(pSrc->pScreen, &cursorBox)) { ! 483: pWin = (WindowPtr)pSrc; ! 484: ! 485: if (ORG_OVERLAP(&cursorBox,pWin->absCorner.x,pWin->absCorner.y, ! 486: srcx, srcy, w, h)) { ! 487: apRemoveCursor(TRUE); ! 488: out = TRUE; ! 489: } ! 490: } ! 491: ! 492: if (!out && pDst->type == DRAWABLE_WINDOW && ! 493: apCursorLoc(pDst->pScreen, &cursorBox)) { ! 494: pWin = (WindowPtr)pDst; ! 495: ! 496: if (ORG_OVERLAP(&cursorBox,pWin->absCorner.x,pWin->absCorner.y, ! 497: dstx, dsty, w, h)) { ! 498: apRemoveCursor(TRUE); ! 499: } ! 500: } ! 501: ! 502: COMPARE_GCS(pGC,pShadowGC); ! 503: (* pShadowGC->CopyPlane) (pSrc, pDst, pShadowGC, srcx, srcy, w, h, ! 504: dstx, dsty, plane); ! 505: } ! 506: ! 507: /*- ! 508: *----------------------------------------------------------------------- ! 509: * apPolyPoint -- ! 510: * See if any of the points lies within the area covered by the ! 511: * cursor and remove the cursor if one does. Then put the points ! 512: * down. ! 513: * ! 514: * Results: ! 515: * None. ! 516: * ! 517: * Side Effects: ! 518: * ! 519: *----------------------------------------------------------------------- ! 520: */ ! 521: void ! 522: apPolyPoint (pDrawable, pGC, mode, npt, pptInit) ! 523: DrawablePtr pDrawable; ! 524: GCPtr pGC; ! 525: int mode; /* Origin or Previous */ ! 526: int npt; ! 527: xPoint *pptInit; ! 528: { ! 529: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 530: register xPoint *pts; ! 531: register int nPts; ! 532: register int xorg; ! 533: register int yorg; ! 534: BoxRec cursorBox; ! 535: ! 536: if (pDrawable->type == DRAWABLE_WINDOW && ! 537: apCursorLoc (pDrawable->pScreen, &cursorBox)) { ! 538: xorg = ((WindowPtr)pDrawable)->absCorner.x; ! 539: yorg = ((WindowPtr)pDrawable)->absCorner.y; ! 540: ! 541: if (mode == CoordModeOrigin) { ! 542: for (pts = pptInit, nPts = npt; nPts--; pts++) { ! 543: if (ORG_OVERLAP(&cursorBox,xorg,yorg,pts->x,pts->y,0,0)){ ! 544: apRemoveCursor(TRUE); ! 545: break; ! 546: } ! 547: } ! 548: } else { ! 549: for (pts = pptInit, nPts = npt; nPts--; pts++) { ! 550: if (ORG_OVERLAP(&cursorBox,xorg,yorg,pts->x,pts->y,0,0)){ ! 551: apRemoveCursor(TRUE); ! 552: break; ! 553: } else { ! 554: xorg += pts->x; ! 555: yorg += pts->y; ! 556: } ! 557: } ! 558: } ! 559: } ! 560: ! 561: COMPARE_GCS(pGC,pShadowGC); ! 562: (* pShadowGC->PolyPoint) (pDrawable, pShadowGC, mode, npt, pptInit); ! 563: } ! 564: ! 565: /*- ! 566: *----------------------------------------------------------------------- ! 567: * apPolylines -- ! 568: * Find the bounding box of the lines and remove the cursor if ! 569: * the box overlaps the area covered by the cursor. Then call ! 570: * the screen's Polylines function to draw the lines themselves. ! 571: * ! 572: * Results: ! 573: * ! 574: * Side Effects: ! 575: * ! 576: *----------------------------------------------------------------------- ! 577: */ ! 578: void ! 579: apPolylines (pDrawable, pGC, mode, npt, pptInit) ! 580: DrawablePtr pDrawable; ! 581: GCPtr pGC; ! 582: int mode; ! 583: int npt; ! 584: DDXPointPtr pptInit; ! 585: { ! 586: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 587: BoxRec cursorBox; ! 588: ! 589: if (pDrawable->type == DRAWABLE_WINDOW && ! 590: apCursorLoc (pDrawable->pScreen, &cursorBox)) { ! 591: apSaveCursorBox(((WindowPtr)pDrawable)->absCorner.x, ! 592: ((WindowPtr)pDrawable)->absCorner.y, ! 593: mode, ! 594: pptInit, ! 595: npt, ! 596: &cursorBox); ! 597: } ! 598: COMPARE_GCS(pGC,pShadowGC); ! 599: (*pShadowGC->Polylines) (pDrawable, pShadowGC, mode, npt, pptInit); ! 600: } ! 601: ! 602: /*- ! 603: *----------------------------------------------------------------------- ! 604: * apPolySegment -- ! 605: * Treat each segment as a box and remove the cursor if any box ! 606: * overlaps the cursor's area. Then draw the segments. Note that ! 607: * the endpoints of the segments are in no way guaranteed to be ! 608: * in the right order, so we find the bounding box of the segment ! 609: * in two comparisons and use that to figure things out. ! 610: * ! 611: * Results: ! 612: * None. ! 613: * ! 614: * Side Effects: ! 615: * ! 616: *----------------------------------------------------------------------- ! 617: */ ! 618: void ! 619: apPolySegment(pDraw, pGC, nseg, pSegs) ! 620: DrawablePtr pDraw; ! 621: GCPtr pGC; ! 622: int nseg; ! 623: xSegment *pSegs; ! 624: { ! 625: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 626: register xSegment *pSeg; ! 627: register int nSeg; ! 628: register int xorg, ! 629: yorg; ! 630: BoxRec cursorBox; ! 631: Bool nuke = FALSE; ! 632: ! 633: if (pDraw->type == DRAWABLE_WINDOW && ! 634: apCursorLoc (pDraw->pScreen, &cursorBox)) { ! 635: xorg = ((WindowPtr)pDraw)->absCorner.x; ! 636: yorg = ((WindowPtr)pDraw)->absCorner.y; ! 637: ! 638: for (nSeg = nseg, pSeg = pSegs; nSeg--; pSeg++) { ! 639: if (pSeg->x1 < pSeg->x2) { ! 640: if (pSeg->y1 < pSeg->y2) { ! 641: nuke = BOX_OVERLAP(&cursorBox, ! 642: pSeg->x1+xorg,pSeg->y1+yorg, ! 643: pSeg->x2+xorg,pSeg->y2+yorg); ! 644: } else { ! 645: nuke = BOX_OVERLAP(&cursorBox, ! 646: pSeg->x1+xorg,pSeg->y2+yorg, ! 647: pSeg->x2+xorg,pSeg->y1+yorg); ! 648: } ! 649: } else if (pSeg->y1 < pSeg->y2) { ! 650: nuke = BOX_OVERLAP(&cursorBox, ! 651: pSeg->x2+xorg,pSeg->y1+yorg, ! 652: pSeg->x1+xorg,pSeg->y2+yorg); ! 653: } else { ! 654: nuke = BOX_OVERLAP(&cursorBox, ! 655: pSeg->x2+xorg,pSeg->y2+yorg, ! 656: pSeg->x1+xorg,pSeg->y1+yorg); ! 657: } ! 658: if (nuke) { ! 659: apRemoveCursor(TRUE); ! 660: break; ! 661: } ! 662: } ! 663: } ! 664: ! 665: COMPARE_GCS(pGC,pShadowGC); ! 666: (* pShadowGC->PolySegment) (pDraw, pShadowGC, nseg, pSegs); ! 667: } ! 668: ! 669: /*- ! 670: *----------------------------------------------------------------------- ! 671: * apPolyRectangle -- ! 672: * Remove the cursor if it overlaps any of the rectangles to be ! 673: * drawn, then draw them. ! 674: * ! 675: * Results: ! 676: * None ! 677: * ! 678: * Side Effects: ! 679: * ! 680: *----------------------------------------------------------------------- ! 681: */ ! 682: void ! 683: apPolyRectangle(pDraw, pGC, nrects, pRects) ! 684: DrawablePtr pDraw; ! 685: GCPtr pGC; ! 686: int nrects; ! 687: xRectangle *pRects; ! 688: { ! 689: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 690: register xRectangle *pRect; ! 691: register int nRect; ! 692: register int xorg, ! 693: yorg; ! 694: BoxRec cursorBox; ! 695: ! 696: if (pDraw->type == DRAWABLE_WINDOW && ! 697: apCursorLoc (pDraw->pScreen, &cursorBox)) { ! 698: xorg = ((WindowPtr)pDraw)->absCorner.x; ! 699: yorg = ((WindowPtr)pDraw)->absCorner.y; ! 700: ! 701: for (nRect = nrects, pRect = pRects; nRect--; pRect++) { ! 702: if (ORGRECT_OVERLAP(&cursorBox,xorg,yorg,pRect)){ ! 703: apRemoveCursor(TRUE); ! 704: break; ! 705: } ! 706: } ! 707: } ! 708: ! 709: COMPARE_GCS(pGC,pShadowGC); ! 710: (* pShadowGC->PolyRectangle) (pDraw, pShadowGC, nrects, pRects); ! 711: } ! 712: ! 713: /*- ! 714: *----------------------------------------------------------------------- ! 715: * apPolyArc -- ! 716: * Using the bounding rectangle of each arc, remove the cursor ! 717: * if it overlaps any arc, then draw all the arcs. ! 718: * ! 719: * Results: ! 720: * ! 721: * Side Effects: ! 722: * ! 723: *----------------------------------------------------------------------- ! 724: */ ! 725: void ! 726: apPolyArc(pDraw, pGC, narcs, parcs) ! 727: DrawablePtr pDraw; ! 728: GCPtr pGC; ! 729: int narcs; ! 730: xArc *parcs; ! 731: { ! 732: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 733: register xArc *pArc; ! 734: register int nArc; ! 735: register int xorg, ! 736: yorg; ! 737: BoxRec cursorBox; ! 738: ! 739: if (pDraw->type == DRAWABLE_WINDOW && ! 740: apCursorLoc (pDraw->pScreen, &cursorBox)) { ! 741: xorg = ((WindowPtr)pDraw)->absCorner.x; ! 742: yorg = ((WindowPtr)pDraw)->absCorner.y; ! 743: ! 744: for (nArc = narcs, pArc = parcs; nArc--; pArc++) { ! 745: if (ORGRECT_OVERLAP(&cursorBox,xorg,yorg,pArc)){ ! 746: apRemoveCursor(TRUE); ! 747: break; ! 748: } ! 749: } ! 750: } ! 751: ! 752: COMPARE_GCS(pGC,pShadowGC); ! 753: (* pShadowGC->PolyArc) (pDraw, pShadowGC, narcs, parcs); ! 754: } ! 755: ! 756: /*- ! 757: *----------------------------------------------------------------------- ! 758: * apFillPolygon -- ! 759: * Find the bounding box of the polygon to fill and remove the ! 760: * cursor if it overlaps this box... ! 761: * ! 762: * Results: ! 763: * None. ! 764: * ! 765: * Side Effects: ! 766: * ! 767: *----------------------------------------------------------------------- ! 768: */ ! 769: void ! 770: apFillPolygon(pDraw, pGC, shape, mode, count, pPts) ! 771: DrawablePtr pDraw; ! 772: register GCPtr pGC; ! 773: int shape, mode; ! 774: register int count; ! 775: DDXPointPtr pPts; ! 776: { ! 777: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 778: BoxRec cursorBox; ! 779: ! 780: if (pDraw->type == DRAWABLE_WINDOW && ! 781: apCursorLoc (pDraw->pScreen, &cursorBox)) { ! 782: apSaveCursorBox(((WindowPtr)pDraw)->absCorner.x, ! 783: ((WindowPtr)pDraw)->absCorner.y, ! 784: mode, ! 785: pPts, ! 786: count, ! 787: &cursorBox); ! 788: } ! 789: ! 790: COMPARE_GCS(pGC,pShadowGC); ! 791: (* pShadowGC->FillPolygon) (pDraw, pShadowGC, shape, mode, count, pPts); ! 792: } ! 793: ! 794: /*- ! 795: *----------------------------------------------------------------------- ! 796: * apPolyFillRect -- ! 797: * Remove the cursor if it overlaps any of the filled rectangles ! 798: * to be drawn by the output routines. ! 799: * ! 800: * Results: ! 801: * None. ! 802: * ! 803: * Side Effects: ! 804: * ! 805: *----------------------------------------------------------------------- ! 806: */ ! 807: void ! 808: apPolyFillRect(pDrawable, pGC, nrectFill, prectInit) ! 809: DrawablePtr pDrawable; ! 810: GCPtr pGC; ! 811: int nrectFill; /* number of rectangles to fill */ ! 812: xRectangle *prectInit; /* Pointer to first rectangle to fill */ ! 813: { ! 814: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 815: register xRectangle *pRect; ! 816: register int nRect; ! 817: register int xorg, ! 818: yorg; ! 819: BoxRec cursorBox; ! 820: ! 821: if (pDrawable->type == DRAWABLE_WINDOW && ! 822: apCursorLoc (pDrawable->pScreen, &cursorBox)) { ! 823: xorg = ((WindowPtr)pDrawable)->absCorner.x; ! 824: yorg = ((WindowPtr)pDrawable)->absCorner.y; ! 825: ! 826: for (nRect = nrectFill, pRect = prectInit; nRect--; pRect++) { ! 827: if (ORGRECT_OVERLAP(&cursorBox,xorg,yorg,pRect)){ ! 828: apRemoveCursor(TRUE); ! 829: break; ! 830: } ! 831: } ! 832: } ! 833: ! 834: COMPARE_GCS(pGC,pShadowGC); ! 835: (* pShadowGC->PolyFillRect) (pDrawable, pShadowGC, nrectFill, prectInit); ! 836: } ! 837: ! 838: /*- ! 839: *----------------------------------------------------------------------- ! 840: * apPolyFillArc -- ! 841: * See if the cursor overlaps any of the bounding boxes for the ! 842: * filled arc and remove it if it does. ! 843: * ! 844: * Results: ! 845: * None. ! 846: * ! 847: * Side Effects: ! 848: * ! 849: *----------------------------------------------------------------------- ! 850: */ ! 851: void ! 852: apPolyFillArc(pDraw, pGC, narcs, parcs) ! 853: DrawablePtr pDraw; ! 854: GCPtr pGC; ! 855: int narcs; ! 856: xArc *parcs; ! 857: { ! 858: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 859: register xArc *pArc; ! 860: register int nArc; ! 861: register int xorg, ! 862: yorg; ! 863: BoxRec cursorBox; ! 864: ! 865: if (pDraw->type == DRAWABLE_WINDOW && ! 866: apCursorLoc (pDraw->pScreen, &cursorBox)) { ! 867: xorg = ((WindowPtr)pDraw)->absCorner.x; ! 868: yorg = ((WindowPtr)pDraw)->absCorner.y; ! 869: ! 870: for (nArc = narcs, pArc = parcs; nArc--; pArc++) { ! 871: if (ORGRECT_OVERLAP(&cursorBox,xorg,yorg,pArc)){ ! 872: apRemoveCursor(TRUE); ! 873: break; ! 874: } ! 875: } ! 876: } ! 877: ! 878: COMPARE_GCS(pGC,pShadowGC); ! 879: (* pShadowGC->PolyFillArc) (pDraw, pShadowGC, narcs, parcs); ! 880: } ! 881: ! 882: /*- ! 883: *----------------------------------------------------------------------- ! 884: * apText -- ! 885: * Find the extent of a text operation and remove the cursor if they ! 886: * overlap. pDraw is assumed to be a window. ! 887: * ! 888: * Results: ! 889: * ! 890: * Side Effects: ! 891: * ! 892: *----------------------------------------------------------------------- ! 893: */ ! 894: int ! 895: apText(pDraw, pGC, x, y, count, chars, fontEncoding, drawFunc) ! 896: DrawablePtr pDraw; ! 897: GCPtr pGC; ! 898: int x, ! 899: y; ! 900: int count; ! 901: char *chars; ! 902: FontEncoding fontEncoding; ! 903: void (*drawFunc)(); ! 904: { ! 905: CharInfoPtr *charinfo; ! 906: unsigned int n, ! 907: w; ! 908: register int xorg, ! 909: yorg; ! 910: ExtentInfoRec extents; ! 911: BoxRec cursorBox; ! 912: ! 913: charinfo = (CharInfoPtr *)ALLOCATE_LOCAL (count * sizeof(CharInfoPtr)); ! 914: if (charinfo == (CharInfoPtr *)NULL) { ! 915: return x; ! 916: } ! 917: ! 918: GetGlyphs(pGC->font, count, chars, fontEncoding, &n, charinfo); ! 919: ! 920: if (apCursorLoc (pDraw->pScreen, &cursorBox)) { ! 921: QueryGlyphExtents(pGC->font, charinfo, count, &extents); ! 922: w = extents.overallWidth; ! 923: xorg = ((WindowPtr)pDraw)->absCorner.x; ! 924: yorg = ((WindowPtr)pDraw)->absCorner.y; ! 925: ! 926: if (BOX_OVERLAP(&cursorBox, ! 927: x + xorg + extents.overallLeft, ! 928: y + yorg - extents.overallAscent, ! 929: x + xorg + extents.overallRight, ! 930: y + yorg + extents.overallDescent)) { ! 931: apRemoveCursor(TRUE); ! 932: } ! 933: } else { ! 934: w = 0; ! 935: } ! 936: ! 937: if (n != 0) { ! 938: (* drawFunc)(pDraw, pGC, x, y, n, charinfo, pGC->font->pGlyphs); ! 939: } ! 940: ! 941: DEALLOCATE_LOCAL(charinfo); ! 942: return x+w; ! 943: } ! 944: ! 945: /*- ! 946: *----------------------------------------------------------------------- ! 947: * apPolyText8 -- ! 948: * ! 949: * Results: ! 950: * ! 951: * Side Effects: ! 952: * ! 953: *----------------------------------------------------------------------- ! 954: */ ! 955: int ! 956: apPolyText8(pDraw, pGC, x, y, count, chars) ! 957: DrawablePtr pDraw; ! 958: GCPtr pGC; ! 959: int x, y; ! 960: int count; ! 961: char *chars; ! 962: { ! 963: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 964: ! 965: COMPARE_GCS(pGC,pShadowGC); ! 966: if (pDraw->type == DRAWABLE_WINDOW) { ! 967: return apText (pDraw, pShadowGC, x, y, count, chars, Linear8Bit, ! 968: pShadowGC->PolyGlyphBlt); ! 969: } else { ! 970: return (* pShadowGC->PolyText8)(pDraw, pShadowGC, x, y, count, chars); ! 971: } ! 972: } ! 973: ! 974: /*- ! 975: *----------------------------------------------------------------------- ! 976: * apPolyText16 -- ! 977: * ! 978: * Results: ! 979: * ! 980: * Side Effects: ! 981: * ! 982: *----------------------------------------------------------------------- ! 983: */ ! 984: int ! 985: apPolyText16(pDraw, pGC, x, y, count, chars) ! 986: DrawablePtr pDraw; ! 987: GCPtr pGC; ! 988: int x, y; ! 989: int count; ! 990: unsigned short *chars; ! 991: { ! 992: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 993: ! 994: COMPARE_GCS(pGC,pShadowGC); ! 995: if (pDraw->type == DRAWABLE_WINDOW) { ! 996: return apText (pDraw, pShadowGC, x, y, count, chars, ! 997: (pShadowGC->font->pFI->lastRow == 0 ? ! 998: Linear16Bit : TwoD16Bit), ! 999: pShadowGC->PolyGlyphBlt); ! 1000: } else { ! 1001: return (* pShadowGC->PolyText16) (pDraw, pShadowGC, x, y, ! 1002: count, chars); ! 1003: } ! 1004: } ! 1005: ! 1006: /*- ! 1007: *----------------------------------------------------------------------- ! 1008: * apImageText8 -- ! 1009: * ! 1010: * Results: ! 1011: * ! 1012: * Side Effects: ! 1013: * ! 1014: *----------------------------------------------------------------------- ! 1015: */ ! 1016: void ! 1017: apImageText8(pDraw, pGC, x, y, count, chars) ! 1018: DrawablePtr pDraw; ! 1019: GCPtr pGC; ! 1020: int x, y; ! 1021: int count; ! 1022: char *chars; ! 1023: { ! 1024: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1025: ! 1026: COMPARE_GCS(pGC,pShadowGC); ! 1027: if (pDraw->type == DRAWABLE_WINDOW) { ! 1028: (void) apText (pDraw, pShadowGC, x, y, count, chars, ! 1029: Linear8Bit, pShadowGC->ImageGlyphBlt); ! 1030: } else { ! 1031: (* pShadowGC->ImageText8) (pDraw, pShadowGC, x, y, count, chars); ! 1032: } ! 1033: } ! 1034: ! 1035: /*- ! 1036: *----------------------------------------------------------------------- ! 1037: * apImageText16 -- ! 1038: * ! 1039: * Results: ! 1040: * ! 1041: * Side Effects: ! 1042: * ! 1043: *----------------------------------------------------------------------- ! 1044: */ ! 1045: void ! 1046: apImageText16(pDraw, pGC, x, y, count, chars) ! 1047: DrawablePtr pDraw; ! 1048: GCPtr pGC; ! 1049: int x, y; ! 1050: int count; ! 1051: unsigned short *chars; ! 1052: { ! 1053: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1054: ! 1055: COMPARE_GCS(pGC,pShadowGC); ! 1056: if (pDraw->type == DRAWABLE_WINDOW) { ! 1057: (void) apText (pDraw, pShadowGC, x, y, count, chars, ! 1058: (pShadowGC->font->pFI->lastRow == 0 ? ! 1059: Linear16Bit : TwoD16Bit), ! 1060: pShadowGC->ImageGlyphBlt); ! 1061: } else { ! 1062: (* pShadowGC->ImageText16) (pDraw, pShadowGC, x, y, count, chars); ! 1063: } ! 1064: } ! 1065: ! 1066: /*- ! 1067: *----------------------------------------------------------------------- ! 1068: * apImageGlyphBlt -- ! 1069: * ! 1070: * Results: ! 1071: * ! 1072: * Side Effects: ! 1073: * ! 1074: *----------------------------------------------------------------------- ! 1075: */ ! 1076: void ! 1077: apImageGlyphBlt(pDrawable, pGC, x, y, nglyph, ppci, pglyphBase) ! 1078: DrawablePtr pDrawable; ! 1079: GC *pGC; ! 1080: int x, y; ! 1081: unsigned int nglyph; ! 1082: CharInfoPtr *ppci; /* array of character info */ ! 1083: pointer pglyphBase; /* start of array of glyphs */ ! 1084: { ! 1085: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1086: BoxRec cursorBox; ! 1087: ExtentInfoRec extents; ! 1088: register int xorg, ! 1089: yorg; ! 1090: ! 1091: if (pDrawable->type == DRAWABLE_WINDOW && ! 1092: apCursorLoc (pDrawable->pScreen, &cursorBox)) { ! 1093: QueryGlyphExtents (pGC->font, ppci, nglyph, &extents); ! 1094: xorg = ((WindowPtr)pDrawable)->absCorner.x + x; ! 1095: yorg = ((WindowPtr)pDrawable)->absCorner.y + y; ! 1096: if (BOX_OVERLAP(&cursorBox,xorg+extents.overallLeft, ! 1097: yorg+extents.overallAscent, ! 1098: xorg+extents.overallRight, ! 1099: yorg+extents.overallDescent)) { ! 1100: apRemoveCursor(TRUE); ! 1101: } ! 1102: } ! 1103: ! 1104: COMPARE_GCS(pGC,pShadowGC); ! 1105: (* pShadowGC->ImageGlyphBlt) (pDrawable, pShadowGC, x, y, nglyph, ! 1106: ppci, pglyphBase); ! 1107: } ! 1108: ! 1109: /*- ! 1110: *----------------------------------------------------------------------- ! 1111: * apPolyGlyphBlt -- ! 1112: * ! 1113: * Results: ! 1114: * ! 1115: * Side Effects: ! 1116: * ! 1117: *----------------------------------------------------------------------- ! 1118: */ ! 1119: void ! 1120: apPolyGlyphBlt(pDrawable, pGC, x, y, nglyph, ppci, pglyphBase) ! 1121: DrawablePtr pDrawable; ! 1122: GCPtr pGC; ! 1123: int x, y; ! 1124: unsigned int nglyph; ! 1125: CharInfoPtr *ppci; /* array of character info */ ! 1126: char *pglyphBase; /* start of array of glyphs */ ! 1127: { ! 1128: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1129: BoxRec cursorBox; ! 1130: ExtentInfoRec extents; ! 1131: register int xorg, ! 1132: yorg; ! 1133: ! 1134: if (pDrawable->type == DRAWABLE_WINDOW && ! 1135: apCursorLoc (pDrawable->pScreen, &cursorBox)) { ! 1136: QueryGlyphExtents (pGC->font, ppci, nglyph, &extents); ! 1137: xorg = ((WindowPtr)pDrawable)->absCorner.x + x; ! 1138: yorg = ((WindowPtr)pDrawable)->absCorner.y + y; ! 1139: if (BOX_OVERLAP(&cursorBox,xorg+extents.overallLeft, ! 1140: yorg+extents.overallAscent, ! 1141: xorg+extents.overallRight, ! 1142: yorg+extents.overallDescent)){ ! 1143: apRemoveCursor(TRUE); ! 1144: } ! 1145: } ! 1146: ! 1147: COMPARE_GCS(pGC,pShadowGC); ! 1148: (* pShadowGC->PolyGlyphBlt) (pDrawable, pShadowGC, x, y, ! 1149: nglyph, ppci, pglyphBase); ! 1150: } ! 1151: ! 1152: /*- ! 1153: *----------------------------------------------------------------------- ! 1154: * apPushPixels -- ! 1155: * ! 1156: * Results: ! 1157: * ! 1158: * Side Effects: ! 1159: * ! 1160: *----------------------------------------------------------------------- ! 1161: */ ! 1162: void ! 1163: apPushPixels(pGC, pBitMap, pDst, w, h, x, y) ! 1164: GCPtr pGC; ! 1165: PixmapPtr pBitMap; ! 1166: DrawablePtr pDst; ! 1167: int w, h, x, y; ! 1168: { ! 1169: ! 1170: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1171: BoxRec cursorBox; ! 1172: register int xorg, ! 1173: yorg; ! 1174: ! 1175: if (pDst->type == DRAWABLE_WINDOW && ! 1176: apCursorLoc (pDst->pScreen, &cursorBox)) { ! 1177: xorg = ((WindowPtr)pDst)->absCorner.x + x; ! 1178: yorg = ((WindowPtr)pDst)->absCorner.y + y; ! 1179: ! 1180: if (BOX_OVERLAP(&cursorBox,xorg,yorg,xorg+w,yorg+h)){ ! 1181: apRemoveCursor(TRUE); ! 1182: } ! 1183: } ! 1184: ! 1185: COMPARE_GCS(pGC,pShadowGC); ! 1186: (* pShadowGC->PushPixels) (pShadowGC, pBitMap, pDst, w, h, x, y); ! 1187: } ! 1188: ! 1189: /*- ! 1190: *----------------------------------------------------------------------- ! 1191: * apLineHelper -- ! 1192: * ! 1193: * Results: ! 1194: * ! 1195: * Side Effects: ! 1196: * ! 1197: *----------------------------------------------------------------------- ! 1198: */ ! 1199: void ! 1200: apLineHelper (pDraw, pGC, caps, npt, pPts, xOrg, yOrg) ! 1201: DrawablePtr pDraw; ! 1202: GCPtr pGC; ! 1203: int caps; ! 1204: int npt; ! 1205: SppPointPtr pPts; ! 1206: int xOrg, yOrg; ! 1207: { ! 1208: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1209: ! 1210: COMPARE_GCS(pGC,pShadowGC); ! 1211: (* pShadowGC->LineHelper) (pDraw, pShadowGC, caps, npt, pPts, xOrg, yOrg); ! 1212: } ! 1213: ! 1214: /*- ! 1215: *----------------------------------------------------------------------- ! 1216: * apChangeClip -- ! 1217: * Front end for changing the clip in the GC. Just passes the command ! 1218: * on through the shadow GC. ! 1219: * ! 1220: * ! 1221: * Results: ! 1222: * None. ! 1223: * ! 1224: * Side Effects: ! 1225: * ??? ! 1226: * ! 1227: *----------------------------------------------------------------------- ! 1228: */ ! 1229: void ! 1230: apChangeClip (pGC, type, pValue, numRects) ! 1231: GCPtr pGC; ! 1232: int type; ! 1233: pointer pValue; ! 1234: int numRects; ! 1235: { ! 1236: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1237: ! 1238: COMPARE_GCS(pGC,pShadowGC); ! 1239: (* pShadowGC->ChangeClip) (pShadowGC, type, pValue, numRects); ! 1240: } ! 1241: ! 1242: /*- ! 1243: *----------------------------------------------------------------------- ! 1244: * apDestroyClip -- ! 1245: * Ditto for destroying the clipping region of the GC. ! 1246: * ! 1247: * Results: ! 1248: * None. ! 1249: * ! 1250: * Side Effects: ! 1251: * ??? ! 1252: * ! 1253: *----------------------------------------------------------------------- ! 1254: */ ! 1255: void ! 1256: apDestroyClip (pGC) ! 1257: GCPtr pGC; ! 1258: { ! 1259: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1260: ! 1261: COMPARE_GCS(pGC,pShadowGC); ! 1262: (* pShadowGC->DestroyClip) (pShadowGC); ! 1263: } ! 1264: ! 1265: /*- ! 1266: *----------------------------------------------------------------------- ! 1267: * apDestroyGC -- ! 1268: * Function called when a GC is being freed. Simply unlinks and frees ! 1269: * the GCInterest structure. ! 1270: * ! 1271: * Results: ! 1272: * None. ! 1273: * ! 1274: * Side Effects: ! 1275: * The GCInterest structure is removed from the chain but its own ! 1276: * links are untouched (so FreeGC has something to follow...) ! 1277: * ! 1278: *----------------------------------------------------------------------- ! 1279: */ ! 1280: void ! 1281: apDestroyGC (pGC, pGCI) ! 1282: GCPtr pGC; /* GC pGCI is attached to */ ! 1283: GCInterestPtr pGCI; /* GCInterest being destroyed */ ! 1284: { ! 1285: if (pGC->devPriv) ! 1286: FreeGC ((GCPtr)pGC->devPriv); ! 1287: Xfree (pGCI); ! 1288: } ! 1289: ! 1290: /*- ! 1291: *----------------------------------------------------------------------- ! 1292: * apValidateGC -- ! 1293: * Called when a GC is about to be used for drawing. Copies all ! 1294: * changes from the GC to its shadow and validates the shadow. ! 1295: * ! 1296: * Results: ! 1297: * TRUE, for no readily apparent reason. ! 1298: * ! 1299: * Side Effects: ! 1300: * Vectors in the shadow GC will likely be changed. ! 1301: * ! 1302: *----------------------------------------------------------------------- ! 1303: */ ! 1304: /*ARGSUSED*/ ! 1305: static void ! 1306: apValidateGC (pGC, pGCI, changes, pDrawable) ! 1307: GCPtr pGC; ! 1308: GCInterestPtr pGCI; ! 1309: Mask changes; ! 1310: DrawablePtr pDrawable; ! 1311: { ! 1312: register GCPtr pShadowGC = (GCPtr) pGC->devPriv; ! 1313: ! 1314: if ( pGC->depth != pDrawable->depth ) ! 1315: FatalError( "apValidateGC: depth mismatch.\n" ); ! 1316: ! 1317: CopyGC (pGC, pShadowGC, changes); ! 1318: pShadowGC->serialNumber = pGC->serialNumber; ! 1319: COMPARE_GCS(pGC,pShadowGC); ! 1320: ValidateGC (pDrawable, pShadowGC); ! 1321: } ! 1322: ! 1323: /*- ! 1324: *----------------------------------------------------------------------- ! 1325: * apCopyGC -- ! 1326: * Called when a GC with its shadow is the destination of a copy. ! 1327: * Calls CopyGC to transfer the changes to the shadow GC as well. ! 1328: * Should not be used for the CopyGCSource since we like to copy from ! 1329: * the real GC to the shadow using CopyGC... ! 1330: * ! 1331: * Results: ! 1332: * None. ! 1333: * ! 1334: * Side Effects: ! 1335: * Any changes in the real GC are copied to the shadow. ! 1336: * ! 1337: *----------------------------------------------------------------------- ! 1338: */ ! 1339: /*ARGSUSED*/ ! 1340: void ! 1341: apCopyGC (pGCDst, pGCI, changes, pGCSrc) ! 1342: GCPtr pGCDst; ! 1343: GCInterestPtr pGCI; ! 1344: int changes; ! 1345: GCPtr pGCSrc; ! 1346: { ! 1347: CopyGC (pGCSrc, (GCPtr) pGCDst->devPriv, changes); ! 1348: COMPARE_GCS(pGCSrc,(GCPtr) pGCDst->devPriv); ! 1349: } ! 1350: ! 1351: /* ! 1352: * Array of functions to replace the functions in the GC. ! 1353: * Caveat: Depends on the ordering of functions in the GC structure. ! 1354: */ ! 1355: static void (* apGCFuncs[]) () = { ! 1356: apFillSpans, ! 1357: apSetSpans, ! 1358: ! 1359: apPutImage, ! 1360: apCopyArea, ! 1361: apCopyPlane, ! 1362: apPolyPoint, ! 1363: apPolylines, ! 1364: apPolySegment, ! 1365: apPolyRectangle, ! 1366: apPolyArc, ! 1367: apFillPolygon, ! 1368: apPolyFillRect, ! 1369: apPolyFillArc, ! 1370: (void(*)())apPolyText8, ! 1371: (void(*)())apPolyText16, ! 1372: apImageText8, ! 1373: apImageText16, ! 1374: apImageGlyphBlt, ! 1375: apPolyGlyphBlt, ! 1376: apPushPixels, ! 1377: apLineHelper, ! 1378: apChangeClip, ! 1379: apDestroyClip ! 1380: }; ! 1381: ! 1382: /*- ! 1383: *----------------------------------------------------------------------- ! 1384: * apCreateGC -- ! 1385: * This function is used to get our own validation hooks into each ! 1386: * GC to preserve the cursor. It calls the regular creation routine ! 1387: * for the screen and then, if that was successful, tacks another ! 1388: * GCInterest structure onto the GC *after* the one placed on by ! 1389: * the screen-specific CreateGC... ! 1390: * ! 1391: * Results: ! 1392: * TRUE if created ok. FALSE otherwise. ! 1393: * ! 1394: * Side Effects: ! 1395: * A GCInterest structure is stuck on the end of the GC's list. ! 1396: * ! 1397: *----------------------------------------------------------------------- ! 1398: */ ! 1399: Bool ! 1400: apCreateGC (pGC) ! 1401: GCPtr pGC; /* The GC to play with */ ! 1402: { ! 1403: GCInterestPtr pGCI; ! 1404: register GCPtr pShadowGC; ! 1405: int i; ! 1406: ! 1407: if ((*apProcs.CreateGC) (pGC)) { ! 1408: ! 1409: if (pGC->depth != pGC->pScreen->rootDepth) { ! 1410: /* This GC will never be used for painting the screen, so no shadow needed */ ! 1411: return TRUE; ! 1412: } ! 1413: ! 1414: pShadowGC = (GCPtr) Xalloc (sizeof (GC)); ! 1415: if (pShadowGC == (GCPtr)NULL) { ! 1416: return FALSE; ! 1417: } ! 1418: ! 1419: *pShadowGC = *pGC; ! 1420: pGC->devPriv = (pointer)pShadowGC; ! 1421: bcopy (apGCFuncs, &pGC->FillSpans, sizeof (apGCFuncs)); ! 1422: ! 1423: pGCI = (GCInterestPtr) Xalloc (sizeof (GCInterestRec)); ! 1424: if (!pGCI) { ! 1425: return FALSE; ! 1426: } ! 1427: ! 1428: /* ! 1429: * Any structure being shared between these two GCs must have its ! 1430: * reference count incremented. This includes: ! 1431: * font, tile, stipple. ! 1432: * Anything which doesn't have a reference count must be duplicated: ! 1433: * pCompositeClip, pAbsClientRegion. ! 1434: * ! 1435: */ ! 1436: if (pGC->font) { ! 1437: pGC->font->refcnt++; ! 1438: } ! 1439: if (pGC->tile) { ! 1440: pGC->tile->refcnt++; ! 1441: } ! 1442: if (pGC->stipple) { ! 1443: pGC->stipple->refcnt++; ! 1444: } ! 1445: pShadowGC->dash = (unsigned char *) ! 1446: Xalloc(2 * sizeof(unsigned char)); ! 1447: for (i=0; i<pGC->numInDashList; i++) ! 1448: pShadowGC->dash[i] = pGC->dash[i]; ! 1449: ! 1450: #ifdef notdef ! 1451: if (pGC->pCompositeClip) { ! 1452: pShadowGC->pCompositeClip = ! 1453: (* pGC->pScreen->RegionCreate) (NULL, 1); ! 1454: (* pGC->pScreen->RegionCopy) (pShadowGC->pCompositeClip, ! 1455: pGC->pCompositeClip); ! 1456: } ! 1457: if (pGC->pAbsClientRegion) { ! 1458: pShadowGC->pAbsClientRegion= ! 1459: (* pGC->pScreen->RegionCreate) (NULL, 1); ! 1460: (* pGC->pScreen->RegionCopy) (pShadowGC->pAbsClientRegion, ! 1461: pGC->pAbsClientRegion); ! 1462: } ! 1463: #endif notdef ! 1464: ! 1465: pGC->pNextGCInterest = pGCI; ! 1466: pGC->pLastGCInterest = pGCI; ! 1467: pGCI->pNextGCInterest = (GCInterestPtr) &pGC->pNextGCInterest; ! 1468: pGCI->pLastGCInterest = (GCInterestPtr) &pGC->pNextGCInterest; ! 1469: pGCI->length = sizeof(GCInterestRec); ! 1470: pGCI->owner = 0; /* server owns this */ ! 1471: pGCI->ValInterestMask = ~0; /* interested in everything */ ! 1472: pGCI->ValidateGC = apValidateGC; ! 1473: pGCI->ChangeInterestMask = 0; /* interested in nothing */ ! 1474: pGCI->ChangeGC = (int (*)()) NULL; ! 1475: pGCI->CopyGCSource = (void (*)())NULL; ! 1476: pGCI->CopyGCDest = apCopyGC; ! 1477: pGCI->DestroyGC = apDestroyGC; ! 1478: ! 1479: ! 1480: /* ! 1481: * Because of this weird way of handling the GCInterest lists, ! 1482: * we need to modify the output library's GCInterest structure to ! 1483: * point to the pNextGCInterest field of the shadow GC... ! 1484: */ ! 1485: pGCI = pShadowGC->pNextGCInterest; ! 1486: pGCI->pLastGCInterest = pGCI->pNextGCInterest = ! 1487: (GCInterestPtr) &pShadowGC->pNextGCInterest; ! 1488: ! 1489: return TRUE; ! 1490: } else { ! 1491: return FALSE; ! 1492: } ! 1493: } ! 1494: ! 1495: /*- ! 1496: * apPaintWindowBackground -- ! 1497: * Paint the window's background while preserving the cursor ! 1498: */ ! 1499: #define apPaintWindowBorder apPaintWindowBackground ! 1500: void ! 1501: apPaintWindowBackground (pWin, pRegion, what) ! 1502: WindowPtr pWin; ! 1503: RegionPtr pRegion; ! 1504: int what; ! 1505: { ! 1506: BoxRec cursorBox; ! 1507: WinPrivPtr pPriv; ! 1508: ScreenPtr pScreen; ! 1509: ! 1510: pScreen = pWin->drawable.pScreen; ! 1511: ! 1512: if (apCursorLoc (pScreen, &cursorBox)) { ! 1513: /* ! 1514: * If the cursor is on the same screen as the window, check the ! 1515: * region to paint for the cursor and remove it as necessary ! 1516: */ ! 1517: if ((* pScreen->RectIn) (pRegion, &cursorBox) != rgnOUT) { ! 1518: apRemoveCursor(TRUE); ! 1519: } ! 1520: } ! 1521: ! 1522: pPriv = (WinPrivPtr) LookupID (pWin->wid, RT_WINDOW, wPrivClass); ! 1523: if (what == PW_BACKGROUND) { ! 1524: (* pPriv->PaintWindowBackground) (pWin, pRegion, what); ! 1525: } else { ! 1526: (* pPriv->PaintWindowBorder) (pWin, pRegion, what); ! 1527: } ! 1528: } ! 1529: ! 1530: /*- ! 1531: *----------------------------------------------------------------------- ! 1532: * apCopyWindow -- ! 1533: * Protect the cursor from window copies.. ! 1534: * ! 1535: * Results: ! 1536: * None. ! 1537: * ! 1538: * Side Effects: ! 1539: * The cursor may be removed. ! 1540: * ! 1541: *----------------------------------------------------------------------- ! 1542: */ ! 1543: void ! 1544: apCopyWindow (pWin, ptOldOrg, prgnSrc) ! 1545: WindowPtr pWin; ! 1546: DDXPointRec ptOldOrg; ! 1547: RegionPtr prgnSrc; ! 1548: { ! 1549: BoxRec cursorBox; ! 1550: WinPrivPtr pPriv; ! 1551: ScreenPtr pScreen; ! 1552: ! 1553: pScreen = pWin->drawable.pScreen; ! 1554: ! 1555: if (apCursorLoc (pScreen, &cursorBox)) { ! 1556: /* ! 1557: * If the cursor is on the same screen, compare the box for the ! 1558: * cursor against the original window clip region (prgnSrc) and ! 1559: * the current window clip region (pWin->borderClip) and if it ! 1560: * overlaps either one, remove the cursor. (Should it really be ! 1561: * borderClip?) ! 1562: */ ! 1563: switch ((* pScreen->RectIn) (prgnSrc, &cursorBox)) { ! 1564: case rgnOUT: ! 1565: if ((* pScreen->RectIn) (pWin->borderClip, &cursorBox) == ! 1566: rgnOUT) { ! 1567: break; ! 1568: } ! 1569: case rgnIN: ! 1570: case rgnPART: ! 1571: apRemoveCursor(TRUE); ! 1572: } ! 1573: } ! 1574: ! 1575: pPriv = (WinPrivPtr) LookupID (pWin->wid, RT_WINDOW, wPrivClass); ! 1576: (* pPriv->CopyWindow) (pWin, ptOldOrg, prgnSrc); ! 1577: } ! 1578: ! 1579: /*- ! 1580: * apCreateWindow -- ! 1581: * Allow the output library to do its thing and then make sure ! 1582: * we intercept calls to PaintWindow{Border,Background} and ! 1583: * ClearToBackground ! 1584: */ ! 1585: Bool ! 1586: apCreateWindow(pWin) ! 1587: WindowPtr pWin; ! 1588: { ! 1589: WinPrivPtr pPriv; ! 1590: ! 1591: (*apProcs.CreateWindow) (pWin); ! 1592: ! 1593: pPriv = (WinPrivPtr) Xalloc (sizeof (WinPrivRec)); ! 1594: pPriv->PaintWindowBackground = pWin->PaintWindowBackground; ! 1595: pPriv->PaintWindowBorder = pWin->PaintWindowBorder; ! 1596: pPriv->CopyWindow = pWin->CopyWindow; ! 1597: ! 1598: AddResource (pWin->wid, RT_WINDOW, (pointer)pPriv, Xfree, ! 1599: wPrivClass); ! 1600: ! 1601: pWin->PaintWindowBackground = apPaintWindowBackground; ! 1602: pWin->PaintWindowBorder = apPaintWindowBorder; ! 1603: pWin->CopyWindow = apCopyWindow; ! 1604: ! 1605: } ! 1606: ! 1607: /*- ! 1608: * apChangeWindowAttributes -- ! 1609: * Catch the changing of the background/border functions ! 1610: */ ! 1611: Bool ! 1612: apChangeWindowAttributes(pWin, mask) ! 1613: WindowPtr pWin; ! 1614: Mask mask; ! 1615: { ! 1616: WinPrivPtr pPriv; ! 1617: ! 1618: (*apProcs.ChangeWindowAttributes) (pWin, mask); ! 1619: ! 1620: pPriv = (WinPrivPtr) LookupID (pWin->wid, RT_WINDOW, wPrivClass); ! 1621: if (pPriv == (WinPrivPtr)0) { ! 1622: FatalError("apChangeWindowAttributes got null pPriv\n"); ! 1623: } ! 1624: ! 1625: if ((char *)pWin->PaintWindowBackground !=(char *)apPaintWindowBackground){ ! 1626: pPriv->PaintWindowBackground = pWin->PaintWindowBackground; ! 1627: pWin->PaintWindowBackground = apPaintWindowBackground; ! 1628: } ! 1629: if ((char *)pWin->PaintWindowBorder != (char *)apPaintWindowBorder) { ! 1630: pPriv->PaintWindowBorder = pWin->PaintWindowBorder; ! 1631: pWin->PaintWindowBorder = apPaintWindowBorder; ! 1632: } ! 1633: if ((char *)pWin->CopyWindow != (char *)apCopyWindow) { ! 1634: pPriv->CopyWindow = pWin->CopyWindow; ! 1635: pWin->CopyWindow = apCopyWindow; ! 1636: } ! 1637: ! 1638: return (TRUE); ! 1639: } ! 1640:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.