summaryrefslogtreecommitdiffstats
path: root/core
diff options
context:
space:
mode:
Diffstat (limited to 'core')
-rw-r--r--core/btdiscovery.cpp5
-rw-r--r--core/dive.c158
-rw-r--r--core/dive.h28
-rw-r--r--core/divelist.c149
-rw-r--r--core/divelist.h5
-rw-r--r--core/downloadfromdcthread.cpp23
-rw-r--r--core/downloadfromdcthread.h5
-rw-r--r--core/libdivecomputer.c2
-rw-r--r--core/qthelper.cpp14
-rw-r--r--core/statistics.c1
-rw-r--r--core/statistics.h1
-rw-r--r--core/subsurface-qt/DiveObjectHelper.cpp43
12 files changed, 119 insertions, 315 deletions
diff --git a/core/btdiscovery.cpp b/core/btdiscovery.cpp
index 6ec4bba7f..207dfacf8 100644
--- a/core/btdiscovery.cpp
+++ b/core/btdiscovery.cpp
@@ -74,6 +74,11 @@ static dc_descriptor_t *getDeviceType(QString btName)
product = "i770R";
}
+ if (btName.contains(QRegularExpression("^ER\\d{6}$"))) {
+ vendor = "Oceanic";
+ product = "Pro Plus X";
+ }
+
if (!vendor.isEmpty() && !product.isEmpty())
return descriptorLookup.value(vendor + product);
diff --git a/core/dive.c b/core/dive.c
index 47143aaa3..49431bffe 100644
--- a/core/dive.c
+++ b/core/dive.c
@@ -3357,70 +3357,6 @@ void dump_taglist(const char *intro, struct tag_entry *tl)
fprintf(stderr, "\n");
}
-// count the dives where the tag list contains the given tag
-int count_dives_with_tag(const char *tag)
-{
- int i, counter = 0;
- struct dive *d;
-
- for_each_dive (i, d) {
- if (empty_string(tag)) {
- // count dives with no tags
- if (d->tag_list == NULL)
- counter++;
- } else if (taglist_contains(d->tag_list, tag)) {
- counter++;
- }
- }
- return counter;
-}
-
-extern bool string_sequence_contains(const char *string_sequence, const char *text);
-
-// count the dives where the person is included in the comma separated string sequences of buddies or divemasters
-int count_dives_with_person(const char *person)
-{
- int i, counter = 0;
- struct dive *d;
-
- for_each_dive (i, d) {
- if (empty_string(person)) {
- // solo dive
- if (empty_string(d->buddy) && empty_string(d->divemaster))
- counter++;
- } else if (string_sequence_contains(d->buddy, person) || string_sequence_contains(d->divemaster, person)) {
- counter++;
- }
- }
- return counter;
-}
-
-// count the dives with exactly the location
-int count_dives_with_location(const char *location)
-{
- int i, counter = 0;
- struct dive *d;
-
- for_each_dive (i, d) {
- if (same_string(get_dive_location(d), location))
- counter++;
- }
- return counter;
-}
-
-// count the dives with exactly the suit
-int count_dives_with_suit(const char *suit)
-{
- int i, counter = 0;
- struct dive *d;
-
- for_each_dive (i, d) {
- if (same_string(d->suit, suit))
- counter++;
- }
- return counter;
-}
-
/*
* Merging two dives can be subtle, because there's two different ways
* of merging:
@@ -3686,17 +3622,6 @@ static int split_dive_at(const struct dive *dive, int a, int b, struct dive **ou
return nr;
}
-static void finish_split(int nr, struct dive *old, struct dive *d1, struct dive *d2)
-{
- if (old->divetrip) {
- add_dive_to_trip(d1, old->divetrip);
- add_dive_to_trip(d2, old->divetrip);
- }
- delete_single_dive(nr);
- add_single_dive(nr, d1);
- add_single_dive(nr + 1, d2);
-}
-
/* in freedive mode we split for as little as 10 seconds on the surface,
* otherwise we use a minute */
static bool should_split(const struct divecomputer *dc, int t1, int t2)
@@ -3716,7 +3641,7 @@ static bool should_split(const struct divecomputer *dc, int t1, int t2)
*
* In other words, this is a (simplified) reversal of the dive merging.
*/
-int split_dive_dont_insert(const struct dive *dive, struct dive **new1, struct dive **new2)
+int split_dive(const struct dive *dive, struct dive **new1, struct dive **new2)
{
int i;
int at_surface, surface_start;
@@ -3758,16 +3683,7 @@ int split_dive_dont_insert(const struct dive *dive, struct dive **new1, struct d
return -1;
}
-void split_dive(struct dive *dive)
-{
- int nr;
- struct dive *new1, *new2;
-
- if ((nr = split_dive_dont_insert(dive, &new1, &new2)) >= 0)
- finish_split(nr, dive, new1, new2);
-}
-
-int split_dive_at_time_dont_insert(const struct dive *dive, duration_t time, struct dive **new1, struct dive **new2)
+int split_dive_at_time(const struct dive *dive, duration_t time, struct dive **new1, struct dive **new2)
{
int i = 0;
struct sample *sample = dive->dc.sample;
@@ -3783,15 +3699,6 @@ int split_dive_at_time_dont_insert(const struct dive *dive, duration_t time, str
return split_dive_at(dive, i, i - 1, new1, new2);
}
-void split_dive_at_time(struct dive *dive, duration_t time)
-{
- int nr;
- struct dive *new1, *new2;
-
- if ((nr = split_dive_at_time_dont_insert(dive, time, &new1, &new2)) >= 0)
- finish_split(nr, dive, new1, new2);
-}
-
/*
* "dc_maxtime()" is how much total time this dive computer
* has for this dive. Note that it can differ from "duration"
@@ -4004,20 +3911,51 @@ static bool new_picture_for_dive(struct dive *d, const char *filename)
return true;
}
+/* Return distance of timestamp to time of dive. Result is always positive, 0 means during dive. */
+static timestamp_t time_from_dive(const struct dive *d, timestamp_t timestamp)
+{
+ timestamp_t end_time = dive_endtime(d);
+ if (timestamp < d->when)
+ return d->when - timestamp;
+ else if (timestamp > end_time)
+ return timestamp - end_time;
+ else
+ return 0;
+}
+
// only add pictures that have timestamps between 30 minutes before the dive and
// 30 minutes after the dive ends
#define D30MIN (30 * 60)
-bool dive_check_picture_time(const struct dive *d, int shift_time, timestamp_t timestamp)
+static bool dive_check_picture_time(const struct dive *d, timestamp_t timestamp)
{
- offset_t offset;
- if (timestamp) {
- offset.seconds = timestamp - d->when + shift_time;
- if (offset.seconds > -D30MIN && offset.seconds < dive_totaltime(d) + D30MIN) {
- // this picture belongs to this dive
- return true;
+ return time_from_dive(d, timestamp) < D30MIN;
+}
+
+/* Return dive closest selected dive to given timestamp or NULL if no dives are selected. */
+static struct dive *nearest_selected_dive(timestamp_t timestamp)
+{
+ struct dive *d, *res = NULL;
+ int i;
+ timestamp_t offset, min = 0;
+
+ for_each_dive(i, d) {
+ if (!d->selected)
+ continue;
+ offset = time_from_dive(d, timestamp);
+ if (!res || offset < min) {
+ res = d;
+ min = offset;
}
+
+ /* We suppose that dives are sorted chronologically. Thus
+ * if the offset starts to increase, we can end. This ignores
+ * pathological cases such as overlapping dives. In such a
+ * case the user will have to add pictures manually.
+ */
+ if (offset == 0 || offset > min)
+ break;
}
- return false;
+ return res;
}
bool picture_check_valid_time(timestamp_t timestamp, int shift_time)
@@ -4026,18 +3964,26 @@ bool picture_check_valid_time(timestamp_t timestamp, int shift_time)
struct dive *dive;
for_each_dive (i, dive)
- if (dive->selected && dive_check_picture_time(dive, shift_time, timestamp))
+ if (dive->selected && dive_check_picture_time(dive, timestamp + shift_time))
return true;
return false;
}
-void dive_create_picture(struct dive *dive, const char *filename, int shift_time, bool match_all)
+void create_picture(const char *filename, int shift_time, bool match_all)
{
struct metadata metadata;
+ struct dive *dive;
+ timestamp_t timestamp;
+
get_metadata(filename, &metadata);
+ timestamp = metadata.timestamp + shift_time;
+ dive = nearest_selected_dive(timestamp);
+
+ if (!dive)
+ return;
if (!new_picture_for_dive(dive, filename))
return;
- if (!match_all && !dive_check_picture_time(dive, shift_time, metadata.timestamp))
+ if (!match_all && !dive_check_picture_time(dive, timestamp))
return;
struct picture *picture = alloc_picture();
diff --git a/core/dive.h b/core/dive.h
index 92bb1bb33..6bc0f6fae 100644
--- a/core/dive.h
+++ b/core/dive.h
@@ -227,12 +227,7 @@ void taglist_cleanup(struct tag_entry **tag_list);
void taglist_init_global();
void taglist_free(struct tag_entry *tag_list);
-
bool taglist_contains(struct tag_entry *tag_list, const char *tag);
-int count_dives_with_tag(const char *tag);
-int count_dives_with_person(const char *person);
-int count_dives_with_location(const char *location);
-int count_dives_with_suit(const char *suit);
struct extra_data {
const char *key;
@@ -278,10 +273,10 @@ struct divecomputer {
#define W_IDX_PRIMARY 0
#define W_IDX_SECONDARY 1
-struct dive_table {
+typedef struct dive_table {
int nr, allocated;
struct dive **dives;
-};
+} dive_table_t;
typedef struct dive_trip
{
@@ -376,8 +371,7 @@ struct picture {
extern struct picture *alloc_picture();
extern void free_picture(struct picture *picture);
-extern bool dive_check_picture_time(const struct dive *d, int shift_time, timestamp_t timestamp);
-extern void dive_create_picture(struct dive *d, const char *filename, int shift_time, bool match_all);
+extern void create_picture(const char *filename, int shift_time, bool match_all);
extern void dive_add_picture(struct dive *d, struct picture *newpic);
extern bool dive_remove_picture(struct dive *d, const char *filename);
extern unsigned int dive_get_picture_count(struct dive *d);
@@ -425,7 +419,7 @@ extern const struct units SI_units, IMPERIAL_units;
extern const struct units *get_units(void);
extern int run_survey, verbose, quit, force_root;
-extern struct dive_table dive_table, downloadTable;
+extern struct dive_table dive_table;
extern struct dive displayed_dive;
extern unsigned int dc_number;
extern struct dive *current_dive;
@@ -553,10 +547,8 @@ extern void fixup_dc_duration(struct divecomputer *dc);
extern int dive_getUniqID();
extern unsigned int dc_airtemp(const struct divecomputer *dc);
extern unsigned int dc_watertemp(const struct divecomputer *dc);
-extern int split_dive_dont_insert(const struct dive *dive, struct dive **new1, struct dive **new2);
-extern void split_dive(struct dive *);
-extern int split_dive_at_time_dont_insert(const struct dive *dive, duration_t time, struct dive **new1, struct dive **new2);
-extern void split_dive_at_time(struct dive *dive, duration_t time);
+extern int split_dive(const struct dive *dive, struct dive **new1, struct dive **new2);
+extern int split_dive_at_time(const struct dive *dive, duration_t time, struct dive **new1, struct dive **new2);
extern struct dive *merge_dives(const struct dive *a, const struct dive *b, int offset, bool prefer_downloaded, struct dive_trip **trip);
extern struct dive *try_to_merge(struct dive *a, struct dive *b, bool prefer_downloaded);
extern struct event *clone_event(const struct event *src_ev);
@@ -759,10 +751,14 @@ extern void average_max_depth(struct diveplan *dive, int *avg_depth, int *max_de
#ifdef __cplusplus
}
-/* Make pointers to dive and dive_trip "Qt metatypes" so that they can
- * be passed through QVariants. */
+/* Make pointers to dive, dive_trip and dive_table "Qt metatypes" so that they can
+ * be passed through QVariants and through QML.
+ * Note: we have to use the typedef "dive_table_t" instead of "struct dive_table",
+ * because MOC removes the "struct", but dive_table is already the name of a global
+ * variable, leading to compilation errors. */
Q_DECLARE_METATYPE(struct dive *);
Q_DECLARE_METATYPE(struct dive_trip *);
+Q_DECLARE_METATYPE(dive_table_t *);
#endif
diff --git a/core/divelist.c b/core/divelist.c
index ee7986466..4659261cd 100644
--- a/core/divelist.c
+++ b/core/divelist.c
@@ -19,7 +19,6 @@
* void insert_trip(dive_trip_t *dive_trip_p)
* void unregister_trip(dive_trip_t *trip)
* void free_trip(dive_trip_t *trip)
- * void remove_dive_from_trip(struct dive *dive)
* void remove_dive_from_trip(struct dive *dive, bool was_autogen)
* void add_dive_to_trip(struct dive *dive, dive_trip_t *trip)
* dive_trip_t *create_and_hookup_trip_from_dive(struct dive *dive)
@@ -32,12 +31,10 @@
* void delete_single_dive(int idx)
* void add_dive_to_table(struct dive_table *table, int idx, struct dive *dive)
* void add_single_dive(int idx, struct dive *dive)
- * struct dive *merge_two_dives(struct dive *a, struct dive *b)
* void select_dive(struct dive *dive)
* void deselect_dive(struct dive *dive)
* void mark_divelist_changed(int changed)
* int unsaved_changes()
- * void remove_autogen_trips()
* bool dive_less_than(const struct dive *a, const struct dive *b)
* bool trip_less_than(const struct dive_trip *a, const struct dive_trip *b)
* bool dive_or_trip_less_than(struct dive_or_trip a, struct dive_or_trip b)
@@ -77,9 +74,6 @@ dive_trip_t *dive_trip_list;
unsigned int amount_selected;
-// We need to stop using globals, really.
-struct dive_table downloadTable;
-
#if DEBUG_SELECTION_TRACKING
void dump_selection(void)
{
@@ -912,11 +906,14 @@ void remove_dive_from_trip(struct dive *dive, short was_autogen)
delete_trip(trip);
}
+/* Add dive to a trip. Caller is responsible for removing dive
+ * from trip beforehand. */
void add_dive_to_trip(struct dive *dive, dive_trip_t *trip)
{
if (dive->divetrip == trip)
return;
- remove_dive_from_trip(dive, false);
+ if (dive->divetrip)
+ fprintf(stderr, "Warning: adding dive to trip that has trip set\n");
add_dive_to_table(&trip->dives, -1, dive);
dive->divetrip = trip;
}
@@ -1075,16 +1072,15 @@ void delete_dive_from_table(struct dive_table *table, int idx)
unregister_dive_from_table(table, idx);
}
-/* this removes a dive from the dive table and trip-list but doesn't
- * free the resources associated with the dive. It returns a pointer
- * to the unregistered dive. The returned dive has the selection-
- * and hidden-flags cleared. */
+/* This removes a dive from the global dive table but doesn't free the
+ * resources associated with the dive. The caller must removed the dive
+ * from the trip-list. Returns a pointer to the unregistered dive.
+ * The unregistered dive has the selection- and hidden-flags cleared. */
struct dive *unregister_dive(int idx)
{
struct dive *dive = get_dive(idx);
if (!dive)
return NULL; /* this should never happen */
- remove_dive_from_trip(dive, false);
unregister_dive_from_table(&dive_table, idx);
if (dive->selected)
amount_selected--;
@@ -1092,8 +1088,8 @@ struct dive *unregister_dive(int idx)
return dive;
}
-/* this implements the mechanics of removing the dive from the table,
- * but doesn't deal with updating dive trips, etc */
+/* this implements the mechanics of removing the dive from the global
+ * dive table and the trip, but doesn't deal with updating dive trips, etc */
void delete_single_dive(int idx)
{
struct dive *dive = get_dive(idx);
@@ -1101,8 +1097,8 @@ void delete_single_dive(int idx)
return; /* this should never happen */
if (dive->selected)
deselect_dive(dive);
- dive = unregister_dive(idx);
- free_dive(dive);
+ remove_dive_from_trip(dive, false);
+ delete_dive_from_table(&dive_table, idx);
}
struct dive **grow_dive_table(struct dive_table *table)
@@ -1184,87 +1180,6 @@ bool consecutive_selected()
return consecutive;
}
-/*
- * Merge two dives. 'a' is always before 'b' in the dive list
- * (and thus in time).
- */
-struct dive *merge_two_dives(struct dive *a, struct dive *b)
-{
- struct dive *res;
- int i, j, nr, nrdiff;
- int id;
-
- if (!a || !b)
- return NULL;
-
- id = a->id;
- i = get_divenr(a);
- j = get_divenr(b);
- if (i < 0 || j < 0)
- // something is wrong with those dives. Bail
- return NULL;
- res = merge_dives(a, b, b->when - a->when, false, NULL);
- if (!res)
- return NULL;
-
- /*
- * If 'a' and 'b' were numbered, and in proper order,
- * then the resulting dive will get the first number,
- * and the subsequent dives will be renumbered by the
- * difference.
- *
- * So if you had a dive list 1 3 6 7 8, and you
- * merge 1 and 3, the resulting numbered list will
- * be 1 4 5 6, because we assume that there were
- * some missing dives (originally dives 4 and 5),
- * that now will still be missing (dives 2 and 3
- * in the renumbered world).
- *
- * Obviously the normal case is that everything is
- * consecutive, and the difference will be 1, so the
- * above example is not supposed to be normal.
- */
- nrdiff = 0;
- nr = a->number;
- if (a->number && b->number > a->number) {
- res->number = nr;
- nrdiff = b->number - nr;
- }
-
- add_single_dive(i, res);
- delete_single_dive(i + 1);
- delete_single_dive(j);
- // now make sure that we keep the id of the first dive.
- // why?
- // because this way one of the previously selected ids is still around
- res->id = id;
-
- // renumber dives from merged one in advance by difference between
- // merged dives numbers. Do not renumber if actual number is zero.
- for (; j < dive_table.nr; j++) {
- struct dive *dive = dive_table.dives[j];
- int newnr;
-
- if (!dive->number)
- continue;
- newnr = dive->number - nrdiff;
-
- /*
- * Don't renumber stuff that isn't in order!
- *
- * So if the new dive number isn't larger than the
- * previous dive number, just stop here.
- */
- if (newnr <= nr)
- break;
- dive->number = newnr;
- nr = newnr;
- }
-
- mark_divelist_changed(true);
- return res;
-}
-
void select_dive(struct dive *dive)
{
if (!dive)
@@ -1336,34 +1251,15 @@ void filter_dive(struct dive *d, bool shown)
}
-/* This only gets called with non-NULL trips.
- * It does not combine notes or location, just picks the first one
- * (or the second one if the first one is empty */
-void combine_trips(struct dive_trip *trip_a, struct dive_trip *trip_b)
-{
- if (empty_string(trip_a->location) && trip_b->location) {
- free(trip_a->location);
- trip_a->location = strdup(trip_b->location);
- }
- if (empty_string(trip_a->notes) && trip_b->notes) {
- free(trip_a->notes);
- trip_a->notes = strdup(trip_b->notes);
- }
- /* this also removes the dives from trip_b and eventually
- * calls delete_trip(trip_b) when the last dive has been moved */
- while (trip_b->dives.nr > 0)
- add_dive_to_trip(trip_b->dives.dives[0], trip_a);
-}
-
/* Out of two strings, copy the string that is not empty (if any). */
static char *copy_non_empty_string(const char *a, const char *b)
{
return copy_string(empty_string(b) ? a : b);
}
-/* Combine trips new. This combines two trips, generating a
+/* This combines the information of two trips, generating a
* new trip. To support undo, we have to preserve the old trips. */
-dive_trip_t *combine_trips_create(struct dive_trip *trip_a, struct dive_trip *trip_b)
+dive_trip_t *combine_trips(struct dive_trip *trip_a, struct dive_trip *trip_b)
{
dive_trip_t *trip;
@@ -1387,19 +1283,6 @@ int unsaved_changes()
return dive_list_changed;
}
-void remove_autogen_trips()
-{
- int i;
- struct dive *dive;
-
- for_each_dive(i, dive) {
- dive_trip_t *trip = dive->divetrip;
-
- if (trip && trip->autogen)
- remove_dive_from_trip(dive, true);
- }
-}
-
/*
* When adding dives to the dive table, we try to renumber
* the new dives based on any old dives in the dive table.
@@ -1522,10 +1405,8 @@ static bool try_to_merge_into(struct dive *dive_to_add, int idx, bool prefer_imp
merged->id = old_dive->id;
merged->selected = old_dive->selected;
dive_table.dives[idx] = merged;
- if (trip) {
+ if (trip)
remove_dive_from_trip(old_dive, false);
- add_dive_to_trip(merged, trip);
- }
free_dive(old_dive);
remove_dive_from_trip(dive_to_add, false);
free_dive(dive_to_add);
diff --git a/core/divelist.h b/core/divelist.h
index 11fa75f50..ce4943660 100644
--- a/core/divelist.h
+++ b/core/divelist.h
@@ -14,7 +14,6 @@ struct dive;
extern void update_cylinder_related_info(struct dive *);
extern void mark_divelist_changed(bool);
extern int unsaved_changes(void);
-extern void remove_autogen_trips(void);
extern int init_decompression(struct deco_state *ds, struct dive *dive);
/* divelist core logic functions */
@@ -37,15 +36,13 @@ extern dive_trip_t *create_and_hookup_trip_from_dive(struct dive *dive);
extern dive_trip_t *get_dives_to_autogroup(int start, int *from, int *to, bool *allocated);
extern dive_trip_t *get_trip_for_new_dive(struct dive *new_dive, bool *allocated);
extern void autogroup_dives(void);
-extern struct dive *merge_two_dives(struct dive *a, struct dive *b);
extern bool consecutive_selected();
extern void select_dive(struct dive *dive);
extern void deselect_dive(struct dive *dive);
extern void select_dives_in_trip(struct dive_trip *trip);
extern void deselect_dives_in_trip(struct dive_trip *trip);
extern void filter_dive(struct dive *d, bool shown);
-extern void combine_trips(struct dive_trip *trip_a, struct dive_trip *trip_b);
-extern dive_trip_t *combine_trips_create(struct dive_trip *trip_a, struct dive_trip *trip_b);
+extern dive_trip_t *combine_trips(struct dive_trip *trip_a, struct dive_trip *trip_b);
extern struct dive *first_selected_dive();
extern struct dive *last_selected_dive();
extern bool is_trip_before_after(const struct dive *dive, bool before);
diff --git a/core/downloadfromdcthread.cpp b/core/downloadfromdcthread.cpp
index 8e937346d..2fdebf129 100644
--- a/core/downloadfromdcthread.cpp
+++ b/core/downloadfromdcthread.cpp
@@ -24,7 +24,6 @@ static QString str_error(const char *fmt, ...)
return str;
}
-
static void updateRememberedDCs()
{
QString current = qPrefDiveComputer::vendor() + " - " + qPrefDiveComputer::product() + " - " + qPrefDiveComputer::device();
@@ -60,9 +59,9 @@ static void updateRememberedDCs()
}
-DownloadThread::DownloadThread()
+DownloadThread::DownloadThread() : downloadTable({ 0 }),
+ m_data(DCDeviceData::instance())
{
- m_data = DCDeviceData::instance();
}
void DownloadThread::run()
@@ -81,7 +80,7 @@ void DownloadThread::run()
internalData->devname = "ftdi";
#endif
qDebug() << "Starting download from " << (internalData->bluetooth_mode ? "BT" : internalData->devname);
- downloadTable.nr = 0;
+ clear_table(&downloadTable);
Q_ASSERT(internalData->download_table != nullptr);
const char *errorText;
@@ -254,7 +253,6 @@ void show_computer_list()
qDebug() << msg;
}
}
-DCDeviceData *DCDeviceData::m_instance = NULL;
DCDeviceData::DCDeviceData()
{
@@ -276,18 +274,12 @@ DCDeviceData::DCDeviceData()
#else
data.libdc_log = false;
#endif
- if (m_instance) {
- qDebug() << "already have an instance of DCDevieData";
- return;
- }
- m_instance = this;
}
DCDeviceData *DCDeviceData::instance()
{
- if (!m_instance)
- m_instance = new DCDeviceData;
- return m_instance;
+ static DCDeviceData self;
+ return &self;
}
QStringList DCDeviceData::getProductListFromVendor(const QString &vendor)
@@ -310,6 +302,11 @@ DCDeviceData *DownloadThread::data()
return m_data;
}
+struct dive_table *DownloadThread::table()
+{
+ return &downloadTable;
+}
+
QString DCDeviceData::vendor() const
{
return data.vendor;
diff --git a/core/downloadfromdcthread.h b/core/downloadfromdcthread.h
index 3e2d7ddc0..b380a88a1 100644
--- a/core/downloadfromdcthread.h
+++ b/core/downloadfromdcthread.h
@@ -6,6 +6,7 @@
#include <QHash>
#include <QLoggingCategory>
+#include "dive.h"
#include "libdivecomputer.h"
#include "connectionlistmodel.h"
#if BT_SUPPORT
@@ -51,7 +52,6 @@ public:
void setSaveDump(bool dumpMode);
void setSaveLog(bool saveLog);
private:
- static DCDeviceData *m_instance;
device_data_t data;
// Bluetooth name is managed outside of libdivecomputer
@@ -60,15 +60,18 @@ private:
class DownloadThread : public QThread {
Q_OBJECT
+ Q_PROPERTY(dive_table_t *table READ table CONSTANT)
public:
DownloadThread();
void run() override;
DCDeviceData *data();
+ struct dive_table *table();
QString error;
private:
+ struct dive_table downloadTable;
DCDeviceData *m_data;
};
diff --git a/core/libdivecomputer.c b/core/libdivecomputer.c
index a2e2890b8..4d2d29bad 100644
--- a/core/libdivecomputer.c
+++ b/core/libdivecomputer.c
@@ -1387,7 +1387,7 @@ const char *do_libdivecomputer_import(device_data_t *data)
/* TODO: Show the logfile to the user on error. */
dc_device_close(data->device);
data->device = NULL;
- if (!downloadTable.nr)
+ if (!data->download_table->nr)
dev_info(data, translate("gettextFromC", "No new dives downloaded from dive computer"));
}
dc_iostream_close(data->iostream);
diff --git a/core/qthelper.cpp b/core/qthelper.cpp
index 8fbaa31af..d47a39fdf 100644
--- a/core/qthelper.cpp
+++ b/core/qthelper.cpp
@@ -362,20 +362,6 @@ extern "C" void copy_image_and_overwrite(const char *cfileName, const char *path
qDebug() << "copy of" << fileName << "to" << newName << "failed";
}
-extern "C" bool string_sequence_contains(const char *string_sequence, const char *text)
-{
- if (empty_string(text) || empty_string(string_sequence))
- return false;
-
- QString stringSequence(string_sequence);
- QStringList strings = stringSequence.split(",", QString::SkipEmptyParts);
- Q_FOREACH (const QString& string, strings) {
- if (string.trimmed().compare(QString(text).trimmed(), Qt::CaseInsensitive) == 0)
- return true;
- }
- return false;
-}
-
static bool lessThan(const QPair<QString, int> &a, const QPair<QString, int> &b)
{
return a.second < b.second;
diff --git a/core/statistics.c b/core/statistics.c
index 6f5efe64f..d6d9418d7 100644
--- a/core/statistics.c
+++ b/core/statistics.c
@@ -53,6 +53,7 @@ static void process_dive(struct dive *dive, stats_t *stats)
stats->max_depth.mm = dive->maxdepth.mm;
if (stats->min_depth.mm == 0 || dive->maxdepth.mm < stats->min_depth.mm)
stats->min_depth.mm = dive->maxdepth.mm;
+ stats->combined_max_depth.mm += dive->maxdepth.mm;
process_temperatures(dive, stats);
diff --git a/core/statistics.h b/core/statistics.h
index d3707b9cb..6072f93b2 100644
--- a/core/statistics.h
+++ b/core/statistics.h
@@ -24,6 +24,7 @@ typedef struct
depth_t max_depth;
depth_t min_depth;
depth_t avg_depth;
+ depth_t combined_max_depth;
volume_t max_sac;
volume_t min_sac;
volume_t avg_sac;
diff --git a/core/subsurface-qt/DiveObjectHelper.cpp b/core/subsurface-qt/DiveObjectHelper.cpp
index e8e11e7d9..c85a3475e 100644
--- a/core/subsurface-qt/DiveObjectHelper.cpp
+++ b/core/subsurface-qt/DiveObjectHelper.cpp
@@ -8,14 +8,13 @@
#include "core/subsurface-string.h"
#include "qt-models/tankinfomodel.h"
-static QString EMPTY_DIVE_STRING = QStringLiteral("");
enum returnPressureSelector {START_PRESSURE, END_PRESSURE};
static QString getFormattedWeight(struct dive *dive, unsigned int idx)
{
weightsystem_t *weight = &dive->weightsystem[idx];
if (!weight->description)
- return QString(EMPTY_DIVE_STRING);
+ return QString();
QString fmt = QString(weight->description);
fmt += ", " + get_weight_string(weight->weight, true);
return fmt;
@@ -26,7 +25,7 @@ static QString getFormattedCylinder(struct dive *dive, unsigned int idx)
cylinder_t *cyl = &dive->cylinder[idx];
const char *desc = cyl->type.description;
if (!desc && idx > 0)
- return QString(EMPTY_DIVE_STRING);
+ return QString();
QString fmt = desc ? QString(desc) : gettextFromC::tr("unknown");
fmt += ", " + get_volume_string(cyl->type.size, true);
fmt += ", " + get_pressure_string(cyl->type.workingpressure, true);
@@ -107,7 +106,7 @@ QString DiveObjectHelper::time() const
QString DiveObjectHelper::location() const
{
- return get_dive_location(m_dive) ? QString::fromUtf8(get_dive_location(m_dive)) : EMPTY_DIVE_STRING;
+ return get_dive_location(m_dive) ? QString::fromUtf8(get_dive_location(m_dive)) : QString();
}
QString DiveObjectHelper::gps() const
@@ -149,35 +148,27 @@ QString DiveObjectHelper::depth() const
QString DiveObjectHelper::divemaster() const
{
- return m_dive->divemaster ? m_dive->divemaster : EMPTY_DIVE_STRING;
+ return m_dive->divemaster ? m_dive->divemaster : QString();
}
QString DiveObjectHelper::buddy() const
{
- return m_dive->buddy ? m_dive->buddy : EMPTY_DIVE_STRING;
+ return m_dive->buddy ? m_dive->buddy : QString();
}
QString DiveObjectHelper::airTemp() const
{
- QString temp = get_temperature_string(m_dive->airtemp, true);
- if (temp.isEmpty()) {
- temp = EMPTY_DIVE_STRING;
- }
- return temp;
+ return get_temperature_string(m_dive->airtemp, true);
}
QString DiveObjectHelper::waterTemp() const
{
- QString temp = get_temperature_string(m_dive->watertemp, true);
- if (temp.isEmpty()) {
- temp = EMPTY_DIVE_STRING;
- }
- return temp;
+ return get_temperature_string(m_dive->watertemp, true);
}
QString DiveObjectHelper::notes() const
{
- QString tmp = m_dive->notes ? QString::fromUtf8(m_dive->notes) : EMPTY_DIVE_STRING;
+ QString tmp = m_dive->notes ? QString::fromUtf8(m_dive->notes) : QString();
if (same_string(m_dive->dc.model, "planned dive")) {
QTextDocument notes;
#define _NOTES_BR "&#92n"
@@ -238,7 +229,7 @@ QString DiveObjectHelper::weightList() const
QString weights;
for (int i = 0; i < MAX_WEIGHTSYSTEMS; i++) {
QString w = getFormattedWeight(m_dive, i);
- if (w == EMPTY_DIVE_STRING)
+ if (w.isEmpty())
continue;
weights += w + "; ";
}
@@ -250,7 +241,7 @@ QStringList DiveObjectHelper::weights() const
QStringList weights;
for (int i = 0; i < MAX_WEIGHTSYSTEMS; i++) {
QString w = getFormattedWeight(m_dive, i);
- if (w == EMPTY_DIVE_STRING)
+ if (w.isEmpty())
continue;
weights << w;
}
@@ -265,13 +256,13 @@ bool DiveObjectHelper::singleWeight() const
QString DiveObjectHelper::weight(int idx) const
{
if ( (idx < 0) || idx > MAX_WEIGHTSYSTEMS )
- return QString(EMPTY_DIVE_STRING);
+ return QString();
return getFormattedWeight(m_dive, idx);
}
QString DiveObjectHelper::suit() const
{
- return m_dive->suit ? m_dive->suit : EMPTY_DIVE_STRING;
+ return m_dive->suit ? m_dive->suit : QString();
}
QStringList DiveObjectHelper::cylinderList() const
@@ -282,7 +273,7 @@ QStringList DiveObjectHelper::cylinderList() const
for_each_dive (i, d) {
for (int j = 0; j < MAX_CYLINDERS; j++) {
QString cyl = d->cylinder[j].type.description;
- if (cyl == EMPTY_DIVE_STRING)
+ if (cyl.isEmpty())
continue;
cylinders << cyl;
}
@@ -290,7 +281,7 @@ QStringList DiveObjectHelper::cylinderList() const
for (unsigned long ti = 0; ti < MAX_TANK_INFO && tank_info[ti].name != NULL; ti++) {
QString cyl = tank_info[ti].name;
- if (cyl == EMPTY_DIVE_STRING)
+ if (cyl.isEmpty())
continue;
cylinders << cyl;
}
@@ -305,7 +296,7 @@ QStringList DiveObjectHelper::cylinders() const
QStringList cylinders;
for (int i = 0; i < MAX_CYLINDERS; i++) {
QString cyl = getFormattedCylinder(m_dive, i);
- if (cyl == EMPTY_DIVE_STRING)
+ if (cyl.isEmpty())
continue;
cylinders << cyl;
}
@@ -315,7 +306,7 @@ QStringList DiveObjectHelper::cylinders() const
QString DiveObjectHelper::cylinder(int idx) const
{
if ( (idx < 0) || idx > MAX_CYLINDERS)
- return QString(EMPTY_DIVE_STRING);
+ return QString();
return getFormattedCylinder(m_dive, idx);
}
@@ -412,6 +403,6 @@ QString DiveObjectHelper::fullText() const
QString DiveObjectHelper::fullTextNoNotes() const
{
- QString tripLocation = m_dive->divetrip ? m_dive->divetrip->location : EMPTY_DIVE_STRING;
+ QString tripLocation = m_dive->divetrip ? m_dive->divetrip->location : QString();
return tripLocation + ":-:" + location() + ":-:" + buddy() + ":-:" + divemaster() + ":-:" + suit() + ":-:" + tags();
}