📄 loader_xmt.c
字号:
} else if (gf_sg_proto_field_is_sftime_offset(n, info)) { xmt_offset_time(parser, (Double *)info->far_ptr); }}static u32 xmt_parse_sf_field(GF_XMTParser *parser, GF_FieldInfo *info, GF_Node *n, char *a_value){ u32 res = 0; switch (info->fieldType) { case GF_SG_VRML_SFINT32: res = xmt_parse_int(parser, info->name, (SFInt32 *)info->far_ptr, a_value); break; case GF_SG_VRML_SFBOOL: res = xmt_parse_bool(parser, info->name, (SFBool *)info->far_ptr, a_value); break; case GF_SG_VRML_SFFLOAT: res = xmt_parse_float(parser, info->name, (SFFloat *)info->far_ptr, a_value); break; case GF_SG_VRML_SFTIME: res = xmt_parse_time(parser, info->name, (SFTime *)info->far_ptr, a_value); xmt_check_time_offset(parser, n, info); break; case GF_SG_VRML_SFCOLOR: res = xmt_parse_float(parser, info->name, & ((SFColor *)info->far_ptr)->red, a_value); res += xmt_parse_float(parser, info->name, & ((SFColor *)info->far_ptr)->green, a_value + res); res += xmt_parse_float(parser, info->name, & ((SFColor *)info->far_ptr)->blue, a_value + res); break; case GF_SG_VRML_SFVEC2F: res = xmt_parse_float(parser, info->name, & ((SFVec2f *)info->far_ptr)->x, a_value); res += xmt_parse_float(parser, info->name, & ((SFVec2f *)info->far_ptr)->y, a_value + res); break; case GF_SG_VRML_SFVEC3F: res = xmt_parse_float(parser, info->name, & ((SFVec3f *)info->far_ptr)->x, a_value); res += xmt_parse_float(parser, info->name, & ((SFVec3f *)info->far_ptr)->y, a_value + res); res += xmt_parse_float(parser, info->name, & ((SFVec3f *)info->far_ptr)->z, a_value + res); break; case GF_SG_VRML_SFROTATION: res = xmt_parse_float(parser, info->name, & ((SFRotation *)info->far_ptr)->x, a_value); res += xmt_parse_float(parser, info->name, & ((SFRotation *)info->far_ptr)->y, a_value + res); res += xmt_parse_float(parser, info->name, & ((SFRotation *)info->far_ptr)->z, a_value + res); res += xmt_parse_float(parser, info->name, & ((SFRotation *)info->far_ptr)->q, a_value + res); break; case GF_SG_VRML_SFSTRING: res = xmt_parse_string(parser, info->name, (SFString*)info->far_ptr, 0, a_value); break; case GF_SG_VRML_SFSCRIPT: res = xmt_parse_script(parser, info->name, (SFScript *)info->far_ptr, 0, a_value); break; case GF_SG_VRML_SFCOMMANDBUFFER: { SFCommandBuffer *cb = (SFCommandBuffer *)info->far_ptr; cb->buffer = (unsigned char*)parser->command; parser->command_buffer = cb; } break; case GF_SG_VRML_SFIMAGE: { u32 k, size, v; SFImage *img = (SFImage *)info->far_ptr; res = xmt_parse_int(parser, "width", (SFInt32*)&img->width, a_value); if (parser->last_error) return res; res += xmt_parse_int(parser, "height", (SFInt32*)&img->height, a_value + res); if (parser->last_error) return res; res += xmt_parse_int(parser, "nbComp", (SFInt32*)&v, a_value + res); if (parser->last_error) return res; img->numComponents = v; size = img->width * img->height * img->numComponents; if (img->pixels) free(img->pixels); img->pixels = (unsigned char*)malloc(sizeof(char) * size); a_value += res; res = 0; for (k=0; k<size; k++) { char *name = "pixels"; XMT_GET_ONE_VAL if (strstr(value, "0x")) sscanf(value, "%x", &v); else sscanf(value, "%d", &v); switch (img->numComponents) { case 1: img->pixels[k] = (char) v; break; case 2: img->pixels[k] = (char) (v>>8)&0xFF; img->pixels[k+1] = (char) (v)&0xFF; k++; break; case 3: img->pixels[k] = (char) (v>>16)&0xFF; img->pixels[k+1] = (char) (v>>8)&0xFF; img->pixels[k+2] = (char) (v)&0xFF; k+=2; break; case 4: img->pixels[k] = (char) (v>>24)&0xFF; img->pixels[k+1] = (char) (v>>16)&0xFF; img->pixels[k+2] = (char) (v>>8)&0xFF; img->pixels[k+3] = (char) (v)&0xFF; k+=3; break; } res += i; a_value += i; } } break; default: parser->last_error = GF_NOT_SUPPORTED; break; } return res;}static void xmt_parse_mf_field(GF_XMTParser *parser, GF_FieldInfo *info, GF_Node *n, char *value){ u32 res; GF_FieldInfo sfInfo; sfInfo.fieldType = gf_sg_vrml_get_sf_type(info->fieldType); sfInfo.name = info->name; gf_sg_vrml_mf_reset(info->far_ptr, info->fieldType); if (!value || !strlen(value)) return; while (value[0] && !parser->last_error) { while (value[0] && value[0] == ' ') value++; if (!value[0]) break; gf_sg_vrml_mf_append(info->far_ptr, info->fieldType, &sfInfo.far_ptr); /*special case for MF type based on string (MFString, MFURL and MFScript), we need to take care of all possible forms of XML multi string encoding*/ if (sfInfo.fieldType == GF_SG_VRML_SFSTRING) { res = xmt_parse_string(parser, info->name, (SFString*)sfInfo.far_ptr, 1, value); } else if (sfInfo.fieldType == GF_SG_VRML_SFURL) { res = xmt_parse_url(parser, info->name, (MFURL *)info->far_ptr, n, 1, value); } else if (sfInfo.fieldType == GF_SG_VRML_SFSCRIPT) { res = xmt_parse_script(parser, info->name, (SFScript*)sfInfo.far_ptr, 1, value); } else { res = xmt_parse_sf_field(parser, &sfInfo, n, value); } if (res) { value += res; } else { break; } }}static Bool xmt_has_been_def(GF_XMTParser *parser, char *node_name){ u32 i, count; count = gf_list_count(parser->def_nodes); for (i=0; i<count; i++) { GF_Node *n = (GF_Node *)gf_list_get(parser->def_nodes, i); if (!strcmp(gf_node_get_name(n), node_name)) return 1; } return 0;}static u32 xmt_get_route(GF_XMTParser *parser, char *name, Bool del_com) { u32 i; GF_Command *com; GF_Route *r = gf_sg_route_find_by_name(parser->load->scene_graph, name); if (r) return r->ID; i=0; while ((com = (GF_Command *)gf_list_enum(parser->inserted_routes, &i))) { if (com->def_name && !strcmp(com->def_name, name)) { if (del_com) gf_list_rem(parser->inserted_routes, i); return com->RouteID; } } return 0;}static Bool xmt_route_id_used(GF_XMTParser *parser, u32 ID){ u32 i; GF_Command *com; GF_Route *r = gf_sg_route_find(parser->load->scene_graph, ID); if (r) return 1; i=0; while ((com = (GF_Command *)gf_list_enum(parser->inserted_routes, &i))) { if (com->RouteID == ID) return 1; } return 0;}static u32 xmt_get_next_route_id(GF_XMTParser *parser){ u32 ID; GF_SceneGraph *sc = parser->load->scene_graph; if (parser->parsing_proto) sc = gf_sg_proto_get_graph(parser->parsing_proto); ID = gf_sg_get_next_available_route_id(sc); if (parser->load->ctx && (ID>parser->load->ctx->max_route_id)) parser->load->ctx->max_route_id = ID; return ID;}static void xmt_resolve_routes(GF_XMTParser *parser){ GF_Command *com; /*resolve all commands*/ while (1) { com = (GF_Command *)gf_list_last(parser->unresolved_routes); if (!com) break; gf_list_rem_last(parser->unresolved_routes); switch (com->tag) { case GF_SG_ROUTE_DELETE: case GF_SG_ROUTE_REPLACE: com->RouteID = xmt_get_route(parser, com->unres_name, 0); if (!com->RouteID) { xmt_report(parser, GF_BAD_PARAM, "Cannot resolve GF_Route DEF %s", com->unres_name); } free(com->unres_name); com->unres_name = NULL; com->unresolved = 0; break; } } while (gf_list_count(parser->inserted_routes)) gf_list_rem(parser->inserted_routes, 0);}static void xmt_parse_route(GF_XMTParser *parser, const GF_XMLAttribute *attributes, u32 nb_attributes, Bool is_insert, GF_Command *com){ GF_Route *r; char *toN, *toNF, *fromN, *fromNF, *ID; GF_Node *orig, *dest; GF_Err e; u32 rID, i; GF_FieldInfo orig_field, dest_field; toN = toNF = fromN = fromNF = ID = NULL; for (i=0; i<nb_attributes; i++) { GF_XMLAttribute *att = (GF_XMLAttribute *) &attributes[i]; if (!att->value || !strlen(att->value)) continue; if (!strcmp(att->name, "fromNode")) fromN = att->value; else if (!strcmp(att->name, "fromField")) fromNF = att->value; else if (!strcmp(att->name, "toNode")) toN = att->value; else if (!strcmp(att->name, "toField")) toNF = att->value; else if (!strcmp(att->name, "DEF")) ID = att->value; } orig = xmt_find_node(parser, fromN); if (!orig) { xmt_report(parser, GF_BAD_PARAM, "ROUTE: Cannot find origin node %s", fromN); return; } e = gf_node_get_field_by_name(orig, fromNF, &orig_field); if ((e != GF_OK) && strstr(fromNF, "_changed")) { char *sz = strstr(fromNF, "_changed"); sz[0] = 0; e = gf_node_get_field_by_name(orig, fromNF, &orig_field); } if (e!=GF_OK) { xmt_report(parser, GF_BAD_PARAM, "%s is not an attribute of node %s", fromNF, fromN); return; } dest = xmt_find_node(parser, toN); if (!dest) { xmt_report(parser, GF_BAD_PARAM, "ROUTE: Cannot find destination node %s", toN); return; } e = gf_node_get_field_by_name(dest, toNF, &dest_field); if ((e != GF_OK) && !strnicmp(toNF, "set_", 4)) e = gf_node_get_field_by_name(dest, &toNF[4], &dest_field); if (e != GF_OK) { xmt_report(parser, GF_BAD_PARAM, "%s is not an attribute of node %s", toNF, toN); return; } rID = 0; if (ID && strlen(ID)) { rID = xmt_get_route(parser, ID, 0); if (!rID && (ID[0]=='R') ) { rID = atoi(&ID[1]); if (rID) { rID++; if (xmt_route_id_used(parser, rID)) rID = 0; } } if (!rID) rID = xmt_get_next_route_id(parser); } if (com) { /*for insert command*/ if (rID) { com->RouteID = rID; com->def_name = strdup(ID); /*whenever not inserting in graph, keep track of max defined ID*/ gf_sg_set_max_defined_route_id(parser->load->scene_graph, rID); if (rID>parser->load->ctx->max_route_id) parser->load->ctx->max_route_id = rID; } com->fromNodeID = gf_node_get_id(orig); com->fromFieldIndex = orig_field.fieldIndex; com->toNodeID = gf_node_get_id(dest); com->toFieldIndex = dest_field.fieldIndex; return; } r = gf_sg_route_new(parser->load->scene_graph, orig, orig_field.fieldIndex, dest, dest_field.fieldIndex); if (rID) { gf_sg_route_set_id(r, rID); gf_sg_route_set_name(r, ID); }}static void xmt_update_timenode(GF_XMTParser *parser, GF_Node *node){ if (!(parser->load->flags & GF_SM_LOAD_FOR_PLAYBACK)) return; switch (gf_node_get_tag(node)) { case TAG_MPEG4_AnimationStream: xmt_offset_time(parser, & ((M_AnimationStream*)node)->startTime); xmt_offset_time(parser, & ((M_AnimationStream*)node)->stopTime); break; case TAG_MPEG4_AudioBuffer: xmt_offset_time(parser, & ((M_AudioBuffer*)node)->startTime); xmt_offset_time(parser, & ((M_AudioBuffer*)node)->stopTime); break; case TAG_MPEG4_AudioClip: xmt_offset_time(parser, & ((M_AudioClip*)node)->startTime); xmt_offset_time(parser, & ((M_AudioClip*)node)->stopTime); break; case TAG_MPEG4_AudioSource: xmt_offset_time(parser, & ((M_AudioSource*)node)->startTime); xmt_offset_time(parser, & ((M_AudioSource*)node)->stopTime); break; case TAG_MPEG4_MovieTexture: xmt_offset_time(parser, & ((M_MovieTexture*)node)->startTime); xmt_offset_time(parser, & ((M_MovieTexture*)node)->stopTime); break; case TAG_MPEG4_TimeSensor: xmt_offset_time(parser, & ((M_TimeSensor*)node)->startTime); xmt_offset_time(parser, & ((M_TimeSensor*)node)->stopTime); break; case TAG_ProtoNode: { u32 i, nbFields; GF_FieldInfo inf; nbFields = gf_node_get_num_fields_in_mode(node, GF_SG_FIELD_CODING_ALL); for (i=0; i<nbFields; i++) { gf_node_get_field(node, i, &inf); if (inf.fieldType != GF_SG_VRML_SFTIME) continue; xmt_check_time_offset(parser, node, &inf); } } break; }}static void xmt_strip_name(char *in, char *out){ while (in[0]==' ') in++; strcpy(out, in); while (out[strlen(out)-1] == ' ') out[strlen(out)-1] = 0;}static u32 xmt_get_ft_by_name(const char *_name){ char name[1024]; xmt_strip_name((char *)_name, name); if (!strcmp(name, "Boolean") || !strcmp(name, "SFBool")) return GF_SG_VRML_SFBOOL; else if (!strcmp(name, "Integer") || !strcmp(name, "SFInt32")) return GF_SG_VRML_SFINT32; else if (!strcmp(name, "Color") || !strcmp(name, "SFColor")) return GF_SG_VRML_SFCOLOR; else if (!strcmp(name, "Vector2") || !strcmp(name, "SFVec2f")) return GF_SG_VRML_SFVEC2F; else if (!strcmp(name, "Image") || !strcmp(name, "SFImage")) return GF_SG_VRML_SFIMAGE; else if (!strcmp(name, "Time") || !strcmp(name, "SFTime")) return GF_SG_VRML_SFTIME; else if (!strcmp(name, "Float") || !strcmp(name, "SFFloat")) return GF_SG_VRML_SFFLOAT; else if (!strcmp(name, "Vector3") || !strcmp(name, "SFVec3f")) return GF_SG_VRML_SFVEC3F; else if (!strcmp(name, "Rotation") || !strcmp(name, "SFRotation")) return GF_SG_VRML_SFROTATION; else if (!strcmp(name, "String") || !strcmp(name, "SFString")) return GF_SG_VRML_SFSTRING; else if (!strcmp(name, "Node") || !strcmp(name, "SFNode")) return GF_SG_VRML_SFNODE; else if (!strcmp(name, "Booleans") || !strcmp(name, "MFBool")) return GF_SG_VRML_MFBOOL; else if (!strcmp(name, "Integers") || !strcmp(name, "MFInt32")) return GF_SG_VRML_MFINT32; else if (!strcmp(name, "Colors") || !strcmp(name, "MFColor")) return GF_SG_VRML_MFCOLOR; else if (!strcmp(name, "Vector2s") || !strcmp(name, "Vector2Array") || !strcmp(name, "MFVec2f")) return GF_SG_VRML_MFVEC2F; else if (!strcmp(name, "Images") || !strcmp(name, "MFImage")) return GF_SG_VRML_MFIMAGE; else if (!strcmp(name, "Times") || !strcmp(name, "MFTime")) return GF_SG_VRML_MFTIME; else if (!strcmp(name, "Floats") || !strcmp(name, "MFFloat")) return GF_SG_VRML_MFFLOAT; else if (!strcmp(name, "Vector3s") || !strcmp(name, "Vector3Array") || !strcmp(name, "MFVec3f")) return GF_SG_VRML_MFVEC3F; else if (!strcmp(name, "Rotations") || !strcmp(name, "MFRotation")) return GF_SG_VRML_MFROTATION; else if (!strcmp(name, "Strings") || !strcmp(name, "MFString")) return GF_SG_VRML_MFSTRING; else if (!strcmp(name, "Nodes") || !strcmp(name, "MFNode")) return GF_SG_VRML_MFNODE; else if (!strcmp(name, "SFColorRGBA")) return GF_SG_VRML_SFCOLORRGBA; else if (!strcmp(name, "MFColorRGBA")) return GF_SG_VRML_MFCOLORRGBA; else if (!strcmp(name, "SFDouble")) return GF_SG_VRML_SFDOUBLE; else if (!strcmp(name, "MFDouble")) return GF_SG_VRML_MFDOUBLE; else if (!strcmp(name, "SFVec3d")) return GF_SG_VRML_SFVEC3D; else if (!strcmp(name, "MFVec3d")) return GF_SG_VRML_MFVEC3D; else if (!strcmp(name, "SFVec2d")) return GF_SG_VRML_SFVEC2D; else if (!strcmp(name, "MFVec2d")) return GF_SG_VRML_MFVEC2D; else return GF_SG_VRML_UNKNOWN;}static u32 xmt_get_script_et_by_name(const char *_name){ char name[1024]; xmt_strip_name((char *)_name, name); if (!strcmp(name, "eventIn") || !strcmp(name, "inputOnly") ) return GF_SG_SCRIPT_TYPE_EVENT_IN; else if (!strcmp(name, "eventOut") || !strcmp(name, "outputOnly")) return GF_SG_SCRIPT_TYPE_EVENT_OUT; else if (!strcmp(name, "field") || !strcmp(name, "initializeOnly") ) return GF_SG_SCRIPT_TYPE_FIELD;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -