Correctly track gases when manually adding and then editing dives

The code had quite a few odd special cases that may have been left-overs
from the old Gtk algorithm. With this the gas is actually in the dive plan
node where it's use starts. And we maintain the gas correctly between
multiple edit sessions.

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
This commit is contained in:
Dirk Hohndel 2013-11-08 21:22:59 +09:00
parent 1578c1edb2
commit 8941e8677e
2 changed files with 48 additions and 26 deletions

View file

@ -233,6 +233,7 @@ struct dive *create_dive_from_plan(struct diveplan *diveplan, const char **error
int time = dp->time; int time = dp->time;
int depth = dp->depth; int depth = dp->depth;
#if 0 // the new planner doesn't use that any more
if (time == 0) { if (time == 0) {
/* special entries that just inform the algorithm about /* special entries that just inform the algorithm about
* additional gases that are available */ * additional gases that are available */
@ -241,6 +242,7 @@ struct dive *create_dive_from_plan(struct diveplan *diveplan, const char **error
dp = dp->next; dp = dp->next;
continue; continue;
} }
#endif
if (!o2 && !he) { if (!o2 && !he) {
o2 = oldo2; o2 = oldo2;
he = oldhe; he = oldhe;
@ -256,14 +258,14 @@ struct dive *create_dive_from_plan(struct diveplan *diveplan, const char **error
/* Create new gas, and gas change event if necessary; /* Create new gas, and gas change event if necessary;
* Sadly, we inherited our gaschange event from libdivecomputer which only * Sadly, we inherited our gaschange event from libdivecomputer which only
* support percentage values, so round the entries */ * support percentage values, so round the entries */
if (o2 != oldo2 || he != oldhe) { if (time == 0 || o2 != oldo2 || he != oldhe) {
int plano2 = (o2 + 5) / 10 * 10; int plano2 = (o2 + 5) / 10 * 10;
int planhe = (he + 5) / 10 * 10; int planhe = (he + 5) / 10 * 10;
int value; int value;
if (add_gas(dive, plano2, planhe) < 0) if (add_gas(dive, plano2, planhe) < 0)
goto gas_error_exit; goto gas_error_exit;
value = (plano2 / 10) | ((planhe / 10) << 16); value = (plano2 / 10) | ((planhe / 10) << 16);
add_event(dc, lasttime, 25, 0, value, "gaschange"); // SAMPLE_EVENT_GASCHANGE2 add_event(dc, time, 25, 0, value, "gaschange"); // SAMPLE_EVENT_GASCHANGE2
oldo2 = o2; oldhe = he; oldo2 = o2; oldhe = he;
} }
/* Create sample */ /* Create sample */

View file

@ -439,7 +439,6 @@ void DivePlannerPointsModel::loadFromDive(dive* d)
for(int i = 0; i < d->dc.samples-1; i++){ for(int i = 0; i < d->dc.samples-1; i++){
backupSamples.push_back( d->dc.sample[i]); backupSamples.push_back( d->dc.sample[i]);
} }
save_dive(stdout, current_dive); save_dive(stdout, current_dive);
save_dive(stdout, backupDive); save_dive(stdout, backupDive);
Q_FOREACH(const sample &s, backupSamples){ Q_FOREACH(const sample &s, backupSamples){
@ -495,9 +494,11 @@ void DivePlannerGraphics::drawProfile()
QPointF p1 = (i == 0) ? QPointF(timeLine->posAtValue(0), depthLine->posAtValue(0)) : handles[i-1]->pos(); QPointF p1 = (i == 0) ? QPointF(timeLine->posAtValue(0), depthLine->posAtValue(0)) : handles[i-1]->pos();
QPointF p2 = handles[i]->pos(); QPointF p2 = handles[i]->pos();
QLineF line(p1, p2); QLineF line(p1, p2);
QPointF pos = line.pointAt(0.5); if (i > 0) {
gases[i]->setPos(pos); QPointF pos = line.pointAt(0.5);
gases[i]->setText( strForAir(dp)); gases[i]->setPos(pos);
gases[i]->setText(strForAir(plannerModel->at(i-1)));
}
} }
// (re-) create the profile with different colors for segments that were // (re-) create the profile with different colors for segments that were
@ -965,10 +966,15 @@ QVariant DivePlannerPointsModel::data(const QModelIndex& index, int role) const
if(role == Qt::DisplayRole) { if(role == Qt::DisplayRole) {
divedatapoint p = divepoints.at(index.row()); divedatapoint p = divepoints.at(index.row());
switch(index.column()) { switch(index.column()) {
case CCSETPOINT: return p.po2; case CCSETPOINT: return p.po2;
case DEPTH: return rint(get_depth_units(p.depth, NULL, NULL)); case DEPTH: return rint(get_depth_units(p.depth, NULL, NULL));
case DURATION: return p.time / 60; case DURATION: return p.time / 60;
case GAS: return strForAir(p); case GAS:
if (index.row() > 0) {
p = divepoints.at(index.row() - 1);
return strForAir(p);
}
return "";
} }
} else if (role == Qt::DecorationRole) { } else if (role == Qt::DecorationRole) {
switch(index.column()) { switch(index.column()) {
@ -985,23 +991,30 @@ bool DivePlannerPointsModel::setData(const QModelIndex& index, const QVariant& v
if(role == Qt::EditRole) { if(role == Qt::EditRole) {
divedatapoint& p = divepoints[index.row()]; divedatapoint& p = divepoints[index.row()];
switch(index.column()) { switch(index.column()) {
case DEPTH: p.depth = units_to_depth(value.toInt()); break; case DEPTH: p.depth = units_to_depth(value.toInt()); break;
case DURATION: p.time = value.toInt() * 60; break; case DURATION: p.time = value.toInt() * 60; break;
case CCSETPOINT:{ case CCSETPOINT: {
int po2 = 0; int po2 = 0;
QByteArray gasv = value.toByteArray(); QByteArray gasv = value.toByteArray();
if (validate_po2(gasv.data(), &po2)) if (validate_po2(gasv.data(), &po2))
p.po2 = po2; p.po2 = po2;
} break;
case GAS: {
int o2 = 0;
int he = 0;
QByteArray gasv = value.toByteArray();
if (validate_gas(gasv.data(), &o2, &he)) {
p.o2 = o2;
p.he = he;
}break;
} }
break;
case GAS: {
if (index.row() == 0) {
qDebug() << "how can index.row be 0???";
return false;
}
divedatapoint& pp = divepoints[index.row() - 1];
int o2 = 0;
int he = 0;
QByteArray gasv = value.toByteArray();
if (validate_gas(gasv.data(), &o2, &he)) {
pp.o2 = o2;
pp.he = he;
}
}
break;
} }
editStop(index.row(), p); editStop(index.row(), p);
} }
@ -1107,6 +1120,13 @@ int DivePlannerPointsModel::addStop(int milimeters, int minutes, int o2, int he,
// check if there's already a new stop before this one: // check if there's already a new stop before this one:
for (int i = 0; i < divepoints.count(); i++) { for (int i = 0; i < divepoints.count(); i++) {
const divedatapoint& dp = divepoints.at(i); const divedatapoint& dp = divepoints.at(i);
if (dp.time == minutes) {
row = i;
beginRemoveRows(QModelIndex(), row, row);
divepoints.remove(row);
endRemoveRows();
break;
}
if (dp.time > minutes ) { if (dp.time > minutes ) {
row = i; row = i;
break; break;