View Javadoc

1   package com.insanityengine.ghia.renderer;
2   
3   import java.awt.*;
4   import java.awt.image.*;
5   import java.awt.event.*;
6   import java.applet.*;
7   
8   import com.insanityengine.ghia.m3.*;
9   import com.insanityengine.ghia.libograf.*;
10  import com.insanityengine.ghia.pixels.*;
11  
12  /***
13   *
14   * <P>
15   * </P>
16   *
17   * @author BrianHammond
18   *
19   * $Header: /usr/local/cvsroot/ghia/src/java/com/insanityengine/ghia/renderer/Scantron.java,v 1.1 2005/03/25 02:45:25 brian Exp $
20   *
21   */
22  public class Scantron {
23  
24  	/*** 
25  	 * 
26  	 * Constructor
27  	 * 
28  	 */
29  	public Scantron() {
30  	}
31  
32  	/*** 
33  	 * 
34  	 * Constructor
35  	 * 
36  	 */
37  	public Scantron( int width, int height ) {
38  		init( width, height );
39  	}
40  	
41  	/*** 
42  	 * 
43  	 * isReady
44  	 * 
45  	 * @return a boolean
46  	 * 
47  	 */
48  	public final boolean isReady() {
49  		return ( null != lx );
50  	}
51  
52  	/*** 
53  	 * 
54  	 * init
55  	 * 
56  	 * @param height
57  	 * 
58  	 */
59  	public final void init( int width, int height ) {
60  		this.w = width;
61  		this.h = height;
62  
63  		lx	= new float[ h ];
64  		lz	= new float[ h ];
65  		ltx	= new float[ h ];
66  		lty	= new float[ h ];
67  		rx	= new float[ h ];
68  		rz	= new float[ h ];
69  		rtx	= new float[ h ];
70  		rty	= new float[ h ];
71  		used = new boolean[ h ];
72  	}
73  
74  	/*** 
75  	 * 
76  	 * hasCandy
77  	 * 
78  	 * @param i
79  	 * 
80  	 * @return a boolean
81  	 * 
82  	 */
83  	public final boolean hasCandy( int i ) {
84  		return ( used[ i ] );
85  	}
86  
87  	/*** 
88  	 * 
89  	 * getDistance
90  	 * 
91  	 * @param i
92  	 * 
93  	 * @return a float
94  	 * 
95  	 */
96  	public final float getDistance( int i ) {
97  		return 1 + rx[ i ] - lx[ i ];
98  	}
99  
100 	public final float getLx( int i ) {   return lx[ i ]; }
101 	public final float getLz( int i ) {   return lz[ i ]; }
102 	public final float getLtx( int i ) {  return ltx[ i ]; }
103 	public final float getLty( int i ) {  return lty[ i ]; }
104 	
105 	public final float getRx( int i ) {   return rx[ i ]; }
106 	public final float getRz( int i ) {   return rz[ i ]; }
107 	public final float getRtx( int i ) {  return rtx[ i ]; }
108 	public final float getRty( int i ) {  return rty[ i ]; }
109 
110 	/*** 
111 	 * 
112 	 * reset
113 	 * 
114 	 */
115 	public final void reset() {
116 		int cleared = 1;
117 		rx[ 0 ] = -M3_Constants.bigNumber;
118 		lx[ 0 ] = +M3_Constants.bigNumber;
119 		used[ 0 ] = false;
120 
121 		// use speedy array copy trick:
122 		for ( cleared = 1 ; cleared < h / 2 ; cleared *= 2 ) {
123 			System.arraycopy( rx, 0, rx, cleared, cleared );
124 			System.arraycopy( lx, 0, lx, cleared, cleared );
125 			System.arraycopy( used, 0, used, cleared, cleared );
126 		}
127 		
128 		// clear any remaining elements
129 		System.arraycopy( rx, 0, rx, cleared, h - cleared );
130 		System.arraycopy( lx, 0, lx, cleared, h - cleared );
131 		System.arraycopy( used, 0, used, cleared, h - cleared );
132 	}
133 	
134 	/*** 
135 	 * 
136 	 * setL
137 	 * 
138 	 * @param i
139 	 * @param x
140 	 * @param z
141 	 * @param tx
142 	 * @param ty
143 	 * 
144 	 */
145 	public final void setL( int i, float _x, float _z, float _tx, float _ty ) {
146 		if ( _x < lx[ i ] ) {
147 			used[ i ] = true;
148 			lx[ i ] = _x; 
149 			lz[ i ] = _z; 
150 			ltx[ i ] = _tx; 
151 			lty[ i ] = _ty;
152 		}
153 	}
154 	
155 	/*** 
156 	 * 
157 	 * setR
158 	 * 
159 	 * @param i
160 	 * @param x
161 	 * @param z
162 	 * @param tx
163 	 * @param ty
164 	 * 
165 	 */
166 	public final void setR( int i, float _x, float _z, float _tx, float _ty ) {
167 		if ( _x < rx[ i ] ) {
168 			used[ i ] = true;
169 			rx[ i ] = _x; 
170 			rz[ i ] = _z; 
171 			rtx[ i ] = _tx; 
172 			rty[ i ] = _ty;
173 		}
174 	}
175 
176 	/*** 
177 	 * 
178 	 * set
179 	 * 
180 	 * @param i
181 	 * @param x
182 	 * @param z
183 	 * @param tx
184 	 * @param ty
185 	 * 
186 	 */
187 	public final void set( int i, float _x, float _z, float _tx, float _ty ) {
188 		if ( _x < lx[ i ] ) {
189 			used[ i ] = true;
190 			lx[ i ] = _x; 
191 			lz[ i ] = _z; 
192 			ltx[ i ] = _tx; 
193 			lty[ i ] = _ty;
194 		}
195 		if ( _x > rx[ i ] ) {
196 			used[ i ] = true;
197 			rx[ i ] = _x; 
198 			rz[ i ] = _z; 
199 			rtx[ i ] = _tx; 
200 			rty[ i ] = _ty;
201 		}
202 	}
203 
204 	/*** 
205 	 * 
206 	 * set
207 	 * 
208 	 */
209 	public final void set( 
210 		int i,
211 		float _lx, float _lz, float _ltx, float _lty,
212 		float _rx, float _rz, float _rtx, float _rty
213 	) {
214 		if ( _lx < lx[ i ] ) {
215 			used[ i ] = true;
216 			lx[ i ] = _lx; 
217 			lz[ i ] = _lz; 
218 			ltx[ i ] = _ltx; 
219 			lty[ i ] = _lty;
220 		}
221 		if ( _rx > rx[ i ] ) {
222 			used[ i ] = true;
223 			rx[ i ] = _rx; 
224 			rz[ i ] = _rz; 
225 			rtx[ i ] = _rtx; 
226 			rty[ i ] = _rty;
227 		}
228 	}
229 
230 	/*** 
231 	 * 
232 	 * scanPolyEdge
233 	 * 
234 	 * @param p0in
235 	 * @param p1in
236 	 * 
237 	 */
238 	public final void scanPolyEdge( Pt3 p0_in, Pt3 p1_in ) {
239 		if ( p0_in.y == p1_in.y ) {
240 			horizonalLine( p0_in, p1_in );
241 		} else {
242 			reallyScan( p0_in, p1_in );
243 		}
244 	}
245 
246 	////
247 
248 	private int w, h;
249 
250 	private float lx[], lz[], ltx[], lty[];
251 	private float rx[], rz[], rtx[], rty[];
252 
253 	private boolean used[];
254 
255 	/*** 
256 	 * 
257 	 * horizonalLine
258 	 * 
259 	 * @param p0in
260 	 * @param p1in
261 	 * 
262 	 */
263 	private final void horizonalLine( Pt3 p0_in, Pt3 p1_in ) {
264 		if ( p0_in.y >= 0 && p0_in.y < h ) {
265 			setL( ( int ) p0_in.y, p0_in.x, p0_in.z, p0_in.s, p0_in.t );
266 			setR( ( int ) p1_in.y, p1_in.x, p1_in.z, p1_in.s, p1_in.t );
267 		}
268 	}
269 
270 	/*** 
271 	 * 
272 	 * reallyScan
273 	 * 
274 	 * @param p0in
275 	 * @param p1in
276 	 * 
277 	 */
278 	private final void reallyScan( Pt3 p0_in, Pt3 p1_in ) {
279 
280 		Pt3 p0 = p0_in;
281 		Pt3 p1 = p1_in;
282 
283 		x0 = ( int ) p0.x;
284 		y0 = ( int ) p0.y;
285 		
286 		x1 = ( int ) p1.x;
287 		y1 = ( int ) p1.y;
288 	
289 		diffx = ( x1 - x0 );
290 		diffy = ( y1 - y0 );
291 		
292 		adiffx = ( diffx < 0 ) ? -diffx : diffx;
293 		adiffy = ( diffy < 0 ) ? -diffy : diffy;
294 
295 		boolean recalc = false;
296 		boolean useX = true;
297 
298 		if ( adiffx < adiffy && 0 != diffx ) {
299 			useX = true;
300 			if ( diffx < 0 ) {
301 				recalc = true;
302 			}
303 		} else {
304 			useX = false;
305 			if ( diffy < 0 ) {
306 				recalc = true;
307 			}
308 		}		
309 
310 		if ( recalc ) {
311 			p1 = p0_in;
312 			p0 = p1_in;
313 		
314 			x0 = ( int ) p0.x;
315 			y0 = ( int ) p0.y;
316 			
317 			x1 = ( int ) p1.x;
318 			y1 = ( int ) p1.y;
319 		
320 			diffx = ( x1 - x0 );
321 			diffy = ( y1 - y0 );
322 		}
323 
324 		z = p0.z;
325 		dz = p1.z - z;
326 		tx = p0.s;
327 		ty = p0.t;
328 		
329 		if ( useX ) {
330 			
331 			zinc = dz / ( adiffy + adiffx );
332 			o_inc = diffy / ( float ) ( 1 + adiffx );
333 
334 			tx_inc = ( p1.s - p0.s ) / ( adiffx + adiffy );
335 			ty_inc = ( p1.t - p0.t ) / ( adiffx + adiffy );
336 		
337 			if ( diffy < 0 ) linc = -1;
338 			else linc = 1;
339 
340 			for ( x = x0, o = y0 ; x != x1 + 1  ; o += o_inc, x++ ) {
341 				
342 				next = ( int ) ( o + o_inc + linc );
343 				for ( j = ( int ) o ; j != next ; j += linc ) {
344 					if ( j > 0 && j < h ) {
345 						//scanner[ j ].set( x, z, tx, ty );
346 						set( j, x, z, tx, ty );
347 					}
348 					
349 					z += zinc;
350 					tx += tx_inc;
351 					ty += ty_inc;
352 				}
353 				
354 			}
355 			
356 		} else {
357 			
358 			zinc = dz / ( adiffy + 1 );
359 			o_inc = diffx / ( float ) ( 1 + adiffy );
360 			
361 			tx_inc = ( p1.s - p0.s ) / ( 1 + adiffy );
362 			ty_inc = ( p1.t - p0.t ) / ( 1 + adiffy );
363 		
364 			for ( y = y0, o = x0 ; y != y1 + 1 ; o += o_inc, y++ ) {
365 				
366 				if ( y > 0 && y < h ) {
367 					//scanner[ y ].set( 
368 					set( 
369 						y,
370 						o,         z,        tx, ty,
371 						o + o_inc, z + zinc, tx, ty
372 					);
373 				}
374 				
375 				z += zinc;
376 				tx += tx_inc;
377 				ty += ty_inc;
378 			}
379 		}
380 	}
381 	
382 	// pulled from scanPolyEdge
383 		int x0, y0;
384 		int x1, y1;
385 		int diffx, diffy;
386 		int adiffx, adiffy;
387 
388 		int x, y, j;
389 
390 		// for that tricky depth thang
391 		float zinc;
392 		float z;
393 		float dz;
394 
395 		// for boppin' 'round in x/y space
396 		float o, o_inc;
397 		int next, inc, linc;
398 
399 		// for movin' around in yucky ole texture space...
400 		float tx;
401 		float ty;
402 		float tx_inc, ty_inc;
403 
404 };
405 
406 /***
407  *
408  * $Log: Scantron.java,v $
409  * Revision 1.1  2005/03/25 02:45:25  brian
410  * split up a bit
411  *
412  *
413  */