Use smooth shaded triangles always. Fix SoF bug.
[mesa.git] / src / mesa / drivers / ggi / default / stubs.c
1 /* GGI-Driver for MESA
2 *
3 * Copyright (C) 1997 Uwe Maurer
4 *
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Library General Public
7 * License as published by the Free Software Foundation; either
8 * version 2 of the License, or (at your option) any later version.
9 *
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Library General Public License for more details.
14 *
15 * You should have received a copy of the GNU Library General Public
16 * License along with this library; if not, write to the Free
17 * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 * ---------------------------------------------------------------------
19 * This code was derived from the following source of information:
20 *
21 * svgamesa.c and ddsample.c by Brian Paul
22 *
23 */
24
25 #include <stdio.h>
26
27 #include <ggi/internal/ggi-dl.h>
28 #include <ggi/mesa/ggimesa_int.h>
29
30 /**********************************************************************/
31 /***** Write spans of pixels *****/
32 /**********************************************************************/
33
34 void GGIwrite_ci32_span(const GLcontext *ctx,
35 GLuint n, GLint x, GLint y,
36 const GLuint ci[],
37 const GLubyte mask[] )
38 {
39 y=FLIP(y);
40 if (mask)
41 {
42 while (n--) {
43 if (*mask++) ggiPutPixel(VIS,x,y,*ci);
44 x++;
45 ci++;
46 }
47 }
48 else
49 {
50 while (n--) ggiPutPixel(VIS,x++,y,*ci++);
51 }
52 }
53
54 void GGIwrite_ci8_span(const GLcontext *ctx,
55 GLuint n, GLint x, GLint y,
56 const GLubyte ci[],
57 const GLubyte mask[] )
58 {
59 y=FLIP(y);
60 if (mask)
61 {
62 while (n--) {
63 if (*mask++) ggiPutPixel(VIS,x,y,*ci);
64 x++;
65 ci++;
66 }
67 }
68 else
69 {
70 while (n--) ggiPutPixel(VIS,x++,y,*ci++);
71 }
72 }
73
74 void GGIwrite_mono_span( const GLcontext *ctx,
75 GLuint n, GLint x, GLint y,
76 const GLubyte mask[] )
77 {
78 y=FLIP(y);
79 if (mask)
80 {
81 while (n--) {
82 if (*mask++) ggiDrawPixel(VIS,x,y);
83 x++;
84 }
85 }
86 else
87 {
88 ggiDrawHLine(VIS,x,y,n);
89 }
90 }
91
92 void GGIwrite_rgba_span( const GLcontext *ctx,
93 GLuint n, GLint x, GLint y,
94 const GLubyte rgba[][4],
95 const GLubyte mask[])
96 {
97 ggi_color rgb;
98 ggi_pixel col;
99 y=FLIP(y);
100
101 if (mask)
102 {
103 while (n--) {
104 if (*mask++)
105 {
106 rgb.r=(uint16)(rgba[0][RCOMP]) << SHIFT;
107 rgb.g=(uint16)(rgba[0][GCOMP]) << SHIFT;
108 rgb.b=(uint16)(rgba[0][BCOMP]) << SHIFT;
109 col=ggiMapColor(VIS,&rgb);
110 ggiPutPixel(VIS,x,y,col);
111 }
112 x++;
113 rgba++;
114 }
115 }
116 else
117 {
118 while (n--)
119 {
120 rgb.r=(uint16)(rgba[0][RCOMP]) << SHIFT;
121 rgb.g=(uint16)(rgba[0][GCOMP]) << SHIFT;
122 rgb.b=(uint16)(rgba[0][BCOMP]) << SHIFT;
123 col=ggiMapColor(VIS,&rgb);
124 ggiPutPixel(VIS,x++,y,col);
125 rgba++;
126 }
127 }
128 }
129 void GGIwrite_rgb_span( const GLcontext *ctx,
130 GLuint n, GLint x, GLint y,
131 const GLubyte rgba[][3],
132 const GLubyte mask[] )
133 {
134 ggi_color rgb;
135 ggi_pixel col;
136 y=FLIP(y);
137
138 if (mask)
139 {
140 while (n--) {
141 if (*mask++)
142 {
143 rgb.r=(uint16)(rgba[0][RCOMP]) << SHIFT;
144 rgb.g=(uint16)(rgba[0][GCOMP]) << SHIFT;
145 rgb.b=(uint16)(rgba[0][BCOMP]) << SHIFT;
146 col=ggiMapColor(VIS,&rgb);
147 ggiPutPixel(VIS,x,y,col);
148 }
149 x++;
150 rgba++;
151 }
152 }
153 else
154 {
155 while (n--)
156 {
157 rgb.r=(uint16)(rgba[0][RCOMP]) << SHIFT;
158 rgb.g=(uint16)(rgba[0][GCOMP]) << SHIFT;
159 rgb.b=(uint16)(rgba[0][BCOMP]) << SHIFT;
160 col=ggiMapColor(VIS,&rgb);
161 ggiPutPixel(VIS,x++,y,col);
162 rgba++;
163 }
164 }
165 }
166
167
168
169 /**********************************************************************/
170 /***** Read spans of pixels *****/
171 /**********************************************************************/
172
173
174 void GGIread_ci32_span( const GLcontext *ctx,
175 GLuint n, GLint x, GLint y, GLuint ci[])
176 {
177 y = FLIP(y);
178 while (n--)
179 ggiGetPixel(VIS, x++, y,ci++);
180 }
181
182 void GGIread_rgba_span( const GLcontext *ctx,
183 GLuint n, GLint x, GLint y,
184 GLubyte rgba[][4])
185 {
186 ggi_color rgb;
187 ggi_pixel col;
188
189 y=FLIP(y);
190
191 while (n--)
192 {
193 ggiGetPixel(VIS,x++,y,&col);
194 ggiUnmapPixel(VIS,col,&rgb);
195 rgba[0][RCOMP] = (GLubyte) (rgb.r >> SHIFT);
196 rgba[0][GCOMP] = (GLubyte) (rgb.g >> SHIFT);
197 rgba[0][BCOMP] = (GLubyte) (rgb.b >> SHIFT);
198 rgba[0][ACOMP] = 0;
199 rgba++;
200 }
201 }
202
203 /**********************************************************************/
204 /***** Write arrays of pixels *****/
205 /**********************************************************************/
206
207 void GGIwrite_ci32_pixels( const GLcontext *ctx,
208 GLuint n, const GLint x[], const GLint y[],
209 const GLuint ci[], const GLubyte mask[] )
210 {
211 while (n--) {
212 if (*mask++) ggiPutPixel(VIS,*x, FLIP(*y),*ci);
213 ci++;
214 x++;
215 y++;
216 }
217 }
218
219 void GGIwrite_mono_pixels( const GLcontext *ctx,
220 GLuint n,
221 const GLint x[], const GLint y[],
222 const GLubyte mask[] )
223 {
224 while (n--) {
225 if (*mask++) ggiDrawPixel(VIS,*x,FLIP(*y));
226 x++;
227 y++;
228 }
229 }
230
231 void GGIwrite_rgba_pixels( const GLcontext *ctx,
232 GLuint n, const GLint x[], const GLint y[],
233 const GLubyte rgba[][4],
234 const GLubyte mask[] )
235 {
236 ggi_pixel col;
237 ggi_color rgb;
238 while (n--) {
239 if (*mask++) {
240 rgb.r=(uint16)(rgba[0][RCOMP]) << SHIFT;
241 rgb.g=(uint16)(rgba[0][GCOMP]) << SHIFT;
242 rgb.b=(uint16)(rgba[0][BCOMP]) << SHIFT;
243 col=ggiMapColor(VIS,&rgb);
244 ggiPutPixel(VIS,*x,FLIP(*y),col);
245 }
246 x++;y++;
247 rgba++;
248 }
249 }
250
251
252 /**********************************************************************/
253 /***** Read arrays of pixels *****/
254 /**********************************************************************/
255
256 void GGIread_ci32_pixels( const GLcontext *ctx,
257 GLuint n, const GLint x[], const GLint y[],
258 GLuint ci[], const GLubyte mask[])
259 {
260 while (n--) {
261 if (*mask++)
262 ggiGetPixel(VIS, *x, FLIP(*y) ,ci);
263 ci++;
264 x++;
265 y++;
266 }
267 }
268
269 void GGIread_rgba_pixels( const GLcontext *ctx,
270 GLuint n, const GLint x[], const GLint y[],
271 GLubyte rgba[][4],
272 const GLubyte mask[] )
273 {
274 ggi_color rgb;
275 ggi_pixel col;
276
277 while (n--)
278 {
279 if (*mask++)
280 {
281 ggiGetPixel(VIS,*x,FLIP(*y),&col);
282 ggiUnmapPixel(VIS,col,&rgb);
283 rgba[0][RCOMP]= rgb.r >> SHIFT;
284 rgba[0][GCOMP]= rgb.g >> SHIFT;
285 rgba[0][BCOMP]= rgb.b >> SHIFT;
286 rgba[0][ACOMP]=0;
287 }
288 x++; y++;
289 rgba++;
290 }
291 }
292
293
294 triangle_func ggiGetTriangleFunc(GLcontext *ctx);
295
296 int GGIsetup_driver(GGIMesaContext ggictx,struct ggi_mesa_info *info)
297 {
298 GLcontext *ctx=ggictx->gl_ctx;
299
300 ctx->Driver.WriteRGBASpan = GGIwrite_rgba_span;
301 ctx->Driver.WriteRGBSpan = GGIwrite_rgb_span;
302 ctx->Driver.WriteMonoRGBASpan = GGIwrite_mono_span;
303 ctx->Driver.WriteRGBAPixels = GGIwrite_rgba_pixels;
304 ctx->Driver.WriteMonoRGBAPixels = GGIwrite_mono_pixels;
305
306 ctx->Driver.WriteCI32Span = GGIwrite_ci32_span;
307 ctx->Driver.WriteCI8Span = GGIwrite_ci8_span;
308 ctx->Driver.WriteMonoCISpan = GGIwrite_mono_span;
309 ctx->Driver.WriteCI32Pixels = GGIwrite_ci32_pixels;
310 ctx->Driver.WriteMonoCIPixels = GGIwrite_mono_pixels;
311
312 ctx->Driver.ReadCI32Span = GGIread_ci32_span;
313 ctx->Driver.ReadRGBASpan = GGIread_rgba_span;
314 ctx->Driver.ReadCI32Pixels = GGIread_ci32_pixels;
315 ctx->Driver.ReadRGBAPixels = GGIread_rgba_pixels;
316
317 return 0;
318 }
319
320 void GGIupdate_state(GLcontext *ctx)
321 {
322 ctx->Driver.TriangleFunc = ggiGetTriangleFunc(ctx);
323 }
324
325
326 void GGItriangle_flat(GLcontext *ctx,GLuint v0,GLuint v1,GLuint v2,GLuint pv)
327 {
328 //#define INTERP_Z 1
329 //#define INTERP_RGB 1
330 //#define INTERP_ALPHA 1
331
332 #define SETUP_CODE \
333 GLubyte r = VB->ColorPtr->data[pv][0]; \
334 GLubyte g = VB->ColorPtr->data[pv][1]; \
335 GLubyte b = VB->ColorPtr->data[pv][2]; \
336 GLubyte a = VB->ColorPtr->data[pv][3]; \
337 (*ctx->Driver.Color)(ctx,r,g,b,a);
338
339 #define INNER_LOOP(LEFT,RIGHT,Y) \
340 ggiDrawHLine(VIS,LEFT,FLIP(Y),RIGHT-LEFT);
341
342 #include "tritemp.h"
343 }
344
345
346 void GGItriangle_flat_depth(GLcontext *ctx, GLuint v0, GLuint v1, GLuint v2, GLuint pv)
347 {
348 #define INTERP_Z 1
349 #define DEPTH_TYPE DEFAULT_SOFTWARE_DEPTH_TYPE
350
351 #define SETUP_CODE \
352 GLubyte r = VB->ColorPtr->data[pv][0]; \
353 GLubyte g = VB->ColorPtr->data[pv][1]; \
354 GLubyte b = VB->ColorPtr->data[pv][2]; \
355 GLubyte a = VB->ColorPtr->data[pv][3]; \
356 (*ctx->Driver.Color)(ctx,r,g,b,a);
357
358 #define INNER_LOOP(LEFT,RIGHT,Y) \
359 { \
360 GLint i,xx=LEFT,yy=FLIP(Y),n=RIGHT-LEFT,length=0; \
361 GLint startx=xx; \
362 for (i=0;i<n;i++){ \
363 GLdepth z=FixedToDepth(ffz); \
364 if (z<zRow[i]) \
365 { \
366 zRow[i]=z; \
367 length++; \
368 } \
369 else \
370 { \
371 if (length) \
372 { \
373 ggiDrawHLine(VIS,startx,yy,length); \
374 length=0; \
375 } \
376 startx=xx+i+1; \
377 } \
378 ffz+=fdzdx; \
379 } \
380 if (length) ggiDrawHLine(VIS,startx,yy,length); \
381 }
382
383 #include "tritemp.h"
384 }
385
386
387 triangle_func ggiGetTriangleFunc(GLcontext *ctx)
388 {
389 if (ctx->Stencil.Enabled) return NULL;
390 if (ctx->Polygon.SmoothFlag) return NULL;
391 if (ctx->Polygon.StippleFlag) return NULL;
392 if (ctx->Texture.Enabled) return NULL;
393 if (ctx->Light.ShadeModel==GL_SMOOTH) return NULL;
394 if (ctx->Depth.Test && ctx->Depth.Func != GL_LESS) return NULL;
395
396 if (ctx->Depth.Test)
397 return GGItriangle_flat_depth;
398
399 return GGItriangle_flat;
400 }
401
402 int GGIdlinit(ggi_visual_t vis, const char *version, void *argptr)
403 {
404 LIBGGI_MESAEXT(vis)->update_state = GGIupdate_state;
405 LIBGGI_MESAEXT(vis)->setup_driver = GGIsetup_driver;
406
407 return 0;
408 }
409
410 int GGIdlcleanup(ggi_visual_t vis)
411 {
412 return 0;
413 }