#include "lts_angle_edit.h" #include "ui_lts_angle_edit.h" #include #include namespace LtsWidgets { inline constexpr double pi() { return M_PI; } inline constexpr double deg2rad() { return pi() / 180.; } inline constexpr double rad2deg() { return 1. / deg2rad(); } constexpr int maxAngleDeg = 360; constexpr int maxAngleMil = 6400; constexpr std::tuple c_limDeg(0, maxAngleDeg, 0, 10); constexpr std::tuple c_limMil(0, maxAngleMil, 0, 50); constexpr std::tuple c_limRad(-99999, 99999, 3, 1); inline constexpr double mil2Deg(const double& mil) { return maxAngleDeg * mil / maxAngleMil; } inline constexpr double deg2Mil(const double& angleDeg) { return maxAngleMil * angleDeg / maxAngleDeg; } inline constexpr double deg2Rad(const double& angleDeg) { return angleDeg * deg2rad(); } inline constexpr double rad2Degree(const double& angleRad) { return angleRad * 180 / pi(); } inline constexpr double mil2Rad(const double& mil) { return deg2Rad(mil2Deg(mil)); } inline constexpr double rad2Mil(const double& angleRad) { return deg2Mil(rad2Degree(angleRad)); } LtsAngleEdit::LtsAngleEdit(QWidget* parent) : QWidget(parent), m_ui(new Ui_LtsAngleEdit) { m_ui->setupUi(this); } LtsAngleEdit::~LtsAngleEdit() { delete m_ui; } void LtsAngleEdit::initAngleEditWidget(const unsigned int sboxCount) { m_dboxLimitMap.insert(AngleUnitType::Deg, c_limDeg); m_dboxLimitMap.insert(AngleUnitType::Mil, c_limMil); m_dboxLimitMap.insert(AngleUnitType::Rad, c_limRad); m_hiddenUnits.clear(); m_hiddenUnits.insert((int)AngleUnitType::Rad); for (unsigned int i = 0; i < sboxCount; ++i) { QSharedPointer spinbox = QSharedPointer(new QDoubleSpinBox(this)); spinbox->setValue(0); spinbox->setAlignment(Qt::AlignRight); spinbox->setMinimumWidth(91); spinbox.data()->setObjectName(spinBoxName + QString::number(m_sBoxMap.count())); m_ui->hLayoutSpinbox->addWidget(spinbox.data(), 0); m_sBoxMap.insert(m_sBoxMap.count(), spinbox); } m_ui->hLayoutSpinbox->setContentsMargins(1, 1, 1, 1); connect(m_ui->cBoxAngleUnit, qOverload(&QComboBox::currentIndexChanged), this, &LtsAngleEdit::onCBoxAngleUnitChanged); setCboxUnit(); } void LtsAngleEdit::setValue(const double value, unsigned int dboxIndex) { if ((int)dboxIndex > m_sBoxMap.count()) return; auto spinbox = m_sBoxMap.value(dboxIndex); spinbox->setValue(value); } void LtsAngleEdit::setValue(const double value, AngleUnitType valueUnit, unsigned int dboxIndex) { setValue(getAngleConverted(value, getAngleCurrentUnit(), valueUnit), dboxIndex); } void LtsAngleEdit::hideUnits(const QVector& list) { for (auto u : list) m_hiddenUnits.insert((int)u); setCboxUnit(); } void LtsAngleEdit::showUnits(const QVector& list) { for (const auto& u : list) m_hiddenUnits.remove((int)u); setCboxUnit(); } void LtsAngleEdit::setCboxUnit() { m_ui->cBoxAngleUnit->clear(); const std::vector allUnits = {AngleUnitType::Deg, AngleUnitType::Mil, AngleUnitType::Rad}; for (const auto& u : allUnits) { if (m_hiddenUnits.contains((int)u)) continue; m_ui->cBoxAngleUnit->insertItem(static_cast(u), toString(u), static_cast(u)); } setAngleUnit(AngleUnitType::Deg); } void LtsAngleEdit::setValue(const double value, AngleUnitType valueUnit) { setValue(getAngleConverted(value, getAngleCurrentUnit(), valueUnit), 0); } void LtsAngleEdit::setAngleUnit(const AngleUnitType& type) { m_ui->cBoxAngleUnit->setCurrentIndex(static_cast(type)); } LtsAngleEdit::AngleUnitType LtsAngleEdit::getAngleCurrentUnit() const { return static_cast(m_ui->cBoxAngleUnit->currentIndex()); } double LtsAngleEdit::getAngle(unsigned int sboxIndex) const { if ((int)sboxIndex > m_sBoxMap.count()) return 0; auto spinbox = m_sBoxMap.value(sboxIndex); return spinbox->value(); } QString LtsAngleEdit::toString(LtsAngleEdit::AngleUnitType t) { switch (t) { case AngleUnitType::Deg: return tr("Degree"); case AngleUnitType::Mil: return tr("Mil"); case AngleUnitType::Rad: return tr("Radian"); default: return tr(""); } return tr(""); } void LtsAngleEdit::onCBoxAngleUnitChanged() { AngleUnitType newUnit = static_cast(m_ui->cBoxAngleUnit->currentData().toInt()); for (auto dbox : std::as_const(m_sBoxMap)) { const double value = getAngleConverted(dbox->value(), newUnit, m_currAngleUnit); auto mapVal = m_dboxLimitMap.value(newUnit); dbox->setMinimum(std::get(mapVal)); dbox->setMaximum(std::get(mapVal)); dbox->setDecimals(std::get(mapVal)); dbox->setSingleStep(std::get(mapVal)); dbox->setValue(value); } m_currAngleUnit = newUnit; } double LtsAngleEdit::getAngleConverted(const double angle, LtsAngleEdit::AngleUnitType newAngleUnit, LtsAngleEdit::AngleUnitType oldAngleUnit) { double convertedAngle = angle; if (oldAngleUnit == AngleUnitType::Deg && newAngleUnit == AngleUnitType::Mil) convertedAngle = deg2Mil(angle); else if (oldAngleUnit == AngleUnitType::Deg && newAngleUnit == AngleUnitType::Rad) convertedAngle = deg2Rad(angle); else if (oldAngleUnit == AngleUnitType::Mil && newAngleUnit == AngleUnitType::Deg) convertedAngle = mil2Deg(angle); else if (oldAngleUnit == AngleUnitType::Mil && newAngleUnit == AngleUnitType::Rad) convertedAngle = mil2Rad(angle); else if (oldAngleUnit == AngleUnitType::Rad && newAngleUnit == AngleUnitType::Deg) convertedAngle = rad2Degree(angle); else if (oldAngleUnit == AngleUnitType::Rad && newAngleUnit == AngleUnitType::Mil) convertedAngle = rad2Mil(angle); return convertedAngle; } void LtsAngleEdit::setEnable(int sbIndex, bool enabled) { if ((int)sbIndex > m_sBoxMap.count()) return; m_sBoxMap.value(sbIndex)->setEnabled(enabled); } void LtsAngleEdit::showSpinbox(int sbIndex, bool visible) { if ((int)sbIndex > m_sBoxMap.count()) return; m_sBoxMap.value(sbIndex)->setVisible(visible); } } // namespace LtsWidgets