poly.h
上传用户:zhongxx05
上传日期:2007-06-06
资源大小:33641k
文件大小:13k
- /* ***** BEGIN LICENSE BLOCK *****
- * Version: RCSL 1.0/RPSL 1.0
- *
- * Portions Copyright (c) 1995-2002 RealNetworks, Inc. All Rights Reserved.
- *
- * The contents of this file, and the files included with this file, are
- * subject to the current version of the RealNetworks Public Source License
- * Version 1.0 (the "RPSL") available at
- * http://www.helixcommunity.org/content/rpsl unless you have licensed
- * the file under the RealNetworks Community Source License Version 1.0
- * (the "RCSL") available at http://www.helixcommunity.org/content/rcsl,
- * in which case the RCSL will apply. You may also obtain the license terms
- * directly from RealNetworks. You may not use this file except in
- * compliance with the RPSL or, if you have a valid RCSL with RealNetworks
- * applicable to this file, the RCSL. Please see the applicable RPSL or
- * RCSL for the rights, obligations and limitations governing use of the
- * contents of the file.
- *
- * This file is part of the Helix DNA Technology. RealNetworks is the
- * developer and/or licensor of the Original Code and owns the copyrights
- * in the portions it created.
- *
- * This file, and the files included with this file, is distributed and made
- * available on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
- * EXPRESS OR IMPLIED, AND REALNETWORKS HEREBY DISCLAIMS ALL SUCH WARRANTIES,
- * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, FITNESS
- * FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
- *
- * Technology Compatibility Kit Test Suite(s) Location:
- * http://www.helixcommunity.org/content/tck
- *
- * Contributor(s):
- *
- * ***** END LICENSE BLOCK ***** */
- #ifndef _POLY_H
- #define _POLY_H
- /************************************************************************
- Copyright (c) 1987 X Consortium
- Permission is hereby granted, free of charge, to any person obtaining a copy
- of this software and associated documentation files (the "Software"), to deal
- in the Software without restriction, including without limitation the rights
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
- copies of the Software, and to permit persons to whom the Software is
- furnished to do so, subject to the following conditions:
- The above copyright notice and this permission notice shall be included in
- all copies or substantial portions of the Software.
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
- AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- Except as contained in this notice, the name of the X Consortium shall not be
- used in advertising or otherwise to promote the sale, use or other dealings
- in this Software without prior written authorization from the X Consortium.
- Copyright 1987 by Digital Equipment Corporation, Maynard, Massachusetts.
- All Rights Reserved
- Permission to use, copy, modify, and distribute this software and its
- documentation for any purpose and without fee is hereby granted,
- provided that the above copyright notice appear in all copies and that
- both that copyright notice and this permission notice appear in
- supporting documentation, and that the name of Digital not be
- used in advertising or publicity pertaining to distribution of the
- software without specific, written prior permission.
- DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
- ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
- DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
- ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
- WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
- ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
- SOFTWARE.
- ************************************************************************/
- /*
- * This file contains a few macros to help track
- * the edge of a filled object. The object is assumed
- * to be filled in scanline order, and thus the
- * algorithm used is an extension of Bresenham's line
- * drawing algorithm which assumes that y is always the
- * major axis.
- * Since these pieces of code are the same for any filled shape,
- * it is more convenient to gather the library in one
- * place, but since these pieces of code are also in
- * the inner loops of output primitives, procedure call
- * overhead is out of the question.
- * See the author for a derivation if needed.
- */
- #include "region.h"
- /*
- * In scan converting polygons, we want to choose those pixels
- * which are inside the polygon. Thus, we add .5 to the starting
- * x coordinate for both left and right edges. Now we choose the
- * first pixel which is inside the pgon for the left edge and the
- * first pixel which is outside the pgon for the right edge.
- * Draw the left pixel, but not the right.
- *
- * How to add .5 to the starting x coordinate:
- * If the edge is moving to the right, then subtract dy from the
- * error term from the general form of the algorithm.
- * If the edge is moving to the left, then add dy to the error term.
- *
- * The reason for the difference between edges moving to the left
- * and edges moving to the right is simple: If an edge is moving
- * to the right, then we want the algorithm to flip immediately.
- * If it is moving to the left, then we don't want it to flip until
- * we traverse an entire pixel.
- */
- #define BRESINITPGON(dy, x1, x2, xStart, d, m, m1, incr1, incr2) {
- int dx; /* local storage */
- /*
- * if the edge is horizontal, then it is ignored
- * and assumed not to be processed. Otherwise, do this stuff.
- */
- if ((dy) != 0) {
- xStart = (x1);
- dx = (x2) - xStart;
- if (dx < 0) {
- m = dx / (dy);
- m1 = m - 1;
- incr1 = -2 * dx + 2 * (dy) * m1;
- incr2 = -2 * dx + 2 * (dy) * m;
- d = 2 * m * (dy) - 2 * dx - 2 * (dy);
- } else {
- m = dx / (dy);
- m1 = m + 1;
- incr1 = 2 * dx - 2 * (dy) * m1;
- incr2 = 2 * dx - 2 * (dy) * m;
- d = -2 * m * (dy) + 2 * dx;
- }
- }
- }
- #define BRESINCRPGON(d, minval, m, m1, incr1, incr2) {
- if (m1 > 0) {
- if (d > 0) {
- minval += m1;
- d += incr1;
- }
- else {
- minval += m;
- d += incr2;
- }
- } else {
- if (d >= 0) {
- minval += m1;
- d += incr1;
- }
- else {
- minval += m;
- d += incr2;
- }
- }
- }
- /*
- * This structure contains all of the information needed
- * to run the bresenham algorithm.
- * The variables may be hardcoded into the declarations
- * instead of using this structure to make use of
- * register declarations.
- */
- typedef struct {
- int minor_axis; /* minor axis */
- int d; /* decision variable */
- int m, m1; /* slope and slope+1 */
- int incr1, incr2; /* error increments */
- } BRESINFO;
- #define BRESINITPGONSTRUCT(dmaj, min1, min2, bres)
- BRESINITPGON(dmaj, min1, min2, bres.minor_axis, bres.d,
- bres.m, bres.m1, bres.incr1, bres.incr2)
- #define BRESINCRPGONSTRUCT(bres)
- BRESINCRPGON(bres.d, bres.minor_axis, bres.m, bres.m1, bres.incr1, bres.incr2)
- /*
- * These are the data structures needed to scan
- * convert regions. Two different scan conversion
- * methods are available -- the even-odd method, and
- * the winding number method.
- * The even-odd rule states that a point is inside
- * the polygon if a ray drawn from that point in any
- * direction will pass through an odd number of
- * path segments.
- * By the winding number rule, a point is decided
- * to be inside the polygon if a ray drawn from that
- * point in any direction passes through a different
- * number of clockwise and counter-clockwise path
- * segments.
- *
- * These data structures are adapted somewhat from
- * the algorithm in (Foley/Van Dam) for scan converting
- * polygons.
- * The basic algorithm is to start at the top (smallest y)
- * of the polygon, stepping down to the bottom of
- * the polygon by incrementing the y coordinate. We
- * keep a list of edges which the current scanline crosses,
- * sorted by x. This list is called the Active Edge Table (AET)
- * As we change the y-coordinate, we update each entry in
- * in the active edge table to reflect the edges new xcoord.
- * This list must be sorted at each scanline in case
- * two edges intersect.
- * We also keep a data structure known as the Edge Table (ET),
- * which keeps track of all the edges which the current
- * scanline has not yet reached. The ET is basically a
- * list of ScanLineList structures containing a list of
- * edges which are entered at a given scanline. There is one
- * ScanLineList per scanline at which an edge is entered.
- * When we enter a new edge, we move it from the ET to the AET.
- *
- * From the AET, we can implement the even-odd rule as in
- * (Foley/Van Dam).
- * The winding number rule is a little trickier. We also
- * keep the EdgeTableEntries in the AET linked by the
- * nextWETE (winding EdgeTableEntry) link. This allows
- * the edges to be linked just as before for updating
- * purposes, but only uses the edges linked by the nextWETE
- * link as edges representing spans of the polygon to
- * drawn (as with the even-odd rule).
- */
- /*
- * for the winding number rule
- */
- #define CLOCKWISE 1
- #define COUNTERCLOCKWISE -1
- typedef struct _EdgeTableEntry {
- int ymax; /* ycoord at which we exit this edge. */
- BRESINFO bres; /* Bresenham info to run the edge */
- struct _EdgeTableEntry *next; /* next in the list */
- struct _EdgeTableEntry *back; /* for insertion sort */
- struct _EdgeTableEntry *nextWETE; /* for winding num rule */
- int ClockWise; /* flag for winding number rule */
- } EdgeTableEntry;
- typedef struct _ScanLineList{
- int scanline; /* the scanline represented */
- EdgeTableEntry *edgelist; /* header node */
- struct _ScanLineList *next; /* next in the list */
- } ScanLineList;
- typedef struct {
- int ymax; /* ymax for the polygon */
- int ymin; /* ymin for the polygon */
- ScanLineList scanlines; /* header node */
- } EdgeTable;
- /*
- * Here is a struct to help with storage allocation
- * so we can allocate a big chunk at a time, and then take
- * pieces from this heap when we need to.
- */
- #define SLLSPERBLOCK 25
- typedef struct _ScanLineListBlock {
- ScanLineList SLLs[SLLSPERBLOCK];
- struct _ScanLineListBlock *next;
- } ScanLineListBlock;
- /*
- *
- * a few macros for the inner loops of the fill code where
- * performance considerations don't allow a procedure call.
- *
- * Evaluate the given edge at the given scanline.
- * If the edge has expired, then we leave it and fix up
- * the active edge table; otherwise, we increment the
- * x value to be ready for the next scanline.
- * The winding number rule is in effect, so we must notify
- * the caller when the edge has been removed so he
- * can reorder the Winding Active Edge Table.
- */
- #define EVALUATEEDGEWINDING(pAET, pPrevAET, y, fixWAET) {
- if (pAET->ymax == y) { /* leaving this edge */
- pPrevAET->next = pAET->next;
- pAET = pPrevAET->next;
- fixWAET = 1;
- if (pAET)
- pAET->back = pPrevAET;
- }
- else {
- BRESINCRPGONSTRUCT(pAET->bres);
- pPrevAET = pAET;
- pAET = pAET->next;
- }
- }
- /*
- * Evaluate the given edge at the given scanline.
- * If the edge has expired, then we leave it and fix up
- * the active edge table; otherwise, we increment the
- * x value to be ready for the next scanline.
- * The even-odd rule is in effect.
- */
- #define EVALUATEEDGEEVENODD(pAET, pPrevAET, y) {
- if (pAET->ymax == y) { /* leaving this edge */
- pPrevAET->next = pAET->next;
- pAET = pPrevAET->next;
- if (pAET)
- pAET->back = pPrevAET;
- }
- else {
- BRESINCRPGONSTRUCT(pAET->bres);
- pPrevAET = pAET;
- pAET = pAET->next;
- }
- }
- #define EvenOddRule 1
- #define WindingRule 2
- #ifdef __cplusplus
- extern "C"
- #endif
- _HXRegion HXPolygonRegion(HXxPoint* Pts, int Count, int rule);
- #endif //_POLY_H