static void load_datablocks(Main *main_tmp, BlendHandle *bpy_openlib, const char *path, int idcode) { LinkNode *names = NULL; int totnames_dummy; names = BLO_blendhandle_get_datablock_names(bpy_openlib, idcode, &totnames_dummy); int i = 0; LinkNode *n = names; while (n) { BLO_library_append_named_part(main_tmp, &bpy_openlib, (char *)n->link, idcode); n = (LinkNode *)n->next; i++; } BLI_linklist_free(names, free); /* free linklist *and* each node's data */ }
static PyObject *bpy_lib_exit(BPy_Library *self, PyObject *UNUSED(args)) { Main *bmain = CTX_data_main(BPy_GetContext()); Main *mainl = NULL; int err = 0; flag_all_listbases_ids(LIB_PRE_EXISTING, 1); /* here appending/linking starts */ mainl = BLO_library_append_begin(bmain, &(self->blo_handle), self->relpath); { int i = 0, code; while ((code = BKE_idcode_iter_step(&i))) { if (BKE_idcode_is_linkable(code)) { const char *name_plural = BKE_idcode_to_name_plural(code); PyObject *ls = PyDict_GetItemString(self->dict, name_plural); // printf("lib: %s\n", name_plural); if (ls && PyList_Check(ls)) { /* loop */ Py_ssize_t size = PyList_GET_SIZE(ls); Py_ssize_t i; PyObject *item; const char *item_str; for (i = 0; i < size; i++) { item = PyList_GET_ITEM(ls, i); item_str = _PyUnicode_AsString(item); // printf(" %s\n", item_str); if (item_str) { ID *id = BLO_library_append_named_part(mainl, &(self->blo_handle), item_str, code); if (id) { #ifdef USE_RNA_DATABLOCKS PointerRNA id_ptr; RNA_id_pointer_create(id, &id_ptr); Py_DECREF(item); item = pyrna_struct_CreatePyObject(&id_ptr); #endif } else { bpy_lib_exit_warn_idname(self, name_plural, item_str); /* just warn for now */ /* err = -1; */ #ifdef USE_RNA_DATABLOCKS item = Py_None; Py_INCREF(item); #endif } /* ID or None */ } else { /* XXX, could complain about this */ bpy_lib_exit_warn_type(self, item); PyErr_Clear(); #ifdef USE_RNA_DATABLOCKS item = Py_None; Py_INCREF(item); #endif } #ifdef USE_RNA_DATABLOCKS PyList_SET_ITEM(ls, i, item); #endif } } } } } if (err == -1) { /* exception raised above, XXX, this leaks some memory */ BLO_blendhandle_close(self->blo_handle); self->blo_handle = NULL; flag_all_listbases_ids(LIB_PRE_EXISTING, 0); return NULL; } else { Library *lib = mainl->curlib; /* newly added lib, assign before append end */ BLO_library_append_end(NULL, mainl, &(self->blo_handle), 0, self->flag); BLO_blendhandle_close(self->blo_handle); self->blo_handle = NULL; { /* copied from wm_operator.c */ /* mark all library linked objects to be updated */ recalc_all_library_objects(G.main); /* append, rather than linking */ if ((self->flag & FILE_LINK) == 0) { BKE_library_make_local(bmain, lib, 1); } } flag_all_listbases_ids(LIB_PRE_EXISTING, 0); Py_RETURN_NONE; } }
bool KX_BlenderSceneConverter::LinkBlendFile(BlendHandle *bpy_openlib, const char *path, char *group, KX_Scene *scene_merge, char **err_str, short options) { Main *main_newlib; /* stored as a dynamic 'main' until we free it */ Main *main_tmp= NULL; /* created only for linking, then freed */ LinkNode *names = NULL; int idcode= BKE_idcode_from_name(group); short flag= 0; /* don't need any special options */ ReportList reports; static char err_local[255]; /* only scene and mesh supported right now */ if (idcode!=ID_SCE && idcode!=ID_ME &&idcode!=ID_AC) { snprintf(err_local, sizeof(err_local), "invalid ID type given \"%s\"\n", group); *err_str= err_local; BLO_blendhandle_close(bpy_openlib); return false; } if (GetMainDynamicPath(path)) { snprintf(err_local, sizeof(err_local), "blend file already open \"%s\"\n", path); *err_str= err_local; BLO_blendhandle_close(bpy_openlib); return false; } if (bpy_openlib==NULL) { snprintf(err_local, sizeof(err_local), "could not open blendfile \"%s\"\n", path); *err_str= err_local; return false; } main_newlib= (Main *)MEM_callocN( sizeof(Main), "BgeMain"); BKE_reports_init(&reports, RPT_STORE); /* here appending/linking starts */ main_tmp = BLO_library_append_begin(main_newlib, &bpy_openlib, (char *)path); int totnames_dummy; names = BLO_blendhandle_get_datablock_names( bpy_openlib, idcode, &totnames_dummy); int i=0; LinkNode *n= names; while(n) { BLO_library_append_named_part(main_tmp, &bpy_openlib, (char *)n->link, idcode); n= (LinkNode *)n->next; i++; } BLI_linklist_free(names, free); /* free linklist *and* each node's data */ BLO_library_append_end(NULL, main_tmp, &bpy_openlib, idcode, flag); /* now do another round of linking for Scenes so all actions are properly loaded */ if (idcode==ID_SCE && options & LIB_LOAD_LOAD_ACTIONS) { main_tmp = BLO_library_append_begin(main_newlib, &bpy_openlib, (char *)path); int totnames_dummy; names = BLO_blendhandle_get_datablock_names( bpy_openlib, ID_AC, &totnames_dummy); int i=0; LinkNode *n= names; while(n) { BLO_library_append_named_part(main_tmp, &bpy_openlib, (char *)n->link, ID_AC); n= (LinkNode *)n->next; i++; } BLI_linklist_free(names, free); /* free linklist *and* each node's data */ BLO_library_append_end(NULL, main_tmp, &bpy_openlib, ID_AC, flag); } BLO_blendhandle_close(bpy_openlib); BKE_reports_clear(&reports); /* done linking */ /* needed for lookups*/ GetMainDynamic().push_back(main_newlib); strncpy(main_newlib->name, path, sizeof(main_newlib->name)); if (idcode==ID_ME) { /* Convert all new meshes into BGE meshes */ ID* mesh; for (mesh= (ID *)main_newlib->mesh.first; mesh; mesh= (ID *)mesh->next ) { if (options & LIB_LOAD_VERBOSE) printf("MeshName: %s\n", mesh->name+2); RAS_MeshObject *meshobj = BL_ConvertMesh((Mesh *)mesh, NULL, scene_merge, this); scene_merge->GetLogicManager()->RegisterMeshName(meshobj->GetName(),meshobj); } } else if (idcode==ID_AC) { /* Convert all actions */ ID *action; for (action= (ID *)main_newlib->action.first; action; action= (ID *)action->next) { if (options & LIB_LOAD_VERBOSE) printf("ActionName: %s\n", action->name+2); scene_merge->GetLogicManager()->RegisterActionName(action->name+2, action); } } else if (idcode==ID_SCE) { /* Merge all new linked in scene into the existing one */ ID *scene; for (scene= (ID *)main_newlib->scene.first; scene; scene= (ID *)scene->next ) { if (options & LIB_LOAD_VERBOSE) printf("SceneName: %s\n", scene->name+2); /* merge into the base scene */ KX_Scene* other= m_ketsjiEngine->CreateScene((Scene *)scene); scene_merge->MergeScene(other); // RemoveScene(other); // Don't run this, it frees the entire scene converter data, just delete the scene delete other; } /* Now handle all the actions */ if (options & LIB_LOAD_LOAD_ACTIONS) { ID *action; for (action= (ID *)main_newlib->action.first; action; action= (ID *)action->next) { if (options & LIB_LOAD_VERBOSE) printf("ActionName: %s\n", action->name+2); scene_merge->GetLogicManager()->RegisterActionName(action->name+2, action); } } } return true; }