00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include "IMDMgr.h"
00022 #include "imd.h"
00023 #include "IMDSimThread.h"
00024 #include "IMDSimBlocking.h"
00025 #include "utilities.h"
00026 #include "TextEvent.h"
00027 #include "Molecule.h"
00028
00029 IMDMgr::IMDMgr(VMDApp *vmdapp)
00030 : UIObject(vmdapp) {
00031 mol = NULL;
00032 sim = NULL;
00033 host = NULL;
00034 port = 0;
00035 Trate = 1;
00036 keep_rate = 0;
00037 frames_received = 0;
00038 energies = new IMDEnergies;
00039 want_command(Command::MOL_DEL);
00040 }
00041
00042 IMDMgr::~IMDMgr() {
00043 if (mol)
00044 detach();
00045 delete [] host;
00046 delete energies;
00047 }
00048
00049 int IMDMgr::connect(Molecule *m, const char *h, int p) {
00050 if (mol) {
00051 return 0;
00052 }
00053
00054 delete [] host;
00055 host = stringdup(h);
00056 port = p;
00057
00058 #ifdef VMDTHREADS
00059 sim = new IMDSimThread(h, p);
00060 #else
00061 sim = new IMDSimBlocking(h, p);
00062 #endif
00063 if (!sim->isConnected()) {
00064 delete sim;
00065 sim = 0;
00066 return 0;
00067 }
00068 mol = m;
00069 frames_received = 0;
00070 return 1;
00071 }
00072
00073 void IMDMgr::pause() {
00074 if (sim) sim->pause();
00075 }
00076
00077 void IMDMgr::unpause() {
00078 if (sim) sim->unpause();
00079 }
00080
00081 void IMDMgr::togglepause() {
00082 if (!sim) return;
00083 int state = sim->getSimState();
00084 if (state == IMDSim::IMDRUNNING)
00085 sim->pause();
00086 else if (state == IMDSim::IMDPAUSED)
00087 sim->unpause();
00088 }
00089
00090 void IMDMgr::detach() {
00091 if (sim) sim->detach();
00092 delete sim;
00093 sim = NULL;
00094 mol = NULL;
00095 }
00096
00097 void IMDMgr::kill() {
00098 if (sim) sim->kill();
00099 delete sim;
00100 sim = NULL;
00101 mol = NULL;
00102 }
00103
00104 int IMDMgr::send_forces(int n, const int *ind, const float *force) {
00105 if (!sim) return 0;
00106
00107
00108 int *tmpind = new int[n];
00109 float *tmpforce = new float[3*n];
00110 memcpy(tmpind, ind, n*sizeof(int));
00111 memcpy(tmpforce, force, 3*n*sizeof(float));
00112 sim->send_forces(n, tmpind, tmpforce);
00113 delete [] tmpind;
00114 delete [] tmpforce;
00115 return 1;
00116 }
00117
00118 void IMDMgr::set_trans_rate(int rate) {
00119 if (rate > 0) {
00120 Trate = rate;
00121 if (sim) sim->set_transrate(rate);
00122 }
00123 }
00124
00125 void IMDMgr::set_keep_rate(int rate) {
00126 if (rate >= 0) {
00127 keep_rate = rate;
00128 }
00129 }
00130
00131 int IMDMgr::check_event() {
00132 if (sim && !sim->isConnected()) {
00133 detach();
00134 msgInfo << "IMD connection ended unexpectedly; connection terminated."
00135 << sendmsg;
00136 }
00137 if (!sim) return 0;
00138
00139 sim->update();
00140 if (sim->next_ts_available()) {
00141 Timestep *newts = mol->get_last_frame();
00142 int do_save = (!newts || frames_received < 1 ||
00143 (keep_rate > 0 && !(frames_received % keep_rate)));
00144 if (do_save)
00145 newts = new Timestep(mol->nAtoms);
00146
00147 float *pos = newts->pos;
00148 sim->get_next_ts(pos, energies);
00149
00150 newts->timesteps = energies->tstep;
00151 newts->energy[TSE_BOND] = energies->Ebond;
00152 newts->energy[TSE_ANGLE] = energies->Eangle;
00153 newts->energy[TSE_DIHE] = energies->Edihe;
00154 newts->energy[TSE_IMPR] = energies->Eimpr;
00155 newts->energy[TSE_VDW] = energies->Evdw;
00156 newts->energy[TSE_COUL] = energies->Eelec;
00157 newts->energy[TSE_HBOND] = 0;
00158 newts->energy[TSE_TEMP] = energies->T;
00159 newts->energy[TSE_PE] = energies->Epot;
00160 newts->energy[TSE_TOTAL] = energies->Etot;
00161 newts->energy[TSE_KE] = energies->Etot - energies->Epot;
00162
00163 if (do_save) {
00164 mol->append_frame(newts);
00165 } else {
00166 mol->force_recalc(DrawMolItem::MOL_REGEN);
00167 }
00168 frames_received++;
00169 runcommand(new TimestepEvent(mol->id(), mol->numframes()-1));
00170 }
00171 return 0;
00172 }
00173
00174 int IMDMgr::act_on_command(int type, Command *cmd) {
00175 if (type == Command::MOL_DEL) {
00176 detach();
00177 mol = NULL;
00178 }
00179 return 0;
00180 }
00181