Exemple #1
0
void
make_face(fastf_t *a, fastf_t *b, fastf_t *c, fastf_t *d, int order)
{
    register struct face_g_snurb	*srf;
    int	interior_pts = 0;
    int	cur_kv;
    int	i;
    int	ki;
    register fastf_t	*fp;

    srf = rt_nurb_new_snurb( order, order,
                             2*order+interior_pts, 2*order+interior_pts,	/* # knots */
                             2+interior_pts, 2+interior_pts,
                             RT_NURB_MAKE_PT_TYPE(3, RT_NURB_PT_XYZ, RT_NURB_PT_NONRAT ),
                             &rt_uniresource );

    /* Build both knot vectors */
    cur_kv = 0;		/* current knot value */
    ki = 0;			/* current knot index */
    for ( i=0; i<order; i++, ki++ )  {
        srf->u.knots[ki] = srf->v.knots[ki] = cur_kv;
    }
    cur_kv++;
    for ( i=0; i<interior_pts; i++, ki++ )  {
        srf->u.knots[ki] = srf->v.knots[ki] = cur_kv++;
    }
    for ( i=0; i<order; i++, ki++ )  {
        srf->u.knots[ki] = srf->v.knots[ki] = cur_kv;
    }

    rt_nurb_pr_kv( &srf->u );

    /*
     *  The control mesh is stored in row-major order.
     */
    /* Head from point A to B */
#if 0
    row = 0;
    for ( col=0; col < srf->s_curve[1]; col++ )  {
        fp = &srf->ctl_points[col*srf->s_curve[1]+row];
        VSET( fp
    }
#endif

#define SSET(_col, _row, _val)	{ \
	fp = &srf->ctl_points[((_col*srf->s_size[1])+_row)*3]; \
	VMOVE( fp, _val ); }

    /* VADD2SCALE( mid, a, b, 0.5 ); */
    SSET( 0, 0, a );
    SSET( 0, 1, b );
    SSET( 1, 0, d );
    SSET( 1, 1, c );

    si.srfs[si.nsrf++] = srf;
}
Exemple #2
0
void
make_face(struct rt_nurb_internal *s, fastf_t *a, fastf_t *b, fastf_t *c, fastf_t *d, int order)
{
    int i;
    int ki;
    int cur_kv;
    int interior_pts = 2;
    fastf_t *fp = NULL;
    struct face_g_snurb *srf = NULL;

    srf = rt_nurb_new_snurb(order, order,
			    2*order+interior_pts, 2*order+interior_pts,	/* # knots */
			    2+interior_pts, 2+interior_pts,
			    RT_NURB_MAKE_PT_TYPE(3, RT_NURB_PT_XYZ, RT_NURB_PT_NONRAT),
			    &rt_uniresource);

    /* Build both knot vectors */

    /* current knot value */
    cur_kv = 0;
    /* current knot index */
    ki = 0;

    for (i=0; i<order; i++, ki++) {
	srf->u.knots[ki] = srf->v.knots[ki] = cur_kv;
    }
    cur_kv++;
    for (i=0; i<interior_pts; i++, ki++) {
	srf->u.knots[ki] = srf->v.knots[ki] = cur_kv++;
    }
    for (i=0; i<order; i++, ki++) {
	srf->u.knots[ki] = srf->v.knots[ki] = cur_kv;
    }

    rt_nurb_pr_kv(&srf->u);

    /*
     * The control mesh is stored in row-major order.
     */

    SSET(fp, srf, 0, 0, a);
    SSET(fp, srf, 0, 1, b);
    SSET(fp, srf, 1, 0, d);
    SSET(fp, srf, 1, 1, c);

    s->srfs[s->nsrf++] = srf;
}
Exemple #3
0
struct edge_g_cnurb *
Get_cnurb_curve(int curve_de, int *linear)
{
    int i;
    int curve;
    struct edge_g_cnurb *crv;

    *linear = 0;

    curve = (curve_de - 1)/2;
    if (curve >= dirarraylen) {
	bu_log("Get_cnurb_curve: DE=%d is too large, dirarraylen = %d\n", curve_de, dirarraylen);
	return (struct edge_g_cnurb *)NULL;
    }

    switch (dir[curve]->type) {
	case 110: {
	    /* line */
	    int pt_type;
	    int type;
	    point_t pt1;
	    point_t start_pt, end_pt;

	    Readrec(dir[curve]->param);
	    Readint(&type, "");
	    if (type != dir[curve]->type) {
		bu_log("Error in Get_cnurb_curve, looking for curve type %d, found %d\n" ,
		       dir[curve]->type, type);
		return (struct edge_g_cnurb *)NULL;

	    }
	    /* Read first point */
	    for (i = 0; i < 3; i++)
		Readcnv(&pt1[i], "");
	    MAT4X3PNT(start_pt, *dir[curve]->rot, pt1);

	    /* Read second point */
	    for (i = 0; i < 3; i++)
		Readcnv(&pt1[i], "");
	    MAT4X3PNT(end_pt, *dir[curve]->rot, pt1);

	    /* pt_type for rational UVW coords */
	    pt_type = RT_NURB_MAKE_PT_TYPE(3, 3, 1);

	    /* make a linear edge_g_cnurb (order=2) */
	    crv = rt_nurb_new_cnurb(2, 4, 2, pt_type);

	    /* insert control mesh */
	    VMOVE(crv->ctl_points, start_pt);
	    VMOVE(&crv->ctl_points[3], end_pt);

	    /* insert knot values */
	    crv->k.knots[0] = 0.0;
	    crv->k.knots[1] = 0.0;
	    crv->k.knots[2] = 1.0;
	    crv->k.knots[3] = 1.0;

	    *linear = 1;

	    return crv;
	}
	case 126:	/* B-spline */
	    crv = Get_cnurb(curve);
	    if (crv->order < 3)
		*linear = 1;
	    return crv;
	default:
	    bu_log("Not yet handling curves of type: %s\n", iges_type(dir[curve]->type));
	    break;
    }

    return (struct edge_g_cnurb *)NULL;
}
Exemple #4
0
struct face_g_snurb *
rt_nurb_project_srf(const struct face_g_snurb *srf, fastf_t *plane1, fastf_t *plane2, struct resource *res)
{

    register struct face_g_snurb *psrf;
    register fastf_t *mp1, *mp2;
    int n_pt_type;
    int rational;
    int i;

    if (RTG.NMG_debug & DEBUG_RT_ISECT)
	bu_log("rt_nurb_project_srf: projecting surface, planes = (%g %g %g %g) (%g %g %g %g)\n",
	       V4ARGS(plane1), V4ARGS(plane2));

    rational = RT_NURB_IS_PT_RATIONAL(srf->pt_type);

    n_pt_type = RT_NURB_MAKE_PT_TYPE(2, RT_NURB_PT_PROJ, 0);

    psrf = (struct face_g_snurb *) rt_nurb_new_snurb(srf->order[0], srf->order[1],
						     srf->u.k_size, srf->v.k_size,
						     srf->s_size[0], srf->s_size[1], n_pt_type, res);

    psrf->dir = RT_NURB_SPLIT_COL;

    for (i = 0; i < srf->u.k_size; i++) {
	psrf->u.knots[i] = srf->u.knots[i];
    }

    for (i = 0; i < srf->v.k_size; i++) {
	psrf->v.knots[i] = srf->v.knots[i];
    }

    mp1 = srf->ctl_points;
    mp2 = psrf->ctl_points;

    for (i = 0; i < srf->s_size[0] * srf->s_size[1]; i++) {

	if (rational) {
	    mp2[0] = (mp1[0] / mp1[3] * plane1[0] +
		      mp1[1] / mp1[3] * plane1[1] +
		      mp1[2] / mp1[3] * plane1[2] - plane1[3]) *
		mp1[3];
	    mp2[1] = (mp1[0] / mp1[3] * plane2[0] +
		      mp1[1] / mp1[3] * plane2[1] +
		      mp1[2] / mp1[3] * plane2[2] - plane2[3]) *
		mp1[3];
	} else {
	    mp2[0] = mp1[0] * plane1[0] + mp1[1] * plane1[1] +
		mp1[2] * plane1[2] - plane1[3];
	    mp2[1] = mp1[0] * plane2[0] + mp1[1] * plane2[1] +
		mp1[2] * plane2[2] - plane2[3];
	}

	if (RTG.NMG_debug & DEBUG_RT_ISECT) {
	    if (rational)
		bu_log("\tmesh pt (%g %g %g %g), becomes (%g %g)\n", V4ARGS(mp1), mp2[0], mp2[1]);
	    else
		bu_log("\tmesh pt (%g %g %g), becomes (%g %g)\n", V3ARGS(mp1), mp2[0], mp2[1]);
	}

	mp1 += RT_NURB_EXTRACT_COORDS(srf->pt_type);
	mp2 += RT_NURB_EXTRACT_COORDS(psrf->pt_type);
    }

    return (struct face_g_snurb *) psrf;
}
Exemple #5
0
/* IEEE patch number of the Bi-Cubic Bezier patch and convert it
 * to a B-Spline surface (Bezier surfaces are a subset of B-spline surfaces
 * and output it to a BRL-CAD binary format.
 */
void
dump_patch(int (*patch)[4])
{
    struct vertex *verts[4];
    struct faceuse *fu;
    struct loopuse *lu;
    struct edgeuse *eu;
    int i, j, pt_type;
    fastf_t *mesh=NULL;
    fastf_t *ukv=NULL;
    fastf_t *vkv=NULL;

    /* U and V parametric Direction Spline parameters
     * Cubic = order 4,
     * knot size is Control point + order = 8
     * control point size is 4
     * point size is 3
     */

    for ( i=0; i<4; i++ )
        verts[i] = (struct vertex *)NULL;

    fu = nmg_cface( s, verts, 4 );
    NMG_CK_FACEUSE( fu );

    for ( i=0; i<4; i++ )
    {
        struct vertexuse *vu;
        vect_t uvw;
        point_t pnt;
        int k, j;

        switch ( i )
        {
        default:
        case 0:
            VSET( uvw, 0.0, 0.0, 0.0 );
            k = 0;
            j = 0;
            break;
        case 1:
            VSET( uvw, 1.0, 0.0, 0.0 );
            k = 0;
            j = 3;
            break;
        case 2:
            VSET( uvw, 1.0, 1.0, 0.0 );
            k = 3;
            j = 3;
            break;
        case 3:
            VSET( uvw, 0.0, 1.0, 0.0 );
            k = 3;
            j = 0;
            break;
        }

        VSET( pnt ,
              ducks[patch[k][j]-1].x * 1000 ,
              ducks[patch[k][j]-1].y * 1000 ,
              ducks[patch[k][j]-1].z * 1000 );
        nmg_vertex_gv( verts[i], pnt );

        for ( BU_LIST_FOR( vu, vertexuse, &verts[i]->vu_hd ) )
            nmg_vertexuse_a_cnurb( vu, uvw );
    }

    pt_type = RT_NURB_MAKE_PT_TYPE(3, RT_NURB_PT_XYZ, 0); /* see nurb.h for details */

    nmg_face_g_snurb( fu, 4, 4, 8, 8, ukv, vkv, 4, 4, pt_type, mesh );

    NMG_CK_FACE( fu->f_p );
    NMG_CK_FACE_G_SNURB( fu->f_p->g.snurb_p );
    mesh = fu->f_p->g.snurb_p->ctl_points;

    /* Copy the control points */

    for ( i = 0; i< 4; i++)
        for ( j = 0; j < 4; j++)
        {
            *mesh = ducks[patch[i][j]-1].x * 1000;
            *(mesh+1) = ducks[patch[i][j]-1].y * 1000;
            *(mesh+2) = ducks[patch[i][j]-1].z * 1000;
            mesh += 3;
        }

    /* Both u and v knot vectors are [ 0 0 0 0 1 1 1 1] */
    ukv = fu->f_p->g.snurb_p->u.knots;
    vkv = fu->f_p->g.snurb_p->v.knots;
    /* set the knot vectors */
    for ( i=0; i<4; i++ )
    {
        *(ukv+i) = 0.0;
        *(vkv+i) = 0.0;
    }
    for ( i=0; i<4; i++ )
    {
        *(ukv+4+i) = 1.0;
        *(vkv+4+i) = 1.0;
    }

    /* set eu geometry */
    pt_type = RT_NURB_MAKE_PT_TYPE(2, RT_NURB_PT_UV, 0); /* see nurb.h for details */
    lu = BU_LIST_FIRST( loopuse, &fu->lu_hd );
    NMG_CK_LOOPUSE( lu );
    for ( BU_LIST_FOR( eu, edgeuse, &lu->down_hd ) )
    {
#if 0
        nmg_edge_g_cnurb( eu, 2, 0, (fastf_t *)NULL, 2 ,
                          pt_type, (fastf_t *)NULL );
#else
        nmg_edge_g_cnurb_plinear( eu );
#endif
    }
    nmg_face_bb( fu->f_p, &tol );
}
Exemple #6
0
int
spline(int entityno, struct face_g_snurb **b_patch)
{
    int k1;	/* upper index of first sum */
    int k2;	/* upper index of second sum */
    int m1;	/* degree of 1st set of basis functions */
    int m2;	/* degree of 2nd set of basis functions */
    int prop1;	/* !0 if closed in first direction */
    int prop2;	/* !0 if closed in second direction */
    int prop3;	/* !0 if polynomial (else rational) */
    int prop4;	/* !0 if periodic in first direction */
    int prop5;	/* !0 if periodic in second direction */
    int sol_num; /* IGES solid type number */
    int n1, n2;
    int i, j, k;
    int count = 0;
    int point_size;
    fastf_t min_knot;
    double max_wt;
    double scan;

    /* Acquiring Data */

    if (dir[entityno]->param <= pstart) {
	bu_log("Illegal parameter pointer for entity D%07d (%s)\n" ,
	       dir[entityno]->direct, dir[entityno]->name);
	return 0;
    }

    Readrec(dir[entityno]->param);
    Readint(&sol_num, "");
    Readint(&k1, "");
    Readint(&k2, "");
    Readint(&m1, "");
    Readint(&m2, "");
    Readint(&prop1, "");
    Readint(&prop2, "");
    Readint(&prop3, "");
    Readint(&prop4, "");
    Readint(&prop5, "");

    n1 = k1 - m1 + 1;
    n2 = k2 - m2 + 1;

    /* spl_new: Creates a spline surface data structure
     * u_order (e.g. cubic = order 4)
     * v_order
     * num_u (e.g. num control points + order)
     * num_v
     * num_rows num control points in V direction
     * num_cols num control points in U direction
     * point_size number of values in a point (e.g. 3 or 4)
     */

    if (prop3 == 0) {
	point_size = 4;
    } else {
	point_size = 3;
    }

    (*b_patch) = rt_nurb_new_snurb(
	m1+1, m2+1,
	n1+2*m1+1, n2+2*m2+1,
	k2+1, k1+1,
	RT_NURB_MAKE_PT_TYPE(point_size, 2,
			     (prop3 == 0 ? RT_NURB_PT_RATIONAL : RT_NURB_PT_NONRAT)),
	(struct resource *)NULL);

    /* U knot vector */
    min_knot = 0.0;
    for (i = 0; i <= n1+2*m1; i++) {
	Readdbl(&scan, "");
	(*b_patch)->u.knots[i] = scan; /* double to fastf_t */
	if ((*b_patch)->u.knots[i] < min_knot)
	    min_knot = (*b_patch)->u.knots[i];
    }

    if (min_knot < 0.0) {
	for (i = 0; i <= n1+2*m1; i++) {
	    (*b_patch)->u.knots[i] -= min_knot;
	}
    }

    min_knot = 0.0;
    /* V knot vector */
    for (i = 0; i <= n2+2*m2; i++) {
	Readdbl(&scan, "");
	(*b_patch)->v.knots[i] = scan; /* double to fastf_t */
	if ((*b_patch)->v.knots[i] < min_knot)
	    min_knot = (*b_patch)->v.knots[i];
    }
    if (min_knot < 0.0) {
	for (i = 0; i <= n2+2*m2; i++) {
	    (*b_patch)->v.knots[i] -= min_knot;
	}
    }


    /* weights */
    max_wt = 0.0;
    count = 0;
    for (i = 0; i <= k2; i++) {
	for (j = 0; j <= k1; j++) {
	    if (point_size == 4) {
		Readdbl(&scan, "");
		(*b_patch)->ctl_points[count*4 + 3] = scan; /* double to fastf_t */
		if ((*b_patch)->ctl_points[count*4 + 3] > max_wt)
		    max_wt = (*b_patch)->ctl_points[count*4 + 3];
	    } else {
		Readdbl(&max_wt, "");
	    }
	    count++;
	}
    }

    /* control points */
    count = 0;
    for (i = 0; i <= k2; i++) {
	for (j = 0; j <= k1; j++) {
	    Readcnv(&(*b_patch)->ctl_points[count*point_size], "");
	    Readcnv(&(*b_patch)->ctl_points[count*point_size + 1], "");
	    Readcnv(&(*b_patch)->ctl_points[count*point_size + 2], "");
	    count++;
	}
    }

    if (point_size == 4) {
	/* apply weights */
	count = 0;
	for (i = 0; i <= k2; i++) {
	    for (j = 0; j <= k1; j++) {
		for (k = 0; k < 3; k++)
		    (*b_patch)->ctl_points[count*4 + k] *= (*b_patch)->ctl_points[count*4 + 3];
		count++;
	    }
	}
    }

    return 1;
}
Exemple #7
0
void
build_spline(char *name, int npts, double radius)
{
    struct face_g_snurb *bp;
    int i;
    int nv;
    int cur_kv;
    fastf_t *meshp;
    int col;
    vect_t point;

    /*
     * This spline will look like a cylinder.
     * In the mesh, the circular cross section will be presented
     * across the first row by filling in the 9 (NCOLS) columns.
     *
     * The U direction is across the first row,
     * and has NCOLS+order[U] positions, 12 in this instance.
     * The V direction is down the first column,
     * and has NROWS+order[V] positions.
     */
    bp = rt_nurb_new_snurb(3,	4,		/* u, v order */
			   N_CIRCLE_KNOTS,	npts+6,		/* u, v knot vector size */
			   npts+2,		NCOLS,		/* nrows, ncols */
			   RT_NURB_MAKE_PT_TYPE(4, 2, 1),
			   &rt_uniresource);

    /* Build the U knots */
    for (i=0; i<N_CIRCLE_KNOTS; i++)
	bp->u.knots[i] = circle_knots[i];

    /* Build the V knots */
    cur_kv = 0;		/* current knot value */
    nv = 0;			/* current knot subscript */
    for (i=0; i<4; i++)
	bp->v.knots[nv++] = cur_kv;
    cur_kv++;
    for (i=4; i<(npts+4-2); i++)
	bp->v.knots[nv++] = cur_kv++;
    for (i=0; i<4; i++)
	bp->v.knots[nv++] = cur_kv;

    /*
     * The control mesh is stored in row-major order,
     * which works out well for us, as a row is one
     * circular slice through the tube.  So we just
     * have to write down the slices, one after another.
     * The first and last "slice" are the center points that
     * create the end caps.
     */
    meshp = bp->ctl_points;

    /* Row 0 */
    for (col=0; col<9; col++) {
	*meshp++ = sample[0][X];
	*meshp++ = sample[0][Y];
	*meshp++ = sample[0][Z];
	*meshp++ = 1;
    }

    /* Rows 1..npts */
    for (i=0; i<npts; i++) {
	/* row = i; */
	VMOVE(point, sample[i]);
	for (col=0; col<9; col++) {
	    fastf_t h;

	    h = polyline[col*4+H];
	    *meshp++ = polyline[col*4+X]*radius + point[X]*h;
	    *meshp++ = polyline[col*4+Y]*radius + point[Y]*h;
	    *meshp++ = polyline[col*4+Z]*radius + point[Z]*h;
	    *meshp++ = h;
	}
    }

    /* Row npts+1 */
    for (col=0; col<9; col++) {
	*meshp++ = sample[npts-1][X];
	*meshp++ = sample[npts-1][Y];
	*meshp++ = sample[npts-1][Z];
	*meshp++ = 1;
    }

    {
	struct face_g_snurb *surfp[2];
	surfp[0] = bp;
	surfp[1] = NULL;
	mk_bspline(outfp, name, surfp);
    }

    rt_nurb_free_snurb(bp, &rt_uniresource);
}