mirror of
https://github.com/Lurkki14/tuxclocker.git
synced 2025-02-25 18:55:24 -06:00
parametrize correctly with all types
This commit is contained in:
parent
5dbcc23323
commit
f9a660afee
@ -82,7 +82,7 @@ void AssignableProxy::apply() {
|
|||||||
|
|
||||||
if (opt.has_value()) {
|
if (opt.has_value()) {
|
||||||
auto proxy = opt.value();
|
auto proxy = opt.value();
|
||||||
m_connection = new DynamicReadableConnection<uint>{*proxy, data.points};
|
m_connection = new DynamicReadableConnection<uint>{*proxy, data};
|
||||||
|
|
||||||
startConnection();
|
startConnection();
|
||||||
m_value = QVariant();
|
m_value = QVariant();
|
||||||
|
@ -17,12 +17,17 @@ using namespace fplus;
|
|||||||
using namespace mpark::patterns;
|
using namespace mpark::patterns;
|
||||||
using namespace TuxClocker::Device;
|
using namespace TuxClocker::Device;
|
||||||
|
|
||||||
class DynamicReadableConnectionData {
|
struct DynamicReadableConnectionData {
|
||||||
public:
|
|
||||||
// y = f(x)
|
// y = f(x)
|
||||||
QVector<QPointF> points;
|
QVector<QPointF> points;
|
||||||
// DBus path
|
// DBus path
|
||||||
QString dynamicReadablePath;
|
QString dynamicReadablePath;
|
||||||
|
RangeInfo rangeInfo;
|
||||||
|
};
|
||||||
|
|
||||||
|
enum class TargetType {
|
||||||
|
IntType,
|
||||||
|
DoubleType
|
||||||
};
|
};
|
||||||
|
|
||||||
Q_DECLARE_METATYPE(DynamicReadableConnectionData)
|
Q_DECLARE_METATYPE(DynamicReadableConnectionData)
|
||||||
@ -32,9 +37,14 @@ Q_DECLARE_METATYPE(DynamicReadableConnectionData)
|
|||||||
template <typename OutType> // Result of linear interpolation
|
template <typename OutType> // Result of linear interpolation
|
||||||
class DynamicReadableConnection : public AssignableConnection {
|
class DynamicReadableConnection : public AssignableConnection {
|
||||||
public:
|
public:
|
||||||
DynamicReadableConnection(
|
DynamicReadableConnection(DynamicReadableProxy &proxy, DynamicReadableConnectionData data,
|
||||||
DynamicReadableProxy &proxy, QVector<QPointF> points, QObject *parent = nullptr)
|
QObject *parent = nullptr)
|
||||||
: AssignableConnection(parent), m_proxy(proxy), m_points(points) {
|
: AssignableConnection(parent), m_proxy(proxy), m_points(data.points) {
|
||||||
|
if (std::holds_alternative<Range<int>>(data.rangeInfo))
|
||||||
|
m_targetType = TargetType::IntType;
|
||||||
|
else
|
||||||
|
m_targetType = TargetType::DoubleType;
|
||||||
|
|
||||||
auto sorted = sort_by(
|
auto sorted = sort_by(
|
||||||
[](auto point_l, auto point_r) { return point_l.x() < point_r.x(); }, m_points);
|
[](auto point_l, auto point_r) { return point_l.x() < point_r.x(); }, m_points);
|
||||||
m_points = sorted;
|
m_points = sorted;
|
||||||
@ -43,23 +53,42 @@ public:
|
|||||||
virtual void start() override {
|
virtual void start() override {
|
||||||
connect(&m_proxy, &DynamicReadableProxy::valueChanged, [this](auto val) {
|
connect(&m_proxy, &DynamicReadableProxy::valueChanged, [this](auto val) {
|
||||||
match(val)(pattern(as<ReadableValue>(arg)) = [this](auto rv) {
|
match(val)(pattern(as<ReadableValue>(arg)) = [this](auto rv) {
|
||||||
match(rv)(pattern(as<uint>(arg)) = [this](auto u) {
|
match(rv)(
|
||||||
emitTargetValue(u);
|
pattern(as<uint>(arg)) = [this](auto u) { emitTargetValue(u); },
|
||||||
});
|
pattern(as<int>(arg)) = [this](int i) { emitTargetValue(i); },
|
||||||
|
pattern(as<double>(arg)) = [this](
|
||||||
|
auto d) { emitTargetValue(d); });
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
virtual void stop() override { disconnect(&m_proxy, nullptr, nullptr, nullptr); }
|
virtual void stop() override { disconnect(&m_proxy, nullptr, nullptr, nullptr); }
|
||||||
private:
|
private:
|
||||||
|
TargetType m_targetType;
|
||||||
DynamicReadableProxy &m_proxy;
|
DynamicReadableProxy &m_proxy;
|
||||||
QTimer m_timer;
|
QTimer m_timer;
|
||||||
QVector<QPointF> m_points;
|
QVector<QPointF> m_points;
|
||||||
|
|
||||||
template <typename T> void doEmit(T targetValue) {
|
template <typename T> void doEmit(T targetValue, QString targetText) {
|
||||||
QDBusVariant arg{QVariant{targetValue}};
|
QDBusVariant arg{QVariant{targetValue}};
|
||||||
QVariant v;
|
QVariant v;
|
||||||
v.setValue(arg);
|
v.setValue(arg);
|
||||||
emit targetValueChanged(v, QString::number(targetValue));
|
emit targetValueChanged(v, targetText);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T> void emitWithType(T value) {
|
||||||
|
switch (m_targetType) {
|
||||||
|
case TargetType::IntType: {
|
||||||
|
int target = static_cast<int>(value);
|
||||||
|
doEmit(target, QString::number(target));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
case TargetType::DoubleType: {
|
||||||
|
auto target = static_cast<double>(value);
|
||||||
|
// TODO: don't hardcode precision in different places
|
||||||
|
doEmit(target, QString::number(target, 'f', 2));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename U> void emitTargetValue(U reading) {
|
template <typename U> void emitTargetValue(U reading) {
|
||||||
@ -72,16 +101,19 @@ private:
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!leftIndex.has_value()) {
|
||||||
// Reading wasn't between points
|
// Reading wasn't between points
|
||||||
if (reading > m_points.last().y()) {
|
if (reading > m_points.last().y()) {
|
||||||
// Use y of rightmost point
|
// Use y of rightmost point
|
||||||
doEmit((uint) qRound(m_points.last().y()));
|
emitWithType(m_points.last().y());
|
||||||
return;
|
return;
|
||||||
} else if (reading < m_points.last().y()) {
|
} else if (reading < m_points.last().y()) {
|
||||||
// Leftmost
|
// Leftmost
|
||||||
doEmit((uint) qRound(m_points.first().y()));
|
emitWithType(m_points.last().y());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (leftIndex == std::nullopt) {
|
if (leftIndex == std::nullopt) {
|
||||||
qWarning("Couldn't calculate target value from reading %s!",
|
qWarning("Couldn't calculate target value from reading %s!",
|
||||||
@ -93,8 +125,9 @@ private:
|
|||||||
double dx = m_points[li + 1].x() - m_points[li].x();
|
double dx = m_points[li + 1].x() - m_points[li].x();
|
||||||
double dvx = reading - m_points[li].x();
|
double dvx = reading - m_points[li].x();
|
||||||
double p = dvx / dx;
|
double p = dvx / dx;
|
||||||
OutType interp_y = lerp(m_points[li].y(), m_points[li + 1].y(), p);
|
U interp_y = lerp(m_points[li].y(), m_points[li + 1].y(), p);
|
||||||
doEmit(interp_y);
|
|
||||||
|
emitWithType(interp_y);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T> T lerp(T a, T b, double t) { return a + (t * (b - a)); }
|
template <typename T> T lerp(T a, T b, double t) { return a + (t * (b - a)); }
|
||||||
|
@ -100,6 +100,7 @@ public:
|
|||||||
auto data = DynamicReadableConnectionData{
|
auto data = DynamicReadableConnectionData{
|
||||||
.points = points,
|
.points = points,
|
||||||
.dynamicReadablePath = proxy->dbusPath(),
|
.dynamicReadablePath = proxy->dbusPath(),
|
||||||
|
.rangeInfo = m_rangeInfo,
|
||||||
};
|
};
|
||||||
emit connectionDataChanged(data);
|
emit connectionDataChanged(data);
|
||||||
this->close();
|
this->close();
|
||||||
@ -133,6 +134,7 @@ public:
|
|||||||
[this](auto ir) { m_dragView->setRange(0, 100, ir.min, ir.max); });
|
[this](auto ir) { m_dragView->setRange(0, 100, ir.min, ir.max); });
|
||||||
|
|
||||||
m_applyButton->setToolTip(disabledReason());
|
m_applyButton->setToolTip(disabledReason());
|
||||||
|
m_rangeInfo = rangeInfo;
|
||||||
}
|
}
|
||||||
void setAssignableName(QString name) {
|
void setAssignableName(QString name) {
|
||||||
m_dependableLabel->setText(QString{"Connecting %1 with:"}.arg(name));
|
m_dependableLabel->setText(QString{"Connecting %1 with:"}.arg(name));
|
||||||
@ -147,6 +149,7 @@ signals:
|
|||||||
private:
|
private:
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
|
RangeInfo m_rangeInfo;
|
||||||
DeviceModel &m_model;
|
DeviceModel &m_model;
|
||||||
DeviceProxyModel m_proxyModel;
|
DeviceProxyModel m_proxyModel;
|
||||||
DragChartView *m_dragView;
|
DragChartView *m_dragView;
|
||||||
|
Loading…
Reference in New Issue
Block a user