Qt ui: improve toggle buttons (#2639)

* works, but is still a bit ugly

* works

* looks much better now

* fix compile error

* reduce diff

* write to params

* cleanup
albatross
grekiki 2020-11-27 17:55:07 +01:00 committed by GitHub
parent feaecbd615
commit 61884d2c50
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 124 additions and 14 deletions

View File

@ -71,9 +71,10 @@ else:
else:
qt_libs += [f"Qt5{m}" for m in qt_modules]
qt_env.Library("qt_widgets",
["qt/qt_window.cc", "qt/qt_sound.cc", "qt/offroad/keyboard.cc", "qt/offroad/input_field.cc",
"qt/offroad/wifi.cc", "qt/offroad/wifiManager.cc"],
"qt/offroad/wifi.cc", "qt/offroad/wifiManager.cc", "qt/offroad/toggle.cc"],
LIBS=qt_libs)
qt_libs.append("qt_widgets")

View File

@ -13,6 +13,7 @@
#include "wifi.hpp"
#include "settings.hpp"
#include "input_field.hpp"
#include "toggle.hpp"
#include "common/params.h"
#include "common/utilpp.h"
@ -21,8 +22,8 @@ const int SIDEBAR_WIDTH = 400;
ParamsToggle::ParamsToggle(QString param, QString title, QString description, QString icon_path, QWidget *parent): QFrame(parent) , param(param) {
QHBoxLayout *hlayout = new QHBoxLayout;
QVBoxLayout *vlayout = new QVBoxLayout;
//Parameter image
hlayout->addSpacing(25);
if (icon_path.length()){
QPixmap pix(icon_path);
@ -34,21 +35,29 @@ ParamsToggle::ParamsToggle(QString param, QString title, QString description, QS
hlayout->addSpacing(100);
}
hlayout->addSpacing(25);
checkbox = new QCheckBox(title);
QLabel *label = new QLabel(description);
//Name of the parameter
QLabel *label = new QLabel(title);
label->setWordWrap(true);
//toggle switch
Toggle* toggle_switch = new Toggle(this);
QSizePolicy switch_policy(QSizePolicy::Preferred, QSizePolicy::Preferred);
switch_policy.setHorizontalStretch(1);
toggle_switch->setSizePolicy(switch_policy);
toggle_switch->setFixedWidth(120);
toggle_switch->setFixedHeight(50);
// TODO: show descriptions on tap
//vlayout->addSpacing(50);
vlayout->addWidget(checkbox);
//vlayout->addWidget(label);
//vlayout->addSpacing(50);
hlayout->addLayout(vlayout);
hlayout->addWidget(label);
hlayout->addSpacing(50);
hlayout->addWidget(toggle_switch);
hlayout->addSpacing(50);
setLayout(hlayout);
checkbox->setChecked(Params().read_db_bool(param.toStdString().c_str()));
if(Params().read_db_bool(param.toStdString().c_str())){
toggle_switch->togglePosition();
}
setStyleSheet(R"(
QCheckBox {
@ -70,7 +79,7 @@ ParamsToggle::ParamsToggle(QString param, QString title, QString description, QS
}
)");
QObject::connect(checkbox, SIGNAL(stateChanged(int)), this, SLOT(checkboxClicked(int)));
QObject::connect(toggle_switch, SIGNAL(stateChanged(int)), this, SLOT(checkboxClicked(int)));
}
void ParamsToggle::checkboxClicked(int state){

View File

@ -0,0 +1,66 @@
#include "toggle.hpp"
#include <QAbstractButton>
#include <QPropertyAnimation>
#include <QWidget>
#include <QDebug>
#include "common/params.h"
Toggle::Toggle(QWidget *parent) : QAbstractButton(parent),
_height(60),
_height_rect(45),
_on(false),
_anim(new QPropertyAnimation(this, "offset_circle", this))
{
_radius = _height / 2;
_x_circle = _radius;
_y_circle = _radius;
_y_rect = (_height - _height_rect)/2;
}
void Toggle::paintEvent(QPaintEvent *e) {
this->setFixedHeight(_height);
QPainter p(this);
p.setPen(Qt::NoPen);
p.setRenderHint(QPainter::Antialiasing, true);
// Draw toggle background left
p.setBrush(QColor("#33ab4c"));
p.drawRoundedRect(QRect(0, _y_rect, _x_circle + _radius, _height_rect), _height_rect/2, _height_rect/2);
// Draw toggle background right
p.setBrush(QColor("#0a1a26"));
p.drawRoundedRect(QRect(_x_circle - _radius, _y_rect, width() -(_x_circle - _radius), _height_rect), _height_rect/2, _height_rect/2);
// Draw toggle circle
p.setBrush(QColor("#fafafa"));
p.drawEllipse(QRectF(_x_circle - _radius, _y_circle - _radius, 2 * _radius, 2 * _radius));
}
void Toggle::mouseReleaseEvent(QMouseEvent *e) {
if (e->button() & Qt::LeftButton) {
togglePosition();
emit stateChanged(_on);
}
}
void Toggle::togglePosition(){
_on = !_on;
if (_on) {
_anim->setStartValue(_radius);
_anim->setEndValue(width() - _radius);
_anim->setDuration(120);
_anim->start();
} else {
_anim->setStartValue(width() - _radius);
_anim->setEndValue(_radius);
_anim->setDuration(120);
_anim->start();
}
}
void Toggle::enterEvent(QEvent *e) {
setCursor(Qt::PointingHandCursor);
QAbstractButton::enterEvent(e);
}

View File

@ -0,0 +1,34 @@
#pragma once
#include <QtWidgets>
class Toggle : public QAbstractButton {
Q_OBJECT
Q_PROPERTY(int offset_circle READ offset_circle WRITE set_offset_circle)
public:
Toggle(QWidget* parent = nullptr);
void togglePosition();//Toggles the toggle
int offset_circle() const {
return _x_circle;
}
void set_offset_circle(int o) {
_x_circle = o;
update();
}
protected:
void paintEvent(QPaintEvent*) override;
void mouseReleaseEvent(QMouseEvent*) override;
void enterEvent(QEvent*) override;
private:
bool _on;
int _x_circle, _y_circle;
int _height, _radius;
int _height_rect, _y_rect;
QPropertyAnimation *_anim = nullptr;
signals:
void stateChanged(int new_state);
};