void Object_To_STEP(struct directory *dp, struct rt_db_internal *intern, struct rt_wdb *wdbp, AP203_Contents *sc) { struct bn_tol tol; ON_Brep **brep; STEPentity *brep_shape; STEPentity *brep_product; STEPentity *brep_manifold; RT_CK_DB_INTERNAL(intern); if (sc->solid_to_step->find(dp) != sc->solid_to_step->end()) return; if (sc->comb_to_step->find(dp) != sc->comb_to_step->end()) return; switch (intern->idb_minor_type) { case DB5_MINORTYPE_BRLCAD_BREP: RT_BREP_TEST_MAGIC((struct rt_brep_internal *)(intern->idb_ptr)); (void)ON_BRep_to_STEP(dp, ((struct rt_brep_internal *)(intern->idb_ptr))->brep, sc, &brep_shape, &brep_product, &brep_manifold); (*sc->solid_to_step)[dp] = brep_product; (*sc->solid_to_step_shape)[dp] = brep_shape; (*sc->solid_to_step_manifold)[dp] = brep_manifold; break; case DB5_MINORTYPE_BRLCAD_COMBINATION: (void)Comb_Tree_to_STEP(dp, wdbp, sc); break; default: /* If it isn't already a BRep and it's not a comb, try to make it * into a BRep */ ON_Brep *brep_obj = ON_Brep::New(); if (intern->idb_meth->ft_brep != NULL) { tol.magic = BN_TOL_MAGIC; tol.dist = BN_TOL_DIST; tol.dist_sq = tol.dist * tol.dist; tol.perp = SMALL_FASTF; tol.para = 1.0 - tol.perp; brep = &brep_obj; intern->idb_meth->ft_brep(brep, intern, &tol); if (!(*brep)) { bu_log("failure to convert brep %s (object type %s)\n", dp->d_namep, intern->idb_meth->ft_label); ON_BRep_to_STEP(dp, NULL, sc, &brep_shape, &brep_product, &brep_manifold); } else { ON_BRep_to_STEP(dp, *brep, sc, &brep_shape, &brep_product, &brep_manifold); } (*sc->solid_to_step)[dp] = brep_product; (*sc->solid_to_step_shape)[dp] = brep_shape; (*sc->solid_to_step_manifold)[dp] = brep_manifold; } else { /* Out of luck */ ON_BRep_to_STEP(dp, NULL, sc, &brep_shape, &brep_product, &brep_manifold); (*sc->solid_to_step)[dp] = brep_product; (*sc->solid_to_step_shape)[dp] = brep_shape; (*sc->solid_to_step_manifold)[dp] = brep_manifold; bu_log("WARNING: No Brep representation available (object type %s) - object %s will be empty in the STEP output.\n", intern->idb_meth->ft_label, dp->d_namep); } delete brep_obj; break; } }
int ged_brep(struct ged *gedp, int argc, const char *argv[]) { struct bn_vlblock*vbp; const char *solid_name; static const char *usage = "brep <obj> [command|brepname|suffix] "; struct directory *ndp; struct rt_db_internal intern; struct rt_brep_internal* bi; struct brep_specific* bs; struct soltab *stp; char commtag[64]; char namebuf[64]; int i, j, real_flag, valid_command, ret; const char *commands[] = {"info", "plot", "translate", "intersect", "csg", "u", "i", "-"}; int num_commands = (int)(sizeof(commands) / sizeof(const char *)); db_op_t op = DB_OP_NULL; GED_CHECK_DATABASE_OPEN(gedp, GED_ERROR); GED_CHECK_DRAWABLE(gedp, GED_ERROR); GED_CHECK_ARGC_GT_0(gedp, argc, GED_ERROR); /* initialize result */ bu_vls_trunc(gedp->ged_result_str, 0); /* must be wanting help */ if (argc < 2) { bu_vls_printf(gedp->ged_result_str, "Usage: %s\n\t%s\n", argv[0], usage); bu_vls_printf(gedp->ged_result_str, "commands:\n"); bu_vls_printf(gedp->ged_result_str, "\tvalid - report on validity of specific BREP\n"); bu_vls_printf(gedp->ged_result_str, "\tinfo - return count information for specific BREP\n"); bu_vls_printf(gedp->ged_result_str, "\tinfo S [index] - return information for specific BREP 'surface'\n"); bu_vls_printf(gedp->ged_result_str, "\tinfo F [index] - return information for specific BREP 'face'\n"); bu_vls_printf(gedp->ged_result_str, "\tplot - plot entire BREP\n"); bu_vls_printf(gedp->ged_result_str, "\tplot S [index] - plot specific BREP 'surface'\n"); bu_vls_printf(gedp->ged_result_str, "\tplot F [index] - plot specific BREP 'face'\n"); bu_vls_printf(gedp->ged_result_str, "\tcsg - convert BREP to implicit primitive CSG tree\n"); bu_vls_printf(gedp->ged_result_str, "\ttranslate SCV index i j dx dy dz - translate a surface control vertex\n"); bu_vls_printf(gedp->ged_result_str, "\tintersect <obj2> <i> <j> [PP|PC|PS|CC|CS|SS] - BREP intersections\n"); bu_vls_printf(gedp->ged_result_str, "\tu|i|- <obj2> <output> - BREP boolean evaluations\n"); bu_vls_printf(gedp->ged_result_str, "\t[brepname] - convert the non-BREP object to BREP form\n"); bu_vls_printf(gedp->ged_result_str, "\t --no-evaluation [suffix] - convert non-BREP comb to unevaluated BREP form\n"); return GED_HELP; } if (argc < 2 || argc > 11) { bu_vls_printf(gedp->ged_result_str, "Usage: %s %s", argv[0], usage); return GED_ERROR; } solid_name = argv[1]; if ((ndp = db_lookup(gedp->ged_wdbp->dbip, solid_name, LOOKUP_NOISY)) == RT_DIR_NULL) { bu_vls_printf(gedp->ged_result_str, "Error: %s is not a solid or does not exist in database", solid_name); return GED_ERROR; } else { real_flag = (ndp->d_addr == RT_DIR_PHONY_ADDR) ? 0 : 1; } if (!real_flag) { /* solid doesn't exist - don't kill */ bu_vls_printf(gedp->ged_result_str, "Error: %s is not a real solid", solid_name); return GED_OK; } GED_DB_GET_INTERNAL(gedp, &intern, ndp, bn_mat_identity, &rt_uniresource, GED_ERROR); RT_CK_DB_INTERNAL(&intern); bi = (struct rt_brep_internal*)intern.idb_ptr; if (BU_STR_EQUAL(argv[2], "valid")) { int valid = rt_brep_valid(&intern, gedp->ged_result_str); return (valid) ? GED_OK : GED_ERROR; } if (BU_STR_EQUAL(argv[2], "intersect")) { /* handle surface-surface intersection */ struct rt_db_internal intern2; /* we need exactly 6 or 7 arguments */ if (argc != 6 && argc != 7) { bu_vls_printf(gedp->ged_result_str, "There should be 6 or 7 arguments for intersection.\n"); bu_vls_printf(gedp->ged_result_str, "See the usage for help.\n"); return GED_ERROR; } /* get the other solid */ if ((ndp = db_lookup(gedp->ged_wdbp->dbip, argv[3], LOOKUP_NOISY)) == RT_DIR_NULL) { bu_vls_printf(gedp->ged_result_str, "Error: %s is not a solid or does not exist in database", argv[3]); return GED_ERROR; } else { real_flag = (ndp->d_addr == RT_DIR_PHONY_ADDR) ? 0 : 1; } if (!real_flag) { /* solid doesn't exist - don't kill */ bu_vls_printf(gedp->ged_result_str, "Error: %s is not a real solid", argv[3]); return GED_OK; } GED_DB_GET_INTERNAL(gedp, &intern2, ndp, bn_mat_identity, &rt_uniresource, GED_ERROR); i = atoi(argv[4]); j = atoi(argv[5]); vbp = rt_vlblock_init(); if (argc == 6 || BU_STR_EQUAL(argv[6], "SS")) { brep_intersect_surface_surface(&intern, &intern2, i, j, vbp); } else if (BU_STR_EQUAL(argv[6], "PP")) { brep_intersect_point_point(&intern, &intern2, i, j); } else if (BU_STR_EQUAL(argv[6], "PC")) { brep_intersect_point_curve(&intern, &intern2, i, j); } else if (BU_STR_EQUAL(argv[6], "PS")) { brep_intersect_point_surface(&intern, &intern2, i, j); } else if (BU_STR_EQUAL(argv[6], "CC")) { brep_intersect_curve_curve(&intern, &intern2, i, j); } else if (BU_STR_EQUAL(argv[6], "CS")) { brep_intersect_curve_surface(&intern, &intern2, i, j); } else { bu_vls_printf(gedp->ged_result_str, "Invalid intersection type %s.\n", argv[6]); } _ged_cvt_vlblock_to_solids(gedp, vbp, namebuf, 0); bn_vlblock_free(vbp); vbp = (struct bn_vlblock *)NULL; rt_db_free_internal(&intern); rt_db_free_internal(&intern2); return GED_OK; } if (BU_STR_EQUAL(argv[2], "csg")) { /* Call csg conversion routine */ struct bu_vls bname_csg; bu_vls_init(&bname_csg); bu_vls_sprintf(&bname_csg, "csg_%s", solid_name); if (db_lookup(gedp->ged_wdbp->dbip, bu_vls_addr(&bname_csg), LOOKUP_QUIET) != RT_DIR_NULL) { bu_vls_printf(gedp->ged_result_str, "%s already exists.", bu_vls_addr(&bname_csg)); bu_vls_free(&bname_csg); return GED_OK; } bu_vls_free(&bname_csg); return _ged_brep_to_csg(gedp, argv[1]); } /* make sure arg isn't --no-evaluate */ if (argc > 2 && argv[2][1] != '-') { op = db_str2op(argv[2]); } if (op != DB_OP_NULL) { /* test booleans on brep. * u: union, i: intersect, -: diff, x: xor */ struct rt_db_internal intern2, intern_res; struct rt_brep_internal *bip; if (argc != 5) { bu_vls_printf(gedp->ged_result_str, "Error: There should be exactly 5 params.\n"); return GED_ERROR; } /* get the other solid */ if ((ndp = db_lookup(gedp->ged_wdbp->dbip, argv[3], LOOKUP_NOISY)) == RT_DIR_NULL) { bu_vls_printf(gedp->ged_result_str, "Error: %s is not a solid or does not exist in database", argv[3]); return GED_ERROR; } else { real_flag = (ndp->d_addr == RT_DIR_PHONY_ADDR) ? 0 : 1; } if (!real_flag) { /* solid doesn't exist - don't kill */ bu_vls_printf(gedp->ged_result_str, "Error: %s is not a real solid", argv[3]); return GED_OK; } GED_DB_GET_INTERNAL(gedp, &intern2, ndp, bn_mat_identity, &rt_uniresource, GED_ERROR); rt_brep_boolean(&intern_res, &intern, &intern2, op); bip = (struct rt_brep_internal*)intern_res.idb_ptr; mk_brep(gedp->ged_wdbp, argv[4], bip->brep); rt_db_free_internal(&intern); rt_db_free_internal(&intern2); rt_db_free_internal(&intern_res); return GED_OK; } if (BU_STR_EQUAL(argv[2], "selection")) { ret = selection_command(gedp, &intern, argc, argv); if (BU_STR_EQUAL(argv[3], "translate") && ret == 0) { GED_DB_PUT_INTERNAL(gedp, ndp, &intern, &rt_uniresource, GED_ERROR); } rt_db_free_internal(&intern); return ret; } if (!RT_BREP_TEST_MAGIC(bi)) { /* The solid is not in brep form. Covert it to brep. */ struct bu_vls bname, suffix; int no_evaluation = 0; bu_vls_init(&bname); bu_vls_init(&suffix); if (argc == 2) { /* brep obj */ bu_vls_sprintf(&bname, "%s_brep", solid_name); bu_vls_sprintf(&suffix, "_brep"); } else if (BU_STR_EQUAL(argv[2], "--no-evaluation")) { no_evaluation = 1; if (argc == 3) { /* brep obj --no-evaluation */ bu_vls_sprintf(&bname, "%s_brep", solid_name); bu_vls_sprintf(&suffix, "_brep"); } else if (argc == 4) { /* brep obj --no-evaluation suffix */ bu_vls_sprintf(&bname, argv[3]); bu_vls_sprintf(&suffix, argv[3]); } } else { /* brep obj brepname/suffix */ bu_vls_sprintf(&bname, argv[2]); bu_vls_sprintf(&suffix, argv[2]); } if (no_evaluation && intern.idb_type == ID_COMBINATION) { struct bu_vls bname_suffix; bu_vls_init(&bname_suffix); bu_vls_sprintf(&bname_suffix, "%s%s", solid_name, bu_vls_addr(&suffix)); if (db_lookup(gedp->ged_wdbp->dbip, bu_vls_addr(&bname_suffix), LOOKUP_QUIET) != RT_DIR_NULL) { bu_vls_printf(gedp->ged_result_str, "%s already exists.", bu_vls_addr(&bname_suffix)); bu_vls_free(&bname); bu_vls_free(&suffix); bu_vls_free(&bname_suffix); return GED_OK; } brep_conversion_comb(&intern, bu_vls_addr(&bname_suffix), bu_vls_addr(&suffix), gedp->ged_wdbp, mk_conv2mm); bu_vls_free(&bname_suffix); } else { struct rt_db_internal brep_db_internal; ON_Brep* brep; if (db_lookup(gedp->ged_wdbp->dbip, bu_vls_addr(&bname), LOOKUP_QUIET) != RT_DIR_NULL) { bu_vls_printf(gedp->ged_result_str, "%s already exists.", bu_vls_addr(&bname)); bu_vls_free(&bname); bu_vls_free(&suffix); return GED_OK; } ret = brep_conversion(&intern, &brep_db_internal, gedp->ged_wdbp->dbip); if (ret == -1) { bu_vls_printf(gedp->ged_result_str, "%s doesn't have a " "brep-conversion function yet. Type: %s", solid_name, intern.idb_meth->ft_label); } else if (ret == -2) { bu_vls_printf(gedp->ged_result_str, "%s cannot be converted " "to brep correctly.", solid_name); } else { brep = ((struct rt_brep_internal *)brep_db_internal.idb_ptr)->brep; ret = mk_brep(gedp->ged_wdbp, bu_vls_addr(&bname), brep); if (ret == 0) { bu_vls_printf(gedp->ged_result_str, "%s is made.", bu_vls_addr(&bname)); } rt_db_free_internal(&brep_db_internal); } } bu_vls_free(&bname); bu_vls_free(&suffix); rt_db_free_internal(&intern); return GED_OK; } BU_ALLOC(stp, struct soltab); if (argc == 2) { bu_vls_printf(gedp->ged_result_str, "Usage: %s %s\n", argv[0], usage); bu_vls_printf(gedp->ged_result_str, "\t%s is in brep form, please input a command.", solid_name); return GED_HELP; } valid_command = 0; for (i = 0; i < num_commands; ++i) { if (BU_STR_EQUAL(argv[2], commands[i])) { valid_command = 1; break; } } if (!valid_command) { bu_vls_printf(gedp->ged_result_str, "Usage: %s %s\n", argv[0], usage); bu_vls_printf(gedp->ged_result_str, "\t%s is in brep form, please input a command.", solid_name); return GED_HELP; } if ((bs = (struct brep_specific*)stp->st_specific) == NULL) { BU_ALLOC(bs, struct brep_specific); bs->brep = bi->brep; bi->brep = NULL; stp->st_specific = (void *)bs; } vbp = rt_vlblock_init(); brep_command(gedp->ged_result_str, solid_name, (const struct rt_tess_tol *)&gedp->ged_wdbp->wdb_ttol, &gedp->ged_wdbp->wdb_tol, bs, bi, vbp, argc, argv, commtag); if (BU_STR_EQUAL(argv[2], "translate")) { bi->brep = bs->brep; GED_DB_PUT_INTERNAL(gedp, ndp, &intern, &rt_uniresource, GED_ERROR); } snprintf(namebuf, 64, "%s%s_", commtag, solid_name); _ged_cvt_vlblock_to_solids(gedp, vbp, namebuf, 0); bn_vlblock_free(vbp); vbp = (struct bn_vlblock *)NULL; rt_db_free_internal(&intern); return GED_OK; }