crumpled.c

Go to the documentation of this file.
00001 /* --
00002 OpenFX version 2.0 - Modelling, Animation and Rendering Package
00003 Copyright (C) 2000 - 2007 OpenFX Development Team
00004 -- */
00005 
00006 // crumpled.c
00007 
00008 #include <stdlib.h>
00009 #include <stdio.h>
00010 #include <math.h>
00011 #include <float.h>
00012 #include <windows.h>
00013 #include <gl/gl.h>
00014 
00015 #if __ZTC__ || __SC__
00016 #ifndef max
00017 #define max(a,b)  ( ((a) > (b)) ? (a) : (b) )
00018 #endif
00019 #endif
00020 
00021 #if __WATCOMC__
00022 #define PI 3.1415926
00023 #endif
00024 
00025 #if __X__MIPS__
00026 BOOL WINAPI _CRT_INIT(HINSTANCE ,DWORD , LPVOID );
00027 #endif
00028 
00029 static HINSTANCE hDLLinstance=NULL;
00030 
00031 #include "..\animate\memory.h" /* for memory definition */
00032 #include "..\animate\memdef.h" /* local names           */
00033 #include "defines.h"
00034 #include "rstruct.h"
00035 #include "crumpled.h"
00036 
00037 #define VECCOPY(a,b)    { b[0] = a[0]; b[1] = a[1]; b[2] = a[2]; }
00038 #define VECSUM(a,b,c)   { c[0]=a[0]+b[0]; c[1]=a[1]+b[1]; c[2]=a[2]+b[2];}
00039 #define VECSUB(a,b,c)   { c[0]=a[0]-b[0]; c[1]=a[1]-b[1]; c[2]=a[2]-b[2];}
00040 #define VECSCALE(a,b,c) { c[0]=(a)*b[0]; c[1]=(a)*b[1]; c[2]=(a)*b[2];}
00041 #define DOT(a,b)        ( (a[0]*b[0]) + (a[1]*b[1]) + (a[2]*b[2]) )
00042 
00043 #define IMOD(z,a) ((z) - ((z)/(a))*(a))
00044 #define PATTERN(x,y,z)   ( ((z)+16384L)*64536L +  \
00045                            ((y)+16384L)*32768L +  \
00046                            ((x)+16384L))
00047 #define FLOOR(x) ((x) >= 0.0 ? floor(x) : (0.0 - floor(0.0 - (x)) - 1.0))
00048 #define FMOD(x,a) ((x) >= 0.0 ? fmod(x,a) :(a - fmod(-(x),a)))
00049 
00050 #include "randno.c"
00051 
00052 static long ip[27][3]={
00053    { 0, 0, 0},
00054    { 1, 0, 0},
00055    { 1, 1, 0},
00056    { 0, 1, 0},
00057    {-1, 1, 0},
00058    {-1, 0, 0},
00059    {-1,-1, 0},
00060    { 0,-1, 0},
00061    { 1,-1, 0},
00062    { 0, 0,-1},
00063    { 1, 0,-1},
00064    { 1, 1,-1},
00065    { 0, 1,-1},
00066    {-1, 1,-1},
00067    {-1, 0,-1},
00068    {-1,-1,-1},
00069    { 0,-1,-1},
00070    { 1,-1,-1},
00071    { 0, 0, 1},
00072    { 1, 0, 1},
00073    { 1, 1, 1},
00074    { 0, 1, 1},
00075    {-1, 1, 1},
00076    {-1, 0, 1},
00077    {-1,-1, 1},
00078    { 0,-1, 1},
00079    { 1,-1, 1}
00080  };
00081 
00082 #if __WATCOMC__
00083 int APIENTRY LibMain(HANDLE hDLL, DWORD dwReason, LPVOID lpReserved){
00084 #else
00085 BOOL WINAPI DllMain(HANDLE hDLL, DWORD dwReason, LPVOID lpReserved){
00086 #endif
00087   HANDLE ghMod;
00088   switch (dwReason) {
00089     case DLL_PROCESS_ATTACH:
00090 #if __X__MIPS__
00091       if(!_CRT_INIT(hDLL,dwReason,lpReserved))return(int)FALSE;
00092 #endif
00093       hDLLinstance = hDLL;  /* handle to DLL file */
00094       break;
00095     case DLL_PROCESS_DETACH:
00096 #if __X__MIPS__
00097       if(!_CRT_INIT(hDLL,dwReason,lpReserved))return(int)FALSE;
00098 #endif
00099       break;
00100   }
00101   return (int)TRUE;
00102 }
00103 
00104 #if __SC__
00105 #pragma startaddress(DllMain)
00106 #endif
00107 
00108 static double x=1.0,y=1.0,z=1.0;
00109 
00110 #if 0
00111 long CALLBACK ExternalTextureStartup(
00112 #else
00113 long _ExternalTextureStartup(
00114 #endif
00115   long frame,long nframes,char *parameter_list, X__SHADER *lpEVI){
00116  if(parameter_list[0] != '#'){
00117    MessageBox ( GetFocus(),
00118                 (LPCTSTR) "External texture: Startup",
00119                 (LPCTSTR) "Parameter list missing",
00120                 MB_OK | MB_SYSTEMMODAL );
00121  }
00122  else {
00123   parameter_list++;
00124   sscanf(parameter_list,"%f %f %f",
00125          &x,&y,&z);
00126  }
00127  return LoadAndCompileShader("crumpled");
00128 }
00129 
00130 #if 0
00131 long CALLBACK ExternalTextureMorph(
00132 #else
00133 long _ExternalTextureMorph(
00134 #endif
00135  char *parameter_list, double mr){
00136  double x_m,y_m,z_m;
00137  parameter_list++;
00138  sscanf(parameter_list,"%f %f %f",
00139         &x_m,&y_m,&z_m);
00140  x=x_m+(x-x_m)*mr;
00141  y=y_m+(y-y_m)*mr;
00142  z=z_m+(z-z_m)*mr;
00143  return 1;
00144 }
00145 
00146 #if 0
00147 long CALLBACK ExternalTextureProcedure(
00148 #else
00149 long _ExternalTextureProcedure(
00150 #endif
00151   long coord_type,  vector p, vector n,
00152   double alpha, double beta, double gamma,
00153   double bump,  double map_x,  double map_y,
00154   double *alpha_channel, unsigned char sc[3], double colour[3],
00155   double *reflectivity, double *transparency,
00156   X__SHADER *lpEVI
00157 ){
00158  static long N=1;
00159  static double bradius=1.0,lradius=0.0;
00160  double a;
00161  vector u,v;
00162  double xx,yy,zz;
00163  double  dpoint[27];
00164  double dradius[27];
00165  vector pp[27];
00166  double dx,dy,dz,cx,cy,cz,zb,ccc,dc,zbb,radius;
00167  long i,ix,iy,iz;
00168  BOOL ins;
00169  long k,j,jid,id,pattern,patterni;
00170  double len,rad;
00171  vector ppc;
00172 
00173  xx=alpha / x;
00174  yy=beta  / y;
00175  zz=gamma / z;
00176 
00177  xx *= 2.0;
00178  yy *= 2.0;
00179  zz *= 2.0;
00180  for(k=0;k<3;k++){
00181  if(k == 1){
00182    vNoise(v,xx,yy,zz);
00183    xx += 0.5*v[0];
00184    yy += 0.5*v[1];
00185    zz += 0.5*v[2];
00186  }
00187  id=0;
00188  ix=FLOOR(xx);
00189  iy=FLOOR(yy);
00190  iz=FLOOR(zz);
00191  cx=xx-(double)ix;
00192  cy=yy-(double)iy;
00193  cz=zz-(double)iz;
00194  zb=-10.0;
00195  ins=TRUE;
00196  id = -1;
00197  len=sqrt(tAxis_u[0]*tAxis_u[0]+
00198           tAxis_u[1]*tAxis_u[1]+
00199           tAxis_u[2]*tAxis_u[2]);
00200  VECCOPY(-tAxis_n,u)
00201  VECSCALE(len,u,u)         // third axis
00202  VECCOPY(tAxis_o,v)
00203  VECSUM(v,cx*tAxis_u,v)
00204  VECSUM(v,cy*tAxis_v,v)
00205  VECSUM(v,cz*u,v)         // coord of point on surface
00206  for(j=0;j<27;j++){
00207  pattern=PATTERN(ix+ip[j][0],iy+ip[j][1],iz+ip[j][2]);
00208  pattern=IMOD(N*pattern,1900);
00209  for(i=0;i<N;i++){
00210    jid=j*N+i;
00211    patterni=pattern+i;
00212    VECSUM((double)ip[j],rand_v[patterni],ppc)
00213    VECSUM(tAxis_o,ppc[0]*tAxis_u,pp[jid])
00214    VECSUM(pp[jid],ppc[1]*tAxis_v,pp[jid])
00215    VECSUM(pp[jid],ppc[2]*u,      pp[jid])
00216 
00217    radius=(bradius+lradius*(rand_v[patterni][1]-0.5))*len;
00218    dradius[jid]=radius;
00219    dpoint[jid] = -1.0;
00220    dx=(v[0]-pp[jid][0]);
00221    dy=(v[1]-pp[jid][1]);
00222    dz=(v[2]-pp[jid][2]);
00223    if(fabs(dx) > radius)continue;
00224    if(fabs(dy) > radius)continue;
00225    if(fabs(dz) > radius)continue;
00226    if((a=sqrt(dx*dx+dy*dy+dz*dz)) < radius){
00227      dpoint[jid]=a;
00228      dc=(radius-a);
00229      if(dc > zb){
00230        id=jid;
00231        zb=dc;
00232      }
00233    }
00234  }
00235  }
00236  if(id >= 0 && ins){
00237    if(1){//zb < 0.2){
00238      VECCOPY(pp[id],ppc)
00239      rad=dradius[id];
00240      VECSUB(v,ppc,u)          //(v-pp) vector from centre of pattern
00241      if((a=sqrt((u[0])*(u[0])+
00242                 (u[1])*(u[1])+
00243                 (u[2])*(u[2]))) < rad){
00244        double mu,moddn,rmu;
00245        vector c,dn;
00246        mu=DOT(u,n);
00247        c[0]=ppc[0]+mu*n[0];
00248        c[1]=ppc[1]+mu*n[1];
00249        c[2]=ppc[2]+mu*n[2];
00250        VECSUB(v,c,dn)
00251        moddn=sqrt(dn[0]*dn[0]+dn[1]*dn[1]+dn[2]*dn[2]);
00252        rmu=sqrt(rad*rad-mu*mu);
00253        if(moddn < rmu){
00254          a=1.0-moddn/rmu;
00255          normalize(dn);
00256          VECSCALE(-1.0,dn,dn);  // dimples
00257          if     (k == 0){a=sin(a*1.57079);}
00258          else if(k == 1)a=0.8;
00259          else if(k == 2)a=0.95;
00260          VECSUM((1.0-a)*dn,(a)*n,n)
00261          normalize(n);
00262        }
00263      }
00264    }
00265  }
00266  xx *= 2.0; yy *= 2.0; zz *=2.0;
00267  }
00268  return 1;
00269 }
00270 
00271 void _ExternalTextureClose(X__SHADER *lpEVI){
00272  UnloadCompiledShader(tGLshaderID);
00273 }
00274 
00275 long _ExternalTextureProcedureGL(
00276   double bump_scale,
00277   unsigned char sc[3],
00278   unsigned char ac[3],
00279   X__SHADER *lpEVI
00280 ){
00281  // Set any shader specific uniform variables here.
00282  SetUniformVector(tGLshaderID,"MaterialC",(GLfloat)ac[0]/255.0,(GLfloat)ac[1]/255.0,(GLfloat)ac[2]/255.0);
00283  SetUniformVector(tGLshaderID,"ScalingV",1.0/x,1.0/z,1.0/y);
00284  DrawShadedPolygons(tmatpass,tpass,tprogID,tattrloc,tNface,tMainFp,tNvert,tMainVp);
00285  return 1;
00286 }
00288 
00289 void CentreDialogOnScreen(HWND hwnd){
00290  RECT rcDlg;
00291  long Xres,Yres;
00292  Yres=GetSystemMetrics(SM_CYSCREEN);
00293  Xres=GetSystemMetrics(SM_CXSCREEN);
00294  GetWindowRect(hwnd,&rcDlg);
00295  OffsetRect(&rcDlg,-rcDlg.left,-rcDlg.top);
00296  OffsetRect(&rcDlg,(Xres-rcDlg.right)/2,(Yres-rcDlg.bottom)/2);
00297  SetWindowPos(hwnd,HWND_TOP,rcDlg.left,rcDlg.top,0,0,SWP_NOSIZE);
00298  return;
00299 }
00300 
00301 static void SetColour(double *colour, HWND parent){
00302  CHOOSECOLOR cc;
00303  static COLORREF CustColours[16]={
00304    RGB(255,255,255), RGB(239,239,239), RGB(223,223,223), RGB(207,207,207),
00305    RGB(191,191,191), RGB(175,175,175), RGB(159,159,159), RGB(143,143,143),
00306    RGB(127,127,127), RGB(111,111,111), RGB( 95, 95, 95), RGB( 79, 79, 79),
00307    RGB( 63, 63, 63), RGB( 47, 47, 47), RGB( 31, 31, 31), RGB( 15, 15, 15) };
00308  cc.lStructSize=sizeof(CHOOSECOLOR);
00309  cc.hwndOwner=parent;
00310  cc.rgbResult=RGB((BYTE)colour[0],(BYTE)colour[1],(BYTE)colour[2]);
00311  cc.lpCustColors=(LPDWORD)CustColours;
00312  cc.Flags= CC_RGBINIT;
00313  cc.lCustData=(DWORD)0;
00314  if(ChooseColor(&cc)){
00315    colour[0]=(double)GetRValue(cc.rgbResult);
00316    colour[1]=(double)GetGValue(cc.rgbResult);
00317    colour[2]=(double)GetBValue(cc.rgbResult);
00318  }
00319 }
00320 
00321 BOOL CALLBACK DlgProc(HWND hwnd,UINT msg,WPARAM wparam,LPARAM lparam);
00322 
00323 #if 0
00324 char * CALLBACK SetExternalParameters(
00325 #else
00326 char * _SetExternalParameters(
00327 #endif
00328   char *Op,                 /* string for the parameters                  */
00329   HWND hWnd,                /* parent window                              */
00330   X__MEMORY_MANAGER *lpEVI /* pointer to structure with memory functions */
00331                              ){
00332  char szbuf[255],*Op1;
00333  if(Op != NULL){  /* parameters exist so read them off the list */
00334    Op1=Op;
00335    Op1++;
00336    sscanf(Op1,"%f %f %f",
00337          &x,&y,&z);
00338  }
00339  if(DialogBox(hDLLinstance,MAKEINTRESOURCE(DLG),hWnd,
00340               (DLGPROC)DlgProc) == FALSE)return Op;
00341  if(Op != NULL)CALL_FREE(Op);  /* free the old string */
00342  sprintf(szbuf,"# %.3f %.3f %.3f",
00343          x,y,z);
00344  if((Op=(char *)CALL_MALLOC(strlen(szbuf)+1)) == NULL){
00345   MessageBox (GetFocus(),"External shader: Out of memory","Error",
00346                 MB_OK|MB_TASKMODAL|MB_ICONSTOP);
00347    return NULL;
00348  }
00349  strcpy(Op,szbuf);
00350  return Op;
00351 }
00352 
00353 BOOL CALLBACK DlgProc(HWND hwnd,UINT msg,WPARAM wparam,LPARAM lparam){
00354  char str[16];
00355  switch( msg ) {
00356    case WM_INITDIALOG:
00357      sprintf(str,"%.2f",x);
00358      SendDlgItemMessage(hwnd,DLG_XSCALE,WM_SETTEXT,0,(LPARAM)str);
00359      SendDlgItemMessage(hwnd,DLG_XSCALE,EM_LIMITTEXT,(WPARAM)12,0);
00360      sprintf(str,"%.2f",y);
00361      SendDlgItemMessage(hwnd,DLG_YSCALE,WM_SETTEXT,0,(LPARAM)str);
00362      SendDlgItemMessage(hwnd,DLG_YSCALE,EM_LIMITTEXT,(WPARAM)12,0);
00363      sprintf(str,"%.2f",z);
00364      SendDlgItemMessage(hwnd,DLG_ZSCALE,WM_SETTEXT,0,(LPARAM)str);
00365      SendDlgItemMessage(hwnd,DLG_ZSCALE,EM_LIMITTEXT,(WPARAM)12,0);
00366      CentreDialogOnScreen(hwnd);
00367      return TRUE;
00368    case WM_COMMAND:
00369      switch(LOWORD(wparam)){
00370         case IDCANCEL:
00371           EndDialog(hwnd,FALSE);
00372           return(TRUE);
00373         case IDOK:
00374           if(GetDlgItemText(hwnd,DLG_XSCALE,str,10) == 0)
00375              EndDialog(hwnd,FALSE);
00376           if((x=atof(str)) == 0)EndDialog(hwnd,FALSE);
00377           if(GetDlgItemText(hwnd,DLG_YSCALE,str,10) == 0)
00378              EndDialog(hwnd,FALSE);
00379           if((y=atof(str)) == 0)EndDialog(hwnd,FALSE);
00380           if(GetDlgItemText(hwnd,DLG_ZSCALE,str,10) == 0)
00381              EndDialog(hwnd,FALSE);
00382           if((z=atof(str)) == 0)EndDialog(hwnd,FALSE);
00383           EndDialog(hwnd,TRUE);
00384           return(TRUE);
00385         default:
00386           break;
00387       }
00388       break;
00389     default: break;
00390  }
00391  return FALSE;
00392 }
Generated on Tue Jan 28 06:18:32 2014 for OpenFX by  doxygen 1.6.3