logic based edge split + group prim number shifting ?

   706   1   0
User Avatar
Member
244 posts
Joined: 12月 2016
オフライン
Hello i`ve got this code to split primitives based on group and prox to point.


problem is when i try to create groups i think there is a bug becouse the poligon numbers that their ints point to are actually incorrect i think i`ve tried various troubleshooting things and i think thats what the problem is unsure if i should keep going at it.

```
// User-defined parameters
vector bias_point = chv("bias_point");
float pos = chf("verhouding");
string edge_group = "corner_to_be";

// Step 1: Get all primitives
int nprims = nprimitives(0);

// Track split primitives so we only split once
int split_prims[];

// === Splitting Function ===
void split_by_halfedge(int h; float split_pos; vector bias) {
    int prim = hedge_prim(0, h);
    if (prim < 0) return;

    split_pos = clamp(split_pos, 1e-3, 1.0 - 1e-3);

    int src_pt = hedge_srcpoint(0, h);
    int dst_pt = hedge_dstpoint(0, h);

    vector src_pos = point(0, "P", src_pt);
    vector dst_pos = point(0, "P", dst_pt);

    // Test both options
    vector mid_pos_A_1 = lerp(src_pos, dst_pos, split_pos);
    vector mid_pos_A_2 = lerp(src_pos, dst_pos, 1 - split_pos);
    
    // Choose the closer to the bias point
    float d1 = distance(mid_pos_A_1, bias);
    float d2 = distance(mid_pos_A_2, bias);
    
    float final_split_pos = (d1 < d2) ? split_pos : 1 - split_pos;
    
    // Use that final one
    vector mid_pos_A = lerp(src_pos, dst_pos, final_split_pos);
    int mid_pt_A = addpoint(0, mid_pos_A);

    // Opposite edge (assumes quad)
    int h1 = hedge_next(0, h);
    int h2 = hedge_next(0, h1);

    int opp_src = hedge_srcpoint(0, h2);
    int opp_dst = hedge_dstpoint(0, h2);

    vector opp_src_pos = point(0, "P", opp_src);
    vector opp_dst_pos = point(0, "P", opp_dst);

    vector mid_pos_B = lerp(opp_src_pos, opp_dst_pos, 1 - final_split_pos);
    int mid_pt_B = addpoint(0, mid_pos_B);

    // Quad corner points
    int p0 = hedge_srcpoint(0, h);
    int p1 = hedge_dstpoint(0, h);
    int p2 = hedge_dstpoint(0, h1);
    int p3 = hedge_dstpoint(0, hedge_next(0, h1));

    int primA[] = array(p0, mid_pt_A, mid_pt_B, p3);
    int primB[] = array(mid_pt_A, p1, p2, mid_pt_B);

    // 
    vector centerA = {0, 0, 0};
    foreach (int pt; primA) {
        centerA += point(0, "P", pt);
    }
    centerA /= len(primA);
    
    // Do the same for primB
    vector centerB = {0, 0, 0};
    foreach (int pt; primB) {
        centerB += point(0, "P", pt);
    }
    centerB /= len(primB);
    
    // Add both new prims to the base group
    int new_primA = addprim(0, "poly", primA);
    int new_primB = addprim(0, "poly", primB);
    
    // Group name for all split quads
    string grp_all = "split_quads";
    string grp_inside = "inside";
    string grp_outside = "outside";
    string edge_group_name = "split_edges";
    
    //add centers
    setprimattrib(0, "mycenter", new_primA, centerA, "set");
    setprimattrib(0, "mycenter", new_primB, centerB, "set");
    
    setprimgroup(0, grp_all, new_primA, 1, "set");
    setprimgroup(0, grp_all, new_primB, 1, "add");

    float distA = distance(centerA, bias);
    float distB = distance(centerB, bias);
    
    if (distA < distB) {
        setprimgroup(0, grp_inside, new_primA, 1, "set");
        setprimgroup(0, grp_outside, new_primB, 1, "set");
    } else {
        setprimgroup(0, grp_inside, new_primB, 1, "set");
        setprimgroup(0, grp_outside, new_primA, 1, "set");
    }
    
    // Create edge group for the new diagonal edge (mid_pt_A to mid_pt_B)
    setedgegroup(0, edge_group_name, mid_pt_A, mid_pt_B, 1);
    
    
    //clean prim
    removeprim(0, prim, 1);
}

// Step 2: Loop over primitives
for (int prim = 0; prim < nprims; prim++) {
    if (find(split_prims, prim) >= 0) continue; // already split

    int h = primhedge(0, prim);
    int start_h = h;

    // Step 3: Loop over half-edges in the primitive
    do {
        int pt0 = hedge_srcpoint(0, h);
        int pt1 = hedge_dstpoint(0, h);

        // Check if this edge is in the edge group (order-sensitive)
        if (inedgegroup(0, edge_group, pt0, pt1)) {

            // Only split if quad
            if (len(primpoints(0, prim)) == 4) {
                // Split using this half-edge
                split_by_halfedge(h, pos, bias_point);
                append(split_prims, prim);
            }

            break; // don't process more edges for this prim
        }

        h = hedge_next(0, h);
    } while (h != start_h);
}
Edited by NicTanghe - 2025年6月18日 11:13:22
User Avatar
Member
9394 posts
Joined: 7月 2007
オフライン
you may want to attach a hip file with your test geo to see it in broken state, since testing on grid it seems to work fine and groups seem correct apart from it messing up the incoming "corner_to_be" which the code doesn't attempt to correct

also it seems to be written for Detail wrangle but processes each prim independently so you can simplify it for prim wrangle and remove your prim loop as well as split_prims checks as each prim is processed just once regardless
Tomas Slancik
CG Supervisor
Framestore, NY
  • Quick Links