21e7ceef5af35a0a60880aee2ffd5c5cfa17ce85
1 /* $Id: s_tritemp.h,v 1.1 2000/10/31 18:00:04 keithw Exp $ */
4 * Mesa 3-D graphics library
7 * Copyright (C) 1999-2000 Brian Paul All Rights Reserved.
9 * Permission is hereby granted, free of charge, to any person obtaining a
10 * copy of this software and associated documentation files (the "Software"),
11 * to deal in the Software without restriction, including without limitation
12 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
13 * and/or sell copies of the Software, and to permit persons to whom the
14 * Software is furnished to do so, subject to the following conditions:
16 * The above copyright notice and this permission notice shall be included
17 * in all copies or substantial portions of the Software.
19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
20 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
22 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
23 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
24 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 * Triangle Rasterizer Template
31 * This file is #include'd to generate custom triangle rasterizers.
33 * The following macros may be defined to indicate what auxillary information
34 * must be interplated across the triangle:
35 * INTERP_Z - if defined, interpolate Z values
36 * INTERP_RGB - if defined, interpolate RGB values
37 * INTERP_SPEC - if defined, interpolate specular RGB values
38 * INTERP_ALPHA - if defined, interpolate Alpha values
39 * INTERP_INDEX - if defined, interpolate color index values
40 * INTERP_INT_TEX - if defined, interpolate integer ST texcoords
41 * (fast, simple 2-D texture mapping)
42 * INTERP_TEX - if defined, interpolate set 0 float STRQ texcoords
43 * NOTE: OpenGL STRQ = Mesa STUV (R was taken for red)
44 * INTERP_MULTITEX - if defined, interpolate N units of STRQ texcoords
46 * When one can directly address pixels in the color buffer the following
47 * macros can be defined and used to compute pixel addresses during
48 * rasterization (see pRow):
49 * PIXEL_TYPE - the datatype of a pixel (GLubyte, GLushort, GLuint)
50 * BYTES_PER_ROW - number of bytes per row in the color buffer
51 * PIXEL_ADDRESS(X,Y) - returns the address of pixel at (X,Y) where
52 * Y==0 at bottom of screen and increases upward.
54 * Similarly, for direct depth buffer access, this type is used for depth
56 * DEPTH_TYPE - either GLushort or GLuint
58 * Optionally, one may provide one-time setup code per triangle:
59 * SETUP_CODE - code which is to be executed once per triangle
61 * The following macro MUST be defined:
62 * INNER_LOOP(LEFT,RIGHT,Y) - code to write a span of pixels.
65 * for (x=LEFT; x<RIGHT;x++) {
67 * // increment fixed point interpolants
70 * This code was designed for the origin to be in the lower-left corner.
72 * Inspired by triangle rasterizer code written by Allen Akin. Thanks Allen!
76 /*void triangle( GLcontext *ctx, GLuint v0, GLuint v1, GLuint v2, GLuint pv )*/
79 GLint v0
, v1
; /* Y(v0) < Y(v1) */
80 GLfloat dx
; /* X(v1) - X(v0) */
81 GLfloat dy
; /* Y(v1) - Y(v0) */
82 GLfixed fdxdy
; /* dx/dy in fixed-point */
83 GLfixed fsx
; /* first sample point x coord */
85 GLfloat adjy
; /* adjust from v[0]->fy to fsy, scaled */
86 GLint lines
; /* number of lines to be sampled on this edge */
87 GLfixed fx0
; /* fixed pt X of lower endpoint */
91 const GLint depthBits
= ctx
->Visual
.DepthBits
;
92 const GLint fixedToDepthShift
= depthBits
<= 16 ? FIXED_SHIFT
: 0;
93 const GLfloat maxDepth
= ctx
->Visual
.DepthMaxF
;
94 #define FixedToDepth(F) ((F) >> fixedToDepthShift)
96 const struct vertex_buffer
*VB
= ctx
->VB
;
97 EdgeT eMaj
, eTop
, eBot
;
99 int vMin
, vMid
, vMax
; /* vertex indexes: Y(vMin)<=Y(vMid)<=Y(vMax) */
100 float bf
= ctx
->backface_sign
;
102 /* find the order of the 3 vertices along the Y axis */
104 GLfloat y0
= VB
->Win
.data
[v0
][1];
105 GLfloat y1
= VB
->Win
.data
[v1
][1];
106 GLfloat y2
= VB
->Win
.data
[v2
][1];
110 vMin
= v0
; vMid
= v1
; vMax
= v2
; /* y0<=y1<=y2 */
113 vMin
= v2
; vMid
= v0
; vMax
= v1
; /* y2<=y0<=y1 */
116 vMin
= v0
; vMid
= v2
; vMax
= v1
; bf
= -bf
; /* y0<=y2<=y1 */
121 vMin
= v1
; vMid
= v0
; vMax
= v2
; bf
= -bf
; /* y1<=y0<=y2 */
124 vMin
= v2
; vMid
= v1
; vMax
= v0
; bf
= -bf
; /* y2<=y1<=y0 */
127 vMin
= v1
; vMid
= v2
; vMax
= v0
; /* y1<=y2<=y0 */
132 /* vertex/edge relationship */
133 eMaj
.v0
= vMin
; eMaj
.v1
= vMax
; /*TODO: .v1's not needed */
134 eTop
.v0
= vMid
; eTop
.v1
= vMax
;
135 eBot
.v0
= vMin
; eBot
.v1
= vMid
;
137 /* compute deltas for each edge: vertex[v1] - vertex[v0] */
138 eMaj
.dx
= VB
->Win
.data
[vMax
][0] - VB
->Win
.data
[vMin
][0];
139 eMaj
.dy
= VB
->Win
.data
[vMax
][1] - VB
->Win
.data
[vMin
][1];
140 eTop
.dx
= VB
->Win
.data
[vMax
][0] - VB
->Win
.data
[vMid
][0];
141 eTop
.dy
= VB
->Win
.data
[vMax
][1] - VB
->Win
.data
[vMid
][1];
142 eBot
.dx
= VB
->Win
.data
[vMid
][0] - VB
->Win
.data
[vMin
][0];
143 eBot
.dy
= VB
->Win
.data
[vMid
][1] - VB
->Win
.data
[vMin
][1];
145 /* compute oneOverArea */
147 const GLfloat area
= eMaj
.dx
* eBot
.dy
- eBot
.dx
* eMaj
.dy
;
149 /* Do backface culling */
156 /* check for very tiny triangle */
157 if (area
* area
< 0.0025F
) /* square it to ensure positive value */
158 oneOverArea
= 1.0F
/ 0.0025F
; /* a close-enough value */
160 oneOverArea
= 1.0F
/ area
;
163 #ifndef DO_OCCLUSION_TEST
164 ctx
->OcclusionResult
= GL_TRUE
;
167 /* Edge setup. For a triangle strip these could be reused... */
169 /* fixed point Y coordinates */
170 GLfixed vMin_fx
= FloatToFixed(VB
->Win
.data
[vMin
][0] + 0.5F
);
171 GLfixed vMin_fy
= FloatToFixed(VB
->Win
.data
[vMin
][1] - 0.5F
);
172 GLfixed vMid_fx
= FloatToFixed(VB
->Win
.data
[vMid
][0] + 0.5F
);
173 GLfixed vMid_fy
= FloatToFixed(VB
->Win
.data
[vMid
][1] - 0.5F
);
174 GLfixed vMax_fy
= FloatToFixed(VB
->Win
.data
[vMax
][1] - 0.5F
);
176 eMaj
.fsy
= FixedCeil(vMin_fy
);
177 eMaj
.lines
= FixedToInt(vMax_fy
+ FIXED_ONE
- FIXED_EPSILON
- eMaj
.fsy
);
178 if (eMaj
.lines
> 0) {
179 GLfloat dxdy
= eMaj
.dx
/ eMaj
.dy
;
180 eMaj
.fdxdy
= SignedFloatToFixed(dxdy
);
181 eMaj
.adjy
= (GLfloat
) (eMaj
.fsy
- vMin_fy
); /* SCALED! */
183 eMaj
.fsx
= eMaj
.fx0
+ (GLfixed
) (eMaj
.adjy
* dxdy
);
189 eTop
.fsy
= FixedCeil(vMid_fy
);
190 eTop
.lines
= FixedToInt(vMax_fy
+ FIXED_ONE
- FIXED_EPSILON
- eTop
.fsy
);
191 if (eTop
.lines
> 0) {
192 GLfloat dxdy
= eTop
.dx
/ eTop
.dy
;
193 eTop
.fdxdy
= SignedFloatToFixed(dxdy
);
194 eTop
.adjy
= (GLfloat
) (eTop
.fsy
- vMid_fy
); /* SCALED! */
196 eTop
.fsx
= eTop
.fx0
+ (GLfixed
) (eTop
.adjy
* dxdy
);
199 eBot
.fsy
= FixedCeil(vMin_fy
);
200 eBot
.lines
= FixedToInt(vMid_fy
+ FIXED_ONE
- FIXED_EPSILON
- eBot
.fsy
);
201 if (eBot
.lines
> 0) {
202 GLfloat dxdy
= eBot
.dx
/ eBot
.dy
;
203 eBot
.fdxdy
= SignedFloatToFixed(dxdy
);
204 eBot
.adjy
= (GLfloat
) (eBot
.fsy
- vMin_fy
); /* SCALED! */
206 eBot
.fsx
= eBot
.fx0
+ (GLfixed
) (eBot
.adjy
* dxdy
);
211 * Conceptually, we view a triangle as two subtriangles
212 * separated by a perfectly horizontal line. The edge that is
213 * intersected by this line is one with maximal absolute dy; we
214 * call it a ``major'' edge. The other two edges are the
215 * ``top'' edge (for the upper subtriangle) and the ``bottom''
216 * edge (for the lower subtriangle). If either of these two
217 * edges is horizontal or very close to horizontal, the
218 * corresponding subtriangle might cover zero sample points;
219 * we take care to handle such cases, for performance as well
222 * By stepping rasterization parameters along the major edge,
223 * we can avoid recomputing them at the discontinuity where
224 * the top and bottom edges meet. However, this forces us to
225 * be able to scan both left-to-right and right-to-left.
226 * Also, we must determine whether the major edge is at the
227 * left or right side of the triangle. We do this by
228 * computing the magnitude of the cross-product of the major
229 * and top edges. Since this magnitude depends on the sine of
230 * the angle between the two edges, its sign tells us whether
231 * we turn to the left or to the right when travelling along
232 * the major edge to the top edge, and from this we infer
233 * whether the major edge is on the left or the right.
235 * Serendipitously, this cross-product magnitude is also a
236 * value we need to compute the iteration parameter
237 * derivatives for the triangle, and it can be used to perform
238 * backface culling because its sign tells us whether the
239 * triangle is clockwise or counterclockwise. In this code we
240 * refer to it as ``area'' because it's also proportional to
241 * the pixel area of the triangle.
245 GLint ltor
; /* true if scanning left-to-right */
247 GLfloat dzdx
, dzdy
; GLfixed fdzdx
;
248 GLfloat dfogdx
, dfogdy
; GLfixed fdfogdx
;
251 GLfloat drdx
, drdy
; GLfixed fdrdx
;
252 GLfloat dgdx
, dgdy
; GLfixed fdgdx
;
253 GLfloat dbdx
, dbdy
; GLfixed fdbdx
;
256 GLfloat dsrdx
, dsrdy
; GLfixed fdsrdx
;
257 GLfloat dsgdx
, dsgdy
; GLfixed fdsgdx
;
258 GLfloat dsbdx
, dsbdy
; GLfixed fdsbdx
;
261 GLfloat dadx
, dady
; GLfixed fdadx
;
264 GLfloat didx
, didy
; GLfixed fdidx
;
266 #ifdef INTERP_INT_TEX
267 GLfloat dsdx
, dsdy
; GLfixed fdsdx
;
268 GLfloat dtdx
, dtdy
; GLfixed fdtdx
;
276 #ifdef INTERP_MULTITEX
277 GLfloat dsdx
[MAX_TEXTURE_UNITS
], dsdy
[MAX_TEXTURE_UNITS
];
278 GLfloat dtdx
[MAX_TEXTURE_UNITS
], dtdy
[MAX_TEXTURE_UNITS
];
279 GLfloat dudx
[MAX_TEXTURE_UNITS
], dudy
[MAX_TEXTURE_UNITS
];
280 GLfloat dvdx
[MAX_TEXTURE_UNITS
], dvdy
[MAX_TEXTURE_UNITS
];
284 * Execute user-supplied setup code
290 ltor
= (oneOverArea
< 0.0F
);
292 /* compute d?/dx and d?/dy derivatives */
295 GLfloat eMaj_dz
, eBot_dz
;
296 eMaj_dz
= VB
->Win
.data
[vMax
][2] - VB
->Win
.data
[vMin
][2];
297 eBot_dz
= VB
->Win
.data
[vMid
][2] - VB
->Win
.data
[vMin
][2];
298 dzdx
= oneOverArea
* (eMaj_dz
* eBot
.dy
- eMaj
.dy
* eBot_dz
);
299 if (dzdx
> maxDepth
|| dzdx
< -maxDepth
) {
300 /* probably a sliver triangle */
305 dzdy
= oneOverArea
* (eMaj
.dx
* eBot_dz
- eMaj_dz
* eBot
.dx
);
308 fdzdx
= SignedFloatToFixed(dzdx
);
310 fdzdx
= (GLint
) dzdx
;
313 GLfloat eMaj_dfog
, eBot_dfog
;
314 eMaj_dfog
= (VB
->FogCoordPtr
->data
[vMax
] - VB
->FogCoordPtr
->data
[vMin
]) * 256;
315 eBot_dfog
= (VB
->FogCoordPtr
->data
[vMid
] - VB
->FogCoordPtr
->data
[vMin
]) * 256;
316 dfogdx
= oneOverArea
* (eMaj_dfog
* eBot
.dy
- eMaj
.dy
* eBot_dfog
);
317 fdfogdx
= SignedFloatToFixed(dfogdx
);
318 dfogdy
= oneOverArea
* (eMaj
.dx
* eBot_dfog
- eMaj_dfog
* eBot
.dx
);
323 GLfloat eMaj_dr
, eBot_dr
;
324 eMaj_dr
= (GLint
) VB
->ColorPtr
->data
[vMax
][0]
325 - (GLint
) VB
->ColorPtr
->data
[vMin
][0];
326 eBot_dr
= (GLint
) VB
->ColorPtr
->data
[vMid
][0]
327 - (GLint
) VB
->ColorPtr
->data
[vMin
][0];
328 drdx
= oneOverArea
* (eMaj_dr
* eBot
.dy
- eMaj
.dy
* eBot_dr
);
329 fdrdx
= SignedFloatToFixed(drdx
);
330 drdy
= oneOverArea
* (eMaj
.dx
* eBot_dr
- eMaj_dr
* eBot
.dx
);
333 GLfloat eMaj_dg
, eBot_dg
;
334 eMaj_dg
= (GLint
) VB
->ColorPtr
->data
[vMax
][1]
335 - (GLint
) VB
->ColorPtr
->data
[vMin
][1];
336 eBot_dg
= (GLint
) VB
->ColorPtr
->data
[vMid
][1]
337 - (GLint
) VB
->ColorPtr
->data
[vMin
][1];
338 dgdx
= oneOverArea
* (eMaj_dg
* eBot
.dy
- eMaj
.dy
* eBot_dg
);
339 fdgdx
= SignedFloatToFixed(dgdx
);
340 dgdy
= oneOverArea
* (eMaj
.dx
* eBot_dg
- eMaj_dg
* eBot
.dx
);
343 GLfloat eMaj_db
, eBot_db
;
344 eMaj_db
= (GLint
) VB
->ColorPtr
->data
[vMax
][2]
345 - (GLint
) VB
->ColorPtr
->data
[vMin
][2];
346 eBot_db
= (GLint
) VB
->ColorPtr
->data
[vMid
][2]
347 - (GLint
) VB
->ColorPtr
->data
[vMin
][2];
348 dbdx
= oneOverArea
* (eMaj_db
* eBot
.dy
- eMaj
.dy
* eBot_db
);
349 fdbdx
= SignedFloatToFixed(dbdx
);
350 dbdy
= oneOverArea
* (eMaj
.dx
* eBot_db
- eMaj_db
* eBot
.dx
);
355 GLfloat eMaj_dsr
, eBot_dsr
;
356 eMaj_dsr
= (GLint
) VB
->SecondaryColorPtr
->data
[vMax
][0]
357 - (GLint
) VB
->SecondaryColorPtr
->data
[vMin
][0];
358 eBot_dsr
= (GLint
) VB
->SecondaryColorPtr
->data
[vMid
][0]
359 - (GLint
) VB
->SecondaryColorPtr
->data
[vMin
][0];
360 dsrdx
= oneOverArea
* (eMaj_dsr
* eBot
.dy
- eMaj
.dy
* eBot_dsr
);
361 fdsrdx
= SignedFloatToFixed(dsrdx
);
362 dsrdy
= oneOverArea
* (eMaj
.dx
* eBot_dsr
- eMaj_dsr
* eBot
.dx
);
365 GLfloat eMaj_dsg
, eBot_dsg
;
366 eMaj_dsg
= (GLint
) VB
->SecondaryColorPtr
->data
[vMax
][1]
367 - (GLint
) VB
->SecondaryColorPtr
->data
[vMin
][1];
368 eBot_dsg
= (GLint
) VB
->SecondaryColorPtr
->data
[vMid
][1]
369 - (GLint
) VB
->SecondaryColorPtr
->data
[vMin
][1];
370 dsgdx
= oneOverArea
* (eMaj_dsg
* eBot
.dy
- eMaj
.dy
* eBot_dsg
);
371 fdsgdx
= SignedFloatToFixed(dsgdx
);
372 dsgdy
= oneOverArea
* (eMaj
.dx
* eBot_dsg
- eMaj_dsg
* eBot
.dx
);
375 GLfloat eMaj_dsb
, eBot_dsb
;
376 eMaj_dsb
= (GLint
) VB
->SecondaryColorPtr
->data
[vMax
][2]
377 - (GLint
) VB
->SecondaryColorPtr
->data
[vMin
][2];
378 eBot_dsb
= (GLint
) VB
->SecondaryColorPtr
->data
[vMid
][2]
379 - (GLint
) VB
->SecondaryColorPtr
->data
[vMin
][2];
380 dsbdx
= oneOverArea
* (eMaj_dsb
* eBot
.dy
- eMaj
.dy
* eBot_dsb
);
381 fdsbdx
= SignedFloatToFixed(dsbdx
);
382 dsbdy
= oneOverArea
* (eMaj
.dx
* eBot_dsb
- eMaj_dsb
* eBot
.dx
);
387 GLfloat eMaj_da
, eBot_da
;
388 eMaj_da
= (GLint
) VB
->ColorPtr
->data
[vMax
][3]
389 - (GLint
) VB
->ColorPtr
->data
[vMin
][3];
390 eBot_da
= (GLint
) VB
->ColorPtr
->data
[vMid
][3]
391 - (GLint
) VB
->ColorPtr
->data
[vMin
][3];
392 dadx
= oneOverArea
* (eMaj_da
* eBot
.dy
- eMaj
.dy
* eBot_da
);
393 fdadx
= SignedFloatToFixed(dadx
);
394 dady
= oneOverArea
* (eMaj
.dx
* eBot_da
- eMaj_da
* eBot
.dx
);
399 GLfloat eMaj_di
, eBot_di
;
400 eMaj_di
= (GLint
) VB
->IndexPtr
->data
[vMax
]
401 - (GLint
) VB
->IndexPtr
->data
[vMin
];
402 eBot_di
= (GLint
) VB
->IndexPtr
->data
[vMid
]
403 - (GLint
) VB
->IndexPtr
->data
[vMin
];
404 didx
= oneOverArea
* (eMaj_di
* eBot
.dy
- eMaj
.dy
* eBot_di
);
405 fdidx
= SignedFloatToFixed(didx
);
406 didy
= oneOverArea
* (eMaj
.dx
* eBot_di
- eMaj_di
* eBot
.dx
);
409 #ifdef INTERP_INT_TEX
411 GLfloat eMaj_ds
, eBot_ds
;
412 eMaj_ds
= (VB
->TexCoordPtr
[0]->data
[vMax
][0]
413 - VB
->TexCoordPtr
[0]->data
[vMin
][0]) * S_SCALE
;
414 eBot_ds
= (VB
->TexCoordPtr
[0]->data
[vMid
][0]
415 - VB
->TexCoordPtr
[0]->data
[vMin
][0]) * S_SCALE
;
416 dsdx
= oneOverArea
* (eMaj_ds
* eBot
.dy
- eMaj
.dy
* eBot_ds
);
417 fdsdx
= SignedFloatToFixed(dsdx
);
418 dsdy
= oneOverArea
* (eMaj
.dx
* eBot_ds
- eMaj_ds
* eBot
.dx
);
420 if (VB
->TexCoordPtr
[0]->size
> 1) {
421 GLfloat eMaj_dt
, eBot_dt
;
422 eMaj_dt
= (VB
->TexCoordPtr
[0]->data
[vMax
][1]
423 - VB
->TexCoordPtr
[0]->data
[vMin
][1]) * T_SCALE
;
424 eBot_dt
= (VB
->TexCoordPtr
[0]->data
[vMid
][1]
425 - VB
->TexCoordPtr
[0]->data
[vMin
][1]) * T_SCALE
;
426 dtdx
= oneOverArea
* (eMaj_dt
* eBot
.dy
- eMaj
.dy
* eBot_dt
);
427 fdtdx
= SignedFloatToFixed(dtdx
);
428 dtdy
= oneOverArea
* (eMaj
.dx
* eBot_dt
- eMaj_dt
* eBot
.dx
);
432 fdtdx
= SignedFloatToFixed(dtdx
);
439 GLfloat wMax
= VB
->Win
.data
[vMax
][3];
440 GLfloat wMin
= VB
->Win
.data
[vMin
][3];
441 GLfloat wMid
= VB
->Win
.data
[vMid
][3];
442 GLfloat eMaj_ds
, eBot_ds
;
443 GLfloat eMaj_dt
, eBot_dt
;
444 GLfloat eMaj_du
, eBot_du
;
445 GLfloat eMaj_dv
, eBot_dv
;
447 eMaj_ds
= VB
->TexCoordPtr
[0]->data
[vMax
][0] * wMax
448 - VB
->TexCoordPtr
[0]->data
[vMin
][0] * wMin
;
449 eBot_ds
= VB
->TexCoordPtr
[0]->data
[vMid
][0] * wMid
450 - VB
->TexCoordPtr
[0]->data
[vMin
][0] * wMin
;
451 dsdx
= oneOverArea
* (eMaj_ds
* eBot
.dy
- eMaj
.dy
* eBot_ds
);
452 dsdy
= oneOverArea
* (eMaj
.dx
* eBot_ds
- eMaj_ds
* eBot
.dx
);
455 if (VB
->TexCoordPtr
[0]->size
> 1) {
456 eMaj_dt
= VB
->TexCoordPtr
[0]->data
[vMax
][1] * wMax
457 - VB
->TexCoordPtr
[0]->data
[vMin
][1] * wMin
;
458 eBot_dt
= VB
->TexCoordPtr
[0]->data
[vMid
][1] * wMid
459 - VB
->TexCoordPtr
[0]->data
[vMin
][1] * wMin
;
460 dtdx
= oneOverArea
* (eMaj_dt
* eBot
.dy
- eMaj
.dy
* eBot_dt
);
461 dtdy
= oneOverArea
* (eMaj
.dx
* eBot_dt
- eMaj_dt
* eBot
.dx
);
468 if (VB
->TexCoordPtr
[0]->size
> 2) {
469 eMaj_du
= VB
->TexCoordPtr
[0]->data
[vMax
][2] * wMax
470 - VB
->TexCoordPtr
[0]->data
[vMin
][2] * wMin
;
471 eBot_du
= VB
->TexCoordPtr
[0]->data
[vMid
][2] * wMid
472 - VB
->TexCoordPtr
[0]->data
[vMin
][2] * wMin
;
473 dudx
= oneOverArea
* (eMaj_du
* eBot
.dy
- eMaj
.dy
* eBot_du
);
474 dudy
= oneOverArea
* (eMaj
.dx
* eBot_du
- eMaj_du
* eBot
.dx
);
481 if (VB
->TexCoordPtr
[0]->size
> 3) {
482 eMaj_dv
= VB
->TexCoordPtr
[0]->data
[vMax
][3] * wMax
483 - VB
->TexCoordPtr
[0]->data
[vMin
][3] * wMin
;
484 eBot_dv
= VB
->TexCoordPtr
[0]->data
[vMid
][3] * wMid
485 - VB
->TexCoordPtr
[0]->data
[vMin
][3] * wMin
;
486 dvdx
= oneOverArea
* (eMaj_dv
* eBot
.dy
- eMaj
.dy
* eBot_dv
);
487 dvdy
= oneOverArea
* (eMaj
.dx
* eBot_dv
- eMaj_dv
* eBot
.dx
);
490 eMaj_dv
= wMax
- wMin
;
491 eBot_dv
= wMid
- wMin
;
492 dvdx
= oneOverArea
* (eMaj_dv
* eBot
.dy
- eMaj
.dy
* eBot_dv
);
493 dvdy
= oneOverArea
* (eMaj
.dx
* eBot_dv
- eMaj_dv
* eBot
.dx
);
497 #ifdef INTERP_MULTITEX
499 GLfloat wMax
= VB
->Win
.data
[vMax
][3];
500 GLfloat wMin
= VB
->Win
.data
[vMin
][3];
501 GLfloat wMid
= VB
->Win
.data
[vMid
][3];
503 for (u
= 0; u
< ctx
->Const
.MaxTextureUnits
; u
++) {
504 if (ctx
->Texture
.Unit
[u
].ReallyEnabled
) {
505 GLfloat eMaj_ds
, eBot_ds
;
506 GLfloat eMaj_dt
, eBot_dt
;
507 GLfloat eMaj_du
, eBot_du
;
508 GLfloat eMaj_dv
, eBot_dv
;
509 eMaj_ds
= VB
->TexCoordPtr
[u
]->data
[vMax
][0] * wMax
510 - VB
->TexCoordPtr
[u
]->data
[vMin
][0] * wMin
;
511 eBot_ds
= VB
->TexCoordPtr
[u
]->data
[vMid
][0] * wMid
512 - VB
->TexCoordPtr
[u
]->data
[vMin
][0] * wMin
;
513 dsdx
[u
] = oneOverArea
* (eMaj_ds
* eBot
.dy
- eMaj
.dy
* eBot_ds
);
514 dsdy
[u
] = oneOverArea
* (eMaj
.dx
* eBot_ds
- eMaj_ds
* eBot
.dx
);
516 if (VB
->TexCoordPtr
[u
]->size
> 1) {
517 eMaj_dt
= VB
->TexCoordPtr
[u
]->data
[vMax
][1] * wMax
518 - VB
->TexCoordPtr
[u
]->data
[vMin
][1] * wMin
;
519 eBot_dt
= VB
->TexCoordPtr
[u
]->data
[vMid
][1] * wMid
520 - VB
->TexCoordPtr
[u
]->data
[vMin
][1] * wMin
;
521 dtdx
[u
] = oneOverArea
* (eMaj_dt
* eBot
.dy
- eMaj
.dy
* eBot_dt
);
522 dtdy
[u
] = oneOverArea
* (eMaj
.dx
* eBot_dt
- eMaj_dt
* eBot
.dx
);
529 if (VB
->TexCoordPtr
[u
]->size
> 2) {
530 eMaj_du
= VB
->TexCoordPtr
[u
]->data
[vMax
][2] * wMax
531 - VB
->TexCoordPtr
[u
]->data
[vMin
][2] * wMin
;
532 eBot_du
= VB
->TexCoordPtr
[u
]->data
[vMid
][2] * wMid
533 - VB
->TexCoordPtr
[u
]->data
[vMin
][2] * wMin
;
534 dudx
[u
] = oneOverArea
* (eMaj_du
* eBot
.dy
- eMaj
.dy
* eBot_du
);
535 dudy
[u
] = oneOverArea
* (eMaj
.dx
* eBot_du
- eMaj_du
* eBot
.dx
);
542 if (VB
->TexCoordPtr
[u
]->size
> 3) {
543 eMaj_dv
= VB
->TexCoordPtr
[u
]->data
[vMax
][3] * wMax
544 - VB
->TexCoordPtr
[u
]->data
[vMin
][3] * wMin
;
545 eBot_dv
= VB
->TexCoordPtr
[u
]->data
[vMid
][3] * wMid
546 - VB
->TexCoordPtr
[u
]->data
[vMin
][3] * wMin
;
547 dvdx
[u
] = oneOverArea
* (eMaj_dv
* eBot
.dy
- eMaj
.dy
* eBot_dv
);
548 dvdy
[u
] = oneOverArea
* (eMaj
.dx
* eBot_dv
- eMaj_dv
* eBot
.dx
);
551 eMaj_dv
= wMax
- wMin
;
552 eBot_dv
= wMid
- wMin
;
553 dvdx
[u
] = oneOverArea
* (eMaj_dv
* eBot
.dy
- eMaj
.dy
* eBot_dv
);
554 dvdy
[u
] = oneOverArea
* (eMaj
.dx
* eBot_dv
- eMaj_dv
* eBot
.dx
);
562 * We always sample at pixel centers. However, we avoid
563 * explicit half-pixel offsets in this code by incorporating
564 * the proper offset in each of x and y during the
565 * transformation to window coordinates.
567 * We also apply the usual rasterization rules to prevent
568 * cracks and overlaps. A pixel is considered inside a
569 * subtriangle if it meets all of four conditions: it is on or
570 * to the right of the left edge, strictly to the left of the
571 * right edge, on or below the top edge, and strictly above
572 * the bottom edge. (Some edges may be degenerate.)
574 * The following discussion assumes left-to-right scanning
575 * (that is, the major edge is on the left); the right-to-left
576 * case is a straightforward variation.
578 * We start by finding the half-integral y coordinate that is
579 * at or below the top of the triangle. This gives us the
580 * first scan line that could possibly contain pixels that are
581 * inside the triangle.
583 * Next we creep down the major edge until we reach that y,
584 * and compute the corresponding x coordinate on the edge.
585 * Then we find the half-integral x that lies on or just
586 * inside the edge. This is the first pixel that might lie in
587 * the interior of the triangle. (We won't know for sure
588 * until we check the other edges.)
590 * As we rasterize the triangle, we'll step down the major
591 * edge. For each step in y, we'll move an integer number
592 * of steps in x. There are two possible x step sizes, which
593 * we'll call the ``inner'' step (guaranteed to land on the
594 * edge or inside it) and the ``outer'' step (guaranteed to
595 * land on the edge or outside it). The inner and outer steps
596 * differ by one. During rasterization we maintain an error
597 * term that indicates our distance from the true edge, and
598 * select either the inner step or the outer step, whichever
599 * gets us to the first pixel that falls inside the triangle.
601 * All parameters (z, red, etc.) as well as the buffer
602 * addresses for color and z have inner and outer step values,
603 * so that we can increment them appropriately. This method
604 * eliminates the need to adjust parameters by creeping a
605 * sub-pixel amount into the triangle at each scanline.
610 GLfixed fx
, fxLeftEdge
, fxRightEdge
, fdxLeftEdge
, fdxRightEdge
;
614 GLfixed fError
, fdError
;
620 int dPRowOuter
, dPRowInner
; /* offset in bytes */
625 int dZRowOuter
, dZRowInner
; /* offset in bytes */
627 GLfixed fz
, fdzOuter
, fdzInner
;
628 GLfixed ffog
, fdfogOuter
, fdfogInner
;
631 GLfixed fr
, fdrOuter
, fdrInner
;
632 GLfixed fg
, fdgOuter
, fdgInner
;
633 GLfixed fb
, fdbOuter
, fdbInner
;
636 GLfixed fsr
, fdsrOuter
, fdsrInner
;
637 GLfixed fsg
, fdsgOuter
, fdsgInner
;
638 GLfixed fsb
, fdsbOuter
, fdsbInner
;
641 GLfixed fa
, fdaOuter
, fdaInner
;
644 GLfixed fi
, fdiOuter
, fdiInner
;
646 #ifdef INTERP_INT_TEX
647 GLfixed fs
, fdsOuter
, fdsInner
;
648 GLfixed ft
, fdtOuter
, fdtInner
;
651 GLfloat sLeft
, dsOuter
, dsInner
;
652 GLfloat tLeft
, dtOuter
, dtInner
;
653 GLfloat uLeft
, duOuter
, duInner
;
654 GLfloat vLeft
, dvOuter
, dvInner
;
656 #ifdef INTERP_MULTITEX
657 GLfloat sLeft
[MAX_TEXTURE_UNITS
];
658 GLfloat tLeft
[MAX_TEXTURE_UNITS
];
659 GLfloat uLeft
[MAX_TEXTURE_UNITS
];
660 GLfloat vLeft
[MAX_TEXTURE_UNITS
];
661 GLfloat dsOuter
[MAX_TEXTURE_UNITS
], dsInner
[MAX_TEXTURE_UNITS
];
662 GLfloat dtOuter
[MAX_TEXTURE_UNITS
], dtInner
[MAX_TEXTURE_UNITS
];
663 GLfloat duOuter
[MAX_TEXTURE_UNITS
], duInner
[MAX_TEXTURE_UNITS
];
664 GLfloat dvOuter
[MAX_TEXTURE_UNITS
], dvInner
[MAX_TEXTURE_UNITS
];
667 for (subTriangle
=0; subTriangle
<=1; subTriangle
++) {
668 EdgeT
*eLeft
, *eRight
;
669 int setupLeft
, setupRight
;
672 if (subTriangle
==0) {
677 lines
= eRight
->lines
;
684 lines
= eLeft
->lines
;
694 lines
= eRight
->lines
;
701 lines
= eLeft
->lines
;
709 if (setupLeft
&& eLeft
->lines
> 0) {
711 GLfixed fsx
= eLeft
->fsx
;
713 fError
= fx
- fsx
- FIXED_ONE
;
714 fxLeftEdge
= fsx
- FIXED_EPSILON
;
715 fdxLeftEdge
= eLeft
->fdxdy
;
716 fdxOuter
= FixedFloor(fdxLeftEdge
- FIXED_EPSILON
);
717 fdError
= fdxOuter
- fdxLeftEdge
+ FIXED_ONE
;
718 idxOuter
= FixedToInt(fdxOuter
);
719 dxOuter
= (float) idxOuter
;
725 adjx
= (float)(fx
- eLeft
->fx0
); /* SCALED! */
726 adjy
= eLeft
->adjy
; /* SCALED! */
727 (void) adjx
; /* silence compiler warnings */
728 (void) adjy
; /* silence compiler warnings */
731 (void) vLower
; /* silence compiler warnings */
735 pRow
= PIXEL_ADDRESS( FixedToInt(fxLeftEdge
), iy
);
736 dPRowOuter
= -((int)BYTES_PER_ROW
) + idxOuter
* sizeof(PIXEL_TYPE
);
737 /* negative because Y=0 at bottom and increases upward */
741 * Now we need the set of parameter (z, color, etc.) values at
742 * the point (fx, fy). This gives us properly-sampled parameter
743 * values that we can step from pixel to pixel. Furthermore,
744 * although we might have intermediate results that overflow
745 * the normal parameter range when we step temporarily outside
746 * the triangle, we shouldn't overflow or underflow for any
747 * pixel that's actually inside the triangle.
752 GLfloat z0
= VB
->Win
.data
[vLower
][2] + ctx
->PolygonZoffset
;
753 if (depthBits
<= 16) {
754 /* interpolate fixed-pt values */
755 GLfloat tmp
= (z0
* FIXED_SCALE
+
756 dzdx
* adjx
+ dzdy
* adjy
) + FIXED_HALF
;
757 if (tmp
< MAX_GLUINT
/ 2)
761 fdzOuter
= SignedFloatToFixed(dzdy
+ dxOuter
* dzdx
);
764 /* interpolate depth values exactly */
765 fz
= (GLint
) (z0
+ dzdx
*FixedToFloat(adjx
) + dzdy
*FixedToFloat(adjy
));
766 fdzOuter
= (GLint
) (dzdy
+ dxOuter
* dzdx
);
769 zRow
= (DEPTH_TYPE
*) _mesa_zbuffer_address(ctx
, FixedToInt(fxLeftEdge
), iy
);
770 dZRowOuter
= (ctx
->DrawBuffer
->Width
+ idxOuter
) * sizeof(DEPTH_TYPE
);
773 ffog
= FloatToFixed(VB
->FogCoordPtr
->data
[vLower
]) * 256 + dfogdx
* adjx
+ dfogdy
* adjy
+ FIXED_HALF
;
774 fdfogOuter
= SignedFloatToFixed(dfogdy
+ dxOuter
* dfogdx
);
777 fr
= (GLfixed
)(IntToFixed(VB
->ColorPtr
->data
[vLower
][0])
778 + drdx
* adjx
+ drdy
* adjy
) + FIXED_HALF
;
779 fdrOuter
= SignedFloatToFixed(drdy
+ dxOuter
* drdx
);
781 fg
= (GLfixed
)(IntToFixed(VB
->ColorPtr
->data
[vLower
][1])
782 + dgdx
* adjx
+ dgdy
* adjy
) + FIXED_HALF
;
783 fdgOuter
= SignedFloatToFixed(dgdy
+ dxOuter
* dgdx
);
785 fb
= (GLfixed
)(IntToFixed(VB
->ColorPtr
->data
[vLower
][2])
786 + dbdx
* adjx
+ dbdy
* adjy
) + FIXED_HALF
;
787 fdbOuter
= SignedFloatToFixed(dbdy
+ dxOuter
* dbdx
);
790 fsr
= (GLfixed
)(IntToFixed(VB
->SecondaryColorPtr
->data
[vLower
][0])
791 + dsrdx
* adjx
+ dsrdy
* adjy
) + FIXED_HALF
;
792 fdsrOuter
= SignedFloatToFixed(dsrdy
+ dxOuter
* dsrdx
);
794 fsg
= (GLfixed
)(IntToFixed(VB
->SecondaryColorPtr
->data
[vLower
][1])
795 + dsgdx
* adjx
+ dsgdy
* adjy
) + FIXED_HALF
;
796 fdsgOuter
= SignedFloatToFixed(dsgdy
+ dxOuter
* dsgdx
);
798 fsb
= (GLfixed
)(IntToFixed(VB
->SecondaryColorPtr
->data
[vLower
][2])
799 + dsbdx
* adjx
+ dsbdy
* adjy
) + FIXED_HALF
;
800 fdsbOuter
= SignedFloatToFixed(dsbdy
+ dxOuter
* dsbdx
);
803 fa
= (GLfixed
)(IntToFixed(VB
->ColorPtr
->data
[vLower
][3])
804 + dadx
* adjx
+ dady
* adjy
) + FIXED_HALF
;
805 fdaOuter
= SignedFloatToFixed(dady
+ dxOuter
* dadx
);
808 fi
= (GLfixed
)(VB
->IndexPtr
->data
[vLower
] * FIXED_SCALE
809 + didx
* adjx
+ didy
* adjy
) + FIXED_HALF
;
810 fdiOuter
= SignedFloatToFixed(didy
+ dxOuter
* didx
);
812 #ifdef INTERP_INT_TEX
815 s0
= VB
->TexCoordPtr
[0]->data
[vLower
][0] * S_SCALE
;
816 fs
= (GLfixed
)(s0
* FIXED_SCALE
+ dsdx
* adjx
+ dsdy
* adjy
) + FIXED_HALF
;
817 fdsOuter
= SignedFloatToFixed(dsdy
+ dxOuter
* dsdx
);
819 if (VB
->TexCoordPtr
[0]->size
> 1)
821 t0
= VB
->TexCoordPtr
[0]->data
[vLower
][1] * T_SCALE
;
822 ft
= (GLfixed
)(t0
* FIXED_SCALE
+ dtdx
* adjx
+ dtdy
* adjy
) + FIXED_HALF
;
823 fdtOuter
= SignedFloatToFixed(dtdy
+ dxOuter
* dtdx
);
828 ft
= (GLfixed
) FIXED_HALF
;
829 fdtOuter
= SignedFloatToFixed(0);
835 GLfloat invW
= VB
->Win
.data
[vLower
][3];
836 GLfloat s0
, t0
, u0
, v0
;
837 s0
= VB
->TexCoordPtr
[0]->data
[vLower
][0] * invW
;
838 sLeft
= s0
+ (dsdx
* adjx
+ dsdy
* adjy
) * (1.0F
/FIXED_SCALE
);
839 dsOuter
= dsdy
+ dxOuter
* dsdx
;
840 if (VB
->TexCoordPtr
[0]->size
> 1) {
841 t0
= VB
->TexCoordPtr
[0]->data
[vLower
][1] * invW
;
842 tLeft
= t0
+ (dtdx
* adjx
+ dtdy
* adjy
) * (1.0F
/FIXED_SCALE
);
843 dtOuter
= dtdy
+ dxOuter
* dtdx
;
846 tLeft
= dtOuter
= 0.0;
848 if (VB
->TexCoordPtr
[0]->size
> 2) {
849 u0
= VB
->TexCoordPtr
[0]->data
[vLower
][2] * invW
;
850 uLeft
= u0
+ (dudx
* adjx
+ dudy
* adjy
) * (1.0F
/FIXED_SCALE
);
851 duOuter
= dudy
+ dxOuter
* dudx
;
854 uLeft
= duOuter
= 0.0;
856 if (VB
->TexCoordPtr
[0]->size
> 3) {
857 v0
= VB
->TexCoordPtr
[0]->data
[vLower
][3] * invW
;
862 vLeft
= v0
+ (dvdx
* adjx
+ dvdy
* adjy
) * (1.0F
/FIXED_SCALE
);
863 dvOuter
= dvdy
+ dxOuter
* dvdx
;
866 #ifdef INTERP_MULTITEX
869 for (u
= 0; u
< ctx
->Const
.MaxTextureUnits
; u
++) {
870 if (ctx
->Texture
.Unit
[u
].ReallyEnabled
) {
871 GLfloat invW
= VB
->Win
.data
[vLower
][3];
872 GLfloat s0
, t0
, u0
, v0
;
873 s0
= VB
->TexCoordPtr
[u
]->data
[vLower
][0] * invW
;
874 sLeft
[u
] = s0
+ (dsdx
[u
] * adjx
+ dsdy
[u
] * adjy
) * (1.0F
/FIXED_SCALE
);
875 dsOuter
[u
] = dsdy
[u
] + dxOuter
* dsdx
[u
];
876 if (VB
->TexCoordPtr
[u
]->size
> 1) {
877 t0
= VB
->TexCoordPtr
[u
]->data
[vLower
][1] * invW
;
878 tLeft
[u
] = t0
+ (dtdx
[u
] * adjx
+ dtdy
[u
] * adjy
) * (1.0F
/FIXED_SCALE
);
879 dtOuter
[u
] = dtdy
[u
] + dxOuter
* dtdx
[u
];
882 tLeft
[u
] = dtOuter
[u
] = 0.0;
884 if (VB
->TexCoordPtr
[u
]->size
> 2) {
885 u0
= VB
->TexCoordPtr
[u
]->data
[vLower
][2] * invW
;
886 uLeft
[u
] = u0
+ (dudx
[u
] * adjx
+ dudy
[u
] * adjy
) * (1.0F
/FIXED_SCALE
);
887 duOuter
[u
] = dudy
[u
] + dxOuter
* dudx
[u
];
890 uLeft
[u
] = duOuter
[u
] = 0.0;
892 if (VB
->TexCoordPtr
[u
]->size
> 3) {
893 v0
= VB
->TexCoordPtr
[u
]->data
[vLower
][3] * invW
;
898 vLeft
[u
] = v0
+ (dvdx
[u
] * adjx
+ dvdy
[u
] * adjy
) * (1.0F
/FIXED_SCALE
);
899 dvOuter
[u
] = dvdy
[u
] + dxOuter
* dvdx
[u
];
908 if (setupRight
&& eRight
->lines
>0) {
909 fxRightEdge
= eRight
->fsx
- FIXED_EPSILON
;
910 fdxRightEdge
= eRight
->fdxdy
;
918 /* Rasterize setup */
920 dPRowInner
= dPRowOuter
+ sizeof(PIXEL_TYPE
);
924 dZRowInner
= dZRowOuter
+ sizeof(DEPTH_TYPE
);
926 fdzInner
= fdzOuter
+ fdzdx
;
927 fdfogInner
= fdfogOuter
+ fdfogdx
;
930 fdrInner
= fdrOuter
+ fdrdx
;
931 fdgInner
= fdgOuter
+ fdgdx
;
932 fdbInner
= fdbOuter
+ fdbdx
;
935 fdsrInner
= fdsrOuter
+ fdsrdx
;
936 fdsgInner
= fdsgOuter
+ fdsgdx
;
937 fdsbInner
= fdsbOuter
+ fdsbdx
;
940 fdaInner
= fdaOuter
+ fdadx
;
943 fdiInner
= fdiOuter
+ fdidx
;
945 #ifdef INTERP_INT_TEX
946 fdsInner
= fdsOuter
+ fdsdx
;
947 fdtInner
= fdtOuter
+ fdtdx
;
950 dsInner
= dsOuter
+ dsdx
;
951 dtInner
= dtOuter
+ dtdx
;
952 duInner
= duOuter
+ dudx
;
953 dvInner
= dvOuter
+ dvdx
;
955 #ifdef INTERP_MULTITEX
958 for (u
= 0; u
< ctx
->Const
.MaxTextureUnits
; u
++) {
959 if (ctx
->Texture
.Unit
[u
].ReallyEnabled
) {
960 dsInner
[u
] = dsOuter
[u
] + dsdx
[u
];
961 dtInner
[u
] = dtOuter
[u
] + dtdx
[u
];
962 duInner
[u
] = duOuter
[u
] + dudx
[u
];
963 dvInner
[u
] = dvOuter
[u
] + dvdx
[u
];
970 /* initialize the span interpolants to the leftmost value */
971 /* ff = fixed-pt fragment */
972 GLint left
= FixedToInt(fxLeftEdge
);
973 GLint right
= FixedToInt(fxRightEdge
);
976 GLfixed fffog
= ffog
;
979 GLfixed ffr
= fr
, ffg
= fg
, ffb
= fb
;
982 GLfixed ffsr
= fsr
, ffsg
= fsg
, ffsb
= fsb
;
990 #ifdef INTERP_INT_TEX
991 GLfixed ffs
= fs
, fft
= ft
;
994 GLfloat ss
= sLeft
, tt
= tLeft
, uu
= uLeft
, vv
= vLeft
;
996 #ifdef INTERP_MULTITEX
997 GLfloat ss
[MAX_TEXTURE_UNITS
];
998 GLfloat tt
[MAX_TEXTURE_UNITS
];
999 GLfloat uu
[MAX_TEXTURE_UNITS
];
1000 GLfloat vv
[MAX_TEXTURE_UNITS
];
1003 for (u
= 0; u
< ctx
->Const
.MaxTextureUnits
; u
++) {
1004 if (ctx
->Texture
.Unit
[u
].ReallyEnabled
) {
1016 /* need this to accomodate round-off errors */
1017 GLfixed ffrend
= ffr
+(right
-left
-1)*fdrdx
;
1018 GLfixed ffgend
= ffg
+(right
-left
-1)*fdgdx
;
1019 GLfixed ffbend
= ffb
+(right
-left
-1)*fdbdx
;
1020 if (ffrend
<0) ffr
-= ffrend
;
1021 if (ffgend
<0) ffg
-= ffgend
;
1022 if (ffbend
<0) ffb
-= ffbend
;
1030 /* need this to accomodate round-off errors */
1031 GLfixed ffsrend
= ffsr
+(right
-left
-1)*fdsrdx
;
1032 GLfixed ffsgend
= ffsg
+(right
-left
-1)*fdsgdx
;
1033 GLfixed ffsbend
= ffsb
+(right
-left
-1)*fdsbdx
;
1034 if (ffsrend
<0) ffsr
-= ffsrend
;
1035 if (ffsgend
<0) ffsg
-= ffsgend
;
1036 if (ffsbend
<0) ffsb
-= ffsbend
;
1037 if (ffsr
<0) ffsr
= 0;
1038 if (ffsg
<0) ffsg
= 0;
1039 if (ffsb
<0) ffsb
= 0;
1044 GLfixed ffaend
= ffa
+(right
-left
-1)*fdadx
;
1045 if (ffaend
<0) ffa
-= ffaend
;
1053 INNER_LOOP( left
, right
, iy
);
1056 * Advance to the next scan line. Compute the
1057 * new edge coordinates, and adjust the
1058 * pixel-center x coordinate so that it stays
1059 * on or inside the major edge.
1064 fxLeftEdge
+= fdxLeftEdge
;
1065 fxRightEdge
+= fdxRightEdge
;
1070 fError
-= FIXED_ONE
;
1071 #ifdef PIXEL_ADDRESS
1072 pRow
= (PIXEL_TYPE
*) ((GLubyte
*)pRow
+ dPRowOuter
);
1076 zRow
= (DEPTH_TYPE
*) ((GLubyte
*)zRow
+ dZRowOuter
);
1082 fr
+= fdrOuter
; fg
+= fdgOuter
; fb
+= fdbOuter
;
1085 fsr
+= fdsrOuter
; fsg
+= fdsgOuter
; fsb
+= fdsbOuter
;
1093 #ifdef INTERP_INT_TEX
1094 fs
+= fdsOuter
; ft
+= fdtOuter
;
1102 #ifdef INTERP_MULTITEX
1105 for (u
= 0; u
< ctx
->Const
.MaxTextureUnits
; u
++) {
1106 if (ctx
->Texture
.Unit
[u
].ReallyEnabled
) {
1107 sLeft
[u
] += dsOuter
[u
];
1108 tLeft
[u
] += dtOuter
[u
];
1109 uLeft
[u
] += duOuter
[u
];
1110 vLeft
[u
] += dvOuter
[u
];
1117 #ifdef PIXEL_ADDRESS
1118 pRow
= (PIXEL_TYPE
*) ((GLubyte
*)pRow
+ dPRowInner
);
1122 zRow
= (DEPTH_TYPE
*) ((GLubyte
*)zRow
+ dZRowInner
);
1128 fr
+= fdrInner
; fg
+= fdgInner
; fb
+= fdbInner
;
1131 fsr
+= fdsrInner
; fsg
+= fdsgInner
; fsb
+= fdsbInner
;
1139 #ifdef INTERP_INT_TEX
1140 fs
+= fdsInner
; ft
+= fdtInner
;
1148 #ifdef INTERP_MULTITEX
1151 for (u
= 0; u
< ctx
->Const
.MaxTextureUnits
; u
++) {
1152 if (ctx
->Texture
.Unit
[u
].ReallyEnabled
) {
1153 sLeft
[u
] += dsInner
[u
];
1154 tLeft
[u
] += dtInner
[u
];
1155 uLeft
[u
] += duInner
[u
];
1156 vLeft
[u
] += dvInner
[u
];
1164 } /* for subTriangle */
1174 #undef BYTES_PER_ROW
1175 #undef PIXEL_ADDRESS
1182 #undef INTERP_INT_TEX
1184 #undef INTERP_MULTITEX
1191 #undef DO_OCCLUSION_TEST