Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
57 | pj | 1 | /* $Id: s_aatritemp.h,v 1.1 2003-02-28 11:49:40 pj Exp $ */ |
2 | |||
3 | /* |
||
4 | * Mesa 3-D graphics library |
||
5 | * Version: 4.1 |
||
6 | * |
||
7 | * Copyright (C) 1999-2002 Brian Paul All Rights Reserved. |
||
8 | * |
||
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: |
||
15 | * |
||
16 | * The above copyright notice and this permission notice shall be included |
||
17 | * in all copies or substantial portions of the Software. |
||
18 | * |
||
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. |
||
25 | */ |
||
26 | |||
27 | |||
28 | /* |
||
29 | * Antialiased Triangle Rasterizer Template |
||
30 | * |
||
31 | * This file is #include'd to generate custom AA triangle rasterizers. |
||
32 | * NOTE: this code hasn't been optimized yet. That'll come after it |
||
33 | * works correctly. |
||
34 | * |
||
35 | * The following macros may be defined to indicate what auxillary information |
||
36 | * must be copmuted across the triangle: |
||
37 | * DO_Z - if defined, compute Z values |
||
38 | * DO_RGBA - if defined, compute RGBA values |
||
39 | * DO_INDEX - if defined, compute color index values |
||
40 | * DO_SPEC - if defined, compute specular RGB values |
||
41 | * DO_TEX - if defined, compute unit 0 STRQ texcoords |
||
42 | * DO_MULTITEX - if defined, compute all unit's STRQ texcoords |
||
43 | */ |
||
44 | |||
45 | /*void triangle( GLcontext *ctx, GLuint v0, GLuint v1, GLuint v2, GLuint pv )*/ |
||
46 | { |
||
47 | const GLfloat *p0 = v0->win; |
||
48 | const GLfloat *p1 = v1->win; |
||
49 | const GLfloat *p2 = v2->win; |
||
50 | const SWvertex *vMin, *vMid, *vMax; |
||
51 | GLint iyMin, iyMax; |
||
52 | GLfloat yMin, yMax; |
||
53 | GLboolean ltor; |
||
54 | GLfloat majDx, majDy; /* major (i.e. long) edge dx and dy */ |
||
55 | |||
56 | struct sw_span span; |
||
57 | |||
58 | #ifdef DO_Z |
||
59 | GLfloat zPlane[4]; |
||
60 | #endif |
||
61 | #ifdef DO_FOG |
||
62 | GLfloat fogPlane[4]; |
||
63 | #else |
||
64 | GLfloat *fog = NULL; |
||
65 | #endif |
||
66 | #ifdef DO_RGBA |
||
67 | GLfloat rPlane[4], gPlane[4], bPlane[4], aPlane[4]; |
||
68 | #endif |
||
69 | #ifdef DO_INDEX |
||
70 | GLfloat iPlane[4]; |
||
71 | #endif |
||
72 | #ifdef DO_SPEC |
||
73 | GLfloat srPlane[4], sgPlane[4], sbPlane[4]; |
||
74 | #endif |
||
75 | #ifdef DO_TEX |
||
76 | GLfloat sPlane[4], tPlane[4], uPlane[4], vPlane[4]; |
||
77 | GLfloat texWidth, texHeight; |
||
78 | #elif defined(DO_MULTITEX) |
||
79 | GLfloat sPlane[MAX_TEXTURE_UNITS][4]; /* texture S */ |
||
80 | GLfloat tPlane[MAX_TEXTURE_UNITS][4]; /* texture T */ |
||
81 | GLfloat uPlane[MAX_TEXTURE_UNITS][4]; /* texture R */ |
||
82 | GLfloat vPlane[MAX_TEXTURE_UNITS][4]; /* texture Q */ |
||
83 | GLfloat texWidth[MAX_TEXTURE_UNITS], texHeight[MAX_TEXTURE_UNITS]; |
||
84 | #endif |
||
85 | GLfloat bf = SWRAST_CONTEXT(ctx)->_backface_sign; |
||
86 | |||
87 | |||
88 | INIT_SPAN(span, GL_POLYGON, 0, 0, SPAN_COVERAGE); |
||
89 | |||
90 | /* determine bottom to top order of vertices */ |
||
91 | { |
||
92 | GLfloat y0 = v0->win[1]; |
||
93 | GLfloat y1 = v1->win[1]; |
||
94 | GLfloat y2 = v2->win[1]; |
||
95 | if (y0 <= y1) { |
||
96 | if (y1 <= y2) { |
||
97 | vMin = v0; vMid = v1; vMax = v2; /* y0<=y1<=y2 */ |
||
98 | } |
||
99 | else if (y2 <= y0) { |
||
100 | vMin = v2; vMid = v0; vMax = v1; /* y2<=y0<=y1 */ |
||
101 | } |
||
102 | else { |
||
103 | vMin = v0; vMid = v2; vMax = v1; bf = -bf; /* y0<=y2<=y1 */ |
||
104 | } |
||
105 | } |
||
106 | else { |
||
107 | if (y0 <= y2) { |
||
108 | vMin = v1; vMid = v0; vMax = v2; bf = -bf; /* y1<=y0<=y2 */ |
||
109 | } |
||
110 | else if (y2 <= y1) { |
||
111 | vMin = v2; vMid = v1; vMax = v0; bf = -bf; /* y2<=y1<=y0 */ |
||
112 | } |
||
113 | else { |
||
114 | vMin = v1; vMid = v2; vMax = v0; /* y1<=y2<=y0 */ |
||
115 | } |
||
116 | } |
||
117 | } |
||
118 | |||
119 | majDx = vMax->win[0] - vMin->win[0]; |
||
120 | majDy = vMax->win[1] - vMin->win[1]; |
||
121 | |||
122 | { |
||
123 | const GLfloat botDx = vMid->win[0] - vMin->win[0]; |
||
124 | const GLfloat botDy = vMid->win[1] - vMin->win[1]; |
||
125 | const GLfloat area = majDx * botDy - botDx * majDy; |
||
126 | ltor = (GLboolean) (area < 0.0F); |
||
127 | /* Do backface culling */ |
||
128 | if (area * bf < 0 || area == 0 || IS_INF_OR_NAN(area)) |
||
129 | return; |
||
130 | } |
||
131 | |||
132 | #ifndef DO_OCCLUSION_TEST |
||
133 | ctx->OcclusionResult = GL_TRUE; |
||
134 | #endif |
||
135 | |||
136 | /* Plane equation setup: |
||
137 | * We evaluate plane equations at window (x,y) coordinates in order |
||
138 | * to compute color, Z, fog, texcoords, etc. This isn't terribly |
||
139 | * efficient but it's easy and reliable. |
||
140 | */ |
||
141 | #ifdef DO_Z |
||
142 | compute_plane(p0, p1, p2, p0[2], p1[2], p2[2], zPlane); |
||
143 | span.arrayMask |= SPAN_Z; |
||
144 | #endif |
||
145 | #ifdef DO_FOG |
||
146 | compute_plane(p0, p1, p2, v0->fog, v1->fog, v2->fog, fogPlane); |
||
147 | span.arrayMask |= SPAN_FOG; |
||
148 | #endif |
||
149 | #ifdef DO_RGBA |
||
150 | if (ctx->Light.ShadeModel == GL_SMOOTH) { |
||
151 | compute_plane(p0, p1, p2, v0->color[0], v1->color[0], v2->color[0], rPlane); |
||
152 | compute_plane(p0, p1, p2, v0->color[1], v1->color[1], v2->color[1], gPlane); |
||
153 | compute_plane(p0, p1, p2, v0->color[2], v1->color[2], v2->color[2], bPlane); |
||
154 | compute_plane(p0, p1, p2, v0->color[3], v1->color[3], v2->color[3], aPlane); |
||
155 | } |
||
156 | else { |
||
157 | constant_plane(v2->color[RCOMP], rPlane); |
||
158 | constant_plane(v2->color[GCOMP], gPlane); |
||
159 | constant_plane(v2->color[BCOMP], bPlane); |
||
160 | constant_plane(v2->color[ACOMP], aPlane); |
||
161 | } |
||
162 | span.arrayMask |= SPAN_RGBA; |
||
163 | #endif |
||
164 | #ifdef DO_INDEX |
||
165 | if (ctx->Light.ShadeModel == GL_SMOOTH) { |
||
166 | compute_plane(p0, p1, p2, (GLfloat) v0->index, |
||
167 | (GLfloat) v1->index, (GLfloat) v2->index, iPlane); |
||
168 | } |
||
169 | else { |
||
170 | constant_plane((GLfloat) v2->index, iPlane); |
||
171 | } |
||
172 | span.arrayMask |= SPAN_INDEX; |
||
173 | #endif |
||
174 | #ifdef DO_SPEC |
||
175 | if (ctx->Light.ShadeModel == GL_SMOOTH) { |
||
176 | compute_plane(p0, p1, p2, v0->specular[0], v1->specular[0], v2->specular[0],srPlane); |
||
177 | compute_plane(p0, p1, p2, v0->specular[1], v1->specular[1], v2->specular[1],sgPlane); |
||
178 | compute_plane(p0, p1, p2, v0->specular[2], v1->specular[2], v2->specular[2],sbPlane); |
||
179 | } |
||
180 | else { |
||
181 | constant_plane(v2->specular[RCOMP], srPlane); |
||
182 | constant_plane(v2->specular[GCOMP], sgPlane); |
||
183 | constant_plane(v2->specular[BCOMP], sbPlane); |
||
184 | } |
||
185 | span.arrayMask |= SPAN_SPEC; |
||
186 | #endif |
||
187 | #ifdef DO_TEX |
||
188 | { |
||
189 | const struct gl_texture_object *obj = ctx->Texture.Unit[0]._Current; |
||
190 | const struct gl_texture_image *texImage = obj->Image[obj->BaseLevel]; |
||
191 | const GLfloat invW0 = v0->win[3]; |
||
192 | const GLfloat invW1 = v1->win[3]; |
||
193 | const GLfloat invW2 = v2->win[3]; |
||
194 | const GLfloat s0 = v0->texcoord[0][0] * invW0; |
||
195 | const GLfloat s1 = v1->texcoord[0][0] * invW1; |
||
196 | const GLfloat s2 = v2->texcoord[0][0] * invW2; |
||
197 | const GLfloat t0 = v0->texcoord[0][1] * invW0; |
||
198 | const GLfloat t1 = v1->texcoord[0][1] * invW1; |
||
199 | const GLfloat t2 = v2->texcoord[0][1] * invW2; |
||
200 | const GLfloat r0 = v0->texcoord[0][2] * invW0; |
||
201 | const GLfloat r1 = v1->texcoord[0][2] * invW1; |
||
202 | const GLfloat r2 = v2->texcoord[0][2] * invW2; |
||
203 | const GLfloat q0 = v0->texcoord[0][3] * invW0; |
||
204 | const GLfloat q1 = v1->texcoord[0][3] * invW1; |
||
205 | const GLfloat q2 = v2->texcoord[0][3] * invW2; |
||
206 | compute_plane(p0, p1, p2, s0, s1, s2, sPlane); |
||
207 | compute_plane(p0, p1, p2, t0, t1, t2, tPlane); |
||
208 | compute_plane(p0, p1, p2, r0, r1, r2, uPlane); |
||
209 | compute_plane(p0, p1, p2, q0, q1, q2, vPlane); |
||
210 | texWidth = (GLfloat) texImage->Width; |
||
211 | texHeight = (GLfloat) texImage->Height; |
||
212 | } |
||
213 | span.arrayMask |= (SPAN_TEXTURE | SPAN_LAMBDA); |
||
214 | #elif defined(DO_MULTITEX) |
||
215 | { |
||
216 | GLuint u; |
||
217 | for (u = 0; u < ctx->Const.MaxTextureUnits; u++) { |
||
218 | if (ctx->Texture.Unit[u]._ReallyEnabled) { |
||
219 | const struct gl_texture_object *obj = ctx->Texture.Unit[u]._Current; |
||
220 | const struct gl_texture_image *texImage = obj->Image[obj->BaseLevel]; |
||
221 | const GLfloat invW0 = v0->win[3]; |
||
222 | const GLfloat invW1 = v1->win[3]; |
||
223 | const GLfloat invW2 = v2->win[3]; |
||
224 | const GLfloat s0 = v0->texcoord[u][0] * invW0; |
||
225 | const GLfloat s1 = v1->texcoord[u][0] * invW1; |
||
226 | const GLfloat s2 = v2->texcoord[u][0] * invW2; |
||
227 | const GLfloat t0 = v0->texcoord[u][1] * invW0; |
||
228 | const GLfloat t1 = v1->texcoord[u][1] * invW1; |
||
229 | const GLfloat t2 = v2->texcoord[u][1] * invW2; |
||
230 | const GLfloat r0 = v0->texcoord[u][2] * invW0; |
||
231 | const GLfloat r1 = v1->texcoord[u][2] * invW1; |
||
232 | const GLfloat r2 = v2->texcoord[u][2] * invW2; |
||
233 | const GLfloat q0 = v0->texcoord[u][3] * invW0; |
||
234 | const GLfloat q1 = v1->texcoord[u][3] * invW1; |
||
235 | const GLfloat q2 = v2->texcoord[u][3] * invW2; |
||
236 | compute_plane(p0, p1, p2, s0, s1, s2, sPlane[u]); |
||
237 | compute_plane(p0, p1, p2, t0, t1, t2, tPlane[u]); |
||
238 | compute_plane(p0, p1, p2, r0, r1, r2, uPlane[u]); |
||
239 | compute_plane(p0, p1, p2, q0, q1, q2, vPlane[u]); |
||
240 | texWidth[u] = (GLfloat) texImage->Width; |
||
241 | texHeight[u] = (GLfloat) texImage->Height; |
||
242 | } |
||
243 | } |
||
244 | } |
||
245 | span.arrayMask |= (SPAN_TEXTURE | SPAN_LAMBDA); |
||
246 | #endif |
||
247 | |||
248 | /* Begin bottom-to-top scan over the triangle. |
||
249 | * The long edge will either be on the left or right side of the |
||
250 | * triangle. We always scan from the long edge toward the shorter |
||
251 | * edges, stopping when we find that coverage = 0. If the long edge |
||
252 | * is on the left we scan left-to-right. Else, we scan right-to-left. |
||
253 | */ |
||
254 | yMin = vMin->win[1]; |
||
255 | yMax = vMax->win[1]; |
||
256 | iyMin = (GLint) yMin; |
||
257 | iyMax = (GLint) yMax + 1; |
||
258 | |||
259 | if (ltor) { |
||
260 | /* scan left to right */ |
||
261 | const GLfloat *pMin = vMin->win; |
||
262 | const GLfloat *pMid = vMid->win; |
||
263 | const GLfloat *pMax = vMax->win; |
||
264 | const GLfloat dxdy = majDx / majDy; |
||
265 | const GLfloat xAdj = dxdy < 0.0F ? -dxdy : 0.0F; |
||
266 | GLfloat x = pMin[0] - (yMin - iyMin) * dxdy; |
||
267 | GLint iy; |
||
268 | for (iy = iyMin; iy < iyMax; iy++, x += dxdy) { |
||
269 | GLint ix, startX = (GLint) (x - xAdj); |
||
270 | GLuint count; |
||
271 | GLfloat coverage = 0.0F; |
||
272 | |||
273 | /* skip over fragments with zero coverage */ |
||
274 | while (startX < MAX_WIDTH) { |
||
275 | coverage = compute_coveragef(pMin, pMid, pMax, startX, iy); |
||
276 | if (coverage > 0.0F) |
||
277 | break; |
||
278 | startX++; |
||
279 | } |
||
280 | |||
281 | /* enter interior of triangle */ |
||
282 | ix = startX; |
||
283 | count = 0; |
||
284 | while (coverage > 0.0F) { |
||
285 | /* (cx,cy) = center of fragment */ |
||
286 | const GLfloat cx = ix + 0.5F, cy = iy + 0.5F; |
||
287 | struct span_arrays *array = span.array; |
||
288 | #ifdef DO_INDEX |
||
289 | array->coverage[count] = (GLfloat) compute_coveragei(pMin, pMid, pMax, ix, iy); |
||
290 | #else |
||
291 | array->coverage[count] = coverage; |
||
292 | #endif |
||
293 | #ifdef DO_Z |
||
294 | array->z[count] = (GLdepth) solve_plane(cx, cy, zPlane); |
||
295 | #endif |
||
296 | #ifdef DO_FOG |
||
297 | array->fog[count] = solve_plane(cx, cy, fogPlane); |
||
298 | #endif |
||
299 | #ifdef DO_RGBA |
||
300 | array->rgba[count][RCOMP] = solve_plane_chan(cx, cy, rPlane); |
||
301 | array->rgba[count][GCOMP] = solve_plane_chan(cx, cy, gPlane); |
||
302 | array->rgba[count][BCOMP] = solve_plane_chan(cx, cy, bPlane); |
||
303 | array->rgba[count][ACOMP] = solve_plane_chan(cx, cy, aPlane); |
||
304 | #endif |
||
305 | #ifdef DO_INDEX |
||
306 | array->index[count] = (GLint) solve_plane(cx, cy, iPlane); |
||
307 | #endif |
||
308 | #ifdef DO_SPEC |
||
309 | array->spec[count][RCOMP] = solve_plane_chan(cx, cy, srPlane); |
||
310 | array->spec[count][GCOMP] = solve_plane_chan(cx, cy, sgPlane); |
||
311 | array->spec[count][BCOMP] = solve_plane_chan(cx, cy, sbPlane); |
||
312 | #endif |
||
313 | #ifdef DO_TEX |
||
314 | { |
||
315 | const GLfloat invQ = solve_plane_recip(cx, cy, vPlane); |
||
316 | array->texcoords[0][count][0] = solve_plane(cx, cy, sPlane) * invQ; |
||
317 | array->texcoords[0][count][1] = solve_plane(cx, cy, tPlane) * invQ; |
||
318 | array->texcoords[0][count][2] = solve_plane(cx, cy, uPlane) * invQ; |
||
319 | array->lambda[0][count] = compute_lambda(sPlane, tPlane, vPlane, |
||
320 | cx, cy, invQ, |
||
321 | texWidth, texHeight); |
||
322 | } |
||
323 | #elif defined(DO_MULTITEX) |
||
324 | { |
||
325 | GLuint unit; |
||
326 | for (unit = 0; unit < ctx->Const.MaxTextureUnits; unit++) { |
||
327 | if (ctx->Texture.Unit[unit]._ReallyEnabled) { |
||
328 | GLfloat invQ = solve_plane_recip(cx, cy, vPlane[unit]); |
||
329 | array->texcoords[unit][count][0] = solve_plane(cx, cy, sPlane[unit]) * invQ; |
||
330 | array->texcoords[unit][count][1] = solve_plane(cx, cy, tPlane[unit]) * invQ; |
||
331 | array->texcoords[unit][count][2] = solve_plane(cx, cy, uPlane[unit]) * invQ; |
||
332 | array->lambda[unit][count] = compute_lambda(sPlane[unit], |
||
333 | tPlane[unit], vPlane[unit], cx, cy, invQ, |
||
334 | texWidth[unit], texHeight[unit]); |
||
335 | } |
||
336 | } |
||
337 | } |
||
338 | #endif |
||
339 | ix++; |
||
340 | count++; |
||
341 | coverage = compute_coveragef(pMin, pMid, pMax, ix, iy); |
||
342 | } |
||
343 | |||
344 | if (ix <= startX) |
||
345 | continue; |
||
346 | |||
347 | span.x = startX; |
||
348 | span.y = iy; |
||
349 | span.end = (GLuint) ix - (GLuint) startX; |
||
350 | ASSERT(span.interpMask == 0); |
||
351 | #if defined(DO_MULTITEX) || defined(DO_TEX) |
||
352 | _mesa_write_texture_span(ctx, &span); |
||
353 | #elif defined(DO_RGBA) |
||
354 | _mesa_write_rgba_span(ctx, &span); |
||
355 | #elif defined(DO_INDEX) |
||
356 | _mesa_write_index_span(ctx, &span); |
||
357 | #endif |
||
358 | } |
||
359 | } |
||
360 | else { |
||
361 | /* scan right to left */ |
||
362 | const GLfloat *pMin = vMin->win; |
||
363 | const GLfloat *pMid = vMid->win; |
||
364 | const GLfloat *pMax = vMax->win; |
||
365 | const GLfloat dxdy = majDx / majDy; |
||
366 | const GLfloat xAdj = dxdy > 0 ? dxdy : 0.0F; |
||
367 | GLfloat x = pMin[0] - (yMin - iyMin) * dxdy; |
||
368 | GLint iy; |
||
369 | for (iy = iyMin; iy < iyMax; iy++, x += dxdy) { |
||
370 | GLint ix, left, startX = (GLint) (x + xAdj); |
||
371 | GLuint count, n; |
||
372 | GLfloat coverage = 0.0F; |
||
373 | |||
374 | /* make sure we're not past the window edge */ |
||
375 | if (startX >= ctx->DrawBuffer->_Xmax) { |
||
376 | startX = ctx->DrawBuffer->_Xmax - 1; |
||
377 | } |
||
378 | |||
379 | /* skip fragments with zero coverage */ |
||
380 | while (startX >= 0) { |
||
381 | coverage = compute_coveragef(pMin, pMax, pMid, startX, iy); |
||
382 | if (coverage > 0.0F) |
||
383 | break; |
||
384 | startX--; |
||
385 | } |
||
386 | |||
387 | /* enter interior of triangle */ |
||
388 | ix = startX; |
||
389 | count = 0; |
||
390 | while (coverage > 0.0F) { |
||
391 | /* (cx,cy) = center of fragment */ |
||
392 | const GLfloat cx = ix + 0.5F, cy = iy + 0.5F; |
||
393 | struct span_arrays *array = span.array; |
||
394 | #ifdef DO_INDEX |
||
395 | array->coverage[ix] = (GLfloat) compute_coveragei(pMin, pMax, pMid, ix, iy); |
||
396 | #else |
||
397 | array->coverage[ix] = coverage; |
||
398 | #endif |
||
399 | #ifdef DO_Z |
||
400 | array->z[ix] = (GLdepth) solve_plane(cx, cy, zPlane); |
||
401 | #endif |
||
402 | #ifdef DO_FOG |
||
403 | array->fog[ix] = solve_plane(cx, cy, fogPlane); |
||
404 | #endif |
||
405 | #ifdef DO_RGBA |
||
406 | array->rgba[ix][RCOMP] = solve_plane_chan(cx, cy, rPlane); |
||
407 | array->rgba[ix][GCOMP] = solve_plane_chan(cx, cy, gPlane); |
||
408 | array->rgba[ix][BCOMP] = solve_plane_chan(cx, cy, bPlane); |
||
409 | array->rgba[ix][ACOMP] = solve_plane_chan(cx, cy, aPlane); |
||
410 | #endif |
||
411 | #ifdef DO_INDEX |
||
412 | array->index[ix] = (GLint) solve_plane(cx, cy, iPlane); |
||
413 | #endif |
||
414 | #ifdef DO_SPEC |
||
415 | array->spec[ix][RCOMP] = solve_plane_chan(cx, cy, srPlane); |
||
416 | array->spec[ix][GCOMP] = solve_plane_chan(cx, cy, sgPlane); |
||
417 | array->spec[ix][BCOMP] = solve_plane_chan(cx, cy, sbPlane); |
||
418 | #endif |
||
419 | #ifdef DO_TEX |
||
420 | { |
||
421 | const GLfloat invQ = solve_plane_recip(cx, cy, vPlane); |
||
422 | array->texcoords[0][ix][0] = solve_plane(cx, cy, sPlane) * invQ; |
||
423 | array->texcoords[0][ix][1] = solve_plane(cx, cy, tPlane) * invQ; |
||
424 | array->texcoords[0][ix][2] = solve_plane(cx, cy, uPlane) * invQ; |
||
425 | array->lambda[0][ix] = compute_lambda(sPlane, tPlane, vPlane, |
||
426 | cx, cy, invQ, texWidth, texHeight); |
||
427 | } |
||
428 | #elif defined(DO_MULTITEX) |
||
429 | { |
||
430 | GLuint unit; |
||
431 | for (unit = 0; unit < ctx->Const.MaxTextureUnits; unit++) { |
||
432 | if (ctx->Texture.Unit[unit]._ReallyEnabled) { |
||
433 | GLfloat invQ = solve_plane_recip(cx, cy, vPlane[unit]); |
||
434 | array->texcoords[unit][ix][0] = solve_plane(cx, cy, sPlane[unit]) * invQ; |
||
435 | array->texcoords[unit][ix][1] = solve_plane(cx, cy, tPlane[unit]) * invQ; |
||
436 | array->texcoords[unit][ix][2] = solve_plane(cx, cy, uPlane[unit]) * invQ; |
||
437 | array->lambda[unit][ix] = compute_lambda(sPlane[unit], |
||
438 | tPlane[unit], |
||
439 | vPlane[unit], |
||
440 | cx, cy, invQ, |
||
441 | texWidth[unit], |
||
442 | texHeight[unit]); |
||
443 | } |
||
444 | } |
||
445 | } |
||
446 | #endif |
||
447 | ix--; |
||
448 | count++; |
||
449 | coverage = compute_coveragef(pMin, pMax, pMid, ix, iy); |
||
450 | } |
||
451 | |||
452 | if (startX <= ix) |
||
453 | continue; |
||
454 | |||
455 | n = (GLuint) startX - (GLuint) ix; |
||
456 | |||
457 | left = ix + 1; |
||
458 | |||
459 | /* shift all values to the left */ |
||
460 | /* XXX this is temporary */ |
||
461 | { |
||
462 | struct span_arrays *array = span.array; |
||
463 | GLint j; |
||
464 | for (j = 0; j < (GLint) n; j++) { |
||
465 | #ifdef DO_RGBA |
||
466 | COPY_4V(array->rgba[j], array->rgba[j + left]); |
||
467 | #endif |
||
468 | #ifdef DO_SPEC |
||
469 | COPY_4V(array->spec[j], array->spec[j + left]); |
||
470 | #endif |
||
471 | #ifdef DO_INDEX |
||
472 | array->index[j] = array->index[j + left]; |
||
473 | #endif |
||
474 | #ifdef DO_Z |
||
475 | array->z[j] = array->z[j + left]; |
||
476 | #endif |
||
477 | #ifdef DO_FOG |
||
478 | array->fog[j] = array->fog[j + left]; |
||
479 | #endif |
||
480 | #ifdef DO_TEX |
||
481 | COPY_4V(array->texcoords[0][j], array->texcoords[0][j + left]); |
||
482 | #endif |
||
483 | #if defined(DO_MULTITEX) || defined(DO_TEX) |
||
484 | array->lambda[0][j] = array->lambda[0][j + left]; |
||
485 | #endif |
||
486 | array->coverage[j] = array->coverage[j + left]; |
||
487 | } |
||
488 | } |
||
489 | #ifdef DO_MULTITEX |
||
490 | /* shift texcoords */ |
||
491 | { |
||
492 | struct span_arrays *array = span.array; |
||
493 | GLuint unit; |
||
494 | for (unit = 0; unit < ctx->Const.MaxTextureUnits; unit++) { |
||
495 | if (ctx->Texture.Unit[unit]._ReallyEnabled) { |
||
496 | GLint j; |
||
497 | for (j = 0; j < (GLint) n; j++) { |
||
498 | array->texcoords[unit][j][0] = array->texcoords[unit][j + left][0]; |
||
499 | array->texcoords[unit][j][1] = array->texcoords[unit][j + left][1]; |
||
500 | array->texcoords[unit][j][2] = array->texcoords[unit][j + left][2]; |
||
501 | array->lambda[unit][j] = array->lambda[unit][j + left]; |
||
502 | } |
||
503 | } |
||
504 | } |
||
505 | } |
||
506 | #endif |
||
507 | |||
508 | span.x = left; |
||
509 | span.y = iy; |
||
510 | span.end = n; |
||
511 | ASSERT(span.interpMask == 0); |
||
512 | #if defined(DO_MULTITEX) || defined(DO_TEX) |
||
513 | _mesa_write_texture_span(ctx, &span); |
||
514 | #elif defined(DO_RGBA) |
||
515 | _mesa_write_rgba_span(ctx, &span); |
||
516 | #elif defined(DO_INDEX) |
||
517 | _mesa_write_index_span(ctx, &span); |
||
518 | #endif |
||
519 | } |
||
520 | } |
||
521 | } |
||
522 | |||
523 | |||
524 | #ifdef DO_Z |
||
525 | #undef DO_Z |
||
526 | #endif |
||
527 | |||
528 | #ifdef DO_FOG |
||
529 | #undef DO_FOG |
||
530 | #endif |
||
531 | |||
532 | #ifdef DO_RGBA |
||
533 | #undef DO_RGBA |
||
534 | #endif |
||
535 | |||
536 | #ifdef DO_INDEX |
||
537 | #undef DO_INDEX |
||
538 | #endif |
||
539 | |||
540 | #ifdef DO_SPEC |
||
541 | #undef DO_SPEC |
||
542 | #endif |
||
543 | |||
544 | #ifdef DO_TEX |
||
545 | #undef DO_TEX |
||
546 | #endif |
||
547 | |||
548 | #ifdef DO_MULTITEX |
||
549 | #undef DO_MULTITEX |
||
550 | #endif |
||
551 | |||
552 | #ifdef DO_OCCLUSION_TEST |
||
553 | #undef DO_OCCLUSION_TEST |
||
554 | #endif |