BRL-CAD
inside.c
Go to the documentation of this file.
1 /* I N S I D E . C
2  * BRL-CAD
3  *
4  * Copyright (c) 2008-2014 United States Government as represented by
5  * the U.S. Army Research Laboratory.
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public License
9  * version 2.1 as published by the Free Software Foundation.
10  *
11  * This library is distributed in the hope that it will be useful, but
12  * WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this file; see the file named COPYING for more
18  * information.
19  */
20 /** @file libged/inside.c
21  *
22  * The inside command.
23  *
24  */
25 
26 #include "common.h"
27 
28 #include <stdlib.h>
29 #include <ctype.h>
30 #include <math.h>
31 #include <string.h>
32 
33 
34 #include "vmath.h"
35 #include "bn.h"
36 #include "nmg.h"
37 #include "rtgeom.h"
38 #include "raytrace.h"
39 #include "db.h"
40 
41 #include "./ged_private.h"
42 
43 
44 static char *p_arb4[] = {
45  "Enter thickness for face 123: ",
46  "Enter thickness for face 124: ",
47  "Enter thickness for face 234: ",
48  "Enter thickness for face 134: ",
49 };
50 
51 
52 static char *p_arb5[] = {
53  "Enter thickness for face 1234: ",
54  "Enter thickness for face 125: ",
55  "Enter thickness for face 235: ",
56  "Enter thickness for face 345: ",
57  "Enter thickness for face 145: ",
58 };
59 
60 
61 static char *p_arb6[] = {
62  "Enter thickness for face 1234: ",
63  "Enter thickness for face 2356: ",
64  "Enter thickness for face 1564: ",
65  "Enter thickness for face 125: ",
66  "Enter thickness for face 346: ",
67 };
68 
69 
70 static char *p_arb7[] = {
71  "Enter thickness for face 1234: ",
72  "Enter thickness for face 567: ",
73  "Enter thickness for face 145: ",
74  "Enter thickness for face 2376: ",
75  "Enter thickness for face 1265: ",
76  "Enter thickness for face 3475: ",
77 };
78 
79 
80 static char *p_arb8[] = {
81  "Enter thickness for face 1234: ",
82  "Enter thickness for face 5678: ",
83  "Enter thickness for face 1485: ",
84  "Enter thickness for face 2376: ",
85  "Enter thickness for face 1265: ",
86  "Enter thickness for face 3487: ",
87 };
88 
89 
90 static char *p_tgcin[] = {
91  "Enter thickness for base (AxB): ",
92  "Enter thickness for top (CxD): ",
93  "Enter thickness for side: ",
94 };
95 
96 
97 static char *p_partin[] = {
98  "Enter thickness for body: ",
99 };
100 
101 
102 static char *p_rpcin[] = {
103  "Enter thickness for front plate (contains V): ",
104  "Enter thickness for back plate: ",
105  "Enter thickness for top plate: ",
106  "Enter thickness for body: ",
107 };
108 
109 
110 static char *p_rhcin[] = {
111  "Enter thickness for front plate (contains V): ",
112  "Enter thickness for back plate: ",
113  "Enter thickness for top plate: ",
114  "Enter thickness for body: ",
115 };
116 
117 
118 static char *p_epain[] = {
119  "Enter thickness for top plate: ",
120  "Enter thickness for body: ",
121 };
122 
123 
124 static char *p_ehyin[] = {
125  "Enter thickness for top plate: ",
126  "Enter thickness for body: ",
127 };
128 
129 
130 static char *p_etoin[] = {
131  "Enter thickness for body: ",
132 };
133 
134 
135 static char *p_nmgin[] = {
136  "Enter thickness for shell: ",
137 };
138 
139 
140 /* finds inside arbs */
141 static int
142 arbin(struct ged *gedp,
143  struct rt_db_internal *ip,
144  fastf_t thick[6],
145  int nface,
146  int cgtype, /* # of points, 4..8 */
147  plane_t planes[6])
148 {
149  struct rt_arb_internal *arb = (struct rt_arb_internal *)ip->idb_ptr;
150  point_t center_pt = VINIT_ZERO;
151  int num_pts=8; /* number of points to solve using rt_arb_3face_intersect */
152  int i;
153 
154  RT_ARB_CK_MAGIC(arb);
155 
156  /* find reference point (center_pt[3]) to find direction of normals */
157  rt_arb_centroid(&center_pt, ip);
158 
159  /* move new face planes for the desired thicknesses
160  * don't do this yet for an arb7 */
161  if (cgtype != 7) {
162  for (i = 0; i < nface; i++) {
163  if ((planes[i][W] - VDOT(center_pt, &planes[i][0])) > 0.0)
164  thick[i] *= -1.0;
165  planes[i][W] += thick[i];
166  }
167  }
168 
169  if (cgtype == 5)
170  num_pts = 4; /* use rt_arb_3face_intersect for first 4 points */
171  else if (cgtype == 7)
172  num_pts = 0; /* don't use rt_arb_3face_intersect for any points */
173 
174  /* find the new vertices by intersecting the new face planes */
175  for (i = 0; i < num_pts; i++) {
176  if (rt_arb_3face_intersect(arb->pt[i], (const plane_t *)planes, cgtype, i*3) < 0) {
177  bu_vls_printf(gedp->ged_result_str, "cannot find inside arb\n");
178  return GED_ERROR;
179  }
180  }
181 
182  /* The following is code for the special cases of arb5 and arb7
183  * These arbs have a vertex that is the intersection of four planes, and
184  * the inside solid may have a single vertex or an edge replacing this vertex
185  */
186  if (cgtype == 5) {
187  /* Here we are only concerned with the one vertex where 4 planes intersect
188  * in the original solid
189  */
190  point_t pt[4];
191  fastf_t dist0, dist1;
192 
193  /* calculate the four possible intersect points */
194  if (bn_mkpoint_3planes(pt[0], planes[1], planes[2], planes[3])) {
195  bu_vls_printf(gedp->ged_result_str, "Cannot find inside arb5\n");
196  bu_vls_printf(gedp->ged_result_str, "Cannot find intersection of three planes for point 0:\n");
197  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[1]));
198  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[2]));
199  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[3]));
200  return GED_ERROR;
201  }
202  if (bn_mkpoint_3planes(pt[1], planes[2], planes[3], planes[4])) {
203  bu_vls_printf(gedp->ged_result_str, "Cannot find inside arb5\n");
204  bu_vls_printf(gedp->ged_result_str, "Cannot find intersection of three planes for point 1:\n");
205  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[2]));
206  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[3]));
207  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[4]));
208  return GED_ERROR;
209  }
210  if (bn_mkpoint_3planes(pt[2], planes[3], planes[4], planes[1])) {
211  bu_vls_printf(gedp->ged_result_str, "Cannot find inside arb5\n");
212  bu_vls_printf(gedp->ged_result_str, "Cannot find intersection of three planes for point 2:\n");
213  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[3]));
214  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[4]));
215  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[1]));
216  return GED_ERROR;
217  }
218  if (bn_mkpoint_3planes(pt[3], planes[4], planes[1], planes[2])) {
219  bu_vls_printf(gedp->ged_result_str, "Cannot find inside arb5\n");
220  bu_vls_printf(gedp->ged_result_str, "Cannot find intersection of three planes for point 3:\n");
221  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[4]));
222  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[1]));
223  bu_vls_printf(gedp->ged_result_str, "\t%f %f %f %f\n", V4ARGS(planes[2]));
224  return GED_ERROR;
225  }
226 
227  if (bn_pt3_pt3_equal(pt[0], pt[1], &gedp->ged_wdbp->wdb_tol)) {
228  /* if any two of the calculates intersection points are equal,
229  * then all four must be equal
230  */
231  for (i = 4; i < 8; i++)
232  VMOVE(arb->pt[i], pt[0]);
233 
234  return GED_OK;
235  }
236 
237  /* There will be an edge where the four planes come together
238  * Two edges of intersection have been calculated
239  * pt[0]<->pt[2]
240  * pt[1]<->pt[3]
241  * the one closest to the non-involved plane (planes[0]) is the
242  * one we want
243  */
244 
245  dist0 = DIST_PT_PLANE(pt[0], planes[0]);
246  if (dist0 < 0.0)
247  dist0 = (-dist0);
248 
249  dist1 = DIST_PT_PLANE(pt[1], planes[0]);
250  if (dist1 < 0.0)
251  dist1 = (-dist1);
252 
253  if (dist0 < dist1) {
254  VMOVE(arb->pt[5], pt[0]);
255  VMOVE(arb->pt[6], pt[0]);
256  VMOVE(arb->pt[4], pt[2]);
257  VMOVE(arb->pt[7], pt[2]);
258  } else {
259  VMOVE(arb->pt[4], pt[3]);
260  VMOVE(arb->pt[5], pt[3]);
261  VMOVE(arb->pt[6], pt[1]);
262  VMOVE(arb->pt[7], pt[1]);
263  }
264  } else if (cgtype == 7) {
265  struct model *m;
266  struct nmgregion *r;
267  struct shell *s = NULL;
268  struct faceuse *fu;
269  struct rt_tess_tol ttol;
270  struct bu_ptbl vert_tab;
271  struct rt_bot_internal *bot;
272 
273  ttol.magic = RT_TESS_TOL_MAGIC;
274  ttol.abs = gedp->ged_wdbp->wdb_ttol.abs;
275  ttol.rel = gedp->ged_wdbp->wdb_ttol.rel;
276  ttol.norm = gedp->ged_wdbp->wdb_ttol.norm;
277 
278  /* Make a model to hold the inside solid */
279  m = nmg_mm();
280 
281  /* get an NMG version of this arb7 */
282  if (!OBJ[ip->idb_type].ft_tessellate || OBJ[ip->idb_type].ft_tessellate(&r, m, ip, &ttol, &gedp->ged_wdbp->wdb_tol)) {
283  bu_vls_printf(gedp->ged_result_str, "Cannot tessellate arb7\n");
285  return GED_ERROR;
286  }
287 
288  /* move face planes */
289  for (i = 0; i < nface; i++) {
290  int found=0;
291 
292  /* look for the face plane with the same geometry as the arb7 planes */
293  s = BU_LIST_FIRST(shell, &r->s_hd);
294  for (BU_LIST_FOR(fu, faceuse, &s->fu_hd)) {
295  struct face_g_plane *fg;
296  plane_t pl;
297 
298  NMG_CK_FACEUSE(fu);
299  if (fu->orientation != OT_SAME)
300  continue;
301 
302  NMG_GET_FU_PLANE(pl, fu);
303  if (bn_coplanar(planes[i], pl, &gedp->ged_wdbp->wdb_tol) > 0) {
304  /* found the NMG face geometry that matches arb face i */
305  found = 1;
306  fg = fu->f_p->g.plane_p;
307  NMG_CK_FACE_G_PLANE(fg);
308 
309  /* move the face by distance "thick[i]" */
310  if (fu->f_p->flip)
311  fg->N[3] += thick[i];
312  else
313  fg->N[3] -= thick[i];
314 
315  break;
316  }
317  }
318  if (!found) {
319  bu_vls_printf(gedp->ged_result_str, "Could not move face plane for arb7, face #%d\n", i);
320  nmg_km(m);
321  return GED_ERROR;
322  }
323  }
324 
325  /* solve for new vertex geometry
326  * This does all the vertices
327  */
328  bu_ptbl_init(&vert_tab, 64, "vert_tab");
329  nmg_vertex_tabulate(&vert_tab, &m->magic);
330  for (i = 0; i < BU_PTBL_END(&vert_tab); i++) {
331  struct vertex *v;
332 
333  v = (struct vertex *)BU_PTBL_GET(&vert_tab, i);
334  NMG_CK_VERTEX(v);
335 
336  if (nmg_in_vert(v, 0, &gedp->ged_wdbp->wdb_tol)) {
337  bu_vls_printf(gedp->ged_result_str, "Could not find coordinates for inside arb7\n");
338  nmg_km(m);
339  bu_ptbl_free(&vert_tab);
340  return GED_ERROR;
341  }
342  }
343  bu_ptbl_free(&vert_tab);
344 
345  /* rebound model */
346  nmg_rebound(m, &gedp->ged_wdbp->wdb_tol);
347 
348  nmg_extrude_cleanup(s, 0, &gedp->ged_wdbp->wdb_tol);
349 
350  /* free old ip pointer */
352 
353  /* convert the NMG to a BOT */
354  bot = (struct rt_bot_internal *)nmg_bot(s, &gedp->ged_wdbp->wdb_tol);
355  nmg_km(m);
356 
357  /* put new solid in "ip" */
358  ip->idb_major_type = DB5_MAJORTYPE_BRLCAD;
359  ip->idb_type = ID_BOT;
360  ip->idb_meth = &OBJ[ID_BOT];
361  ip->idb_ptr = (void *)bot;
362  }
363 
364  return GED_OK;
365 }
366 
367 
368 /* Calculates inside TGC
369  *
370  * thick[0] is thickness for base (AxB)
371  * thick[1] is thickness for top (CxD)
372  * thick[2] is thickness for side
373  */
374 static int
375 tgcin(struct ged *gedp, struct rt_db_internal *ip, fastf_t thick[6])
376 {
377  struct rt_tgc_internal *tgc = (struct rt_tgc_internal *)ip->idb_ptr;
378  vect_t norm; /* unit vector normal to base */
379  fastf_t normal_height; /* height in direction normal to base */
380  vect_t v, h; /* parameters for inside TGC */
381  point_t top; /* vertex at top of inside TGC */
382  fastf_t mag_a, mag_b, mag_c, mag_d; /* lengths of original semi-radii */
383  fastf_t new_mag_a, new_mag_b, new_mag_c, new_mag_d; /* new lengths */
384  vect_t unit_a, unit_b, unit_c, unit_d; /* unit vectors along semi radii */
385  fastf_t ratio;
386 
387  RT_TGC_CK_MAGIC(tgc);
388 
389  VSETALL(unit_a, 0);
390  VSETALL(unit_b, 0);
391  VSETALL(unit_c, 0);
392  VSETALL(unit_d, 0);
393 
394  VCROSS(norm, tgc->a, tgc->b);
395  VUNITIZE(norm);
396 
397  normal_height = VDOT(norm, tgc->h);
398  if (normal_height < 0.0) {
399  normal_height = (-normal_height);
400  VREVERSE(norm, norm);
401  }
402 
403  if ((thick[0] + thick[1]) >= normal_height) {
404  bu_vls_printf(gedp->ged_result_str, "TGC shorter than base and top thicknesses\n");
405  return GED_ERROR;
406  }
407 
408  mag_a = MAGNITUDE(tgc->a);
409  mag_b = MAGNITUDE(tgc->b);
410  mag_c = MAGNITUDE(tgc->c);
411  mag_d = MAGNITUDE(tgc->d);
412 
413  if ((mag_a < VDIVIDE_TOL && mag_c < VDIVIDE_TOL) ||
414  (mag_b < VDIVIDE_TOL && mag_d < VDIVIDE_TOL)) {
415  bu_vls_printf(gedp->ged_result_str, "TGC is too small too create inside solid");
416  return GED_ERROR;
417  }
418 
419  if (mag_a >= VDIVIDE_TOL) {
420  VSCALE(unit_a, tgc->a, 1.0/mag_a);
421  } else if (mag_c >= VDIVIDE_TOL) {
422  VSCALE(unit_a, tgc->c, 1.0/mag_c);
423  }
424 
425  if (mag_c >= VDIVIDE_TOL) {
426  VSCALE(unit_c, tgc->c, 1.0/mag_c);
427  } else if (mag_a >= VDIVIDE_TOL) {
428  VSCALE(unit_c, tgc->a, 1.0/mag_a);
429  }
430 
431  if (mag_b >= VDIVIDE_TOL) {
432  VSCALE(unit_b, tgc->b, 1.0/mag_b);
433  } else if (mag_d >= VDIVIDE_TOL) {
434  VSCALE(unit_b, tgc->d, 1.0/mag_d);
435  }
436 
437  if (mag_d >= VDIVIDE_TOL) {
438  VSCALE(unit_d, tgc->d, 1.0/mag_d);
439  } else if (mag_c >= VDIVIDE_TOL) {
440  VSCALE(unit_d, tgc->b, 1.0/mag_b);
441  }
442 
443  /* Calculate new vertex from base thickness */
444  if (!ZERO(thick[0])) {
445  /* calculate new vertex using similar triangles */
446  ratio = thick[0]/normal_height;
447  VJOIN1(v, tgc->v, ratio, tgc->h);
448 
449  /* adjust lengths of a and c to account for new vertex position */
450  new_mag_a = mag_a + (mag_c - mag_a)*ratio;
451  new_mag_b = mag_b + (mag_d - mag_b)*ratio;
452  } else {
453  /* just copy the existing values */
454  VMOVE(v, tgc->v);
455  new_mag_a = mag_a;
456  new_mag_b = mag_b;
457  }
458 
459  /* calculate new height vector */
460  if (!ZERO(thick[1])) {
461  /* calculate new height vector using similar triangles */
462  ratio = thick[1]/normal_height;
463  VJOIN1(top, tgc->v, 1.0 - ratio, tgc->h);
464 
465  /* adjust lengths of c and d */
466  new_mag_c = mag_c + (mag_a - mag_c)*ratio;
467  new_mag_d = mag_d + (mag_b - mag_d)*ratio;
468  } else {
469  /* just copy existing values */
470  VADD2(top, tgc->v, tgc->h);
471  new_mag_c = mag_c;
472  new_mag_d = mag_d;
473  }
474 
475  /* calculate new height vector based on new vertex and top */
476  VSUB2(h, top, v);
477 
478  if (!ZERO(thick[2])) {
479  /* ther is a side thickness */
480  vect_t ctoa; /* unit vector from tip of C to tip of A */
481  vect_t dtob; /* unit vector from tip of D to tip of B */
482  point_t pt_a, pt_b, pt_c, pt_d; /* points at tips of semi radii */
483  fastf_t delta_ac, delta_bd; /* radius change for thickness */
484  fastf_t dot; /* dot product */
485  fastf_t ratio1, ratio2;
486 
487  if ((thick[2] >= new_mag_a || thick[2] >= new_mag_b) &&
488  (thick[2] >= new_mag_c || thick[2] >= new_mag_d)) {
489  /* can't make a small enough TGC */
490  bu_vls_printf(gedp->ged_result_str, "Side thickness too large\n");
491  return GED_ERROR;
492  }
493 
494  /* approach this as two 2D problems. One is in the plane containing
495  * the a, h, and c vectors. The other is in the plane containing
496  * the b, h, and d vectors.
497  * In the ahc plane:
498  * Calculate the amount that both a and c must be changed to produce
499  * a normal thickness of thick[2]. Use the vector from tip of c to tip
500  * of a and the unit_a vector to get sine of angle that the normal
501  * side thickness makes with vector a (and so also with vector c).
502  * The amount vectors a and c must change is thick[2]/(cosine of that angle).
503  * Similar for the bhd plane.
504  */
505 
506  /* Calculate unit vectors from tips of c/d to tips of a/b */
507  VJOIN1(pt_a, v, new_mag_a, unit_a);
508  VJOIN1(pt_b, v, new_mag_b, unit_b);
509  VJOIN2(pt_c, v, 1.0, h, new_mag_c, unit_c);
510  VJOIN2(pt_d, v, 1.0, h, new_mag_d, unit_d);
511  VSUB2(ctoa, pt_a, pt_c);
512  VSUB2(dtob, pt_b, pt_d);
513  VUNITIZE(ctoa);
514  VUNITIZE(dtob);
515 
516  /* Calculate amount vectors a and c must change */
517  dot = VDOT(ctoa, unit_a);
518  delta_ac = thick[2]/sqrt(1.0 - dot*dot);
519 
520  /* Calculate amount vectors d and d must change */
521  dot = VDOT(dtob, unit_b);
522  delta_bd = thick[2]/sqrt(1.0 - dot*dot);
523 
524  if ((delta_ac > new_mag_a || delta_bd > new_mag_b) &&
525  (delta_ac > new_mag_c || delta_bd > new_mag_d)) {
526  /* Can't make TGC small enough */
527  bu_vls_printf(gedp->ged_result_str, "Side thickness too large\n");
528  return GED_ERROR;
529  }
530 
531  /* Check if changes will make vectors a or d lengths negative */
532  if (delta_ac >= new_mag_c || delta_bd >= new_mag_d) {
533  /* top vertex (height) must move. Calculate similar triangle ratios */
534  if (delta_ac >= new_mag_c)
535  ratio1 = (new_mag_a - delta_ac)/(new_mag_a - new_mag_c);
536  else
537  ratio1 = 1.0;
538 
539  if (delta_bd >= new_mag_d)
540  ratio2 = (new_mag_b - delta_bd)/(new_mag_b - new_mag_d);
541  else
542  ratio2 = 1.0;
543 
544  /* choose the smallest similar triangle for setting new top vertex */
545  if (ratio1 < ratio2)
546  ratio = ratio1;
547  else
548  ratio = ratio2;
549 
550  if (ZERO(ratio1 - ratio) && ratio1 < 1.0) /* c vector must go to zero */
551  new_mag_c = SQRT_SMALL_FASTF;
552  else if (ratio1 > ratio && ratio < 1.0) {
553  /* vector d will go to zero, but vector c will not */
554 
555  /* calculate original length of vector c at new top vertex */
556  new_mag_c = new_mag_c + (new_mag_a - new_mag_c)*(1.0 - ratio);
557 
558  /* now just subtract delta */
559  new_mag_c -= delta_ac;
560  } else /* just change c vector length by delta */
561  new_mag_c -= delta_ac;
562 
563  if (ZERO(ratio2 - ratio) && ratio2 < 1.0) /* vector d must go to zero */
564  new_mag_d = SQRT_SMALL_FASTF;
565  else if (ratio2 > ratio && ratio < 1.0) {
566  /* calculate vector length at new top vertex */
567  new_mag_d = new_mag_d + (new_mag_b - new_mag_d)*(1.0 - ratio);
568 
569  /* now just subtract delta */
570  new_mag_d -= delta_bd;
571  } else /* just adjust length */
572  new_mag_d -= delta_bd;
573 
574  VSCALE(h, h, ratio);
575  new_mag_a -= delta_ac;
576  new_mag_b -= delta_bd;
577  } else if (delta_ac >= new_mag_a || delta_bd >= new_mag_b) {
578  /* base vertex (v) must move */
579 
580  /* Calculate similar triangle ratios */
581  if (delta_ac >= new_mag_a)
582  ratio1 = (new_mag_c - delta_ac)/(new_mag_c - new_mag_a);
583  else
584  ratio1 = 1.0;
585 
586  if (delta_bd >= new_mag_b)
587  ratio2 = (new_mag_d - delta_bd)/(new_mag_d - new_mag_b);
588  else
589  ratio2 = 1.0;
590 
591  /* select smallest triangle to set new base vertex */
592  if (ratio1 < ratio2)
593  ratio = ratio1;
594  else
595  ratio = ratio2;
596 
597  if (ZERO(ratio1 - ratio) && ratio1 < 1.0) /* vector a must go to zero */
598  new_mag_a = SQRT_SMALL_FASTF;
599  else if (ratio1 > ratio && ratio < 1.0) {
600  /* calculate length of vector a if it were at new base location */
601  new_mag_a = new_mag_c + (new_mag_a - new_mag_c)*ratio;
602 
603  /* now just subtract delta */
604  new_mag_a -= delta_ac;
605  } else /* just subtract delta */
606  new_mag_a -= delta_ac;
607 
608  if (ZERO(ratio2 - ratio) && ratio2 < 1.0) /* vector b must go to zero */
609  new_mag_b = SQRT_SMALL_FASTF;
610  else if (ratio2 > ratio && ratio < 1.0) {
611  /* Calculate length of b if it were at new base vector */
612  new_mag_b = new_mag_d + (new_mag_b - new_mag_d)*ratio;
613 
614  /* now just subtract delta */
615  new_mag_b -= delta_bd;
616  } else /* just subtract delta */
617  new_mag_b -= delta_bd;
618 
619  /* adjust height vector using smallest similar triangle ratio */
620  VJOIN1(v, v, 1.0-ratio, h);
621  VSUB2(h, top, v);
622  new_mag_c -= delta_ac;
623  new_mag_d -= delta_bd;
624  } else {
625  /* just change the vector lengths */
626  new_mag_a -= delta_ac;
627  new_mag_b -= delta_bd;
628  new_mag_c -= delta_ac;
629  new_mag_d -= delta_bd;
630  }
631  }
632 
633 /* copy new values into the TGC */
634  VMOVE(tgc->v, v);
635  VMOVE(tgc->h, h);
636  VSCALE(tgc->a, unit_a, new_mag_a);
637  VSCALE(tgc->b, unit_b, new_mag_b);
638  VSCALE(tgc->c, unit_c, new_mag_c);
639  VSCALE(tgc->d, unit_d, new_mag_d);
640 
641  return GED_OK;
642 }
643 
644 
645 /* finds inside of torus */
646 static int
647 torin(struct ged *gedp, struct rt_db_internal *ip, fastf_t thick[6])
648 {
649  struct rt_tor_internal *tor = (struct rt_tor_internal *)ip->idb_ptr;
650 
651  RT_TOR_CK_MAGIC(tor);
652  if (ZERO(thick[0]))
653  return GED_OK;
654 
655  if (thick[0] < 0) {
656  if ((tor->r_h - thick[0]) > (tor->r_a + .01)) {
657  bu_vls_printf(gedp->ged_result_str, "cannot do: r2 > r1\n");
658  return GED_ERROR;
659  }
660  }
661  if (thick[0] >= tor->r_h) {
662  bu_vls_printf(gedp->ged_result_str, "cannot do: r2 <= 0\n");
663  return GED_ERROR;
664  }
665 
666  tor->r_h = tor->r_h - thick[0];
667 
668  return GED_OK;
669 }
670 
671 
672 /* finds inside ell */
673 static int
674 ellin(struct ged *gedp, struct rt_db_internal *ip, fastf_t thick[6])
675 {
676  struct rt_ell_internal *ell = (struct rt_ell_internal *)ip->idb_ptr;
677  int i;
678  fastf_t mag[3], nmag[3];
679 
680  thick[2] = thick[1] = thick[0]; /* uniform thickness */
681 
682  RT_ELL_CK_MAGIC(ell);
683  mag[0] = MAGNITUDE(ell->a);
684  mag[1] = MAGNITUDE(ell->b);
685  mag[2] = MAGNITUDE(ell->c);
686 
687  if (thick[0] > 0 && (mag[0] < thick[0] + RT_LEN_TOL)){
688  bu_vls_printf(gedp->ged_result_str, "Magnitude of ell->a (%.2f) is too small for an inside thickness of %.2f \n", mag[0], thick[0]);
689  return GED_ERROR;
690  }
691  if (thick[1] > 0 && (mag[1] < thick[1] + RT_LEN_TOL)){
692  bu_vls_printf(gedp->ged_result_str, "Magnitude of ell->b (%.2f) is too small for an inside thickness of %.2f \n", mag[1], thick[1]);
693  return GED_ERROR;
694  }
695  if (thick[2] > 0 && (mag[2] < thick[2] + RT_LEN_TOL)){
696  bu_vls_printf(gedp->ged_result_str, "Magnitude of ell->c (%.2f) is too small for an inside thickness of %.2f \n", mag[2], thick[2]);
697  return GED_ERROR;
698  }
699 
700  for (i = 0; i < 3; i++) {
701  nmag[i] = mag[i] - thick[i];
702  }
703  VSCALE(ell->a, ell->a, nmag[0]/mag[0]);
704  VSCALE(ell->b, ell->b, nmag[1]/mag[1]);
705  VSCALE(ell->c, ell->c, nmag[2]/mag[2]);
706 
707  return GED_OK;
708 }
709 
710 
711 /* find inside of particle solid */
712 static int
713 partin(struct ged *UNUSED(gedp), struct rt_db_internal *ip, fastf_t *thick)
714 {
715  struct rt_part_internal *part = (struct rt_part_internal *)ip->idb_ptr;
716 
717  RT_PART_CK_MAGIC(part);
718 
719  if (*thick >= part->part_vrad || *thick >= part->part_hrad)
720  return 1; /* BAD */
721 
722  part->part_vrad -= *thick;
723  part->part_hrad -= *thick;
724 
725  return GED_OK;
726 }
727 
728 
729 /* finds inside of rpc, not quite right - r needs to be smaller */
730 static int
731 rpcin(struct ged *UNUSED(gedp), struct rt_db_internal *ip, fastf_t thick[4])
732 {
733  struct rt_rpc_internal *rpc = (struct rt_rpc_internal *)ip->idb_ptr;
734  fastf_t b;
735  vect_t Bu, Hu, Ru;
736 
737  RT_RPC_CK_MAGIC(rpc);
738 
739  /* get unit coordinate axes */
740  VMOVE(Bu, rpc->rpc_B);
741  VMOVE(Hu, rpc->rpc_H);
742  VCROSS(Ru, Hu, Bu);
743  VUNITIZE(Bu);
744  VUNITIZE(Hu);
745  VUNITIZE(Ru);
746 
747  b = MAGNITUDE(rpc->rpc_B);
748  VJOIN2(rpc->rpc_V, rpc->rpc_V, thick[0], Hu, thick[2], Bu);
749  VSCALE(rpc->rpc_H, Hu, MAGNITUDE(rpc->rpc_H) - thick[0] - thick[1]);
750  VSCALE(rpc->rpc_B, Bu, b - thick[2] - thick[3]);
751  rpc->rpc_r -= thick[3];
752 
753  return GED_OK;
754 }
755 
756 
757 /* XXX finds inside of rhc, not quite right */
758 static int
759 rhcin(struct ged *UNUSED(gedp), struct rt_db_internal *ip, fastf_t thick[4])
760 {
761  struct rt_rhc_internal *rhc = (struct rt_rhc_internal *)ip->idb_ptr;
762  vect_t Bn, Hn, Bu, Hu, Ru;
763 
764  RT_RHC_CK_MAGIC(rhc);
765 
766  VMOVE(Bn, rhc->rhc_B);
767  VMOVE(Hn, rhc->rhc_H);
768 
769  /* get unit coordinate axes */
770  VMOVE(Bu, Bn);
771  VMOVE(Hu, Hn);
772  VCROSS(Ru, Hu, Bu);
773  VUNITIZE(Bu);
774  VUNITIZE(Hu);
775  VUNITIZE(Ru);
776 
777  VJOIN2(rhc->rhc_V, rhc->rhc_V, thick[0], Hu, thick[2], Bu);
778  VSCALE(rhc->rhc_H, Hu, MAGNITUDE(rhc->rhc_H) - thick[0] - thick[1]);
779  VSCALE(rhc->rhc_B, Bu, MAGNITUDE(rhc->rhc_B) - thick[2] - thick[3]);
780  rhc->rhc_r -= thick[3];
781 
782  return GED_OK;
783 }
784 
785 
786 /* finds inside of epa, not quite right */
787 static int
788 epain(struct ged *UNUSED(gedp), struct rt_db_internal *ip, fastf_t thick[2])
789 {
790  struct rt_epa_internal *epa = (struct rt_epa_internal *)ip->idb_ptr;
791  vect_t Hu;
792 
793  RT_EPA_CK_MAGIC(epa);
794 
795  VMOVE(Hu, epa->epa_H);
796  VUNITIZE(Hu);
797 
798  VJOIN1(epa->epa_V, epa->epa_V, thick[0], Hu);
799  VSCALE(epa->epa_H, Hu, MAGNITUDE(epa->epa_H) - thick[0] - thick[1]);
800  epa->epa_r1 -= thick[1];
801  epa->epa_r2 -= thick[1];
802 
803  return GED_OK;
804 }
805 
806 
807 /* finds inside of ehy, not quite right, */
808 static int
809 ehyin(struct ged *UNUSED(gedp), struct rt_db_internal *ip, fastf_t thick[2])
810 {
811  struct rt_ehy_internal *ehy = (struct rt_ehy_internal *)ip->idb_ptr;
812  vect_t Hu;
813 
814  RT_EHY_CK_MAGIC(ehy);
815 
816  VMOVE(Hu, ehy->ehy_H);
817  VUNITIZE(Hu);
818 
819  VJOIN1(ehy->ehy_V, ehy->ehy_V, thick[0], Hu);
820  VSCALE(ehy->ehy_H, Hu, MAGNITUDE(ehy->ehy_H) - thick[0] - thick[1]);
821  ehy->ehy_r1 -= thick[1];
822  ehy->ehy_r2 -= thick[1];
823 
824  return GED_OK;
825 }
826 
827 
828 /* finds inside of eto */
829 static int
830 etoin(struct ged *UNUSED(gedp), struct rt_db_internal *ip, fastf_t thick[1])
831 {
832  fastf_t c;
833  struct rt_eto_internal *eto = (struct rt_eto_internal *)ip->idb_ptr;
834 
835  RT_ETO_CK_MAGIC(eto);
836 
837  c = 1.0 - thick[0]/MAGNITUDE(eto->eto_C);
838  VSCALE(eto->eto_C, eto->eto_C, c);
839  eto->eto_rd -= thick[0];
840 
841  return GED_OK;
842 }
843 
844 
845 /* find inside for NMG */
846 static int
847 nmgin(struct ged *gedp, struct rt_db_internal *ip, fastf_t thick)
848 {
849  struct model *m;
850  struct nmgregion *r;
851 
852  if (ip->idb_type != ID_NMG)
853  return GED_ERROR;
854 
855  m = (struct model *)ip->idb_ptr;
856  NMG_CK_MODEL(m);
857 
858  r = BU_LIST_FIRST(nmgregion, &m->r_hd);
859  while (BU_LIST_NOT_HEAD(r, &m->r_hd)) {
860  struct nmgregion *next_r;
861  struct shell *s;
862 
863  NMG_CK_REGION(r);
864 
865  next_r = BU_LIST_PNEXT(nmgregion, &r->l);
866 
867  s = BU_LIST_FIRST(shell, &r->s_hd);
868  while (BU_LIST_NOT_HEAD(s, &r->s_hd)) {
869  struct shell *next_s;
870 
871  next_s = BU_LIST_PNEXT(shell, &s->l);
872 
874  if (!nmg_kill_cracks(s))
875  (void)nmg_extrude_shell(s, thick, 0, 0, &gedp->ged_wdbp->wdb_tol);
876 
877  s = next_s;
878  }
879 
880  if (BU_LIST_IS_EMPTY(&r->s_hd))
881  nmg_kr(r);
882 
883  r = next_r;
884  }
885 
886  if (BU_LIST_IS_EMPTY(&m->r_hd)) {
887  bu_vls_printf(gedp->ged_result_str, "No inside created\n");
888  nmg_km(m);
889  return GED_ERROR;
890  } else
891  return GED_OK;
892 }
893 
894 
895 int
896 ged_inside_internal(struct ged *gedp, struct rt_db_internal *ip, int argc, const char *argv[], int arg, char *o_name)
897 {
898  int i;
899  struct directory *dp;
900  int cgtype = 8; /* cgtype ARB 4..8 */
901  int nface;
902  fastf_t thick[6];
903  plane_t planes[6];
904  char *newname;
905 
906  /* initialize result */
907  bu_vls_trunc(gedp->ged_result_str, 0);
908 
909  if (ip->idb_type == ID_ARB8) {
910  /* find the comgeom arb type, & reorganize */
911  int uvec[8], svec[11];
912  struct bu_vls error_msg = BU_VLS_INIT_ZERO;
913 
914  if (rt_arb_get_cgtype(&cgtype, (struct rt_arb_internal *)ip->idb_ptr, &gedp->ged_wdbp->wdb_tol, uvec, svec) == 0) {
915  bu_vls_printf(gedp->ged_result_str, "%s: BAD ARB\n", o_name);
916  return GED_ERROR;
917  }
918 
919  /* must find new plane equations to account for
920  * any editing in the es_mat matrix or path to this solid.
921  */
922  if (rt_arb_calc_planes(&error_msg, (struct rt_arb_internal *)ip->idb_ptr, cgtype, planes, &gedp->ged_wdbp->wdb_tol) < 0) {
923  bu_vls_printf(gedp->ged_result_str, "%s\nrt_arb_calc_planes(%s): failed\n", bu_vls_addr(&error_msg), o_name);
924  bu_vls_free(&error_msg);
925  return GED_ERROR;
926  }
927  bu_vls_free(&error_msg);
928  }
929 
930  /* "ip" is loaded with the outside solid data */
931 
932  /* get the inside solid name */
933  if (argc < arg+1) {
934  bu_vls_printf(gedp->ged_result_str, "Enter name of the inside solid: ");
935  return GED_MORE;
936  }
937  if (db_lookup(gedp->ged_wdbp->dbip, argv[arg], LOOKUP_QUIET) != RT_DIR_NULL) {
938  bu_vls_printf(gedp->ged_result_str, "%s: %s already exists.\n", argv[0], argv[arg]);
939  return GED_ERROR;
940  }
941  if (db_version(gedp->ged_wdbp->dbip) < 5 && (int)strlen(argv[arg]) > NAMESIZE) {
942  bu_vls_printf(gedp->ged_result_str, "Database version 4 names are limited to %d characters\n", NAMESIZE);
943  return GED_ERROR;
944  }
945  newname = (char *)argv[arg];
946  ++arg;
947 
948  /* get thicknesses and calculate parameters for newrec */
949  switch (ip->idb_type) {
950 
951  case ID_ARB8: {
952  char **prompt = p_arb6;
953  struct rt_arb_internal *arb = (struct rt_arb_internal *)ip->idb_ptr;
954 
955  nface = 6;
956 
957  switch (cgtype) {
958  case 8:
959  prompt = p_arb8;
960  break;
961 
962  case 7:
963  prompt = p_arb7;
964  break;
965 
966  case 6:
967  prompt = p_arb6;
968  nface = 5;
969  VMOVE(arb->pt[5], arb->pt[6]);
970  break;
971 
972  case 5:
973  prompt = p_arb5;
974  nface = 5;
975  break;
976 
977  case 4:
978  prompt = p_arb4;
979  nface = 4;
980  VMOVE(arb->pt[3], arb->pt[4]);
981  break;
982  }
983 
984  for (i = 0; i < nface; i++) {
985  if (argc < arg+1) {
986  bu_vls_printf(gedp->ged_result_str, "%s", prompt[i]);
987  return GED_MORE;
988  }
989  thick[i] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
990  ++arg;
991  }
992 
993  if (arbin(gedp, ip, thick, nface, cgtype, planes))
994  return GED_ERROR;
995  break;
996  }
997 
998  case ID_TGC:
999  for (i = 0; i < 3; i++) {
1000  if (argc < arg+1) {
1001  bu_vls_printf(gedp->ged_result_str, "%s", p_tgcin[i]);
1002  return GED_MORE;
1003  }
1004  thick[i] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1005  ++arg;
1006  }
1007 
1008  if (tgcin(gedp, ip, thick))
1009  return GED_ERROR;
1010  break;
1011 
1012  case ID_ELL:
1013  if (argc < arg+1) {
1014  bu_vls_printf(gedp->ged_result_str, "Enter desired thickness: ");
1015  return GED_MORE;
1016  }
1017  thick[0] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1018  ++arg;
1019 
1020  if (ellin(gedp, ip, thick))
1021  return GED_ERROR;
1022  break;
1023 
1024  case ID_TOR:
1025  if (argc < arg+1) {
1026  bu_vls_printf(gedp->ged_result_str, "Enter desired thickness: ");
1027  return GED_MORE;
1028  }
1029  thick[0] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1030  ++arg;
1031 
1032  if (torin(gedp, ip, thick))
1033  return GED_ERROR;
1034  break;
1035 
1036  case ID_PARTICLE:
1037  for (i = 0; i < 1; i++) {
1038  if (argc < arg+1) {
1039  bu_vls_printf(gedp->ged_result_str, "%s", p_partin[i]);
1040  return GED_MORE;
1041  }
1042  thick[i] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1043  ++arg;
1044  }
1045 
1046  if (partin(gedp, ip, thick))
1047  return GED_ERROR;
1048  break;
1049 
1050  case ID_RPC:
1051  for (i = 0; i < 4; i++) {
1052  if (argc < arg+1) {
1053  bu_vls_printf(gedp->ged_result_str, "%s", p_rpcin[i]);
1054  return GED_MORE;
1055  }
1056  thick[i] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1057  ++arg;
1058  }
1059 
1060  if (rpcin(gedp, ip, thick))
1061  return GED_ERROR;
1062  break;
1063 
1064  case ID_RHC:
1065  for (i = 0; i < 4; i++) {
1066  if (argc < arg+1) {
1067  bu_vls_printf(gedp->ged_result_str, "%s", p_rhcin[i]);
1068  return GED_MORE;
1069  }
1070  thick[i] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1071  ++arg;
1072  }
1073 
1074  if (rhcin(gedp, ip, thick))
1075  return GED_ERROR;
1076  break;
1077 
1078  case ID_EPA:
1079  for (i = 0; i < 2; i++) {
1080  if (argc < arg+1) {
1081  bu_vls_printf(gedp->ged_result_str, "%s", p_epain[i]);
1082  return GED_MORE;
1083  }
1084  thick[i] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1085  ++arg;
1086  }
1087 
1088  if (epain(gedp, ip, thick))
1089  return GED_ERROR;
1090  break;
1091 
1092  case ID_EHY:
1093  for (i = 0; i < 2; i++) {
1094  if (argc < arg+1) {
1095  bu_vls_printf(gedp->ged_result_str, "%s", p_ehyin[i]);
1096  return GED_MORE;
1097  }
1098  thick[i] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1099  ++arg;
1100  }
1101 
1102  if (ehyin(gedp, ip, thick))
1103  return GED_ERROR;
1104  break;
1105 
1106  case ID_ETO:
1107  for (i = 0; i < 1; i++) {
1108  if (argc < arg+1) {
1109  bu_vls_printf(gedp->ged_result_str, "%s", p_etoin[i]);
1110  return GED_MORE;
1111  }
1112  thick[i] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1113  ++arg;
1114  }
1115 
1116  if (etoin(gedp, ip, thick))
1117  return GED_ERROR;
1118  break;
1119 
1120  case ID_NMG:
1121  if (argc < arg+1) {
1122  bu_vls_printf(gedp->ged_result_str, "%s", *p_nmgin);
1123  return GED_MORE;
1124  }
1125  thick[0] = atof(argv[arg]) * gedp->ged_wdbp->dbip->dbi_local2base;
1126  ++arg;
1127  if (nmgin(gedp, ip, thick[0]))
1128  return GED_ERROR;
1129  break;
1130 
1131  default:
1132  if (ip->idb_type < 0) {
1133  bu_vls_printf(gedp->ged_result_str, "Cannot find inside of uninitialized object.\n");
1134  } else {
1135  bu_vls_printf(gedp->ged_result_str, "Cannot find inside for '%s' solid\n", OBJ[ip->idb_type].ft_name);
1136  }
1137  return GED_ERROR;
1138  }
1139 
1140  /* Add to in-core directory */
1141  dp = db_diradd(gedp->ged_wdbp->dbip, newname, RT_DIR_PHONY_ADDR, 0, RT_DIR_SOLID, (void *)&ip->idb_type);
1142  if (dp == RT_DIR_NULL) {
1143  bu_vls_printf(gedp->ged_result_str, "%s: Database alloc error, aborting\n", argv[0]);
1144  return GED_ERROR;
1145  }
1146  if (rt_db_put_internal(dp, gedp->ged_wdbp->dbip, ip, &rt_uniresource) < 0) {
1147  bu_vls_printf(gedp->ged_result_str, "%s: Database write error, aborting\n", argv[0]);
1148  return GED_ERROR;
1149  }
1150 
1151  bu_vls_printf(gedp->ged_result_str, "%s", argv[2]);
1152  return GED_OK;
1153 }
1154 
1155 
1156 int
1157 ged_inside(struct ged *gedp, int argc, const char *argv[])
1158 {
1159  struct directory *outdp;
1160  struct rt_db_internal intern;
1161  int arg = 1;
1162 
1165  GED_CHECK_ARGC_GT_0(gedp, argc, GED_ERROR);
1166 
1167  /* initialize result */
1168  bu_vls_trunc(gedp->ged_result_str, 0);
1169 
1170  RT_DB_INTERNAL_INIT(&intern);
1171 
1172  if (argc < arg+1) {
1173  bu_vls_printf(gedp->ged_result_str, "Enter name of outside solid: ");
1174  return GED_MORE;
1175  }
1176  if ((outdp = db_lookup(gedp->ged_wdbp->dbip, argv[arg], LOOKUP_QUIET)) == RT_DIR_NULL) {
1177  bu_vls_printf(gedp->ged_result_str, "%s: %s not found", argv[0], argv[arg]);
1178  return GED_ERROR;
1179  }
1180  ++arg;
1181 
1182  if (rt_db_get_internal(&intern, outdp, gedp->ged_wdbp->dbip, bn_mat_identity, &rt_uniresource) < 0) {
1183  bu_vls_printf(gedp->ged_result_str, "Database read error, aborting");
1184  return GED_ERROR;
1185  }
1186 
1187  return ged_inside_internal(gedp, &intern, argc, argv, arg, outdp->d_namep);
1188 }
1189 
1190 
1191 /*
1192  * Local Variables:
1193  * tab-width: 8
1194  * mode: C
1195  * indent-tabs-mode: t
1196  * c-file-style: "stroustrup"
1197  * End:
1198  * ex: shiftwidth=4 tabstop=8
1199  */
#define GED_OK
Definition: ged.h:55
char * d_namep
pointer to name string
Definition: raytrace.h:859
int rt_arb_calc_planes(struct bu_vls *error_msg_ret, struct rt_arb_internal *arb, int type, plane_t planes[6], const struct bn_tol *tol)
Definition: arb8.c:1871
#define BU_LIST_FOR(p, structure, hp)
Definition: list.h:365
#define RT_LEN_TOL
Definition: raytrace.h:169
int rt_db_get_internal(struct rt_db_internal *ip, const struct directory *dp, const struct db_i *dbip, const mat_t mat, struct resource *resp)
Definition: dir.c:76
struct rt_bot_internal * nmg_bot(struct shell *s, const struct bn_tol *tol)
Definition: nmg_misc.c:10826
int rt_db_put_internal(struct directory *dp, struct db_i *dbip, struct rt_db_internal *ip, struct resource *resp)
Definition: dir.c:136
int bn_coplanar(const plane_t a, const plane_t b, const struct bn_tol *tol)
Test if two planes are identical. If so, their dot products will be either +1 or -1, with the distance from the origin equal in magnitude.
Definition: ged.h:338
const mat_t bn_mat_identity
Matrix and vector functionality.
Definition: mat.c:46
struct db_i * dbip
Definition: raytrace.h:1266
#define ID_ARB8
Generalized ARB. V + 7 vectors.
Definition: raytrace.h:462
if lu s
Definition: nmg_mod.c:3860
void bu_ptbl_init(struct bu_ptbl *b, size_t len, const char *str)
Definition: ptbl.c:32
void rt_arb_centroid(point_t *cent, const struct rt_db_internal *ip)
Definition: arb8.c:345
#define VSETALL(a, s)
Definition: color.c:54
int nmg_kr(struct nmgregion *r)
Definition: nmg_mk.c:1595
void bu_vls_trunc(struct bu_vls *vp, int len)
Definition: vls.c:198
#define ID_BOT
Bag o' triangles.
Definition: raytrace.h:488
#define BU_LIST_IS_EMPTY(hp)
Definition: list.h:295
#define GED_CHECK_ARGC_GT_0(_gedp, _argc, _flags)
Definition: ged.h:202
struct directory * db_lookup(const struct db_i *, const char *name, int noisy)
Definition: db_lookup.c:153
int db_version(struct db_i *dbip)
Definition: db5_scan.c:414
#define ID_PARTICLE
Particle system solid.
Definition: raytrace.h:474
void nmg_rebound(struct model *m, const struct bn_tol *tol)
Definition: nmg_misc.c:2072
struct rt_wdb * ged_wdbp
Definition: ged.h:340
int ged_inside_internal(struct ged *gedp, struct rt_db_internal *ip, int argc, const char *argv[], int arg, char *o_name)
Definition: inside.c:896
Header file for the BRL-CAD common definitions.
#define ID_TOR
Toroid.
Definition: raytrace.h:459
int bn_mkpoint_3planes(point_t pt, const plane_t a, const plane_t b, const plane_t c)
Given the description of three planes, compute the point of intersection, if any. The direction vecto...
struct rt_tess_tol wdb_ttol
Definition: raytrace.h:1268
#define GED_ERROR
Definition: ged.h:61
Definition: ptbl.h:62
double rel
rel dist tol
Definition: raytrace.h:181
int idb_major_type
Definition: raytrace.h:192
void bu_vls_free(struct bu_vls *vp)
Definition: vls.c:248
struct resource rt_uniresource
default. Defined in librt/globals.c
Definition: globals.c:41
#define GED_CHECK_DATABASE_OPEN(_gedp, _flags)
Definition: ged.h:114
#define ID_EHY
Elliptical Hyperboloid.
Definition: raytrace.h:478
void nmg_shell_coplanar_face_merge(struct shell *s, const struct bn_tol *tol, const int simplify)
Definition: nmg_mod.c:93
#define RT_DIR_SOLID
this name is a solid
Definition: raytrace.h:883
int rt_arb_3face_intersect(point_t point, const plane_t planes[6], int type, int loc)
#define BU_PTBL_GET(ptbl, i)
Definition: ptbl.h:108
#define RT_DB_INTERNAL_INIT(_p)
Definition: raytrace.h:199
#define LOOKUP_QUIET
Definition: raytrace.h:893
const struct rt_functab * idb_meth
for ft_ifree(), etc.
Definition: raytrace.h:194
#define ID_NMG
n-Manifold Geometry solid
Definition: raytrace.h:469
struct shell * nmg_extrude_shell(struct shell *s, const fastf_t dist, const int normal_ward, const int approximate, const struct bn_tol *tol)
Definition: nmg_extrude.c:1181
void nmg_km(struct model *m)
Definition: nmg_mk.c:1634
static void top()
#define SQRT_SMALL_FASTF
Definition: defines.h:346
#define RT_DIR_PHONY_ADDR
Special marker for d_addr field.
Definition: raytrace.h:879
#define BU_LIST_PNEXT(structure, p)
Definition: list.h:422
char ft_name[17]
Definition: raytrace.h:2043
#define UNUSED(parameter)
Definition: common.h:239
char * bu_vls_addr(const struct bu_vls *vp)
Definition: vls.c:111
struct bu_vls * ged_result_str
Definition: ged.h:357
struct fg_node fg
Definition: chull3d.cpp:80
void bu_ptbl_free(struct bu_ptbl *b)
Definition: ptbl.c:226
#define ID_RHC
Right Hyperbolic Cylinder.
Definition: raytrace.h:476
#define ID_EPA
Elliptical Paraboloid.
Definition: raytrace.h:477
struct model * nmg_mm(void)
Definition: nmg_mk.c:235
struct directory * db_diradd(struct db_i *, const char *name, off_t laddr, size_t len, int flags, void *ptr)
Definition: db_lookup.c:190
#define ZERO(val)
Definition: units.c:38
void * idb_ptr
Definition: raytrace.h:195
int nmg_kill_cracks(struct shell *s)
Definition: nmg_misc.c:8187
struct bn_tol wdb_tol
Definition: raytrace.h:1269
const struct rt_functab OBJ[]
Definition: table.c:159
struct shell * nmg_extrude_cleanup(struct shell *in_shell, const int is_void, const struct bn_tol *tol)
Definition: nmg_extrude.c:803
#define BU_PTBL_END(ptbl)
Definition: ptbl.h:106
double abs
absolute dist tol
Definition: raytrace.h:180
void bu_vls_printf(struct bu_vls *vls, const char *fmt,...) _BU_ATTR_PRINTF23
Definition: vls.c:694
#define RT_DIR_NULL
Definition: raytrace.h:875
int(* ft_tessellate)(struct nmgregion **, struct model *, struct rt_db_internal *, const struct rt_tess_tol *, const struct bn_tol *)
Definition: raytrace.h:2114
double norm
normal tol
Definition: raytrace.h:182
#define RT_TESS_TOL_MAGIC
Definition: magic.h:170
double dbi_local2base
local2mm
Definition: raytrace.h:807
#define BU_VLS_INIT_ZERO
Definition: vls.h:84
int bn_pt3_pt3_equal(const point_t a, const point_t b, const struct bn_tol *tol)
#define ID_RPC
Right Parabolic Cylinder.
Definition: raytrace.h:475
#define ID_TGC
Generalized Truncated General Cone.
Definition: raytrace.h:460
#define GED_CHECK_READ_ONLY(_gedp, _flags)
Definition: ged.h:181
Definition: vls.h:56
int rt_arb_get_cgtype(int *cgtype, struct rt_arb_internal *arb, const struct bn_tol *tol, register int *uvec, register int *svec)
Definition: arb8.c:203
#define ID_ETO
Elliptical Torus.
Definition: raytrace.h:479
double fastf_t
Definition: defines.h:300
#define ID_ELL
Ellipsoid.
Definition: raytrace.h:461
#define BU_LIST_NOT_HEAD(p, hp)
Definition: list.h:324
int ged_inside(struct ged *gedp, int argc, const char *argv[])
Definition: inside.c:1157
void rt_db_free_internal(struct rt_db_internal *ip)
Definition: dir.c:216
#define BU_LIST_FIRST(structure, hp)
Definition: list.h:312
void nmg_vertex_tabulate(struct bu_ptbl *tab, const uint32_t *magic_p)
Definition: nmg_info.c:1985
int nmg_in_vert(struct vertex *new_v, const int approximate, const struct bn_tol *tol)
Definition: nmg_misc.c:8086
#define GED_MORE
Definition: ged.h:63