1*4882a593Smuzhiyun /* 2*4882a593Smuzhiyun 3*4882a593Smuzhiyun Copyright 1987, 1998 The Open Group 4*4882a593Smuzhiyun 5*4882a593Smuzhiyun Permission to use, copy, modify, distribute, and sell this software and its 6*4882a593Smuzhiyun documentation for any purpose is hereby granted without fee, provided that 7*4882a593Smuzhiyun the above copyright notice appear in all copies and that both that 8*4882a593Smuzhiyun copyright notice and this permission notice appear in supporting 9*4882a593Smuzhiyun documentation. 10*4882a593Smuzhiyun 11*4882a593Smuzhiyun The above copyright notice and this permission notice shall be included 12*4882a593Smuzhiyun in all copies or substantial portions of the Software. 13*4882a593Smuzhiyun 14*4882a593Smuzhiyun THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 15*4882a593Smuzhiyun OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 16*4882a593Smuzhiyun MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 17*4882a593Smuzhiyun IN NO EVENT SHALL THE OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR 18*4882a593Smuzhiyun OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 19*4882a593Smuzhiyun ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 20*4882a593Smuzhiyun OTHER DEALINGS IN THE SOFTWARE. 21*4882a593Smuzhiyun 22*4882a593Smuzhiyun Except as contained in this notice, the name of The Open Group shall 23*4882a593Smuzhiyun not be used in advertising or otherwise to promote the sale, use or 24*4882a593Smuzhiyun other dealings in this Software without prior written authorization 25*4882a593Smuzhiyun from The Open Group. 26*4882a593Smuzhiyun 27*4882a593Smuzhiyun */ 28*4882a593Smuzhiyun 29*4882a593Smuzhiyun #ifdef HAVE_DIX_CONFIG_H 30*4882a593Smuzhiyun #include <dix-config.h> 31*4882a593Smuzhiyun #endif 32*4882a593Smuzhiyun 33*4882a593Smuzhiyun #ifndef SCANFILLINCLUDED 34*4882a593Smuzhiyun #define SCANFILLINCLUDED 35*4882a593Smuzhiyun /* 36*4882a593Smuzhiyun * scanfill.h 37*4882a593Smuzhiyun * 38*4882a593Smuzhiyun * Written by Brian Kelleher; Jan 1985 39*4882a593Smuzhiyun * 40*4882a593Smuzhiyun * This file contains a few macros to help track 41*4882a593Smuzhiyun * the edge of a filled object. The object is assumed 42*4882a593Smuzhiyun * to be filled in scanline order, and thus the 43*4882a593Smuzhiyun * algorithm used is an extension of Bresenham's line 44*4882a593Smuzhiyun * drawing algorithm which assumes that y is always the 45*4882a593Smuzhiyun * major axis. 46*4882a593Smuzhiyun * Since these pieces of code are the same for any filled shape, 47*4882a593Smuzhiyun * it is more convenient to gather the library in one 48*4882a593Smuzhiyun * place, but since these pieces of code are also in 49*4882a593Smuzhiyun * the inner loops of output primitives, procedure call 50*4882a593Smuzhiyun * overhead is out of the question. 51*4882a593Smuzhiyun * See the author for a derivation if needed. 52*4882a593Smuzhiyun */ 53*4882a593Smuzhiyun 54*4882a593Smuzhiyun /* 55*4882a593Smuzhiyun * In scan converting polygons, we want to choose those pixels 56*4882a593Smuzhiyun * which are inside the polygon. Thus, we add .5 to the starting 57*4882a593Smuzhiyun * x coordinate for both left and right edges. Now we choose the 58*4882a593Smuzhiyun * first pixel which is inside the pgon for the left edge and the 59*4882a593Smuzhiyun * first pixel which is outside the pgon for the right edge. 60*4882a593Smuzhiyun * Draw the left pixel, but not the right. 61*4882a593Smuzhiyun * 62*4882a593Smuzhiyun * How to add .5 to the starting x coordinate: 63*4882a593Smuzhiyun * If the edge is moving to the right, then subtract dy from the 64*4882a593Smuzhiyun * error term from the general form of the algorithm. 65*4882a593Smuzhiyun * If the edge is moving to the left, then add dy to the error term. 66*4882a593Smuzhiyun * 67*4882a593Smuzhiyun * The reason for the difference between edges moving to the left 68*4882a593Smuzhiyun * and edges moving to the right is simple: If an edge is moving 69*4882a593Smuzhiyun * to the right, then we want the algorithm to flip immediately. 70*4882a593Smuzhiyun * If it is moving to the left, then we don't want it to flip until 71*4882a593Smuzhiyun * we traverse an entire pixel. 72*4882a593Smuzhiyun */ 73*4882a593Smuzhiyun #define BRESINITPGON(dy, x1, x2, xStart, d, m, m1, incr1, incr2) { \ 74*4882a593Smuzhiyun int dx; /* local storage */ \ 75*4882a593Smuzhiyun \ 76*4882a593Smuzhiyun /* \ 77*4882a593Smuzhiyun * if the edge is horizontal, then it is ignored \ 78*4882a593Smuzhiyun * and assumed not to be processed. Otherwise, do this stuff. \ 79*4882a593Smuzhiyun */ \ 80*4882a593Smuzhiyun if ((dy) != 0) { \ 81*4882a593Smuzhiyun xStart = (x1); \ 82*4882a593Smuzhiyun dx = (x2) - xStart; \ 83*4882a593Smuzhiyun if (dx < 0) { \ 84*4882a593Smuzhiyun m = dx / (dy); \ 85*4882a593Smuzhiyun m1 = m - 1; \ 86*4882a593Smuzhiyun incr1 = -2 * dx + 2 * (dy) * m1; \ 87*4882a593Smuzhiyun incr2 = -2 * dx + 2 * (dy) * m; \ 88*4882a593Smuzhiyun d = 2 * m * (dy) - 2 * dx - 2 * (dy); \ 89*4882a593Smuzhiyun } else { \ 90*4882a593Smuzhiyun m = dx / (dy); \ 91*4882a593Smuzhiyun m1 = m + 1; \ 92*4882a593Smuzhiyun incr1 = 2 * dx - 2 * (dy) * m1; \ 93*4882a593Smuzhiyun incr2 = 2 * dx - 2 * (dy) * m; \ 94*4882a593Smuzhiyun d = -2 * m * (dy) + 2 * dx; \ 95*4882a593Smuzhiyun } \ 96*4882a593Smuzhiyun } \ 97*4882a593Smuzhiyun } 98*4882a593Smuzhiyun 99*4882a593Smuzhiyun #define BRESINCRPGON(d, minval, m, m1, incr1, incr2) { \ 100*4882a593Smuzhiyun if (m1 > 0) { \ 101*4882a593Smuzhiyun if (d > 0) { \ 102*4882a593Smuzhiyun minval += m1; \ 103*4882a593Smuzhiyun d += incr1; \ 104*4882a593Smuzhiyun } \ 105*4882a593Smuzhiyun else { \ 106*4882a593Smuzhiyun minval += m; \ 107*4882a593Smuzhiyun d += incr2; \ 108*4882a593Smuzhiyun } \ 109*4882a593Smuzhiyun } else {\ 110*4882a593Smuzhiyun if (d >= 0) { \ 111*4882a593Smuzhiyun minval += m1; \ 112*4882a593Smuzhiyun d += incr1; \ 113*4882a593Smuzhiyun } \ 114*4882a593Smuzhiyun else { \ 115*4882a593Smuzhiyun minval += m; \ 116*4882a593Smuzhiyun d += incr2; \ 117*4882a593Smuzhiyun } \ 118*4882a593Smuzhiyun } \ 119*4882a593Smuzhiyun } 120*4882a593Smuzhiyun 121*4882a593Smuzhiyun /* 122*4882a593Smuzhiyun * This structure contains all of the information needed 123*4882a593Smuzhiyun * to run the bresenham algorithm. 124*4882a593Smuzhiyun * The variables may be hardcoded into the declarations 125*4882a593Smuzhiyun * instead of using this structure to make use of 126*4882a593Smuzhiyun * register declarations. 127*4882a593Smuzhiyun */ 128*4882a593Smuzhiyun typedef struct { 129*4882a593Smuzhiyun int minor; /* minor axis */ 130*4882a593Smuzhiyun int d; /* decision variable */ 131*4882a593Smuzhiyun int m, m1; /* slope and slope+1 */ 132*4882a593Smuzhiyun int incr1, incr2; /* error increments */ 133*4882a593Smuzhiyun } BRESINFO; 134*4882a593Smuzhiyun 135*4882a593Smuzhiyun #define BRESINITPGONSTRUCT(dmaj, min1, min2, bres) \ 136*4882a593Smuzhiyun BRESINITPGON(dmaj, min1, min2, bres.minor, bres.d, \ 137*4882a593Smuzhiyun bres.m, bres.m1, bres.incr1, bres.incr2) 138*4882a593Smuzhiyun 139*4882a593Smuzhiyun #define BRESINCRPGONSTRUCT(bres) \ 140*4882a593Smuzhiyun BRESINCRPGON(bres.d, bres.minor, bres.m, bres.m1, bres.incr1, bres.incr2) 141*4882a593Smuzhiyun 142*4882a593Smuzhiyun #endif 143