Fill method like MsPaint almost working correctly

aewarnick

Well-known member
Joined
Jan 29, 2003
Messages
1,031
C#:
public static void FillArea(Bitmap editBitmap, int x, int y, Color replThisColor, Color withThisColor)
			{
				if(editBitmap.GetPixel(x,y)==replThisColor)
				{
					editBitmap.SetPixel(x,y, withThisColor);

					int l= x-1;
					int r= x+1;
					int u= y-1;
					int d= y+1;

					if(r < editBitmap.Width)
					{
						if(editBitmap.GetPixel(r, y)==replThisColor) FillArea(editBitmap, r, y, replThisColor, withThisColor);
					}
					if(d < editBitmap.Height)
					{
						if(editBitmap.GetPixel(x, d)==replThisColor) FillArea(editBitmap, x, d, replThisColor, withThisColor);
					}
					if(l > -1)
					{
						if(editBitmap.GetPixel(l, y)==replThisColor) FillArea(editBitmap, l, y, replThisColor, withThisColor);
					}
					/*if(u > -1)
					{
						if(editBitmap.GetPixel(x, u)==replThisColor) FillArea(editBitmap, x, u, replThisColor, withThisColor);
					}*/
				}
I always get a stack overflow right away if I have all 4 directions running. Is there a better way to do this?
 
Your code will keep hitting the same pixels over and over. You could try passing something like a "direction" to your function so that you know which way you were coming from. Using that direction you would NO check the IF for pixels in that direction.

For example, say you had a 3x3 grid. The first pixel is in the upper left. Say your second pixel is to the right, so you call your function again. When checking the pixels around this second pixel (top middle pixel in the 3x3) you dont want to go back and do anything with the top left pixel since youve already visited it. By using a direction you can avoid that.

Thats the easiest change, using your existing code. A better solution involves more work as you would create a structure to know which pixels youd already hit. With my solution (just using a direction), youll still revisit pixels but not indefinately.

Isnt there some kind of FloodFill function built into GDI or GDI+? I dont know...

-Nerseus
 
It looks like he left something out- using the points he added...

I didnt notice the first time divil, that you did not write a + after GDI. It is an api call. Ill just stick with my own.
 
Last edited by a moderator:
Now it is even worse. I dont even get an error, the program just quits!
Are you suggesting using an array list and looping through each element(point structure) to see if I did that one already?
C#:
public static void FloodFill(Bitmap editBitmap, int x, int y, Color replThisColor, Color withThisColor, char direction)
			{
				if(editBitmap.GetPixel(x,y)==replThisColor)
				{
					editBitmap.SetPixel(x,y, withThisColor);

					int l= x-1;
					int r= x+1;
					int u= y-1;
					int d= y+1;

					if(direction != R)
					{
						if(r < editBitmap.Width)
						{
							if(editBitmap.GetPixel(r, y)==replThisColor) FloodFill(editBitmap, r, y, replThisColor, withThisColor, L);
						}
					}
					if(direction != D)
					{
						if(d < editBitmap.Height)
						{
							if(editBitmap.GetPixel(x, d)==replThisColor) FloodFill(editBitmap, x, d, replThisColor, withThisColor, U);
						}
					}
					if(direction != L)
					{
						if(l > -1)
						{
							if(editBitmap.GetPixel(l, y)==replThisColor) FloodFill(editBitmap, l, y, replThisColor, withThisColor, R);
						}
					}
					if(direction != U)
					{
						if(u > -1)
						{
							if(editBitmap.GetPixel(x, u)==replThisColor) FloodFill(editBitmap, x, u, replThisColor, withThisColor, D);
						}
					}
							
				}
			}
 
I thought this was an interesting problem and searched for a way to solve it - first I ran into the same problems mentioned above (stack overflow/app exiting without throwing any exception etc...) but then I remembered my Math lessons - Pythagoras!!

one of his most famous discoverys says that the sides of a rectangular triangle always have the relationship (a*a) + (b*b) = (c*c) where a and b have a 90
 
Back
Top