GF_Err BE_FieldReplace(GF_BifsEncoder *codec, GF_Command *com, GF_BitStream *bs) { GF_Err e; u32 ind, NumBits; GF_FieldInfo field; GF_CommandField *inf; if (!gf_list_count(com->command_fields)) return GF_OK; inf = (GF_CommandField *)gf_list_get(com->command_fields, 0); GF_BIFS_WRITE_INT(codec, bs, gf_node_get_id(com->node) - 1, codec->info->config.NodeIDBits, "NodeID", NULL); NumBits = gf_get_bit_size(gf_node_get_num_fields_in_mode(com->node, GF_SG_FIELD_CODING_IN)-1); gf_bifs_field_index_by_mode(com->node, inf->fieldIndex, GF_SG_FIELD_CODING_IN, &ind); GF_BIFS_WRITE_INT(codec, bs, ind, NumBits, "field", NULL); e = gf_node_get_field(com->node, inf->fieldIndex, &field); if (e) return e; field.far_ptr = inf->field_ptr; /* Warning: To be changed when proper solution is found */ if (gf_sg_vrml_get_sf_type(field.fieldType) == GF_SG_VRML_SFSCRIPT) codec->is_encoding_command = 1; e = gf_bifs_enc_field(codec, bs, com->node, &field); codec->is_encoding_command = 0; return e; }
static GF_Err BE_MultipleReplace(GF_BifsEncoder * codec, GF_Command *com, GF_BitStream *bs) { u32 i, j, nbBits, count, numFields, allField; Bool use_list; GF_FieldInfo field; GF_Err e; gf_bs_write_int(bs, gf_node_get_id(com->node)-1, codec->info->config.NodeIDBits); count = gf_list_count(com->command_fields); use_list = 1; numFields = gf_node_get_num_fields_in_mode(com->node, GF_SG_FIELD_CODING_DEF); nbBits = gf_get_bit_size(numFields - 1); if (count < 1+count*(1+nbBits)) use_list = 0; GF_BIFS_WRITE_INT(codec, bs, use_list ? 0 : 1, 1, "isMask", NULL); for (i=0; i<numFields; i++) { GF_CommandField *inf = NULL; gf_bifs_get_field_index(com->node, i, GF_SG_FIELD_CODING_DEF, &allField); for (j=0; j<count; j++) { inf = (GF_CommandField *)gf_list_get(com->command_fields, j); if (inf->fieldIndex==allField) break; inf = NULL; } if (!inf) { if (!use_list) GF_BIFS_WRITE_INT(codec, bs, 0, 1, "Mask", NULL); continue; } /*common case*/ gf_node_get_field(com->node, inf->fieldIndex, &field); if (use_list) { /*not end flag*/ GF_BIFS_WRITE_INT(codec, bs, 0, 1, "end", NULL); } else { /*mask flag*/ GF_BIFS_WRITE_INT(codec, bs, 1, 1, "Mask", NULL); } if (use_list) GF_BIFS_WRITE_INT(codec, bs, i, nbBits, "field", (char*)field.name); field.far_ptr = inf->field_ptr; e = gf_bifs_enc_field(codec, bs, com->node, &field); if (e) return e; } /*end flag*/ if (use_list) GF_BIFS_WRITE_INT(codec, bs, 1, 1, "end", NULL); return GF_OK; }
static GF_Err BE_MultipleIndexedReplace(GF_BifsEncoder * codec, GF_Command *com, GF_BitStream *bs) { u32 i,nbBits, count, maxPos, nbBitsPos; GF_FieldInfo field; GF_Err e; GF_CommandField *inf; if (!gf_list_count(com->command_fields)) return GF_OK; inf = (GF_CommandField *)gf_list_get(com->command_fields, 0); gf_bs_write_int(bs, gf_node_get_id(com->node)-1, codec->info->config.NodeIDBits); nbBits = gf_get_bit_size(gf_node_get_num_fields_in_mode(com->node, GF_SG_FIELD_CODING_IN)-1); gf_bifs_field_index_by_mode(com->node, inf->fieldIndex, GF_SG_FIELD_CODING_IN, &i); GF_BIFS_WRITE_INT(codec, bs, i, nbBits, "field", NULL); gf_node_get_field(com->node, inf->fieldIndex, &field); field.fieldType = inf->fieldType; count = gf_list_count(com->command_fields); maxPos = 0; for (i=0; i<count; i++) { inf = (GF_CommandField *)gf_list_get(com->command_fields, i); if (maxPos < (u32) inf->pos) maxPos = inf->pos; } nbBitsPos = gf_get_bit_size(maxPos); GF_BIFS_WRITE_INT(codec, bs, nbBitsPos, 5, "nbBitsPos", NULL); nbBits = gf_get_bit_size(count); GF_BIFS_WRITE_INT(codec, bs, nbBits, 5, "nbBits", NULL); GF_BIFS_WRITE_INT(codec, bs, count, nbBits, "count", NULL); for (i=0; i<count; i++) { inf = (GF_CommandField *)gf_list_get(com->command_fields, i); GF_BIFS_WRITE_INT(codec, bs, inf->pos, nbBitsPos, "idx", NULL); field.far_ptr = inf->field_ptr; e = gf_bifs_enc_field(codec, bs, com->node, &field); if (e) return e; } return GF_OK; }
GF_Err EncNodeFields(GF_BifsEncoder * codec, GF_BitStream *bs, GF_Node *node) { u8 mode; GF_Route *isedField; GF_Node *clone; GF_Err e; s32 *enc_fields; u32 numBitsALL, numBitsDEF, allInd, count, i, nbBitsProto, nbFinal; Bool use_list, nodeIsFDP = GF_FALSE; GF_FieldInfo field, clone_field; e = GF_OK; if (codec->encoding_proto) { mode = GF_SG_FIELD_CODING_ALL; nbBitsProto = gf_get_bit_size(gf_sg_proto_get_field_count(codec->encoding_proto) - 1); numBitsALL = gf_get_bit_size(gf_node_get_num_fields_in_mode(node, GF_SG_FIELD_CODING_ALL) - 1); } else { mode = GF_SG_FIELD_CODING_DEF; nbBitsProto = 0; numBitsALL = 0; } count = gf_node_get_num_fields_in_mode(node, mode); if (node->sgprivate->tag==TAG_MPEG4_Script) count = 3; if (!count) { GF_BIFS_WRITE_INT(codec, bs, 0, 1, "isMask", NULL); GF_BIFS_WRITE_INT(codec, bs, 1, 1, "end", NULL); return GF_OK; } if (node->sgprivate->tag == TAG_ProtoNode) { clone = gf_sg_proto_create_instance(node->sgprivate->scenegraph, ((GF_ProtoInstance *)node)->proto_interface);; } else { clone = gf_node_new(node->sgprivate->scenegraph, node->sgprivate->tag); } if (clone) gf_node_register(clone, NULL); numBitsDEF = gf_get_bit_size(gf_node_get_num_fields_in_mode(node, GF_SG_FIELD_CODING_DEF) - 1); enc_fields = (s32*)gf_malloc(sizeof(s32) * count); nbFinal = 0; for (i=0; i<count; i++) { enc_fields[i] = -1; /*get field in ALL mode*/ if (mode == GF_SG_FIELD_CODING_ALL) { allInd = i; } else { gf_bifs_get_field_index(node, i, GF_SG_FIELD_CODING_DEF, &allInd); } /*encode proto code*/ if (codec->encoding_proto) { isedField = gf_bifs_enc_is_field_ised(codec, node, allInd); if (isedField) { enc_fields[i] = allInd; nbFinal ++; continue; } } /*common case*/ gf_node_get_field(node, allInd, &field); /*if event don't encode (happens when encoding protos)*/ if ((field.eventType == GF_SG_EVENT_IN) || (field.eventType == GF_SG_EVENT_OUT)) continue; /*if field is default skip*/ switch (field.fieldType) { case GF_SG_VRML_SFNODE: if (* (GF_Node **) field.far_ptr) { enc_fields[i] = allInd; nbFinal++; } break; case GF_SG_VRML_MFNODE: if (* (GF_ChildNodeItem **) field.far_ptr) { enc_fields[i] = allInd; nbFinal++; } break; case GF_SG_VRML_SFCOMMANDBUFFER: { SFCommandBuffer *cb = (SFCommandBuffer *)field.far_ptr; if (gf_list_count(cb->commandList)) { enc_fields[i] = allInd; nbFinal++; } } break; case GF_SG_VRML_MFSCRIPT: enc_fields[i] = allInd; nbFinal++; break; default: gf_node_get_field(clone, allInd, &clone_field); if (!gf_sg_vrml_field_equal(clone_field.far_ptr, field.far_ptr, field.fieldType)) { enc_fields[i] = allInd; nbFinal++; } break; } } if (clone) gf_node_unregister(clone, NULL); use_list = GF_TRUE; /* patch for FDP node : */ /* cannot use default field sorting due to spec "mistake", so use list to imply inversion between field 2 and field 3 of FDP*/ if (node->sgprivate->tag == TAG_MPEG4_FDP) { s32 s4SwapValue = enc_fields[2]; enc_fields[2] = enc_fields[3]; enc_fields[3] = s4SwapValue; nodeIsFDP = GF_TRUE; use_list = GF_TRUE; } /*number of bits in mask node is count*1, in list node is 1+nbFinal*(1+numBitsDEF) */ else if (count < 1+nbFinal*(1+numBitsDEF)) use_list = GF_FALSE; GF_BIFS_WRITE_INT(codec, bs, use_list ? 0 : 1, 1, "isMask", NULL); for (i=0; i<count; i++) { if (enc_fields[i] == -1) { if (!use_list) GF_BIFS_WRITE_INT(codec, bs, 0, 1, "Mask", NULL); continue; } allInd = (u32) enc_fields[i]; /*encode proto code*/ if (codec->encoding_proto) { isedField = gf_bifs_enc_is_field_ised(codec, node, allInd); if (isedField) { if (use_list) { GF_BIFS_WRITE_INT(codec, bs, 0, 1, "end", NULL); } else { GF_BIFS_WRITE_INT(codec, bs, 1, 1, "Mask", NULL); } GF_BIFS_WRITE_INT(codec, bs, 1, 1, "isedField", NULL); if (use_list) GF_BIFS_WRITE_INT(codec, bs, allInd, numBitsALL, "nodeField", NULL); if (isedField->ToNode == node) { GF_BIFS_WRITE_INT(codec, bs, isedField->FromField.fieldIndex, nbBitsProto, "protoField", NULL); } else { GF_BIFS_WRITE_INT(codec, bs, isedField->ToField.fieldIndex, nbBitsProto, "protoField", NULL); } continue; } } /*common case*/ gf_node_get_field(node, allInd, &field); if (use_list) { /*not end flag*/ GF_BIFS_WRITE_INT(codec, bs, 0, 1, "end", NULL); } else { /*mask flag*/ GF_BIFS_WRITE_INT(codec, bs, 1, 1, "Mask", NULL); } /*not ISed field*/ if (codec->encoding_proto) GF_BIFS_WRITE_INT(codec, bs, 0, 1, "isedField", NULL); if (use_list) { if (codec->encoding_proto || nodeIsFDP) { u32 ind=0; /*for proto, we're in ALL mode and we need DEF mode*/ /*for FDP, encoding requires to get def id from all id as fields 2 and 3 are reversed*/ gf_bifs_field_index_by_mode(node, allInd, GF_SG_FIELD_CODING_DEF, &ind); GF_BIFS_WRITE_INT(codec, bs, ind, numBitsDEF, "field", (char*)field.name); } else { GF_BIFS_WRITE_INT(codec, bs, i, numBitsDEF, "field", (char*)field.name); } } e = gf_bifs_enc_field(codec, bs, node, &field); if (e) goto exit; } /*end flag*/ if (use_list) GF_BIFS_WRITE_INT(codec, bs, 1, 1, "end", NULL); exit: gf_free(enc_fields); return e; }
static GF_Err EncScriptFields(ScriptEnc *sc_enc) { u32 nbFields, nbBits, eType, nbBitsProto, i; Bool use_list; GF_Err e; GF_FieldInfo info; nbFields = gf_node_get_num_fields_in_mode(sc_enc->script, GF_SG_FIELD_CODING_ALL) - 3; use_list = 1; nbBits = gf_get_bit_size(nbFields); if (nbFields+1 > 4 + gf_get_bit_size(nbFields)) use_list = 0; if (!nbFields) { GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, 1, 1, "Script::isList", NULL); GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, 1, 1, "end", NULL); return GF_OK; } GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, use_list ? 1 : 0, 1, "Script::isList", NULL); if (!use_list) { GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, nbBits, 4, "nbBits", NULL); GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, nbFields, nbBits, "count", NULL); } nbBitsProto = 0; if (sc_enc->codec->encoding_proto) nbBitsProto = gf_get_bit_size(gf_sg_proto_get_field_count(sc_enc->codec->encoding_proto) - 1); for (i=0; i<nbFields; i++) { if (use_list) GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, 0, 1, "end", NULL); gf_node_get_field(sc_enc->script, i+3, &info); switch (info.eventType) { case GF_SG_EVENT_IN: eType = GF_SG_SCRIPT_TYPE_EVENT_IN; break; case GF_SG_EVENT_OUT: eType = GF_SG_SCRIPT_TYPE_EVENT_OUT; break; default: eType = GF_SG_SCRIPT_TYPE_FIELD; break; } GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, eType, 2, "eventType", NULL); GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, info.fieldType, 6, "fieldType", NULL); gf_bifs_enc_name(sc_enc->codec, sc_enc->bs, (char *) info.name); /*this is an identifier for script*/ gf_list_add(sc_enc->identifiers, gf_strdup(info.name)); if (sc_enc->codec->encoding_proto) { GF_Route *isedField = gf_bifs_enc_is_field_ised(sc_enc->codec, sc_enc->script, i+3); if (isedField) { GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, 1, 1, "isedField", NULL); if (isedField->ToNode == sc_enc->script) { GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, isedField->FromField.fieldIndex, nbBitsProto, "protoField", NULL); } else { GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, isedField->ToField.fieldIndex, nbBitsProto, "protoField", NULL); } continue; } GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, 0, 1, "isedField", NULL); } /*default value*/ if (eType == GF_SG_SCRIPT_TYPE_FIELD) { GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, (info.far_ptr) ? 1 : 0, 1, "hasInitialValue", NULL); if (info.far_ptr) { e = gf_bifs_enc_field(sc_enc->codec, sc_enc->bs, sc_enc->script, &info); if (e) return e; } } } if (use_list) GF_BIFS_WRITE_INT(sc_enc->codec, sc_enc->bs, 1, 1, "end", NULL); return GF_OK; }
static GF_Err BE_XReplace(GF_BifsEncoder * codec, GF_Command *com, GF_BitStream *bs) { u32 i,nbBits; GF_FieldInfo field; GF_Err e; GF_CommandField *inf; if (!gf_list_count(com->command_fields)) return GF_BAD_PARAM; inf = (GF_CommandField *)gf_list_get(com->command_fields, 0); gf_bs_write_int(bs, gf_node_get_id(com->node)-1, codec->info->config.NodeIDBits); nbBits = gf_get_bit_size(gf_node_get_num_fields_in_mode(com->node, GF_SG_FIELD_CODING_IN)-1); gf_bifs_field_index_by_mode(com->node, inf->fieldIndex, GF_SG_FIELD_CODING_IN, &i); GF_BIFS_WRITE_INT(codec, bs, i, nbBits, "field", NULL); gf_node_get_field(com->node, inf->fieldIndex, &field); if (!gf_sg_vrml_is_sf_field(field.fieldType)) { if ((inf->pos != -2) || com->toNodeID) { GF_BIFS_WRITE_INT(codec, bs, 1, 1, "indexedReplacement", NULL); if (com->toNodeID) { GF_Node *n = gf_bifs_enc_find_node(codec, com->toNodeID); GF_BIFS_WRITE_INT(codec, bs, 1, 1, "dynamicIndex", NULL); GF_BIFS_WRITE_INT(codec, bs, com->toNodeID-1, codec->info->config.NodeIDBits, "idxNodeID", NULL); nbBits = gf_get_bit_size(gf_node_get_num_fields_in_mode(n, GF_SG_FIELD_CODING_DEF)-1); gf_bifs_field_index_by_mode(n, com->toFieldIndex, GF_SG_FIELD_CODING_DEF, &i); GF_BIFS_WRITE_INT(codec, bs, i, nbBits, "idxField", NULL); } else { GF_BIFS_WRITE_INT(codec, bs, 0, 1, "dynamicIndex", NULL); if (inf->pos==-1) { GF_BIFS_WRITE_INT(codec, bs, 3, 2, "replacementPosition", NULL); } else if (inf->pos==0) { GF_BIFS_WRITE_INT(codec, bs, 2, 2, "replacementPosition", NULL); } else { GF_BIFS_WRITE_INT(codec, bs, 0, 2, "replacementPosition", NULL); GF_BIFS_WRITE_INT(codec, bs, inf->pos, 16, "position", NULL); } } } else { GF_BIFS_WRITE_INT(codec, bs, 0, 1, "indexedReplacement", NULL); } } if (field.fieldType==GF_SG_VRML_MFNODE) { if (com->ChildNodeTag) { GF_Node *n; if (com->ChildNodeTag>0) { n = gf_node_new(codec->scene_graph, com->ChildNodeTag); } else { GF_Proto *proto = gf_sg_find_proto(codec->scene_graph, -com->ChildNodeTag , NULL); if (!proto) return GF_SG_UNKNOWN_NODE; n = gf_sg_proto_create_instance(codec->scene_graph, proto); } if (!n) return GF_SG_UNKNOWN_NODE; gf_node_register(n, NULL); GF_BIFS_WRITE_INT(codec, bs, 1, 1, "childField", NULL); nbBits = gf_get_bit_size(gf_node_get_num_fields_in_mode(n, GF_SG_FIELD_CODING_IN)-1); gf_bifs_field_index_by_mode(n, com->child_field, GF_SG_FIELD_CODING_IN, &i); GF_BIFS_WRITE_INT(codec, bs, i, nbBits, "childField", NULL); gf_node_unregister(n, NULL); } else { GF_BIFS_WRITE_INT(codec, bs, 0, 1, "childField", NULL); } } if (com->fromNodeID) { GF_Node *n = gf_bifs_enc_find_node(codec, com->fromNodeID); GF_BIFS_WRITE_INT(codec, bs, 1, 1, "valueFromNode", NULL); GF_BIFS_WRITE_INT(codec, bs, com->fromNodeID-1, codec->info->config.NodeIDBits, "sourceNodeID", NULL); nbBits = gf_get_bit_size(gf_node_get_num_fields_in_mode(n, GF_SG_FIELD_CODING_DEF)-1); gf_bifs_field_index_by_mode(n, com->fromFieldIndex, GF_SG_FIELD_CODING_DEF, &i); GF_BIFS_WRITE_INT(codec, bs, i, nbBits, "sourceField", NULL); return GF_OK; } GF_BIFS_WRITE_INT(codec, bs, 0, 1, "valueFromNode", NULL); field.far_ptr = inf->field_ptr; field.fieldType = inf->fieldType; e = gf_bifs_enc_field(codec, bs, com->node, &field); return e; }