Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations strongm on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

button

Status
Not open for further replies.

julianluthor

Programmer
Nov 3, 2003
18
MY
hi..
i have image edge detection function in button 2 and thinning function in button 3.how can i make so that my thinning function in button 3 can continue from button 2 (so it can thinning the edge image not the original image) without combine it in one button?below is my code..

Code:
void __fastcall TForm1::Button2Click(TObject *Sender) 
{ 
int n,m; 
long max,min; 
max = min = Data[0][0]; 

int DataWidth = Image1->Picture->Width; 
int DataHeight = Image1->Picture->Height; 

for (int y=0; y<DataHeight; y++) 
for (int x=0; x<DataWidth; x++) 
temp[y][x] = (Byte)Image1->Canvas->Pixels[x][y]; 

for (int j=0; j<400; j++) 
for (int i=0; i<400; i++) 
Data[i][j] = temp[i][j]; 

for(int j=0;j<400;j++) 
for(int i=0;i<400;i++) 

{ 

m=Data[j-1][i-1]+2*Data[j-1][i]+Data[j-1][i+1]-(Data[j+1][i-1]+2*Data[j+1][i]+Data[j+1][i+1]); 

n=Data[j-1][i+1]+2*Data[j][i+1]+Data[j+1][i+1]-(Data[j-1][i-1]+2*Data[j][i-1]+Data[j+1][i-1]); 

dataconv[j][i] = abs(m) + abs(n); 

if(dataconv[j][i]>max) 

max=dataconv[j][i]; 

if(dataconv[j][i]<min) 

min=dataconv[j][i]; 

} 
for(int j=0;j<400;j++) 
for(int i=0;i<400;i++) 

Data[i][j]=(unsigned char)(((float)dataconv[j][i]-min)/(max-min)*255); 

TStringList* papar = new TStringList; 

AnsiString str_line; 

for(int j=0; j<400; j++) 

{ 

str_line = &quot;&quot;; 

for(int i=0; i<400; i++) 

{ 

if(i) 

str_line += &quot;, &quot;; 

temp[i][j]= Data[i][j]; 

if (temp[i][j]>127) 

{ 

temp[i][j] = 0; 

} 

else 

{ 

temp[i][j] = 1; 

} 

str_line += IntToStr(temp[i][j]); 

} 

papar->Add(str_line); 

} 

papar->SaveToFile(&quot;EgdeDetection.dat&quot;); 

delete papar; 
} 
//--------------------------------------------------------------------------- 

void __fastcall TForm1::Button3Click(TObject *Sender) 
{ 
int count,count2,i,j,a,b; 
int num_transitions ; 
int num_transitions2 ; 
int temp_array[400][400]; 

int DataWidth = Image1->Picture->Width; 

int DataHeight = Image1->Picture->Height; 

for (int y=0; y<DataHeight; y++) 

for (int x=0; x<DataWidth; x++) 

Data[y][x] = (Byte)Image1->Canvas->Pixels[x][y]; 

TStringList* display = new TStringList; 

AnsiString str_line; 

for(j=0; j<400; j++) 

{ 

str_line = &quot;&quot;; 

for(i=0; i<400; i++) 

{ 

if(i) 

str_line += &quot; &quot;; 

Data[i][j]= (Byte)Image1->Canvas->Pixels[i][j]; 

if (Data[i][j]>127) 

{ 

Data[i][j] = 0; 

} 

else 

{ 

Data[i][j] = 1; 

} 

str_line += IntToStr(Data[i][j]); 

display->Add(str_line); 

count = 0; 

num_transitions = 0; 

// check for N(p) 

if (Data[i][j] == 1) 

{ 

if (Data[i-1][j-1] != 0) 

count++; 

if (Data[i][j-1] != 0) 

count++; 

if (Data[i+1][j-1] != 0) 

count++; 

if (Data[i+1][j] != 0) 

count++; 

if (Data[i-1][j] != 0) 

count++; 

if (Data[i+1][j+1] != 0) 

count++; 

if (Data[i][j+1] != 0) 

count++; 

if (Data[i-1][j+1] != 0) 

count++; 

if (count != 8) 

{ 

// 2 <= N(p) <= 6 

if (count >= 2 && count <= 6) 

{ 

if(Data[i-1][j] == 0 && 

Data[i-1][j+1] == 1) 

num_transitions++ ; 

if(Data[i-1][j+1] == 0 && 

Data[i][j+1] == 1) 

num_transitions++ ; 

if(Data[i][j+1] == 0 && 

Data[i+1][j+1] == 1) 

num_transitions++ ; 

if(Data[i+1][j+1] == 0 && 

Data[i+1][j] == 1) 

num_transitions++ ; 

if(Data[i+1][j] == 0 && 

Data[i+1][j-1] == 1) 

num_transitions++ ; 

if(Data[i+1][j-1] == 0 && 

Data[i][j-1] == 1) 

num_transitions++ ; 

if(Data[i][j-1] == 0 && 

Data[i-1][j-1] == 1) 

num_transitions++ ; 

if(Data[i-1][j-1] == 0 && 

Data[i-1][j] == 1) 

num_transitions++ ; 

//S(p) = 1 

if (num_transitions == 1) 

{ 

// if p2 * p4 * p6 = 0 

if (Data[i][j-1] == 0 || 

Data[i][j+1] == 0 || 

Data[i+1][j] == 0) 

{ 

// if p4 * p6 * p8 = 0 

if(Data[i][j+1] == 0 || 

Data[i+1][j] == 0 || 

Data[i][j-1] == 0) 

temp_array[i][j] = 0; 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] =0; 

}} 

//copy thinned image back to original 

for(j=0; j<400; j++) 

for(i=0; i<400; i++) 

Data[i][j]=temp_array[i][j]; 

for(j=0; j<400; j++) { 

for(i=0; i<400; i++) 

{ 

count2 = 0; 

num_transitions2 = 0; 

// check for N(p) 

if (Data[i][j] == 1) 

{ 

if (Data[i-1][j-1] != 0) 

count2++; 

if (Data[i][j-1] != 0) 

count2++; 

if (Data[i+1][j-1] != 0) 

count2++; 

if (Data[i+1][j] != 0) 

count2++; 

if (Data[i-1][j] != 0) 

count2++; 

if (Data[i+1][j+1] != 0) 

count2++; 

if (Data[i][j+1] != 0) 

count2++; 

if (Data[i-1][j+1] != 0) 

count2++; 

if (count2 != 8) 

{ 

// 2 <= N(p) <= 6 

if (count2 >= 2 && count2 <= 6) 

{ 

if(Data[i-1][j] == 0 && 

Data[i-1][j+1] == 1) 

num_transitions2++ ; 

if(Data[i-1][j+1] == 0 && 

Data[i][j+1] == 1) 

num_transitions2++ ; 

if(Data[i][j+1] == 0 && 

Data[i+1][j+1] == 1) 

num_transitions2++ ; 

if(Data[i+1][j+1] == 0 && 

Data[i+1][j] == 1) 

num_transitions2++ ; 

if(Data[i+1][j] == 0 && 

Data[i+1][j-1] == 1) 

num_transitions2++ ; 

if(Data[i+1][j-1] == 0 && 

Data[i][j-1] == 1) 

num_transitions2++ ; 

if(Data[i][j-1] == 0 && 

Data[i-1][j-1] == 1) 

num_transitions2++ ; 

if(Data[i-1][j-1] == 0 && 

Data[i-1][j] == 1) 

num_transitions2++ ; 

//S(p) = 1 

if (num_transitions2 == 1) 

{ 

// if p2 * p4 * p8 = 0 

if (Data[i-1][j] == 0 || 

Data[i][j+1] == 0 || 

Data[i][j-1] == 0) 

{ 

// if p2 * p6 * p8 = 0 

if(Data[i-1][j] == 0 || 

Data[i+1][j] == 0 || 

Data[i][j-1] == 0) 

temp_array[i][j] = 0; 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] = 1; 

} 

else 

temp_array[i][j] =0; 

}} 

//copy thinned image back to original 

for(j=0; j<400; j++) 

for(i=0; i<400; i++) 

Data[i][j]=temp_array[i][j]; 

TStringList* display2 = new TStringList; 
AnsiString str_line2; 
for(int b=0; b<400; b++) 
{ 
str_line2 = &quot;&quot;; 
for(int a=0; a<400; a++) 
{ 
if(i) 
str_line2 += &quot; , &quot;; 
Data[a][b]= temp_array[a][b]; 
str_line2 += IntToStr(Data[a][b]); 
} 
display2->Add(str_line2); 
} 
display2->SaveToFile(&quot;Thinning.dat&quot;); 
delete display2;
}

 
I have not read your code too intense but as i understand it you would like button 2 to do it's function and then &quot;autoklick&quot; button 3 and do that function.
If that's the function you would like just put in:
Button3Click(0); // or Button3Click(Sender);
at the very end of button 2 function.

Totte
 
You need to create another function that takes a pointer or an array. You can cast it to a two dimensional array afterwards if you want. Make sure that the final variable you use is called 'Data' and that it's a 2 dimensional array. In this function, put everything that's in the Button3Click() function that appears AFTER this line:

Data[y][x] = (Byte)Image1->Canvas->Pixels[x][y];

Do NOT include the above line or any line above that one.

At the END of the Button2Click() and Button3Click() functions, call your new function with 'Data' as the parameter.

Your new function could be declared as so:

void __fastcall TForm1::processData(int Data[][400])
{
...
}

If Data isn't an int, change it to the correct type.

Actually, it seems Data is global. In that case, you can simply leave out the argument and use this:

void __fastcall TForm1::processData()
{

}

Cheers


A programmer is a device for converting Coke into software.
 

hi..i'm very new in this programming area and actually i don't understand what are you trying to say.
where must i put the new function?did i have to add another button for the new function?how can i call this new function?
this is my final year project and i really need someone's help.thanks for your time...

 
Ok, I'll start again. I don't usually do this, so this'll be a one time deal. Plus, I'm really bored right now ;)

NOTE: As a previous post says, you can just call the code for Button3, but it wouldn't be the data from Button2. The Data would get overwritten.

So there are TWO ways to do this. I'll show you the proper way here (long and more difficult), and another hack (easy) at the end.

Method #1

This time around I'll assume the 'Data' variable is global in some way. At the very least, it's defined in the TForm1 class.

If you're asking where to put the function, that means you need to go read some books on prototypes and function definitions. It's the basis for most procedural languages anyways. C++ builds on top of that.

What we're going to do is take the functionality OUT of Button3 and put it in its own function. That way, we can just call it whenever we want that functionality.

Ok, put this in your TForm1 class definition (in the private section will do fine) Remember, this is inside your .h file:

void __fastcall ProcessData();

That was called a prototype. Or more precisely, a method declaration.

Now, you gotta define it in the .cpp file. Add a new function at the bottom of your .cpp file. From the way you were talking, it's almost as if you think only the GUI can create functions. You can create functions yourself manually like we're doing now. My apologies if you already know this.

Now, in your .cpp file. Anywhere's at all, but I recommend at the very bottom, type this:

void __fastcall TForm1::processData()
{
}

Ok, now we need to fill this function in. We're gonna be cut&pasting from the Button3Click() function. There'll be almost nothing left in the Button3Click() function when we're done.

CUT all these lines from the Button3Click() function and PASTE it into the ProcessData() function:

int count,count2,i,j,a,b;
int num_transitions ;
int num_transitions2 ;
int temp_array[400][400];

Those were your variable declarations. Yes, I did say CUT, so they should be gone from the Button3Click() function.

Now we need the code. CUT from this line all the way to the very END of your Button3Click() function:

TStringList* display = new TStringList;

The above line is included in the CUT.
PASTE all these lines at the end of your ProcessData() function after the variable declarations that you pasted earlier.

There should only be 5 lines left in Button3Click().

All right, now how to call this function. First off, your Button3Click() function is rather stripped of its functionality. So we gotta call ProcessData(). We do this by simply typing this at the end of the Button3Click() function:

ProcessData();

Isn't that simple.

Now you said you wanted to execute the code from Button3 after you click Button2. Well, that functionality is now in the ProcessData() function. So we just call ProcessData() at the end of Button2Click(). Do the same thing again, type this at the end of the Button2Click() function:

ProcessData();

And that my friends is why you should always put computational code inside seperate functions and never inside event methods.

Now for method #2.

If you follow this, it assumes that you didn't do ANYTHING in method #1 described above. The code must be exactly as you posted in your 1st post.

As stated earlier, the problem we have by typing this:

Button3Click(NULL);

at the end of Button2Click() function is that the Data array will be overwritten. Not what you want if I understand correctly. So we have to have some way of knowing that Button3Click is called from Button2Click(). If it's called from Button2Click(), we DON'T want to fill in the Data array again.

Well, Button3Click() takes 1 parameter, so we'll use this to tell where it was called from.

At the very end of the Button2Click() function, type this:

Button3Click(Button2);

That will tell Button3Click() that it was called from Button2Click().

Now we have to put a check inside Button3Click().

Add the following if statement around the 3 lines that initialize 'Data'. This is in Button3Click()

if (Sender!=Button2)
{
for (int y=0; y<DataHeight; y++)
for (int x=0; x<DataWidth; x++)
Data[y][x] = (Byte)Image1->Canvas->Pixels[x][y];
}

[The only thing added here is the 'if' line and the curly braces. The 3 inside lines are from the original code.]

That's it. I still call this a hack although it's a lot easier. What if you add another button and you want it to execute Button3's code. You gotta change it again. But with the 1st method, you just call a function.

Cheers
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top