mxArray* ParticleSimulator::SaveConvexity() { ParticleFactory* factory = ParticleFactory::getInstance(); const int dims[] = { factory->particles.size(), 3 }; vector<float> F(dims[0] * dims[1]); for (int i = 0; i < dims[0]; ++i) { MovingParticle* p = factory->particles[i]; CParticleF pr = p->project(p->created + 0.1); SetData2(F, i, 0, dims[0], dims[1], pr.m_X); SetData2(F, i, 1, dims[0], dims[1], pr.m_Y); SetData2(F, i, 2, dims[0], dims[1], p->reflexive<=0 ? 0.0f: 1.0f); } return StoreData(F, mxSINGLE_CLASS, 2, dims); }
/* a snapshot provides neighborhood information at a particular point in time. We try to reproduce the configuration of the system as accurately as possible. We need to consider the following steps. 1. all particles that are created after the time point need to be removed from the system. 2. all particles that are still active at the time point need to be activated. 3. children of a particle need to be erased if they are created after the time point. */ bool ParticleSimulator::Restore(vector<Snapshot>& snapshots) { ParticleFactory* factory = ParticleFactory::getInstance(); float time0 = 0; for (int i = 0; i < snapshots.size(); ++i) { if (snapshots[i].getTime() > time0) { time0 = snapshots[i].getTime(); } } time = time0; for (int i = 0; i < factory->particles.size(); ++i) { MovingParticle* p = factory->particles[i]; for (int j = 0; j < 2; ++j) { if (p->children[j] != NULL && p->children[j]->created > time) { p->children[j] = NULL; } } } vector<MovingParticle*> toremove; for (int i = 0; i < factory->particles.size(); ++i) { MovingParticle* p = factory->particles[i]; if (p->created > time) { toremove.push_back(p); } } //activate those that are still active. vector<MovingParticle*> toactivate; for (int i = 0; i < factory->particles.size(); ++i) { MovingParticle* p = factory->particles[i]; if (p->bActive == false && p->created < time && p->time > time) { toactivate.push_back(p); } } //set neighbors for (int i = 0; i < snapshots.size(); ++i) { float t = snapshots[i].getTime(); for (int j = 0; j < snapshots[i].size(); ++j) { int id = snapshots[i].get(j); int id0 = snapshots[i].get(j == 0 ? snapshots[i].size() - 1 : j - 1); int id2 = snapshots[i].get(j == snapshots[i].size() - 1 ? 0 : j + 1); MovingParticle* p = factory->get(id); if (p == NULL) { return false; } p->setNeighbors(p, factory->get(id0), factory->get(id2)); } } //delete future particles from memory for (int i = 0; i < toremove.size(); ++i) { factory->remove(toremove[i]); } //factory->activeSet.clear(); for (int i = 0; i < toactivate.size(); ++i) { factory->activeSet.insert(toactivate[i]); } //recalculate positions for (set<MovingParticle*>::iterator it = factory->activeSet.begin(); it != factory->activeSet.end(); ++it) { MovingParticle* p = *it; p->p = p->project(time); p->time = time; } //recalculate events for (set<MovingParticle*>::iterator it = factory->activeSet.begin(); it != factory->activeSet.end(); ++it) { (*it)->event.type == UnknownEvent; (*it)->updateEvent(); } return true; }