diff options
Diffstat (limited to 'xorg-server/hw/xfree86/xaa/xaaDashLine.c')
-rw-r--r-- | xorg-server/hw/xfree86/xaa/xaaDashLine.c | 687 |
1 files changed, 353 insertions, 334 deletions
diff --git a/xorg-server/hw/xfree86/xaa/xaaDashLine.c b/xorg-server/hw/xfree86/xaa/xaaDashLine.c index adae2e583..c7e52cd0b 100644 --- a/xorg-server/hw/xfree86/xaa/xaaDashLine.c +++ b/xorg-server/hw/xfree86/xaa/xaaDashLine.c @@ -1,334 +1,353 @@ -
-#ifdef HAVE_XORG_CONFIG_H
-#include <xorg-config.h>
-#endif
-
-#include <stdlib.h>
-
-#include <X11/X.h>
-#include "misc.h"
-#include "xf86.h"
-#include "xf86_OSproc.h"
-
-#include "scrnintstr.h"
-#include "pixmapstr.h"
-#include "miline.h"
-#include "xf86str.h"
-#include "xaa.h"
-#include "xaalocal.h"
-
-
-void
-#ifdef POLYSEGMENT
-XAAPolySegmentDashed(
- DrawablePtr pDrawable,
- GCPtr pGC,
- int nseg,
- xSegment *pSeg
-#else
-XAAPolyLinesDashed(
- DrawablePtr pDrawable,
- GCPtr pGC,
- int mode, /* Origin or Previous */
- int npt, /* number of points */
- DDXPointPtr pptInit
-#endif
-){
- XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC);
- XAAGCPtr pGCPriv = (XAAGCPtr)dixLookupPrivate(&pGC->devPrivates,
- XAAGetGCKey());
- BoxPtr pboxInit = RegionRects(pGC->pCompositeClip);
- int nboxInit = RegionNumRects(pGC->pCompositeClip);
- unsigned int bias = miGetZeroLineBias(pDrawable->pScreen);
- int xorg = pDrawable->x;
- int yorg = pDrawable->y;
- int nbox;
- BoxPtr pbox;
-#ifndef POLYSEGMENT
- DDXPointPtr ppt;
-#endif
- unsigned int oc1, oc2;
- int dmin, dmaj, e, octant;
- int x1, x2, y1, y2, tmp, len, offset;
- int PatternLength, PatternOffset;
-
- if(!nboxInit)
- return;
-
- if (infoRec->DashedLineFlags & LINE_LIMIT_COORDS) {
- int minValX = infoRec->DashedLineLimits.x1;
- int maxValX = infoRec->DashedLineLimits.x2;
- int minValY = infoRec->DashedLineLimits.y1;
- int maxValY = infoRec->DashedLineLimits.y2;
-#ifdef POLYSEGMENT
- int n = nseg;
- xSegment *s = pSeg;
-
- while (n--)
-#else
- int n = npt;
- int xorgtmp = xorg;
- int yorgtmp = yorg;
-
- ppt = pptInit;
- x2 = ppt->x + xorgtmp;
- y2 = ppt->y + yorgtmp;
- while (--n)
-#endif
- {
-#ifdef POLYSEGMENT
- x1 = s->x1 + xorg;
- y1 = s->y1 + yorg;
- x2 = s->x2 + xorg;
- y2 = s->y2 + yorg;
- s++;
-#else
- x1 = x2;
- y1 = y2;
- ++ppt;
- if (mode == CoordModePrevious) {
- xorgtmp = x1;
- yorgtmp = y1;
- }
- x2 = ppt->x + xorgtmp;
- y2 = ppt->y + yorgtmp;
-#endif
- if (x1 > maxValX || x1 < minValX ||
- x2 > maxValX || x2 < minValX ||
- y1 > maxValY || y1 < minValY ||
- y2 > maxValY || y2 < minValY) {
-#ifdef POLYSEGMENT
- XAAFallbackOps.PolySegment(pDrawable, pGC, nseg, pSeg);
-#else
- XAAFallbackOps.Polylines(pDrawable, pGC, mode, npt, pptInit);
-#endif
- return;
- }
- }
- }
-
- PatternLength = pGCPriv->DashLength;
- PatternOffset = pGC->dashOffset % PatternLength;
-
- (*infoRec->SetupForDashedLine)(infoRec->pScrn, pGC->fgPixel,
- (pGC->lineStyle == LineDoubleDash) ? pGC->bgPixel : -1,
- pGC->alu, pGC->planemask, PatternLength, pGCPriv->DashPattern);
-
-
-#ifdef POLYSEGMENT
- while (nseg--)
-#else
- ppt = pptInit;
- x2 = ppt->x + xorg;
- y2 = ppt->y + yorg;
- while(--npt)
-#endif
- {
- nbox = nboxInit;
- pbox = pboxInit;
-
-#ifdef POLYSEGMENT
- x1 = pSeg->x1 + xorg;
- y1 = pSeg->y1 + yorg;
- x2 = pSeg->x2 + xorg;
- y2 = pSeg->y2 + yorg;
- pSeg++;
-#else
- x1 = x2;
- y1 = y2;
- ++ppt;
- if (mode == CoordModePrevious) {
- xorg = x1;
- yorg = y1;
- }
- x2 = ppt->x + xorg;
- y2 = ppt->y + yorg;
-#endif
-
-
- if (infoRec->SubsequentDashedBresenhamLine) {
- if((dmaj = x2 - x1) < 0) {
- dmaj = -dmaj;
- octant = XDECREASING;
- } else octant = 0;
-
- if((dmin = y2 - y1) < 0) {
- dmin = -dmin;
- octant |= YDECREASING;
- }
-
- if(dmin >= dmaj){
- tmp = dmin; dmin = dmaj; dmaj = tmp;
- octant |= YMAJOR;
- }
-
- e = -dmaj - ((bias >> octant) & 1);
- len = dmaj;
- dmin <<= 1;
- dmaj <<= 1;
- } else { /* Muffle compiler */
- dmin = dmaj = e = octant = len = 0;
- }
-
- while(nbox--) {
- oc1 = oc2 = 0;
- OUTCODES(oc1, x1, y1, pbox);
- OUTCODES(oc2, x2, y2, pbox);
- if (!(oc1 | oc2)) { /* uncliped */
- if(infoRec->SubsequentDashedTwoPointLine) {
- (*infoRec->SubsequentDashedTwoPointLine)(
- infoRec->pScrn, x1, y1, x2, y2,
-#ifdef POLYSEGMENT
- (pGC->capStyle != CapNotLast) ? 0 :
-#endif
- OMIT_LAST, PatternOffset);
- } else {
- (*infoRec->SubsequentDashedBresenhamLine)(
- infoRec->pScrn, x1, y1, dmaj, dmin, e,
-#ifdef POLYSEGMENT
- (pGC->capStyle != CapNotLast) ? (len+1) :
-#endif
- len, octant, PatternOffset);
- }
- break;
- } else if (oc1 & oc2) { /* completely clipped */
- pbox++;
- } else if (infoRec->ClippingFlags & HARDWARE_CLIP_DASHED_LINE) {
- (*infoRec->SetClippingRectangle)(infoRec->pScrn,
- pbox->x1, pbox->y1, pbox->x2 - 1, pbox->y2 - 1);
-
- if(infoRec->SubsequentDashedBresenhamLine) {
- (*infoRec->SubsequentDashedBresenhamLine)(
- infoRec->pScrn, x1, y1, dmaj, dmin, e,
-#ifdef POLYSEGMENT
- (pGC->capStyle != CapNotLast) ? (len+1) :
-#endif
- len, octant, PatternOffset);
- } else {
- (*infoRec->SubsequentDashedTwoPointLine)(
- infoRec->pScrn, x1, y1, x2, y2,
-#ifdef POLYSEGMENT
- (pGC->capStyle != CapNotLast) ? 0 :
-#endif
- OMIT_LAST, PatternOffset
- );
- }
- (*infoRec->DisableClipping)(infoRec->pScrn);
- pbox++;
- } else {
- int new_x1 = x1, new_y1 = y1, new_x2 = x2, new_y2 = y2;
- int clip1 = 0, clip2 = 0;
- int err, adx, ady;
-
- if(octant & YMAJOR) {
- ady = dmaj >> 1;
- adx = dmin >> 1;
- } else {
- ady = dmin >> 1;
- adx = dmaj >> 1;
- }
-
- if (miZeroClipLine(pbox->x1, pbox->y1,
- pbox->x2 - 1, pbox->y2 - 1,
- &new_x1, &new_y1, &new_x2, &new_y2,
- adx, ady, &clip1, &clip2,
- octant, bias, oc1, oc2) == -1)
- {
- pbox++;
- continue;
- }
-
- if (octant & YMAJOR)
- len = abs(new_y2 - new_y1);
- else
- len = abs(new_x2 - new_x1);
-#ifdef POLYSEGMENT
- if (clip2 != 0 || pGC->capStyle != CapNotLast)
- len++;
-#else
- len += (clip2 != 0);
-#endif
- if (len) {
- int abserr, clipdx, clipdy;
- /* unwind bresenham error term to first point */
- if (clip1) {
- clipdx = abs(new_x1 - x1);
- clipdy = abs(new_y1 - y1);
-
- if (octant & YMAJOR)
- err = e + clipdy*dmin - clipdx*dmaj;
- else
- err = e + clipdx*dmin - clipdy*dmaj;
- } else
- err = e;
-
-#define range infoRec->DashedBresenhamLineErrorTermBits
- abserr = abs(err);
- while((abserr & range) ||
- (dmaj & range) ||
- (dmin & range)) {
- dmin >>= 1;
- dmaj >>= 1;
- abserr >>= 1;
- err /= 2;
- }
-
- if(octant & YMAJOR)
- offset = abs(new_y1 - y1);
- else
- offset = abs(new_x1 - x1);
-
- offset += PatternOffset;
- offset %= PatternLength;
-
- (*infoRec->SubsequentDashedBresenhamLine)(
- infoRec->pScrn, new_x1, new_y1,
- dmaj, dmin, err, len, octant, offset);
- }
- pbox++;
- }
- } /* while (nbox--) */
-#ifndef POLYSEGMENT
- len = abs(y2 - y1);
- tmp = abs(x2 - x1);
- PatternOffset += (len > tmp) ? len : tmp;
- PatternOffset %= PatternLength;
-#endif
- } /* while (nline--) */
-
-#ifndef POLYSEGMENT
- /* paint the last point if the end style isn't CapNotLast.
- (Assume that a projecting, butt, or round cap that is one
- pixel wide is the same as the single pixel of the endpoint.)
- */
-
- if ((pGC->capStyle != CapNotLast) &&
- ((ppt->x + xorg != pptInit->x + pDrawable->x) ||
- (ppt->y + yorg != pptInit->y + pDrawable->y) ||
- (ppt == pptInit + 1)))
- {
- nbox = nboxInit;
- pbox = pboxInit;
- while (nbox--) {
- if ((x2 >= pbox->x1) && (y2 >= pbox->y1) &&
- (x2 < pbox->x2) && (y2 < pbox->y2))
- {
- if(infoRec->SubsequentDashedTwoPointLine) {
- (*infoRec->SubsequentDashedTwoPointLine)(
- infoRec->pScrn, x2, y2, x2, y2, 0,
- PatternOffset);
- } else {
- (*infoRec->SubsequentDashedBresenhamLine)(
- infoRec->pScrn, x2, y2, 2, 0, -1,
- 1, 0, PatternOffset);
- }
- break;
- } else
- pbox++;
- }
- }
-#endif
-
- SET_SYNC_FLAG(infoRec);
-}
-
+ +#ifdef HAVE_XORG_CONFIG_H +#include <xorg-config.h> +#endif + +#include <stdlib.h> + +#include <X11/X.h> +#include "misc.h" +#include "xf86.h" +#include "xf86_OSproc.h" + +#include "scrnintstr.h" +#include "pixmapstr.h" +#include "miline.h" +#include "xf86str.h" +#include "xaa.h" +#include "xaalocal.h" + +void +#ifdef POLYSEGMENT + XAAPolySegmentDashed(DrawablePtr pDrawable, + GCPtr pGC, int nseg, xSegment * pSeg +#else +XAAPolyLinesDashed(DrawablePtr pDrawable, GCPtr pGC, int mode, /* Origin or Previous */ + int npt, /* number of points */ + DDXPointPtr pptInit +#endif + ) +{ + XAAInfoRecPtr infoRec = GET_XAAINFORECPTR_FROM_GC(pGC); + XAAGCPtr pGCPriv = (XAAGCPtr) dixLookupPrivate(&pGC->devPrivates, + XAAGetGCKey()); + BoxPtr pboxInit = RegionRects(pGC->pCompositeClip); + int nboxInit = RegionNumRects(pGC->pCompositeClip); + unsigned int bias = miGetZeroLineBias(pDrawable->pScreen); + int xorg = pDrawable->x; + int yorg = pDrawable->y; + int nbox; + BoxPtr pbox; + +#ifndef POLYSEGMENT + DDXPointPtr ppt; +#endif + unsigned int oc1, oc2; + int dmin, dmaj, e, octant; + int x1, x2, y1, y2, tmp, len, offset; + int PatternLength, PatternOffset; + + if (!nboxInit) + return; + + if (infoRec->DashedLineFlags & LINE_LIMIT_COORDS) { + int minValX = infoRec->DashedLineLimits.x1; + int maxValX = infoRec->DashedLineLimits.x2; + int minValY = infoRec->DashedLineLimits.y1; + int maxValY = infoRec->DashedLineLimits.y2; + +#ifdef POLYSEGMENT + int n = nseg; + xSegment *s = pSeg; + + while (n--) +#else + int n = npt; + int xorgtmp = xorg; + int yorgtmp = yorg; + + ppt = pptInit; + x2 = ppt->x + xorgtmp; + y2 = ppt->y + yorgtmp; + while (--n) +#endif + { +#ifdef POLYSEGMENT + x1 = s->x1 + xorg; + y1 = s->y1 + yorg; + x2 = s->x2 + xorg; + y2 = s->y2 + yorg; + s++; +#else + x1 = x2; + y1 = y2; + ++ppt; + if (mode == CoordModePrevious) { + xorgtmp = x1; + yorgtmp = y1; + } + x2 = ppt->x + xorgtmp; + y2 = ppt->y + yorgtmp; +#endif + if (x1 > maxValX || x1 < minValX || + x2 > maxValX || x2 < minValX || + y1 > maxValY || y1 < minValY || y2 > maxValY || y2 < minValY) { +#ifdef POLYSEGMENT + XAAFallbackOps.PolySegment(pDrawable, pGC, nseg, pSeg); +#else + XAAFallbackOps.Polylines(pDrawable, pGC, mode, npt, pptInit); +#endif + return; + } + } + } + + PatternLength = pGCPriv->DashLength; + PatternOffset = pGC->dashOffset % PatternLength; + + (*infoRec->SetupForDashedLine) (infoRec->pScrn, pGC->fgPixel, + (pGC->lineStyle == + LineDoubleDash) ? pGC->bgPixel : -1, + pGC->alu, pGC->planemask, PatternLength, + pGCPriv->DashPattern); + +#ifdef POLYSEGMENT + while (nseg--) +#else + ppt = pptInit; + x2 = ppt->x + xorg; + y2 = ppt->y + yorg; + while (--npt) +#endif + { + nbox = nboxInit; + pbox = pboxInit; + +#ifdef POLYSEGMENT + x1 = pSeg->x1 + xorg; + y1 = pSeg->y1 + yorg; + x2 = pSeg->x2 + xorg; + y2 = pSeg->y2 + yorg; + pSeg++; +#else + x1 = x2; + y1 = y2; + ++ppt; + if (mode == CoordModePrevious) { + xorg = x1; + yorg = y1; + } + x2 = ppt->x + xorg; + y2 = ppt->y + yorg; +#endif + + if (infoRec->SubsequentDashedBresenhamLine) { + if ((dmaj = x2 - x1) < 0) { + dmaj = -dmaj; + octant = XDECREASING; + } + else + octant = 0; + + if ((dmin = y2 - y1) < 0) { + dmin = -dmin; + octant |= YDECREASING; + } + + if (dmin >= dmaj) { + tmp = dmin; + dmin = dmaj; + dmaj = tmp; + octant |= YMAJOR; + } + + e = -dmaj - ((bias >> octant) & 1); + len = dmaj; + dmin <<= 1; + dmaj <<= 1; + } + else { /* Muffle compiler */ + dmin = dmaj = e = octant = len = 0; + } + + while (nbox--) { + oc1 = oc2 = 0; + OUTCODES(oc1, x1, y1, pbox); + OUTCODES(oc2, x2, y2, pbox); + if (!(oc1 | oc2)) { /* uncliped */ + if (infoRec->SubsequentDashedTwoPointLine) { + (*infoRec->SubsequentDashedTwoPointLine) (infoRec->pScrn, + x1, y1, x2, y2, +#ifdef POLYSEGMENT + (pGC->capStyle != + CapNotLast) ? 0 : +#endif + OMIT_LAST, + PatternOffset); + } + else { + (*infoRec->SubsequentDashedBresenhamLine) (infoRec->pScrn, + x1, y1, dmaj, + dmin, e, +#ifdef POLYSEGMENT + (pGC->capStyle != + CapNotLast) + ? (len + 1) : +#endif + len, octant, + PatternOffset); + } + break; + } + else if (oc1 & oc2) { /* completely clipped */ + pbox++; + } + else if (infoRec->ClippingFlags & HARDWARE_CLIP_DASHED_LINE) { + (*infoRec->SetClippingRectangle) (infoRec->pScrn, + pbox->x1, pbox->y1, + pbox->x2 - 1, pbox->y2 - 1); + + if (infoRec->SubsequentDashedBresenhamLine) { + (*infoRec->SubsequentDashedBresenhamLine) (infoRec->pScrn, + x1, y1, dmaj, + dmin, e, +#ifdef POLYSEGMENT + (pGC->capStyle != + CapNotLast) + ? (len + 1) : +#endif + len, octant, + PatternOffset); + } + else { + (*infoRec->SubsequentDashedTwoPointLine) (infoRec->pScrn, + x1, y1, x2, y2, +#ifdef POLYSEGMENT + (pGC->capStyle != + CapNotLast) ? 0 : +#endif + OMIT_LAST, + PatternOffset); + } + (*infoRec->DisableClipping) (infoRec->pScrn); + pbox++; + } + else { + int new_x1 = x1, new_y1 = y1, new_x2 = x2, new_y2 = y2; + int clip1 = 0, clip2 = 0; + int err, adx, ady; + + if (octant & YMAJOR) { + ady = dmaj >> 1; + adx = dmin >> 1; + } + else { + ady = dmin >> 1; + adx = dmaj >> 1; + } + + if (miZeroClipLine(pbox->x1, pbox->y1, + pbox->x2 - 1, pbox->y2 - 1, + &new_x1, &new_y1, &new_x2, &new_y2, + adx, ady, &clip1, &clip2, + octant, bias, oc1, oc2) == -1) { + pbox++; + continue; + } + + if (octant & YMAJOR) + len = abs(new_y2 - new_y1); + else + len = abs(new_x2 - new_x1); +#ifdef POLYSEGMENT + if (clip2 != 0 || pGC->capStyle != CapNotLast) + len++; +#else + len += (clip2 != 0); +#endif + if (len) { + int abserr, clipdx, clipdy; + + /* unwind bresenham error term to first point */ + if (clip1) { + clipdx = abs(new_x1 - x1); + clipdy = abs(new_y1 - y1); + + if (octant & YMAJOR) + err = e + clipdy * dmin - clipdx * dmaj; + else + err = e + clipdx * dmin - clipdy * dmaj; + } + else + err = e; + +#define range infoRec->DashedBresenhamLineErrorTermBits + abserr = abs(err); + while ((abserr & range) || (dmaj & range) || (dmin & range)) { + dmin >>= 1; + dmaj >>= 1; + abserr >>= 1; + err /= 2; + } + + if (octant & YMAJOR) + offset = abs(new_y1 - y1); + else + offset = abs(new_x1 - x1); + + offset += PatternOffset; + offset %= PatternLength; + + (*infoRec->SubsequentDashedBresenhamLine) (infoRec->pScrn, + new_x1, new_y1, + dmaj, dmin, err, + len, octant, + offset); + } + pbox++; + } + } /* while (nbox--) */ +#ifndef POLYSEGMENT + len = abs(y2 - y1); + tmp = abs(x2 - x1); + PatternOffset += (len > tmp) ? len : tmp; + PatternOffset %= PatternLength; +#endif + } /* while (nline--) */ + +#ifndef POLYSEGMENT + /* paint the last point if the end style isn't CapNotLast. + (Assume that a projecting, butt, or round cap that is one + pixel wide is the same as the single pixel of the endpoint.) + */ + + if ((pGC->capStyle != CapNotLast) && + ((ppt->x + xorg != pptInit->x + pDrawable->x) || + (ppt->y + yorg != pptInit->y + pDrawable->y) || + (ppt == pptInit + 1))) { + nbox = nboxInit; + pbox = pboxInit; + while (nbox--) { + if ((x2 >= pbox->x1) && (y2 >= pbox->y1) && + (x2 < pbox->x2) && (y2 < pbox->y2)) { + if (infoRec->SubsequentDashedTwoPointLine) { + (*infoRec->SubsequentDashedTwoPointLine) (infoRec->pScrn, + x2, y2, x2, y2, 0, + PatternOffset); + } + else { + (*infoRec->SubsequentDashedBresenhamLine) (infoRec->pScrn, + x2, y2, 2, 0, -1, + 1, 0, + PatternOffset); + } + break; + } + else + pbox++; + } + } +#endif + + SET_SYNC_FLAG(infoRec); +} |