gba-x3dtest

diff src/polyfill.c @ 17:0a7f402892b3

texture mapping
author John Tsiombikas <nuclear@member.fsf.org>
date Thu, 26 Jun 2014 06:57:51 +0300
parents b755fb002f17
children 62390f9cc93e
line diff
     1.1 --- a/src/polyfill.c	Wed Jun 25 18:18:05 2014 +0300
     1.2 +++ b/src/polyfill.c	Thu Jun 26 06:57:51 2014 +0300
     1.3 @@ -13,10 +13,11 @@
     1.4  static void fill_scanline_pal(int y, int32_t x0, int32_t x1, int32_t u0, int32_t u1,
     1.5  		int32_t v0, int32_t v1, uint8_t color);
     1.6  static void fill_scanline_rgb(int y, int32_t x0, int32_t x1, int32_t u0, int32_t u1,
     1.7 -		int32_t v0, int32_t v1, uint16_t color);
     1.8 +		int32_t v0, int32_t v1, uint16_t color, struct texture *tex);
     1.9  static int winding(int32_t x0, int32_t y0, int32_t x1, int32_t y1);
    1.10  
    1.11 -void draw_poly(int num, const pvec3 *verts, const pvec2 *tex, uint16_t color)
    1.12 +void draw_poly(int num, const pvec3 *verts, const pvec2 *texcoords, uint16_t color,
    1.13 +		struct texture *tex)
    1.14  {
    1.15  	int i, topidx = 0, botidx = 0;
    1.16  	int lidx[2] = {-1, -1}, ridx[2] = {-1, -1};
    1.17 @@ -69,10 +70,10 @@
    1.18  	}
    1.19  	lx = verts[lidx[0]].x;
    1.20  	ldxdy = x16div(verts[lidx[1]].x - lx, ldy);
    1.21 -	lu = tex[lidx[0]].x;
    1.22 -	ldudy = x16div(tex[lidx[1]].x - lu, ldy);
    1.23 -	lv = tex[lidx[0]].y;
    1.24 -	ldvdy = x16div(tex[lidx[1]].y - lv, ldy);
    1.25 +	lu = texcoords[lidx[0]].x;
    1.26 +	ldudy = x16div(texcoords[lidx[1]].x - lu, ldy);
    1.27 +	lv = texcoords[lidx[0]].y;
    1.28 +	ldvdy = x16div(texcoords[lidx[1]].y - lv, ldy);
    1.29  
    1.30  	/* find starting right edge */
    1.31  	ridx[1] = VNEXT(ridx[0], num);
    1.32 @@ -90,10 +91,10 @@
    1.33  	}
    1.34  	rx = verts[ridx[0]].x;
    1.35  	rdxdy = x16div(verts[ridx[1]].x - rx, rdy);
    1.36 -	ru = tex[ridx[0]].x;
    1.37 -	rdudy = x16div(tex[ridx[1]].x - ru, rdy);
    1.38 -	rv = tex[ridx[0]].y;
    1.39 -	rdvdy = x16div(tex[ridx[1]].y - rv, rdy);
    1.40 +	ru = texcoords[ridx[0]].x;
    1.41 +	rdudy = x16div(texcoords[ridx[1]].x - ru, rdy);
    1.42 +	rv = texcoords[ridx[0]].y;
    1.43 +	rdvdy = x16div(texcoords[ridx[1]].y - rv, rdy);
    1.44  
    1.45  	start = topy >> 16;
    1.46  	end = boty >> 16;
    1.47 @@ -112,17 +113,17 @@
    1.48  				break;
    1.49  			}
    1.50  
    1.51 -			lu = tex[lidx[0]].x;
    1.52 -			lv = tex[lidx[0]].y;
    1.53 +			lu = texcoords[lidx[0]].x;
    1.54 +			lv = texcoords[lidx[0]].y;
    1.55  
    1.56  			if(ldy) {
    1.57  				ldxdy = x16div(verts[lidx[1]].x - lx, ldy);
    1.58 -				ldudy = x16div(tex[lidx[1]].x - lu, ldy);
    1.59 -				ldvdy = x16div(tex[lidx[1]].y - lv, ldy);
    1.60 +				ldudy = x16div(texcoords[lidx[1]].x - lu, ldy);
    1.61 +				ldvdy = x16div(texcoords[lidx[1]].y - lv, ldy);
    1.62  			} else {
    1.63  				ldxdy = verts[lidx[1]].x - lx;
    1.64 -				ldudy = tex[lidx[1]].x - lu;
    1.65 -				ldvdy = tex[lidx[1]].y - lv;
    1.66 +				ldudy = texcoords[lidx[1]].x - lu;
    1.67 +				ldvdy = texcoords[lidx[1]].y - lv;
    1.68  			}
    1.69  		}
    1.70  		if(y >= verts[ridx[1]].y) {
    1.71 @@ -134,17 +135,17 @@
    1.72  				break;
    1.73  			}
    1.74  
    1.75 -			ru = tex[ridx[0]].x;
    1.76 -			rv = tex[ridx[0]].y;
    1.77 +			ru = texcoords[ridx[0]].x;
    1.78 +			rv = texcoords[ridx[0]].y;
    1.79  
    1.80  			if(rdy) {
    1.81  				rdxdy = x16div(verts[ridx[1]].x - rx, rdy);
    1.82 -				rdudy = x16div(tex[ridx[1]].x - ru, rdy);
    1.83 -				rdvdy = x16div(tex[ridx[1]].y - rv, rdy);
    1.84 +				rdudy = x16div(texcoords[ridx[1]].x - ru, rdy);
    1.85 +				rdvdy = x16div(texcoords[ridx[1]].y - rv, rdy);
    1.86  			} else {
    1.87  				rdxdy = verts[ridx[1]].x - rx;
    1.88 -				rdudy = tex[ridx[1]].x - ru;
    1.89 -				rdvdy = tex[ridx[1]].y - rv;
    1.90 +				rdudy = texcoords[ridx[1]].x - ru;
    1.91 +				rdvdy = texcoords[ridx[1]].y - rv;
    1.92  			}
    1.93  		}
    1.94  
    1.95 @@ -152,7 +153,7 @@
    1.96  #ifdef PALMODE
    1.97  			fill_scanline_pal(i, lx, rx, lu, ru, lv, rv, (uint8_t)color);
    1.98  #else
    1.99 -			fill_scanline_rgb(i, lx, rx, lu, ru, lv, rv, color);
   1.100 +			fill_scanline_rgb(i, lx, rx, lu, ru, lv, rv, color, tex);
   1.101  #endif
   1.102  		}
   1.103  
   1.104 @@ -229,7 +230,7 @@
   1.105  }
   1.106  
   1.107  static void fill_scanline_rgb(int y, int32_t x0, int32_t x1, int32_t u0, int32_t u1,
   1.108 -		int32_t v0, int32_t v1, uint16_t color)
   1.109 +		int32_t v0, int32_t v1, uint16_t color, struct texture *tex)
   1.110  {
   1.111  	int i, ix0, ix1;
   1.112  	uint16_t *pixels;
   1.113 @@ -268,7 +269,14 @@
   1.114  		if(cr > 255) cr = 255;
   1.115  		if(cg > 255) cg = 255;
   1.116  
   1.117 -		*pixels++ = RGB(cr, cg, 0);
   1.118 +		if(tex) {
   1.119 +			int tx = (u >> (16 - tex->ushift)) & tex->umask;
   1.120 +			int ty = (v >> (16 - tex->vshift)) & tex->vmask;
   1.121 +			uint16_t texel = ((uint16_t*)tex->pixels)[ty * tex->xsz + tx];
   1.122 +			*pixels++ = texel;
   1.123 +		} else {
   1.124 +			*pixels++ = color;
   1.125 +		}
   1.126  
   1.127  		u += dudx;
   1.128  		v += dvdx;