/*! * \return * \ingroup WlzTransform * \brief Gets a 3D section through a byte packed bitmap. * \param sizeBitData Number of bytes in bitmap. * \param bitData Bitmap data. * \param width Bitmap width. * \param height Bitmap height. * \param x_offset Horizontal ofset into the bitmap. * \param y_offset Vertical offset into the bitmap. * \param x Fixed point x coordinate. * \param y Fixed point y coordinate. * \param z Fixed point z coordinate. * \param theta Angle of rotation about the z-axis * (radians). * \param phi Angle between the viewing direction * and the original z-axis (radians). * \param distance Perpendicular distance from the * fixed point to the view plane. * \param dstErr Destination error pointer, may be NULL. */ WlzObject *Wlz3DViewTransformBitmap( int sizeBitData, WlzUByte *bitData, int width, int height, int x_offset, int y_offset, double x, double y, double z, double theta, double phi, double distance, WlzErrorNum *dstErr) { WlzErrorNum errNum=WLZ_ERR_NONE; WlzObject *rtnObj=NULL; WlzObject *tmpObj; WlzIVertex2 arraySizeDat; WlzIVertex2 arrayOrigin; WlzThreeDViewStruct *viewStr; arraySizeDat.vtX = width; arraySizeDat.vtY = height; arrayOrigin.vtX = x_offset; arrayOrigin.vtY = y_offset; if((tmpObj = WlzAssignObject(WlzFromBArray1D(arraySizeDat, bitData, arrayOrigin, &errNum), NULL)) != NULL) { /* make and initialise WlzThreeDViewStruct */ if((viewStr = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum)) != NULL) { viewStr->fixed.vtX = x; viewStr->fixed.vtY = y; viewStr->fixed.vtZ = z; viewStr->theta = theta * WLZ_M_PI / 180.0; viewStr->phi = phi * WLZ_M_PI / 180.0; viewStr->dist = distance; viewStr->scale = 1.0; viewStr->view_mode = WLZ_UP_IS_UP_MODE; viewStr->up.vtX = 0.0; viewStr->up.vtY = 0.0; viewStr->up.vtZ = -1.0; WlzInit3DViewStruct(viewStr, tmpObj); /* transform the 2D section to 3D */ rtnObj = Wlz3DViewTransformObj(tmpObj, viewStr, &errNum); /* clean up */ WlzFree3DViewStruct(viewStr); } WlzFreeObj(tmpObj); } if( dstErr ) { *dstErr = errNum; } return rtnObj; }
int free_view_struct( ThreeDViewStruct *view_struct) { WlzErrorNum errNum=WLZ_ERR_NONE; errNum = WlzFree3DViewStruct(view_struct->wlzViewStr); if( errNum == WLZ_ERR_NONE ){ view_struct->ximage->data = NULL; XDestroyImage(view_struct->ximage); glDeleteLists(view_struct->display_list, 1); MAOpenGLDrawScene( globals.canvas ); } /* check the view, painted and masked objects */ if( (errNum == WLZ_ERR_NONE) && (view_struct->view_object != NULL) ) { errNum = WlzFreeObj( view_struct->view_object ); view_struct->view_object = NULL; } if( (errNum == WLZ_ERR_NONE) && (view_struct->painted_object != NULL) ) { errNum = WlzFreeObj( view_struct->painted_object ); view_struct->painted_object = NULL; } if( (errNum == WLZ_ERR_NONE) && (view_struct->masked_object != NULL) ) { errNum = WlzFreeObj( view_struct->masked_object ); view_struct->masked_object = NULL; } if( (errNum == WLZ_ERR_NONE) && (view_struct->prev_view_obj != NULL) ) { errNum = WlzFreeObj( view_struct->prev_view_obj ); view_struct->prev_view_obj = NULL; } if( errNum != WLZ_ERR_NONE ){ MAPaintReportWlzError(globals.topl, "reset_view_struct", errNum); return 1; } return( 0 ); }
/*! * \return Woolz error code. * \ingroup WlzAllocation * \brief Free a domain structure of any type. All domain * structures must have a type and linkcount. Most * also have a freeptr by which, if set, all the space * allocated can be freed, however there are some special * cases. * \param domain Domain to be freed. */ WlzErrorNum WlzFreeDomain(WlzDomain domain) { WlzErrorNum errNum = WLZ_ERR_NONE; AlcErrno alcErrNum = ALC_ER_NONE; if(domain.core != NULL) { if(WlzUnlink(&(domain.core->linkcount), &errNum)) { switch(domain.core->type) { case WLZ_CMESH_2D: errNum = WlzCMeshFree2D(domain.cm2); break; case WLZ_CMESH_3D: errNum = WlzCMeshFree3D(domain.cm3); break; case WLZ_3D_VIEW_STRUCT: errNum = WlzFree3DViewStruct(domain.vs3d); break; default: /* Most domains are are freed in the same way. */ if(domain.core->freeptr != NULL) { alcErrNum = AlcFreeStackFree(domain.core->freeptr); } AlcFree((void *)domain.core); if(alcErrNum != ALC_ER_NONE) { errNum = WLZ_ERR_MEM_FREE; } break; } } } return(errNum); }
void setup_ref_display_list_cb( Widget w, XtPointer client_data, XtPointer call_data) { WlzPlaneDomain *planedmn; WlzThreeDViewStruct *viewStr; WlzErrorNum errNum=WLZ_ERR_NONE; if( globals.obj == NULL || globals.obj->type != WLZ_3D_DOMAINOBJ || globals.ref_display_list == 0){ return; } /* create a new display list */ glDeleteLists(globals.ref_display_list, 1); globals.ref_display_list = glGenLists( (GLsizei) 1 ); planedmn = globals.obj->domain.p; /* create the reference object 3D display DisplayList */ glNewList( globals.ref_display_list, GL_COMPILE ); glBegin(GL_LINES); glColor3f(1.0, 0.0, 0.0); glIndexi( (int) HGU_XGetColorPixel(globals.dpy, globals.cmap, 1.0, 0.0, 0.0) ); glVertex3i(planedmn->kol1, planedmn->line1, planedmn->plane1); glVertex3i(planedmn->lastkl, planedmn->line1, planedmn->plane1); glVertex3i(planedmn->kol1, planedmn->line1, planedmn->lastpl); glVertex3i(planedmn->lastkl, planedmn->line1, planedmn->lastpl); glVertex3i(planedmn->kol1, planedmn->lastln, planedmn->plane1); glVertex3i(planedmn->lastkl, planedmn->lastln, planedmn->plane1); glVertex3i(planedmn->kol1, planedmn->lastln, planedmn->lastpl); glVertex3i(planedmn->lastkl, planedmn->lastln, planedmn->lastpl); glColor3f(0.0, 1.0, 0.0); glIndexi( (int) HGU_XGetColorPixel(globals.dpy, globals.cmap, 0.0, 1.0, 0.0) ); glVertex3i(planedmn->kol1, planedmn->line1, planedmn->plane1); glVertex3i(planedmn->kol1, planedmn->lastln, planedmn->plane1); glVertex3i(planedmn->kol1, planedmn->line1, planedmn->lastpl); glVertex3i(planedmn->kol1, planedmn->lastln, planedmn->lastpl); glVertex3i(planedmn->lastkl, planedmn->line1, planedmn->plane1); glVertex3i(planedmn->lastkl, planedmn->lastln, planedmn->plane1); glVertex3i(planedmn->lastkl, planedmn->line1, planedmn->lastpl); glVertex3i(planedmn->lastkl, planedmn->lastln, planedmn->lastpl); glColor3f(0.0, 0.0, 1.0); glIndexi( (int) HGU_XGetColorPixel(globals.dpy, globals.cmap, 0.0, 0.0, 1.0) ); glVertex3i(planedmn->kol1, planedmn->line1, planedmn->plane1); glVertex3i(planedmn->kol1, planedmn->line1, planedmn->lastpl); glVertex3i(planedmn->kol1, planedmn->lastln, planedmn->plane1); glVertex3i(planedmn->kol1, planedmn->lastln, planedmn->lastpl); glVertex3i(planedmn->lastkl, planedmn->line1, planedmn->plane1); glVertex3i(planedmn->lastkl, planedmn->line1, planedmn->lastpl); glVertex3i(planedmn->lastkl, planedmn->lastln, planedmn->plane1); glVertex3i(planedmn->lastkl, planedmn->lastln, planedmn->lastpl); glEnd(); if( globals.fb_obj && (globals.fb_obj->type == WLZ_3D_DOMAINOBJ) ){ WlzObject *obj1, *boundobj; WlzValues values; int z, step; /* establish the step size */ planedmn = globals.fb_obj->domain.p; step = (planedmn->lastkl - planedmn->kol1) / 6; z = (planedmn->lastln - planedmn->line1) / 6; step = WLZ_MIN(step, z); z = (planedmn->lastpl - planedmn->plane1) / 6; step = WLZ_MIN(step, z); /* set up const z boundaries */ glColor3f(1.0, 1.0, 1.0); glIndexi((int) HGU_XGetColorPixel(globals.dpy, globals.cmap, 1.0, 1.0, 1.0)); (void) glLineWidth( (GLfloat) 2.0 ); for(z=planedmn->plane1+step/2; z <= planedmn->lastpl; z += step) { values.core = NULL; obj1 = WlzMakeMain(WLZ_2D_DOMAINOBJ, planedmn->domains[z - planedmn->plane1], values, NULL, NULL, NULL); if( obj1->domain.core != NULL ) { boundobj = WlzObjToBoundary(obj1, 1, &errNum); if( boundobj != NULL ) { MAOpenGLDisplayBoundList(boundobj->domain.b, (float) z ); WlzFreeObj( boundobj ); } if( errNum != WLZ_ERR_NONE ){ break; } } WlzFreeObj( obj1 ); } (void) glLineWidth( (GLfloat) 1.0 ); /* set up const y boundaries */ if( errNum == WLZ_ERR_NONE ){ glColor3f(1.0, 1.0, 0.0); glIndexi((int) HGU_XGetColorPixel(globals.dpy, globals.cmap, 1.0, 1.0, 0.0)); if((viewStr = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum))){ viewStr->theta = WLZ_M_PI / 2.0; viewStr->phi = WLZ_M_PI / 2.0; viewStr->dist = planedmn->line1 - step/2; errNum = WlzInit3DViewStruct(viewStr, globals.fb_obj); for(z=viewStr->dist+step; (errNum == WLZ_ERR_NONE) && (z <= planedmn->lastln); z += step) { Wlz3DSectionIncrementDistance(viewStr, (double) step); if((obj1 = WlzGetSectionFromObject(globals.fb_obj, viewStr, WLZ_INTERPOLATION_NEAREST, &errNum))){ obj1 = WlzAssignObject(obj1, NULL); boundobj = WlzObjToBoundary(obj1, 1, &errNum); if( boundobj != NULL ) { /* convert boundary coordinates to voxel coordinates */ Wlz3DSectionTransformYBound(boundobj->domain.b, viewStr); MAOpenGLDisplayYBoundList(boundobj->domain.b, (float) z); WlzFreeObj( boundobj ); } WlzFreeObj( obj1 ); } } WlzFree3DViewStruct(viewStr); } } /* set up const x boundaries */ if( errNum == WLZ_ERR_NONE ){ glIndexi((int) HGU_XGetColorPixel(globals.dpy, globals.cmap, 1.0, 1.0, 0.0)); glColor3f(1.0, 1.0, 0.0); if((viewStr = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum))){ viewStr->theta = 0.0; viewStr->phi = WLZ_M_PI / 2.0; viewStr->dist = planedmn->kol1 - step/2; errNum = WlzInit3DViewStruct(viewStr, globals.fb_obj); for(z=viewStr->dist+step; (errNum == WLZ_ERR_NONE) && (z <= planedmn->lastkl); z += step) { Wlz3DSectionIncrementDistance(viewStr, (double) step); if((obj1 = WlzGetSectionFromObject(globals.fb_obj, viewStr, WLZ_INTERPOLATION_NEAREST, &errNum))){ obj1 = WlzAssignObject(obj1, NULL); boundobj = WlzObjToBoundary(obj1, 1, &errNum); if( boundobj != NULL ) { /* convert boundary coordinates to voxel coordinates */ Wlz3DSectionTransformXBound(boundobj->domain.b, viewStr); MAOpenGLDisplayXBoundList(boundobj->domain.b, (float) z); WlzFreeObj( boundobj ); } WlzFreeObj( obj1 ); } } WlzFree3DViewStruct(viewStr); } } } if( errNum == WLZ_ERR_NONE ){ glIndexi( (int) HGU_XGetColorPixel(globals.dpy, globals.cmap, 1.0, 1.0, 1.0) ); glColor3f(1.0, 1.0, 1.0); glEndList(); WLZ_VTX_3_SET(globals.bbox_vtx, planedmn->kol1 - 2.0, planedmn->line1 - 2.0, planedmn->plane1 - 2.0); WLZ_VTX_3_SET(globals.bbox_size, planedmn->lastkl - planedmn->kol1 + 4.0, planedmn->lastln - planedmn->line1 + 4.0, planedmn->lastpl - planedmn->plane1 + 4.0); glFogf(GL_FOG_DENSITY, 0.25/globals.bbox_size.vtX); MAOpenGLDrawScene( globals.canvas ); } else { MAPaintReportWlzError(globals.topl, "setup_ref_display_list_cb", errNum); } return; }
int main(int argc, char **argv) { int option, ok = 1, usage = 0, nVx = 0, inputWlz = 0, testFlg = 0; WlzVertexP vxp; WlzDVertex3 up, nrm, pip; WlzObject *outObj = NULL; WlzVertexType vtxType = WLZ_VERTEX_D3; WlzObjectType outObjType = WLZ_NULL; WlzDomain outDomain; WlzValues outValues; WlzErrorNum errNum = WLZ_ERR_NONE; WlzFitPlaneAlg alg = WLZ_FITPLANE_ALG_SVD; WlzFitPlaneOut out = WLZ_FITPLANE_OUT_SECTION; char *inFileStr = NULL, *outFileStr = NULL; const char *errMsg; static char optList[] = "ahstTwA:o:u:", fileStrDef[] = "-"; /* These vertices correspond to a plane in EMA27 with * fp=0,0,0, dist=123, pitch=123, yaw=45 which should give * the following text output: * -0.593865 -0.592398 0.544417 211.6 137.7 154.4 57.0152 224.929 */ const int testVxCount = 10; static WlzDVertex3 testVx[10] = { {181,62,39}, {105,192,97}, {281,185,282}, {342,81,235}, {118,139,54}, {221,146,173}, {312,147,274}, {225,69,94}, {190,148,142}, {141,208,154} }; opterr = 0; vxp.v = NULL; up.vtX = 0.0; up.vtY = 0.0; up.vtZ = 0.0; outDomain.core = NULL; outValues.core = NULL; inFileStr = fileStrDef; outFileStr = fileStrDef; while(ok && ((option = getopt(argc, argv, optList)) != -1)) { switch(option) { case 'A': if(WlzStringMatchValue((int *)&alg, optarg, "SVD", WLZ_FITPLANE_ALG_SVD, NULL) == 0) { usage = 1; ok = 0; } break; case 'a': out = WLZ_FITPLANE_OUT_AFFINE; break; case 'o': outFileStr = optarg; break; case 's': out = WLZ_FITPLANE_OUT_SECTION; break; case 't': out = WLZ_FITPLANE_OUT_TEXT; break; case 'T': testFlg = 1; break; case 'u': if(sscanf(optarg, "%lg,%lg,%lg", &(up.vtX), &(up.vtY), &(up.vtZ)) < 3) { usage = 1; ok = 0; } break; case 'w': inputWlz = 1; break; case 'h': default: usage = 1; ok = 0; break; } } if(ok && (optind < argc)) { if((optind + 1) != argc) { usage = 1; ok = 0; } else { inFileStr = *(argv + optind); } } if(ok) { if(testFlg) { nVx = testVxCount; vxp.d3 = testVx; } else { FILE *fP = NULL; if((*inFileStr == '\0') || ((fP = (strcmp(inFileStr, "-")? fopen(inFileStr, "r"): stdin)) == NULL)) { ok = 0; errNum = WLZ_ERR_READ_EOF; } else { if(inputWlz) { WlzObject *inObj = NULL; if((inObj = WlzReadObj(fP, &errNum)) != NULL) { WlzVertexP inVxP; WlzVertexType inVxType; inVxP = WlzVerticesFromObj(inObj, NULL, &nVx, &inVxType, &errNum); if(errNum == WLZ_ERR_NONE) { switch(inVxType) { case WLZ_VERTEX_I3: /* FALLTHROUGH */ case WLZ_VERTEX_F3: /* FALLTHROUGH */ case WLZ_VERTEX_D3: vtxType = inVxType; vxp.v = inVxP.v; inVxP.v = NULL; break; default: errNum = WLZ_ERR_OBJECT_TYPE; break; } AlcFree(inVxP.v); } (void )WlzFreeObj(inObj); } } else { size_t nM = 0, nN = 0; double **inData = NULL; if((AlcDouble2ReadAsci(fP, &inData, &nM, &nN) != ALC_ER_NONE) || (nM < 1) || (nN != 3)) { ok = 0; errNum = WLZ_ERR_PARAM_DATA; } (void )fclose(fP); if(ok) { nVx = nM; if((vxp.d3 = (WlzDVertex3 *) AlcMalloc(nVx * sizeof(WlzDVertex3))) == NULL) { ok = 0; errNum = WLZ_ERR_MEM_ALLOC; } } if(ok) { int idx; for(idx = 0; idx < nVx; ++idx) { vxp.d3[idx].vtX = inData[idx][0]; vxp.d3[idx].vtY = inData[idx][1]; vxp.d3[idx].vtZ = inData[idx][2]; } } (void )AlcDouble2Free(inData); } if(strcmp(inFileStr, "-")) { (void )fclose(fP); } } if(!ok) { (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed to input vertices from file %s (%s).\n", *argv, inFileStr, errMsg); } } } if(ok) { switch(alg) { case WLZ_FITPLANE_ALG_SVD: errNum = WlzFitPlaneSVD(vtxType, nVx, vxp, &pip, &nrm); if(errNum == WLZ_ERR_NONE) { outDomain.vs3d = Wlz3DViewStructFromNormal(nrm, pip, up, &errNum); } break; default: errNum = WLZ_ERR_PARAM_TYPE; break; } if(errNum == WLZ_ERR_NONE) { switch(out) { case WLZ_FITPLANE_OUT_AFFINE: outObjType = WLZ_AFFINE_TRANS; { WlzAffineTransform *tr = NULL; errNum = WlzInit3DViewStructAffineTransform(outDomain.vs3d); if(errNum == WLZ_ERR_NONE) { tr = WlzAffineTransformCopy(outDomain.vs3d->trans, &errNum); (void )WlzFree3DViewStruct(outDomain.vs3d); outDomain.t = tr; } } break; case WLZ_FITPLANE_OUT_SECTION: outObjType = WLZ_3D_VIEW_STRUCT; break; case WLZ_FITPLANE_OUT_TEXT: outObjType = WLZ_NULL; break; default: errNum = WLZ_ERR_PARAM_TYPE; break; } } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed to compute best fit plane (%s).\n", *argv, errMsg); } } if((testFlg == 0) && (vxp.v != NULL)) { AlcFree(vxp.v); } if(ok && (outObjType != WLZ_NULL)) { outObj = WlzMakeMain(outObjType, outDomain, outValues, NULL, NULL, &errNum); if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed to make output object (%s).\n", *argv, errMsg); } } if(ok) { FILE *fP = NULL; errNum = WLZ_ERR_WRITE_EOF; if((fP = (strcmp(outFileStr, "-")? fopen(outFileStr, "w"): stdout)) != NULL) { if(outObjType == WLZ_NULL) { double theta, phi; theta = outDomain.vs3d->theta * 180.0 / ALG_M_PI; phi = outDomain.vs3d->phi * 180.0 / ALG_M_PI; while(theta < 0.0) { theta += 360.0; } while(phi < 0.0) { phi += 360.0; } if(fprintf(fP, "%g %g %g %g %g %g %g %g\n", nrm.vtX, nrm.vtY, nrm.vtZ, pip.vtX, pip.vtY, pip.vtZ, phi, theta) > 16) { errNum = WLZ_ERR_NONE; } } else { errNum = WlzWriteObj(fP, outObj); } } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed to write output object " "to file %s (%s).\n", *argv, outFileStr, errMsg); } if(fP && strcmp(outFileStr, "-")) { (void )fclose(fP); } } if(outObj) { WlzFreeObj(outObj); } if(usage) { (void )fprintf(stderr, "Usage: %s%s%s%s", *argv, " [-a] [-A <alg>] [-o <output file>] [-h]\n" "\t\t[-s] [-t] [-T] [-u<x>,<y>,<z>] [<input file>]\n" "Version: ", WlzVersion(), "\n" "Options:\n" " -A Force the algorithm selection, valid algorithms are:\n" " SVD Singular Value Decomposition based least squares\n" " (the default).\n" " -a Output is an affine transform.\n" " -h Help, prints this usage message.\n" " -o Output file name.\n" " -s Output is a 3D view struct (default).\n" " -t Output is a text description of the plane.\n" " -T Use test data, probably only useful for debugging.\n" " -u Up vector, the default is (0, 0, 0) which implies that\n" " the up vector is not explicitly set.\n" " -w Input is a Woolz object rather than ascii vertices.\n" "Calculates the best (least squares) plane through the given input\n" "vertices or object.\n" "Text output is of the form:\n" " <nx> <ny> <nz> <cx> <cy> <cz> <pitch> <yaw>\n" "where these are the normal components, centroid location in the plane\n" "and the Euler angles (in degrees).\n" "The input vertices are read from an ascii file with the format:\n" " <vtx x> <vtx y> <vtx z>\n" "The input data are read from stdin and the output object is written\n" "to stdout unless the filenames are given.\n"); } return(!ok); }
int main(int argc, char **argv) { FILE *inFile = NULL; /* used to read Woolz object */ FILE *outFile = NULL; /* used to read Woolz object */ int i,j,k=0, m; /* , l1, label[3], individual[4] */ int option; int TotalN; /* numChar, numChar1, */ /* int outputAutoMeshVTK = 0, outputAutoMeshWLZ = 0, outputTransformedMeshWLZ = 0, outputCutPlaneAndCorrepSurfaceVTK = 0; */ /* WARP = 1 */ /* int basisFnPolyOrder = 3; */ int Inumber, num; int globalCycle; /* int binObjFlag; */ int centorOfMass = 1; int numOf2DWlzFiles = 0, numOfSampleBibFiles = 0; /* int initialn0, endNum0,initialn1, endNum1; */ int BibFileIndex[50]; /* double zConst = 0.; */ /* double mass = 0.0; */ /* char under ='_'; */ /* char ctemp; */ char *inFileStr, *inFileStr1, *outFileStr; /* *inFileStr3, */ char *inFileStrw, *outputBibFilesDir; /* , inFileStrSec[100]; */ char TwoDImageFilesNameList[1000][120]; char TwoDImagePureFilesNameList[1000][70]; char PureBibFilesNameList[700][70]; char SampleBibFilesNameList[100][120]; char SampleBibPureFilesName[100][70]; char SampleBibFilesDir[100]; char TwoDImageFilesDir[100]; char *List2DImageFilesStr, *SampleBibFilesStr; /* char *cstr; */ /* const char *errMsg; */ /* WlzDVertex2 cMass, cMassS; */ WlzErrorNum errNum = WLZ_ERR_NONE; /* WlzInterpolationType interp = WLZ_INTERPOLATION_NEAREST; Use the nearest neighbour */ WlzThreeDViewStruct *wlzViewStr, *wlzViewStr1, *wlzViewStrInter; /* AlcErrno alcErr = ALC_ER_NONE; */ WlzObject *WObjS;/*, *WObj2DS, *WObj2D;*/ /* WlzObjectType wtp = WLZ_3D_DOMAINOBJ; */ /* read the argument list and check for an input file */ static char optList[] = "i:I:f:w:o:d:z:M:m:n:r:R:L:B:h", opterr = 0; while( (option = getopt(argc, argv, optList)) != EOF ) { switch( option ) { case 'h': usage(argv[0]); return(0); case 'i': inFileStr = optarg; /* outFileStr = optarg; */ break; case 'I': inFileStr1 = optarg; break; case 'L': List2DImageFilesStr = optarg; break; case 'B': SampleBibFilesStr = optarg; break; case 'w': inFileStrw = optarg; break; case 'n': if(sscanf(optarg, "%d", &num) != 1) { printf("read error"); exit(1); } break; case 'o': outFileStr = optarg; break; case 'd': outputBibFilesDir = optarg; break; default: return(0); } } /* Read 2D Wlz files List */ printf("Read 2D Wlz file list\n"); if((inFile = fopen(List2DImageFilesStr, "r")) == NULL ) { printf("cannot open the 2D image files list file.\n"); exit(1); } i=0; /* get the number of files */ while(!feof(inFile)){ fscanf(inFile, "%s", *(TwoDImageFilesNameList + i )); /* printf("%s\n", *(TwoDImageFilesNameList + i ) ); */ i++; } fclose(inFile); inFile = NULL; numOf2DWlzFiles = i-1; printf("number of files = %d\n", numOf2DWlzFiles ); /* extract pure wlz filename without directory */ printf("extract pure wlz filename without directory\n"); for(m=0; m<numOf2DWlzFiles; m++) { for(i=0; i<sizeof(TwoDImageFilesNameList[m]); i++){ if( TwoDImageFilesNameList[m][i] == (char )NULL ) break; if( TwoDImageFilesNameList[m][i] == '/' ) k = i; } if(k != 0) k++; for(j=k; j<i; j++) { TwoDImagePureFilesNameList[m][j-k] = TwoDImageFilesNameList[m][j]; PureBibFilesNameList[m][j-k] = TwoDImageFilesNameList[m][j]; } TwoDImagePureFilesNameList[m][j-k] = (char ) NULL; PureBibFilesNameList[m][j-k] = (char ) NULL; PureBibFilesNameList[m][j-k-3] = 'b'; PureBibFilesNameList[m][j-k-2] = 'i'; PureBibFilesNameList[m][j-k-1] = 'b'; /* extract directory */ if(m == 0) { for(j=0; j<k; j++) { TwoDImageFilesDir[j] = TwoDImageFilesNameList[m][j]; } TwoDImageFilesDir[j] = (char ) NULL; printf("I_DIR %s\n",TwoDImageFilesDir ); } printf("%s\n", TwoDImagePureFilesNameList[m]); } /* changeToBibFileNamse */ /*--- Read Sample bib File name list ----*/ if((inFile = fopen(SampleBibFilesStr, "r")) == NULL ) { printf("cannot open the sample bib files list file.\n"); exit(1); } i=0; while(!feof(inFile)){ fscanf(inFile, "%s", SampleBibFilesNameList[i]); printf("%s\n", SampleBibFilesNameList[i]); i++; } fclose(inFile); inFile = NULL; numOfSampleBibFiles = i-1; printf("number of files = %d\n", numOfSampleBibFiles ); /* extract pure sample bib filename without directory */ printf("extract pure sample bib filename without directory\n"); for(m=0; m<numOfSampleBibFiles; m++) { for(i=0; i<sizeof(SampleBibFilesNameList[m]); i++){ if( SampleBibFilesNameList[m][i] == (char ) NULL ) break; if( SampleBibFilesNameList[m][i] == '/' ) k = i; } if(k != 0) k++; for(j=k; j<i; j++) { SampleBibPureFilesName[m][j-k] = SampleBibFilesNameList[m][j]; } SampleBibPureFilesName[m][j-k] = (char ) NULL; /* extract directory */ if(m == 0) { for(j=0; j<k; j++) { SampleBibFilesDir[j] = SampleBibFilesNameList[m][j]; } SampleBibFilesDir[j] = (char) NULL; printf("B_DIR %s\n",SampleBibFilesDir); } printf("%s\n", SampleBibPureFilesName[m]); } /*---------- extract the bib File number ----------- */ for(i=0; i<numOfSampleBibFiles; i++) { BibFileIndex[i] = -1; for(m=0; m<numOf2DWlzFiles; m++) { /* printf("%s %s\n", PureBibFilesNameList[m], SampleBibPureFilesName[i] ); */ if(strcmp(PureBibFilesNameList[m], SampleBibPureFilesName[i] ) == 0) { BibFileIndex[i] = m; break; } } printf("m = %d\n",BibFileIndex[i]); } centorOfMass = 0; if(centorOfMass) { /* read Woolz object */ if((inFile = fopen(inFileStrw, "r")) == NULL ) { printf("cannot open the input woolz file.\n"); exit(1); } if( !(WObjS = WlzReadObj(inFile, &errNum) ) ) { printf("input Woolz Object Error.\n"); fclose(inFile); exit(1); } fclose(inFile); inFile = NULL; } /* read Section viewer parameters */ centorOfMass = 1; if(centorOfMass) { wlzViewStr = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, NULL); wlzViewStr1 = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, NULL); wlzViewStrInter = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, NULL); } /* interpolation */ globalCycle = 0; while(globalCycle < numOfSampleBibFiles - 1) { printf("%d\n",globalCycle ); errNum = ReadBibFile(inFile, SampleBibFilesNameList[globalCycle], wlzViewStr ); errNum = ReadBibFile(inFile, SampleBibFilesNameList[globalCycle+1], wlzViewStr1 ); errNum = ReadBibFile(inFile, SampleBibFilesNameList[globalCycle], wlzViewStrInter ); TotalN = BibFileIndex[globalCycle+1] - BibFileIndex[globalCycle]; /* cycle through between sample bib file */ j = BibFileIndex[globalCycle] + 1; k = BibFileIndex[globalCycle+1]; printf("NNNN: %d %d\n",j,k ); i=j; while ( i < k ) { Inumber = i - BibFileIndex[globalCycle]; /* linear interpolations */ errNum = LinearInterpolations(wlzViewStr, wlzViewStr1, wlzViewStrInter, Inumber, TotalN); /* change the fixed point to (0 0 0) */ errNum = ChangeFixedPoint(wlzViewStrInter, 0., 0., 0.); /* write Section viewer parameters */ printf("%s\n", PureBibFilesNameList[i]); errNum = WriteBibFile(outFile, PureBibFilesNameList[i], inFileStrw, TwoDImageFilesNameList[i], wlzViewStrInter); i++; } globalCycle++; } /* Now cover the orginal input bib files with new */ globalCycle = 0; while(globalCycle < numOfSampleBibFiles) { i = BibFileIndex[globalCycle]; errNum = ReadBibFile(inFile, SampleBibFilesNameList[globalCycle], wlzViewStr ); errNum = ReadBibFile(inFile, SampleBibFilesNameList[globalCycle], wlzViewStr1 ); errNum = ReadBibFile(inFile, SampleBibFilesNameList[globalCycle], wlzViewStrInter ); errNum = LinearInterpolations(wlzViewStr, wlzViewStr, wlzViewStrInter, 1, 1); /* change the fixed point to (0 0 0) */ errNum = ChangeFixedPoint(wlzViewStrInter, 0., 0., 0.); errNum = WriteBibFile(outFile, PureBibFilesNameList[i], inFileStrw, TwoDImageFilesNameList[i], wlzViewStrInter); globalCycle++; } /* */ centorOfMass = 0; if(centorOfMass) { WlzFreeObj(WObjS); } centorOfMass = 1; if(centorOfMass) { WlzFree3DViewStruct(wlzViewStr); WlzFree3DViewStruct(wlzViewStr1); WlzFree3DViewStruct(wlzViewStrInter); } return ( 0 ); }
int main(int argc, char *argv[]) { int option, ok = 1, usage = 0, dim = 2, section = 0, timer = 0; double yaw = 0.0, pitch = 0.0, roll = 0.0, dist = 0.0, scale = 1.0; WlzPixelV bgdV; WlzGreyType gType; WlzDVertex3 up, fixed; WlzInterpolationType interp = WLZ_INTERPOLATION_NEAREST; WlzThreeDViewMode mode = WLZ_UP_IS_UP_MODE; WlzErrorNum errNum = WLZ_ERR_NONE; FILE *fP = NULL; WlzObject *inObj = NULL, *tlObj = NULL; char *inFileStr, *outFileStr, *secFileStr; struct timeval times[3]; const char *errMsg; const size_t tlSz = 4096; static char optList[] = "hsto:S:", inFileStrDef[] = "-"; opterr = 0; outFileStr = NULL; inFileStr = inFileStrDef; secFileStr = inFileStrDef; gType = WLZ_GREY_UBYTE; bgdV.type = WLZ_GREY_UBYTE; bgdV.v.ubv = 0; up.vtX = up.vtY = 0.0; up.vtZ = -1.0; fixed.vtX = fixed.vtY = fixed.vtZ = 0.0; while(ok && ((option = getopt(argc, argv, optList)) != -1)) { switch(option) { case 'o': outFileStr = optarg; break; case 's': section = 1; break; case 'S': secFileStr = optarg; break; case 't': timer = 1; break; case 'h': /* FALLTHROUGH */ default: usage = 1; break; } } if((usage == 0) && (optind < argc)) { if((optind + 1) != argc) { usage = 1; } else { inFileStr = *(argv + optind); } } ok = !usage; if(ok) { fP = NULL; errNum = WLZ_ERR_READ_EOF; if(((fP = (strcmp(inFileStr, "-")? fopen(inFileStr, "r"): stdin)) == NULL) || ((inObj= WlzAssignObject(WlzReadObj(fP, &errNum), NULL)) == NULL)) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: Failed to read object from file %s (%s).\n", *argv, inFileStr, errMsg); } if(fP && strcmp(inFileStr, "-")) { (void )fclose(fP); } } if(ok) { if(inObj == NULL) { errNum = WLZ_ERR_OBJECT_NULL; } else if(inObj->domain.core == NULL) { errNum = WLZ_ERR_DOMAIN_NULL; } else { switch(inObj->type) { case WLZ_2D_DOMAINOBJ: dim = 2; break; case WLZ_3D_DOMAINOBJ: dim = 3; break; default: errNum = WLZ_ERR_OBJECT_TYPE; break; } } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: invalid object read from file %s (%s).\n", *argv, inFileStr, errMsg); } } if(ok) { if(timer) { gettimeofday(times + 0, NULL); } tlObj = WlzMakeTiledValuesFromObj(inObj, tlSz, 1, gType, bgdV, &errNum); if(timer) { gettimeofday(times + 1, NULL); timersub(times + 1, times + 0, times + 2); (void )fprintf(stderr, "%s: Elapsed time for WlzMakeTiledValuesFromObj() %gs\n", *argv, times[2].tv_sec + (0.000001 * times[2].tv_usec)); } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: Failed to create object with tiled values (%s).\n", *argv, errMsg); } } if(ok && (outFileStr != NULL)) { if(((fP = (strcmp(outFileStr, "-")? fopen(outFileStr, "w"): stdout)) == NULL) || ((errNum = WlzWriteObj(fP, tlObj)) != WLZ_ERR_NONE)) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: Failed to write tiled object to file %s (%s).\n", *argv, outFileStr, errMsg); } } if(ok && section && (dim == 3)) { WlzObject *secObj = NULL; WlzThreeDViewStruct *view = NULL; view = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum); if(errNum == WLZ_ERR_NONE) { view->theta = yaw * WLZ_M_PI / 180.0; view->phi = pitch * WLZ_M_PI / 180.0; view->zeta = roll * WLZ_M_PI / 180.0; view->dist = dist; view->fixed = fixed; view->up = up; view->view_mode = mode; view->scale = scale; errNum = WlzInit3DViewStruct(view, tlObj); } if(errNum == WLZ_ERR_NONE) { if(timer) { gettimeofday(times + 0, NULL); } secObj = WlzGetSubSectionFromObject(tlObj, NULL, view, interp, NULL, &errNum); if(timer) { gettimeofday(times + 1, NULL); timersub(times + 1, times + 0, times + 2); (void )fprintf(stderr, "%s: Elapsed time for WlzGetSubSectionFromObject() %gs\n", *argv, times[2].tv_sec + (0.000001 * times[2].tv_usec)); } fP = NULL; errNum = WLZ_ERR_WRITE_EOF; if(((fP = (strcmp(secFileStr, "-")? fopen(secFileStr, "w"): stdout)) == NULL) || ((errNum = WlzWriteObj(fP, secObj)) != WLZ_ERR_NONE)) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: Failed to write section object to file %s (%s).\n", *argv, secFileStr, errMsg); } if(fP && strcmp(secFileStr, "-")) { (void )fclose(fP); } } (void )WlzFree3DViewStruct(view); (void )WlzFreeObj(secObj); } (void )WlzFreeObj(tlObj); (void )WlzFreeObj(inObj); if(usage) { (void )fprintf(stderr, "Usage: %s%s", *argv, " [-o<output object>] [-h] [-o <file>] [-s] [-S <file>] [-t]\n" " [<input object>]\n" "Copied the input object to an object with tiled values.\n" "Options:\n" " -h Prints this usage information.\n" " -o Output tiled object.\n" " -s Cut section from tiled object.\n" " -S Output file for section object.\n" " -t Output timing information.\n"); } return(!ok); }
int main(int argc, char **argv) { int tI, errIdx, option, keep2D = 0, ok = 1, usage = 0; WlzDDOVxSzSrc voxSzSrc = WLZDDO_VSS_UNIT; WlzDVertex2 org; WlzThreeDViewStruct *view = NULL; WlzErrorNum errNum = WLZ_ERR_NONE; WlzObject *dwnObj = NULL, *refObj = NULL; FILE *fP = NULL; char *errMsg0, *cmdStr = NULL, *refFileStr = NULL, *outFileStr, *inFileStr; double voxSz[3]; const char *errMsg; static char optList[] = "a:b:d:E:f:g:m:o:r:s:u:2eh", outFileStrDef[] = "-", inFileStrDef[] = "-"; opterr = 0; errMsg = errMsg0 = ""; org.vtX = org.vtY = 0.0; inFileStr = inFileStrDef; outFileStr = outFileStrDef; voxSz[0] = voxSz[1] = voxSz[2] = 1.0; if((view = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum)) == NULL) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed to create view structure (%s)\n", *argv, errMsg); } if(ok) { view->dist = 0.0; view->scale = 1.0; view->ref_obj = NULL; view->view_mode = WLZ_UP_IS_UP_MODE; view->phi = view->theta = view->zeta = 0.0; view->up.vtX = view->up.vtY = 0.0; view->up.vtZ = 1.0; view->fixed.vtX = view->fixed.vtY = view->fixed.vtZ = 0.0; while((usage == 0) && ((option = getopt(argc, argv, optList)) != -1)) { switch(option) { case '2': keep2D = 1; break; case 'a': usage = WlzDrawDomObjScanTriple(optarg, &(view->phi), &(view->theta), &(view->zeta)) < 1; break; case 'e': voxSzSrc = WLZDDO_VSS_OBJ; break; case 'E': voxSzSrc = WLZDDO_VSS_GVN; usage = WlzDrawDomObjScanTriple(optarg, &(voxSz[0]), &(voxSz[1]), &(voxSz[2])) < 1; break; case 'f': usage = WlzDrawDomObjScanTriple(optarg, &(view->fixed.vtX), &(view->fixed.vtY), &(view->fixed.vtZ)) < 1; break; case 'd': usage = sscanf(optarg, "%lg", &(view->dist)) != 1; break; case 'b': usage = WlzDrawDomObjReadView(optarg, view, &errMsg0) != WLZ_ERR_NONE; if(usage) { (void )fprintf(stderr, "%s: failed to read view parameters from file " "%s (%s)\n", *argv, optarg, errMsg0); } break; case 'm': if(WlzStringMatchValue(&tI, optarg, "up-is-up", WLZ_UP_IS_UP_MODE, "statue", WLZ_STATUE_MODE, "absolute", WLZ_ZETA_MODE, NULL)) { view->view_mode = (WlzThreeDViewMode )tI; } else { usage = 1; } break; case 'u': usage = WlzDrawDomObjScanTriple(optarg, &(view->up.vtX), &(view->up.vtY), &(view->up.vtZ)) < 1; break; case 'g': usage = WlzDrawDomObjScanPair(optarg, &(org.vtX), &(org.vtY)) < 1; break; case 'o': outFileStr = optarg; break; case 'r': refFileStr = optarg; errNum = WLZ_ERR_READ_EOF; if((refFileStr == NULL) || (*refFileStr == '\0') || ((fP = (strcmp(refFileStr, "-")? fopen(refFileStr, "r"): stdin)) == NULL) || ((refObj = WlzAssignObject( WlzReadObj(fP, &errNum), NULL)) == NULL) || (errNum != WLZ_ERR_NONE)) { usage = 1; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed to read 3D reference object from %s (%s)\n", *argv, refFileStr, errMsg); } if(fP) { if(strcmp(refFileStr, "-")) { (void )fclose(fP); } fP = NULL; } break; case 's': if((cmdStr = AlcStrDup(optarg)) == NULL) { usage = 1; errNum = WLZ_ERR_MEM_ALLOC; } break; case 'h': default: usage = 1; ok = 0; break; } } if((usage == 0) && (cmdStr == NULL)) { if((optind == argc)) { inFileStr = inFileStrDef; } else if(optind + 1 == argc ) { inFileStr = *(argv + optind); } else { usage = 1; } if(usage == 0) { cmdStr = WlzDrawDomObjReadStr(inFileStr, &errNum); } } ok = usage == 0; } if(ok) { switch(voxSzSrc) { case WLZDDO_VSS_UNIT: view->voxelRescaleFlg = 0; view->voxelSize[0] = 1.0f; view->voxelSize[1] = 1.0f; view->voxelSize[2] = 1.0f; break; case WLZDDO_VSS_GVN: view->voxelRescaleFlg = 1; view->voxelSize[0] = (float )WLZ_CLAMP(voxSz[0], FLT_MIN, FLT_MAX); view->voxelSize[1] = (float )WLZ_CLAMP(voxSz[1], FLT_MIN, FLT_MAX); view->voxelSize[2] = (float )WLZ_CLAMP(voxSz[2], FLT_MIN, FLT_MAX); break; case WLZDDO_VSS_OBJ: /* Handled below. */ break; } } if(ok && refObj) { WlzObject *sObj = NULL; WlzThreeDViewStruct *v = NULL; v = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum); if(errNum == WLZ_ERR_NONE) { v->type = view->type; v->fixed = view->fixed; v->theta = view->theta; v->phi = view->phi; v->zeta = view->zeta; v->dist = view->dist; v->scale = view->scale; if(voxSzSrc == WLZDDO_VSS_OBJ) { view->voxelRescaleFlg = 1; if((refObj->type == WLZ_3D_DOMAINOBJ) && (refObj->domain.core != NULL) && (refObj->domain.core->type == WLZ_PLANEDOMAIN_DOMAIN)) { view->voxelSize[0] = refObj->domain.p->voxel_size[0]; view->voxelSize[1] = refObj->domain.p->voxel_size[1]; view->voxelSize[2] = refObj->domain.p->voxel_size[2]; } } v->voxelRescaleFlg = view->voxelRescaleFlg; v->voxelSize[0] = view->voxelSize[0]; v->voxelSize[1] = view->voxelSize[1]; v->voxelSize[2] = view->voxelSize[2]; v->interp = view->interp; v->view_mode = view->view_mode; v->up = view->up; v->fixed_2 = view->fixed_2; v->fixed_line_angle = view->fixed_line_angle; errNum = WlzInit3DViewStruct(v, refObj); } if(errNum == WLZ_ERR_NONE) { sObj = WlzGetSectionFromObject(refObj, v, WLZ_INTERPOLATION_NEAREST, &errNum); } if(errNum == WLZ_ERR_NONE) { if((sObj->type != WLZ_2D_DOMAINOBJ) || (sObj->domain.core == NULL)) { errNum = WLZ_ERR_DOMAIN_DATA; } else { org.vtX += sObj->domain.i->kol1; org.vtY += sObj->domain.i->line1; } } (void )WlzFree3DViewStruct(v); (void )WlzFreeObj(sObj); if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed find offset from reference object (%s).\n", *argv, errMsg); } } if(ok) { dwnObj = WlzDrawDomainObj(org, view, keep2D, cmdStr, &errIdx, &errNum); if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed to draw object in command prior to string\n" "position %d (%s)\n", *argv, errIdx, errMsg); } } if(ok) { errNum = WLZ_ERR_WRITE_EOF; if((fP = (strcmp(outFileStr, "-")? fopen(outFileStr, "w"): stdout)) == NULL) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: failed to open output file (%s).\n", *argv, errMsg); } else { if((errNum = WlzWriteObj(fP, dwnObj)) != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: Failed to write output object (%s).\n", argv[0], errMsg); } } if(fP && strcmp(outFileStr, "-")) { fclose(fP); } } AlcFree(cmdStr); (void )WlzFreeObj(refObj); (void )WlzFree3DViewStruct(view); (void )WlzFreeObj(dwnObj); if(usage) { (void )fprintf(stderr, "Usage: %s%s%s%sExample: %s%s", *argv, " [-2] [-a<pitch,yaw,roll>]\n" " [-f <fx,fy,fz>]\n" " [-d <dist> [-b <view bib file>]\n" " [-m <mode>] [-u<ux,uy,uz>]\n" " [-e] [-E<vx,vy,vz>]\n" " [-g <ox,oy,oz>] [-h] [-o<output>]\n" " [-r <ref object>]\n" " [-s <cmd str>] [<cmd str file>>]\n" "Version: ", WlzVersion(), "\n" "Options:\n" " -2 Ignore the view struct and keep as a 2D object.\n" " -a Viewing angles: pitch (phi), yaw (theta) and roll (zeta),\n" " default 0.0,0.0,0.0.\n" " -f Fixed point position, default 0.0,0.0,0.0.\n" " -d Distance parameter, default 0.0.\n" " -b Bib file with view parameters, e.g. saved from MAPaint.\n" " -m Viewing mode, one of: up-is-up, statue or absolute, default\n" " is up-is-up.\n" " -u Up vector, default 0.0,0.0,1.0.\n" " -e Use object voxel size, default is voxel size 1.0,1.0,1.0.\n" " -E Use supplied voxel size rather than the object voxel size,\n" " default 1.0,1.0,1.0.\n" " -g Origin of the drawing with respect to the 2D Woolz object\n" " cut using the view transform, default 0.0,0.0.\n" " -r Reference object. If given this is must be a 3D spatial domain\n" " object. The object is used to determine an additional offset\n" " for the origin of the 2D plane with respect to the section in 3D\n" " (i.e. it is added to any offset given using the -g option).\n" " -s Drawing command string.\n" " -h Help, prints this usage message.\n" " -o Output file name.\n" "Reads drawing commands from either a string given on the command line,\n" "a file given on the command line or the standard input (in this order\n" "of precidence). The drawing commands are used to create a drawn\n" "section which is placed into 3D using the view transform.\n" "\n" "The command string must have the following syntax:\n" " <command string> = <init command>[<command>]+<end command>\n" " <init command> = <ident>:<version>;\n" " <end command> = END:;\n" " <ident> = WLZ_DRAW_DOMAIN\n" " <version> = 1\n" " <command> = <command name>:[<parameter>[,<parameter>]*];\n" " <command name> = PEN | LINE | CIRCLE\n" "In addition to the init and end commands, the following\n" "drawing commands are recognised:\n" " CIRCLE:<action>:<radius>,<x>,<y>;\n" " LINE:<action>:<width>,<x>,<y>,<x>,<y>;\n" " PEN:<action>,<width>,<x>,<y>[,<x>,<y>]*;\n" "Where:\n" " <action> = DRAW | ERASE\n" "The circle command draws or erases a filled circle which is specified\n" "by it's radius and centre parameters.\n" "The line command draws a rectangle using the given width and end\n" "coordinates of the mid-line.\n" "The pen command draws a polyline which is composed of a series of\n" "rectangular segments, with each segment ending in a semi-circular cap.\n" "The parameters of the pen command are the width and line segment end\n" "point coordinates.\n" "All widths, radii and coordinates may be in any floating point format\n" "recognised by scanf(3).\n" "Other commands may be present provided they have the same syntax\n" "described above, but they will be ignored.\n" "All white space characters are ignored.\n", *argv, " -o out.wlz -s 'WLZ_DRAW_DOMAIN:1; CIRCLE:DRAW,100,200,300; END:;'\n" "This creates a 3D domain object with a single plane at z = 0\n" "which has a domain that is a single circle (radius = 100,\n" "centre = 200,300).\n"); } return(!ok); }
int main(int argc, char *argv[]) { int ok, idx, option, nMsk = 0, nTr = 0, nPart = 1, usage = 0; char *inFileName, *outFileName, *prjFileName, *secFileName; char **mskFileNames = NULL, **trFileNames = NULL; WlzObject *inObj = NULL, *outObj= NULL; WlzObject **mskObjs = NULL, **trObjs = NULL; WlzThreeDViewStruct *prjView = NULL, *secView = NULL; WlzErrorNum errNum = WLZ_ERR_NONE; const char *errMsg; static char optList[] = "ho:p:s:n:m:t:", defFileName[] = "-"; opterr = 0; inFileName = defFileName; outFileName = defFileName; prjFileName = defFileName; secFileName = defFileName; while((usage == 0) && ((option = getopt(argc, argv, optList)) != -1)) { switch(option) { case 'o': outFileName = optarg; break; case 'p': prjFileName = optarg; break; case 's': secFileName = optarg; break; case 'n': if((sscanf(optarg, "%d\n", &nPart) != 1) || (nPart < 1)) { usage = 1; } break; case 'm': if((nMsk = WlzProjDomParseNameList(&mskFileNames, optarg, nPart)) < 1) { usage = 1; } break; case 't': if((nTr = WlzProjDomParseNameList(&trFileNames, optarg, nPart)) < 1) { usage = 1; } break; case 'h': /* FALLTHROUGH */ default: usage = 1; break; } } if(nMsk != nTr) { usage = 0; } if((usage == 0) && (optind < argc)) { if((optind + 1) != argc) { usage = 1; } else { inFileName = *(argv + optind); } } ok = (usage == 0); if(ok) { if(((prjView = WlzAssign3DViewStruct( WlzProjDomReadViewFromNamedFile(prjFileName, &errNum), NULL)) == NULL) || ((secView = WlzAssign3DViewStruct( WlzProjDomReadViewFromNamedFile(secFileName, &errNum), NULL)) == NULL) || ((inObj = WlzAssignObject( WlzProjDomReadObjFromNamedFile(inFileName, &errNum), NULL)) == NULL)) { ok = 0; } if(ok) { if(((trObjs = (WlzObject **) AlcCalloc(nPart, sizeof(WlzObject *))) == NULL) || ((mskObjs = (WlzObject **) AlcCalloc(nPart, sizeof(WlzObject *))) == NULL)) { ok = 0; } } if(ok) { for(idx = 0; idx < nPart; ++idx) { if(strcmp(trFileNames[idx], "null")) { if((trObjs[idx] = WlzAssignObject( WlzProjDomReadObjFromNamedFile(trFileNames[idx], &errNum), NULL)) == NULL) { ok = 0; break; } } } } if(ok) { for(idx = 0; idx < nPart; ++idx) { if(strcmp(mskFileNames[idx], "null")) { if((mskObjs[idx] = WlzAssignObject( WlzProjDomReadObjFromNamedFile(mskFileNames[idx], &errNum), NULL)) == NULL) { ok = 0; break; } } } } if(ok == 0) { (void )fprintf(stderr, "%s: Failed to read input view or object.\n", *argv); } } AlcFree(trFileNames); AlcFree(mskFileNames); if(ok) { outObj = WlzProj3DToSection(inObj, nPart, mskObjs, prjView, nPart, trObjs, secView, &errNum); if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: Failed to create projected section (%s).\n", *argv, errMsg); } } if(ok) { FILE *fP = NULL; errNum = WLZ_ERR_WRITE_EOF; if(((fP = (strcmp(outFileName, "-")? fopen(outFileName, "w"): stdout)) == NULL) || ((errNum = WlzWriteObj(fP, outObj)) != WLZ_ERR_NONE)) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: Failed to write output object (%s).\n", *argv, errMsg); } if(fP && strcmp(outFileName, "-")) { (void )fclose(fP); } } (void )WlzFree3DViewStruct(prjView); (void )WlzFree3DViewStruct(secView); (void )WlzFreeObj(inObj); (void )WlzFreeObj(outObj); if(trObjs) { for(idx = 0; idx < nPart; ++idx) { WlzFreeObj(trObjs[idx]); } AlcFree(trObjs); } if(mskObjs) { for(idx = 0; idx < nPart; ++idx) { WlzFreeObj(mskObjs[idx]); } AlcFree(mskObjs); } if(usage) { (void )fprintf(stderr, "Usage: %s%s%s%s%s%s\n", *argv, " [-h] [-o<out object>] [-p<proj>] [-s[<sec>]\n" " [-n#] [-m<mask1>[,<mask2>,...,<maskn>]]\n" " [-t<tr1>[,<tr2>,...,<trn>]] <input object>\n" "Projects the given input 3D (spatial domain) object into a section,\n" "as used for EMAGE wholemount views.\n" "The input domain may be projected and transformed in parts to allow\n" "the separation of regions that may otherwise be obscured in a\n" "projected view.\n" "Options are:\n" " -h Help - prints this usage message\n" " -o Output file for the projected section view.\n" " -p Projection from the 3D space of the input object and mask\n" " domains onto a plane. This must be defined by a bibfile (as\n" " saved by MAPaint).\n" " -s Section transform which maps the plane back into a 3D space.\n" " This must be defined by a bibfile (as saved by MAPaint).\n" " -n The number of parts to be used for the projection.\n" " If the number of parts is one (which is the default) then\n" " no mask is required. In this case the default in-plane\n" " transform is the identity transform.\n" " -m Mask domains for each of the parts. If the mask is to cover\n" " the whole of the input object's domain then the string\n" " \"null\" (without the quotes) may be used.\n" " -t Transforms withing the plane for each part. If the identity\n" " transform is required then the string \"null\" (without\n" " the quotes) may be used.\n" "The list of masks and in-plane transforms should be comma separated\n" "and a missing string represents either the universal domain or an\n" "identity transform.\n" "Examples:\n", *argv, " -o out.wlz -p prj.bib -s sec.bib -n 2 \\\n" " -m body-msk.wlz,tail-msk.wlz \\\n" " -t body-tr.wlz,tail-tr.wlz domain.wlz\n" "The 3D domain in the file domain.wlz is masked using the 3D domains\n" "read from the files body-msk.wlz and tail-msk.wlz. The resulting\n" "domains are projected onto a plane using the projection defined in\n" "the bibfile prj.bib. Each of these projected domains is then\n" "transformed independently using the transforms read from the files\n" "body-tr.wlz and tail-tr.wlz. The union of these transformed 2D\n" "domains is then made a section defined by the section transform\n" "read from the bibfile sec.bib.\n", *argv, " -o out.wlz -p prj.bib -s sec.bib domain.wlz\n" "The 3D domain in the file domain.wlz is projected onto a plane\n" "using the projecttion transform defined in the bibfile prj.bib\n" "this is then made a section defined by the section transform\n" "read from the bibfile sec.bib.\n"); } exit(!ok); }
int main(int argc, char **argv) { FILE *inFile = NULL; /* used to read Woolz object */ int i,j,k=0, m; int option; int startJ; int cycleI, cycleNext; double ntnm,nfnm,nsnm; int numOf2DWlzFiles = 0, numOfBibFiles = 0; int ok, usage1, idx; double deltaZ; double sx=0,sy=0,sz=0, fx=0,fy=100,fz=0, tx=100,ty=0,tz=0; double Sx=0,Sy=0,Sz=60, Fx=0,Fy=100,Fz=60, Tx=100,Ty=0,Tz=60; double lengthTS; char *inFileStr, *inFileStr1, *outFileStr; char *inFileStrw=NULL, *outputWlzFilesDir=NULL; char TwoDImageFilesNameList[700][120]; char TwoDImagePureFilesNameList[700][120]; char warpedFilesNameList[700][120]; char BibFilesNameList[700][120]; char TwoDImageFilesDir[120]; char *List2DImageFilesStr= NULL, *ListBibFilesStr= NULL; WlzVertex vs, vt, vf, vS, vT, vF; WlzVertex vs1, vt1, vf1, vsp, vtp, vfp, vST; WlzVertex vsr, vtr, vfr; WlzVertex ns, nf, nt, nsp, nfp, ntp, nz,nm; WlzDVertex2 *vtxVec1; WlzErrorNum errNum = WLZ_ERR_NONE; WlzThreeDViewStruct *wlzViewStr, *wlzViewStr1; WlzObject *WObjS; char *cutStr[3]; double cutVal[3]; /* read the argument list and check for an input file */ static char optList[] = "i:I:w:o:d:s:S:f:F:t:T:M:n:r:R:L:B:h",opterr = 0; ok = 1; while( (option = getopt(argc, argv, optList)) != EOF ) { switch( option ) { case 'h': usage(argv[0]); return(0); case 'i': inFileStr = optarg; /* outFileStr = optarg; */ break; case 'I': inFileStr1 = optarg; break; case 'L': List2DImageFilesStr = optarg; break; case 'B': ListBibFilesStr = optarg; break; case 'w': inFileStrw = optarg; break; case 'n': if(sscanf(optarg, "%d", &startJ) != 1) { printf("read error"); exit(1); } break; case 's': case 'f': case 't': case 'S': case 'F': case 'T': if(optarg) { while(*optarg && isspace(*optarg)) { ++optarg; } if(*optarg == ',') { cutStr[0] = NULL; cutStr[1] = strtok(optarg, ","); cutStr[2] = strtok(optarg, ","); } else { cutStr[0] = strtok(optarg, ","); cutStr[1] = strtok(NULL, ","); cutStr[2] = strtok(NULL, ","); } if((cutStr[0] == NULL) && (cutStr[1] == NULL) && (cutStr[2] == NULL) ) { usage1 = 1; ok = 0; } else { idx = 0; while(ok && (idx < 3)) { if(cutStr[idx] && (sscanf(cutStr[idx], "%lg", cutVal + idx) != 1)) { usage1 = 1; ok = 0; } ++idx; } } } if(ok) { switch(option) { case 's': sx = (double) cutVal[0]; sy = (double) cutVal[1]; sz = (double) cutVal[2]; break; case 'f': fx = (double) cutVal[0]; fy = (double) cutVal[1]; fz = (double) cutVal[2]; break; case 't': tx = (double) cutVal[0]; ty = (double) cutVal[1]; tz = (double) cutVal[2]; break; case 'S': Sx = (double) cutVal[0]; Sy = (double) cutVal[1]; Sz = (double) cutVal[2]; break; case 'F': Fx = (double) cutVal[0]; Fy = (double) cutVal[1]; Fz = (double) cutVal[2]; break; case 'T': Tx = (double) cutVal[0]; Ty = (double) cutVal[1]; Tz = (double) cutVal[2]; break; } } break; case 'o': outFileStr = optarg; break; case 'd': outputWlzFilesDir = optarg; break; default: return(0); } } printf("t: %f %f %f\n",tx,ty, tz ); printf("T: %f %f %f\n",Tx,Ty, Tz ); /*------- allocate memory --------*/ if ( ((vtxVec1 = (WlzDVertex2 *)AlcCalloc(sizeof(WlzDVertex2), 3)) == NULL) ) { errNum = WLZ_ERR_MEM_ALLOC; } /* ------Read 2D Wlz files List------- */ printf("Read 2D Wlz file list\n"); if((inFile = fopen(List2DImageFilesStr, "r")) == NULL ) { printf("cannot open the 2D image files list file.\n"); exit(1); } i=0; /* get the number of files */ while(!feof(inFile)){ fscanf(inFile, "%s", *(TwoDImageFilesNameList + i )); /* printf("%s\n", *(TwoDImageFilesNameList + i ) ); */ i++; } fclose(inFile); inFile = NULL; numOf2DWlzFiles = i-1; printf("number of files = %d\n", numOf2DWlzFiles ); /* extract pure wlz filename without directory */ printf("extract pure wlz filename without directory\n"); for(m=0; m<numOf2DWlzFiles; m++) { for(i=0; i<sizeof(TwoDImageFilesNameList[m]); i++){ if( TwoDImageFilesNameList[m][i] == (char) NULL ) break; if( TwoDImageFilesNameList[m][i] == '/' ) k = i; } if(k != 0) k++; for(j=k; j<i; j++) { TwoDImagePureFilesNameList[m][j-k] = TwoDImageFilesNameList[m][j]; warpedFilesNameList[m][j-k] = TwoDImageFilesNameList[m][j]; } TwoDImagePureFilesNameList[m][j-k] = ( char ) NULL; warpedFilesNameList[m][j-k] = ( char ) NULL; /* extract directory */ if(m == 0) { for(j=0; j<k; j++) { TwoDImageFilesDir[j] = TwoDImageFilesNameList[m][j]; } TwoDImageFilesDir[j] = ( char ) NULL; printf("I_DIR %s\n",TwoDImageFilesDir ); } printf("%s\n", TwoDImagePureFilesNameList[m]); } /*--- Read bib File name list ----*/ if((inFile = fopen(ListBibFilesStr, "r")) == NULL ) { printf("cannot open the 2D image files list file.\n"); exit(1); } i=0; while(!feof(inFile)){ fscanf(inFile, "%s", BibFilesNameList[i]); printf("%s\n", BibFilesNameList[i]); i++; } fclose(inFile); inFile = NULL; numOfBibFiles = i-1; printf("number of files bib files = %d\n", numOfBibFiles ); /* check whether the number of bib files is the same as number of Wlz 2D sections */ if(numOfBibFiles != numOf2DWlzFiles ) { printf("Number of 2D woolz files and number of bib files are different\n"); exit(1); } /* get the output file namelist */ i = (int) strlen( (const char *) outputWlzFilesDir); printf("%d\n", i); for( j = 0; j < numOfBibFiles; j++) { strcpy( warpedFilesNameList[j], (const char *) outputWlzFilesDir ); strcat( warpedFilesNameList[j], "/"); strcat(warpedFilesNameList[j], (const char *) TwoDImagePureFilesNameList[j]); printf("%s\n", warpedFilesNameList[j] ); } /* --------read Woolz object--------- */ if((inFile = fopen(inFileStrw, "r")) == NULL ) { printf("cannot open the input woolz file.\n"); exit(1); } if( !(WObjS = WlzReadObj(inFile, &errNum) ) ) { printf("input Woolz Object Error.\n"); fclose(inFile); exit(1); } fclose(inFile); inFile = NULL; /* ------get the fixed S , T and F ready and s, t, f in OPT space------ */ vS.d3.vtX = Sx; vS.d3.vtY = Sy; vS.d3.vtZ = Sz; vT.d3.vtX = Tx; vT.d3.vtY = Ty; vT.d3.vtZ = Tz; vF.d3.vtX = Fx; vF.d3.vtY = Fy; vF.d3.vtZ = Fz; vs.d3.vtX = sx; vs.d3.vtY = sy; vs.d3.vtZ = sz; vt.d3.vtX = tx; vt.d3.vtY = ty; vt.d3.vtZ = tz; vf.d3.vtX = fx; vf.d3.vtY = fy; vf.d3.vtZ = fz; printf("vt: %f %f %f\n",vt.d3.vtX,vt.d3.vtY, vt.d3.vtZ ); printf("vT: %f %f %f\n",vT.d3.vtX,vT.d3.vtY, vT.d3.vtZ ); /* -----get the three directions in OPT space------- n = 1/(|r2-r1|) { (x2-x1) i + (y2-y1) j + (z2-z1) k } */ WLZ_VTX_3_SUB(vST.d3,vS.d3,vs.d3); lengthTS = WLZ_VTX_3_LENGTH( vST.d3); ns.d3.vtX = vST.d3.vtX/ lengthTS; ns.d3.vtY = vST.d3.vtY/ lengthTS; ns.d3.vtZ = vST.d3.vtZ/ lengthTS; WLZ_VTX_3_SUB(vST.d3,vF.d3,vf.d3); lengthTS = WLZ_VTX_3_LENGTH( vST.d3); nf.d3.vtX = vST.d3.vtX/ lengthTS; nf.d3.vtY = vST.d3.vtY/ lengthTS; nf.d3.vtZ = vST.d3.vtZ/ lengthTS; WLZ_VTX_3_SUB(vST.d3,vT.d3,vt.d3); printf("vt: %f %f %f\n",vt.d3.vtX,vt.d3.vtY, vt.d3.vtZ ); printf("vT: %f %f %f\n",vT.d3.vtX,vT.d3.vtY, vT.d3.vtZ ); lengthTS = WLZ_VTX_3_LENGTH( vST.d3); printf("Length: %f\n",lengthTS); nt.d3.vtX = vST.d3.vtX/ lengthTS; nt.d3.vtY = vST.d3.vtY/ lengthTS; nt.d3.vtZ = vST.d3.vtZ/ lengthTS; /* ---- get the three points in the master plane ( startJ plane ) ---- */ /* allocate memory and give default values for viewer strcuture */ wlzViewStr = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, NULL); wlzViewStr1 = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, NULL); /* set up */ cycleI = startJ; /* read Section viewer parameters */ errNum = ReadBibFile(inFile, (char *) BibFilesNameList[cycleI], wlzViewStr ); if(errNum != WLZ_ERR_NONE) { printf("Read or parse bib file err.\n"); exit(1); } inFile = NULL; WlzInit3DViewStruct(wlzViewStr, WObjS); /* -------- get the corresponding three directions in Main view space ------- (It is also the stack up space nsp = Tm ns, nfp = Tm nf, ntp = Tm nt; */ errNum = Wlz3DSectionTransformVtxR(wlzViewStr, ns.d3, &nsp.d3 ); if(errNum != WLZ_ERR_NONE) { printf("can not get the direction in stack up space for ns err.\n"); exit(1); } errNum = Wlz3DSectionTransformVtxR(wlzViewStr, nf.d3, &nfp.d3 ); if(errNum != WLZ_ERR_NONE) { printf("can not get the direction in stack up space for nf err.\n"); exit(1); } errNum = Wlz3DSectionTransformVtxR(wlzViewStr, nt.d3, &ntp.d3 ); if(errNum != WLZ_ERR_NONE) { printf("can not get the direction in stack up space for np err.\n"); exit(1); } /* --- get the main plane direction in OPT space --- */ /* it can got by inverse transform from stack up viewer space to OPT space */ /* in stack up space or master plane sapce */ nz.d3.vtX = 0.0; nz.d3.vtY = 0.0; nz.d3.vtZ = 1.0; /* nm = Tm^-1 nz (inverse transform used here ) nm is in OPT space */ errNum = Wlz3DSectionTransformInvVtxR(wlzViewStr, nz.d3, &nm.d3 ); if(errNum != WLZ_ERR_NONE) { printf("can not get the main plane direction in OPT space err.\n"); printf("Which means your three straight line has to be rechosen\n"); exit(1); } /* get the nt dot nm, etc */ ntnm = WLZ_VTX_3_DOT(nt.d3, nm.d3); nfnm = WLZ_VTX_3_DOT(nf.d3, nm.d3); nsnm = WLZ_VTX_3_DOT(ns.d3, nm.d3); ntnm = nm.d3.vtX * nt.d3.vtX + nm.d3.vtY * nt.d3.vtY + nm.d3.vtZ * nt.d3.vtZ; if( ( ( ntnm == 0 ) || ( nfnm == 0 ) ) ||( nsnm == 0 ) ) { printf("At least one of your three strait lines are parallel to the main plane err.\n"); printf("Which means your three straight line has to be rechosen or chose another plane\n"); printf("as main plane\n"); exit(1); } /* get crossed point in this plane p_{i} then project to viewer space */ errNum = WlzGetCorssPoint(vs, ns, &vsr, wlzViewStr); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } errNum = WlzGetCorssPoint(vt, nt, &vtr, wlzViewStr); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } errNum = WlzGetCorssPoint(vf, nf, &vfr, wlzViewStr); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } /* use this 3 point as refernce */ /* --------Get Tie-points -------- */ /* get the target points for this plane in stack up space */ (vtxVec1 )->vtX = vsr.d3.vtX; (vtxVec1 )->vtY = vsr.d3.vtY; (vtxVec1 + 1)->vtX = vtr.d3.vtX; (vtxVec1 + 1)->vtY = vtr.d3.vtY; (vtxVec1 + 2)->vtX = vfr.d3.vtX; (vtxVec1 + 2)->vtY = vfr.d3.vtY; /* get the source point */ /* get ( sx' sy' sz' )_i */ printf("%f %f\n", sx, sy); vsp.d3.vtX = vsr.d3.vtX; vsp.d3.vtY = vsr.d3.vtY; vsp.d3.vtZ = vsr.d3.vtZ; /* get ( tx' ty' tz' )_i */ printf("%f %f\n", tx, ty); vtp.d3.vtX = vtr.d3.vtX; vtp.d3.vtY = vtr.d3.vtY; vtp.d3.vtZ = vtr.d3.vtZ; /* get ( fx' fy' fz' )_i */ printf("%f %f\n", fx, fy); vfp.d3.vtX = vfr.d3.vtX; vfp.d3.vtY = vfr.d3.vtY; vfp.d3.vtZ = vfr.d3.vtZ; /* ------ output the affine transformed Wlz ------*/ errNum = outputTheWarpedWlz( vsp, vtp, vfp, vtxVec1, TwoDImageFilesNameList[cycleI], warpedFilesNameList[cycleI] ); while(cycleI < numOfBibFiles - 1) { cycleNext = cycleI + 1; errNum = ReadBibFile(inFile, (char *) BibFilesNameList[cycleNext], wlzViewStr1 ); WlzInit3DViewStruct(wlzViewStr1, WObjS); /* ------ get Tie - points -------*/ /* get crossed point in this plane p_{i} then project to viewer space */ errNum = WlzGetCorssPoint(vs, ns, &vs1, wlzViewStr1); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } errNum = WlzGetCorssPoint(vt, nt, &vt1, wlzViewStr1); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } errNum = WlzGetCorssPoint(vf, nf, &vf1, wlzViewStr1); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } /* get the source points */ /* get ( sx' sy' sz' )_i */ /* printf("%f %f\n", sx, sy); */ vsp.d3.vtX = vs1.d3.vtX; vsp.d3.vtY = vs1.d3.vtY; vsp.d3.vtZ = vs1.d3.vtZ; /* get ( tx' ty' tz' )_i */ /* printf("%f %f\n", tx, ty); */ vtp.d3.vtX = vt1.d3.vtX; vtp.d3.vtY = vt1.d3.vtY; vtp.d3.vtZ = vt1.d3.vtZ; /* get ( fx' fy' fz' )_i */ /* printf("%f %f\n", fx, fy); */ vfp.d3.vtX = vf1.d3.vtX; vfp.d3.vtY = vf1.d3.vtY; vfp.d3.vtZ = vf1.d3.vtZ; /* get the target points */ /* find the target points by keep the same direction in stack up space and the OPT space.The following are in stack up space */ deltaZ = (double) ( cycleNext - startJ ); errNum = WlzGetDxDy( nsp, deltaZ, &vs1); if(errNum != WLZ_ERR_NONE) { printf("can not get Dx Dy err.\n"); exit(1); } errNum = WlzGetDxDy( nfp, deltaZ, &vf1); if(errNum != WLZ_ERR_NONE) { printf("can not get Dx Dy err.\n"); exit(1); } errNum = WlzGetDxDy( ntp, deltaZ, &vt1); if(errNum != WLZ_ERR_NONE) { printf("can not get Dx Dy err.\n"); exit(1); } (vtxVec1 )->vtX = vsr.d3.vtX + vs1.d3.vtX; (vtxVec1 )->vtY = vsr.d3.vtY + vs1.d3.vtY; (vtxVec1 + 1)->vtX = vtr.d3.vtX + vt1.d3.vtX; (vtxVec1 + 1)->vtY = vtr.d3.vtY + vt1.d3.vtY; (vtxVec1 + 2)->vtX = vfr.d3.vtX + vf1.d3.vtX; (vtxVec1 + 2)->vtY = vfr.d3.vtY + vf1.d3.vtY; /* ------ output the affine transformed Wlz ------*/ printf("----------- %d\n",cycleI); /* out put the source and target for checking */ errNum = outputTheWarpedWlz( vsp, vtp, vfp, vtxVec1, TwoDImageFilesNameList[cycleNext], warpedFilesNameList[cycleNext] ); /* track from s_i' to s_{i+1}' */ /* scale = |T - S |/|t - s| */ cycleI++; } cycleI = startJ; while( cycleI > 0 ) { cycleNext = cycleI - 1; errNum = ReadBibFile(inFile, (char *) BibFilesNameList[cycleNext], wlzViewStr1 ); WlzInit3DViewStruct(wlzViewStr1, WObjS); /* ------ get Tie - points -------*/ /* get crossed point in this plane p_{i} then project to viewer space */ errNum = WlzGetCorssPoint(vs, ns, &vs1, wlzViewStr1); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } errNum = WlzGetCorssPoint(vt, nt, &vt1, wlzViewStr1); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } errNum = WlzGetCorssPoint(vf, nf, &vf1, wlzViewStr1); if(errNum != WLZ_ERR_NONE) { printf("can not find crossed point err.\n"); exit(1); } /* get the source points */ /* get ( sx' sy' sz' )_i */ printf("%f %f\n", sx, sy); vsp.d3.vtX = vs1.d3.vtX; vsp.d3.vtY = vs1.d3.vtY; vsp.d3.vtZ = vs1.d3.vtZ; /* get ( tx' ty' tz' )_i */ printf("%f %f\n", tx, ty); vtp.d3.vtX = vt1.d3.vtX; vtp.d3.vtY = vt1.d3.vtY; vtp.d3.vtZ = vt1.d3.vtZ; /* get ( fx' fy' fz' )_i */ printf("%f %f\n", fx, fy); vfp.d3.vtX = vf1.d3.vtX; vfp.d3.vtY = vf1.d3.vtY; vfp.d3.vtZ = vf1.d3.vtZ; /* get the target points */ /* find the target points by keep the same direction in stack up space and the OPT space.The following are in stack up space */ deltaZ = (double) ( cycleNext - startJ ); errNum = WlzGetDxDy( nsp, deltaZ, &vs1); if(errNum != WLZ_ERR_NONE) { printf("can not get Dx Dy err.\n"); exit(1); } errNum = WlzGetDxDy( nfp, deltaZ, &vf1); if(errNum != WLZ_ERR_NONE) { printf("can not get Dx Dy err.\n"); exit(1); } errNum = WlzGetDxDy( ntp, deltaZ, &vt1); if(errNum != WLZ_ERR_NONE) { printf("can not get Dx Dy err.\n"); exit(1); } /* target points */ (vtxVec1 )->vtX = vsr.d3.vtX + vs1.d3.vtX; (vtxVec1 )->vtY = vsr.d3.vtY + vs1.d3.vtY; (vtxVec1 + 1)->vtX = vtr.d3.vtX + vt1.d3.vtX; (vtxVec1 + 1)->vtY = vtr.d3.vtY + vt1.d3.vtY; (vtxVec1 + 2)->vtX = vfr.d3.vtX + vf1.d3.vtX; (vtxVec1 + 2)->vtY = vfr.d3.vtY + vf1.d3.vtY; /* ------ output the affine transformed Wlz ------*/ errNum = outputTheWarpedWlz( vsp, vtp, vfp, vtxVec1, TwoDImageFilesNameList[cycleNext], warpedFilesNameList[cycleNext] ); /* track from s_i' to s_{i+1}' */ /* scale = |T - S |/|t - s| */ cycleI--; } AlcFree(vtxVec1 ); /* */ WlzFree3DViewStruct(wlzViewStr); WlzFree3DViewStruct(wlzViewStr1); return ( 0 ); }
int main(int argc, char **argv) { WlzObject *obj = NULL, *nobj = NULL, *subDomain = NULL; FILE *inFP = NULL, *outFP = NULL, *trFP = NULL, *bibFP = NULL; char *outFile = NULL, *trFile = NULL, *bibFile = NULL; char optList[] = "ACLNTa:b:d:f:m:o:r:s:t:u:R:h"; int option; int i, j, iVal, timer = 0, voxRescale = 0, allFlg = 0; double dist=0.0, pitch=0.0, yaw=0.0, roll=0.0; double scale=1.0; WlzDVertex3 fixed={0.0,0.0,0.0}; WlzDVertex3 up={0.0,0.0,-1.0}; WlzThreeDViewStruct *viewStr=NULL; WlzThreeDViewMode mode=WLZ_UP_IS_UP_MODE; WlzInterpolationType interp = WLZ_INTERPOLATION_NEAREST; WlzErrorNum errNum=WLZ_ERR_NONE; BibFileRecord *bibfileRecord; BibFileError bibFileErr; struct timeval times[3]; char *errMsg; /* additional defaults */ outFile = "-"; bibFile = NULL; trFile = NULL; subDomain = NULL; /* read the argument list and check for an input file */ opterr = 0; while( (option = getopt(argc, argv, optList)) != EOF ){ switch( option ){ case 'A': allFlg = 1; break; case 'C': interp = WLZ_INTERPOLATION_CLASSIFY_1; break; case 'L': interp = WLZ_INTERPOLATION_LINEAR; break; case 'N': interp = WLZ_INTERPOLATION_NEAREST; break; case 'a': switch( sscanf(optarg, "%lg,%lg,%lg", &pitch, &yaw, &roll) ){ default: usage(argv[0]); return 1; case 2: break; case 3: mode = WLZ_ZETA_MODE; break; } break; case 'b': bibFile = optarg; break; case 'd': if( sscanf(optarg, "%lg", &dist) < 1 ){ usage(argv[0]); return 1; } break; case 'f': if( sscanf(optarg, "%lg,%lg,%lg", &(fixed.vtX), &(fixed.vtY), &(fixed.vtZ)) < 3 ){ usage(argv[0]); return 1; } break; case 'm': if( sscanf(optarg, "%d", &iVal) < 1 ){ usage(argv[0]); return 1; } else if( mode != WLZ_ZETA_MODE ){ switch( iVal ){ default: usage(argv[0]); return 1; case 0: mode = WLZ_UP_IS_UP_MODE; break; case 1: mode = WLZ_STATUE_MODE; break; case 2: mode = WLZ_ZETA_MODE; break; } } break; case 'o': outFile = optarg; break; case 'r': if( sscanf(optarg, "%d", &voxRescale) < 1 ){ usage(argv[0]); return 1; } break; case 's': if( sscanf(optarg, "%lg", &scale) < 1 ){ usage(argv[0]); return 1; } break; case 'u': if( sscanf(optarg, "%lg,%lg,%lg", &(up.vtX), &(up.vtY), &(up.vtZ)) < 3 ){ usage(argv[0]); return 1; } break; case 'R': if((inFP = fopen(optarg, "rb"))){ if((subDomain = WlzReadObj(inFP, &errNum)) == NULL){ fprintf(stderr, "%s: can't read sub-domain object %s\n", argv[0], optarg); usage(argv[0]); return 1; } fclose(inFP); } else { fprintf(stderr, "%s: can't open file %s\n", argv[0], optarg); usage(argv[0]); return 1; } break; case 'T': timer = 1; break; case 't': trFile = optarg; break; case 'h': default: usage(argv[0]); return 0; } } /* check input file/stream */ inFP = stdin; if( optind < argc ){ if( (inFP = fopen(*(argv+optind), "rb")) == NULL ){ fprintf(stderr, "%s: can't open file %s\n", argv[0], *(argv+optind)); usage(argv[0]); return 1; } } /* check output file/stream */ if( allFlg ){ if(strcmp(outFile, "-")) { /* strip any file extension */ for(i=0, j=strlen(outFile); i < strlen(outFile); i++){ if( outFile[i] == '.' ){ j = i; } } outFile[j] = '\0'; } else { outFile = "plane"; } } else { if(strcmp(outFile, "-")) { if((outFP = fopen(outFile, "wb")) == NULL) { errNum = WLZ_ERR_WRITE_EOF; } } else { outFP = stdout; } } /* create view structure */ if((viewStr = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum)) != NULL){ viewStr->theta = yaw * WLZ_M_PI / 180.0; viewStr->phi = pitch * WLZ_M_PI / 180.0; viewStr->zeta = roll * WLZ_M_PI / 180.0; viewStr->dist = dist; viewStr->fixed = fixed; viewStr->up = up; viewStr->view_mode = mode; viewStr->scale = scale; viewStr->voxelRescaleFlg = voxRescale; } if((errNum == WLZ_ERR_NONE) && (bibFile != NULL) && (trFile != NULL)) { fprintf(stderr, "%s: both bibfile and transform file specified.\n", argv[0]); } /* check bibfile - select first section parameters in the file */ if((errNum == WLZ_ERR_NONE) && (bibFile != NULL)){ if((bibFP = fopen(bibFile, "r")) != NULL){ bibFileErr = BibFileRecordRead(&bibfileRecord, &errMsg, bibFP); while((bibFileErr == BIBFILE_ER_NONE) && (strncmp(bibfileRecord->name, "Wlz3DSectionViewParams", 22))){ BibFileRecordFree(&bibfileRecord); bibFileErr = BibFileRecordRead(&bibfileRecord, &errMsg, bibFP); } fclose( bibFP ); if( bibFileErr != BIBFILE_ER_NONE ){ fprintf(stderr, "%s: error reading bibfile: %s\n", argv[0], errMsg); AlcFree((void *) errMsg); return 1; } WlzEffBibParse3DSectionViewParamsRecord(bibfileRecord, viewStr); BibFileRecordFree(&bibfileRecord); } else { fprintf(stderr, "%s: can't open parameter bibfile %s\n", argv[0], bibFile); return 1; } } if((errNum == WLZ_ERR_NONE) && (trFile != NULL)){ if((trFP = fopen(trFile, "r")) != NULL){ WlzObject *trObj = NULL; if((trObj = WlzReadObj(trFP, &errNum)) != NULL) { if(trObj->type != WLZ_3D_VIEW_STRUCT) { errNum = WLZ_ERR_OBJECT_TYPE; } else if (trObj->domain.core == NULL) { errNum = WLZ_ERR_DOMAIN_NULL; } else { WlzThreeDViewStruct *fViewStr; fViewStr = trObj->domain.vs3d; viewStr->theta = fViewStr->theta; viewStr->phi = fViewStr->phi; viewStr->zeta = fViewStr->zeta; viewStr->dist = fViewStr->dist; viewStr->fixed = fViewStr->fixed; viewStr->up = fViewStr->up; viewStr->view_mode = fViewStr->view_mode; viewStr->scale = fViewStr->scale; viewStr->voxelRescaleFlg = fViewStr->voxelRescaleFlg; } (void )WlzFreeObj(trObj); } } if(errNum != WLZ_ERR_NONE) { fprintf(stderr, "%s: error reading section view transform from %s.\n", argv[0], trFile); return 1; } } /* read objects and section if possible */ while((errNum == WLZ_ERR_NONE) && ((obj = WlzReadObj(inFP, &errNum)) != NULL)) { obj = WlzAssignObject(obj, &errNum); switch( obj->type ) { case WLZ_CONTOUR: case WLZ_3D_DOMAINOBJ: if(voxRescale && obj->domain.core) { viewStr->voxelSize[0] = obj->domain.p->voxel_size[0]; viewStr->voxelSize[1] = obj->domain.p->voxel_size[1]; viewStr->voxelSize[2] = obj->domain.p->voxel_size[2]; } WlzInit3DViewStruct(viewStr, obj); if(timer) { gettimeofday(times + 0, NULL); } if( allFlg ){ /* loop through all possible planes */ for(i=WLZ_NINT(viewStr->minvals.vtZ), j=0; i <= WLZ_NINT(viewStr->maxvals.vtZ); i++, j++){ viewStr->dist = i; WlzInit3DViewStruct(viewStr, obj); nobj = WlzGetSubSectionFromObject(obj, subDomain, viewStr, interp, NULL, &errNum); if( nobj != NULL){ char fileBuf[256]; sprintf(fileBuf, "%s%06d.wlz", outFile, j); if((outFP = fopen(fileBuf, "w")) != NULL){ WlzWriteObj(outFP, nobj); fclose(outFP); } } else { return errNum; } WlzFreeObj(nobj); } } else { nobj = WlzGetSubSectionFromObject(obj, subDomain, viewStr, interp, NULL, &errNum); if( nobj != NULL){ WlzWriteObj(outFP, nobj); } else { return errNum; } WlzFreeObj(nobj); } if(timer) { gettimeofday(times + 1, NULL); ALC_TIMERSUB(times + 1, times + 0, times + 2); (void )fprintf(stderr, "%s: Elapsed time = %g\n", *argv, times[2].tv_sec + (0.000001 * times[2].tv_usec)); } break; default: WlzWriteObj(outFP, obj); break; } WlzFreeObj(obj); } if(errNum == WLZ_ERR_READ_EOF) { errNum = WLZ_ERR_NONE; } if( viewStr ){ WlzFree3DViewStruct(viewStr); } if( subDomain ){ WlzFreeObj(subDomain); } return errNum; }
/*! * \return projection object * \ingroup WlzTransform * \brief Use the view transform to define a projection from * 3D to 2D. Currently only the domain is projected as * an opaque shadow. * This is old code temporarily kept for compatibility. * \param obj source 3D object * \param viewStr view structure defining the projection * \param intFunc grey-value summation function * \param intFuncData data to be passed to the integration function * \param dstErr error return */ WlzObject *WlzGetProjectionFromObject( WlzObject *obj, WlzThreeDViewStruct *viewStr, Wlz3DProjectionIntFn intFunc, void *intFuncData, WlzErrorNum *dstErr) { WlzObject *rtnObj=NULL, *obj1; WlzThreeDViewStruct *viewStr1=NULL; WlzDomain domain; WlzValues values; WlzGreyType srcGType = WLZ_GREY_UBYTE, dstGType = WLZ_GREY_UBYTE; WlzPixelV pixval; WlzPixelP pixptr; WlzIntervalWSpace iwsp; WlzGreyWSpace gwsp; WlzGreyValueWSpace *gVWSp = NULL; WlzDVertex3 vtx, vtx1; double x, y, z; double *s_to_x=NULL; double *s_to_y=NULL; double *s_to_z=NULL; int k, xp, yp, s, sp; int length = 0, size = 0, occupiedFlg; WlzErrorNum errNum=WLZ_ERR_NONE; /* check inputs */ if( obj == NULL ){ errNum = WLZ_ERR_OBJECT_NULL; } else if( obj->type != WLZ_3D_DOMAINOBJ ){ errNum = WLZ_ERR_OBJECT_TYPE; } else if( obj->domain.core == NULL ){ errNum = WLZ_ERR_DOMAIN_NULL; } else if( obj->domain.core->type != WLZ_PLANEDOMAIN_DOMAIN ){ errNum = WLZ_ERR_DOMAIN_TYPE; } if( (errNum == WLZ_ERR_NONE) && (viewStr == NULL) ){ errNum = WLZ_ERR_OBJECT_NULL; } /* create new view transform */ if( errNum == WLZ_ERR_NONE ){ if((viewStr1 = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum)) != NULL){ /* need to worry about fixed line mode here sometime */ viewStr1->fixed = viewStr->fixed; viewStr1->theta = viewStr->theta; viewStr1->phi = viewStr->phi; viewStr1->zeta = viewStr->zeta; viewStr1->dist = viewStr->dist; viewStr1->scale = viewStr->scale; viewStr1->voxelSize[0] = viewStr->voxelSize[0]; viewStr1->voxelSize[1] = viewStr->voxelSize[1]; viewStr1->voxelSize[2] = viewStr->voxelSize[2]; viewStr1->voxelRescaleFlg = viewStr->voxelRescaleFlg; viewStr1->interp = viewStr->interp; viewStr1->view_mode = viewStr->view_mode; viewStr1->up = viewStr->up; /* now intialize it */ /* could optimise by setting fixed point to object centre */ if( (errNum = WlzInit3DViewStruct(viewStr1, obj)) != WLZ_ERR_NONE ){ WlzFree3DViewStruct(viewStr1); viewStr1 = NULL; } } } /* set up orthogonal line parameters & luts */ if( errNum == WLZ_ERR_NONE ){ length = WLZ_NINT(viewStr1->maxvals.vtZ) - WLZ_NINT(viewStr1->minvals.vtZ) + 1; s_to_x = (double *) AlcMalloc(sizeof(double) * length ); s_to_y = (double *) AlcMalloc(sizeof(double) * length ); s_to_z = (double *) AlcMalloc(sizeof(double) * length ); /* transform a perpendicular vector */ vtx.vtX = 0.0; vtx.vtY = 0.0; vtx.vtZ = 1.0; Wlz3DSectionTransformInvVtx(&vtx, viewStr1); vtx1.vtX = 0.0; vtx1.vtY = 0.0; vtx1.vtZ = 0.0; Wlz3DSectionTransformInvVtx(&vtx1, viewStr1); vtx.vtX -= vtx1.vtX; vtx.vtY -= vtx1.vtY; vtx.vtZ -= vtx1.vtZ; /* assign lut values */ s = (int )(WLZ_NINT(viewStr1->minvals.vtZ) - viewStr1->dist); for(sp=0; sp < length; sp++, s++){ s_to_x[sp] = s * vtx.vtX; s_to_y[sp] = s * vtx.vtY; s_to_z[sp] = s * vtx.vtZ; } } /* if there is an integration function then allocate space for the grey-level array */ if( (errNum == WLZ_ERR_NONE) && (intFunc) ){ srcGType = WlzGreyTypeFromObj(obj, &errNum); switch( srcGType ){ case WLZ_GREY_LONG: size = sizeof(WlzLong)*length; break; case WLZ_GREY_INT: size = sizeof(int)*length; break; case WLZ_GREY_SHORT: size = sizeof(short)*length; break; case WLZ_GREY_UBYTE: size = sizeof(WlzUByte)*length; break; case WLZ_GREY_FLOAT: size = sizeof(float)*length; break; case WLZ_GREY_DOUBLE: size = sizeof(double)*length; break; case WLZ_GREY_RGBA: size = sizeof(int)*length; break; default: errNum = WLZ_ERR_GREY_TYPE; break; } if( (pixptr.p.inp = (int *) AlcMalloc(size)) == NULL ){ errNum = WLZ_ERR_MEM_ALLOC; } pixptr.type = srcGType; /* set up the grey-value workspace for random access */ gVWSp = WlzGreyValueMakeWSp(obj, &errNum); } /* create rectangular projection image */ if( errNum == WLZ_ERR_NONE ){ if((domain.i = WlzMakeIntervalDomain(WLZ_INTERVALDOMAIN_RECT, WLZ_NINT(viewStr1->minvals.vtY), WLZ_NINT(viewStr1->maxvals.vtY), WLZ_NINT(viewStr1->minvals.vtX), WLZ_NINT(viewStr1->maxvals.vtX), &errNum)) != NULL){ values.core = NULL; if((rtnObj = WlzMakeMain(WLZ_2D_DOMAINOBJ, domain, values, NULL, NULL, &errNum)) != NULL){ /* note the grey-values required are determined by the integration function. Here we use WlzUByte and reset later if needed */ dstGType = WLZ_GREY_UBYTE; pixval.type = WLZ_GREY_UBYTE; pixval.v.ubv = (WlzUByte )0; if((values.v = WlzNewValueTb(rtnObj, WlzGreyTableType(WLZ_GREY_TAB_RECT, dstGType, NULL), pixval, &errNum)) != NULL){ rtnObj->values = WlzAssignValues(values, &errNum); } else { WlzFreeObj(rtnObj); rtnObj = NULL; } } else { WlzFreeDomain(domain); domain.core = NULL; } } } /* scan image setting values */ if( errNum == WLZ_ERR_NONE ){ errNum = WlzInitGreyScan(rtnObj, &iwsp, &gwsp); } if( errNum == WLZ_ERR_NONE ){ while( (errNum = WlzNextGreyInterval(&iwsp)) == WLZ_ERR_NONE ){ yp = iwsp.linpos - WLZ_NINT(viewStr1->minvals.vtY); for(k=iwsp.lftpos; k <= iwsp.rgtpos; k++){ xp = k - WLZ_NINT(viewStr1->minvals.vtX); vtx.vtX = viewStr1->xp_to_x[xp] + viewStr1->yp_to_x[yp]; vtx.vtY = viewStr1->xp_to_y[xp] + viewStr1->yp_to_y[yp]; vtx.vtZ = viewStr1->xp_to_z[xp] + viewStr1->yp_to_z[yp]; /* get the projection values */ /* if no function then just check for occupancy */ if( intFunc == NULL ){ occupiedFlg = 0; sp = (int )(viewStr1->dist - WLZ_NINT(viewStr1->minvals.vtZ)); for(; !occupiedFlg && (sp < length); sp++){ x = vtx.vtX + s_to_x[sp]; y = vtx.vtY + s_to_y[sp]; z = vtx.vtZ + s_to_z[sp]; if( WlzInsideDomain(obj, z, y, x, &errNum) ){ occupiedFlg = 1; } } sp = (int )(viewStr1->dist - WLZ_NINT(viewStr1->minvals.vtZ) - 1); for(; !occupiedFlg && (sp >= 0); sp--){ x = vtx.vtX + s_to_x[sp]; y = vtx.vtY + s_to_y[sp]; z = vtx.vtZ + s_to_z[sp]; if( WlzInsideDomain(obj, z, y, x, &errNum) ){ occupiedFlg = 1; } } /* set the integrated value - only WlzUByte at the moment */ *(gwsp.u_grintptr.ubp) = (WlzUByte )occupiedFlg; gwsp.u_grintptr.ubp++; } /* use integration function */ else { /* set array of pixel values */ for(sp=0; sp < length; sp++){ x = vtx.vtX + s_to_x[sp]; y = vtx.vtY + s_to_y[sp]; z = vtx.vtZ + s_to_z[sp]; WlzGreyValueGet(gVWSp, WLZ_NINT(z), WLZ_NINT(y), WLZ_NINT(x)); switch( srcGType ){ case WLZ_GREY_LONG: pixptr.p.lnp[sp] = gVWSp->gVal[0].lnv; break; case WLZ_GREY_INT: pixptr.p.inp[sp] = gVWSp->gVal[0].inv; break; case WLZ_GREY_SHORT: pixptr.p.shp[sp] = gVWSp->gVal[0].shv; break; case WLZ_GREY_UBYTE: pixptr.p.ubp[sp] = gVWSp->gVal[0].ubv; break; case WLZ_GREY_FLOAT: pixptr.p.flp[sp] = gVWSp->gVal[0].flv; break; case WLZ_GREY_DOUBLE: pixptr.p.dbp[sp] = gVWSp->gVal[0].dbv; break; case WLZ_GREY_RGBA: pixptr.p.rgbp[sp] = gVWSp->gVal[0].rgbv; break; default: errNum = WLZ_ERR_GREY_TYPE; break; } } /* call integration function and seet value */ intFunc(pixptr, length, (int )(viewStr1->dist - WLZ_NINT(viewStr1->minvals.vtZ)), intFuncData, &errNum); } } } (void )WlzEndGreyScan(&iwsp, &gwsp); if(errNum == WLZ_ERR_EOO) /* Reset error from end of intervals */ { errNum = WLZ_ERR_NONE; } /* if no integration function then threshold - binary only */ if( intFunc == NULL ){ pixval.v.ubv = 1; rtnObj = WlzAssignObject(rtnObj, NULL); if((obj1 = WlzThreshold(rtnObj, pixval, WLZ_THRESH_HIGH, &errNum)) != NULL){ WlzFreeObj(rtnObj); values.core = NULL; rtnObj = WlzMakeMain(WLZ_2D_DOMAINOBJ, obj1->domain, values, NULL, NULL, &errNum); WlzFreeObj(obj1); } else { WlzFreeObj(rtnObj); rtnObj = NULL; } } } /* clear space */ if( viewStr1 ){ errNum = WlzFree3DViewStruct(viewStr1); } if( s_to_x ){ AlcFree( s_to_x ); } if( s_to_y ){ AlcFree( s_to_y ); } if( s_to_z ){ AlcFree( s_to_z ); } /* check error and return */ if( dstErr ){ *dstErr = errNum; } return rtnObj; }
/*! * \return New object with the rojection. * \ingroup WlzTransform * \brief Use the view transform to define a projection from * 3D to 2D and then project the object onto this plane. * The object supplied to this function must be a 3D * spatial domain object (WLZ_3D_DOMAINOBJ) with either * no values or for integration WLZ_GREY_UBYTE values. * Integration will assign each output pixel the sum of * all input voxels mapped via either the domain density * or the voxel density. * The integration is controled by the integrate parameter * with valid values: * WLZ_PROJECT_INT_MODE_NONE - a "shadow domain" without values * is computed, * WLZ_PROJECT_INT_MODE_DOMAIN - the voxels of the domain are * integrated using * \f[ p = \frac{1}{255} n d \f] * WLZ_PROJECT_INT_MODE_VALUES - the voxel values are integrated * using * \f[ p = \frac{1}{255} \sum{l\left[v\right]}. \f] * Where * \f$p\f$ is the projected image value, * \f$n\f$ is the number of voxels projected for \f$p\f$, * \f$d\f$ is the density of domain voxels, * \f$l\f$ is the voxel value density look up table and * \f$v\f$ is a voxel value. * \param obj The given object. * \param vStr Given view structure defining the * projection plane. * \param intMod This may take three values: * WLZ_PROJECT_INT_MODE_NONE, * WLZ_PROJECT_INT_MODE_DOMAIN or * WLZ_PROJECT_INT_MODE_VALUES. * \param denDom Density of domain voxels this value * is not used unless the integration * mode is WLZ_PROJECT_INT_MODE_DOMAIN. * \param denVal Density look up table for object * voxel density values which must be * an array of 256 values. This may be * NULL if the integration mode is not * WLZ_PROJECT_INT_MODE_VALUES. * \param depth If greater than zero, the projection * depth perpendicular to the viewing * plane. * \param dstErr Destination error pointer, may be NULL. */ WlzObject *WlzProjectObjToPlane(WlzObject *obj, WlzThreeDViewStruct *vStr, WlzProjectIntMode intMod, WlzUByte denDom, WlzUByte *denVal, double depth, WlzErrorNum *dstErr) { int nThr = 1, itvVal = 0; WlzIVertex2 prjSz; WlzIBox2 prjBox = {0}; double pln[4]; WlzObject *bufObj = NULL, *prjObj = NULL; WlzThreeDViewStruct *vStr1 = NULL; double **vMat = NULL; WlzValues nullVal; WlzErrorNum errNum = WLZ_ERR_NONE; WlzAffineTransform *rescaleTr = NULL; WlzGreyValueWSpace **gVWSp = NULL; void ***prjAry = NULL; const double eps = 0.000001; #ifdef WLZ_DEBUG_PROJECT3D_TIME struct timeval times[3]; #endif /* WLZ_DEBUG_PROJECT3D_TIME */ nullVal.core = NULL; if(obj == NULL) { errNum = WLZ_ERR_OBJECT_NULL; } else if(obj->type != WLZ_3D_DOMAINOBJ) { errNum = WLZ_ERR_OBJECT_TYPE; } else if(obj->domain.core == NULL) { errNum = WLZ_ERR_DOMAIN_NULL; } else if(obj->domain.core->type != WLZ_PLANEDOMAIN_DOMAIN) { errNum = WLZ_ERR_DOMAIN_TYPE; } else if(vStr == NULL) { errNum = WLZ_ERR_TRANSFORM_NULL; } else if((intMod == WLZ_PROJECT_INT_MODE_VALUES) && (obj->values.core == NULL)) { errNum = WLZ_ERR_VALUES_NULL; } #ifdef WLZ_DEBUG_PROJECT3D_TIME gettimeofday(times + 0, NULL); #endif /* WLZ_DEBUG_PROJECT3D_TIME */ /* Create new view transform without voxel scaling. The voxel scaling * is done after the projection. */ if(errNum == WLZ_ERR_NONE) { if((vStr1 = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum)) != NULL) { vStr1->fixed = vStr->fixed; vStr1->theta = vStr->theta; vStr1->phi = vStr->phi; vStr1->zeta = vStr->zeta; vStr1->dist = vStr->dist; vStr1->scale = vStr->scale; vStr1->voxelSize[0] = 1.0; vStr1->voxelSize[1] = 1.0; vStr1->voxelSize[2] = 1.0; vStr1->voxelRescaleFlg = 0; vStr1->interp = vStr->interp; vStr1->view_mode = vStr->view_mode; vStr1->up = vStr->up; vStr1->initialised = WLZ_3DVIEWSTRUCT_INIT_NONE; vMat = vStr1->trans->mat; errNum = WlzInit3DViewStructAffineTransform(vStr1); if(errNum == WLZ_ERR_NONE) { errNum = Wlz3DViewStructTransformBB(obj, vStr1); } if(errNum != WLZ_ERR_NONE) { WlzFree3DViewStruct(vStr1); vStr1 = NULL; } } } /* Compute bounding box of the projection. */ if(errNum == WLZ_ERR_NONE) { prjBox.xMin = WLZ_NINT(vStr1->minvals.vtX); prjBox.yMin = WLZ_NINT(vStr1->minvals.vtY); prjBox.xMax = WLZ_NINT(vStr1->maxvals.vtX); prjBox.yMax = WLZ_NINT(vStr1->maxvals.vtY); prjSz.vtX = prjBox.xMax - prjBox.xMin + 1; prjSz.vtY = prjBox.yMax - prjBox.yMin + 1; } /* Compute post projection scaling. */ if((errNum == WLZ_ERR_NONE) && (vStr->voxelRescaleFlg != 0)) { WlzIBox2 sBox; WlzIVertex2 sSz; WlzThreeDViewStruct *vStr2; vStr2 = WlzMake3DViewStruct(WLZ_3D_VIEW_STRUCT, &errNum); if(errNum == WLZ_ERR_NONE) { vStr2->fixed = vStr->fixed; vStr2->theta = vStr->theta; vStr2->phi = vStr->phi; vStr2->zeta = vStr->zeta; vStr2->dist = vStr->dist; vStr2->scale = vStr->scale; vStr2->voxelSize[0] = vStr->voxelSize[0]; vStr2->voxelSize[1] = vStr->voxelSize[1]; vStr2->voxelSize[2] = vStr->voxelSize[2]; vStr2->voxelRescaleFlg = vStr->voxelRescaleFlg; vStr2->interp = vStr->interp; vStr2->view_mode = vStr->view_mode; vStr2->up = vStr->up; vStr2->initialised = WLZ_3DVIEWSTRUCT_INIT_NONE; errNum = WlzInit3DViewStructAffineTransform(vStr2); if(errNum == WLZ_ERR_NONE) { errNum = Wlz3DViewStructTransformBB(obj, vStr2); } if(errNum == WLZ_ERR_NONE) { sBox.xMin = WLZ_NINT(vStr2->minvals.vtX); sBox.yMin = WLZ_NINT(vStr2->minvals.vtY); sBox.xMax = WLZ_NINT(vStr2->maxvals.vtX); sBox.yMax = WLZ_NINT(vStr2->maxvals.vtY); sSz.vtX = sBox.xMax - sBox.xMin + 1; sSz.vtY = sBox.yMax - sBox.yMin + 1; rescaleTr = WlzMakeAffineTransform(WLZ_TRANSFORM_2D_AFFINE, &errNum); } if(errNum == WLZ_ERR_NONE) { double **m; m = rescaleTr->mat; m[0][0] = (sSz.vtX * eps) / (prjSz.vtX * eps); m[1][1] = (sSz.vtY * eps) / (prjSz.vtY * eps); m[0][2] = sBox.xMin - WLZ_NINT(m[0][0] * prjBox.xMin); m[1][2] = sBox.yMin - WLZ_NINT(m[1][1] * prjBox.yMin); } (void )WlzFree3DViewStruct(vStr2); } } /* Compute plane equation, used to clip intervals if depth was given. */ if((errNum == WLZ_ERR_NONE) && (depth > eps)) { Wlz3DViewGetPlaneEqn(vStr1, pln + 0, pln + 1, pln + 2, pln + 3); } /* Create rectangular projection array buffers, one for each thread, * also if integrating values create a grey value workspace per thread. */ if(errNum == WLZ_ERR_NONE) { int idB; #ifdef _OPENMP #pragma omp parallel { #pragma omp master { nThr = omp_get_num_threads(); } } #endif if((prjAry = (void ***)AlcCalloc(nThr, sizeof(void **))) == NULL) { errNum = WLZ_ERR_MEM_ALLOC; } else { if(intMod == WLZ_PROJECT_INT_MODE_NONE) { for(idB = 0; idB < nThr; ++idB) { if(AlcUnchar2Calloc((WlzUByte ***)&(prjAry[idB]), prjSz.vtY, prjSz.vtX) != ALC_ER_NONE) { errNum = WLZ_ERR_MEM_ALLOC; break; } } } else { for(idB = 0; idB < nThr; ++idB) { if(AlcInt2Calloc((int ***)&(prjAry[idB]), prjSz.vtY, prjSz.vtX) != ALC_ER_NONE) { errNum = WLZ_ERR_MEM_ALLOC; break; } } } } if((errNum == WLZ_ERR_NONE) && (intMod == WLZ_PROJECT_INT_MODE_VALUES)) { itvVal = (WlzGreyTableIsTiled(obj->values.core->type) == 0); if(itvVal == 0) { if((gVWSp = AlcCalloc(nThr, sizeof(WlzGreyValueWSpace *))) == NULL) { errNum = WLZ_ERR_MEM_ALLOC; } else { for(idB = 0; idB < nThr; ++idB) { gVWSp[idB] = WlzGreyValueMakeWSp(obj, &errNum); if(gVWSp[idB]->gType != WLZ_GREY_UBYTE) { errNum = WLZ_ERR_GREY_TYPE; break; } } } } } } /* Scan through the 3D domain setting value in the projection array. */ if(errNum == WLZ_ERR_NONE) { int pIdx, pCnt; WlzDomain *doms; WlzValues *vals = NULL; doms = obj->domain.p->domains; if(itvVal) { vals = obj->values.vox->values; } pCnt = obj->domain.p->lastpl - obj->domain.p->plane1 + 1; #ifdef _OPENMP #pragma omp parallel for #endif for(pIdx = 0; pIdx < pCnt; ++pIdx) { int thrId = 0; if((errNum == WLZ_ERR_NONE) && (doms[pIdx].core != NULL)) { WlzObject *obj2; WlzGreyWSpace gWSp; WlzIntervalWSpace iWSp; WlzErrorNum errNum2 = WLZ_ERR_NONE; #ifdef _OPENMP thrId = omp_get_thread_num(); #endif obj2 = WlzMakeMain(WLZ_2D_DOMAINOBJ, doms[pIdx], (vals)? vals[pIdx]: nullVal, NULL, NULL, &errNum2); if(errNum2 == WLZ_ERR_NONE) { if(itvVal) { errNum2 = WlzInitGreyScan(obj2, &iWSp, &gWSp); } else { errNum2 = WlzInitRasterScan(obj2, &iWSp, WLZ_RASTERDIR_ILIC); } } if(errNum2 == WLZ_ERR_NONE) { double plnZ, vMZX, vMZY; WlzIVertex3 p0, p1; p0.vtZ = p1.vtZ = obj->domain.p->plane1 + pIdx; vMZX = (vMat[0][2] * p0.vtZ) + vMat[0][3] - prjBox.xMin; vMZY = (vMat[1][2] * p0.vtZ) + vMat[1][3] - prjBox.yMin; plnZ = (pln[2] * p0.vtZ) + pln[3]; while(((itvVal == 0) && ((errNum2 = WlzNextInterval(&iWSp)) == WLZ_ERR_NONE)) || ((itvVal != 0) && ((errNum2 = WlzNextGreyInterval(&iWSp)) == WLZ_ERR_NONE))) { int skip = 0; WlzDVertex2 q0, q1; p0.vtX = iWSp.lftpos; p1.vtX = iWSp.rgtpos; p0.vtY = p1.vtY = iWSp.linpos; if(depth > eps) { int c; double d0, d1, plnYZ; /* Clip the 3D line segment p0,p1 using the plane equation. */ plnYZ = (pln[1] * p0.vtY) + plnZ; d0 = (pln[0] * p0.vtX) + plnYZ; d1 = (pln[0] * p1.vtX) + plnYZ; c = ((d1 > depth) << 3) | ((d0 > depth) << 2) | ((d1 < -depth) << 1) | (d0 < -depth); if(c) { if((c == 3) || (c == 12)) /* 00-- or ++00 */ { /* Both out of range, so don't render. */ skip = 1; } else { if(fabs(pln[0]) > eps) { double plnX; plnX = -1.0 / pln[0]; if((c & 1) != 0) /* x0x- */ { p0.vtX = plnX * (plnYZ + depth); } else if((c & 4) != 0) /* x+x0 */ { p0.vtX = plnX * (plnYZ - depth); } if((c & 2) != 0) /* 0x-x */ { p1.vtX = plnX * (plnYZ + depth); } else if((c & 8) != 0) /* +x0x */ { p1.vtX = plnX * (plnYZ - depth); } } } } } if(skip == 0) { q0.vtX = (vMat[0][0] * p0.vtX) + (vMat[0][1] * p0.vtY) + vMZX; q0.vtY = (vMat[1][0] * p0.vtX) + (vMat[1][1] * p0.vtY) + vMZY; q1.vtX = (vMat[0][0] * p1.vtX) + (vMat[0][1] * p1.vtY) + vMZX; q1.vtY = (vMat[1][0] * p1.vtX) + (vMat[1][1] * p1.vtY) + vMZY; switch(intMod) { case WLZ_PROJECT_INT_MODE_NONE: { WlzIVertex2 u0, u1; WLZ_VTX_2_NINT(u0, q0); WLZ_VTX_2_NINT(u1, q1); WlzProjectObjLine((WlzUByte **)(prjAry[thrId]), u0, u1); } break; case WLZ_PROJECT_INT_MODE_DOMAIN: { int np, nq; WlzDVertex3 dq; WlzIVertex2 u0, u1; WLZ_VTX_2_NINT(u0, q0); WLZ_VTX_2_NINT(u1, q1); WLZ_VTX_2_SUB(dq, q0, q1); np = denDom * (iWSp.rgtpos - iWSp.lftpos + 1); nq = (int )ceil(WLZ_VTX_2_LENGTH(dq) + eps); WlzProjectObjLineDom((int **)(prjAry[thrId]), np / nq, u0, u1); } break; case WLZ_PROJECT_INT_MODE_VALUES: if(itvVal) { WlzProjectObjLineVal((int **)(prjAry[thrId]), denVal, gWSp.u_grintptr.ubp, NULL, vMat, vMZX, vMZY, p0, p1); } else { WlzProjectObjLineVal((int **)(prjAry[thrId]), denVal, NULL, gVWSp[thrId], vMat, vMZX, vMZY, p0, p1); } break; } } } (void )WlzEndGreyScan(&iWSp, &gWSp); if(errNum2 == WLZ_ERR_EOO) { errNum2 = WLZ_ERR_NONE; } } (void )WlzFreeObj(obj2); if(errNum2 != WLZ_ERR_NONE) { #ifdef _OPENMP #pragma omp critical { #endif if(errNum == WLZ_ERR_NONE) { errNum = errNum2; } #ifdef _OPENMP } #endif } } } } /* Free grey value workspaces if they were created. */ if(gVWSp) { int idB; for(idB = 0; idB < nThr; ++idB) { WlzGreyValueFreeWSp(gVWSp[idB]); } AlcFree(gVWSp); } if(errNum == WLZ_ERR_NONE) { int idB; size_t idC, bufSz; WlzGreyP buf0, buf1; WlzIVertex2 prjOrg; prjOrg.vtX = prjBox.xMin; prjOrg.vtY = prjBox.yMin; bufSz = prjSz.vtX * prjSz.vtY; for(idB = 1; idB < nThr; ++idB) { if(intMod == WLZ_PROJECT_INT_MODE_NONE) { buf0.ubp = ((WlzUByte ***)(prjAry))[0][0], buf1.ubp = ((WlzUByte ***)(prjAry))[idB][0]; for(idC = 0; idC < bufSz; ++idC) { buf0.ubp[idC] += buf1.ubp[idC]; } } else { buf0.inp = ((int ***)(prjAry))[0][0], buf1.inp = ((int ***)(prjAry))[idB][0]; for(idC = 0; idC < bufSz; ++idC) { buf0.inp[idC] += buf1.inp[idC]; } } } switch(intMod != WLZ_PROJECT_INT_MODE_NONE) { buf0.inp = ((int ***)(prjAry))[0][0]; for(idC = 0; idC < bufSz; ++idC) { buf0.inp[idC] /= 256; } } if(intMod == WLZ_PROJECT_INT_MODE_NONE) { bufObj = WlzAssignObject( WlzFromArray2D((void **)(prjAry[0]), prjSz, prjOrg, WLZ_GREY_UBYTE, WLZ_GREY_UBYTE, 0.0, 1.0, 1, 0, &errNum), NULL); } else { bufObj = WlzAssignObject( WlzFromArray2D((void **)(prjAry[0]), prjSz, prjOrg, WLZ_GREY_INT, WLZ_GREY_INT, 0.0, 1.0, 1, 0, &errNum), NULL); } } /* Free the projection array(s). */ if(prjAry) { int idB; for(idB = 0; idB < nThr; ++idB) { (void )Alc2Free((prjAry[idB])); } AlcFree(prjAry); } /* Make return object using threshold. */ if(errNum == WLZ_ERR_NONE) { WlzPixelV tV; WlzObject *tObj = NULL; tV.type = WLZ_GREY_UBYTE; tV.v.ubv = 1; tObj = WlzAssignObject( WlzThreshold(bufObj, tV, WLZ_THRESH_HIGH, &errNum), NULL); if(tObj) { if(intMod == WLZ_PROJECT_INT_MODE_NONE) { prjObj = WlzMakeMain(tObj->type, tObj->domain, nullVal, NULL, NULL, &errNum); } else { prjObj = WlzMakeMain(tObj->type, tObj->domain, tObj->values, NULL, NULL, &errNum); } } (void )WlzFreeObj(tObj); } (void )WlzFreeObj(bufObj); (void )WlzFree3DViewStruct(vStr1); /* Scale image. */ if(rescaleTr != NULL) { if(errNum == WLZ_ERR_NONE) { WlzObject *tObj = NULL; tObj = WlzAffineTransformObj(prjObj, rescaleTr, WLZ_INTERPOLATION_NEAREST, &errNum); (void )WlzFreeObj(prjObj); prjObj = tObj; } (void )WlzFreeAffineTransform(rescaleTr); } #ifdef WLZ_DEBUG_PROJECT3D_TIME gettimeofday(times + 1, NULL); ALC_TIMERSUB(times + 1, times + 0, times + 2); (void )fprintf(stderr, "WlzGetProjectionFromObject: Elapsed time = %g\n", times[2].tv_sec + (0.000001 * times[2].tv_usec)); #endif /* WLZ_DEBUG_PROJECT3D_TIME */ if(dstErr) { *dstErr = errNum; } return(prjObj); }
int main(int argc, char **argv) { int option, ok = 1, debug = 0, usage = 0, verbose = 0, verboseDat = 0, idx0, index, binFlg = 0, nMatch = 0, useCOfM = 0, maxItr = 200, minSpx = 15, minSegSpx = 10, matchImpNN = 7, noMatching = 0, decompLimit = INT_MAX, removeRefOrg = 1, refMedianSz = 0, srcMedianSz = 0, multipleFiles = 0; double tD0, tD1, delta = 0.01, maxAng = 30 * (ALG_M_PI / 180.0), maxDeform = 0.5, maxDisp = 20.0, refCThr = 20.0, srcCThr = 20.0, refThr = 254.0, srcThr = 254.0, matchImpThr = 2.5, refSmooth = 3.0, srcSmooth = 3.0; FILE *vFP, *lFP = NULL, *fP = NULL; char *inFileStr = NULL, *inTrFileStr = NULL, *outFileBaseStr = NULL, *ctrFileBaseStr = NULL; char secParFile[256]; char *refObjFileStr = NULL, *srcObjFileStr = NULL; WlzThresholdType thrType = WLZ_THRESH_LOW; WlzEffFormat refObjFileType = WLZEFF_FORMAT_WLZ, srcObjFileType = WLZEFF_FORMAT_WLZ; WlzObject *tObj0 = NULL, *refObj3D = NULL, *refObj2D = NULL, *srcObj2D = NULL, *refCObj2D = NULL, *srcCObj2D = NULL; WlzDVertex2 tDV0, refCOfM, srcCOfM, refObj2DOrg; WlzAffineTransform *inTr = NULL, *inPTr = NULL; WlzThreeDViewStruct *view = NULL; WlzVertexP matchRP, matchSP; WlzInterpolationType interp = WLZ_INTERPOLATION_NEAREST; WlzMatchICPWeightCbData cbData; WlzAffineTransformPrim inTrPrim; WlzErrorNum errNum = WLZ_ERR_NONE; char fileNameBuf[FILENAME_MAX]; const char *errMsg; static char optList[] = "dhvVo:r:Yt:x:y:a:s:efg:k:u:b:B:i:p:A:E:S:F:P:m:n:c:NL"; const int nScatter = 5; const char nullStr[] = "<NULL>", inFileStrDef[] = "-", outFileStrDef[] = "-"; matchRP.v = matchSP.v = NULL; srcCOfM.vtX = srcCOfM.vtY = 0.0; inFileStr = (char *)inFileStrDef; outFileBaseStr = (char *)outFileStrDef; (void )memset(&inTrPrim, 0, sizeof(WlzAffineTransformPrim)); inTrPrim.scale = 1.0; while((usage == 0) && ok && ((option = getopt(argc, argv, optList)) != -1)) { switch(option) { case 'd': debug = 1; break; case 'h': usage = 1; break; case 'v': verbose = 1; break; case 'V': verboseDat = 1; break; case 'o': outFileBaseStr = optarg; break; case 'r': if((refObjFileStr = AlcStrDup(optarg)) == NULL) { ok = 0; (void )fprintf(stderr, "%s Failed to allocate enough memory.\n", *argv); } break; case 'Y': multipleFiles = 1; break; case 't': inTrFileStr = optarg; break; case 'x': if(sscanf(optarg, "%lg", &(inTrPrim.tx)) != 1) { usage = 1; } break; case 'y': if(sscanf(optarg, "%lg", &(inTrPrim.ty)) != 1) { usage = 1; } break; case 'a': if(sscanf(optarg, "%lg", &(inTrPrim.theta)) != 1) { usage = 1; } else { inTrPrim.theta *= ALG_M_PI / 180.0; } break; case 's': if(sscanf(optarg, "%lg", &(inTrPrim.scale)) != 1) { usage = 1; } break; case 'e': useCOfM = 1; break; case 'f': removeRefOrg = 0; break; case 'b': binFlg = 1; thrType = WLZ_THRESH_LOW; usage = WlzMatchICPPlaneParseDPair(optarg, &refThr, &srcThr) != 3; break; case 'B': binFlg = 1; thrType = WLZ_THRESH_HIGH; usage = WlzMatchICPPlaneParseDPair(optarg, &refThr, &srcThr) != 3; break; case 'g': usage = WlzMatchICPPlaneParseDPair(optarg, &refCThr, &srcCThr) != 3; break; case 'k': usage = WlzMatchICPPlaneParseDPair(optarg, &tD0, &tD1) != 3; refMedianSz = WLZ_NINT(tD0); srcMedianSz = WLZ_NINT(tD1); break; case 'u': usage = WlzMatchICPPlaneParseDPair(optarg, &refSmooth, &srcSmooth) != 3; break; case 'i': if((sscanf(optarg, "%d", &maxItr) != 1) || (maxItr <= 0)) { usage = 1; } break; case 'p': if((sscanf(optarg, "%d", &minSpx) != 1) || (minSpx <= 10)) { usage = 1; } break; case 'P': if(sscanf(optarg, "%d", &minSegSpx) != 1) { usage = 1; } break; case 'A': if((sscanf(optarg, "%lg", &maxAng) != 1) || (maxAng < 0.0) || (maxAng > 180.0)) { usage = 1; } else { maxAng *= ALG_M_PI / 180; } break; case 'E': if((sscanf(optarg, "%lg", &delta) != 1) || (delta < 0.0)) { usage = 1; } case 'F': if((sscanf(optarg, "%lg", &maxDeform) != 1) || (maxDeform < 0.0)) { usage = 1; } break; case 'S': if((sscanf(optarg, "%lg", &maxDisp) != 1) || (maxDisp <= 0.0)) { usage = 1; } break; case 'm': if((sscanf(optarg, "%lg", &matchImpThr) != 1) || (matchImpThr < 0.0)) { usage = 1; } break; case 'n': if((sscanf(optarg, "%d", &matchImpNN) != 1) || (matchImpNN < 1)) { usage = 1; } break; case 'c': ctrFileBaseStr = optarg; if(strlen(ctrFileBaseStr) > (FILENAME_MAX - 16)) { usage = 1; } break; case 'N': noMatching = 1; break; case 'L': interp = WLZ_INTERPOLATION_LINEAR; break; default: usage = 1; break; } } if(usage) { ok = 0; } if(ok) { if((inFileStr == NULL) || (*inFileStr == '\0') || (outFileBaseStr == NULL) || (*outFileBaseStr == '\0')) { ok = 0; usage = 1; } if(ok && (optind < argc)) { if((optind + 1) != argc) { usage = 1; ok = 0; } else { inFileStr = *(argv + optind); } } } if(verbose) { (void )fprintf(stderr, "Parameter and other internal variable values:\n"); (void )fprintf(stderr, " ok = %d\n", ok); (void )fprintf(stderr, " debug = %d\n", debug); (void )fprintf(stderr, " verbose = %d\n", verbose); (void )fprintf(stderr, " verboseDat = %d\n", verboseDat); (void )fprintf(stderr, " outFileBaseStr = %s\n", outFileBaseStr? outFileBaseStr: nullStr); (void )fprintf(stderr, " refObjFileStr = %s\n", refObjFileStr? refObjFileStr: nullStr); (void )fprintf(stderr, " multipleFiles = %d\n", multipleFiles); (void )fprintf(stderr, " inTrFileStr = %s\n", inTrFileStr? inTrFileStr: nullStr); (void )fprintf(stderr, " inTrPrim.tx = %g\n", inTrPrim.tx); (void )fprintf(stderr, " inTrPrim.ty = %g\n", inTrPrim.ty); (void )fprintf(stderr, " inTrPrim.theta = %g (Radians)\n", inTrPrim.theta); (void )fprintf(stderr, " inTrPrim.scale = %g\n", inTrPrim.scale); (void )fprintf(stderr, " useCOfM = %d\n", useCOfM); (void )fprintf(stderr, " removeRefOrg = %d\n", removeRefOrg); (void )fprintf(stderr, " binFlg = %d\n", binFlg); (void )fprintf(stderr, " thrType = %s\n", (thrType == WLZ_THRESH_LOW)? "WLZ_THRESH_LOW": "WLZ_THRESH_HIGH"); (void )fprintf(stderr, " refThr = %g\n", refThr); (void )fprintf(stderr, " srcThr = %g\n", srcThr); (void )fprintf(stderr, " refCThr = %g\n", refCThr); (void )fprintf(stderr, " srcCThr = %g\n", srcCThr); (void )fprintf(stderr, " refMedianSz = %d\n", refMedianSz); (void )fprintf(stderr, " srcMedianSz = %d\n", srcMedianSz); (void )fprintf(stderr, " refSmooth = %g\n", refSmooth); (void )fprintf(stderr, " srcSmooth = %g\n", srcSmooth); (void )fprintf(stderr, " delta = %g\n", delta); (void )fprintf(stderr, " maxItr = %d\n", maxItr); (void )fprintf(stderr, " minSpx = %d\n", minSpx); (void )fprintf(stderr, " maxAng = %g (Radians)\n", maxAng); (void )fprintf(stderr, " maxDeform = %g\n", maxDeform); (void )fprintf(stderr, " maxDisp = %g\n", maxDisp); (void )fprintf(stderr, " matchImpThr = %g\n", matchImpThr); (void )fprintf(stderr, " matchImpNN = %d\n", matchImpNN); (void )fprintf(stderr, " ctrFileBaseStr = %s\n", ctrFileBaseStr? ctrFileBaseStr: nullStr); (void )fprintf(stderr, " noMatching = %d\n", noMatching); (void )fprintf(stderr, " usage = %d\n", usage); } /* Create the initial affine transform and it's inverse. */ if(ok) { if(inTrFileStr) { tObj0 = NULL; if(((fP = fopen(inTrFileStr, "r")) == NULL) || ((tObj0 = WlzReadObj(fP, &errNum)) == NULL) || (tObj0->type != WLZ_AFFINE_TRANS) || (tObj0->domain.core == NULL)) { errNum = WLZ_ERR_READ_INCOMPLETE; } else { inTr = WlzAffineTransformCopy(tObj0->domain.t, &errNum); } if(fP) { (void )fclose(fP); fP = NULL; } if(tObj0) { WlzFreeObj(tObj0); tObj0 = NULL; } } else { inTr = WlzMakeAffineTransform(WLZ_TRANSFORM_2D_AFFINE, &errNum); if(errNum == WLZ_ERR_NONE) { errNum = WlzAffineTransformPrimSet(inTr, inTrPrim); } } if(errNum == WLZ_ERR_NONE) { if(verbose) { (void )fprintf(stderr, "Affine transform inTr = \n"); (void )AlcDouble2WriteAsci(stderr, inTr->mat, 3, 3); } } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s: Failed to set initial affine transform (%s).\n", *argv, errMsg); } } /* If the reference file name was given on the command line then it use it * in place of the reference file name in the section parameters bibfile. */ if(ok && refObjFileStr) { if(((refObj3D = WlzAssignObject( WlzEffReadObj(NULL, refObjFileStr, refObjFileType, 0, 0, 0, &errNum), NULL)) == NULL) || (errNum != WLZ_ERR_NONE)) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to read the reference object from file %s (%s).\n", *argv, refObjFileStr, errMsg); } } if(ok) { if((lFP = (strcmp(inFileStr, "-")? fopen(inFileStr, "r"): stdin)) == NULL) { ok = 0; (void )fprintf(stderr, "%s Failed to open the input section parameters file %s.\n", *argv, inFileStr); } } /* Get each input section parameters file and process it. */ index = 0; while(ok && ((fP = WlzMatchICPPlaneSecParFile(lFP, multipleFiles, index, secParFile)) != NULL)) { errNum = WlzMatchICPPlaneReadSecParam(fP, &view, refObjFileStr? NULL: &refObjFileStr, &refObjFileType, refObj3D? NULL: &refObj3D, &srcObjFileStr, &srcObjFileType, &srcObj2D); /* Note: srcObj2D assigned in WlzMatchICPPlaneReadSecParam(). */ if(errNum == WLZ_ERR_NONE) { if(verboseDat) { if(verbose) { (void )fprintf(stderr, "Writing srcObj2D to dbg-srcObj2D.wlz.\n"); } if((vFP = fopen("dbg-srcObj2D.wlz", "w")) != NULL) { (void )WlzWriteObj(vFP, srcObj2D); (void )fclose(vFP); } } errNum = WlzInit3DViewStruct(view, refObj3D); } if(fP) { fclose(fP); fP = NULL; } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to read input section parameters from file %s (%s).\n", argv[0], secParFile, errMsg); } /* Create the section object. */ if(ok) { refObj2D = WlzAssignObject( WlzMatchICPPlaneGetSection(refObj3D, view, interp, &errNum), NULL); if((errNum == WLZ_ERR_NONE) && (refObj2D != NULL) && (refObj2D->type = WLZ_2D_DOMAINOBJ) && (refObj2D->domain.core)) { refObj2DOrg.vtX = refObj2D->domain.i->kol1; refObj2DOrg.vtY = refObj2D->domain.i->line1; if(verboseDat) { if(verbose) { (void )fprintf(stderr, "Writing refObj2D to dbg-refObj2D.wlz.\n"); } if((vFP = fopen("dbg-refObj2D.wlz", "w")) != NULL) { (void )WlzWriteObj(vFP, refObj2D); (void )fclose(vFP); } } } else { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to get section from reference object (%s).\n", argv[0], errMsg); } } /* Create the contour objects. */ if(ok) { refCObj2D = WlzMatchICPPlaneCreateContourObj(refObj2D, binFlg, thrType, refThr, refMedianSz, refSmooth, refCThr, minSpx, debug, verboseDat? "dbg-refObj2D.wlz": NULL, &errNum); if(errNum == WLZ_ERR_NONE) { srcCObj2D = WlzMatchICPPlaneCreateContourObj(srcObj2D, binFlg, thrType, srcThr, srcMedianSz, srcSmooth, srcCThr, minSpx, debug, verboseDat? "dbg-srcObj2D.wlz": NULL, &errNum); } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to compute contours (%s).\n", argv[0], errMsg); } } /* Compute translation using centre of mass if required. Then create * modified initial and inverse transforms for this plane. */ if(ok) { if(useCOfM) { if(verbose) { (void )fprintf(stderr, "Using centre of mass to refine initial affine transform.\n"); } refCOfM = WlzCentreOfMass2D(refCObj2D, 0, NULL, &errNum); tObj0 = NULL; if(errNum == WLZ_ERR_NONE) { tObj0 = WlzAssignObject( WlzAffineTransformObj(srcCObj2D, inTr, WLZ_INTERPOLATION_NEAREST, &errNum), NULL); } if(errNum == WLZ_ERR_NONE) { srcCOfM = WlzCentreOfMass2D(tObj0, 0, NULL, &errNum); } (void )WlzFreeObj(tObj0); if(errNum == WLZ_ERR_NONE) { if(verbose) { (void )fprintf(stderr, "centres of mass are: refCOfM = {%g,%g}, srcCOfM = {%g,%g}.\n", refCOfM.vtX, refCOfM.vtY, srcCOfM.vtX, srcCOfM.vtY); } inPTr = WlzAffineTransformCopy(inTr, &errNum); } if(errNum == WLZ_ERR_NONE) { WLZ_VTX_2_SUB(tDV0, refCOfM, srcCOfM); inPTr->mat[0][2] += tDV0.vtX; inPTr->mat[1][2] += tDV0.vtY; } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to modify transform using centre of mass (%s).\n", argv[0], errMsg); } } if(errNum == WLZ_ERR_NONE) { if(verbose) { (void )fprintf(stderr, "Affine transform inPTr = "); if(inPTr) { (void )fprintf(stderr, "\n"); (void )AlcDouble2WriteAsci(stderr, inPTr->mat, 3, 3); } else { (void )fprintf(stderr, "Identity\n"); } } } } if(ok && ctrFileBaseStr) { if(multipleFiles) { sprintf(fileNameBuf, "%s_%06d_ctr_ref.wlz", ctrFileBaseStr, index); } else { sprintf(fileNameBuf, "%s_ctr_ref.wlz", ctrFileBaseStr); } errNum = WLZ_ERR_FILE_OPEN; ok = (fP = fopen(fileNameBuf, "w")) != NULL; if(ok) { ok = (errNum = WlzWriteObj(fP, refCObj2D)) == WLZ_ERR_NONE; } if(fP) { (void )fclose(fP); fP = NULL; } if(ok) { if(multipleFiles) { sprintf(fileNameBuf, "%s_%06d_ctr_src.wlz", ctrFileBaseStr, index); } else { sprintf(fileNameBuf, "%s_ctr_src.wlz", ctrFileBaseStr); } ok = (fP = fopen(fileNameBuf, "w")) != NULL; } if(ok) { ok = (errNum = WlzWriteObj(fP, srcCObj2D)) == WLZ_ERR_NONE; } if(fP) { (void )fclose(fP); fP = NULL; } tObj0 = NULL; if(ok) { tObj0 = WlzAffineTransformObj(srcCObj2D, inPTr, WLZ_INTERPOLATION_NEAREST, &errNum); ok = errNum == WLZ_ERR_NONE; } if(ok) { if(multipleFiles) { sprintf(fileNameBuf, "%s_%06d_ctr_itrsrc.wlz", ctrFileBaseStr, index); } else { sprintf(fileNameBuf, "%s_ctr_itrsrc.wlz", ctrFileBaseStr); } ok = (fP = fopen(fileNameBuf, "w")) != NULL; } if(ok) { ok = (errNum = WlzWriteObj(fP, tObj0)) == WLZ_ERR_NONE; } (void )WlzFreeObj(tObj0); if(fP) { (void )fclose(fP); fP = NULL; } if(!ok) { (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to write contour to file %s (%s)\n", argv[0], fileNameBuf, errMsg); } } if(ok && (noMatching == 0)) { /* Set up weighting function callback data. */ cbData.tGM = refCObj2D->domain.ctr->model; cbData.sGM = srcCObj2D->domain.ctr->model; cbData.maxDisp = maxDisp; cbData.nScatter = nScatter; errNum = WlzMatchICPCtr(refCObj2D->domain.ctr, srcCObj2D->domain.ctr, inPTr, maxItr, minSpx, minSegSpx, &nMatch, &matchRP, &matchSP, decompLimit, maxDisp, maxAng, maxDeform, matchImpNN, matchImpThr, WlzMatchICPWeightMatches, &cbData, delta); if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to compute tie-points from contours (%s).\n", argv[0], errMsg); } } if(ok && verboseDat) { if(verbose) { (void )fprintf(stderr, "Writing tie points to dbg-tiepoints.num.\n"); } if((vFP = fopen("dbg-tiepoints.num", "w")) != NULL) { for(idx0 = 0; idx0 < nMatch; ++ idx0) { (void )fprintf(vFP, "%g %g %g %g\n", (matchSP.d2 + idx0)->vtX, (matchSP.d2 + idx0)->vtY, (matchRP.d2 + idx0)->vtX - (matchSP.d2 + idx0)->vtX, (matchRP.d2 + idx0)->vtY - (matchSP.d2 + idx0)->vtY); } (void )fclose(vFP); } } if(ok && ctrFileBaseStr) { if(multipleFiles) { sprintf(fileNameBuf, "%s_%06d_ctr_dcp.wlz", ctrFileBaseStr, index); } else { sprintf(fileNameBuf, "%s_ctr_dcp.wlz", ctrFileBaseStr); } if((fP = fopen(fileNameBuf, "w")) == NULL) { ok = 0; (void )fprintf(stderr, "%s Failed to open contour file %s\n", argv[0], fileNameBuf); } else { if((errNum = WlzWriteObj(fP, srcCObj2D)) != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to write contour to file %s (%s)\n", argv[0], fileNameBuf, errMsg); } (void )fclose(fP); fP = NULL; } } /* Write the new section parameters file together with the computed * tie-points. */ if(ok) { if(multipleFiles) { sprintf(fileNameBuf, "%s_%06d.bib", outFileBaseStr, index); } else { sprintf(fileNameBuf, "%s.bib", outFileBaseStr); } if((fP = fopen(fileNameBuf, "w")) == NULL) { ok = 0; (void )fprintf(stderr, "%s Failed to open the output section parameters file %s.\n", *argv, fileNameBuf); } } if(ok) { if(verbose) { (void )fprintf(stderr, "Writing section parameters.\n"); } errNum = WlzMatchICPPlaneWriteSecParam(fP, view, refObjFileStr, refObjFileType, srcObjFileStr, srcObjFileType, nMatch, matchRP.d2, matchSP.d2, removeRefOrg? &refObj2DOrg: NULL); if(fP && strcmp(outFileBaseStr, "-")) { fclose(fP); fP = NULL; } if(errNum != WLZ_ERR_NONE) { ok = 0; (void )WlzStringFromErrorNum(errNum, &errMsg); (void )fprintf(stderr, "%s Failed to write output section parameters to file %s (%s).\n", argv[0], fileNameBuf, errMsg); } } WlzFreeAffineTransform(inPTr); inPTr = NULL; ++index; } (void )WlzFree3DViewStruct(view); AlcFree(refObjFileStr); AlcFree(srcObjFileStr); AlcFree(matchRP.v); AlcFree(matchSP.v); (void )WlzFreeAffineTransform(inTr); (void )WlzFreeObj(refObj3D); (void )WlzFreeObj(refObj2D); (void )WlzFreeObj(srcObj2D); (void )WlzFreeObj(refCObj2D); (void )WlzFreeObj(srcCObj2D); if(usage) { (void )fprintf(stderr, "Usage: %s%s%s%s", *argv, " [-h] [-d] [-v] [-V]\n" " [-o<output file base>] [-r <reference file>]\n" " [-Y] [-t#] [-x#] [-y#] [-a#] [-s#] [-e]\n" " [-g#,#] [-k#,#] [-u#,#] [-b #] [-B #]\n" " [-f] [-i#] [-s#] [-A#] [-S#] [-F#] [-m#] [-n#]\n" " [-c<contour file base>] [-N] [-L]\n" " [<section parameters file>]\n" "Version: ", WlzVersion(), "\n" "Options:\n" " -h Prints this usage information.\n" " -d Perform extra tests to aid debuging.\n" " -E Tolerance in mean registration metric value.\n" " -v Be verbose, lots of text output to the standard error output!\n" " -V Be verbose with Woolz objects and data, with file name names\n" " prefixed by dbg-.\n" " -o Output file base.\n" " -r Reference file.\n" " -Y The section parameters file is a list of section parameters\n" " files, one per line.\n" " -e Use centres of mass of geometric models to compute translation,\n" " with this translaton being applied after the optional initial\n" " affine transform.\n" " -t Initial affine transform (if given all initial affine\n" " transform primitives are ignored).\n" " -x Initial horizontal translation.\n" " -y Initial vertical translation.\n" " -a Initial angle of rotation (degrees).\n" " -s Initial scale factor.\n" " -g Maximal gradient contour thresholds, with the format:\n" " <ref threshold>,<src threshold>, either may be omitted.\n" " -k Median filter size, with the format:\n" " <ref size>,<src size>, either may be omitted.\n" " -u Gaussian smoothing factors, with the format:\n" " <ref smooth>,<src smooth>, either may be omitted.\n" " -b Low threshold values used to produce binary mask images for\n" " matching instead of the grey valued images, with objects\n" " having values at or below the given thresholds.\n" " -B High threshold values used to produce binary mask images for\n" " matching instead of the grey valued images, with objects\n" " having values above the given thresholds.\n" " -f Keep the reference offset in the reference tie-points (MAPaint\n" " doesn't do this).\n" " -i Maximum number of iterations.\n" " -p Minimum number of simplices per shell.\n" " -P Minimum number of simplices per matched shell segment, with a\n" " pair of correspondence points possibly being generated per\n" " matched shell segment.\n" " -A Maximum angle (degrees) from a global transformation.\n" " -S Maximum displacement from a global transformed position.\n" " -F Maximum deformation from a global transformation.\n" " -m Implausibility threshold for rejecting implausible\n" " correspondence points which should be greater than zero,\n" " although the useful range is probably [0.5-5.0]. Higher\n" " values allow more implausible matches to be returned.\n" " -n Number of match points in neighbourhood when checking the\n" " plausibility of the correspondence points.\n" " -c Outputs the computed and decomposed geometric models using\n" " the given file base.\n" " -N Don't compute the tie-points.\n" " -L Use linear interpolation (instead of nearest neighbour) when\n" " cuting sections.\n" " Reads either a 2D or 3D reference object and an MAPaint section\n" "parameters file. Computes tie-points and then writes a new MAPaint\n" "section parameters file which includes the tie-points.\n" " An initial affine transform is computed from the (optional) initial\n" "translation, rotation and scale parameters. A centre of mass can be\n" "computed to improve the initial translation estimates. If a centre of\n" "mass computation is used then the images must have background with\n" "high values and foreground with low values. This initial affine\n" "transform is appiled to the source image before computing the\n" "tie-points. Once computed, the tie-points are transformed using the\n" "inverse of the intial transform, before output.\n" " The tie-points are computed using an ICP based matching algorithm\n" "in which geometric models built from the maximal gradient edges\n" "extracted from the computed section of the reference object and\n" "the source object (refered to in the section parameters file).\n" " To aid rejection of poor tie-points, the tie-points are ranked by\n" "plausibility, with the most plausible first.\n"); } return(!ok); }