Beispiel #1
0
//  ---------- Create a bridge segment between current segment/side and marked segment/side ----------
int CreateBridge()
{
    if (!med_form_bridge_segment(Cursegp,Curside,Markedsegp,Markedside)) {
        Update_flags |= UF_WORLD_CHANGED;
        mine_changed = 1;
        autosave_mine(mine_filename);
        diagnostic_message("Bridge segment formed.");
        strcpy(undo_status[Autosave_count], "Bridge segment UNDONE.");
        warn_if_concave_segments();
    }
    return 1;
}
Beispiel #2
0
int generate_curve( fix r1scale, fix r4scale ) {
    vms_vector vec_dir, tvec;
    vms_vector coord,prev_point;
    vms_equation coeffs;
    fix enddist, nextdist;
    int firstsegflag;
    fix t, maxscale;
    fixang rangle, uangle;

	const vcsegptr_t cursegp = Cursegp;
	compute_center_point_on_side(p1, cursegp, Curside);

    switch( Curside ) {
        case WLEFT:
            extract_right_vector_from_segment(cursegp, r1);
            vm_vec_scale(r1, -F1_0 );
            break;
        case WTOP:
            extract_up_vector_from_segment(cursegp, r1);
            break;
        case WRIGHT:
            extract_right_vector_from_segment(cursegp, r1);
            break;
        case WBOTTOM:
            extract_up_vector_from_segment(cursegp, r1);
            vm_vec_scale(r1, -F1_0 );
            break;
        case WBACK:
            extract_forward_vector_from_segment(cursegp, r1);
            break;
        case WFRONT:
            extract_forward_vector_from_segment(cursegp, r1);
            vm_vec_scale(r1, -F1_0 );
            break;
        }            

	const vcsegptr_t markedsegp = Markedsegp;
	compute_center_point_on_side(p4, markedsegp, Markedside);

    switch( Markedside ) {
        case WLEFT:
            extract_right_vector_from_segment(markedsegp, r4);
            extract_up_vector_from_segment(markedsegp, r4t);
            break;
        case WTOP:
            extract_up_vector_from_segment(markedsegp, r4);
            vm_vec_scale(r4, -F1_0 );
            extract_forward_vector_from_segment(markedsegp, r4t);
            vm_vec_scale(r4t, -F1_0 );
            break;
        case WRIGHT:
            extract_right_vector_from_segment(markedsegp, r4);
            vm_vec_scale(r4, -F1_0 );
            extract_up_vector_from_segment(markedsegp, r4t);
            break;
        case WBOTTOM:
            extract_up_vector_from_segment(markedsegp, r4);
            extract_forward_vector_from_segment(markedsegp, r4t);
            break;
        case WBACK:
            extract_forward_vector_from_segment(markedsegp, r4);
            vm_vec_scale(r4, -F1_0 );
            extract_up_vector_from_segment(markedsegp, r4t);
            break;
        case WFRONT:
            extract_forward_vector_from_segment(markedsegp, r4);
            extract_up_vector_from_segment(markedsegp, r4t);
            break;
        }

    r1save = r1;
    tvec = r1;
    vm_vec_scale(r1,r1scale);
    vm_vec_scale(r4,r4scale);

    create_curve( p1, p4, r1, r4, coeffs );
    OriginalSeg = Cursegp;
    OriginalMarkedSeg = Markedsegp;
    OriginalSide = Curside;
    OriginalMarkedSide = Markedside;
    CurveNumSegs = 0;
    coord = prev_point = p1;

    t=0;
    firstsegflag = 1;
    enddist = F1_0; nextdist = 0;
    while ( enddist > fixmul( nextdist, 1.5*F1_0 )) {
            vms_matrix  rotmat;
            if (firstsegflag==1)
                firstsegflag=0;
            else
                extract_forward_vector_from_segment(cursegp, tvec);
            nextdist = vm_vec_mag(tvec);                                   // nextdist := distance to next point
            t = curve_dist(&coeffs, 3, t, prev_point, nextdist);               // t = argument at which function is forward vector magnitude units away from prev_point (in 3-space, not along curve)
            coord = evaluate_curve(&coeffs, 3, t);                                          // coord := point about forward vector magnitude units away from prev_point
            enddist = vm_vec_dist(coord, p4);                  // enddist := distance from current to end point, vec_dir used as a temporary variable
            //vm_vec_normalize(vm_vec_sub(&vec_dir, &coord, &prev_point));
            vm_vec_normalized_dir(vec_dir, coord, prev_point);
			if (!med_attach_segment(Cursegp, vmsegptr(&New_segment), Curside, AttachSide))
		{
			med_extract_matrix_from_segment(cursegp, &rotmat);                   // rotmat := matrix describing orientation of Cursegp
			const auto tdest = vm_vec_rotate(vec_dir,rotmat);	// tdest := vec_dir in reference frame of Cursegp
			vec_dir = tdest;

            const auto rotmat2 = vm_vector_2_matrix(vec_dir,nullptr,nullptr);

            med_rotate_segment( Cursegp, rotmat2 );
			prev_point = coord;
            Curside = Side_opposite[AttachSide];

            CurveSegs[CurveNumSegs]=Cursegp;
            CurveNumSegs++;
        } else return 0;
	}

    extract_up_vector_from_segment(cursegp, tvec);
    uangle = vm_vec_delta_ang( tvec, r4t, r4 );
    if (uangle >= F1_0 * 1/8) uangle -= F1_0 * 1/4;
    if (uangle >= F1_0 * 1/8) uangle -= F1_0 * 1/4;
    if (uangle <= -F1_0 * 1/8) uangle += F1_0 * 1/4;
    if (uangle <= -F1_0 * 1/8) uangle += F1_0 * 1/4;
    extract_right_vector_from_segment(cursegp, tvec);
    rangle = vm_vec_delta_ang( tvec, r4t, r4 );
    if (rangle >= F1_0/8) rangle -= F1_0/4;
    if (rangle >= F1_0/8) rangle -= F1_0/4;
    if (rangle <= -F1_0/8) rangle += F1_0/4;
    if (rangle <= -F1_0/8) rangle += F1_0/4;

    if ((uangle != 0) && (rangle != 0)) {
        maxscale = CurveNumSegs*F1_0;
        generate_banked_curve(maxscale, coeffs);
    }

    if (CurveNumSegs) {
        med_form_bridge_segment( Cursegp, Side_opposite[AttachSide], Markedsegp, Markedside );
        CurveSegs[CurveNumSegs] = vmsegptr(Markedsegp->children[Markedside]);
        CurveNumSegs++;
	}

    Cursegp = OriginalSeg;
    Curside = OriginalSide;

	med_create_new_segment_from_cursegp();

	//warn_if_concave_segments();

    if (CurveNumSegs) return 1;
        else return 0;
}