/**************************************************************************************** This is a template image processing program to be used in E161. This program contains the basic input, processing and output parts. You can copy this program to your own directory and modify it according to your needs. In particular, you can replace the sample processing function called negative included in this program by any other processing functions write for the projects assigned during the semester. Also included in this program are two histogram functions (one for color images, one for black/white images). These are gifts for you to be used in the class. To compile this program, enter: gcc -lm processing.c -o processing To run the program, enter: processing filename_of_input_image filename_of_output_image or simply enter processing and the program will prompt you to enter the filenames for both input and output images. *********************************************************************************************/ #include #include #include #include #include "array_utility.h" // utility functions for matrix operations #include "svd.h" // singular value decomposition #define glevel 256 #define Pi 3.1415926536 #define Sqrt2 1.4142136 #define SWAP(a,b) tempr=(a); (a)=(b); (b)=tempr // These are global variables used by all functions char *strstr(); char in_filename[50], out_filename[50]; int M_in,N_in, M_out,N_out,Max,color_in, color_out; float **temp2_in, **temp2_out, ***temp3_in, ***temp3_out; vflip(float **img, int m, int n) // vertical flip of img { int i,j,m2=m/2; float v; for (j=0; jtmp[i][j]) min=tmp[i][j]; if (maxtmp[k][i][j]) min=tmp[k][i][j]; if (maxn) k=m; y = (float *) malloc(k*sizeof(float)); printf(" row transform...\n"); for (i=0; im) k=n; wm=Pi/2/m, wn=Pi/2/n; u0=sqrt(1.0/m); u=sqrt(2.0/m); v0=sqrt(1.0/n); v=sqrt(2.0/n); t=alloc2df(k,k); y=alloc2df(m,n); /* preparing for column transform matrix */ for (i=0; i>1; i=i^j; /* converting binary to Gray code */ i=i^(i>>1); j=0; for (k=0; k> k)); /* bit-reversal */ return j; } wht(x,m,sequency,inverse) float x[]; int m,inverse,sequency; { int mmax,step,i,j,k,j1,n,nu,N; float *y,t; N=pow(2,m); y=(float *)malloc(N*sizeof(float)); for (i=0; i1) w=1; if (w<-1) w=-1; *H=acos(w); if (*H < 0) { printf("H<0: %f\n",*H); pause(); } if (B > G) *H=2*Pi-*H; if (r <= g && r <= b) *S=1-3*r; if (g <= r && g <= b) *S=1-3*g; if (b <= r && b <= g) *S=1-3*b; } } hsi_rgb(H,S,I,R,G,B) // based on RGBCube model float *R, *G, *B, H, S, I; { float r, g, b; // printf("I=%f, H=%f, S=%f\n\n", I, H*180/Pi, S); if (S>1) S=1; if (I>1) I=1; if (S==0) *R=*G=*B=I; else { if ( (H >= 0) && (H <2*Pi/3) ) { b=(1-S)/3; r=(1+S*cos(H)/cos(Pi/3-H))/3; g=1-r-b; } else if ( (H>=2*Pi/3) && (H<4*Pi/3) ) { H=H-2*Pi/3; r=(1-S)/3; g=(1+S*cos(H)/cos(Pi/3-H))/3; b=1-r-g; } else if ( (H>=4*Pi/3) && (H<2*Pi) ) { H=H-4*Pi/3; g=(1-S)/3; b=(1+S*cos(H)/cos(Pi/3-H))/3; r=1-b-g; } else { printf("\nH out of range: %f\n",H*180/Pi); pause();} if (r<0 || g<0 || b<0) { printf("\n\nr,g,b: %f, %f, %f",r,g,b); printf(" h,s,i: %f, %f, %f\n",H,S,I); pause(); } if (r < 0) r=0; if (g < 0) g=0; if (b < 0) b=0; *R=3*I*r; *G=3*I*g; *B=3*I*b; if (*R > 1) *R=1; if (*G > 1) *G=1; if (*B > 1) *B=1; } // printf("R=%6.2f, G=%6.2f, B=%6.2f\n\n",*R,*G,*B); } RGB_HSI(r,g,b,h,s,v) // based on hexcone model float r,g,b,*h,*s,*v; { float max,min,delta; max=myMAX(r,g,b); min=myMIN(r,g,b); *v=max; if (max==min || max==0) { *s=*h=0.0; return 1; } else *s=(max-min)/max; delta=max-min; if (delta==0.0) { printf("(%f, %f, %f), max=%f, min=%f, delta=%f\n",r,g,b,max,min,delta); pause(); } if (r==max) *h=(g-b)/delta; else if (g==max) *h=2.0+(b-r)/delta; else if (b==max) *h=4.0+(r-g)/delta; *h*=Pi/3; if (*h<0.0) *h+=2*Pi; } HSI_RGB(h,s,v,r,g,b) // based on hexcone model float *r, *g, *b, h, s, v; { float f,p,q,t; int i; if (s>1.0) s=1.0; if (v>1.0) v=1.0; if (s==0.0) { *r=*g=*b=v; // if (h!=0.0) { printf("Error, return..."); return 0; } } if (h>=2*Pi) h=0.0; h=h*3/Pi; i=h; f=h-i; p=v*(1-s); q=v*(1-s*f); t=v*(1-s*(1-f)); switch (i){ case 0: *r=v; *g=t; *b=p; break; case 1: *r=q; *g=v; *b=p; break; case 2: *r=p; *g=v; *b=t; break; case 3: *r=p; *g=q; *b=v; break; case 4: *r=t; *g=p; *b=v; break; case 5: *r=v; *g=p; *b=q; } } float myMAX(x,y,z) float x,y,z; { if (x>=y && x>=z) return x; if (y>=x && y>=z) return y; if (z>=x && z>=y) return z; } float myMIN(x,y,z) float x,y,z; { if (x<=y && x<=z) return x; if (y<=x && y<=z) return y; if (z<=x && z<=y) return z; } sort(bin,k) short *bin; int k; { int i,j; short w; // printf("\nk=%d\n",k); // for (i=0; ibin[j] ) { w=bin[i]; bin[i]=bin[j]; bin[j]=w; } // printf("\n"); // for (i=0; im) k=n; xr = (float *) malloc(k*sizeof(float)); xi = (float *) malloc(k*sizeof(float)); printf("Forward 2DFFT\n row transform...\n"); for (i=0; im) k=n; xr = (float *) malloc(k*sizeof(float)); xi = (float *) malloc(k*sizeof(float)); printf(" column transform...\n"); for (j=0; jm) k=n; wm=Pi*2/m, wn=Pi*2/n; w=1.0/sqrt((float)(m*n)); tr=alloc2df(k,k); ti=alloc2df(k,k); /* transfor matrices */ yr=alloc2df(m,n); yi=alloc2df(m,n); /* spectral matrics */ /* preparing for column transform matrix */ printf("Column transform...\n"); for (i=0; im) k=n; xr = (float *) malloc(k*sizeof(float)); xi = (float *) malloc(k*sizeof(float)); printf("\nRow xform...\n"); for (j=0; j> k)); if (j < i) { SWAP(xr[i],xr[j]); SWAP(xi[i],xi[j]); } } for (i=0; i=n-d/2) { printf("index %d outside range (%d -- %d)...",k,d/2,n-d/2); pause(); } u=1.0; for (i=1; i<=d2; i++) if (i) u*=(time[k]-time[k-i])*(time[k]-time[k+i]); dy=0; for (i=-d2; i<=d2; i++) { v=1.0; for (j=-d2; j<=d2; j++) if (i!=j) v=v*(time[k+i]-time[k+j]); if (i) dy+=data[k+i]*u/(time[k]-time[k+i])/v; else for (j=-d2; j<=d2; j++) if (j) dy+=data[k]/(time[k]-time[k+j]); } return dy; }