diff options
Diffstat (limited to 'source/blender/render/intern/raytrace/rayobject_octree.cpp')
-rw-r--r-- | source/blender/render/intern/raytrace/rayobject_octree.cpp | 136 |
1 files changed, 68 insertions, 68 deletions
diff --git a/source/blender/render/intern/raytrace/rayobject_octree.cpp b/source/blender/render/intern/raytrace/rayobject_octree.cpp index a45b3989e7b..4b73e64ca45 100644 --- a/source/blender/render/intern/raytrace/rayobject_octree.cpp +++ b/source/blender/render/intern/raytrace/rayobject_octree.cpp @@ -77,11 +77,11 @@ typedef struct Octree { int branchcount, nodecount; /* during building only */ - char *ocface; - + char *ocface; + RayFace **ro_nodes; int ro_nodes_size, ro_nodes_used; - + } Octree; static int RE_rayobject_octree_intersect(RayObject *o, Isect *isec); @@ -126,7 +126,7 @@ static void calc_ocval_face(float *v1, float *v2, float *v3, float *v4, short x, { float min[3], max[3]; int ocmin, ocmax; - + copy_v3_v3(min, v1); copy_v3_v3(max, v1); DO_MINMAX(v2, min, max); @@ -134,7 +134,7 @@ static void calc_ocval_face(float *v1, float *v2, float *v3, float *v4, short x, if (v4) { DO_MINMAX(v4, min, max); } - + ocmin = OCVALRES * (min[0] - x); ocmax = OCVALRES * (max[0] - x); ov->ocx = BROW16(ocmin, ocmax); @@ -152,7 +152,7 @@ static void calc_ocval_face(float *v1, float *v2, float *v3, float *v4, short x, static void calc_ocval_ray(OcVal *ov, float xo, float yo, float zo, float *vec1, float *vec2) { int ocmin, ocmax; - + if (vec1[0] < vec2[0]) { ocmin = OCVALRES * (vec1[0] - xo); ocmax = OCVALRES * (vec2[0] - xo); @@ -189,12 +189,12 @@ static void calc_ocval_ray(OcVal *ov, float xo, float yo, float zo, float *vec1, static Branch *addbranch(Octree *oc, Branch *br, short ocb) { int index; - + if (br->b[ocb]) return br->b[ocb]; - + oc->branchcount++; index = oc->branchcount >> 12; - + if (oc->adrbranch[index] == NULL) oc->adrbranch[index] = (Branch *)MEM_callocN(4096 * sizeof(Branch), "new oc branch"); @@ -202,17 +202,17 @@ static Branch *addbranch(Octree *oc, Branch *br, short ocb) printf("error; octree branches full\n"); oc->branchcount = 0; } - + return br->b[ocb] = oc->adrbranch[index] + (oc->branchcount & 4095); } static Node *addnode(Octree *oc) { int index; - + oc->nodecount++; index = oc->nodecount >> 12; - + if (oc->adrnode[index] == NULL) oc->adrnode[index] = (Node *)MEM_callocN(4096 * sizeof(Node), "addnode"); @@ -220,7 +220,7 @@ static Node *addnode(Octree *oc) printf("error; octree nodes full\n"); oc->nodecount = 0; } - + return oc->adrnode[index] + (oc->nodecount & 4095); } @@ -228,14 +228,14 @@ static bool face_in_node(RayFace *face, short x, short y, short z, float rtf[4][ { static float nor[3], d; float fx, fy, fz; - - // init static vars + + // init static vars if (face) { normal_tri_v3(nor, rtf[0], rtf[1], rtf[2]); d = -nor[0] * rtf[0][0] - nor[1] * rtf[0][1] - nor[2] * rtf[0][2]; return 0; } - + fx = x; fy = y; fz = z; @@ -260,7 +260,7 @@ static bool face_in_node(RayFace *face, short x, short y, short z, float rtf[4][ if ((fx ) * nor[0] + (fy + 1) * nor[1] + (fz + 1) * nor[2] + d > 0.0f) return 1; if ((fx + 1) * nor[0] + (fy + 1) * nor[1] + (fz + 1) * nor[2] + d > 0.0f) return 1; } - + return 0; } @@ -313,9 +313,9 @@ static void ocwrite(Octree *oc, RayFace *face, int quad, short x, short y, short else { while (no->v[a] != NULL) a++; } - + no->v[a] = (RayFace *) RE_rayobject_align(face); - + if (quad) calc_ocval_face(rtf[0], rtf[1], rtf[2], rtf[3], x >> 2, y >> 1, z, &no->ov[a]); else @@ -377,19 +377,19 @@ static void d2dda(Octree *oc, short b1, short b2, short c1, short c2, char *ocfa lambda_y = 1.0f; ldy = 0; } - + x = ocx1; y = ocy1; lambda = MIN2(lambda_x, lambda_y); - + while (true) { - + if (x < 0 || y < 0 || x >= oc->ocres || y >= oc->ocres) { /* pass*/ } else { ocface[oc->ocres * x + y] = 1; } - + lambda_o = lambda; if (lambda_x == lambda_y) { lambda_x += ldx; @@ -460,7 +460,7 @@ static void RE_rayobject_octree_free(RayObject *tree) oc->adrbranch = NULL; } oc->branchcount = 0; - + if (oc->adrnode) { int a = 0; while (oc->adrnode[a]) { @@ -481,16 +481,16 @@ RayObject *RE_rayobject_octree_create(int ocres, int size) { Octree *oc = (Octree *)MEM_callocN(sizeof(Octree), "Octree"); assert(RE_rayobject_isAligned(oc) ); /* RayObject API assumes real data to be 4-byte aligned */ - + oc->rayobj.api = &octree_api; - + oc->ocres = ocres; - + oc->ro_nodes = (RayFace **)MEM_callocN(sizeof(RayFace *) * size, "octree rayobject nodes"); oc->ro_nodes_size = size; oc->ro_nodes_used = 0; - + return RE_rayobject_unalignRayAPI((RayObject *) oc); } @@ -537,7 +537,7 @@ static void octree_fill_rayface(Octree *oc, RayFace *face) rts[3][c] = (short)rtf[3][c]; } } - + for (c = 0; c < 3; c++) { oc1 = rts[0][c]; oc2 = rts[1][c]; @@ -554,12 +554,12 @@ static void octree_fill_rayface(Octree *oc, RayFace *face) if (ocmax[c] > oc->ocres - 1) ocmax[c] = oc->ocres - 1; if (ocmin[c] < 0) ocmin[c] = 0; } - + if (ocmin[0] == ocmax[0] && ocmin[1] == ocmax[1] && ocmin[2] == ocmax[2]) { ocwrite(oc, face, RE_rayface_isQuad(face), ocmin[0], ocmin[1], ocmin[2], rtf); } else { - + d2dda(oc, 0, 1, 0, 1, ocface + ocres2, rts, rtf); d2dda(oc, 0, 1, 0, 2, ocface, rts, rtf); d2dda(oc, 0, 1, 1, 2, ocface + 2 * ocres2, rts, rtf); @@ -583,10 +583,10 @@ static void octree_fill_rayface(Octree *oc, RayFace *face) filltriangle(oc, 0, 1, ocface + ocres2, ocmin, ocmax); filltriangle(oc, 0, 2, ocface, ocmin, ocmax); filltriangle(oc, 1, 2, ocface + 2 * ocres2, ocmin, ocmax); - + /* init static vars here */ face_in_node(face, 0, 0, 0, rtf); - + for (x = ocmin[0]; x <= ocmax[0]; x++) { a = oc->ocres * x; for (y = ocmin[1]; y <= ocmax[1]; y++) { @@ -601,7 +601,7 @@ static void octree_fill_rayface(Octree *oc, RayFace *face) } } } - + /* same loops to clear octree, doubt it can be done smarter */ for (x = ocmin[0]; x <= ocmax[0]; x++) { a = oc->ocres * x; @@ -627,19 +627,19 @@ static void RE_rayobject_octree_done(RayObject *tree) int c; float t00, t01, t02; int ocres2 = oc->ocres * oc->ocres; - + INIT_MINMAX(oc->min, oc->max); - + /* Calculate Bounding Box */ for (c = 0; c < oc->ro_nodes_used; c++) RE_rayobject_merge_bb(RE_rayobject_unalignRayFace(oc->ro_nodes[c]), oc->min, oc->max); - + /* Alloc memory */ oc->adrbranch = (Branch **)MEM_callocN(sizeof(void *) * BRANCH_ARRAY, "octree branches"); oc->adrnode = (Node **)MEM_callocN(sizeof(void *) * NODE_ARRAY, "octree nodes"); - + oc->adrbranch[0] = (Branch *)MEM_callocN(4096 * sizeof(Branch), "makeoctree"); - + /* the lookup table, per face, for which nodes to fill in */ oc->ocface = (char *)MEM_callocN(3 * ocres2 + 8, "ocface"); memset(oc->ocface, 0, 3 * ocres2); @@ -652,12 +652,12 @@ static void RE_rayobject_octree_done(RayObject *tree) t00 = oc->max[0] - oc->min[0]; t01 = oc->max[1] - oc->min[1]; t02 = oc->max[2] - oc->min[2]; - + /* this minus 0.1 is old safety... seems to be needed? */ oc->ocfacx = (oc->ocres - 0.1f) / t00; oc->ocfacy = (oc->ocres - 0.1f) / t01; oc->ocfacz = (oc->ocres - 0.1f) / t02; - + oc->ocsize = sqrtf(t00 * t00 + t01 * t01 + t02 * t02); /* global, max size octree */ for (c = 0; c < oc->ro_nodes_used; c++) { @@ -690,7 +690,7 @@ static int testnode(Octree *UNUSED(oc), Isect *is, Node *no, OcVal ocval) /* return on any first hit */ if (is->mode == RE_RAY_SHADOW) { - + for (; no; no = no->next) { for (nr = 0; nr < 8; nr++) { RayFace *face = no->v[nr]; @@ -708,7 +708,7 @@ static int testnode(Octree *UNUSED(oc), Isect *is, Node *no, OcVal ocval) else { /* else mirror or glass or shadowtra, return closest face */ int found = 0; - + for (; no; no = no->next) { for (nr = 0; nr < 8; nr++) { RayFace *face = no->v[nr]; @@ -723,7 +723,7 @@ static int testnode(Octree *UNUSED(oc), Isect *is, Node *no, OcVal ocval) } } } - + return found; } @@ -735,12 +735,12 @@ static Node *ocread(Octree *oc, int x, int y, int z) { Branch *br; int oc1; - + x <<= 2; y <<= 1; - + br = oc->adrbranch[0]; - + if (oc->ocres == 512) { oc1 = ((x & 1024) + (y & 512) + (z & 256)) >> 8; br = br->b[oc1]; @@ -762,7 +762,7 @@ static Node *ocread(Octree *oc, int x, int y, int z) return NULL; } } - + oc1 = ((x & 128) + (y & 64) + (z & 32)) >> 5; br = br->b[oc1]; if (br) { @@ -785,7 +785,7 @@ static Node *ocread(Octree *oc, int x, int y, int z) } } } - + return NULL; } @@ -817,26 +817,26 @@ static int cliptest(float p, float q, float *u1, float *u2) /* extensive coherence checks/storage cancels out the benefit of it, and gives errors... we * need better methods, sample code commented out below (ton) */ - + #if 0 in top : static int coh_nodes[16 * 16 * 16][6]; in makeoctree : memset(coh_nodes, 0, sizeof(coh_nodes)); - + static void add_coherence_test(int ocx1, int ocx2, int ocy1, int ocy2, int ocz1, int ocz2) { short *sp; - + sp = coh_nodes[(ocx2 & 15) + 16 * (ocy2 & 15) + 256 * (ocz2 & 15)]; sp[0] = ocx1; sp[1] = ocy1; sp[2] = ocz1; sp[3] = ocx2; sp[4] = ocy2; sp[5] = ocz2; - + } static int do_coherence_test(int ocx1, int ocx2, int ocy1, int ocy2, int ocz1, int ocz2) { short *sp; - + sp = coh_nodes[(ocx2 & 15) + 16 * (ocy2 & 15) + 256 * (ocz2 & 15)]; if (sp[0] == ocx1 && sp[1] == ocy1 && sp[2] == ocz1 && sp[3] == ocx2 && sp[4] == ocy2 && sp[5] == ocz2) return 1; @@ -859,10 +859,10 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) int dx, dy, dz; int xo, yo, zo, c1 = 0; int ocx1, ocx2, ocy1, ocy2, ocz1, ocz2; - + /* clip with octree */ if (oc->branchcount == 0) return 0; - + /* do this before intersect calls */ #if 0 is->facecontr = NULL; /* to check shared edge */ @@ -877,7 +877,7 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) o_lambda = is->dist; u1 = 0.0f; u2 = 1.0f; - + /* clip with octree cube */ if (cliptest(-ldx, start[0] - oc->min[0], &u1, &u2)) { if (cliptest(ldx, oc->max[0] - start[0], &u1, &u2)) { @@ -925,7 +925,7 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) ocx2 = (int)ox2; ocy2 = (int)oy2; ocz2 = (int)oz2; - + if (ocx1 == ocx2 && ocy1 == ocy2 && ocz1 == ocz2) { no = ocread(oc, ocx1, ocy1, ocz1); if (no) { @@ -941,7 +941,7 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) //static int coh_ocx1, coh_ocx2, coh_ocy1, coh_ocy2, coh_ocz1, coh_ocz2; float dox, doy, doz; int eqval; - + /* calc lambda en ld */ dox = ox1 - ox2; doy = oy1 - oy2; @@ -994,14 +994,14 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) ldz = 0; dz = 0; } - + xo = ocx1; yo = ocy1; zo = ocz1; dda_lambda = min_fff(lambda_x, lambda_y, lambda_z); - + vec2[0] = ox1; vec2[1] = oy1; vec2[2] = oz1; - + /* this loop has been constructed to make sure the first and last node of ray * are always included, even when dda_lambda==1.0f or larger */ @@ -1009,7 +1009,7 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) no = ocread(oc, xo, yo, zo); if (no) { - + /* calculate ray intersection with octree node */ copy_v3_v3(vec1, vec2); // dox, y, z is negative @@ -1028,7 +1028,7 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) lambda_o = dda_lambda; - + /* traversing octree nodes need careful detection of smallest values, with proper * exceptions for equal lambdas */ eqval = (lambda_x == lambda_y); @@ -1073,7 +1073,7 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) eqval = (lambda_x < lambda_y); if (lambda_y < lambda_z) eqval += 2; if (lambda_x < lambda_z) eqval += 4; - + if (eqval == 7 || eqval == 5) { // x smallest xo += dx; lambda_x += ldx; } @@ -1083,7 +1083,7 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) else { // z smallest zo += dz; lambda_z += ldz; } - + } dda_lambda = min_fff(lambda_x, lambda_y, lambda_z); @@ -1092,10 +1092,10 @@ static int RE_rayobject_octree_intersect(RayObject *tree, Isect *is) if (lambda_o >= 1.0f) break; } } - + /* reached end, no intersections found */ return 0; -} +} |