mirror of
https://github.com/subsurface/subsurface.git
synced 2024-11-27 20:58:47 +00:00
9f455b1457
This tries to encapsulate the management of the current dive and divecomputer in the selection code. The current dive is alreay set by setSelection(). Add a new parameter to also set the current divecomputer. If -1 is passed, then the current computer number is remained. This will allow us to audit the code. Because for now, the whole "current dive computer" thing seems to be ill-defined. This fixes a bug: the dive-computer number wasn't validated when making a new dive the current dive. The new code has some drawbacks though: when selecting a whole trip, the validation will be called for all dives in the trip and thus the dive computer number will depend on the dive with the lowest amount of dive computers in the trip. This will need to be fixed. Signed-off-by: Berthold Stoeger <bstoeger@mail.tuwien.ac.at>
162 lines
3.9 KiB
C++
162 lines
3.9 KiB
C++
// SPDX-License-Identifier: GPL-2.
|
|
#include "qmlprofile.h"
|
|
#include "profilescene.h"
|
|
#include "mobile-widgets/qmlmanager.h"
|
|
#include "core/errorhelper.h"
|
|
#include "core/subsurface-float.h"
|
|
#include "core/metrics.h"
|
|
#include "core/subsurface-string.h"
|
|
#include <QTransform>
|
|
#include <QScreen>
|
|
#include <QElapsedTimer>
|
|
|
|
QMLProfile::QMLProfile(QQuickItem *parent) :
|
|
QQuickPaintedItem(parent),
|
|
m_diveId(0),
|
|
m_dc(0),
|
|
m_devicePixelRatio(1.0),
|
|
m_margin(0),
|
|
m_xOffset(0.0),
|
|
m_yOffset(0.0)
|
|
{
|
|
createProfileView();
|
|
setAntialiasing(true);
|
|
setFlags(QQuickItem::ItemClipsChildrenToShape | QQuickItem::ItemHasContents );
|
|
connect(QMLManager::instance(), &QMLManager::sendScreenChanged, this, &QMLProfile::screenChanged);
|
|
connect(this, &QMLProfile::scaleChanged, this, &QMLProfile::triggerUpdate);
|
|
connect(&diveListNotifier, &DiveListNotifier::divesChanged, this, &QMLProfile::divesChanged);
|
|
setDevicePixelRatio(QMLManager::instance()->lastDevicePixelRatio());
|
|
}
|
|
|
|
QMLProfile::~QMLProfile()
|
|
{
|
|
}
|
|
|
|
void QMLProfile::createProfileView()
|
|
{
|
|
m_profileWidget.reset(new ProfileScene(m_devicePixelRatio * 0.8, false, false));
|
|
}
|
|
|
|
// we need this so we can connect update() to the scaleChanged() signal - which the connect above cannot do
|
|
// directly as it chokes on the default parameter for update().
|
|
// If the scale changes we may need to change our offsets to ensure that we still only show a subset of
|
|
// the profile and not empty space around it, which the paint() method below will take care of, which will
|
|
// eventually get called after we call update()
|
|
void QMLProfile::triggerUpdate()
|
|
{
|
|
update();
|
|
}
|
|
|
|
void QMLProfile::paint(QPainter *painter)
|
|
{
|
|
QElapsedTimer timer;
|
|
if (verbose)
|
|
timer.start();
|
|
|
|
// let's look at the intended size of the content and scale our scene accordingly
|
|
// for some odd reason the painter transformation is set up to scale by the dpr - which results
|
|
// in applying that dpr scaling twice. So we hard-code it here to be the identity matrix
|
|
QRect painterRect = painter->viewport();
|
|
painter->resetTransform();
|
|
if (m_diveId < 0)
|
|
return;
|
|
struct dive *d = get_dive_by_uniq_id(m_diveId);
|
|
if (!d)
|
|
return;
|
|
m_profileWidget->draw(painter, painterRect, d, m_dc, nullptr, false);
|
|
}
|
|
|
|
void QMLProfile::setMargin(int margin)
|
|
{
|
|
m_margin = margin;
|
|
}
|
|
|
|
int QMLProfile::diveId() const
|
|
{
|
|
return m_diveId;
|
|
}
|
|
|
|
void QMLProfile::setDiveId(int diveId)
|
|
{
|
|
m_diveId = diveId;
|
|
emit numDCChanged();
|
|
}
|
|
|
|
qreal QMLProfile::devicePixelRatio() const
|
|
{
|
|
return m_devicePixelRatio;
|
|
}
|
|
|
|
void QMLProfile::setDevicePixelRatio(qreal dpr)
|
|
{
|
|
if (dpr != m_devicePixelRatio) {
|
|
m_devicePixelRatio = dpr;
|
|
// Recreate the view to redraw the text items with the new scale.
|
|
createProfileView();
|
|
emit devicePixelRatioChanged();
|
|
}
|
|
}
|
|
|
|
// don't update the profile here, have the user update x and y and then manually trigger an update
|
|
void QMLProfile::setXOffset(qreal value)
|
|
{
|
|
if (nearly_equal(value, m_xOffset))
|
|
return;
|
|
m_xOffset = value;
|
|
emit xOffsetChanged();
|
|
}
|
|
|
|
// don't update the profile here, have the user update x and y and then manually trigger an update
|
|
void QMLProfile::setYOffset(qreal value)
|
|
{
|
|
if (nearly_equal(value, m_yOffset))
|
|
return;
|
|
m_yOffset = value;
|
|
emit yOffsetChanged();
|
|
}
|
|
|
|
void QMLProfile::screenChanged(QScreen *screen)
|
|
{
|
|
setDevicePixelRatio(screen->devicePixelRatio());
|
|
}
|
|
|
|
void QMLProfile::divesChanged(const QVector<dive *> &dives, DiveField)
|
|
{
|
|
for (struct dive *d: dives) {
|
|
if (d->id == m_diveId) {
|
|
qDebug() << "dive #" << d->number << "changed, trigger profile update";
|
|
triggerUpdate();
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
|
|
void QMLProfile::nextDC()
|
|
{
|
|
rotateDC(1);
|
|
}
|
|
|
|
void QMLProfile::prevDC()
|
|
{
|
|
rotateDC(-1);
|
|
}
|
|
|
|
void QMLProfile::rotateDC(int dir)
|
|
{
|
|
struct dive *d = get_dive_by_uniq_id(m_diveId);
|
|
if (!d)
|
|
return;
|
|
int numDC = number_of_computers(d);
|
|
if (numDC == 1)
|
|
return;
|
|
m_dc = (m_dc + dir) % numDC;
|
|
if (m_dc < 0)
|
|
m_dc += numDC;
|
|
triggerUpdate();
|
|
}
|
|
|
|
int QMLProfile::numDC() const
|
|
{
|
|
struct dive *d = get_dive_by_uniq_id(m_diveId);
|
|
return d ? number_of_computers(d) : 0;
|
|
}
|