Make dive planner more useful for closed circuit diving

Add a sample at time 0 to allow for a pO2 from the start of the dive.
Remember the last pO2 so it doesn't have to be repeated (and the right
thing happens for the planned part of the dive).

This still doesn't allow us to change the setpoint at a certain depth
(which would be analogous to being able to switch to a certain gas at a
certain depth in OC plans), but with this commit it's already usable.

This commit also fixes a couple of small bugs in commit b8ee3de870fa
("Dive planning for closed circuit rebreather") where a pO2 of 1.1 was
hardcoded in one place, throwing off all plan calculations and integer
math was used to calculate a floating point value (leading to most pO2
values actually used being 1.0).

Signed-off-by: Dirk Hohndel <dirk@hohndel.org>
This commit is contained in:
Dirk Hohndel 2013-01-28 19:54:05 -08:00
parent 9df9fc088d
commit 55b3fd12a8
2 changed files with 15 additions and 7 deletions

View file

@ -763,7 +763,7 @@ static int calculate_otu(struct dive *dive, struct divecomputer *dc)
struct sample *psample = sample - 1;
t = sample->time.seconds - psample->time.seconds;
if (sample->po2) {
po2 = sample->po2 / 1000;
po2 = sample->po2 / 1000.0;
} else {
int o2 = active_o2(dive, dc, sample->time);
po2 = o2 / 1000.0 * depth_to_mbar(sample->depth.mm, dive) / 1000.0;

View file

@ -112,7 +112,7 @@ double tissue_at_end(struct dive *dive, char **cached_datap)
for (j = t0; j < t1; j++) {
int depth = interpolate(lastdepth, sample->depth.mm, j - t0, t1 - t0);
tissue_tolerance = add_segment(depth_to_mbar(depth, dive) / 1000.0,
&dive->cylinder[gasidx].gasmix, 1, sample->po2 / 1000, dive);
&dive->cylinder[gasidx].gasmix, 1, sample->po2 / 1000.0, dive);
}
psample = sample;
t0 = t1;
@ -139,7 +139,7 @@ int time_at_last_depth(struct dive *dive, int next_stop, char **cached_data_p)
while (deco_allowed_depth(tissue_tolerance, surface_pressure, dive, 1) > next_stop) {
wait++;
tissue_tolerance = add_segment(depth_to_mbar(depth, dive) / 1000.0,
&dive->cylinder[gasidx].gasmix, 1, 1.1, dive);
&dive->cylinder[gasidx].gasmix, 1, sample->po2 / 1000.0, dive);
}
return wait;
}
@ -173,7 +173,9 @@ struct dive *create_dive_from_plan(struct diveplan *diveplan)
struct dive *dive;
struct divedatapoint *dp;
struct divecomputer *dc;
struct sample *sample;
int oldo2 = O2_IN_AIR, oldhe = 0;
int oldpo2 = 0;
int lasttime = 0;
if (!diveplan || !diveplan->dp)
@ -194,13 +196,15 @@ struct dive *create_dive_from_plan(struct diveplan *diveplan)
oldo2 = dp->o2;
oldhe = dp->he;
}
sample = prepare_sample(dc);
sample->po2 = dp->po2;
finish_sample(dc);
add_gas(dive, oldo2, oldhe);
while (dp) {
int o2 = dp->o2, he = dp->he;
int po2 = dp->po2;
int po2 = dp->po2 ? : oldpo2;
int time = dp->time;
int depth = dp->depth;
struct sample *sample;
if (time == 0) {
/* special entries that just inform the algorithm about
@ -224,14 +228,18 @@ struct dive *create_dive_from_plan(struct diveplan *diveplan)
/* Create sample */
sample = prepare_sample(dc);
/* set po2 at beginning of this segment */
/* and keep it valid for last sample - where it likely doesn't matter */
sample[-1].po2 = po2;
sample->po2 = po2;
sample->time.seconds = time;
sample->depth.mm = depth;
finish_sample(dc);
lasttime = time;
oldpo2 = po2;
dp = dp->next;
}
if (dc->samples == 0) {
if (dc->samples <= 1) {
/* not enough there yet to create a dive - most likely the first time is missing */
free(dive);
dive = NULL;
@ -1097,7 +1105,7 @@ static GtkWidget *add_gas_combobox_to_box(GtkWidget *box, const char *label, int
gas_model = gtk_list_store_new(1, G_TYPE_STRING);
add_string_list_entry("AIR", gas_model);
add_string_list_entry("EAN32", gas_model);
add_string_list_entry("EAN36 @ 1.6", gas_model);
add_string_list_entry("EAN36", gas_model);
}
combo = combo_box_with_model_and_entry(gas_model);
gtk_widget_add_events(combo, GDK_FOCUS_CHANGE_MASK);