1 /*
2 
3 Copyright (C) 2015-2018 Night Dive Studios, LLC.
4 
5 This program is free software: you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation, either version 3 of the License, or
8 (at your option) any later version.
9 
10 This program 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
13 GNU General Public License for more details.
14 
15 You should have received a copy of the GNU General Public License
16 along with this program.  If not, see <http://www.gnu.org/licenses/>.
17 
18 */
19 /*
20  * $Source: r:/prj/lib/src/2d/RCS/fl8sply.c $
21  * $Revision: 1.1 $
22  * $Author: kevin $
23  * $Date: 1994/08/16 13:11:44 $
24  *
25  * Routines for drawing flat shaded polygons onto a flat 8 canvas.
26  *
27  * This file is part of the 2d library.
28  */
29 
30 #include "cnvdat.h"
31 #include "gente.h"
32 #include "poly.h"
33 #include "tlucdat.h"
34 #include "tmapint.h"
35 
36 // prototypes
37 int gri_spoly_loop(grs_tmap_loop_info *ti);
38 void gri_spoly_init(grs_tmap_loop_info *ti);
39 void gri_clut_spoly_init(grs_tmap_loop_info *ti);
40 void gri_stpoly_init(grs_tmap_loop_info *ti);
41 void gri_clut_stpoly_init(grs_tmap_loop_info *ti);
42 
gri_spoly_loop(grs_tmap_loop_info * ti)43 int gri_spoly_loop(grs_tmap_loop_info *ti) {
44     int d;
45     fix i, di;
46     fix xl, xr;
47     uchar *ti_d;
48     fix ti_li, ti_ri;
49 
50     xl = ti->left.x;
51     xr = ti->right.x;
52     ti_li = ti->left.i;
53     ti_ri = ti->right.i;
54     ti_d = ti->d;
55 
56     do {
57         i = ti_li;
58         di = fix_div(ti_ri - i, xr - xl);
59         i += fix_mul(fix_ceil(xl) - xl, di);
60 
61         if ((d = fix_cint(xr) - fix_cint(xl)) > 0) {
62             switch (ti->bm.hlog) {
63                 int x;
64             case GRL_OPAQUE:
65                 for (x = fix_cint(xl); x < fix_cint(xr); x++) {
66                     ti_d[x] = fix_fint(i);
67                     i += di;
68                 }
69                 break;
70             case GRL_CLUT:
71                 for (x = fix_cint(xl); x < fix_cint(xr); x++) {
72                     ti_d[x] = ti->clut[fix_fint(i)];
73                     i += di;
74                 }
75                 break;
76             case GRL_TLUC8:
77                 for (x = fix_cint(xl); x < fix_cint(xr); x++) {
78                     ti_d[x] = tluc8stab[fix_light(i) + ti_d[x]];
79                     i += di;
80                 }
81                 break;
82             case GRL_CLUT | GRL_TLUC8:
83                 for (x = fix_cint(xl); x < fix_cint(xr); x++) {
84                     ti_d[x] = ti->clut[tluc8stab[fix_light(i) + ti_d[x]]];
85                     i += di;
86                 }
87                 break;
88             }
89         } else if (d < 0) {
90             return TRUE;
91         }
92         /* update span extrema and destination. */
93         ti_d += grd_bm.row;
94         xl += ti->left.dx;
95         xr += ti->right.dx;
96         ti_li += ti->left.di;
97         ti_ri += ti->right.di;
98     } while ((--(ti->n)) > 0);
99 
100     ti->d = ti_d;
101     ti->left.x = xl;
102     ti->right.x = xr;
103     ti->left.i = ti_li;
104     ti->right.i = ti_ri;
105 
106     return FALSE;
107 }
108 
gri_spoly_init(grs_tmap_loop_info * ti)109 void gri_spoly_init(grs_tmap_loop_info *ti) {
110     ti->bm.hlog = GRL_OPAQUE;
111     ti->d = ti->y * grd_bm.row + grd_bm.bits;
112     ti->loop_func = (void (*)())gri_spoly_loop;
113     ti->top_edge_func = (void (*)())gri_ix_edge;
114     ti->bot_edge_func = (void (*)())gri_ix_edge;
115 }
116 
gri_clut_spoly_init(grs_tmap_loop_info * ti)117 void gri_clut_spoly_init(grs_tmap_loop_info *ti) {
118     ti->bm.hlog = GRL_CLUT;
119     ti->d = ti->y * grd_bm.row + grd_bm.bits;
120     ti->loop_func = (void (*)())gri_spoly_loop;
121     ti->top_edge_func = (void (*)())gri_ix_edge;
122     ti->bot_edge_func = (void (*)())gri_ix_edge;
123 }
124 
gri_stpoly_init(grs_tmap_loop_info * ti)125 void gri_stpoly_init(grs_tmap_loop_info *ti) {
126     if (tluc8stab != NULL)
127         ti->bm.hlog = GRL_TLUC8;
128     else
129         ti->bm.hlog = GRL_OPAQUE;
130     ti->d = ti->y * grd_bm.row + grd_bm.bits;
131     ti->loop_func = (void (*)())gri_spoly_loop;
132     ti->top_edge_func = (void (*)())gri_ix_edge;
133     ti->bot_edge_func = (void (*)())gri_ix_edge;
134 }
135 
gri_clut_stpoly_init(grs_tmap_loop_info * ti)136 void gri_clut_stpoly_init(grs_tmap_loop_info *ti) {
137     if (tluc8stab != NULL)
138         ti->bm.hlog = GRL_CLUT | GRL_TLUC8;
139     else
140         ti->bm.hlog = GRL_CLUT;
141     ti->d = ti->y * grd_bm.row + grd_bm.bits;
142     ti->loop_func = (void (*)())gri_spoly_loop;
143     ti->top_edge_func = (void (*)())gri_ix_edge;
144     ti->bot_edge_func = (void (*)())gri_ix_edge;
145 }
146