summaryrefslogtreecommitdiffstats
path: root/desktop-widgets
AgeCommit message (Collapse)Author
2019-05-12Mainwindow: simplify application-state codeGravatar Berthold Stoeger
The way the application state would enable/disable widgets was very "dynamic". A property-list would be generated and put in a set of arrays. Very hard to figure out what is going on. Replace these property-list by flags and explicit old-fashioned boolean expressions. Join the two arrays (widget- and property-lists) into an array of a unified data structure. Replace the macro that sets the widgets by a simple static function. Factor out the four loops that added widgets to the quadrants into a simple static function. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-12Turn application state into enumGravatar Berthold Stoeger
The application state was encoded in a QByteArray. Thus, there was no compile-time checking. Typos would lead to silent failures. Turn the application state into an enum. Use the enum-class construct, so that the values don't polute the global namespace. Moreover, this makes them strongly typed, i.e. they don't auto-convert to integers. A disadvantage is that the enums now have to be cast to int explicitly when used to index an array. Replace two hash-maps in MainWindow to arrays of fixed sizes. Move the application-state details into their own files. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Dive site: Add button to display all dive sitesGravatar Berthold Stoeger
On the main dive tab, add a button that opens the dive-site selection widget showing all dive sites. This is done by setting the "temporary dive site name" to the empty string. Thus no dive sites are filtered and the "add new dive site" entries are not shown. Moreover, the text is selected. The user can therefore immediately start typing to activate the filter or enter the name of a new dive site. The idea is that after downloading dives with GPS information the user can select one of the close dive sites. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Cleanup: simplify DiveLocationLineEdit::showPopup()Gravatar Berthold Stoeger
DiveLocationLineEdit::showPopup() called the functions - fixPopupPosition() - proxy->invalidate() - proxy->sort(LocationInformationModel::NAME) - view->show() All these calls are redundant, as they are already performed by setTemporaryDiveSiteName(). Remove them. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Dive site: show distance to current dive using extra dataGravatar Berthold Stoeger
Currently, in the dive-site selection widget the distance to the dive site of the current dive is shown. Instead, use the recently introduced dive_get_gps_location() function. Thus, the actual GPS coordinates extracted by libdivecomputer are used. The function is only called when the current dive changes and the location is stored in the item delegate. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Dive site: sort by distance to current diveGravatar Berthold Stoeger
When presenting the list of dive sites on the dive-info tab, sort the dive sites by distance to the current dive. The idea is that when the user wants to select a dive site, close dive sites should be prioritized. The location of the dive is determined with the dive_get_gps_location() function introduced in the previous commit. This actual GPS data get precedence over the currently set dive site for that dive. On change of dive, the current location is updated in the DiveLocationFilterProxyModel so that a potentially expensive search for GPS data is not repeated for every comparison. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Dive site: create new dive site at location from GPS dataGravatar Berthold Stoeger
Some dive computers save GPS data. Currently, this is stored by libdivecomputer in an "extra field". When generating a new dive site for a dive try to use this data to place the dive site. To do so, create a "dive_get_gps_location()" function. This function can be extended later to use e.g. event. When creating a dive site, use the result of this function over a potential pre-existing dive site. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Map: automatically update names on the mapGravatar Berthold Stoeger
Currently, dive site names are only updated on full reload. Instead hook directly into the corresponding signal in the MapLocationModel to set the name. Also to the coordinates directly there instead of going via the MapWidgetHelper. In the MapWidgetHelper, just center on the changed dive site. Hook into the signal directly there and remove the slot from the MapWidget. This makes the whole call-chain at least one call shorter. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Map: construct list of dive sites from dive site tableGravatar Berthold Stoeger
Instead of looping over the dive table and extract dive sites, loop over the dive site table. This makes it possible to show dive sites that have no dive associated with them. But we have to create to functions that check whether a dive site has any shown dives or has any selected dives. Moreover, change the code to add near dive sites of the same name if in edit mode. Other wise (erroneously added?) dive sites with the same name cannot be moved on the map. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Map: remove skipReload logic in mapwidget.cppGravatar Berthold Stoeger
There used to be a flag to avoid reloading of the map. Since this is not used anymore, remove it. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Filter: add reference counting for dive-site modeGravatar Berthold Stoeger
The dive-site-edit and dive-site-table tabs both put the filter into a special dive-site mode. When switching between both, it could happen that the one got its show befor the other got its hide event. Thus, the first would start dive-site filtering and the second stop it. Now the app was not in filter mode even though it should. To solve this problem, add reference counting for the filter's dive-site mode. In both tabs call the enter/exit functions on show/hide. In the dive-site-table tab, when the selection changes, use a set function that doesn't modify the reference count. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Map: make edit mode depend on dive-site-filteringGravatar Berthold Stoeger
Since the dive-site-filter is active either on the dive-site-edit page or the dive-site-list page, use that as the flag for dive-site-edit mode. Moreover, when the filter is reset, the MapWidgetHelper::reloadMapLocations() function is called, so we can use that place to enter/exit edit mode. This makes it easier to keep everything consistent. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Selection: automatically unselect old selection in selectDives()Gravatar Berthold Stoeger
DiveListView::selectDives() would only select new dives but not clear the old selection. Thus, callers would have to clear the selection first. That would lead to two selection-changed signals. Move the unselectDives() call into DiveListView::selectDives(). The DiveListView has an internal flag to prevent double signals. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Map: remove MapWidget::centerOnSelectedDiveSiteGravatar Berthold Stoeger
This was only used locally and only a stub for calling MapWidgetHelper::centerOnSelectedDiveSite. Call the latter directly instead. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Map: reload on selection change directlyGravatar Berthold Stoeger
When changing the dive selection, we have to reload the map to show the correctly highlighted flags. Do this directly by hooking into the DiveListNotifier::divesChanged signal instead of indirectly via the MainTab. Moreover, on reload center on the highlighted dive sites. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Cleanup: remove MapWidgetHelper::m_selectedDiveIds memberGravatar Berthold Stoeger
This member variable was only used locally in functions. Accordingly, make it a function-local variable. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Map: don't reload map when in edit modeGravatar Berthold Stoeger
During edit mode, we could get spurious reload() requests owing to tabs being hidden. This led to undefined behavior: In some cases entering dive site edit mode would show all dive sites, in some only the dive site of the currently edited dive. Therefore, refuse to reload the map while in edit mode. The corresponding flag already exists. Partially fixes #2076 Reported-by: Doug Junkins <junkins@foghead.com> Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11Map: don't call exitEditMode() in MapWidget::reload()Gravatar Berthold Stoeger
On reload of the map, the map exits edit mode. Sounds logical at first, but the whole map-mode code is very unpredictable. What happened was that when switching from the dive site table to dive site edit mode, the code would enter map edit mode first. Then, the dive site tab got its hide-signal, which would reset the filter. This would reload the map and thus exit mode. Hence the user can't drag the flag on the map. Partially fixes #2076 Reported-by: Doug Junkins <junkins@foghead.com> Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-05-11CSV Import: add heartrate supportGravatar Miika Turkia
Signed-off-by: Miika Turkia <miika.turkia@gmail.com>
2019-05-06Create DivesiteImportDialog to select sites to importGravatar Doug Junkins
Creates the dialog box to select which sites to import from the file selected in mainwindow.cpp. The DivesiteImportModel is created as a table to display and select which sites are to be imported. Once the sites are selected, the Command::importDiveSites command is called to add the sites to the core dive site table with undo/redo functions. Signed-off-by: Doug Junkins <junkins@foghead.com>
2019-05-06Add "Import dive sites" menu to mainwindowGravatar Doug Junkins
Adds "Import->Import dive sites" menu to mainwindow.cpp and adds the on_actionImportDiveSites_triggered() method to prompt for the filename to import from. The files are parsed and then any dive and trip data is cleared before opening a dialog box to select which sites are to be imported. Signed-off-by: Doug Junkins <junkins@foghead.com>
2019-05-06Add undo/redo commands for importing dive sitesGravatar Doug Junkins
ImportDiveSites adds the provided dive sites to the core dive site table and stores the source data so it can be undone. Signed-off-by: Doug Junkins <junkins@foghead.com>
2019-05-05Desktop: fix crash on dive site tabGravatar Berthold Stoeger
An interesting crash: 1) On the dive site tab select a dive site such that only one trip is shown. 2) Unselect all dives. 3) Press CTRL-A while the dive list has focus. 4) This will select a trip. 5) In MainTab::updateDiveInfo() this will switch to the previous tab active when in trip mode. 6) This will reset the filter. 7) This will reset the currentTrip field which we just set. 8) Since we just set the currentTrip field, we don't expect it to change and reference a null pointer. To fix, don't switch tabs when on the dive site tab. This also improves user experience as there seems to be no reason to switch away from the dive site tab. Currently the index of the dive site tab is hard-coded - this should be changed! Fixes #2077 Reported-by: Doug Junkins <junkins@foghead.com> Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Cleanup: make objects in desktop-widgets/modeldelegates.cppGravatar Berthold Stoeger
A number of objects in this file were global. Yet they weren't used anywhere else. Don't export these symbols by making them of static linkage. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Cleanup: fix leak in delegatesGravatar Berthold Stoeger
A copy of a C-string was assigned to a QString. The copy was never freed. Instead, assign the C-string directly. This does the right thing. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Cleanup: implement proper Qt-model semantics in WeightInfoModelGravatar Berthold Stoeger
- Use a beginResetModel()/endResetModel() pair instead of distinct addRows / removeRows pairs. - Reuse the update function in the constructor(). - Let "rows" be the number of rows, not the number of rows minus one. - Remove updateInfo() function as it does the same as update(). Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Cleanup: simplify YearInfo classGravatar Berthold Stoeger
YearInfo is a trivial wrapper around "stats_t *". All the constructor / destructor rigmarole seems completely unnecessary. Remove it. Probably the whole class could be removed, but for that I'd need more insight into Grantlee, which is low on my list of priorities for now. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Cleanup: remove stale include in desktop-widgets/templatelayout.cppGravatar Berthold Stoeger
Including <string> is not necessary in this file. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Printing: fix memory leakGravatar Berthold Stoeger
For printing, DiveObjectHelpers are allocated and pointers to these are stored in a QVariantList. The objects are never freed. To fix this leak, keep the objects in a std::list<>. std::list<> was chosen because 1) Pointers to elements stay valid during its lifetime. 2) Objects can be constructed directly in the list with emplace_back() Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Cleanup: rename variable PrintOptions to printOptionsGravatar Berthold Stoeger
We're quite inconsistent when it comes to variable naming. The general usage is camelCase for Qt parts and snake_case for core code. Virtually nowhere do we start variable names with a capital letter. Therefore, turn this one weird case into camelCase. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Cleanup: remove TemplateLayout::m_engine member variableGravatar Berthold Stoeger
TemplateLayout::m_engine is a Grantlee::Engine that is reallocated for every function call. Instead of the archaic memory-management, remove the member variable and make it a local variable of the two functions that need it. There seems to be no point in keeping the object alive beyond the function's scope. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Cleanup: remove redundant string clearingGravatar Berthold Stoeger
The default QString constructor generates an empty string. No point in assigning the empty string to such a thing. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Desktop: automatically update dive information tabGravatar Berthold Stoeger
Currently, the dive information tab was not updated when the user edited fields. The fields were only updated when switching between dives. Therefore, hook into the "divesChanged" signal and update the fields accordingly. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Desktop: use current_dive in information tabGravatar Berthold Stoeger
The information tab used displayed_dive to fill out its field. For consistency with the main tab and in a bigger effort to remove displayed_dive, use current_dive instead. Only clear the fields if no current_dive is set. The code used to clear the fields and overwrite them later. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-29Desktop: set dive fields only when not in trip modeGravatar Berthold Stoeger
On the main-tab, when looking at a trip, the fields were filled out with dive-data and then either hidden or overwritten with trip data. Move the update of the fields into the corresponding if-branch that is only active if on dive-mode. This means removing the UPDATE_* macros, which updated or cleared dive-fields depending on whether a current dive was set. These operations are now performed explicitly in the corresponding if-branches. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-16Write dive data as video subtitlesGravatar Robert C. Helling
This commit adds an entry to the dive media context menu which offers to write a subtitle file. This creates an .ass file for the selected videos. In an attempt to to clutter the screen too much, don't show irrelevant entries (zero temperature or NDL and show TTS only for dives with stops). VLC is able to show these subtitles directly, they can be integrated into the video file with ffmpeg. Signed-off-by: Robert C. Helling <helling@atdotde.de>
2019-04-16Desktop: don't show special dive site entries if there is no filterGravatar Berthold Stoeger
In the dive site selection widget there are two special entries (add dive site with given name). Don't show this if the user didn't enter a string. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-16Desktop: enable sorting in dive site selection widgetGravatar Berthold Stoeger
The dive site selection widget implements a lessThan() function, but that was never called. Apparently in a QListView one has to start sorting by hand? Do just that. In any case, the lessThan function was erroneous as it would happily sort away the first two special entries. Fix it with a special case for these to. Finally use case insensitive string comparison. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-16Cleanup: access filter-model directly without castGravatar Berthold Stoeger
To reset the filter-model, LocationInformationWidget would extract the model from the diveSiteListView and then downcasts it. Instead, it can access it directly, because the filter-model is a subobject of LocationInformationWidget. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-16Cleanup: remove global DiveLocationLineEdit variableGravatar Berthold Stoeger
DiveLocationLineEdit stored a pointer to itself in a global variable so that the DiveLocationModel can access it to access the filter text. Instead, on change simply pass the filter text down from DiveLocationLineEdit to DiveLocationModel. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-15Dive site: display proper text for the two special optionsGravatar Berthold Stoeger
The dive-site line edit box features two special entries for adding new dive sites. These should display different texts depending on whether the current dive has a dive site or not. The current check is wrong, because it used displayed_dive, but since the last set of undo-changes, this might not be filled out correctly anymore. Instead the code should check the actual current dive. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-15Cleanup: remove completers from MainTab objectGravatar Berthold Stoeger
This struct is used to store the completers during construction of the object. But it is never accessed afterwards. Therefore, remove it from the object and remove the structure definition from the header file. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-15Cleanup: Move dive-equipment tab into own translation unitsGravatar Berthold Stoeger
Most tabs in the dive-information widget have there own translation units and ui-files. Only the equipment tab was married with the main tab. Move it out to get more reasonably sized translation units and some isolation. Currently, this needs ugly hacks when entering / checking for edit mode: Access to MainTab is via the MainWindow. And vice/versa, when accessing the DiveEquipmentTab from the MainTab, the former is hardcoded as the first item of an array. These hacks will soon be removed though, when making equipment editing undoable. The tabs will then be independent. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-15Cleanup: Remove MainTab::getEditMode() functionGravatar Berthold Stoeger
The only caller of said function used to check whether MainTab is in edit mode. For this case there is already a function - use that instead. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-15Undo: don't store insertion index in undo commandGravatar Berthold Stoeger
When adding dives in an undo command, the index is saved in the command. This seemed logical at first, because why calculate the index more than once? But actually it made the code rather subtle and brittle when multiple dives were added. Moreover, this is a pointless optimization, as it doesn't optimize the common case (only one execution). Remove this for now and calculate the index on every execution. If it ever turns out to be a bottle neck, it will be much more effective to turn the linear search of the index into a binary search. A further sensible optimization would be inserting in batches. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-14Desktop: remove edit-check in tag-widget completerGravatar Berthold Stoeger
The tag-widget was only showing the completer if we were in edit mode. The edit mode does not exist anymore - therefore remove the check. Hopefully this has no unintended consequences, like the completer not disappearing when it should. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-13Add export option to export dive sites.Gravatar Doug Junkins
Selecting "Selected dives" exports the dive sites for the selected dives. Selecting "All dives" exports all dive sites. XML format is the subsection of the divelog XML that describes the sites headed with a <divesites> section like: <divesites program='subsurface' version='3'> </divesites> Signed-off-by: Doug Junkins <junkins@foghead.com>
2019-04-14Desktop: destroy maintab before destructing mainwindowGravatar Berthold Stoeger
Apparently, in some Qt-versions the destructor of the base class calls hide on child-objects (according to Qt's object hierarchy). This is obviously called after the derived class has been destructed. In a concrete case, the base class of the destructed MainWindow would hide the TabDiveSite object. That would reset the filtering if a dive site was selected, which would indirectly access the MainWindow, which is already partially destroyed. Therefore, destroy the MainTab before destroying the MainWindow. Do this by keeping it as a std::unique_ptr subobject. Thus, it will be destroyed before the MainWindow and remove itself from Qt's object hierarchy. Reported-by: Dirk Hohndel <dirk@hohndel.org> Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-13Desktop: put dive site table in "row selection mode"Gravatar Berthold Stoeger
This feels more natural than selecting a single cell. Still, the "delete" cell is not visibly selected, which give a strange impression. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
2019-04-13Desktop: update dive site list on file-closeGravatar Berthold Stoeger
The model was not reset on file close, leading to weird effects. New dive sites would be added at the end of a table full of empty entries. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>