ORIENT.C

Go to the documentation of this file.
00001 /* --
00002 OpenFX - Modelling, Animation and Rendering Package
00003 -- */
00004 
00005 /*  ORIENT.C  */
00006 
00007 #include <stdlib.h>
00008 #include <stdio.h>
00009 #include <math.h>
00010 #include <windows.h>
00011 
00012 #include "struct.h"
00013 #include "dstruct.h"
00014 
00015 #define DLG_CUT 600
00016 
00017 #include "orient.h"
00018 
00019 #define DESELECTED 0
00020 #define SELECTED   1
00021 #define INEDITOR   3
00022 
00023 static HWND      hParent;
00024 static HINSTANCE hThisInstance;
00025 
00026 static void Orientate(HWND);
00027 
00028 #if __WATCOMC__
00029 int APIENTRY LibMain(HANDLE hDLL, DWORD dwReason, LPVOID lpReserved){
00030 #else
00031 BOOL WINAPI DllMain(HANDLE hDLL, DWORD dwReason, LPVOID lpReserved){
00032 #endif
00033   switch (dwReason) {
00034     case DLL_PROCESS_ATTACH: {
00035       hThisInstance=hDLL;
00036       if(hDLL == NULL)MessageBox( GetFocus()," NULL instance",NULL, MB_OK);
00037       break;
00038     }
00039     case DLL_PROCESS_DETACH:
00040       break;
00041   }
00042   return TRUE;
00043 }
00044 
00045 #if __SC__
00046 #pragma startaddress(DllMain)
00047 #endif
00048 
00049 static BOOL CALLBACK OrientateDlgProc(HWND hwnd, UINT msg,
00050                              WPARAM wparam, LPARAM lparam){
00051  switch( msg ) {
00052    case WM_INITDIALOG:
00053      CentreDlgOnS(hwnd);
00054      return (TRUE);
00055    case WM_COMMAND:
00056       switch(LOWORD(wparam)){
00057         case IDCANCEL:
00058           EndDialog(hwnd,FALSE);
00059           return(TRUE);
00060         case IDOK:
00061           EndDialog(hwnd,TRUE);
00062           return(TRUE);
00063         default:
00064           break;
00065       }
00066       break;
00067     default: break;
00068  }
00069  return(FALSE);
00070 }
00071 
00072 BOOL _Xmodeler
00073  (HWND parent_window,HWND info_window,X__STRUCTURE *lpevi){
00074  HCURSOR hSave;
00075  lpEVI=lpevi;
00076  hParent=parent_window;
00077  if(DialogBox(hThisInstance,MAKEINTRESOURCE(DLG_CUT),hParent,
00078              (DLGPROC)OrientateDlgProc) == FALSE)return FALSE;
00079  hSave=SetCursor(LoadCursor(NULL,IDC_WAIT));
00080  Orientate(parent_window);
00081  SetCursor(hSave);
00082  return TRUE;
00083 }
00084 
00085 static int Nchange,Npieces;
00086 static workface *WF;
00087 
00088 static void MakeSameOrientation(long last, long id){
00089  face *f;
00090  long i0,i1,i2,l0,l1,l2,a0,a1,a2;
00091  f=(MainFp+WF[last].f); l0=f->V[0]; l1=f->V[1]; l2=f->V[2];
00092  f=(MainFp+WF[id].f);   i0=f->V[0]; i1=f->V[1]; i2=f->V[2];
00093  a0=WF[id].fa[0]; a1=WF[id].fa[1]; a2=WF[id].fa[2];
00094  if((i2 == l2 && i1 == l1) ||
00095     (i2 == l1 && i1 == l0) ||
00096     (i2 == l0 && i1 == l2)){
00097    WF[id].fa[2]=a0; WF[id].fa[0]=a2;
00098    f->V[2]=i1; f->V[1]=i2; Nchange++;
00099    return;
00100  }
00101  if((i0 == l2 && i2 == l1) ||
00102     (i0 == l1 && i2 == l0) ||
00103     (i0 == l0 && i2 == l2)){
00104    WF[id].fa[0]=a1; WF[id].fa[1]=a0;
00105    f->V[0]=i2; f->V[2]=i0; Nchange++;
00106    return;
00107  }
00108  if((i1 == l1 && i0 == l0) ||
00109     (i1 == l2 && i0 == l1) ||
00110     (i1 == l0 && i0 == l2)){
00111    WF[id].fa[1]=a2; WF[id].fa[2]=a1;
00112    f->V[1]=i0; f->V[0]=i1; Nchange++;
00113    return;
00114  }
00115  return;
00116 }
00117 
00118 static void SetConnectingID(long last,long id){
00119  if(WF[id].id == 1)return;
00120  WF[id].id=1;
00121  if(last >= 0)MakeSameOrientation(last,id);
00122  last=id;
00123  if(WF[id].fa[0] >= 0)SetConnectingID(last,WF[id].fa[0]);
00124  if(WF[id].fa[1] >= 0)SetConnectingID(last,WF[id].fa[1]);
00125  if(WF[id].fa[2] >= 0)SetConnectingID(last,WF[id].fa[2]);
00126 }
00127 
00128 static void Reorientate(workface *wf, long nf){
00129  long i,id;
00130  WF=wf;
00131  Nchange=0; Npieces=0;
00132  for(i=0;i<nf;i++)wf[i].id = -1;
00133  while(1){ /* keep going until all the bits have been processed */
00134    for(id=0;id<nf;id++){
00135      if(wf[id].id == -1)goto PROCESSIT;
00136    }
00137    break;      /* no bits have been found - so breakout */
00138    PROCESSIT:
00139    SetConnectingID(-1,id);
00140    Npieces++;
00141  }
00142  return;
00143 }
00144 
00145 static int FindAdjFaces(workface *wf, long nf){
00146  face *f;
00147  vertex *vp;
00148  vtxadj *vl=NULL;
00149  long c,nvl=0;
00150  long *fl,i,j,k,id,id0,id1,id2,fjd,fkd,n,m,kk,nl[3],ml[3];
00151  vp=MainVp; for(c=0;c<Nvert;c++){
00152    if(vp->status == SELECTED){ /* work vertex */
00153      vp->id=nvl;
00154      nvl++;
00155    }
00156    else vp->id = -10; /* just for fun */
00157    vp++;
00158  }
00159  if((vl=(vtxadj *)X__Malloc(nvl*sizeof(vtxadj))) == NULL)return 0;
00160  for(i=0;i<nvl;i++){
00161    vl[i].nf=0;
00162    vl[i].flist=NULL;
00163  }
00164  for(i=0;i<nf;i++){ /* make list of work faces attached to each vertex */
00165    f=(MainFp+wf[i].f);
00166    for(j=0;j<3;j++){
00167      id=(MainVp+(f->V[j]))->id;
00168      fl=vl[id].flist;
00169      n=vl[id].nf;
00170      if(fl == NULL){
00171        if((fl=(long *)X__Malloc(sizeof(long))) == NULL)return 0;
00172      }
00173      else{
00174        if((fl=(long *)X__Realloc(fl,(n+1)*sizeof(long))) == NULL)return 0;
00175      }
00176      fl[n]=i;
00177      vl[id].flist=fl;
00178      vl[id].nf=n+1;
00179    }
00180  }
00181  for(i=0;i<nf;i++){ /* find faces that are adjacent to face i */
00182    f=(MainFp+wf[i].f);
00183    id0=(MainVp+(f->V[0]))->id;
00184    id1=(MainVp+(f->V[1]))->id;
00185    id2=(MainVp+(f->V[2]))->id;
00186    nl[0]=id0; ml[0]=id1;
00187    nl[1]=id1; ml[1]=id2;
00188    nl[2]=id2; ml[2]=id0;
00189    for(kk=0;kk<3;kk++){
00190      wf[i].fa[kk] = -1;
00191      if((n=vl[nl[kk]].nf) > 0 && (m=vl[ml[kk]].nf) > 0){
00192        for(j=0;j<n;j++){
00193          fjd=vl[nl[kk]].flist[j];
00194          for(k=0;k<m;k++){
00195            fkd=vl[ml[kk]].flist[k];
00196            if(fkd == fjd && fkd != i){
00197              wf[i].fa[kk]=fkd;
00198              goto ENDF;
00199            }
00200          }
00201        }
00202      }
00203      ENDF:;
00204    }
00205  }
00206  for(i=0;i<nvl;i++){
00207    if(vl[i].flist != NULL)X__Free(vl[i].flist);
00208  }
00209  X__Free(vl);
00210  return nvl;
00211 }
00212 
00213 static void Orientate(HWND hWnd){
00214  /* workface is the face being worked on */
00215  /* tool face is the face doing the cutting */
00216  char str[256];
00217  workface *w;
00218  face *ff1;
00219  vertex *v0,*v1,*v2;
00220  long c,i,j;
00221  long n_work_face=0;
00222  if(NvertSelect == 0 || NvertSelect > 64000)return;
00223  if((ff1=MainFp) == NULL)return;
00224  w=NULL;
00225  for(c=0;c<Nface;c++){ /* find number of work and tool faces */
00226    v0=(MainVp+ff1->V[0]); v1=(MainVp+ff1->V[1]); v2=(MainVp+ff1->V[2]);
00227    if(v0->status == SELECTED &&
00228       v1->status == SELECTED &&
00229       v2->status == SELECTED)n_work_face++;
00230    ff1++;
00231  }
00232  if((w=(workface *)X__Malloc(n_work_face*(long)sizeof(workface)))
00233        == NULL)return;
00234  n_work_face=0;
00235  for(ff1=MainFp,c=0;c<Nface;c++){
00236   v0=(MainVp+ff1->V[0]); v1=(MainVp+ff1->V[1]); v2=(MainVp+ff1->V[2]);
00237   if(v0->status == SELECTED &&
00238      v1->status == SELECTED &&
00239      v2->status == SELECTED){
00240    w[n_work_face].f=c;
00241     for(i=0;i<3;i++){
00242       w[n_work_face].fa[i] = -1;
00243     }
00244     n_work_face++;
00245   }
00246   ff1++;
00247  }
00248  if(n_work_face != 0){
00249    FindAdjFaces(w,n_work_face);
00250    Reorientate(w,n_work_face);
00251  }
00252  if(w != NULL)X__Free(w);
00253  sprintf(str,"%ld Selected Faces in   \n%ld Separate pieces.   \n%ld Faces re-orientated  ",
00254          n_work_face,Npieces,Nchange);
00255  MessageBox(hWnd,str,"Orientate Faces",MB_OK|MB_ICONINFORMATION);
00256  return;
00257 }
00258 

Generated on Sun Apr 27 14:20:11 2014 for OpenFX by  doxygen 1.5.6