Jump to content
  • Advertisement
Sign in to follow this  
Alrecenk

Buggy Triangle Filling

This topic is 4848 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

This is your basic Z-buffering scanline triangle filler. It is written in java and draws into a 1D array where a position in the array is x + y*width. It works with most triangles, but sometimes it doesn't fill in the whole triangle and sometimes it fills way out to the right of the triangle. I would really appreciate it if someone could tell me what is wrong. Thanks in advance. Here's the code:


//fills a triangle with one color
public final void flatshade(double pts[][],short g[],final int gwidth, final short color, final short z){
  	
  	
  	//sorts points from top to bottom
  if(pts[2][1]<pts[1][1]){
	  		temp=pts[2] ;
	  		pts[2]=pts[1] ;
	  		pts[1]=temp ;
	  		
	  }
	  if(pts[1][1]<pts[0][1]){
	  		temp=pts[0] ;
	  		pts[0]=pts[1] ;
	  		pts[1]=temp ;
	  		
	  }	
	  
if(pts[2][1]<pts[1][1]){
	  		temp=pts[2] ;
	  		pts[2]=pts[1] ;
	  		pts[1]=temp ;
	  }
	  
  	
  	
  y = gwidth*(int)(pts[0][1]) ;
  ye = gwidth*(int)(pts[1][1]) ;

//fixes error when triangle has a flat top
if(y==ye){
	pts[0][1]-- ; 
	y = gwidth*(int)(pts[0][1]) ; }
  
  //sets X change per y for both lines
  xs1= (pts[0][0]-pts[1][0])/(pts[0][1]-pts[1][1]) ;
  xs2= (pts[0][0]-pts[2][0])/(pts[0][1]-pts[2][1]) ;
  
  //makes sure xs1 is to the left of xs2 for scanline drawing
  reverse = xs1>xs2 ;
  
  if(reverse){
  	x1 = xs1 ;
  	xs1=xs2 ;
  	xs2=x1;	
  }
  
  x1 = pts[0][0] ;
  x2 = pts[0][0] ;
  
  while(y<ye){
  	
  	//if inside screen checks removed for speed
  	//this is not the problem
  x = y+(int)x1 ; 
  xe = y+(int)x2 ; 
  
  //scanlines
 while(x<=xe){
 	if(Zbuffer[x]>z){//uses Z buffer
 	Zbuffer[x]=z ;	
  	g[x] =  color ;
  	}
  	x++; }
  	
  
  
  x1+=xs1 ;
  x2+=xs2 ;
  y+=gwidth;
}

//checks if reversed and sets slope(x per y) for last line
if(reverse){
xs2 = (pts[2][0]-pts[1][0])/(pts[2][1]-pts[1][1]) ;	
}else{
xs1 = (pts[2][0]-pts[1][0])/(pts[2][1]-pts[1][1]) ;
}
y = gwidth*(int)(pts[1][1]) ;
ye = gwidth*(int)(pts[2][1]) ;



//same as above except with bottom of triangle
while(y<ye){
	
  
  x = y+(int)x1 ;
  xe = y+(int)x2 ; 
  
 while(x<=xe){
  	if(Zbuffer[x]>z){
 	Zbuffer[x]=z ;	
  	g[x] =  color ;
  	}
  	x++; }
  	
  
  
  x1+=xs1 ;
  x2+=xs2 ;
  y+=gwidth;
}
  
}



Share this post


Link to post
Share on other sites
Advertisement
hm your code seems pretty complex

on thing that just came to my mind while reading your code

you could project the edges of the triangle into your 2d plane
now draw your lines into a boolean map and calculate the 2d boundary of your triangle

then start to fill the triangle from left to right line for line until you reach a boolean in your boolean map that is true set the boolean to false
and proceed with the next line until you have done this for each of line within the 2d boundary for horizontal lines you just look ahead if the next pixel is true again

i don t know how expensive this would be but i think you get rid of a lot of comparsions only equality of the boolean map has to be tested

you could farther improve this by using 32 bit integers (4 pixels in a row) instead of bytes

Share this post


Link to post
Share on other sites
That sound like it could be pretty expensive. The scanlines would be faster, but converting into and out of the boolean map would add a lot of overhead. I think my idea is solid, it is just my code is flawed somehow.....

Share this post


Link to post
Share on other sites
i would test it that aren t more than 30 to 40 lines of code
and you can do this with any polygon even concave ones and you don t need to do a check whether the triangle is on the screen you have got the boundary if its parially inside the screen you only update the pixels inside the boundary

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!