ReactOS 0.4.16-dev-320-g3bd9ddc
polyfill.c File Reference
#include <win32k.h>
#include <debug.h>
Include dependency graph for polyfill.c:

Go to the source code of this file.

Classes

struct  _tagFILL_EDGE
 
struct  _FILL_EDGE_LIST
 

Macros

#define NDEBUG
 
#define FILL_EDGE_ALLOC_TAG   0x45465044
 
#define DEBUG_PRINT_ACTIVE_EDGELIST(x)
 

Typedefs

typedef struct _tagFILL_EDGE FILL_EDGE
 
typedef struct _FILL_EDGE_LIST FILL_EDGE_LIST
 

Functions

static void FASTCALL POLYGONFILL_DestroyEdgeList (FILL_EDGE_LIST *list)
 
static FILL_EDGE *FASTCALL POLYGONFILL_MakeEdge (POINT From, POINT To)
 
static INT FASTCALL FILL_EDGE_Compare (FILL_EDGE *Edge1, FILL_EDGE *Edge2)
 
static void FASTCALL POLYGONFILL_ActiveListInsert (FILL_EDGE **activehead, FILL_EDGE *NewEdge)
 
static FILL_EDGE_LIST *FASTCALL POLYGONFILL_MakeEdgeList (PPOINT Points, int Count)
 
static void FASTCALL POLYGONFILL_UpdateScanline (FILL_EDGE *pEdge, int Scanline)
 
static void APIENTRY POLYGONFILL_BuildActiveList (int Scanline, FILL_EDGE_LIST *list, FILL_EDGE **ActiveHead)
 
static void APIENTRY POLYGONFILL_FillScanLineAlternate (PDC dc, int ScanLine, FILL_EDGE *ActiveHead, SURFACE *psurf, BRUSHOBJ *BrushObj, MIX RopMode)
 
static void APIENTRY POLYGONFILL_FillScanLineWinding (PDC dc, int ScanLine, FILL_EDGE *ActiveHead, SURFACE *psurf, BRUSHOBJ *BrushObj, MIX RopMode)
 
BOOL APIENTRY FillPolygon (PDC dc, SURFACE *psurf, BRUSHOBJ *BrushObj, MIX RopMode, CONST PPOINT Points, int Count, RECTL BoundRect)
 
BOOL FASTCALL IntFillPolygon (PDC dc, SURFACE *psurf, BRUSHOBJ *BrushObj, CONST PPOINT Points, int Count, RECTL DestRect, POINTL *BrushOrigin)
 

Macro Definition Documentation

◆ DEBUG_PRINT_ACTIVE_EDGELIST

#define DEBUG_PRINT_ACTIVE_EDGELIST (   x)

Definition at line 68 of file polyfill.c.

◆ FILL_EDGE_ALLOC_TAG

#define FILL_EDGE_ALLOC_TAG   0x45465044

Definition at line 14 of file polyfill.c.

◆ NDEBUG

#define NDEBUG

Definition at line 11 of file polyfill.c.

Typedef Documentation

◆ FILL_EDGE

◆ FILL_EDGE_LIST

Function Documentation

◆ FILL_EDGE_Compare()

static INT FASTCALL FILL_EDGE_Compare ( FILL_EDGE Edge1,
FILL_EDGE Edge2 
)
static

Definition at line 176 of file polyfill.c.

177{
178 int e1 = Edge1->XIntercept[0] + Edge1->XIntercept[1];
179 int e2 = Edge2->XIntercept[0] + Edge2->XIntercept[1];
180
181 return e1 - e2;
182}
int XIntercept[2]
Definition: polytest.cpp:186

Referenced by POLYGONFILL_ActiveListInsert().

◆ FillPolygon()

BOOL APIENTRY FillPolygon ( PDC  dc,
SURFACE psurf,
BRUSHOBJ BrushObj,
MIX  RopMode,
CONST PPOINT  Points,
int  Count,
RECTL  BoundRect 
)

Definition at line 538 of file polyfill.c.

546{
547 FILL_EDGE_LIST *list = 0;
548 FILL_EDGE *ActiveHead = 0;
549 int ScanLine;
550 PDC_ATTR pdcattr = dc->pdcattr;
551 void
552 (APIENTRY *FillScanLine)(
553 PDC dc,
554 int ScanLine,
555 FILL_EDGE* ActiveHead,
556 SURFACE *psurf,
557 BRUSHOBJ *BrushObj,
558 MIX RopMode);
559
560 //DPRINT("FillPolygon\n");
561
562 /* Create Edge List. */
564 /* DEBUG_PRINT_EDGELIST(list); */
565 if (NULL == list)
566 return FALSE;
567
568 if (WINDING == pdcattr->jFillMode)
569 FillScanLine = POLYGONFILL_FillScanLineWinding;
570 else /* Default */
572
573 /* For each Scanline from BoundRect.bottom to BoundRect.top,
574 * determine line segments to draw
575 */
576 for (ScanLine = BoundRect.top; ScanLine < BoundRect.bottom; ++ScanLine)
577 {
578 POLYGONFILL_BuildActiveList(ScanLine, list, &ActiveHead);
579 //DEBUG_PRINT_ACTIVE_EDGELIST(ActiveHead);
580 FillScanLine(dc, ScanLine, ActiveHead, psurf, BrushObj, RopMode);
581 }
582
583 /* Free Edge List. If any are left. */
585
586 return TRUE;
587}
#define WINDING
Definition: constants.h:279
Definition: list.h:37
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define APIENTRY
Definition: api.h:79
static const WCHAR dc[]
int Count
Definition: noreturn.cpp:7
static void APIENTRY POLYGONFILL_FillScanLineAlternate(PDC dc, int ScanLine, FILL_EDGE *ActiveHead, SURFACE *psurf, BRUSHOBJ *BrushObj, MIX RopMode)
Definition: polyfill.c:389
static void APIENTRY POLYGONFILL_FillScanLineWinding(PDC dc, int ScanLine, FILL_EDGE *ActiveHead, SURFACE *psurf, BRUSHOBJ *BrushObj, MIX RopMode)
Definition: polyfill.c:437
static FILL_EDGE_LIST *FASTCALL POLYGONFILL_MakeEdgeList(PPOINT Points, int Count)
Definition: polyfill.c:236
static void FASTCALL POLYGONFILL_DestroyEdgeList(FILL_EDGE_LIST *list)
Definition: polyfill.c:77
static void APIENTRY POLYGONFILL_BuildActiveList(int Scanline, FILL_EDGE_LIST *list, FILL_EDGE **ActiveHead)
Definition: polyfill.c:361
Definition: polytest.cpp:41
long bottom
Definition: polytest.cpp:53
long top
Definition: polytest.cpp:53
BYTE jFillMode
Definition: ntgdihdl.h:309
ULONG MIX
Definition: winddi.h:129

◆ IntFillPolygon()

BOOL FASTCALL IntFillPolygon ( PDC  dc,
SURFACE psurf,
BRUSHOBJ BrushObj,
CONST PPOINT  Points,
int  Count,
RECTL  DestRect,
POINTL BrushOrigin 
)

Definition at line 590 of file polyfill.c.

598{
599 FILL_EDGE_LIST *list = 0;
600 FILL_EDGE *ActiveHead = 0;
601 FILL_EDGE *pLeft, *pRight;
602 int ScanLine;
603
604 //DPRINT("IntFillPolygon\n");
605
606 /* Create Edge List. */
608 /* DEBUG_PRINT_EDGELIST(list); */
609 if (NULL == list)
610 return FALSE;
611
612 /* For each Scanline from DestRect.top to DestRect.bottom, determine line segments to draw */
613 for (ScanLine = DestRect.top; ScanLine < DestRect.bottom; ++ScanLine)
614 {
615 POLYGONFILL_BuildActiveList(ScanLine, list, &ActiveHead);
616 //DEBUG_PRINT_ACTIVE_EDGELIST(ActiveHead);
617
618 if (!ActiveHead)
619 {
621 return FALSE;
622 }
623
624 pLeft = ActiveHead;
625 pRight = pLeft->pNext;
626 ASSERT(pRight);
627
628 while (NULL != pRight)
629 {
630 int x1 = pLeft->XIntercept[0];
631 int x2 = pRight->XIntercept[1];
632
633 if (x2 > x1)
634 {
635 RECTL LineRect;
636 LineRect.top = ScanLine;
637 LineRect.bottom = ScanLine + 1;
638 LineRect.left = x1;
639 LineRect.right = x2;
640
641 IntEngBitBlt(&psurf->SurfObj,
642 NULL,
643 NULL,
644 (CLIPOBJ *)&dc->co,
645 NULL,
646 &LineRect,
647 NULL,
648 NULL,
649 BrushObj,
650 BrushOrigin,
652 }
653
654 pLeft = pRight->pNext;
655 pRight = pLeft ? pLeft->pNext : NULL;
656 }
657 }
658
659 /* Free Edge List. If any are left. */
661
662 return TRUE;
663}
#define ROP4_FROM_INDEX(index)
Definition: inteng.h:42
@ R3_OPINDEX_PATCOPY
Definition: inteng.h:35
#define ASSERT(a)
Definition: mode.c:44
long right
Definition: polytest.cpp:53
long left
Definition: polytest.cpp:53
SURFOBJ SurfObj
Definition: surface.h:8
struct _tagFILL_EDGE * pNext
Definition: polytest.cpp:192
BOOL APIENTRY IntEngBitBlt(SURFOBJ *psoTrg, SURFOBJ *psoSrc, SURFOBJ *psoMask, CLIPOBJ *pco, XLATEOBJ *pxlo, RECTL *prclTrg, POINTL *pptlSrc, POINTL *pptlMask, BRUSHOBJ *pbo, POINTL *pptlBrush, ROP4 Rop4)
Definition: bitblt.c:656
_In_ CLIPOBJ _In_ BRUSHOBJ _In_ LONG _In_ LONG _In_ LONG x2
Definition: winddi.h:3710
_In_ CLIPOBJ _In_ BRUSHOBJ _In_ LONG x1
Definition: winddi.h:3708

Referenced by IntEngFillPolygon(), and IntGdiPolygon().

◆ POLYGONFILL_ActiveListInsert()

static void FASTCALL POLYGONFILL_ActiveListInsert ( FILL_EDGE **  activehead,
FILL_EDGE NewEdge 
)
static

Definition at line 191 of file polyfill.c.

192{
193 FILL_EDGE *pPrev, *pThis;
194 //DPRINT1("In POLYGONFILL_ActiveListInsert()\n");
195 ASSERT(activehead && NewEdge);
196
197 if (!*activehead)
198 {
199 NewEdge->pNext = NULL;
200 *activehead = NewEdge;
201 return;
202 }
203 /*
204 ** First lets check to see if we have a new smallest value.
205 */
206 if (FILL_EDGE_Compare(NewEdge, *activehead) <= 0)
207 {
208 NewEdge->pNext = *activehead;
209 *activehead = NewEdge;
210 return;
211 }
212
213 /*
214 ** Ok, now scan to the next spot to put this item.
215 */
216 pThis = *activehead;
217 pPrev = NULL;
218 while ( pThis && FILL_EDGE_Compare(pThis, NewEdge) < 0 )
219 {
220 pPrev = pThis;
221 pThis = pThis->pNext;
222 }
223
224 ASSERT(pPrev);
225 NewEdge->pNext = pPrev->pNext;
226 pPrev->pNext = NewEdge;
227 //DEBUG_PRINT_ACTIVE_EDGELIST(*activehead);
228}
static INT FASTCALL FILL_EDGE_Compare(FILL_EDGE *Edge1, FILL_EDGE *Edge2)
Definition: polyfill.c:176

Referenced by POLYGONFILL_BuildActiveList().

◆ POLYGONFILL_BuildActiveList()

static void APIENTRY POLYGONFILL_BuildActiveList ( int  Scanline,
FILL_EDGE_LIST list,
FILL_EDGE **  ActiveHead 
)
static

Definition at line 361 of file polyfill.c.

365{
366 int i;
367
368 ASSERT(list && ActiveHead);
369 *ActiveHead = 0;
370 for (i = 0; i < list->Count; i++)
371 {
372 FILL_EDGE* pEdge = list->Edges[i];
373 ASSERT(pEdge);
374 if (pEdge->FromY <= Scanline && pEdge->ToY > Scanline)
375 {
376 POLYGONFILL_UpdateScanline(pEdge, Scanline);
377 POLYGONFILL_ActiveListInsert(ActiveHead, pEdge);
378 }
379 }
380}
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
static void FASTCALL POLYGONFILL_ActiveListInsert(FILL_EDGE **activehead, FILL_EDGE *NewEdge)
Definition: polyfill.c:191
static void FASTCALL POLYGONFILL_UpdateScanline(FILL_EDGE *pEdge, int Scanline)
Definition: polyfill.c:294

Referenced by FillPolygon(), and IntFillPolygon().

◆ POLYGONFILL_DestroyEdgeList()

static void FASTCALL POLYGONFILL_DestroyEdgeList ( FILL_EDGE_LIST list)
static

Definition at line 77 of file polyfill.c.

78{
79 int i;
80
81 if (list)
82 {
83 if (list->Edges)
84 {
85 for (i = 0; i < list->Count; i++)
86 {
88 if (list->Edges[i])
89 EngFreeMem(list->Edges[i]);
90 }
91
92 EngFreeMem(list->Edges);
93 }
94
96 }
97}
#define EngFreeMem
Definition: polytest.cpp:56
#define _PRAGMA_WARNING_SUPPRESS(x)
Definition: suppress.h:28
#define __WARNING_USING_UNINIT_VAR
Definition: suppress.h:31

Referenced by FillPolygon(), IntFillPolygon(), and POLYGONFILL_MakeEdgeList().

◆ POLYGONFILL_FillScanLineAlternate()

static void APIENTRY POLYGONFILL_FillScanLineAlternate ( PDC  dc,
int  ScanLine,
FILL_EDGE ActiveHead,
SURFACE psurf,
BRUSHOBJ BrushObj,
MIX  RopMode 
)
static

Definition at line 389 of file polyfill.c.

396{
397 FILL_EDGE *pLeft, *pRight;
398
399 if (!ActiveHead)
400 return;
401
402 pLeft = ActiveHead;
403 pRight = pLeft->pNext;
404 ASSERT(pRight);
405
406 while (NULL != pRight)
407 {
408 int x1 = pLeft->XIntercept[0];
409 int x2 = pRight->XIntercept[1];
410 if (x2 > x1)
411 {
412 RECTL BoundRect;
413 BoundRect.top = ScanLine;
414 BoundRect.bottom = ScanLine + 1;
415 BoundRect.left = x1;
416 BoundRect.right = x2;
417
418 //DPRINT("Fill Line (%d, %d) to (%d, %d)\n",x1, ScanLine, x2, ScanLine);
419 IntEngLineTo(&psurf->SurfObj,
420 (CLIPOBJ *)&dc->co,
421 BrushObj,
422 x1,
423 ScanLine,
424 x2,
425 ScanLine,
426 &BoundRect, // Bounding rectangle
427 RopMode); // MIX
428 }
429 pLeft = pRight->pNext;
430 pRight = pLeft ? pLeft->pNext : NULL;
431 }
432}
void IntEngLineTo(SURFOBJ *, CLIPOBJ, PBRUSHOBJ, int x1, int y1, int x2, int y2, RECTL *, MIX mix)
Definition: polytest.cpp:107

Referenced by FillPolygon().

◆ POLYGONFILL_FillScanLineWinding()

static void APIENTRY POLYGONFILL_FillScanLineWinding ( PDC  dc,
int  ScanLine,
FILL_EDGE ActiveHead,
SURFACE psurf,
BRUSHOBJ BrushObj,
MIX  RopMode 
)
static

Definition at line 437 of file polyfill.c.

444{
445 FILL_EDGE *pLeft, *pRight;
446 int x1, x2, winding = 0;
447 RECTL BoundRect;
448
449 if (!ActiveHead)
450 return;
451
452 BoundRect.top = ScanLine;
453 BoundRect.bottom = ScanLine + 1;
454
455 pLeft = ActiveHead;
456 winding = pLeft->YDirection;
457 pRight = pLeft->pNext;
458 ASSERT(pRight);
459
460 // Setup first line...
461 x1 = pLeft->XIntercept[0];
462 x2 = pRight->XIntercept[1];
463
464 pLeft = pRight;
465 pRight = pLeft->pNext;
466 winding += pLeft->YDirection;
467
468 while ( NULL != pRight )
469 {
470 int newx1 = pLeft->XIntercept[0];
471 int newx2 = pRight->XIntercept[1];
472 if ( winding )
473 {
474 // Check and see if this new line touches the previous...
475 if ((newx1 >= x1 && newx1 <= x2) ||
476 (newx2 >= x1 && newx2 <= x2) ||
477 (x1 >= newx1 && x1 <= newx2) ||
478 (x2 >= newx2 && x2 <= newx2))
479 {
480 // Yup, just tack it on to our existing line
481 x1 = min(x1,newx1);
482 x2 = max(x2,newx2);
483 }
484 else
485 {
486 // Nope - render the old line..
487 BoundRect.left = x1;
488 BoundRect.right = x2;
489
490 //DPRINT("Fill Line (%d, %d) to (%d, %d)\n",x1, ScanLine, x2, ScanLine);
491 IntEngLineTo(&psurf->SurfObj,
492 (CLIPOBJ *)&dc->co,
493 BrushObj,
494 x1,
495 ScanLine,
496 x2,
497 ScanLine,
498 &BoundRect, // Bounding rectangle
499 RopMode); // MIX
500
501 x1 = newx1;
502 x2 = newx2;
503 }
504 }
505
506 pLeft = pRight;
507 pRight = pLeft->pNext;
508 winding += pLeft->YDirection;
509 }
510
511 // There will always be a line left-over, render it now...
512 BoundRect.left = x1;
513 BoundRect.right = x2;
514
515 //DPRINT("Fill Line (%d, %d) to (%d, %d)\n",x1, ScanLine, x2, ScanLine);
516 IntEngLineTo(&psurf->SurfObj,
517 (CLIPOBJ *)&dc->co,
518 BrushObj,
519 x1,
520 ScanLine,
521 x2,
522 ScanLine,
523 &BoundRect, // Bounding rectangle
524 RopMode); // MIX
525}
#define min(a, b)
Definition: monoChain.cc:55
#define max(a, b)
Definition: svc.c:63

Referenced by FillPolygon().

◆ POLYGONFILL_MakeEdge()

static FILL_EDGE *FASTCALL POLYGONFILL_MakeEdge ( POINT  From,
POINT  To 
)
static

Definition at line 105 of file polyfill.c.

106{
108
109 if (0 == rc)
110 return NULL;
111
112 //DPRINT1("Making Edge: (%d, %d) to (%d, %d)\n", From.x, From.y, To.x, To.y);
113 // Now fill the struct.
114 if ( To.y < From.y )
115 {
116 rc->FromX = To.x;
117 rc->FromY = To.y;
118 rc->ToX = From.x;
119 rc->ToY = From.y;
120 rc->YDirection = -1;
121
122 // Lines that go up get walked backwards, so need to be offset
123 // by -1 in order to make the walk identically on a pixel-level
124 rc->Error = -1;
125 }
126 else
127 {
128 rc->FromX = From.x;
129 rc->FromY = From.y;
130 rc->ToX = To.x;
131 rc->ToY = To.y;
132 rc->YDirection = 1;
133
134 rc->Error = 0;
135 }
136
137 rc->x = rc->FromX;
138 rc->y = rc->FromY;
139 rc->dx = rc->ToX - rc->FromX;
140 rc->dy = rc->ToY - rc->FromY;
141 rc->absdx = abs(rc->dx);
142 rc->absdy = abs(rc->dy);
143
144 rc->xmajor = rc->absdx > rc->absdy;
145
146 rc->ErrorMax = max(rc->absdx,rc->absdy);
147
148 rc->Error += rc->ErrorMax / 2;
149
150 rc->XDirection = (rc->dx < 0)?(-1):(1);
151
152 rc->pNext = 0;
153
154 //DPRINT("MakeEdge (%i,%i)->(%i,%i) d=(%i,%i) dir=(%i,%i) err=%i max=%i\n",
155 // From.x, From.y, To.x, To.y, rc->dx, rc->dy, rc->XDirection, rc->YDirection, rc->Error, rc->ErrorMax );
156
157 return rc;
158}
#define abs(i)
Definition: fconv.c:206
#define FILL_EDGE_ALLOC_TAG
Definition: polyfill.c:14
#define FL_ZERO_MEMORY
Definition: polytest.cpp:58
void * EngAllocMem(int zero, unsigned long size, int tag=0)
Definition: polytest.cpp:70
long y
Definition: polytest.cpp:48
long x
Definition: polytest.cpp:48

Referenced by POLYGONFILL_MakeEdgeList().

◆ POLYGONFILL_MakeEdgeList()

static FILL_EDGE_LIST *FASTCALL POLYGONFILL_MakeEdgeList ( PPOINT  Points,
int  Count 
)
static

Definition at line 236 of file polyfill.c.

237{
238 int CurPt = 0;
239 FILL_EDGE_LIST* list = 0;
240 FILL_EDGE* e = 0;
241
242 if (0 == Points || 2 > Count)
243 return 0;
244
246 if ( 0 == list )
247 goto fail;
248 list->Count = 0;
250 if ( !list->Edges )
251 goto fail;
252
253 memset(list->Edges, 0, Count * sizeof(FILL_EDGE*));
254
255 for (CurPt = 1; CurPt < Count; ++CurPt)
256 {
257 e = POLYGONFILL_MakeEdge ( Points[CurPt-1], Points[CurPt] );
258 if (!e)
259 goto fail;
260
261 // If a straight horizontal line - who cares?
262 if (!e->absdy)
263 EngFreeMem(e);
264 else
265 list->Edges[list->Count++] = e;
266 }
267 e = POLYGONFILL_MakeEdge ( Points[CurPt-1], Points[0] );
268 if ( !e )
269 goto fail;
270
271 if (!e->absdy)
272 EngFreeMem(e);
273 else
274 list->Edges[list->Count++] = e;
275 return list;
276
277fail:
278
279 DPRINT1("Out Of MEMORY!!\n");
281 return 0;
282}
#define DPRINT1
Definition: precomp.h:8
#define e
Definition: ke_i.h:82
static FILL_EDGE *FASTCALL POLYGONFILL_MakeEdge(POINT From, POINT To)
Definition: polyfill.c:105
#define list
Definition: rosglue.h:35
#define memset(x, y, z)
Definition: compat.h:39

Referenced by FillPolygon(), and IntFillPolygon().

◆ POLYGONFILL_UpdateScanline()

static void FASTCALL POLYGONFILL_UpdateScanline ( FILL_EDGE pEdge,
int  Scanline 
)
static

Definition at line 294 of file polyfill.c.

295{
296 if (0 == pEdge->dy)
297 return;
298
299 ASSERT(pEdge->FromY <= Scanline && pEdge->ToY > Scanline);
300
301 if (pEdge->xmajor)
302 {
303 int steps;
304
305 ASSERT(pEdge->y == Scanline);
306
307 // Now shoot to end of scanline collision
308 steps = (pEdge->ErrorMax-pEdge->Error-1)/pEdge->absdy;
309 if (steps)
310 {
311 // Record first collision with scanline
312 int x1 = pEdge->x;
313 pEdge->x += steps * pEdge->XDirection;
314 pEdge->Error += steps * pEdge->absdy;
315 ASSERT ( pEdge->Error < pEdge->ErrorMax );
316 pEdge->XIntercept[0] = min(x1,pEdge->x);
317 pEdge->XIntercept[1] = max(x1,pEdge->x);
318 }
319 else
320 {
321 pEdge->XIntercept[0] = pEdge->x;
322 pEdge->XIntercept[1] = pEdge->x;
323 }
324
325 // We should require exactly 1 step to step onto next scanline...
326 ASSERT((pEdge->ErrorMax-pEdge->Error-1) / pEdge->absdy == 0);
327 pEdge->x += pEdge->XDirection;
328 pEdge->Error += pEdge->absdy;
329 ASSERT(pEdge->Error >= pEdge->ErrorMax);
330
331 // Now step onto next scanline...
332 pEdge->Error -= pEdge->absdx;
333 pEdge->y++;
334 }
335 else // Then this is a y-major line
336 {
337 pEdge->XIntercept[0] = pEdge->x;
338 pEdge->XIntercept[1] = pEdge->x;
339
340 pEdge->Error += pEdge->absdx;
341 pEdge->y++;
342
343 if (pEdge->Error >= pEdge->ErrorMax)
344 {
345 pEdge->Error -= pEdge->ErrorMax;
346 pEdge->x += pEdge->XDirection;
347 ASSERT ( pEdge->Error < pEdge->ErrorMax );
348 }
349 }
350
351 //DPRINT("Line (%d, %d) to (%d, %d) intersects scanline %d at (%d,%d)\n",
352 // pEdge->FromX, pEdge->FromY, pEdge->ToX, pEdge->ToY, Scanline, pEdge->XIntercept[0], pEdge->XIntercept[1] );
353}
if(dx< 0)
Definition: linetemp.h:194
static DWORD DWORD DWORD DWORD * steps
Definition: cursoricon.c:1638

Referenced by POLYGONFILL_BuildActiveList().