diff options
Diffstat (limited to 'source/blender/blenlib/intern')
-rw-r--r-- | source/blender/blenlib/intern/BLI_kdopbvh.c | 270 | ||||
-rw-r--r-- | source/blender/blenlib/intern/arithb.c | 589 | ||||
-rw-r--r-- | source/blender/blenlib/intern/bpath.c | 34 | ||||
-rw-r--r-- | source/blender/blenlib/intern/fileops.c | 14 | ||||
-rw-r--r-- | source/blender/blenlib/intern/freetypefont.c | 3 | ||||
-rw-r--r-- | source/blender/blenlib/intern/matrixops.c | 438 | ||||
-rw-r--r-- | source/blender/blenlib/intern/storage.c | 18 | ||||
-rw-r--r-- | source/blender/blenlib/intern/threads.c | 19 | ||||
-rw-r--r-- | source/blender/blenlib/intern/util.c | 7 | ||||
-rw-r--r-- | source/blender/blenlib/intern/vectorops.c | 166 | ||||
-rw-r--r-- | source/blender/blenlib/intern/voxel.c | 198 |
11 files changed, 866 insertions, 890 deletions
diff --git a/source/blender/blenlib/intern/BLI_kdopbvh.c b/source/blender/blenlib/intern/BLI_kdopbvh.c index 61d9cce1a58..07e81b291f5 100644 --- a/source/blender/blenlib/intern/BLI_kdopbvh.c +++ b/source/blender/blenlib/intern/BLI_kdopbvh.c @@ -72,10 +72,10 @@ struct BVHTree char start_axis, stop_axis; // KDOP_AXES array indices according to axis }; -typedef struct BVHOverlapData -{ - BVHTree *tree1, *tree2; - BVHTreeOverlap *overlap; +typedef struct BVHOverlapData +{ + BVHTree *tree1, *tree2; + BVHTreeOverlap *overlap; int i, max_overlap; /* i is number of overlaps */ int start_axis, stop_axis; } BVHOverlapData; @@ -109,7 +109,7 @@ typedef struct BVHRayCastData //////////////////////////////////////////////////////////////////////// // Bounding Volume Hierarchy Definition -// +// // Notes: From OBB until 26-DOP --> all bounding volumes possible, just choose type below // Notes: You have to choose the type at compile time ITM // Notes: You can choose the tree type --> binary, quad, octree, choose below @@ -188,10 +188,10 @@ int ADJUST_MEMORY(void *local_memblock, void **memblock, int new_size, int *max_ ////////////////////////////////////////////////////////////////////////////////////////////////////// -// Introsort +// Introsort // with permission deriven from the following Java code: // http://ralphunden.net/content/tutorials/a-guide-to-introsort/ -// and he derived it from the SUN STL +// and he derived it from the SUN STL ////////////////////////////////////////////////////////////////////////////////////////////////////// static int size_threshold = 16; /* @@ -362,7 +362,7 @@ static void create_kdop_hull(BVHTree *tree, BVHNode *node, float *co, int numpoi float newminmax; float *bv = node->bv; int i, k; - + // don't init boudings for the moving case if(!moving) { @@ -372,7 +372,7 @@ static void create_kdop_hull(BVHTree *tree, BVHNode *node, float *co, int numpoi bv[2*i + 1] = -FLT_MAX; } } - + for(k = 0; k < numpoints; k++) { // for all Axes. @@ -394,7 +394,7 @@ static void refit_kdop_hull(BVHTree *tree, BVHNode *node, int start, int end) int i, j; float *bv = node->bv; - + for (i = tree->start_axis; i < tree->stop_axis; i++) { bv[2*i] = FLT_MAX; @@ -406,10 +406,10 @@ static void refit_kdop_hull(BVHTree *tree, BVHNode *node, int start, int end) // for all Axes. for (i = tree->start_axis; i < tree->stop_axis; i++) { - newmin = tree->nodes[j]->bv[(2 * i)]; + newmin = tree->nodes[j]->bv[(2 * i)]; if ((newmin < bv[(2 * i)])) bv[(2 * i)] = newmin; - + newmax = tree->nodes[j]->bv[(2 * i) + 1]; if ((newmax > bv[(2 * i) + 1])) bv[(2 * i) + 1] = newmax; @@ -427,14 +427,14 @@ static char get_largest_axis(float *bv) middle_point[0] = (bv[1]) - (bv[0]); // x axis middle_point[1] = (bv[3]) - (bv[2]); // y axis middle_point[2] = (bv[5]) - (bv[4]); // z axis - if (middle_point[0] > middle_point[1]) + if (middle_point[0] > middle_point[1]) { if (middle_point[0] > middle_point[2]) return 1; // max x axis else return 5; // max z axis } - else + else { if (middle_point[1] > middle_point[2]) return 3; // max y axis @@ -448,24 +448,24 @@ static char get_largest_axis(float *bv) static void node_join(BVHTree *tree, BVHNode *node) { int i, j; - + for (i = tree->start_axis; i < tree->stop_axis; i++) { node->bv[2*i] = FLT_MAX; node->bv[2*i + 1] = -FLT_MAX; } - + for (i = 0; i < tree->tree_type; i++) { - if (node->children[i]) + if (node->children[i]) { for (j = tree->start_axis; j < tree->stop_axis; j++) { - // update minimum - if (node->children[i]->bv[(2 * j)] < node->bv[(2 * j)]) + // update minimum + if (node->children[i]->bv[(2 * j)] < node->bv[(2 * j)]) node->bv[(2 * j)] = node->children[i]->bv[(2 * j)]; - - // update maximum + + // update maximum if (node->children[i]->bv[(2 * j) + 1] > node->bv[(2 * j) + 1]) node->bv[(2 * j) + 1] = node->children[i]->bv[(2 * j) + 1]; } @@ -518,7 +518,7 @@ static void bvhtree_info(BVHTree *tree) static void verify_tree(BVHTree *tree) { int i, j, check = 0; - + // check the pointer list for(i = 0; i < tree->totleaf; i++) { @@ -538,7 +538,7 @@ static void verify_tree(BVHTree *tree) check = 0; } } - + // check the leaf list for(i = 0; i < tree->totleaf; i++) { @@ -558,7 +558,7 @@ static void verify_tree(BVHTree *tree) check = 0; } } - + printf("branches: %d, leafs: %d, total: %d\n", tree->totbranch, tree->totleaf, tree->totbranch + tree->totleaf); } #endif @@ -703,7 +703,7 @@ static void non_recursive_bvh_div_nodes(BVHTree *tree, BVHNode *branches_array, BVHBuildHelper data; int depth; - + // set parent from root node to NULL BVHNode *tmp = branches_array+0; tmp->parent = NULL; @@ -722,7 +722,7 @@ static void non_recursive_bvh_div_nodes(BVHTree *tree, BVHNode *branches_array, } branches_array--; //Implicit trees use 1-based indexs - + build_implicit_tree_helper(tree, &data); //Loop tree levels (log N) loops @@ -806,11 +806,11 @@ BVHTree *BLI_bvhtree_new(int maxsize, float epsilon, char tree_type, char axis) { BVHTree *tree; int numnodes, i; - + // theres not support for trees below binary-trees :P if(tree_type < 2) return NULL; - + if(tree_type > MAX_TREETYPE) return NULL; @@ -820,13 +820,13 @@ BVHTree *BLI_bvhtree_new(int maxsize, float epsilon, char tree_type, char axis) //so that tangent rays can still hit a bounding volume.. //this bug would show up when casting a ray aligned with a kdop-axis and with an edge of 2 faces epsilon = MAX2(FLT_EPSILON, epsilon); - + if(tree) { tree->epsilon = epsilon; - tree->tree_type = tree_type; + tree->tree_type = tree_type; tree->axis = axis; - + if(axis == 26) { tree->start_axis = 0; @@ -863,13 +863,13 @@ BVHTree *BLI_bvhtree_new(int maxsize, float epsilon, char tree_type, char axis) numnodes = maxsize + implicit_needed_branches(tree_type, maxsize) + tree_type; tree->nodes = (BVHNode **)MEM_callocN(sizeof(BVHNode *)*numnodes, "BVHNodes"); - + if(!tree->nodes) { MEM_freeN(tree); return NULL; } - + tree->nodebv = (float*)MEM_callocN(sizeof(float)* axis * numnodes, "BVHNodeBV"); if(!tree->nodebv) { @@ -886,7 +886,7 @@ BVHTree *BLI_bvhtree_new(int maxsize, float epsilon, char tree_type, char axis) } tree->nodearray = (BVHNode *)MEM_callocN(sizeof(BVHNode)* numnodes, "BVHNodeArray"); - + if(!tree->nodearray) { MEM_freeN(tree->nodechild); @@ -902,14 +902,14 @@ BVHTree *BLI_bvhtree_new(int maxsize, float epsilon, char tree_type, char axis) tree->nodearray[i].bv = tree->nodebv + i * axis; tree->nodearray[i].children = tree->nodechild + i * tree_type; } - + } return tree; } void BLI_bvhtree_free(BVHTree *tree) -{ +{ if(tree) { MEM_freeN(tree->nodes); @@ -946,27 +946,27 @@ int BLI_bvhtree_insert(BVHTree *tree, int index, float *co, int numpoints) { int i; BVHNode *node = NULL; - + // insert should only possible as long as tree->totbranch is 0 if(tree->totbranch > 0) return 0; - + if(tree->totleaf+1 >= MEM_allocN_len(tree->nodes)/sizeof(*(tree->nodes))) return 0; - + // TODO check if have enough nodes in array - + node = tree->nodes[tree->totleaf] = &(tree->nodearray[tree->totleaf]); tree->totleaf++; - + create_kdop_hull(tree, node, co, numpoints, 0); node->index= index; - + // inflate the bv with some epsilon for (i = tree->start_axis; i < tree->stop_axis; i++) { - node->bv[(2 * i)] -= tree->epsilon; // minimum - node->bv[(2 * i) + 1] += tree->epsilon; // maximum + node->bv[(2 * i)] -= tree->epsilon; // minimum + node->bv[(2 * i) + 1] += tree->epsilon; // maximum } return 1; @@ -978,23 +978,23 @@ int BLI_bvhtree_update_node(BVHTree *tree, int index, float *co, float *co_movin { int i; BVHNode *node= NULL; - + // check if index exists if(index > tree->totleaf) return 0; - + node = tree->nodearray + index; - + create_kdop_hull(tree, node, co, numpoints, 0); - + if(co_moving) create_kdop_hull(tree, node, co_moving, numpoints, 1); - + // inflate the bv with some epsilon for (i = tree->start_axis; i < tree->stop_axis; i++) { - node->bv[(2 * i)] -= tree->epsilon; // minimum - node->bv[(2 * i) + 1] += tree->epsilon; // maximum + node->bv[(2 * i)] -= tree->epsilon; // minimum + node->bv[(2 * i) + 1] += tree->epsilon; // maximum } return 1; @@ -1030,24 +1030,24 @@ static int tree_overlap(BVHNode *node1, BVHNode *node2, int start_axis, int stop float *bv2 = node2->bv; float *bv1_end = bv1 + (stop_axis<<1); - + bv1 += start_axis<<1; bv2 += start_axis<<1; - + // test all axis if min + max overlap for (; bv1 != bv1_end; bv1+=2, bv2+=2) { - if ((*(bv1) > *(bv2 + 1)) || (*(bv2) > *(bv1 + 1))) + if ((*(bv1) > *(bv2 + 1)) || (*(bv2) > *(bv1 + 1))) return 0; } - + return 1; } static void traverse(BVHOverlapData *data, BVHNode *node1, BVHNode *node2) { int j; - + if(tree_overlap(node1, node2, data->start_axis, data->stop_axis)) { // check if node1 is a leaf @@ -1056,17 +1056,17 @@ static void traverse(BVHOverlapData *data, BVHNode *node1, BVHNode *node2) // check if node2 is a leaf if(!node2->totnode) { - + if(node1 == node2) { return; } - + if(data->i >= data->max_overlap) - { + { // try to make alloc'ed memory bigger data->overlap = realloc(data->overlap, sizeof(BVHTreeOverlap)*data->max_overlap*2); - + if(!data->overlap) { printf("Out of Memory in traverse\n"); @@ -1074,7 +1074,7 @@ static void traverse(BVHOverlapData *data, BVHNode *node1, BVHNode *node2) } data->max_overlap *= 2; } - + // both leafs, insert overlap! data->overlap[data->i].indexA = node1->index; data->overlap[data->i].indexB = node2->index; @@ -1092,7 +1092,7 @@ static void traverse(BVHOverlapData *data, BVHNode *node1, BVHNode *node2) } else { - + for(j = 0; j < data->tree2->tree_type; j++) { if(node1->children[j]) @@ -1108,21 +1108,21 @@ BVHTreeOverlap *BLI_bvhtree_overlap(BVHTree *tree1, BVHTree *tree2, int *result) int j, total = 0; BVHTreeOverlap *overlap = NULL, *to = NULL; BVHOverlapData **data; - + // check for compatibility of both trees (can't compare 14-DOP with 18-DOP) if((tree1->axis != tree2->axis) && (tree1->axis == 14 || tree2->axis == 14) && (tree1->axis == 18 || tree2->axis == 18)) return 0; - + // fast check root nodes for collision before doing big splitting + traversal if(!tree_overlap(tree1->nodes[tree1->totleaf], tree2->nodes[tree2->totleaf], MIN2(tree1->start_axis, tree2->start_axis), MIN2(tree1->stop_axis, tree2->stop_axis))) return 0; data = MEM_callocN(sizeof(BVHOverlapData *)* tree1->tree_type, "BVHOverlapData_star"); - + for(j = 0; j < tree1->tree_type; j++) { data[j] = (BVHOverlapData *)MEM_callocN(sizeof(BVHOverlapData), "BVHOverlapData"); - + // init BVHOverlapData data[j]->overlap = (BVHTreeOverlap *)malloc(sizeof(BVHTreeOverlap)*MAX2(tree1->totleaf, tree2->totleaf)); data[j]->tree1 = tree1; @@ -1138,25 +1138,25 @@ BVHTreeOverlap *BLI_bvhtree_overlap(BVHTree *tree1, BVHTree *tree2, int *result) { traverse(data[j], tree1->nodes[tree1->totleaf]->children[j], tree2->nodes[tree2->totleaf]); } - + for(j = 0; j < tree1->tree_type; j++) total += data[j]->i; - + to = overlap = (BVHTreeOverlap *)MEM_callocN(sizeof(BVHTreeOverlap)*total, "BVHTreeOverlap"); - + for(j = 0; j < tree1->tree_type; j++) { memcpy(to, data[j]->overlap, data[j]->i*sizeof(BVHTreeOverlap)); to+=data[j]->i; } - + for(j = 0; j < tree1->tree_type; j++) { free(data[j]->overlap); MEM_freeN(data[j]); } MEM_freeN(data); - + (*result) = total; return overlap; } @@ -1173,7 +1173,7 @@ static float squared_dist(const float *a, const float *b) } //Determines the nearest point of the given node BV. Returns the squared distance to that point. -static float calc_nearest_point(const float *proj, BVHNode *node, float *nearest) +static float calc_nearest_point(BVHNearestData *data, BVHNode *node, float *nearest) { int i; const float *bv = node->bv; @@ -1181,12 +1181,12 @@ static float calc_nearest_point(const float *proj, BVHNode *node, float *nearest //nearest on AABB hull for(i=0; i != 3; i++, bv += 2) { - if(bv[0] > proj[i]) + if(bv[0] > data->proj[i]) nearest[i] = bv[0]; - else if(bv[1] < proj[i]) + else if(bv[1] < data->proj[i]) nearest[i] = bv[1]; else - nearest[i] = proj[i]; + nearest[i] = data->proj[i]; } /* @@ -1208,7 +1208,7 @@ static float calc_nearest_point(const float *proj, BVHNode *node, float *nearest } } */ - return squared_dist(proj, nearest); + return squared_dist(data->co, nearest); } @@ -1231,7 +1231,7 @@ static void dfs_find_nearest_dfs(BVHNearestData *data, BVHNode *node) else { data->nearest.index = node->index; - data->nearest.dist = calc_nearest_point(data->proj, node, data->nearest.co); + data->nearest.dist = calc_nearest_point(data, node, data->nearest.co); } } else @@ -1240,12 +1240,12 @@ static void dfs_find_nearest_dfs(BVHNearestData *data, BVHNode *node) int i; float nearest[3]; - if(data->proj[ node->main_axis ] <= node->children[0]->bv[node->main_axis*2+1]) + if(data->proj[ (int)node->main_axis ] <= node->children[0]->bv[(int)node->main_axis*2+1]) { for(i=0; i != node->totnode; i++) { - if( calc_nearest_point(data->proj, node->children[i], nearest) >= data->nearest.dist) continue; + if( calc_nearest_point(data, node->children[i], nearest) >= data->nearest.dist) continue; dfs_find_nearest_dfs(data, node->children[i]); } } @@ -1253,7 +1253,7 @@ static void dfs_find_nearest_dfs(BVHNearestData *data, BVHNode *node) { for(i=node->totnode-1; i >= 0 ; i--) { - if( calc_nearest_point(data->proj, node->children[i], nearest) >= data->nearest.dist) continue; + if( calc_nearest_point(data, node->children[i], nearest) >= data->nearest.dist) continue; dfs_find_nearest_dfs(data, node->children[i]); } } @@ -1263,7 +1263,7 @@ static void dfs_find_nearest_dfs(BVHNearestData *data, BVHNode *node) static void dfs_find_nearest_begin(BVHNearestData *data, BVHNode *node) { float nearest[3], sdist; - sdist = calc_nearest_point(data->proj, node, nearest); + sdist = calc_nearest_point(data, node, nearest); if(sdist >= data->nearest.dist) return; dfs_find_nearest_dfs(data, node); } @@ -1301,7 +1301,7 @@ static void bfs_find_nearest(BVHNearestData *data, BVHNode *node) } current.node = node; - current.dist = calc_nearest_point(data->proj, node, nearest); + current.dist = calc_nearest_point(data, node, nearest); while(current.dist < data->nearest.dist) { @@ -1329,7 +1329,7 @@ static void bfs_find_nearest(BVHNearestData *data, BVHNode *node) } heap[heap_size].node = current.node->children[i]; - heap[heap_size].dist = calc_nearest_point(data->proj, current.node->children[i], nearest); + heap[heap_size].dist = calc_nearest_point(data, current.node->children[i], nearest); if(heap[heap_size].dist >= data->nearest.dist) continue; heap_size++; @@ -1339,7 +1339,7 @@ static void bfs_find_nearest(BVHNearestData *data, BVHNode *node) push_heaps++; } } - + if(heap_size == 0) break; current = heap[0]; @@ -1355,7 +1355,6 @@ static void bfs_find_nearest(BVHNearestData *data, BVHNode *node) } #endif - int BLI_bvhtree_find_nearest(BVHTree *tree, const float *co, BVHTreeNearest *nearest, BVHTree_NearestPointCallback callback, void *userdata) { int i; @@ -1436,7 +1435,7 @@ static float ray_nearest_hit(BVHRayCastData *data, float *bv) if(lu > low) low = lu; if(ll < upper) upper = ll; } - + if(low > upper) return FLT_MAX; } } @@ -1533,115 +1532,28 @@ float BLI_bvhtree_bb_raycast(float *bv, float *light_start, float *light_end, fl float dist = 0.0; data.hit.dist = FLT_MAX; - + // get light direction data.ray.direction[0] = light_end[0] - light_start[0]; data.ray.direction[1] = light_end[1] - light_start[1]; data.ray.direction[2] = light_end[2] - light_start[2]; - + data.ray.radius = 0.0; - + data.ray.origin[0] = light_start[0]; data.ray.origin[1] = light_start[1]; data.ray.origin[2] = light_start[2]; - + Normalize(data.ray.direction); VECCOPY(data.ray_dot_axis, data.ray.direction); - + dist = ray_nearest_hit(&data, bv); - + if(dist > 0.0) { VECADDFAC(pos, light_start, data.ray.direction, dist); } return dist; - -} - -/* - * Range Query - as request by broken :P - * - * Allocs and fills an array with the indexs of node that are on the given spherical range (center, radius) - * Returns the size of the array. - */ -typedef struct RangeQueryData -{ - BVHTree *tree; - const float *center; - float radius; //squared radius - - int hits; - - BVHTree_RangeQuery callback; - void *userdata; - - -} RangeQueryData; - - -static void dfs_range_query(RangeQueryData *data, BVHNode *node) -{ - if(node->totnode == 0) - { - - //Calculate the node min-coords (if the node was a point then this is the point coordinates) - float co[3]; - co[0] = node->bv[0]; - co[1] = node->bv[2]; - co[2] = node->bv[4]; - } - else - { - int i; - for(i=0; i != node->totnode; i++) - { - float nearest[3]; - float dist = calc_nearest_point(data->center, node->children[i], nearest); - if(dist < data->radius) - { - //Its a leaf.. call the callback - if(node->children[i]->totnode == 0) - { - data->hits++; - data->callback( data->userdata, node->children[i]->index, dist ); - } - else - dfs_range_query( data, node->children[i] ); - } - } - } } -int BLI_bvhtree_range_query(BVHTree *tree, const float *co, float radius, BVHTree_RangeQuery callback, void *userdata) -{ - BVHNode * root = tree->nodes[tree->totleaf]; - - RangeQueryData data; - data.tree = tree; - data.center = co; - data.radius = radius*radius; - data.hits = 0; - - data.callback = callback; - data.userdata = userdata; - - if(root != NULL) - { - float nearest[3]; - float dist = calc_nearest_point(data.center, root, nearest); - if(dist < data.radius) - { - //Its a leaf.. call the callback - if(root->totnode == 0) - { - data.hits++; - data.callback( data.userdata, root->index, dist ); - } - else - dfs_range_query( &data, root ); - } - } - - return data.hits; -} diff --git a/source/blender/blenlib/intern/arithb.c b/source/blender/blenlib/intern/arithb.c index 96056ba7783..a26e333e095 100644 --- a/source/blender/blenlib/intern/arithb.c +++ b/source/blender/blenlib/intern/arithb.c @@ -1408,6 +1408,22 @@ void RotationBetweenVectorsToQuat(float *q, float v1[3], float v2[3]) AxisAngleToQuat(q, axis, angle); } +void AxisAngleToQuat(float *q, float *axis, float angle) +{ + float nor[3]; + float si; + + VecCopyf(nor, axis); + Normalize(nor); + + angle /= 2; + si = (float)sin(angle); + q[0] = (float)cos(angle); + q[1] = nor[0] * si; + q[2] = nor[1] * si; + q[3] = nor[2] * si; +} + void vectoquat(float *vec, short axis, short upflag, float *q) { float q2[4], nor[3], *fp, mat[3][3], angle, si, co, x2, y2, z2, len1; @@ -1594,7 +1610,7 @@ void VecUpMat3(float *vec, float mat[][3], short axis) } /* A & M Watt, Advanced animation and rendering techniques, 1992 ACM press */ -void QuatInterpolW(float *, float *, float *, float ); // XXX why this? +void QuatInterpolW(float *, float *, float *, float ); void QuatInterpolW(float *result, float *quat1, float *quat2, float t) { @@ -2160,13 +2176,6 @@ void VecSubf(float *v, float *v1, float *v2) v[2]= v1[2]- v2[2]; } -void VecMulVecf(float *v, float *v1, float *v2) -{ - v[0] = v1[0] * v2[0]; - v[1] = v1[1] * v2[1]; - v[2] = v1[2] * v2[2]; -} - void VecLerpf(float *target, float *a, float *b, float t) { float s = 1.0f-t; @@ -2791,241 +2800,6 @@ void MeanValueWeights(float v[][3], int n, float *co, float *w) /* ************ EULER *************** */ -/* Euler Rotation Order Code: - * was adapted from - ANSI C code from the article - "Euler Angle Conversion" - by Ken Shoemake, shoemake@graphics.cis.upenn.edu - in "Graphics Gems IV", Academic Press, 1994 - * for use in Blender - */ - -/* Type for rotation order info - see wiki for derivation details */ -typedef struct RotOrderInfo { - short i; /* first axis index */ - short j; /* second axis index */ - short k; /* third axis index */ - short parity; /* parity of axis permuation (even=0, odd=1) - 'n' in original code */ -} RotOrderInfo; - -/* Array of info for Rotation Order calculations - * WARNING: must be kept in same order as eEulerRotationOrders - */ -static RotOrderInfo rotOrders[]= { - /* i, j, k, n */ - {0, 1, 2, 0}, // XYZ - {0, 2, 1, 1}, // XZY - {1, 0, 2, 1}, // YXZ - {1, 2, 0, 0}, // YZX - {2, 0, 1, 0}, // ZXY - {2, 1, 0, 1} // ZYZ -}; - -/* Get relevant pointer to rotation order set from the array - * NOTE: since we start at 1 for the values, but arrays index from 0, - * there is -1 factor involved in this process... - */ -#define GET_ROTATIONORDER_INFO(order) (((order)>=1) ? &rotOrders[(order)-1] : &rotOrders[0]) - -/* Construct quaternion from Euler angles (in radians). */ -void EulOToQuat(float e[3], short order, float q[4]) -{ - RotOrderInfo *R= GET_ROTATIONORDER_INFO(order); - short i=R->i, j=R->j, k=R->k; - double ti, tj, th, ci, cj, ch, si, sj, sh, cc, cs, sc, ss; - double a[3]; - - ti = e[i]/2; tj = e[j]/2; th = e[k]/2; - - if (R->parity) e[j] = -e[j]; - - ci = cos(ti); cj = cos(tj); ch = cos(th); - si = sin(ti); sj = sin(tj); sh = sin(th); - - cc = ci*ch; cs = ci*sh; - sc = si*ch; ss = si*sh; - - a[i] = cj*sc - sj*cs; - a[j] = cj*ss + sj*cc; - a[k] = cj*cs - sj*sc; - - q[0] = cj*cc + sj*ss; - q[1] = a[0]; - q[2] = a[1]; - q[3] = a[2]; - - if (R->parity) q[j] = -q[j]; -} - -/* Convert quaternion to Euler angles (in radians). */ -void QuatToEulO(float q[4], float e[3], short order) -{ - float M[3][3]; - - QuatToMat3(q, M); - Mat3ToEulO(M, e, order); -} - -/* Construct 3x3 matrix from Euler angles (in radians). */ -void EulOToMat3(float e[3], short order, float M[3][3]) -{ - RotOrderInfo *R= GET_ROTATIONORDER_INFO(order); - short i=R->i, j=R->j, k=R->k; - double ti, tj, th, ci, cj, ch, si, sj, sh, cc, cs, sc, ss; - - if (R->parity) { - ti = -e[i]; tj = -e[j]; th = -e[k]; - } - else { - ti = e[i]; tj = e[j]; th = e[k]; - } - - ci = cos(ti); cj = cos(tj); ch = cos(th); - si = sin(ti); sj = sin(tj); sh = sin(th); - - cc = ci*ch; cs = ci*sh; - sc = si*ch; ss = si*sh; - - M[i][i] = cj*ch; M[j][i] = sj*sc-cs; M[k][i] = sj*cc+ss; - M[i][j] = cj*sh; M[j][j] = sj*ss+cc; M[k][j] = sj*cs-sc; - M[i][k] = -sj; M[j][k] = cj*si; M[k][k] = cj*ci; -} - -/* Construct 4x4 matrix from Euler angles (in radians). */ -void EulOToMat4(float e[3], short order, float M[4][4]) -{ - float m[3][3]; - - /* for now, we'll just do this the slow way (i.e. copying matrices) */ - Mat3Ortho(m); - EulOToMat3(e, order, m); - Mat4CpyMat3(M, m); -} - -/* Convert 3x3 matrix to Euler angles (in radians). */ -void Mat3ToEulO(float M[3][3], float e[3], short order) -{ - RotOrderInfo *R= GET_ROTATIONORDER_INFO(order); - short i=R->i, j=R->j, k=R->k; - double cy = sqrt(M[i][i]*M[i][i] + M[i][j]*M[i][j]); - - if (cy > 16*FLT_EPSILON) { - e[i] = atan2(M[j][k], M[k][k]); - e[j] = atan2(-M[i][k], cy); - e[k] = atan2(M[i][j], M[i][i]); - } - else { - e[i] = atan2(-M[k][j], M[j][j]); - e[j] = atan2(-M[i][k], cy); - e[k] = 0; - } - - if (R->parity) { - e[0] = -e[0]; - e[1] = -e[1]; - e[2] = -e[2]; - } -} - -/* Convert 4x4 matrix to Euler angles (in radians). */ -void Mat4ToEulO(float M[4][4], float e[3], short order) -{ - float m[3][3]; - - /* for now, we'll just do this the slow way (i.e. copying matrices) */ - Mat3CpyMat4(m, M); - Mat3Ortho(m); - Mat3ToEulO(m, e, order); -} - -/* returns two euler calculation methods, so we can pick the best */ -static void mat3_to_eulo2(float M[3][3], float *e1, float *e2, short order) -{ - RotOrderInfo *R= GET_ROTATIONORDER_INFO(order); - short i=R->i, j=R->j, k=R->k; - float m[3][3]; - double cy; - - /* process the matrix first */ - Mat3CpyMat3(m, M); - Mat3Ortho(m); - - cy= sqrt(m[i][i]*m[i][i] + m[i][j]*m[i][j]); - - if (cy > 16*FLT_EPSILON) { - e1[i] = atan2(m[j][k], m[k][k]); - e1[j] = atan2(-m[i][k], cy); - e1[k] = atan2(m[i][j], m[i][i]); - - e2[i] = atan2(-m[j][k], -m[k][k]); - e2[j] = atan2(-m[i][k], -cy); - e2[k] = atan2(-m[i][j], -m[i][i]); - } - else { - e1[i] = atan2(-m[k][j], m[j][j]); - e1[j] = atan2(-m[i][k], cy); - e1[k] = 0; - - VecCopyf(e2, e1); - } - - if (R->parity) { - e1[0] = -e1[0]; - e1[1] = -e1[1]; - e1[2] = -e1[2]; - - e2[0] = -e2[0]; - e2[1] = -e2[1]; - e2[2] = -e2[2]; - } -} - -/* uses 2 methods to retrieve eulers, and picks the closest */ -void Mat3ToCompatibleEulO(float mat[3][3], float eul[3], float oldrot[3], short order) -{ - float eul1[3], eul2[3]; - float d1, d2; - - mat3_to_eulo2(mat, eul1, eul2, order); - - compatible_eul(eul1, oldrot); - compatible_eul(eul2, oldrot); - - d1= (float)fabs(eul1[0]-oldrot[0]) + (float)fabs(eul1[1]-oldrot[1]) + (float)fabs(eul1[2]-oldrot[2]); - d2= (float)fabs(eul2[0]-oldrot[0]) + (float)fabs(eul2[1]-oldrot[1]) + (float)fabs(eul2[2]-oldrot[2]); - - /* return best, which is just the one with lowest difference */ - if (d1 > d2) - VecCopyf(eul, eul2); - else - VecCopyf(eul, eul1); -} - -/* rotate the given euler by the given angle on the specified axis */ -// NOTE: is this safe to do with different axis orders? -void eulerO_rot(float beul[3], float ang, char axis, short order) -{ - float eul[3], mat1[3][3], mat2[3][3], totmat[3][3]; - - eul[0]= eul[1]= eul[2]= 0.0f; - if (axis=='x') - eul[0]= ang; - else if (axis=='y') - eul[1]= ang; - else - eul[2]= ang; - - EulOToMat3(eul, order, mat1); - EulOToMat3(beul, order, mat2); - - Mat3MulMat3(totmat, mat2, mat1); - - Mat3ToEulO(totmat, beul, order); -} - -/* ************ EULER (old XYZ) *************** */ - -/* XYZ order */ void EulToMat3( float *eul, float mat[][3]) { double ci, cj, ch, si, sj, sh, cc, cs, sc, ss; @@ -3053,7 +2827,6 @@ void EulToMat3( float *eul, float mat[][3]) } -/* XYZ order */ void EulToMat4( float *eul,float mat[][4]) { double ci, cj, ch, si, sj, sh, cc, cs, sc, ss; @@ -3085,7 +2858,6 @@ void EulToMat4( float *eul,float mat[][4]) } /* returns two euler calculation methods, so we can pick the best */ -/* XYZ order */ static void mat3_to_eul2(float tmat[][3], float *eul1, float *eul2) { float cy, quat[4], mat[3][3]; @@ -3116,7 +2888,6 @@ static void mat3_to_eul2(float tmat[][3], float *eul1, float *eul2) } } -/* XYZ order */ void Mat3ToEul(float tmat[][3], float *eul) { float eul1[3], eul2[3]; @@ -3132,7 +2903,6 @@ void Mat3ToEul(float tmat[][3], float *eul) } } -/* XYZ order */ void Mat4ToEul(float tmat[][4], float *eul) { float tempMat[3][3]; @@ -3142,7 +2912,6 @@ void Mat4ToEul(float tmat[][4], float *eul) Mat3ToEul(tempMat, eul); } -/* XYZ order */ void QuatToEul(float *quat, float *eul) { float mat[3][3]; @@ -3151,7 +2920,7 @@ void QuatToEul(float *quat, float *eul) Mat3ToEul(mat, eul); } -/* XYZ order */ + void EulToQuat(float *eul, float *quat) { float ti, tj, th, ci, cj, ch, si, sj, sh, cc, cs, sc, ss; @@ -3167,155 +2936,6 @@ void EulToQuat(float *eul, float *quat) quat[3] = cj*cs - sj*sc; } -/* XYZ order */ -void euler_rot(float *beul, float ang, char axis) -{ - float eul[3], mat1[3][3], mat2[3][3], totmat[3][3]; - - eul[0]= eul[1]= eul[2]= 0.0f; - if(axis=='x') eul[0]= ang; - else if(axis=='y') eul[1]= ang; - else eul[2]= ang; - - EulToMat3(eul, mat1); - EulToMat3(beul, mat2); - - Mat3MulMat3(totmat, mat2, mat1); - - Mat3ToEul(totmat, beul); - -} - -/* exported to transform.c */ -/* order independent! */ -void compatible_eul(float *eul, float *oldrot) -{ - float dx, dy, dz; - - /* correct differences of about 360 degrees first */ - dx= eul[0] - oldrot[0]; - dy= eul[1] - oldrot[1]; - dz= eul[2] - oldrot[2]; - - while(fabs(dx) > 5.1) { - if(dx > 0.0f) eul[0] -= 2.0f*(float)M_PI; else eul[0]+= 2.0f*(float)M_PI; - dx= eul[0] - oldrot[0]; - } - while(fabs(dy) > 5.1) { - if(dy > 0.0f) eul[1] -= 2.0f*(float)M_PI; else eul[1]+= 2.0f*(float)M_PI; - dy= eul[1] - oldrot[1]; - } - while(fabs(dz) > 5.1) { - if(dz > 0.0f) eul[2] -= 2.0f*(float)M_PI; else eul[2]+= 2.0f*(float)M_PI; - dz= eul[2] - oldrot[2]; - } - - /* is 1 of the axis rotations larger than 180 degrees and the other small? NO ELSE IF!! */ - if( fabs(dx) > 3.2 && fabs(dy)<1.6 && fabs(dz)<1.6 ) { - if(dx > 0.0) eul[0] -= 2.0f*(float)M_PI; else eul[0]+= 2.0f*(float)M_PI; - } - if( fabs(dy) > 3.2 && fabs(dz)<1.6 && fabs(dx)<1.6 ) { - if(dy > 0.0) eul[1] -= 2.0f*(float)M_PI; else eul[1]+= 2.0f*(float)M_PI; - } - if( fabs(dz) > 3.2 && fabs(dx)<1.6 && fabs(dy)<1.6 ) { - if(dz > 0.0) eul[2] -= 2.0f*(float)M_PI; else eul[2]+= 2.0f*(float)M_PI; - } - - /* the method below was there from ancient days... but why! probably because the code sucks :) - */ -#if 0 - /* calc again */ - dx= eul[0] - oldrot[0]; - dy= eul[1] - oldrot[1]; - dz= eul[2] - oldrot[2]; - - /* special case, tested for x-z */ - - if( (fabs(dx) > 3.1 && fabs(dz) > 1.5 ) || ( fabs(dx) > 1.5 && fabs(dz) > 3.1 ) ) { - if(dx > 0.0) eul[0] -= M_PI; else eul[0]+= M_PI; - if(eul[1] > 0.0) eul[1]= M_PI - eul[1]; else eul[1]= -M_PI - eul[1]; - if(dz > 0.0) eul[2] -= M_PI; else eul[2]+= M_PI; - - } - else if( (fabs(dx) > 3.1 && fabs(dy) > 1.5 ) || ( fabs(dx) > 1.5 && fabs(dy) > 3.1 ) ) { - if(dx > 0.0) eul[0] -= M_PI; else eul[0]+= M_PI; - if(dy > 0.0) eul[1] -= M_PI; else eul[1]+= M_PI; - if(eul[2] > 0.0) eul[2]= M_PI - eul[2]; else eul[2]= -M_PI - eul[2]; - } - else if( (fabs(dy) > 3.1 && fabs(dz) > 1.5 ) || ( fabs(dy) > 1.5 && fabs(dz) > 3.1 ) ) { - if(eul[0] > 0.0) eul[0]= M_PI - eul[0]; else eul[0]= -M_PI - eul[0]; - if(dy > 0.0) eul[1] -= M_PI; else eul[1]+= M_PI; - if(dz > 0.0) eul[2] -= M_PI; else eul[2]+= M_PI; - } -#endif -} - -/* uses 2 methods to retrieve eulers, and picks the closest */ -/* XYZ order */ -void Mat3ToCompatibleEul(float mat[][3], float *eul, float *oldrot) -{ - float eul1[3], eul2[3]; - float d1, d2; - - mat3_to_eul2(mat, eul1, eul2); - - compatible_eul(eul1, oldrot); - compatible_eul(eul2, oldrot); - - d1= (float)fabs(eul1[0]-oldrot[0]) + (float)fabs(eul1[1]-oldrot[1]) + (float)fabs(eul1[2]-oldrot[2]); - d2= (float)fabs(eul2[0]-oldrot[0]) + (float)fabs(eul2[1]-oldrot[1]) + (float)fabs(eul2[2]-oldrot[2]); - - /* return best, which is just the one with lowest difference */ - if( d1 > d2) { - VecCopyf(eul, eul2); - } - else { - VecCopyf(eul, eul1); - } - -} - -/* ************ AXIS ANGLE *************** */ - -/* Axis angle to Quaternions */ -void AxisAngleToQuat(float *q, float *axis, float angle) -{ - float nor[3]; - float si; - - VecCopyf(nor, axis); - Normalize(nor); - - angle /= 2; - si = (float)sin(angle); - q[0] = (float)cos(angle); - q[1] = nor[0] * si; - q[2] = nor[1] * si; - q[3] = nor[2] * si; -} - -/* Quaternions to Axis Angle */ -void QuatToAxisAngle(float q[4], float axis[3], float *angle) -{ - float ha, si; - - /* calculate angle/2, and sin(angle/2) */ - ha= (float)acos(q[0]); - si= (float)sin(ha); - - /* from half-angle to angle */ - *angle= ha * 2; - - /* prevent division by zero for axis conversion */ - if (fabs(si) < 0.0005) - si= 1.0f; - - axis[0]= q[1] / si; - axis[1]= q[2] / si; - axis[2]= q[3] / si; -} - -/* axis angle to 3x3 matrix */ void VecRotToMat3(float *vec, float phi, float mat[][3]) { /* rotation of phi radials around vec */ @@ -3342,7 +2962,6 @@ void VecRotToMat3(float *vec, float phi, float mat[][3]) } -/* axis angle to 4x4 matrix */ void VecRotToMat4(float *vec, float phi, float mat[][4]) { float tmat[3][3]; @@ -3352,7 +2971,6 @@ void VecRotToMat4(float *vec, float phi, float mat[][4]) Mat4CpyMat3(mat, tmat); } -/* axis angle to quaternion */ void VecRotToQuat(float *vec, float phi, float *quat) { /* rotation of phi radials around vec */ @@ -3374,41 +2992,6 @@ void VecRotToQuat(float *vec, float phi, float *quat) } } -/* Returns a vector bisecting the angle at v2 formed by v1, v2 and v3 */ -void VecBisect3(float *out, float *v1, float *v2, float *v3) -{ - float d_12[3], d_23[3]; - VecSubf(d_12, v2, v1); - VecSubf(d_23, v3, v2); - Normalize(d_12); - Normalize(d_23); - VecAddf(out, d_12, d_23); - Normalize(out); -} - -/* Returns a reflection vector from a vector and a normal vector -reflect = vec - ((2 * DotVecs(vec, mirror)) * mirror) -*/ -void VecReflect(float *out, float *v1, float *v2) -{ - float vec[3], normal[3]; - float reflect[3] = {0.0f, 0.0f, 0.0f}; - float dot2; - - VecCopyf(vec, v1); - VecCopyf(normal, v2); - - Normalize(normal); - - dot2 = 2 * Inpf(vec, normal); - - reflect[0] = vec[0] - (dot2 * normal[0]); - reflect[1] = vec[1] - (dot2 * normal[1]); - reflect[2] = vec[2] - (dot2 * normal[2]); - - VecCopyf(out, reflect); -} - /* Return the angle in degrees between vecs 1-2 and 2-3 in degrees If v1 is a shoulder, v2 is the elbow and v3 is the hand, this would return the angle at the elbow */ @@ -3484,6 +3067,111 @@ float NormalizedVecAngle2_2D(float *v1, float *v2) return 2.0f*(float)saasin(Vec2Lenf(v2, v1)/2.0f); } +void euler_rot(float *beul, float ang, char axis) +{ + float eul[3], mat1[3][3], mat2[3][3], totmat[3][3]; + + eul[0]= eul[1]= eul[2]= 0.0f; + if(axis=='x') eul[0]= ang; + else if(axis=='y') eul[1]= ang; + else eul[2]= ang; + + EulToMat3(eul, mat1); + EulToMat3(beul, mat2); + + Mat3MulMat3(totmat, mat2, mat1); + + Mat3ToEul(totmat, beul); + +} + +/* exported to transform.c */ +void compatible_eul(float *eul, float *oldrot) +{ + float dx, dy, dz; + + /* correct differences of about 360 degrees first */ + dx= eul[0] - oldrot[0]; + dy= eul[1] - oldrot[1]; + dz= eul[2] - oldrot[2]; + + while(fabs(dx) > 5.1) { + if(dx > 0.0f) eul[0] -= 2.0f*(float)M_PI; else eul[0]+= 2.0f*(float)M_PI; + dx= eul[0] - oldrot[0]; + } + while(fabs(dy) > 5.1) { + if(dy > 0.0f) eul[1] -= 2.0f*(float)M_PI; else eul[1]+= 2.0f*(float)M_PI; + dy= eul[1] - oldrot[1]; + } + while(fabs(dz) > 5.1) { + if(dz > 0.0f) eul[2] -= 2.0f*(float)M_PI; else eul[2]+= 2.0f*(float)M_PI; + dz= eul[2] - oldrot[2]; + } + + /* is 1 of the axis rotations larger than 180 degrees and the other small? NO ELSE IF!! */ + if( fabs(dx) > 3.2 && fabs(dy)<1.6 && fabs(dz)<1.6 ) { + if(dx > 0.0) eul[0] -= 2.0f*(float)M_PI; else eul[0]+= 2.0f*(float)M_PI; + } + if( fabs(dy) > 3.2 && fabs(dz)<1.6 && fabs(dx)<1.6 ) { + if(dy > 0.0) eul[1] -= 2.0f*(float)M_PI; else eul[1]+= 2.0f*(float)M_PI; + } + if( fabs(dz) > 3.2 && fabs(dx)<1.6 && fabs(dy)<1.6 ) { + if(dz > 0.0) eul[2] -= 2.0f*(float)M_PI; else eul[2]+= 2.0f*(float)M_PI; + } + + /* the method below was there from ancient days... but why! probably because the code sucks :) + */ +#if 0 + /* calc again */ + dx= eul[0] - oldrot[0]; + dy= eul[1] - oldrot[1]; + dz= eul[2] - oldrot[2]; + + /* special case, tested for x-z */ + + if( (fabs(dx) > 3.1 && fabs(dz) > 1.5 ) || ( fabs(dx) > 1.5 && fabs(dz) > 3.1 ) ) { + if(dx > 0.0) eul[0] -= M_PI; else eul[0]+= M_PI; + if(eul[1] > 0.0) eul[1]= M_PI - eul[1]; else eul[1]= -M_PI - eul[1]; + if(dz > 0.0) eul[2] -= M_PI; else eul[2]+= M_PI; + + } + else if( (fabs(dx) > 3.1 && fabs(dy) > 1.5 ) || ( fabs(dx) > 1.5 && fabs(dy) > 3.1 ) ) { + if(dx > 0.0) eul[0] -= M_PI; else eul[0]+= M_PI; + if(dy > 0.0) eul[1] -= M_PI; else eul[1]+= M_PI; + if(eul[2] > 0.0) eul[2]= M_PI - eul[2]; else eul[2]= -M_PI - eul[2]; + } + else if( (fabs(dy) > 3.1 && fabs(dz) > 1.5 ) || ( fabs(dy) > 1.5 && fabs(dz) > 3.1 ) ) { + if(eul[0] > 0.0) eul[0]= M_PI - eul[0]; else eul[0]= -M_PI - eul[0]; + if(dy > 0.0) eul[1] -= M_PI; else eul[1]+= M_PI; + if(dz > 0.0) eul[2] -= M_PI; else eul[2]+= M_PI; + } +#endif +} + +/* uses 2 methods to retrieve eulers, and picks the closest */ +void Mat3ToCompatibleEul(float mat[][3], float *eul, float *oldrot) +{ + float eul1[3], eul2[3]; + float d1, d2; + + mat3_to_eul2(mat, eul1, eul2); + + compatible_eul(eul1, oldrot); + compatible_eul(eul2, oldrot); + + d1= (float)fabs(eul1[0]-oldrot[0]) + (float)fabs(eul1[1]-oldrot[1]) + (float)fabs(eul1[2]-oldrot[2]); + d2= (float)fabs(eul2[0]-oldrot[0]) + (float)fabs(eul2[1]-oldrot[1]) + (float)fabs(eul2[2]-oldrot[2]); + + /* return best, which is just the one with lowest difference */ + if( d1 > d2) { + VecCopyf(eul, eul2); + } + else { + VecCopyf(eul, eul1); + } + +} + /* ******************************************** */ void SizeToMat3( float *size, float mat[][3]) @@ -5006,8 +4694,7 @@ float PdistVL3Dfl(float *v1, float *v2, float *v3) /* make a 4x4 matrix out of 3 transform components */ /* matrices are made in the order: scale * rot * loc */ -// TODO: need to have a version that allows for rotation order... -void LocEulSizeToMat4(float mat[4][4], float loc[3], float eul[3], float size[3]) +void LocEulSizeToMat4(float mat[][4], float loc[3], float eul[3], float size[3]) { float rmat[3][3], smat[3][3], tmat[3][3]; @@ -5030,31 +4717,7 @@ void LocEulSizeToMat4(float mat[4][4], float loc[3], float eul[3], float size[3] /* make a 4x4 matrix out of 3 transform components */ /* matrices are made in the order: scale * rot * loc */ -void LocEulOSizeToMat4(float mat[4][4], float loc[3], float eul[3], float size[3], short rotOrder) -{ - float rmat[3][3], smat[3][3], tmat[3][3]; - - /* initialise new matrix */ - Mat4One(mat); - - /* make rotation + scaling part */ - EulOToMat3(eul, rotOrder, rmat); - SizeToMat3(size, smat); - Mat3MulMat3(tmat, rmat, smat); - - /* copy rot/scale part to output matrix*/ - Mat4CpyMat3(mat, tmat); - - /* copy location to matrix */ - mat[3][0] = loc[0]; - mat[3][1] = loc[1]; - mat[3][2] = loc[2]; -} - - -/* make a 4x4 matrix out of 3 transform components */ -/* matrices are made in the order: scale * rot * loc */ -void LocQuatSizeToMat4(float mat[4][4], float loc[3], float quat[4], float size[3]) +void LocQuatSizeToMat4(float mat[][4], float loc[3], float quat[4], float size[3]) { float rmat[3][3], smat[3][3], tmat[3][3]; @@ -5075,8 +4738,6 @@ void LocQuatSizeToMat4(float mat[4][4], float loc[3], float quat[4], float size[ mat[3][2] = loc[2]; } -/********************************************************/ - /* Tangents */ /* For normal map tangents we need to detect uv boundaries, and only average diff --git a/source/blender/blenlib/intern/bpath.c b/source/blender/blenlib/intern/bpath.c index cadf8d2bdd1..6c89afe7173 100644 --- a/source/blender/blenlib/intern/bpath.c +++ b/source/blender/blenlib/intern/bpath.c @@ -26,24 +26,6 @@ * ***** END GPL LICENSE BLOCK ***** */ -#include <sys/stat.h> -#include <sys/types.h> - -#include <fcntl.h> -#include <stdio.h> -#include <string.h> -#include <stdlib.h> -#include <string.h> - -/* path/file handeling stuff */ -#ifndef WIN32 - #include <dirent.h> - #include <unistd.h> -#else - #include <io.h> - #include "BLI_winstuff.h" -#endif - #include "MEM_guardedalloc.h" #include "DNA_ID.h" /* Library */ @@ -71,7 +53,23 @@ //XXX define below from BSE_sequence.h - otherwise potentially odd behaviour #define SEQ_HAS_PATH(seq) (seq->type==SEQ_MOVIE || seq->type==SEQ_IMAGE) +/* path/file handeling stuff */ +#ifndef WIN32 + #include <dirent.h> + #include <unistd.h> +#else + #include "BLI_winstuff.h" + #include <io.h> +#endif +#include <sys/stat.h> +#include <sys/types.h> + +#include <fcntl.h> +#include <stdio.h> +#include <string.h> +#include <stdlib.h> +#include <string.h> #define FILE_MAX 240 diff --git a/source/blender/blenlib/intern/fileops.c b/source/blender/blenlib/intern/fileops.c index e7dc9b0eb1f..0228032df01 100644 --- a/source/blender/blenlib/intern/fileops.c +++ b/source/blender/blenlib/intern/fileops.c @@ -31,29 +31,27 @@ #include <stdio.h> #include <stdlib.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <fcntl.h> - -#include <errno.h> - #include "zlib.h" #ifdef WIN32 -#include <io.h> #include "BLI_winstuff.h" +#include <io.h> #else #include <unistd.h> // for read close #include <sys/param.h> #endif - #include "BLI_blenlib.h" #include "BLI_storage.h" #include "BLI_fileops.h" #include "BLI_callbacks.h" +#include <sys/types.h> +#include <sys/stat.h> +#include <fcntl.h> + #include "BKE_utildefines.h" +#include <errno.h> #include "BLO_sys_types.h" // for intptr_t support diff --git a/source/blender/blenlib/intern/freetypefont.c b/source/blender/blenlib/intern/freetypefont.c index 985700efda1..bde4b561f26 100644 --- a/source/blender/blenlib/intern/freetypefont.c +++ b/source/blender/blenlib/intern/freetypefont.c @@ -146,10 +146,9 @@ void freetypechar_to_vchar(FT_Face face, FT_ULong charcode, VFontData *vfd) bezt = (BezTriple*)MEM_callocN((onpoints[j])* sizeof(BezTriple),"objfnt_bezt") ; BLI_addtail(&che->nurbsbase, nu); - nu->type= CU_BEZIER; + nu->type= CU_BEZIER+CU_2D; nu->pntsu = onpoints[j]; nu->resolu= 8; - nu->flag= CU_2D; nu->flagu= CU_CYCLIC; nu->bezt = bezt; diff --git a/source/blender/blenlib/intern/matrixops.c b/source/blender/blenlib/intern/matrixops.c new file mode 100644 index 00000000000..0f9fc65f016 --- /dev/null +++ b/source/blender/blenlib/intern/matrixops.c @@ -0,0 +1,438 @@ +/* + * + * Some matrix operations. + * + * Always use + * - vector with x components : float x[3], int x[3], etc + * + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +/* ------------------------------------------------------------------------- */ +#include <string.h> +#include "MTC_matrixops.h" +#include "MTC_vectorops.h" +/* ------------------------------------------------------------------------- */ + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +#if defined(__sun__) || defined( __sun ) || defined (__sparc) || defined (__sparc__) +#include <strings.h> +#endif + +#define ABS(x) ((x) < 0 ? -(x) : (x)) +#define SWAP(type, a, b) { type sw_ap; sw_ap=(a); (a)=(b); (b)=sw_ap; } + +void MTC_Mat4CpyMat4(float m1[][4], float m2[][4]) +{ + memcpy(m1, m2, 4*4*sizeof(float)); +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4MulSerie(float answ[][4], + float m1[][4], float m2[][4], float m3[][4], + float m4[][4], float m5[][4], float m6[][4], + float m7[][4], float m8[][4]) +{ + float temp[4][4]; + + if(m1==0 || m2==0) return; + + MTC_Mat4MulMat4(answ, m2, m1); + if(m3) { + MTC_Mat4MulMat4(temp, m3, answ); + if(m4) { + MTC_Mat4MulMat4(answ, m4, temp); + if(m5) { + MTC_Mat4MulMat4(temp, m5, answ); + if(m6) { + MTC_Mat4MulMat4(answ, m6, temp); + if(m7) { + MTC_Mat4MulMat4(temp, m7, answ); + if(m8) { + MTC_Mat4MulMat4(answ, m8, temp); + } + else MTC_Mat4CpyMat4(answ, temp); + } + } + else MTC_Mat4CpyMat4(answ, temp); + } + } + else MTC_Mat4CpyMat4(answ, temp); + } +} + +/* ------------------------------------------------------------------------- */ +void MTC_Mat4MulMat4(float m1[][4], float m2[][4], float m3[][4]) +{ + /* matrix product: c[j][k] = a[j][i].b[i][k] */ + + m1[0][0] = m2[0][0]*m3[0][0] + m2[0][1]*m3[1][0] + m2[0][2]*m3[2][0] + m2[0][3]*m3[3][0]; + m1[0][1] = m2[0][0]*m3[0][1] + m2[0][1]*m3[1][1] + m2[0][2]*m3[2][1] + m2[0][3]*m3[3][1]; + m1[0][2] = m2[0][0]*m3[0][2] + m2[0][1]*m3[1][2] + m2[0][2]*m3[2][2] + m2[0][3]*m3[3][2]; + m1[0][3] = m2[0][0]*m3[0][3] + m2[0][1]*m3[1][3] + m2[0][2]*m3[2][3] + m2[0][3]*m3[3][3]; + + m1[1][0] = m2[1][0]*m3[0][0] + m2[1][1]*m3[1][0] + m2[1][2]*m3[2][0] + m2[1][3]*m3[3][0]; + m1[1][1] = m2[1][0]*m3[0][1] + m2[1][1]*m3[1][1] + m2[1][2]*m3[2][1] + m2[1][3]*m3[3][1]; + m1[1][2] = m2[1][0]*m3[0][2] + m2[1][1]*m3[1][2] + m2[1][2]*m3[2][2] + m2[1][3]*m3[3][2]; + m1[1][3] = m2[1][0]*m3[0][3] + m2[1][1]*m3[1][3] + m2[1][2]*m3[2][3] + m2[1][3]*m3[3][3]; + + m1[2][0] = m2[2][0]*m3[0][0] + m2[2][1]*m3[1][0] + m2[2][2]*m3[2][0] + m2[2][3]*m3[3][0]; + m1[2][1] = m2[2][0]*m3[0][1] + m2[2][1]*m3[1][1] + m2[2][2]*m3[2][1] + m2[2][3]*m3[3][1]; + m1[2][2] = m2[2][0]*m3[0][2] + m2[2][1]*m3[1][2] + m2[2][2]*m3[2][2] + m2[2][3]*m3[3][2]; + m1[2][3] = m2[2][0]*m3[0][3] + m2[2][1]*m3[1][3] + m2[2][2]*m3[2][3] + m2[2][3]*m3[3][3]; + + m1[3][0] = m2[3][0]*m3[0][0] + m2[3][1]*m3[1][0] + m2[3][2]*m3[2][0] + m2[3][3]*m3[3][0]; + m1[3][1] = m2[3][0]*m3[0][1] + m2[3][1]*m3[1][1] + m2[3][2]*m3[2][1] + m2[3][3]*m3[3][1]; + m1[3][2] = m2[3][0]*m3[0][2] + m2[3][1]*m3[1][2] + m2[3][2]*m3[2][2] + m2[3][3]*m3[3][2]; + m1[3][3] = m2[3][0]*m3[0][3] + m2[3][1]*m3[1][3] + m2[3][2]*m3[2][3] + m2[3][3]*m3[3][3]; + +} +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4MulVecfl(float mat[][4], float *vec) +{ + float x,y; + + x=vec[0]; + y=vec[1]; + vec[0]=x*mat[0][0] + y*mat[1][0] + mat[2][0]*vec[2] + mat[3][0]; + vec[1]=x*mat[0][1] + y*mat[1][1] + mat[2][1]*vec[2] + mat[3][1]; + vec[2]=x*mat[0][2] + y*mat[1][2] + mat[2][2]*vec[2] + mat[3][2]; +} + +/* ------------------------------------------------------------------------- */ +void MTC_Mat3MulVecfl(float mat[][3], float *vec) +{ + float x,y; + + x=vec[0]; + y=vec[1]; + vec[0]= x*mat[0][0] + y*mat[1][0] + mat[2][0]*vec[2]; + vec[1]= x*mat[0][1] + y*mat[1][1] + mat[2][1]*vec[2]; + vec[2]= x*mat[0][2] + y*mat[1][2] + mat[2][2]*vec[2]; +} + +/* ------------------------------------------------------------------------- */ + +int MTC_Mat4Invert(float inverse[][4], float mat[][4]) +{ + int i, j, k; + double temp; + float tempmat[4][4]; + float max; + int maxj; + + /* Set inverse to identity */ + for (i=0; i<4; i++) + for (j=0; j<4; j++) + inverse[i][j] = 0; + for (i=0; i<4; i++) + inverse[i][i] = 1; + + /* Copy original matrix so we don't mess it up */ + for(i = 0; i < 4; i++) + for(j = 0; j <4; j++) + tempmat[i][j] = mat[i][j]; + + for(i = 0; i < 4; i++) { + /* Look for row with max pivot */ + max = ABS(tempmat[i][i]); + maxj = i; + for(j = i + 1; j < 4; j++) { + if(ABS(tempmat[j][i]) > max) { + max = ABS(tempmat[j][i]); + maxj = j; + } + } + /* Swap rows if necessary */ + if (maxj != i) { + for( k = 0; k < 4; k++) { + SWAP(float, tempmat[i][k], tempmat[maxj][k]); + SWAP(float, inverse[i][k], inverse[maxj][k]); + } + } + + temp = tempmat[i][i]; + if (temp == 0) + return 0; /* No non-zero pivot */ + for(k = 0; k < 4; k++) { + tempmat[i][k] /= temp; + inverse[i][k] /= temp; + } + for(j = 0; j < 4; j++) { + if(j != i) { + temp = tempmat[j][i]; + for(k = 0; k < 4; k++) { + tempmat[j][k] -= tempmat[i][k]*temp; + inverse[j][k] -= inverse[i][k]*temp; + } + } + } + } + return 1; +} + +/* ------------------------------------------------------------------------- */ +void MTC_Mat3CpyMat4(float m1[][3], float m2[][4]) +{ + + m1[0][0]= m2[0][0]; + m1[0][1]= m2[0][1]; + m1[0][2]= m2[0][2]; + + m1[1][0]= m2[1][0]; + m1[1][1]= m2[1][1]; + m1[1][2]= m2[1][2]; + + m1[2][0]= m2[2][0]; + m1[2][1]= m2[2][1]; + m1[2][2]= m2[2][2]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat3CpyMat3(float m1[][3], float m2[][3]) +{ + memcpy(m1, m2, 3*3*sizeof(float)); +} + +/* ------------------------------------------------------------------------- */ +/* void Mat3MulMat3(float m1[][3], float m3[][3], float m2[][3]) */ +void MTC_Mat3MulMat3(float m1[][3], float m3[][3], float m2[][3]) +{ + /* be careful about this rewrite... */ + /* m1[i][j] = m2[i][k]*m3[k][j], args are flipped! */ + m1[0][0]= m2[0][0]*m3[0][0] + m2[0][1]*m3[1][0] + m2[0][2]*m3[2][0]; + m1[0][1]= m2[0][0]*m3[0][1] + m2[0][1]*m3[1][1] + m2[0][2]*m3[2][1]; + m1[0][2]= m2[0][0]*m3[0][2] + m2[0][1]*m3[1][2] + m2[0][2]*m3[2][2]; + + m1[1][0]= m2[1][0]*m3[0][0] + m2[1][1]*m3[1][0] + m2[1][2]*m3[2][0]; + m1[1][1]= m2[1][0]*m3[0][1] + m2[1][1]*m3[1][1] + m2[1][2]*m3[2][1]; + m1[1][2]= m2[1][0]*m3[0][2] + m2[1][1]*m3[1][2] + m2[1][2]*m3[2][2]; + + m1[2][0]= m2[2][0]*m3[0][0] + m2[2][1]*m3[1][0] + m2[2][2]*m3[2][0]; + m1[2][1]= m2[2][0]*m3[0][1] + m2[2][1]*m3[1][1] + m2[2][2]*m3[2][1]; + m1[2][2]= m2[2][0]*m3[0][2] + m2[2][1]*m3[1][2] + m2[2][2]*m3[2][2]; + +/* m1[0]= m2[0]*m3[0] + m2[1]*m3[3] + m2[2]*m3[6]; */ +/* m1[1]= m2[0]*m3[1] + m2[1]*m3[4] + m2[2]*m3[7]; */ +/* m1[2]= m2[0]*m3[2] + m2[1]*m3[5] + m2[2]*m3[8]; */ +/* m1+=3; */ +/* m2+=3; */ +/* m1[0]= m2[0]*m3[0] + m2[1]*m3[3] + m2[2]*m3[6]; */ +/* m1[1]= m2[0]*m3[1] + m2[1]*m3[4] + m2[2]*m3[7]; */ +/* m1[2]= m2[0]*m3[2] + m2[1]*m3[5] + m2[2]*m3[8]; */ +/* m1+=3; */ +/* m2+=3; */ +/* m1[0]= m2[0]*m3[0] + m2[1]*m3[3] + m2[2]*m3[6]; */ +/* m1[1]= m2[0]*m3[1] + m2[1]*m3[4] + m2[2]*m3[7]; */ +/* m1[2]= m2[0]*m3[2] + m2[1]*m3[5] + m2[2]*m3[8]; */ +} /* end of void Mat3MulMat3(float m1[][3], float m3[][3], float m2[][3]) */ + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4Ortho(float mat[][4]) +{ + float len; + + len= MTC_normalize3DF(mat[0]); + if(len!=0.0) mat[0][3]/= len; + len= MTC_normalize3DF(mat[1]); + if(len!=0.0) mat[1][3]/= len; + len= MTC_normalize3DF(mat[2]); + if(len!=0.0) mat[2][3]/= len; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4Mul3Vecfl(float mat[][4], float *vec) +{ + float x,y; + /* vec = mat^T dot vec !!! or vec a row, then vec = vec dot mat*/ + + x= vec[0]; + y= vec[1]; + vec[0]= x*mat[0][0] + y*mat[1][0] + mat[2][0]*vec[2]; + vec[1]= x*mat[0][1] + y*mat[1][1] + mat[2][1]*vec[2]; + vec[2]= x*mat[0][2] + y*mat[1][2] + mat[2][2]*vec[2]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4One(float m[][4]) +{ + + m[0][0]= m[1][1]= m[2][2]= m[3][3]= 1.0; + m[0][1]= m[0][2]= m[0][3]= 0.0; + m[1][0]= m[1][2]= m[1][3]= 0.0; + m[2][0]= m[2][1]= m[2][3]= 0.0; + m[3][0]= m[3][1]= m[3][2]= 0.0; +} + + +/* ------------------------------------------------------------------------- */ +/* Result is a 3-vector!*/ +void MTC_Mat3MulVecd(float mat[][3], double *vec) +{ + double x,y; + + /* vec = mat^T dot vec !!! or vec a row, then vec = vec dot mat*/ + x=vec[0]; + y=vec[1]; + vec[0]= x * mat[0][0] + y * mat[1][0] + mat[2][0] * vec[2]; + vec[1]= x * mat[0][1] + y * mat[1][1] + mat[2][1] * vec[2]; + vec[2]= x * mat[0][2] + y * mat[1][2] + mat[2][2] * vec[2]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat3Inv(float m1[][3], float m2[][3]) +{ + short a,b; + float det; + + /* first adjoint */ + MTC_Mat3Adj(m1,m2); + + /* then determinant old mat! */ + det= m2[0][0]* (m2[1][1]*m2[2][2] - m2[1][2]*m2[2][1]) + -m2[1][0]* (m2[0][1]*m2[2][2] - m2[0][2]*m2[2][1]) + +m2[2][0]* (m2[0][1]*m2[1][2] - m2[0][2]*m2[1][1]); + + if(det==0) det=1; + det= 1/det; + for(a=0;a<3;a++) { + for(b=0;b<3;b++) { + m1[a][b]*=det; + } + } +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat3Adj(float m1[][3], float m[][3]) +{ + m1[0][0]=m[1][1]*m[2][2]-m[1][2]*m[2][1]; + m1[0][1]= -m[0][1]*m[2][2]+m[0][2]*m[2][1]; + m1[0][2]=m[0][1]*m[1][2]-m[0][2]*m[1][1]; + + m1[1][0]= -m[1][0]*m[2][2]+m[1][2]*m[2][0]; + m1[1][1]=m[0][0]*m[2][2]-m[0][2]*m[2][0]; + m1[1][2]= -m[0][0]*m[1][2]+m[0][2]*m[1][0]; + + m1[2][0]=m[1][0]*m[2][1]-m[1][1]*m[2][0]; + m1[2][1]= -m[0][0]*m[2][1]+m[0][1]*m[2][0]; + m1[2][2]=m[0][0]*m[1][1]-m[0][1]*m[1][0]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat3One(float m[][3]) +{ + + m[0][0]= m[1][1]= m[2][2]= 1.0; + m[0][1]= m[0][2]= 0.0; + m[1][0]= m[1][2]= 0.0; + m[2][0]= m[2][1]= 0.0; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4SwapMat4(float m1[][4], float m2[][4]) +{ + float t; + int i, j; + + for(i = 0; i < 4; i++) { + for (j = 0; j < 4; j++) { + t = m1[i][j]; + m1[i][j] = m2[i][j]; + m2[i][j] = t; + } + } +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4MulVec4fl(float mat[][4], float *vec) +{ + float x,y,z; + + x = vec[0]; + y = vec[1]; + z = vec[2]; + vec[0] = x*mat[0][0] + y*mat[1][0] + z*mat[2][0] + mat[3][0]*vec[3]; + vec[1] = x*mat[0][1] + y*mat[1][1] + z*mat[2][1] + mat[3][1]*vec[3]; + vec[2] = x*mat[0][2] + y*mat[1][2] + z*mat[2][2] + mat[3][2]*vec[3]; + vec[3] = x*mat[0][3] + y*mat[1][3] + z*mat[2][3] + mat[3][3]*vec[3]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4CpyMat3nc(float m1[][4], float m2[][3]) /* no clear */ +{ + m1[0][0]= m2[0][0]; + m1[0][1]= m2[0][1]; + m1[0][2]= m2[0][2]; + + m1[1][0]= m2[1][0]; + m1[1][1]= m2[1][1]; + m1[1][2]= m2[1][2]; + + m1[2][0]= m2[2][0]; + m1[2][1]= m2[2][1]; + m1[2][2]= m2[2][2]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_Mat4MulMat33(float m1[][3], float m2[][4], float m3[][3]) +{ + /* m1_i_j = m2_i_k * m3_k_j ? */ + + m1[0][0] = m2[0][0]*m3[0][0] + m2[0][1]*m3[1][0] + m2[0][2]*m3[2][0]; + m1[0][1] = m2[0][0]*m3[0][1] + m2[0][1]*m3[1][1] + m2[0][2]*m3[2][1]; + m1[0][2] = m2[0][0]*m3[0][2] + m2[0][1]*m3[1][2] + m2[0][2]*m3[2][2]; + + m1[1][0] = m2[1][0]*m3[0][0] + m2[1][1]*m3[1][0] + m2[1][2]*m3[2][0]; + m1[1][1] = m2[1][0]*m3[0][1] + m2[1][1]*m3[1][1] + m2[1][2]*m3[2][1]; + m1[1][2] = m2[1][0]*m3[0][2] + m2[1][1]*m3[1][2] + m2[1][2]*m3[2][2]; + + m1[2][0] = m2[2][0]*m3[0][0] + m2[2][1]*m3[1][0] + m2[2][2]*m3[2][0]; + m1[2][1] = m2[2][0]*m3[0][1] + m2[2][1]*m3[1][1] + m2[2][2]*m3[2][1]; + m1[2][2] = m2[2][0]*m3[0][2] + m2[2][1]*m3[1][2] + m2[2][2]*m3[2][2]; + +} + +/* ------------------------------------------------------------------------- */ + +/* eof */ diff --git a/source/blender/blenlib/intern/storage.c b/source/blender/blenlib/intern/storage.c index cdc5cec705f..e6e37c58805 100644 --- a/source/blender/blenlib/intern/storage.c +++ b/source/blender/blenlib/intern/storage.c @@ -33,6 +33,13 @@ #include <stdio.h> #include <stdlib.h> +#ifdef WIN32 +#include "BLI_winstuff.h" +#include <sys/types.h> +#include <io.h> +#include <direct.h> +#endif + #ifndef WIN32 #include <dirent.h> #endif @@ -63,6 +70,9 @@ #include <fcntl.h> +#if !defined(WIN32) +#include <sys/mtio.h> /* tape comando's */ +#endif #include <string.h> /* strcpy etc.. */ #ifndef WIN32 @@ -75,14 +85,6 @@ #include <malloc.h> #endif -#ifdef WIN32 -#include <sys/types.h> -#include <io.h> -#include <direct.h> -#include "BLI_winstuff.h" -#endif - - /* lib includes */ #include "MEM_guardedalloc.h" diff --git a/source/blender/blenlib/intern/threads.c b/source/blender/blenlib/intern/threads.c index ed3e07b7f7e..2812f17d58f 100644 --- a/source/blender/blenlib/intern/threads.c +++ b/source/blender/blenlib/intern/threads.c @@ -142,10 +142,10 @@ void BLI_init_threads(ListBase *threadbase, void *(*do_thread)(void *), int tot) tslot->do_thread= do_thread; tslot->avail= 1; } - - MEM_set_lock_callback(BLI_lock_malloc_thread, BLI_unlock_malloc_thread); - thread_levels++; } + + MEM_set_lock_callback(BLI_lock_malloc_thread, BLI_unlock_malloc_thread); + thread_levels++; } /* amount of available threads */ @@ -235,21 +235,18 @@ void BLI_end_threads(ListBase *threadbase) { ThreadSlot *tslot; - /* only needed if there's actually some stuff to end - * this way we don't end up decrementing thread_levels on an empty threadbase - * */ - if (threadbase && threadbase->first != NULL) { + if (threadbase) { for(tslot= threadbase->first; tslot; tslot= tslot->next) { if(tslot->avail==0) { pthread_join(tslot->pthread, NULL); } } BLI_freelistN(threadbase); - - thread_levels--; - if(thread_levels==0) - MEM_set_lock_callback(NULL, NULL); } + + thread_levels--; + if(thread_levels==0) + MEM_set_lock_callback(NULL, NULL); } void BLI_lock_thread(int type) diff --git a/source/blender/blenlib/intern/util.c b/source/blender/blenlib/intern/util.c index c7bb7a54457..3c441a81d6b 100644 --- a/source/blender/blenlib/intern/util.c +++ b/source/blender/blenlib/intern/util.c @@ -54,8 +54,6 @@ #include "BKE_utildefines.h" - - #ifdef HAVE_CONFIG_H #include <config.h> #endif @@ -77,6 +75,11 @@ #include "BLI_winstuff.h" +/* for duplicate_defgroup */ +#if !(defined vsnprintf) +#define vsnprintf _vsnprintf +#endif + #endif diff --git a/source/blender/blenlib/intern/vectorops.c b/source/blender/blenlib/intern/vectorops.c new file mode 100644 index 00000000000..3bff5235cfd --- /dev/null +++ b/source/blender/blenlib/intern/vectorops.c @@ -0,0 +1,166 @@ +/* + * + * Some vector operations. + * + * Always use + * - vector with x components : float x[3], int x[3], etc + * + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL LICENSE BLOCK ***** + */ + +/* ------------------------------------------------------------------------- */ +/* General format: op(a, b, c): a = b op c */ +/* Copying is done cp <from, to> */ +/* ------------------------------------------------------------------------- */ + +#include "MTC_vectorops.h" +#include <math.h> + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +void MTC_diff3Int(int v1[3], int v2[3], int v3[3]) +{ + v1[0] = v2[0] - v3[0]; + v1[1] = v2[1] - v3[1]; + v1[2] = v2[2] - v3[2]; +} + +/* ------------------------------------------------------------------------- */ +void MTC_diff3Float(float v1[3], float v2[3], float v3[3]) +{ + v1[0] = v2[0] - v3[0]; + v1[1] = v2[1] - v3[1]; + v1[2] = v2[2] - v3[2]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_cross3Int(int v1[3], int v2[3], int v3[3]) +{ + v1[0] = v2[1]*v3[2] - v2[2]*v3[1]; + v1[1] = v2[2]*v3[0] - v2[0]*v3[2]; + v1[2] = v2[0]*v3[1] - v2[1]*v3[0]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_cross3Float(float v1[3], float v2[3], float v3[3]) +{ + v1[0] = v2[1]*v3[2] - v2[2]*v3[1]; + v1[1] = v2[2]*v3[0] - v2[0]*v3[2]; + v1[2] = v2[0]*v3[1] - v2[1]*v3[0]; +} +/* ------------------------------------------------------------------------- */ + +void MTC_cross3Double(double v1[3], double v2[3], double v3[3]) +{ + v1[0] = v2[1]*v3[2] - v2[2]*v3[1]; + v1[1] = v2[2]*v3[0] - v2[0]*v3[2]; + v1[2] = v2[0]*v3[1] - v2[1]*v3[0]; +} + +/* ------------------------------------------------------------------------- */ + +int MTC_dot3Int(int v1[3], int v2[3]) +{ + return (v1[0]*v2[0] + v1[1]*v2[1] + v1[2]*v2[2]); +} + +/* ------------------------------------------------------------------------- */ + +float MTC_dot3Float(float v1[3], float v2[3]) +{ + return (v1[0]*v2[0] + v1[1]*v2[1] + v1[2]*v2[2]); +} + +/* ------------------------------------------------------------------------- */ + +void MTC_cp3Float(float v1[3], float v2[3]) +{ + v2[0] = v1[0]; + v2[1] = v1[1]; + v2[2] = v1[2]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_cp3FloatInv(float v1[3], float v2[3]) +{ + v2[0] = -v1[0]; + v2[1] = -v1[1]; + v2[2] = -v1[2]; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_swapInt(int *i1, int *i2) +{ + int swap; + swap = *i1; + *i1 = *i2; + *i2 = swap; +} + +/* ------------------------------------------------------------------------- */ + +void MTC_diff3DFF(double v1[3], float v2[3], float v3[3]) +{ + v1[0] = v2[0] - v3[0]; + v1[1] = v2[1] - v3[1]; + v1[2] = v2[2] - v3[2]; +} + +/* ------------------------------------------------------------------------- */ +float MTC_normalize3DF(float n[3]) +{ + float d; + + d= n[0]*n[0]+n[1]*n[1]+n[2]*n[2]; + /* FLT_EPSILON is too large! A larger value causes normalize errors in */ + /* a scaled down utah teapot */ + if(d>0.0000000000001) { + + /* d= sqrt(d); This _should_ be sqrt, but internally it's a double*/ + /* anyway. This is safe. */ + d = sqrt(d); + + n[0]/=d; + n[1]/=d; + n[2]/=d; + } else { + n[0]=n[1]=n[2]= 0.0; + d= 0.0; + } + return d; +} + +/* ------------------------------------------------------------------------- */ + +/* eof */ diff --git a/source/blender/blenlib/intern/voxel.c b/source/blender/blenlib/intern/voxel.c deleted file mode 100644 index 7dad854af3a..00000000000 --- a/source/blender/blenlib/intern/voxel.c +++ /dev/null @@ -1,198 +0,0 @@ -/** - * - * ***** BEGIN GPL LICENSE BLOCK ***** - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License - * as published by the Free Software Foundation; either version 2 - * of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software Foundation, - * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. - * - * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. - * All rights reserved. - * - * The Original Code is: all of this file. - * - * Contributor(s): Matt Ebb, Raul Fernandez Hernandez (Farsthary). - * - * ***** END GPL LICENSE BLOCK ***** - */ -#include <math.h> - -#include "BLI_voxel.h" - -#include "BKE_utildefines.h" - - -#if defined( _MSC_VER ) && !defined( __cplusplus ) -# define inline __inline -#endif // defined( _MSC_VER ) && !defined( __cplusplus ) - -static inline float D(float *data, int *res, int x, int y, int z) -{ - CLAMP(x, 0, res[0]-1); - CLAMP(y, 0, res[1]-1); - CLAMP(z, 0, res[2]-1); - return data[ V_I(x, y, z, res) ]; -} - -/* *** nearest neighbour *** */ -/* input coordinates must be in bounding box 0.0 - 1.0 */ -float voxel_sample_nearest(float *data, int *res, float *co) -{ - int xi, yi, zi; - - xi = co[0] * res[0]; - yi = co[1] * res[1]; - zi = co[2] * res[2]; - - return D(data, res, xi, yi, zi); -} - -// returns highest integer <= x as integer (slightly faster than floor()) -inline int FLOORI(float x) -{ - const int r = (int)x; - return ((x >= 0.f) || (float)r == x) ? r : (r - 1); -} - -// clamp function, cannot use the CLAMPIS macro, it sometimes returns unwanted results apparently related to gcc optimization flag -fstrict-overflow which is enabled at -O2 -// this causes the test (x + 2) < 0 with int x == 2147483647 to return false (x being an integer, x + 2 should wrap around to -2147483647 so the test < 0 should return true, which it doesn't) -inline int _clamp(int a, int b, int c) -{ - return (a < b) ? b : ((a > c) ? c : a); -} - -float voxel_sample_trilinear(float *data, int *res, float *co) -{ - if (data) { - - const float xf = co[0] * res[0] - 0.5f; - const float yf = co[1] * res[1] - 0.5f; - const float zf = co[2] * res[2] - 0.5f; - - const int x = FLOORI(xf), y = FLOORI(yf), z = FLOORI(zf); - - const int xc[2] = {_clamp(x, 0, res[0] - 1), _clamp(x + 1, 0, res[0] - 1)}; - const int yc[2] = {res[0] * _clamp(y, 0, res[1] - 1), res[0] * _clamp(y + 1, 0, res[1] - 1)}; - const int zc[2] = {res[0] * res[1] * _clamp(z, 0, res[2] - 1), res[0] * res[1] * _clamp(z + 1, 0, res[2] - 1)}; - - const float dx = xf - (float)x; - const float dy = yf - (float)y; - const float dz = zf - (float)z; - - const float u[2] = {1.f - dx, dx}; - const float v[2] = {1.f - dy, dy}; - const float w[2] = {1.f - dz, dz}; - - return w[0] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[0]] + u[1] * data[xc[1] + yc[0] + zc[0]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[0]] + u[1] * data[xc[1] + yc[1] + zc[0]] ) ) - + w[1] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[1]] + u[1] * data[xc[1] + yc[0] + zc[1]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[1]] + u[1] * data[xc[1] + yc[1] + zc[1]] ) ); - - } - return 0.f; -} - - -float voxel_sample_triquadratic(float *data, int *res, float *co) -{ - if (data) { - - const float xf = co[0] * res[0], yf = co[1] * res[1], zf = co[2] * res[2]; - const int x = FLOORI(xf), y = FLOORI(yf), z = FLOORI(zf); - - const int xc[3] = {_clamp(x - 1, 0, res[0] - 1), _clamp(x, 0, res[0] - 1), _clamp(x + 1, 0, res[0] - 1)}; - const int yc[3] = {res[0] * _clamp(y - 1, 0, res[1] - 1), res[0] * _clamp(y, 0, res[1] - 1), res[0] * _clamp(y + 1, 0, res[1] - 1)}; - const int zc[3] = {res[0] * res[1] * _clamp(z - 1, 0, res[2] - 1), res[0] * res[1] * _clamp(z, 0, res[2] - 1), res[0] * res[1] * _clamp(z + 1, 0, res[2] - 1)}; - - const float dx = xf - (float)x, dy = yf - (float)y, dz = zf - (float)z; - const float u[3] = {dx*(0.5f*dx - 1.f) + 0.5f, dx*(1.f - dx) + 0.5f, 0.5f*dx*dx}; - const float v[3] = {dy*(0.5f*dy - 1.f) + 0.5f, dy*(1.f - dy) + 0.5f, 0.5f*dy*dy}; - const float w[3] = {dz*(0.5f*dz - 1.f) + 0.5f, dz*(1.f - dz) + 0.5f, 0.5f*dz*dz}; - - return w[0] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[0]] + u[1] * data[xc[1] + yc[0] + zc[0]] + u[2] * data[xc[2] + yc[0] + zc[0]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[0]] + u[1] * data[xc[1] + yc[1] + zc[0]] + u[2] * data[xc[2] + yc[1] + zc[0]] ) - + v[2] * ( u[0] * data[xc[0] + yc[2] + zc[0]] + u[1] * data[xc[1] + yc[2] + zc[0]] + u[2] * data[xc[2] + yc[2] + zc[0]] ) ) - + w[1] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[1]] + u[1] * data[xc[1] + yc[0] + zc[1]] + u[2] * data[xc[2] + yc[0] + zc[1]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[1]] + u[1] * data[xc[1] + yc[1] + zc[1]] + u[2] * data[xc[2] + yc[1] + zc[1]] ) - + v[2] * ( u[0] * data[xc[0] + yc[2] + zc[1]] + u[1] * data[xc[1] + yc[2] + zc[1]] + u[2] * data[xc[2] + yc[2] + zc[1]] ) ) - + w[2] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[2]] + u[1] * data[xc[1] + yc[0] + zc[2]] + u[2] * data[xc[2] + yc[0] + zc[2]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[2]] + u[1] * data[xc[1] + yc[1] + zc[2]] + u[2] * data[xc[2] + yc[1] + zc[2]] ) - + v[2] * ( u[0] * data[xc[0] + yc[2] + zc[2]] + u[1] * data[xc[1] + yc[2] + zc[2]] + u[2] * data[xc[2] + yc[2] + zc[2]] ) ); - -} - return 0.f; -} - -float voxel_sample_tricubic(float *data, int *res, float *co, int bspline) -{ - if (data) { - - const float xf = co[0] * res[0] - 0.5f, yf = co[1] * res[1] - 0.5f, zf = co[2] * res[2] - 0.5f; - const int x = FLOORI(xf), y = FLOORI(yf), z = FLOORI(zf); - - const int xc[4] = {_clamp(x - 1, 0, res[0] - 1), _clamp(x, 0, res[0] - 1), _clamp(x + 1, 0, res[0] - 1), _clamp(x + 2, 0, res[0] - 1)}; - const int yc[4] = {res[0] * _clamp(y - 1, 0, res[1] - 1), res[0] * _clamp(y, 0, res[1] - 1), res[0] * _clamp(y + 1, 0, res[1] - 1), res[0] * _clamp(y + 2, 0, res[1] - 1)}; - const int zc[4] = {res[0] * res[1] * _clamp(z - 1, 0, res[2] - 1), res[0] * res[1] * _clamp(z, 0, res[2] - 1), res[0] * res[1] * _clamp(z + 1, 0, res[2] - 1), res[0] * res[1] * _clamp(z + 2, 0, res[2] - 1)}; - - const float dx = xf - (float)x, dy = yf - (float)y, dz = zf - (float)z; - - float u[4], v[4], w[4]; - if (bspline) { // B-Spline - u[0] = (((-1.f/6.f)*dx + 0.5f)*dx - 0.5f)*dx + (1.f/6.f); - u[1] = (( 0.5f*dx - 1.f )*dx )*dx + (2.f/3.f); - u[2] = (( -0.5f*dx + 0.5f)*dx + 0.5f)*dx + (1.f/6.f); - u[3] = ( 1.f/6.f)*dx*dx*dx; - v[0] = (((-1.f/6.f)*dy + 0.5f)*dy - 0.5f)*dy + (1.f/6.f); - v[1] = (( 0.5f*dy - 1.f )*dy )*dy + (2.f/3.f); - v[2] = (( -0.5f*dy + 0.5f)*dy + 0.5f)*dy + (1.f/6.f); - v[3] = ( 1.f/6.f)*dy*dy*dy; - w[0] = (((-1.f/6.f)*dz + 0.5f)*dz - 0.5f)*dz + (1.f/6.f); - w[1] = (( 0.5f*dz - 1.f )*dz )*dz + (2.f/3.f); - w[2] = (( -0.5f*dz + 0.5f)*dz + 0.5f)*dz + (1.f/6.f); - w[3] = ( 1.f/6.f)*dz*dz*dz; - } - else { // Catmull-Rom - u[0] = ((-0.5f*dx + 1.0f)*dx - 0.5f)*dx; - u[1] = (( 1.5f*dx - 2.5f)*dx )*dx + 1.0f; - u[2] = ((-1.5f*dx + 2.0f)*dx + 0.5f)*dx; - u[3] = (( 0.5f*dx - 0.5f)*dx )*dx; - v[0] = ((-0.5f*dy + 1.0f)*dy - 0.5f)*dy; - v[1] = (( 1.5f*dy - 2.5f)*dy )*dy + 1.0f; - v[2] = ((-1.5f*dy + 2.0f)*dy + 0.5f)*dy; - v[3] = (( 0.5f*dy - 0.5f)*dy )*dy; - w[0] = ((-0.5f*dz + 1.0f)*dz - 0.5f)*dz; - w[1] = (( 1.5f*dz - 2.5f)*dz )*dz + 1.0f; - w[2] = ((-1.5f*dz + 2.0f)*dz + 0.5f)*dz; - w[3] = (( 0.5f*dz - 0.5f)*dz )*dz; - } - - return w[0] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[0]] + u[1] * data[xc[1] + yc[0] + zc[0]] + u[2] * data[xc[2] + yc[0] + zc[0]] + u[3] * data[xc[3] + yc[0] + zc[0]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[0]] + u[1] * data[xc[1] + yc[1] + zc[0]] + u[2] * data[xc[2] + yc[1] + zc[0]] + u[3] * data[xc[3] + yc[1] + zc[0]] ) - + v[2] * ( u[0] * data[xc[0] + yc[2] + zc[0]] + u[1] * data[xc[1] + yc[2] + zc[0]] + u[2] * data[xc[2] + yc[2] + zc[0]] + u[3] * data[xc[3] + yc[2] + zc[0]] ) - + v[3] * ( u[0] * data[xc[0] + yc[3] + zc[0]] + u[1] * data[xc[1] + yc[3] + zc[0]] + u[2] * data[xc[2] + yc[3] + zc[0]] + u[3] * data[xc[3] + yc[3] + zc[0]] ) ) - + w[1] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[1]] + u[1] * data[xc[1] + yc[0] + zc[1]] + u[2] * data[xc[2] + yc[0] + zc[1]] + u[3] * data[xc[3] + yc[0] + zc[1]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[1]] + u[1] * data[xc[1] + yc[1] + zc[1]] + u[2] * data[xc[2] + yc[1] + zc[1]] + u[3] * data[xc[3] + yc[1] + zc[1]] ) - + v[2] * ( u[0] * data[xc[0] + yc[2] + zc[1]] + u[1] * data[xc[1] + yc[2] + zc[1]] + u[2] * data[xc[2] + yc[2] + zc[1]] + u[3] * data[xc[3] + yc[2] + zc[1]] ) - + v[3] * ( u[0] * data[xc[0] + yc[3] + zc[1]] + u[1] * data[xc[1] + yc[3] + zc[1]] + u[2] * data[xc[2] + yc[3] + zc[1]] + u[3] * data[xc[3] + yc[3] + zc[1]] ) ) - + w[2] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[2]] + u[1] * data[xc[1] + yc[0] + zc[2]] + u[2] * data[xc[2] + yc[0] + zc[2]] + u[3] * data[xc[3] + yc[0] + zc[2]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[2]] + u[1] * data[xc[1] + yc[1] + zc[2]] + u[2] * data[xc[2] + yc[1] + zc[2]] + u[3] * data[xc[3] + yc[1] + zc[2]] ) - + v[2] * ( u[0] * data[xc[0] + yc[2] + zc[2]] + u[1] * data[xc[1] + yc[2] + zc[2]] + u[2] * data[xc[2] + yc[2] + zc[2]] + u[3] * data[xc[3] + yc[2] + zc[2]] ) - + v[3] * ( u[0] * data[xc[0] + yc[3] + zc[2]] + u[1] * data[xc[1] + yc[3] + zc[2]] + u[2] * data[xc[2] + yc[3] + zc[2]] + u[3] * data[xc[3] + yc[3] + zc[2]] ) ) - + w[3] * ( v[0] * ( u[0] * data[xc[0] + yc[0] + zc[3]] + u[1] * data[xc[1] + yc[0] + zc[3]] + u[2] * data[xc[2] + yc[0] + zc[3]] + u[3] * data[xc[3] + yc[0] + zc[3]] ) - + v[1] * ( u[0] * data[xc[0] + yc[1] + zc[3]] + u[1] * data[xc[1] + yc[1] + zc[3]] + u[2] * data[xc[2] + yc[1] + zc[3]] + u[3] * data[xc[3] + yc[1] + zc[3]] ) - + v[2] * ( u[0] * data[xc[0] + yc[2] + zc[3]] + u[1] * data[xc[1] + yc[2] + zc[3]] + u[2] * data[xc[2] + yc[2] + zc[3]] + u[3] * data[xc[3] + yc[2] + zc[3]] ) - + v[3] * ( u[0] * data[xc[0] + yc[3] + zc[3]] + u[1] * data[xc[1] + yc[3] + zc[3]] + u[2] * data[xc[2] + yc[3] + zc[3]] + u[3] * data[xc[3] + yc[3] + zc[3]] ) ); - - } - return 0.f; -} |