GF_EXPORT Bool gf_node_in_table_by_tag(u32 tag, u32 NDTType) { if (!tag) return 0; if (tag==TAG_ProtoNode) return 1; else if (tag<=GF_NODE_RANGE_LAST_MPEG4) { #ifndef GPAC_DISABLE_BIFS u32 i; for (i=0;i<GF_BIFS_LAST_VERSION; i++) { if (gf_bifs_get_node_type(NDTType, tag, i+1)) return 1; } return 0; #else /*if BIFS is disabled, we don't have the NDTs - we therefore allow any node in any table otherwise we would reject them all*/ return 1; #endif } #ifndef GPAC_DISABLE_X3D else if (tag<=GF_NODE_RANGE_LAST_X3D) { return gf_x3d_get_node_type(NDTType, tag); } #endif return 0; }
static Bool gf_node_in_table_by_tag(u32 tag, u32 NDTType) { if (!tag) return 0; if (tag==TAG_ProtoNode) return 1; else if (tag<=GF_NODE_RANGE_LAST_MPEG4) { u32 i; u32 gf_bifs_get_node_type(u32 NDT_Tag, u32 NodeTag, u32 Version); for (i=0;i<GF_BIFS_LAST_VERSION; i++) { if (gf_bifs_get_node_type(NDTType, tag, i+1)) return 1; } return 0; } else if (tag<=GF_NODE_RANGE_LAST_X3D) { Bool X3D_IsNodeInTable(u32 NDT_Tag, u32 NodeTag); return X3D_IsNodeInTable(NDTType, tag); } return 0; }
GF_Err gf_bifs_enc_node(GF_BifsEncoder * codec, GF_Node *node, u32 NDT_Tag, GF_BitStream *bs, GF_Node *parent_node) { u32 NDTBits, node_type, node_tag, BVersion, node_id; const char *node_name; Bool flag, reset_qp14; GF_Node *new_node; GF_Err e; assert(codec->info); GF_LOG(GF_LOG_DEBUG, GF_LOG_CODEC, ("[BIFS] Encode node %s\n", gf_node_get_class_name(node) )); /*NULL node is a USE of maxID*/ if (!node) { GF_BIFS_WRITE_INT(codec, bs, 1, 1, "USE", NULL); GF_BIFS_WRITE_INT(codec, bs, (1<<codec->info->config.NodeIDBits) - 1 , codec->info->config.NodeIDBits, "NodeID", "NULL"); return GF_OK; } flag = BE_NodeIsUSE(codec, node); GF_BIFS_WRITE_INT(codec, bs, flag ? 1 : 0, 1, "USE", (char*)gf_node_get_class_name(node)); if (flag) { gf_bs_write_int(bs, gf_node_get_id(node) - 1, codec->info->config.NodeIDBits); new_node = gf_bifs_enc_find_node(codec, gf_node_get_id(node) ); if (!new_node) return codec->LastError = GF_SG_UNKNOWN_NODE; /*restore QP14 length*/ switch (gf_node_get_tag(new_node)) { case TAG_MPEG4_Coordinate: { u32 nbCoord = ((M_Coordinate *)new_node)->point.count; gf_bifs_enc_qp14_enter(codec, GF_TRUE); gf_bifs_enc_qp14_set_length(codec, nbCoord); gf_bifs_enc_qp14_enter(codec, GF_FALSE); } break; case TAG_MPEG4_Coordinate2D: { u32 nbCoord = ((M_Coordinate2D *)new_node)->point.count; gf_bifs_enc_qp14_enter(codec, GF_TRUE); gf_bifs_enc_qp14_set_length(codec, nbCoord); gf_bifs_enc_qp14_enter(codec, GF_FALSE); } break; } return GF_OK; } BVersion = GF_BIFS_V1; node_tag = node->sgprivate->tag; while (1) { node_type = gf_bifs_get_node_type(NDT_Tag, node_tag, BVersion); NDTBits = gf_bifs_get_ndt_bits(NDT_Tag, BVersion); if (BVersion==2 && (node_tag==TAG_ProtoNode)) node_type = 1; GF_BIFS_WRITE_INT(codec, bs, node_type, NDTBits, "ndt", NULL); if (node_type) break; BVersion += 1; if (BVersion > GF_BIFS_NUM_VERSION) { if (parent_node) { GF_LOG(GF_LOG_ERROR, GF_LOG_CODEC, ("[BIFS] Cannot encode node %s as a child of %s\n", gf_node_get_class_name(node), gf_node_get_class_name(parent_node) )); } else { GF_LOG(GF_LOG_ERROR, GF_LOG_CODEC, ("[BIFS] Cannot encode node %s in the SFWorldNode context\n", gf_node_get_class_name(node) )); } return codec->LastError = GF_BIFS_UNKNOWN_VERSION; } } if (BVersion==2 && node_type==1) { GF_Proto *proto = ((GF_ProtoInstance *)node)->proto_interface; GF_BIFS_WRITE_INT(codec, bs, proto->ID, codec->info->config.ProtoIDBits, "protoID", NULL); } /*special handling of 3D mesh*/ /*DEF'd node*/ node_name = gf_node_get_name_and_id(node, &node_id); GF_BIFS_WRITE_INT(codec, bs, node_id ? 1 : 0, 1, "DEF", NULL); if (node_id) { GF_BIFS_WRITE_INT(codec, bs, node_id - 1, codec->info->config.NodeIDBits, "NodeID", NULL); if (codec->UseName) gf_bifs_enc_name(codec, bs, (char*) node_name ); } /*no updates of time fields for now - NEEDED FOR A LIVE ENCODER*/ /*if coords were not stored for QP14 before coding this node, reset QP14 it when leaving*/ reset_qp14 = !codec->coord_stored; /*QP14 case*/ switch (node_tag) { case TAG_MPEG4_Coordinate: case TAG_MPEG4_Coordinate2D: gf_bifs_enc_qp14_enter(codec, GF_TRUE); } e = EncNodeFields(codec, bs, node); if (e) return e; if (codec->coord_stored && reset_qp14) gf_bifs_enc_qp14_reset(codec); switch (node_tag) { case TAG_MPEG4_Coordinate: case TAG_MPEG4_Coordinate2D: gf_bifs_enc_qp14_enter(codec, GF_FALSE); break; } return GF_OK; }