⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mesh.c

📁 一个用于智能手机的多媒体库适合S60 WinCE的跨平台开发库
💻 C
📖 第 1 页 / 共 5 页
字号:
		if (faces[i]->v_count) TesselateFaceMesh(mesh, faces[i]);		mesh_free(faces[i]);	}	free(faces);	mesh_update_bounds(mesh);	if (!coord2D) gf_mesh_build_aabbtree(mesh);	if (colorRGBA) mesh->flags |= MESH_HAS_ALPHA;	if (gen_tex_coords) mesh_generate_tex_coords(mesh, __texCoords);}void mesh_new_ifs2d(GF_Mesh *mesh, GF_Node *node){	M_IndexedFaceSet2D *ifs2D = (M_IndexedFaceSet2D *)node;	mesh_new_ifs_intern(mesh, ifs2D->coord, &ifs2D->coordIndex,							ifs2D->color, &ifs2D->colorIndex, ifs2D->colorPerVertex,							NULL, NULL, 0, ifs2D->texCoord, &ifs2D->texCoordIndex, 0);	mesh->flags |= MESH_IS_2D;}void mesh_new_ifs(GF_Mesh *mesh, GF_Node *node){	M_IndexedFaceSet *ifs = (M_IndexedFaceSet *)node;	mesh_new_ifs_intern(mesh, ifs->coord, &ifs->coordIndex, ifs->color, &ifs->colorIndex, ifs->colorPerVertex,						ifs->normal, &ifs->normalIndex, ifs->normalPerVertex, ifs->texCoord, &ifs->texCoordIndex, ifs->creaseAngle);	if (ifs->solid) mesh->flags |= MESH_IS_SOLID;	if (!ifs->ccw) mesh->flags |= MESH_IS_CW;}void mesh_new_elevation_grid(GF_Mesh *mesh, GF_Node *node){	u32 i, j, face_count, pt_count, zDimension, xDimension, cur_face, idx, pt_idx;	Bool has_normal, has_txcoord, has_color, smooth_normals;	GF_Mesh **faces;	GF_Vertex vx;	SFVec3f v1, v2, n;	struct face_info *faces_info;	struct pt_info *pts_info;	M_ElevationGrid *eg = (M_ElevationGrid *) node;	M_Normal *norm = (M_Normal *)eg->normal;	M_Color *colorRGB = (M_Color *)eg->color;	X_ColorRGBA *colorRGBA = (X_ColorRGBA *)eg->color;	M_TextureCoordinate *txc = (M_TextureCoordinate *)eg->texCoord;	mesh_reset(mesh);	if (!eg->height.count || (eg->xDimension<2) || (eg->zDimension<2)) return;	has_txcoord = txc ? txc->point.count : 0;	has_normal = norm ? norm->vector.count : 0;	has_color = 0;	if (eg->color) {		if (gf_node_get_tag(eg->color)==TAG_X3D_ColorRGBA) {			colorRGB = NULL;			has_color = colorRGBA->color.count ? 1 : 0;		} else {			colorRGBA = NULL;			has_color = colorRGB->color.count ? 1 : 0;		}	}	face_count = (eg->xDimension-1) * (eg->zDimension-1);	pt_count = eg->xDimension * eg->zDimension;	if (pt_count>eg->height.count) return;	smooth_normals = (!has_normal && (eg->creaseAngle > FIX_EPSILON)) ? 1 : 0;	faces = NULL;	faces_info = NULL;	pts_info = NULL;	/*alloc face & normals tables*/	if (smooth_normals) {		faces = (GF_Mesh **)malloc(sizeof(GF_Mesh *)*face_count);		faces_info = (struct face_info*)malloc(sizeof(struct face_info)*face_count);		memset(faces_info, 0, sizeof(struct face_info)*face_count);		pts_info = (struct pt_info*)malloc(sizeof(struct pt_info)*pt_count);		memset(pts_info, 0, sizeof(struct pt_info)*pt_count);	}	zDimension = (u32) eg->zDimension;	xDimension = (u32) eg->xDimension;	cur_face = 0;	pt_idx = 0;	if (smooth_normals) faces[cur_face] = new_mesh();	for (j=0; j<zDimension-1; j++) {		for (i = 0; i < xDimension-1; i++) {			u32 k, l;			/*get face color*/            if (has_color && !eg->colorPerVertex) {				idx = i + j * (xDimension-1);				MESH_GET_COL(vx.color, idx);            }			/*get face normal*/			if (has_normal && !eg->normalPerVertex) {				idx = i + j * (xDimension-1);				if (idx<norm->vector.count) {					vx.normal = norm->vector.vals[idx];					gf_vec_norm(&vx.normal);				}			}			for (k=0; k<2; k++) {				vx.pos.z = eg->zSpacing * (j+k);				for (l=0; l<2; l++) {					vx.pos.y = eg->height.vals[(i+l) +(j+k)*xDimension];					vx.pos.x = eg->xSpacing * (i+l);					/*get color per vertex*/					if (has_color && eg->colorPerVertex) {						idx = i+l + (j+k) * xDimension;						MESH_GET_COL(vx.color, idx);					}					/*get tex coord*/					if (!has_txcoord) {						vx.texcoords.x = INT2FIX(i+l) / (xDimension - 1);						vx.texcoords.y = INT2FIX(j+k) / (zDimension - 1);					} else {						idx = (i+l) +(j+k)*xDimension;						if (idx<txc->point.count) vx.texcoords = txc->point.vals[idx];					}					/*get normal per vertex*/					if (has_normal && eg->normalPerVertex) {						idx = (i+l) + (j+k) * xDimension;						if (idx<norm->vector.count) {							vx.normal = norm->vector.vals[idx];							gf_vec_norm(&vx.normal);						}					}					/*update face to point and point to face structures*/					if (smooth_normals) {						mesh_set_vertex_vx(faces[cur_face], &vx);						register_point_in_face(&faces_info[cur_face], (i+l) + (j+k)*xDimension);						register_face_in_point(&pts_info[(i+l) + (j+k)*xDimension], cur_face);					} else {						mesh_set_vertex_vx(mesh, &vx);					}				}			}			/*compute face normal*/			if (smooth_normals) {				mesh_set_triangle(faces[cur_face], 0, 2, 3);				mesh_set_triangle(faces[cur_face], 0, 3, 1);				gf_vec_diff(v1, faces[cur_face]->vertices[0].pos, faces[cur_face]->vertices[1].pos);				gf_vec_diff(v2, faces[cur_face]->vertices[3].pos, faces[cur_face]->vertices[1].pos);				faces_info[cur_face].nor = gf_vec_cross(v1, v2);				gf_vec_norm(&faces_info[cur_face].nor);				/*done with face*/				cur_face++;				if (cur_face<face_count) faces[cur_face] = new_mesh();			} else {				mesh_set_triangle(mesh, pt_idx+0, pt_idx+2, pt_idx+3);				mesh_set_triangle(mesh, pt_idx+0, pt_idx+3, pt_idx+1);				if (!has_normal) {					gf_vec_diff(v1, mesh->vertices[pt_idx+0].pos, mesh->vertices[pt_idx+1].pos);					gf_vec_diff(v2, mesh->vertices[pt_idx+3].pos, mesh->vertices[pt_idx+1].pos);					n = gf_vec_cross(v1, v2);					gf_vec_norm(&n);					mesh->vertices[pt_idx+0].normal = n; mesh->vertices[pt_idx+1].normal = n;					mesh->vertices[pt_idx+2].normal = n; mesh->vertices[pt_idx+3].normal = n;				}				pt_idx+=4;			}		}	}	/*generate normals*/	if (smooth_normals) {		Fixed cosCrease;		/*we only support 0->PI, whatever exceeds is smoothest*/		if (eg->creaseAngle>GF_PI) cosCrease = -FIX_ONE;		else cosCrease = gf_cos(eg->creaseAngle);		for (i=0; i<face_count; i++) { for (j=0; j<faces[i]->v_count; j++) {				faces[i]->vertices[j].normal = smooth_face_normals(pts_info, pt_count, faces_info, face_count, 										j, i, cosCrease); 		} } 		if (faces_info) {			for (i=0; i<face_count; i++) if (faces_info[i].idx) free(faces_info[i].idx);			free(faces_info);		}		if (pts_info) {			for (i=0; i<pt_count; i++) if (pts_info[i].faces) free(pts_info[i].faces);			free(pts_info);		}		mesh->flags |= MESH_IS_SMOOTHED;			for (i=0; i<face_count; i++) {			if (faces[i]->v_count) {				u32 init_idx;				GF_Mesh *face = faces[i];				init_idx = mesh->v_count;				/*quads only*/				mesh_set_vertex_vx(mesh, &face->vertices[0]);				mesh_set_vertex_vx(mesh, &face->vertices[1]);				mesh_set_vertex_vx(mesh, &face->vertices[2]);				mesh_set_vertex_vx(mesh, &face->vertices[3]);				mesh_set_triangle(mesh, init_idx, init_idx + 2, init_idx + 3);				mesh_set_triangle(mesh, init_idx, init_idx + 3, init_idx + 1);			}			mesh_free(faces[i]);		}		/*destroy faces*/		free(faces);	}	mesh->mesh_type = MESH_TRIANGLES;	if (has_color) mesh->flags |= MESH_HAS_COLOR;	mesh_update_bounds(mesh);	if (!eg->ccw) mesh->flags |= MESH_IS_CW;	if (eg->solid) mesh->flags |= MESH_IS_SOLID;	if (colorRGBA) mesh->flags |= MESH_HAS_ALPHA;	gf_mesh_build_aabbtree(mesh);}typedef struct{	SFVec3f yaxis, zaxis, xaxis;} SCP;typedef struct{	SFVec3f pt, yaxis, zaxis, xaxis;	u32 max_idx;} SCPInfo;#define REGISTER_POINT_FACE(FACE_IDX) \	{	u32 fidx;	\		fidx = FACE_IDX; \		mesh_set_vertex_vx(faces[fidx], &vx);	\		if (smooth_normals) {	\			register_point_in_face(&faces_info[fidx], pidx);	\			register_face_in_point(&pts_info[pidx], fidx);	\		} \	} \#define NEAR_ZERO(__x) (ABS(__x)<=FIX_EPSILON) static void mesh_extrude_path_intern(GF_Mesh *mesh, GF_Path *path, MFVec3f *thespine, Fixed creaseAngle, Fixed min_cx, Fixed min_cy, Fixed width_cx, Fixed width_cy, Bool begin_cap, Bool end_cap, MFRotation *spine_ori, MFVec2f *spine_scale, Bool tx_along_spine){	GF_Mesh **faces;	GF_Vertex vx;	struct face_info *faces_info;	struct pt_info *pts_info;	GF_Matrix mx;	SCP *SCPs, SCPbegin, SCPend;	SCPInfo *SCPi;	Bool smooth_normals, spine_closed, check_first_spine_vec, do_close;	u32 i, j, k, nb_scp, nb_spine, face_count, pt_count, faces_per_cross, begin_face, end_face, face_spines, pts_per_cross, cur_pts_in_cross,cur, nb_pts, convexity;	SFVec3f *spine, v1, v2, n, spine_vec;	Fixed cross_len, spine_len, cur_cross, cur_spine;	SFRotation r;	SFVec2f scale;	if (!path->n_contours) return;	if (path->n_points<2) return;	if (thespine->count<2) return;	spine_closed = 0;	if (gf_vec_equal(thespine->vals[0], thespine->vals[thespine->count-1])) spine_closed = 1;	if (spine_closed && (thespine->count==2)) return;	gf_path_flatten(path);	pts_per_cross = 0;	cross_len = 0;	cur = 0;	for (i=0; i<path->n_contours; i++) {		nb_pts = 1 + path->contours[i] - cur;		pts_per_cross += nb_pts;		for (j=0; j<nb_pts; j++) {			if (j) {				v1.z = 0;				v1.x = path->points[j+cur].x - path->points[j-1+cur].x;				v1.y = path->points[j+cur].y - path->points[j-1+cur].y;				cross_len += gf_vec_len(v1);			}		}	}	faces_per_cross	= pts_per_cross - path->n_contours;	begin_face = end_face = 0;	face_spines = face_count = (thespine->count-1)*faces_per_cross;	if (begin_cap) {		begin_face = face_count; 		face_count ++;	}	if (end_cap) {		end_face = face_count; 		face_count ++;	}	pt_count = pts_per_cross * thespine->count;	smooth_normals = NEAR_ZERO(creaseAngle) ? 0 : 1;	faces = (GF_Mesh**)malloc(sizeof(GF_Mesh *)*face_count);	for (i=0; i<face_count; i++) faces[i] = new_mesh();	faces_info = NULL;	pts_info = NULL;		/*alloc face & normals tables*/	if (smooth_normals) {		faces_info = (struct face_info*)malloc(sizeof(struct face_info)*face_count);		memset(faces_info, 0, sizeof(struct face_info)*face_count);		pts_info = (struct pt_info*)malloc(sizeof(struct pt_info)*pt_count);		memset(pts_info, 0, sizeof(struct pt_info)*pt_count);	}		spine = thespine->vals;	nb_spine = thespine->count;	SCPs = (SCP *)malloc(sizeof(SCP) * nb_spine);	memset(SCPs, 0, sizeof(SCP) * nb_spine);	SCPi = (SCPInfo *) malloc(sizeof(SCPInfo) * nb_spine);	memset(SCPi, 0, sizeof(SCPInfo) * nb_spine);	/*collect all # SCPs: 	1- if a spine has identical consecutive points with # orientation, these points use the same SCPs	2- if 2 segs of the spine are colinear, they also use the same SCP	*/	SCPi[0].pt = spine[0];	SCPi[0].max_idx = 0;	nb_scp=1;	spine_len = 0;	check_first_spine_vec = 1;	for (i=1; i<nb_spine; i++) {		Fixed len;		/*also get spine length for txcoord*/		gf_vec_diff(v2, spine[i], spine[i-1]);		len = gf_vec_len(v2);		spine_len += len;		if (check_first_spine_vec && len) {			check_first_spine_vec = 0;			spine_vec = v2;		}		/*case 1: same point, same SCP*/		if (gf_vec_equal(SCPi[nb_scp-1].pt, spine[i])) {			SCPi[nb_scp-1].max_idx = i;			continue;		} 		/*last point in spine*/		if (i+1 == nb_spine) {			nb_scp++;			SCPi[nb_scp-1].pt = spine[i];			SCPi[nb_scp-1].max_idx = i;			break;		}		gf_vec_diff(v1, spine[i+1], spine[i]);		gf_vec_diff(v2, SCPi[nb_scp-1].pt, spine[i]);		n = gf_vec_cross(v1, v2);		/*case 2: spine segs are colinear*/		if (!n.x && !n.y && !n.z) {			SCPi[nb_scp-1].max_idx = i;		}		/*OK new SCP*/		else {			nb_scp++;			SCPi[nb_scp-1].pt = spine[i];			SCPi[nb_scp-1].max_idx = i;		}	}	/*all colinear!!*/	if (nb_scp<=2) {		SCPi[0].xaxis.x = FIX_ONE; SCPi[0].xaxis.y = 0; SCPi[0].xaxis.z = 0;		SCPi[0].yaxis.x = 0; SCPi[0].yaxis.y = FIX_ONE; SCPi[0].yaxis.z = 0;		SCPi[0].zaxis.x = 0; SCPi[0].zaxis.y = 0; SCPi[0].zaxis.z = FIX_ONE;		/*compute rotation from (0, 1, 0) to spine_vec*/		if (!check_first_spine_vec) {			Fixed alpha, gamma;			Fixed cos_a, sin_a, sin_g, cos_g;			gf_vec_norm(&spine_vec);			if (! NEAR_ZERO(spine_vec.x) ) {				if (spine_vec.x >= FIX_ONE-FIX_EPSILON) alpha = GF_PI2;				else if (spine_vec.x <= -FIX_ONE+FIX_EPSILON) alpha = -GF_PI2;				else alpha = gf_asin(spine_vec.x);				cos_a = gf_cos(alpha);				sin_a = spine_vec.x;				sin_g = 0;				if (NEAR_ZERO(cos_a)) gamma = 0;				else {					Fixed __abs;					gamma = gf_acos(gf_divfix(spine_vec.y, cos_a));					sin_g = gf_sin(gamma);					__abs = gf_divfix(spine_vec.z, cos_a) + sin_g;					if (ABS(__abs) > ABS(sin_g) ) gamma *= -1;				}				cos_g = gf_cos(gamma);				if (NEAR_ZERO(cos_g)) {					cos_g = 0;					sin_g = 1;				} else {					sin_g = gf_sin(gamma);				}				SCPi[0].yaxis.y = gf_mulfix(cos_a, sin_g);				SCPi[0].yaxis.z = gf_mulfix(cos_a, cos_g);				SCPi[0].yaxis.x = sin_a;				SCPi[0].zaxis.y = -gf_mulfix(sin_a, sin_g);				SCPi[0].zaxis.z = -gf_mulfix(sin_a, cos_g);				SCPi[0].zaxis.x = cos_a;			}			if (! NEAR_ZERO(spine_vec.z) ) {				if (spine_vec.z >= FIX_ONE-FIX_EPSILON) alpha = GF_PI2;				else if (spine_vec.z <= -FIX_ONE+FIX_EPSILON) alpha = -GF_PI2;				else alpha = gf_asin(spine_vec.z);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -