Sample CodeOverviewThe sample code below illustrates the use of the BoolDll library. It performs one of the following boolean operations (OR, DIFF, XOR, AND) on two polygons and writes the results to a DXF file. Program FlowThe basic calls for using the boolean are listed below: Reserve LicenseGet Handle Set Boolean Parameters Execute Boolean Operation Write the DXF Free Output Return Handle Release License Header#include <stdio.h> #include <strings.h> #include <stdlib.h> #include <booldll.h> #include <unistd.h> #define Grid 0.001 #define COPYRIGHTYR "2009" #define COMPANYINFO "Artwork Conversion Software, Inc.\n\ 417 Ingalls Street, Santa Cruz, CA 95060\n\ Tel: 831 426 8183 Web http://www.artwork.com" void RunBoolean(FILE * strm, int handle, int opcode, int vnum, int *v1, int *v2); Static Variables// the output DXF file name will depend on the operation performed static char *fname[] = { (char*)"or.dxf", (char*)"diff.dxf", (char*)"xor.dxf", (char*)"and.dxf" }; // these are the vertices for the first polygon. The second polygon // will be created by shifting these vertices static int poly_template[] = { 20000, 30000, 50000, 30000, 50000, 10000, 90000, 10000, 90000, 40000, 60000, 70000, 20000, 70000, 20000, 30000 }; Main Program Loopint main (int argc, const char** argv) { fprintf(stderr, "\n%s\n", BoolDllGetVersion()); fprintf(stderr, "(C) %s %s\n\n\n", COPYRIGHTYR, COMPANYINFO); // we define the four operation codes; one of these will be passed to the // boolean library when the boolean is executed. int opcode = UNION_OPCODE; if(argc > 1){ if(strcasecmp(argv[1], "or") == 0) opcode = UNION_OPCODE; else if(strcasecmp(argv[1], "diff") == 0) opcode = DIFFERENCE_OPCODE; else if(strcasecmp(argv[1], "xor") == 0) opcode = XOR_OPCODE; else if(strcasecmp(argv[1], "and") == 0) opcode = INTERSECTION_OPCODE; else{ fprintf(stderr, "USAGE: %s [ or | diff | xor | and ]\n\n", argv[0]); return 0; } } // The working directory is where we will store any temporary files to disk // and also where we look for the input file and write any output files and log files. char workingdir[256]; getcwd(workingdir, sizeof(workingdir)); Reserve the License(s)The very first call should be to reserve a license -- otherwise subsequent calls will fail due to the lack of a license to execute. If you are going to run multiple threads of booldll, you must reserve all of the licenses in advance. After reserving the license, get the handle for the booldll thread. //Reserve 1 BoolDll license if(BoolDllReserveLicenses(workingdir, 1)) fprintf(stderr, "Failed to reserve BoolDll license\n\n"); else{ //Get 1 BoolDll handle int BHandle = BoolDllInit_MT(); if(BHandle < 0) fprintf(stderr, "Failed to get BoolDll handle\n\n"); else{ Create the Two Input PolygonsWe have to get our polygon data set up. In this simple example we simply read the template we set up in the static data section for the first polygon and shift it slightly to create the second polygon. Of course, in a real application the polygon vertices would come from some external source. //Create boolean's polygon input (derived from poly_template) int vnum = 8; int poly_original[16]; int poly_shifted[16]; for(int i = 0; i < vnum*2; i++){ poly_original[i] = poly_template[i]; poly_shifted[i] = poly_template[i]+10000; } Set Boolean ParametersBefore calling the boolean operation, we first must define the various parameters that control the boolean. You will notice that since we are not illustrating the use of the sizing operation we have commented out the parameter settting calls related to sizing. //Set Boolean clip mode to auto (optimal horizontal stripes) BoolClip_Init_MT(1, 100, BOOL_CLIP_MODE_AUTO, BHandle); //Set Boolean output polygon's maximum vertex count to 16384 BoolSet_Maxpts_MT(16384, BHandle); //Redirect Boolean log to /dev/null BoolSetLogFileParm_MT(REMLOGFILENAME_PARM, "/dev/null", BHandle); //Set Sizing Mode (NO_SIZING, STD_SIZING, INCR_SIZING, NON_ISOTR_SIZING) SizingMode_MT(NO_SIZING, BHandle); /* //If sizing is standard or incremental set sizing value BoolSetDoubleParm_MT(SIZING_PARM, 5000.0, BHandle); //If sizing is non-isotropic BoolSetNonIsotrSzParms_MT(4500.0, 5500.0, BHandle); //If sizing mode is incremental or non-isotropic //Set Corner Mode (RIGHT_ANGLE_CORNER, THREE_POINT_CORNER, FIVE_POINT_CORNER) RoundCorners_MT(RIGHT_ANGLE_CORNER, BHandle); */ Execute the BooleanNow that both input polygons have been created and the booldll parameters have been set, we can call the main function of booldll and get back a unionized (or other operation) polygon. //Run Boolean RunBoolean(out, BHandle, opcode, vnum, poly_original, poly_shifted); Create the DXF FileTo create a valid DXF file we first must write the file header. Once that is complete we can write the two input polygons and the resulting booleanized polygon as entities, then a short section to end the DXF file and close it. fprintf(stderr, "Creating output file: %s\n\n", fname[opcode-1]); //Create the output DXF file FILE * out = fopen(fname[opcode-1], "w+"); if(!out) fprintf(stderr, "Failed to create output file\n\n"); else{ //Write DXF file header fprintf(out, " 0\nSECTION\n 2\nTABLES\n 0\nTABLE\n 2\nLAYER\n 70\n 3\n"); fprintf(out, " 0\nLAYER\n 2\nINPUT1\n 70\n 0\n 62\n 1\n 6\nCONTINUOUS\n"); fprintf(out, " 0\nLAYER\n 2\nINPUT2\n 70\n 0\n 62\n 2\n 6\nCONTINUOUS\n"); fprintf(out, " 0\nLAYER\n 2\nOUTPUT\n 70\n 0\n 62\n 3\n 6\nCONTINUOUS\n"); fprintf(out, " 0\nENDTAB\n 0\nENDSEC\n 0\nSECTION\n 2\nENTITIES\n"); //Write original poly to DXF as a zero width closed polyline fprintf(out, " 0\nPOLYLINE\n 8\nINPUT1\n 66\n 1\n 10\n0.0\n 20\n0.0\n"); for(int j = 0; j < vnum*2; j+=2){ fprintf(out, " 0\nVERTEX\n 8\nINPUT1\n 10\n%g\n 20\n%g\n", ((double)poly_original[j])*Grid, ((double)poly_original[j+1])*Grid); } fprintf(out, " 0\nSEQEND\n 8\nINPUT1\n"); //Write the shifted polygon to DXF fprintf(out, " 0\nPOLYLINE\n 8\nINPUT2\n 66\n 1\n 10\n0.0\n 20\n0.0\n"); for(int j = 0; j < vnum*2; j+=2){ fprintf(out, " 0\nVERTEX\n 8\nINPUT2\n 10\n%g\n 20\n%g\n", ((double)poly_shifted[j])*Grid, ((double)poly_shifted[j+1])*Grid); } fprintf(out, " 0\nSEQEND\n 8\nINPUT2\n"); //Write Boolean output polygon(s) to DXF for(int i = 0; i < opnum; i++){ fprintf(strm, " 0\nPOLYLINE\n 8\nOUTPUT\n 66\n 1\n 10\n0.0\n 20\n0.0\n"); for(int j = 0; j < ovnum[i]*2; j+=2){ fprintf(strm, " 0\nVERTEX\n 8\nOUTPUT\n 10\n%g\n 20\n%g\n", ((double)overt[i][j])*Grid, ((double)overt[i][j+1])*Grid); } fprintf(strm, " 0\nSEQEND\n 8\nOUTPUT\n"); //Write end of DXF file fprintf(out, " 0\nENDSEC\n 0\nEOF\n"); //Close DXF file fclose(out); out = NULL; Free OutputNow we release memory used by the boolean operation. //Cleanup Boolean output BoolRelease_memory(overt, ovnum, opnum); Return the Handle//Return BoolDll handle if(BoolDllClose_MT(BHandle)) fprintf(stderr, "Failed to return BoolDll handle\n\n"); Release the License} //Release all reserved BoolDll licenses BoolDllReleaseLicenses(); } return 0; } RunBooleanvoid RunBoolean(FILE * strm, int handle, int opcode, int vnum, int *v1, int *v2) { int ** overt = NULL; int * ovnum = NULL; int opnum = 0; //Booleanize input polygons int ret = Boolean_MT(&overt, &ovnum, &opnum, &v1, &vnum, 1, &v2, &vnum, 1, opcode, handle); if(ret) fprintf(stderr, "Boolean Error (opcode %d): %d\n\n", opcode, ret); else{ } } |