void KX_BlenderSceneConverter::ResetPhysicsObjectsAnimationIpo(bool clearIpo) { //TODO this entire function is deprecated, written for 2.4x //the functionality should be rewritten, currently it does nothing KX_SceneList *scenes = m_ketsjiEngine->CurrentScenes(); int numScenes = scenes->size(); int i; for (i = 0; i < numScenes; i++) { KX_Scene *scene = scenes->at(i); CListValue *parentList = scene->GetRootParentList(); int numObjects = parentList->GetCount(); int g; for (g = 0; g < numObjects; g++) { KX_GameObject *gameObj = (KX_GameObject *)parentList->GetValue(g); if (gameObj->IsRecordAnimation()) { Object *blenderObject = gameObj->GetBlenderObject(); if (blenderObject) { #if 0 //erase existing ipo's Ipo* ipo = blenderObject->ipo;//findIpoForName(blenderObject->id.name+2); if (ipo) { //clear the curve data if (clearIpo) {//rcruiz IpoCurve *icu1; int numCurves = 0; for ( icu1 = (IpoCurve*)ipo->curve.first; icu1; ) { IpoCurve* tmpicu = icu1; /*int i; BezTriple *bezt; for ( bezt = tmpicu->bezt, i = 0; i < tmpicu->totvert; i++, bezt++) { printf("(%f,%f,%f),(%f,%f,%f),(%f,%f,%f)\n",bezt->vec[0][0],bezt->vec[0][1],bezt->vec[0][2],bezt->vec[1][0],bezt->vec[1][1],bezt->vec[1][2],bezt->vec[2][0],bezt->vec[2][1],bezt->vec[2][2]); }*/ icu1 = icu1->next; numCurves++; BLI_remlink( &( blenderObject->ipo->curve ), tmpicu ); if ( tmpicu->bezt ) MEM_freeN( tmpicu->bezt ); MEM_freeN( tmpicu ); localDel_ipoCurve( tmpicu ); } } } else { ipo = NULL; // XXX add_ipo(blenderObject->id.name+2, ID_OB); blenderObject->ipo = ipo; } #endif } } } } }
static void update_anim_thread_func(TaskPool *pool, void *taskdata, int UNUSED(threadid)) { KX_GameObject *gameobj, *child; CListValue *children; bool needs_update; double curtime = *(double*)BLI_task_pool_userdata(pool); gameobj = (KX_GameObject*)taskdata; // Non-armature updates are fast enough, so just update them needs_update = gameobj->GetGameObjectType() != SCA_IObject::OBJ_ARMATURE; if (!needs_update) { // If we got here, we're looking to update an armature, so check its // children meshes to see if we need to bother with a more expensive // pose update children = gameobj->GetChildren(); bool has_mesh = false, has_non_mesh = false; // Check for meshes that haven't been culled for (int j=0; j<children->GetCount(); ++j) { child = (KX_GameObject*)children->GetValue(j); if (!child->GetCulled()) { needs_update = true; break; } if (child->GetMeshCount() == 0) has_non_mesh = true; else has_mesh = true; } // If we didn't find a non-culled mesh, check to see // if we even have any meshes, and update if this // armature has only non-mesh children. if (!needs_update && !has_mesh && has_non_mesh) needs_update = true; children->Release(); } if (needs_update) gameobj->UpdateActionManager(curtime); }
void KX_BlenderSceneConverter::TestHandlesPhysicsObjectToAnimationIpo() { KX_SceneList* scenes = m_ketsjiEngine->CurrentScenes(); int numScenes = scenes->size(); int i; for (i=0;i<numScenes;i++) { KX_Scene* scene = scenes->at(i); //PHY_IPhysicsEnvironment* physEnv = scene->GetPhysicsEnvironment(); CListValue* parentList = scene->GetRootParentList(); int numObjects = parentList->GetCount(); int g; for (g=0;g<numObjects;g++) { KX_GameObject* gameObj = (KX_GameObject*)parentList->GetValue(g); if (gameObj->IsDynamic()) { //KX_IPhysicsController* physCtrl = gameObj->GetPhysicsController(); Object* blenderObject = gameObj->GetBlenderObject(); if (blenderObject && blenderObject->ipo) { // XXX animato #if 0 Ipo* ipo = blenderObject->ipo; //create the curves, if not existing //testhandles_ipocurve checks for NULL testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"LocX")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"LocY")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"LocZ")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"RotX")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"RotY")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"RotZ")); #endif } } } } }
void KX_BlenderSceneConverter::TestHandlesPhysicsObjectToAnimationIpo() { KX_SceneList *scenes = m_ketsjiEngine->CurrentScenes(); int numScenes = scenes->size(); int i; for (i = 0; i < numScenes; i++) { KX_Scene *scene = scenes->at(i); //PHY_IPhysicsEnvironment* physEnv = scene->GetPhysicsEnvironment(); CListValue *parentList = scene->GetRootParentList(); int numObjects = parentList->GetCount(); int g; for (g = 0; g < numObjects; g++) { KX_GameObject *gameObj = (KX_GameObject *)parentList->GetValue(g); if (gameObj->IsRecordAnimation()) { Object *blenderObject = gameObj->GetBlenderObject(); if (blenderObject && blenderObject->adt) { bAction *act = verify_adt_action(&blenderObject->id, false); FCurve *fcu; if (!act) { continue; } /* for now, not much choice but to run this on all curves... */ for (fcu = (FCurve *)act->curves.first; fcu; fcu = fcu->next) { /* Note: calling `sort_time_fcurve()` here is not needed, since * all keys have been added in 'right' order. */ calchandles_fcurve(fcu); } #if 0 // XXX animato Ipo* ipo = blenderObject->ipo; //create the curves, if not existing //testhandles_ipocurve checks for NULL testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"LocX")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"LocY")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"LocZ")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"RotX")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"RotY")); testhandles_ipocurve(findIpoCurve((IpoCurve *)ipo->curve.first,"RotZ")); #endif } } } } }
void KX_KetsjiEngine::RenderShadowBuffers(KX_Scene *scene) { CListValue *lightlist = scene->GetLightList(); int i, drawmode; m_rendertools->SetAuxilaryClientInfo(scene); for(i=0; i<lightlist->GetCount(); i++) { KX_GameObject *gameobj = (KX_GameObject*)lightlist->GetValue(i); KX_LightObject *light = (KX_LightObject*)gameobj; light->Update(); if(m_drawingmode == RAS_IRasterizer::KX_TEXTURED && light->HasShadowBuffer()) { /* make temporary camera */ RAS_CameraData camdata = RAS_CameraData(); KX_Camera *cam = new KX_Camera(scene, scene->m_callbacks, camdata, true, true); cam->SetName("__shadow__cam__"); MT_Transform camtrans; /* switch drawmode for speed */ drawmode = m_rasterizer->GetDrawingMode(); m_rasterizer->SetDrawingMode(RAS_IRasterizer::KX_SHADOW); /* binds framebuffer object, sets up camera .. */ light->BindShadowBuffer(m_rasterizer, cam, camtrans); /* update scene */ scene->CalculateVisibleMeshes(m_rasterizer, cam, light->GetShadowLayer()); /* render */ m_rasterizer->ClearDepthBuffer(); scene->RenderBuckets(camtrans, m_rasterizer, m_rendertools); /* unbind framebuffer object, restore drawmode, free camera */ light->UnbindShadowBuffer(m_rasterizer); m_rasterizer->SetDrawingMode(drawmode); cam->Release(); } } }
void KX_BlenderSceneConverter::resetNoneDynamicObjectToIpo() { if (addInitFromFrame) { KX_SceneList* scenes = m_ketsjiEngine->CurrentScenes(); int numScenes = scenes->size(); if (numScenes>=0) { KX_Scene* scene = scenes->at(0); CListValue* parentList = scene->GetRootParentList(); for (int ix=0;ix<parentList->GetCount();ix++) { KX_GameObject* gameobj = (KX_GameObject*)parentList->GetValue(ix); if (!gameobj->IsDynamic()) { Object* blenderobject = gameobj->GetBlenderObject(); if (!blenderobject) continue; if (blenderobject->type==OB_ARMATURE) continue; float eu[3]; mat4_to_eul(eu,blenderobject->obmat); MT_Point3 pos = MT_Point3( blenderobject->obmat[3][0], blenderobject->obmat[3][1], blenderobject->obmat[3][2] ); MT_Vector3 eulxyz = MT_Vector3( eu[0], eu[1], eu[2] ); MT_Vector3 scale = MT_Vector3( blenderobject->size[0], blenderobject->size[1], blenderobject->size[2] ); gameobj->NodeSetLocalPosition(pos); gameobj->NodeSetLocalOrientation(MT_Matrix3x3(eulxyz)); gameobj->NodeSetLocalScale(scale); gameobj->NodeUpdateGS(0); } } } } }
static int listvalue_buffer_contains(PyObject *self_v, PyObject *value) { CListValue *self = static_cast<CListValue *>(BGE_PROXY_REF(self_v)); if (self == NULL) { PyErr_SetString(PyExc_SystemError, "val in CList, "BGE_PROXY_ERROR_MSG); return -1; } if (PyUnicode_Check(value)) { if (self->FindValue((const char *)_PyUnicode_AsString(value))) { return 1; } } else if (PyObject_TypeCheck(value, &CValue::Type)) { /* not dict like at all but this worked before __contains__ was used */ CValue *item= static_cast<CValue *>(BGE_PROXY_REF(value)); for (int i=0; i < self->GetCount(); i++) if (self->GetValue(i) == item) // Com return 1; } // not using CheckEqual return 0; }
/* clist + list, return a list that python owns */ static PyObject *listvalue_buffer_concat(PyObject *self, PyObject *other) { CListValue *listval= static_cast<CListValue *>(BGE_PROXY_REF(self)); Py_ssize_t i, numitems, numitems_orig; if (listval==NULL) { PyErr_SetString(PyExc_SystemError, "CList+other, "BGE_PROXY_ERROR_MSG); return NULL; } numitems_orig= listval->GetCount(); // for now, we support CListValue concatenated with items // and CListValue concatenated to Python Lists // and CListValue concatenated with another CListValue /* Shallow copy, don't use listval->GetReplica(), it will screw up with KX_GameObjects */ CListValue* listval_new = new CListValue(); if (PyList_Check(other)) { CValue* listitemval; bool error = false; numitems = PyList_GET_SIZE(other); /* copy the first part of the list */ listval_new->Resize(numitems_orig + numitems); for (i=0;i<numitems_orig;i++) listval_new->SetValue(i, listval->GetValue(i)->AddRef()); for (i=0;i<numitems;i++) { listitemval = listval->ConvertPythonToValue(PyList_GetItem(other,i), "cList + pyList: CListValue, "); if (listitemval) { listval_new->SetValue(i+numitems_orig, listitemval); } else { error= true; break; } } if (error) { listval_new->Resize(numitems_orig+i); /* resize so we don't try release NULL pointers */ listval_new->Release(); return NULL; /* ConvertPythonToValue above sets the error */ } } else if (PyObject_TypeCheck(other, &CListValue::Type)) { // add items from otherlist to this list CListValue* otherval = static_cast<CListValue *>(BGE_PROXY_REF(other)); if (otherval==NULL) { listval_new->Release(); PyErr_SetString(PyExc_SystemError, "CList+other, "BGE_PROXY_ERROR_MSG); return NULL; } numitems = otherval->GetCount(); /* copy the first part of the list */ listval_new->Resize(numitems_orig + numitems); /* resize so we don't try release NULL pointers */ for (i=0;i<numitems_orig;i++) listval_new->SetValue(i, listval->GetValue(i)->AddRef()); /* now copy the other part of the list */ for (i=0;i<numitems;i++) listval_new->SetValue(i+numitems_orig, otherval->GetValue(i)->AddRef()); } return listval_new->NewProxy(true); /* python owns this list */ }
///this generates ipo curves for position, rotation, allowing to use game physics in animation void KX_BlenderSceneConverter::WritePhysicsObjectToAnimationIpo(int frameNumber) { KX_SceneList* scenes = m_ketsjiEngine->CurrentScenes(); int numScenes = scenes->size(); int i; for (i=0;i<numScenes;i++) { KX_Scene* scene = scenes->at(i); //PHY_IPhysicsEnvironment* physEnv = scene->GetPhysicsEnvironment(); CListValue* parentList = scene->GetObjectList(); int numObjects = parentList->GetCount(); int g; for (g=0;g<numObjects;g++) { KX_GameObject* gameObj = (KX_GameObject*)parentList->GetValue(g); Object* blenderObject = gameObj->GetBlenderObject(); if (blenderObject && blenderObject->parent==NULL && gameObj->IsDynamic()) { //KX_IPhysicsController* physCtrl = gameObj->GetPhysicsController(); if (blenderObject->adt==NULL) BKE_id_add_animdata(&blenderObject->id); if (blenderObject->adt) { const MT_Point3& position = gameObj->NodeGetWorldPosition(); //const MT_Vector3& scale = gameObj->NodeGetWorldScaling(); const MT_Matrix3x3& orn = gameObj->NodeGetWorldOrientation(); position.getValue(blenderObject->loc); float tmat[3][3]; for (int r=0;r<3;r++) for (int c=0;c<3;c++) tmat[r][c] = (float)orn[c][r]; mat3_to_compatible_eul(blenderObject->rot, blenderObject->rot, tmat); insert_keyframe(NULL, &blenderObject->id, NULL, NULL, "location", -1, (float)frameNumber, INSERTKEY_FAST); insert_keyframe(NULL, &blenderObject->id, NULL, NULL, "rotation_euler", -1, (float)frameNumber, INSERTKEY_FAST); #if 0 const MT_Point3& position = gameObj->NodeGetWorldPosition(); //const MT_Vector3& scale = gameObj->NodeGetWorldScaling(); const MT_Matrix3x3& orn = gameObj->NodeGetWorldOrientation(); float eulerAngles[3]; float eulerAnglesOld[3] = {0.0f, 0.0f, 0.0f}; float tmat[3][3]; // XXX animato Ipo* ipo = blenderObject->ipo; //create the curves, if not existing, set linear if new IpoCurve *icu_lx = findIpoCurve((IpoCurve *)ipo->curve.first,"LocX"); if (!icu_lx) { icu_lx = verify_ipocurve(&blenderObject->id, ipo->blocktype, NULL, NULL, NULL, OB_LOC_X, 1); if (icu_lx) icu_lx->ipo = IPO_LIN; } IpoCurve *icu_ly = findIpoCurve((IpoCurve *)ipo->curve.first,"LocY"); if (!icu_ly) { icu_ly = verify_ipocurve(&blenderObject->id, ipo->blocktype, NULL, NULL, NULL, OB_LOC_Y, 1); if (icu_ly) icu_ly->ipo = IPO_LIN; } IpoCurve *icu_lz = findIpoCurve((IpoCurve *)ipo->curve.first,"LocZ"); if (!icu_lz) { icu_lz = verify_ipocurve(&blenderObject->id, ipo->blocktype, NULL, NULL, NULL, OB_LOC_Z, 1); if (icu_lz) icu_lz->ipo = IPO_LIN; } IpoCurve *icu_rx = findIpoCurve((IpoCurve *)ipo->curve.first,"RotX"); if (!icu_rx) { icu_rx = verify_ipocurve(&blenderObject->id, ipo->blocktype, NULL, NULL, NULL, OB_ROT_X, 1); if (icu_rx) icu_rx->ipo = IPO_LIN; } IpoCurve *icu_ry = findIpoCurve((IpoCurve *)ipo->curve.first,"RotY"); if (!icu_ry) { icu_ry = verify_ipocurve(&blenderObject->id, ipo->blocktype, NULL, NULL, NULL, OB_ROT_Y, 1); if (icu_ry) icu_ry->ipo = IPO_LIN; } IpoCurve *icu_rz = findIpoCurve((IpoCurve *)ipo->curve.first,"RotZ"); if (!icu_rz) { icu_rz = verify_ipocurve(&blenderObject->id, ipo->blocktype, NULL, NULL, NULL, OB_ROT_Z, 1); if (icu_rz) icu_rz->ipo = IPO_LIN; } if (icu_rx) eulerAnglesOld[0]= eval_icu( icu_rx, frameNumber - 1 ) / ((180 / 3.14159265f) / 10); if (icu_ry) eulerAnglesOld[1]= eval_icu( icu_ry, frameNumber - 1 ) / ((180 / 3.14159265f) / 10); if (icu_rz) eulerAnglesOld[2]= eval_icu( icu_rz, frameNumber - 1 ) / ((180 / 3.14159265f) / 10); // orn.getValue((float *)tmat); // uses the wrong ordering, cant use this for (int r=0;r<3;r++) for (int c=0;c<3;c++) tmat[r][c] = orn[c][r]; // mat3_to_eul( eulerAngles,tmat); // better to use Mat3ToCompatibleEul mat3_to_compatible_eul( eulerAngles, eulerAnglesOld,tmat); //eval_icu for (int x = 0; x < 3; x++) eulerAngles[x] *= (float) ((180 / 3.14159265f) / 10.0); //fill the curves with data if (icu_lx) insert_vert_icu(icu_lx, frameNumber, position.x(), 1); if (icu_ly) insert_vert_icu(icu_ly, frameNumber, position.y(), 1); if (icu_lz) insert_vert_icu(icu_lz, frameNumber, position.z(), 1); if (icu_rx) insert_vert_icu(icu_rx, frameNumber, eulerAngles[0], 1); if (icu_ry) insert_vert_icu(icu_ry, frameNumber, eulerAngles[1], 1); if (icu_rz) insert_vert_icu(icu_rz, frameNumber, eulerAngles[2], 1); // Handles are corrected at the end, testhandles_ipocurve isn't needed yet #endif } } } } }
void KX_BlenderSceneConverter::ResetPhysicsObjectsAnimationIpo(bool clearIpo) { KX_SceneList* scenes = m_ketsjiEngine->CurrentScenes(); int numScenes = scenes->size(); int i; for (i=0;i<numScenes;i++) { KX_Scene* scene = scenes->at(i); //PHY_IPhysicsEnvironment* physEnv = scene->GetPhysicsEnvironment(); CListValue* parentList = scene->GetRootParentList(); int numObjects = parentList->GetCount(); int g; for (g=0;g<numObjects;g++) { KX_GameObject* gameObj = (KX_GameObject*)parentList->GetValue(g); if (gameObj->IsDynamic()) { //KX_IPhysicsController* physCtrl = gameObj->GetPhysicsController(); Object* blenderObject = gameObj->GetBlenderObject(); if (blenderObject) { #if 0 //erase existing ipo's Ipo* ipo = blenderObject->ipo;//findIpoForName(blenderObject->id.name+2); if (ipo) { //clear the curve data if (clearIpo) {//rcruiz IpoCurve *icu1; int numCurves = 0; for ( icu1 = (IpoCurve*)ipo->curve.first; icu1; ) { IpoCurve* tmpicu = icu1; /*int i; BezTriple *bezt; for ( bezt = tmpicu->bezt, i = 0; i < tmpicu->totvert; i++, bezt++) { printf("(%f,%f,%f),(%f,%f,%f),(%f,%f,%f)\n",bezt->vec[0][0],bezt->vec[0][1],bezt->vec[0][2],bezt->vec[1][0],bezt->vec[1][1],bezt->vec[1][2],bezt->vec[2][0],bezt->vec[2][1],bezt->vec[2][2]); }*/ icu1 = icu1->next; numCurves++; BLI_remlink( &( blenderObject->ipo->curve ), tmpicu ); if ( tmpicu->bezt ) MEM_freeN( tmpicu->bezt ); MEM_freeN( tmpicu ); localDel_ipoCurve( tmpicu ); } } } else { ipo = NULL; // XXX add_ipo(blenderObject->id.name+2, ID_OB); blenderObject->ipo = ipo; } #endif } } } } }
/* Note m_map_*** are all ok and don't need to be freed * most are temp and NewRemoveObject frees m_map_gameobject_to_blender */ bool KX_BlenderSceneConverter::FreeBlendFile(Main *maggie) { int maggie_index = -1; int i = 0; if (maggie == NULL) return false; // If the given library is currently in loading, we do nothing. if (m_status_map.count(maggie->name)) { BLI_mutex_lock(&m_threadinfo->m_mutex); const bool finished = m_status_map[maggie->name]->IsFinished(); BLI_mutex_unlock(&m_threadinfo->m_mutex); if (!finished) { printf("Library (%s) is currently being loaded asynchronously, and cannot be freed until this process is done\n", maggie->name); return false; } } /* tag all false except the one we remove */ for (vector<Main *>::iterator it = m_DynamicMaggie.begin(); !(it == m_DynamicMaggie.end()); it++) { Main *main = *it; if (main != maggie) { BKE_main_id_tag_all(main, LIB_TAG_DOIT, false); } else { maggie_index = i; } i++; } /* should never happen but just to be safe */ if (maggie_index == -1) return false; m_DynamicMaggie.erase(m_DynamicMaggie.begin() + maggie_index); BKE_main_id_tag_all(maggie, LIB_TAG_DOIT, true); /* free all tagged objects */ KX_SceneList *scenes = m_ketsjiEngine->CurrentScenes(); int numScenes = scenes->size(); for (int scene_idx = 0; scene_idx < numScenes; scene_idx++) { KX_Scene *scene = scenes->at(scene_idx); if (IS_TAGGED(scene->GetBlenderScene())) { m_ketsjiEngine->RemoveScene(scene->GetName()); m_mat_cache.erase(scene); m_polymat_cache.erase(scene); scene_idx--; numScenes--; } else { /* in case the mesh might be refered to later */ { CTR_Map<STR_HashedString, void *> &mapStringToMeshes = scene->GetLogicManager()->GetMeshMap(); for (int i = 0; i < mapStringToMeshes.size(); i++) { RAS_MeshObject *meshobj = (RAS_MeshObject *) *mapStringToMeshes.at(i); if (meshobj && IS_TAGGED(meshobj->GetMesh())) { STR_HashedString mn = meshobj->GetName(); mapStringToMeshes.remove(mn); m_map_mesh_to_gamemesh.remove(CHashedPtr(meshobj->GetMesh())); i--; } } } /* Now unregister actions */ { CTR_Map<STR_HashedString, void *> &mapStringToActions = scene->GetLogicManager()->GetActionMap(); for (int i = 0; i < mapStringToActions.size(); i++) { ID *action = (ID*) *mapStringToActions.at(i); if (IS_TAGGED(action)) { STR_HashedString an = action->name + 2; mapStringToActions.remove(an); m_map_blender_to_gameAdtList.remove(CHashedPtr(action)); i--; } } } //scene->FreeTagged(); /* removed tagged objects and meshes*/ CListValue *obj_lists[] = {scene->GetObjectList(), scene->GetInactiveList(), NULL}; for (int ob_ls_idx = 0; obj_lists[ob_ls_idx]; ob_ls_idx++) { CListValue *obs = obj_lists[ob_ls_idx]; RAS_MeshObject *mesh; for (int ob_idx = 0; ob_idx < obs->GetCount(); ob_idx++) { KX_GameObject *gameobj = (KX_GameObject*)obs->GetValue(ob_idx); if (IS_TAGGED(gameobj->GetBlenderObject())) { int size_before = obs->GetCount(); /* Eventually calls RemoveNodeDestructObject * frees m_map_gameobject_to_blender from UnregisterGameObject */ scene->RemoveObject(gameobj); if (size_before != obs->GetCount()) ob_idx--; else { printf("ERROR COULD NOT REMOVE \"%s\"\n", gameobj->GetName().ReadPtr()); } } else { gameobj->RemoveTaggedActions(); /* free the mesh, we could be referecing a linked one! */ int mesh_index = gameobj->GetMeshCount(); while (mesh_index--) { mesh = gameobj->GetMesh(mesh_index); if (IS_TAGGED(mesh->GetMesh())) { gameobj->RemoveMeshes(); /* XXX - slack, should only remove meshes that are library items but mostly objects only have 1 mesh */ break; } else { /* also free the mesh if it's using a tagged material */ int mat_index = mesh->NumMaterials(); while (mat_index--) { if (IS_TAGGED(mesh->GetMeshMaterial(mat_index)->m_bucket->GetPolyMaterial()->GetBlenderMaterial())) { gameobj->RemoveMeshes(); /* XXX - slack, same as above */ break; } } } } /* make sure action actuators are not referencing tagged actions */ for (unsigned int act_idx = 0; act_idx < gameobj->GetActuators().size(); act_idx++) { if (gameobj->GetActuators()[act_idx]->IsType(SCA_IActuator::KX_ACT_ACTION)) { BL_ActionActuator *act = (BL_ActionActuator *)gameobj->GetActuators()[act_idx]; if (IS_TAGGED(act->GetAction())) act->SetAction(NULL); } } } } } } } int size; // delete the entities of this scene /* TODO - */ #if 0 vector<pair<KX_Scene*,KX_WorldInfo*> >::iterator worldit; size = m_worldinfos.size(); for (i=0, worldit=m_worldinfos.begin(); i<size; ) { if ((*worldit).second) { delete (*worldit).second; *worldit = m_worldinfos.back(); m_worldinfos.pop_back(); size--; } else { i++; worldit++; } } #endif /* Worlds don't reference original blender data so we need to make a set from them */ typedef std::set<KX_WorldInfo *> KX_WorldInfoSet; KX_WorldInfoSet worldset; for (int scene_idx = 0; scene_idx < numScenes; scene_idx++) { KX_Scene *scene = scenes->at(scene_idx); if (scene->GetWorldInfo()) worldset.insert(scene->GetWorldInfo()); } vector<pair<KX_Scene *, KX_WorldInfo *> >::iterator worldit; size = m_worldinfos.size(); for (i = 0, worldit = m_worldinfos.begin(); i < size;) { if (worldit->second && (worldset.count(worldit->second)) == 0) { delete worldit->second; *worldit = m_worldinfos.back(); m_worldinfos.pop_back(); size--; } else { i++; worldit++; } } worldset.clear(); /* done freeing the worlds */ vector<pair<KX_Scene *, RAS_IPolyMaterial *> >::iterator polymit; size = m_polymaterials.size(); for (i = 0, polymit = m_polymaterials.begin(); i < size; ) { RAS_IPolyMaterial *mat = polymit->second; Material *bmat = NULL; KX_BlenderMaterial *bl_mat = static_cast<KX_BlenderMaterial *>(mat); bmat = bl_mat->GetBlenderMaterial(); if (IS_TAGGED(bmat)) { /* only remove from bucket */ polymit->first->GetBucketManager()->RemoveMaterial(mat); } i++; polymit++; } for (i = 0, polymit = m_polymaterials.begin(); i < size; ) { RAS_IPolyMaterial *mat = polymit->second; Material *bmat = NULL; KX_BlenderMaterial *bl_mat = static_cast<KX_BlenderMaterial*>(mat); bmat = bl_mat->GetBlenderMaterial(); if (IS_TAGGED(bmat)) { // Remove the poly material coresponding to this Blender Material. m_polymat_cache[polymit->first].erase(bmat); delete polymit->second; *polymit = m_polymaterials.back(); m_polymaterials.pop_back(); size--; } else { i++; polymit++; } } vector<pair<KX_Scene *, BL_Material *> >::iterator matit; size = m_materials.size(); for (i = 0, matit = m_materials.begin(); i < size; ) { BL_Material *mat = matit->second; if (IS_TAGGED(mat->material)) { // Remove the bl material coresponding to this Blender Material. m_mat_cache[matit->first].erase(mat->material); delete matit->second; *matit = m_materials.back(); m_materials.pop_back(); size--; } else { i++; matit++; } } vector<pair<KX_Scene *, RAS_MeshObject *> >::iterator meshit; RAS_BucketManager::BucketList::iterator bit; list<RAS_MeshSlot>::iterator msit; RAS_BucketManager::BucketList buckets; size = m_meshobjects.size(); for (i = 0, meshit = m_meshobjects.begin(); i < size;) { RAS_MeshObject *me = meshit->second; if (IS_TAGGED(me->GetMesh())) { // Before deleting the mesh object, make sure the rasterizer is // no longer referencing it. buckets = meshit->first->GetBucketManager()->GetSolidBuckets(); for (bit = buckets.begin(); bit != buckets.end(); bit++) { msit = (*bit)->msBegin(); while (msit != (*bit)->msEnd()) { if (msit->m_mesh == meshit->second) (*bit)->RemoveMesh(&(*msit++)); else msit++; } } // And now the alpha buckets buckets = meshit->first->GetBucketManager()->GetAlphaBuckets(); for (bit = buckets.begin(); bit != buckets.end(); bit++) { msit = (*bit)->msBegin(); while (msit != (*bit)->msEnd()) { if (msit->m_mesh == meshit->second) (*bit)->RemoveMesh(&(*msit++)); else msit++; } } // Now it should be safe to delete delete meshit->second; *meshit = m_meshobjects.back(); m_meshobjects.pop_back(); size--; } else { i++; meshit++; } } #ifdef WITH_PYTHON /* make sure this maggie is removed from the import list if it's there * (this operation is safe if it isn't in the list) */ removeImportMain(maggie); #endif delete m_status_map[maggie->name]; m_status_map.erase(maggie->name); BKE_main_free(maggie); return true; }