ui/networking: remove call to clearLayout (#29037)

* build list inplace

* move clearLayout to cabana

* cleanup include

* polish style

---------

Co-authored-by: Adeeb Shihadeh <adeebshihadeh@gmail.com>
pull/29377/head
Dean Lee 2 years ago committed by GitHub
parent 3a00149f56
commit fd8a9c8520
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 136
      selfdrive/ui/qt/offroad/networking.cc
  2. 31
      selfdrive/ui/qt/offroad/networking.h
  3. 13
      selfdrive/ui/qt/util.cc
  4. 2
      selfdrive/ui/qt/util.h
  5. 14
      tools/cabana/streams/pandastream.cc

@ -2,14 +2,11 @@
#include <algorithm>
#include <QDebug>
#include <QHBoxLayout>
#include <QLabel>
#include <QPainter>
#include <QScrollBar>
#include <QStyle>
#include "selfdrive/ui/ui.h"
#include "selfdrive/ui/qt/util.h"
#include "selfdrive/ui/qt/qt_window.h"
#include "selfdrive/ui/qt/widgets/controls.h"
#include "selfdrive/ui/qt/widgets/prime.h"
@ -211,7 +208,7 @@ void AdvancedNetworking::toggleTethering(bool enabled) {
// WifiUI functions
WifiUI::WifiUI(QWidget *parent, WifiManager* wifi) : QWidget(parent), wifi(wifi) {
main_layout = new QVBoxLayout(this);
QVBoxLayout *main_layout = new QVBoxLayout(this);
main_layout->setContentsMargins(0, 0, 0, 0);
main_layout->setSpacing(0);
@ -228,8 +225,9 @@ WifiUI::WifiUI(QWidget *parent, WifiManager* wifi) : QWidget(parent), wifi(wifi)
scanningLabel->setStyleSheet("font-size: 65px;");
main_layout->addWidget(scanningLabel, 0, Qt::AlignCenter);
list_layout = new QVBoxLayout;
main_layout->addLayout(list_layout);
wifi_list_widget = new ListWidget(this);
wifi_list_widget->setVisible(false);
main_layout->addWidget(wifi_list_widget);
setStyleSheet(R"(
QScrollBar::handle:vertical {
@ -279,76 +277,88 @@ WifiUI::WifiUI(QWidget *parent, WifiManager* wifi) : QWidget(parent), wifi(wifi)
}
void WifiUI::refresh() {
// TODO: don't rebuild this every time
clearLayout(list_layout);
bool is_empty = wifi->seenNetworks.isEmpty();
scanningLabel->setVisible(is_empty);
wifi_list_widget->setVisible(!is_empty);
if (is_empty) return;
setUpdatesEnabled(false);
const bool is_tethering_enabled = wifi->isTetheringEnabled();
QList<Network> sortedNetworks = wifi->seenNetworks.values();
std::sort(sortedNetworks.begin(), sortedNetworks.end(), compare_by_strength);
// add networks
ListWidget *list = new ListWidget(this);
int n = 0;
for (Network &network : sortedNetworks) {
QHBoxLayout *hlayout = new QHBoxLayout;
hlayout->setContentsMargins(44, 0, 73, 0);
hlayout->setSpacing(50);
// Clickable SSID label
ElidedLabel *ssidLabel = new ElidedLabel(network.ssid);
ssidLabel->setObjectName("ssidLabel");
ssidLabel->setEnabled(network.security_type != SecurityType::UNSUPPORTED);
ssidLabel->setProperty("disconnected", network.connected == ConnectedType::DISCONNECTED);
if (network.connected == ConnectedType::DISCONNECTED) {
QObject::connect(ssidLabel, &ElidedLabel::clicked, this, [=]() { emit connectToNetwork(network); });
}
hlayout->addWidget(ssidLabel, network.connected == ConnectedType::CONNECTING ? 0 : 1);
if (network.connected == ConnectedType::CONNECTING) {
QPushButton *connecting = new QPushButton(tr("CONNECTING..."));
connecting->setObjectName("connecting");
hlayout->addWidget(connecting, 2, Qt::AlignLeft);
}
// Forget button
if (wifi->isKnownConnection(network.ssid) && !is_tethering_enabled) {
QPushButton *forgetBtn = new QPushButton(tr("FORGET"));
forgetBtn->setObjectName("forgetBtn");
QObject::connect(forgetBtn, &QPushButton::clicked, [=]() {
if (ConfirmationDialog::confirm(tr("Forget Wi-Fi Network \"%1\"?").arg(QString::fromUtf8(network.ssid)), tr("Forget"), this)) {
wifi->forgetConnection(network.ssid);
}
});
hlayout->addWidget(forgetBtn, 0, Qt::AlignRight);
}
// Status icon
QPixmap status_icon;
if (network.connected == ConnectedType::CONNECTED) {
QLabel *connectIcon = new QLabel();
connectIcon->setPixmap(checkmark);
hlayout->addWidget(connectIcon, 0, Qt::AlignRight);
status_icon = checkmark;
} else if (network.security_type == SecurityType::UNSUPPORTED) {
QLabel *unsupportedIcon = new QLabel();
unsupportedIcon->setPixmap(circled_slash);
hlayout->addWidget(unsupportedIcon, 0, Qt::AlignRight);
status_icon = circled_slash;
} else if (network.security_type == SecurityType::WPA) {
QLabel *lockIcon = new QLabel();
lockIcon->setPixmap(lock);
hlayout->addWidget(lockIcon, 0, Qt::AlignRight);
} else {
hlayout->addSpacing(lock.width() + hlayout->spacing());
status_icon = lock;
}
bool show_forget_btn = wifi->isKnownConnection(network.ssid) && !is_tethering_enabled;
QPixmap strength = strengths[std::clamp((int)round(network.strength / 33.), 0, 3)];
// Strength indicator
QLabel *strength = new QLabel();
strength->setPixmap(strengths[std::clamp((int)round(network.strength / 33.), 0, 3)]);
hlayout->addWidget(strength, 0, Qt::AlignRight);
auto item = getItem(n++);
item->setItem(network, status_icon, show_forget_btn, strength);
item->setVisible(true);
}
for (; n < wifi_items.size(); ++n) wifi_items[n]->setVisible(false);
list->addItem(hlayout);
setUpdatesEnabled(true);
}
WifiItem *WifiUI::getItem(int n) {
auto item = n < wifi_items.size() ? wifi_items[n] : wifi_items.emplace_back(new WifiItem(tr("CONNECTING..."), tr("FORGET")));
if (!item->parentWidget()) {
QObject::connect(item, &WifiItem::connectToNetwork, this, &WifiUI::connectToNetwork);
QObject::connect(item, &WifiItem::forgotNetwork, [this](const Network &n) {
if (ConfirmationDialog::confirm(tr("Forget Wi-Fi Network \"%1\"?").arg(QString::fromUtf8(n.ssid)), tr("Forget"), this))
wifi->forgetConnection(n.ssid);
});
wifi_list_widget->addItem(item);
}
list_layout->addWidget(list);
list_layout->addStretch(1);
return item;
}
// WifiItem
WifiItem::WifiItem(const QString &connecting_text, const QString &forget_text, QWidget *parent) : QWidget(parent) {
QHBoxLayout *hlayout = new QHBoxLayout(this);
hlayout->setContentsMargins(44, 0, 73, 0);
hlayout->setSpacing(50);
hlayout->addWidget(ssidLabel = new ElidedLabel());
ssidLabel->setObjectName("ssidLabel");
ssidLabel->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred);
hlayout->addWidget(connecting = new QPushButton(connecting_text), 0, Qt::AlignRight);
connecting->setObjectName("connecting");
hlayout->addWidget(forgetBtn = new QPushButton(forget_text), 0, Qt::AlignRight);
forgetBtn->setObjectName("forgetBtn");
hlayout->addWidget(iconLabel = new QLabel(), 0, Qt::AlignRight);
hlayout->addWidget(strengthLabel = new QLabel(), 0, Qt::AlignRight);
QObject::connect(forgetBtn, &QPushButton::clicked, [this]() { emit forgotNetwork(network); });
QObject::connect(ssidLabel, &ElidedLabel::clicked, [this]() {
if (network.connected == ConnectedType::DISCONNECTED) emit connectToNetwork(network);
});
}
void WifiItem::setItem(const Network &n, const QPixmap &status_icon, bool show_forget_btn, const QPixmap &strength_icon) {
network = n;
ssidLabel->setText(n.ssid);
ssidLabel->setEnabled(n.security_type != SecurityType::UNSUPPORTED);
ssidLabel->setProperty("disconnected", network.connected == ConnectedType::DISCONNECTED);
ssidLabel->style()->unpolish(ssidLabel);
ssidLabel->style()->polish(ssidLabel);
ssidLabel->update();
connecting->setVisible(n.connected == ConnectedType::CONNECTING);
forgetBtn->setVisible(show_forget_btn);
iconLabel->setPixmap(status_icon);
strengthLabel->setPixmap(strength_icon);
}

@ -1,14 +1,29 @@
#pragma once
#include <QButtonGroup>
#include <QVBoxLayout>
#include <QWidget>
#include "selfdrive/ui/qt/offroad/wifiManager.h"
#include "selfdrive/ui/qt/widgets/input.h"
#include "selfdrive/ui/qt/widgets/ssh_keys.h"
#include "selfdrive/ui/qt/widgets/toggle.h"
class WifiItem : public QWidget {
Q_OBJECT
public:
explicit WifiItem(const QString &connecting_text, const QString &forget_text, QWidget* parent = nullptr);
void setItem(const Network& n, const QPixmap &icon, bool show_forget_btn, const QPixmap &strength);
signals:
void connectToNetwork(const Network &n);
void forgotNetwork(const Network &n);
protected:
ElidedLabel* ssidLabel;
QPushButton* connecting;
QPushButton* forgetBtn;
QLabel* iconLabel;
QLabel* strengthLabel;
Network network;
};
class WifiUI : public QWidget {
Q_OBJECT
@ -16,14 +31,16 @@ public:
explicit WifiUI(QWidget *parent = 0, WifiManager* wifi = 0);
private:
WifiItem *getItem(int n);
WifiManager *wifi = nullptr;
QVBoxLayout *list_layout = nullptr;
QLabel *scanningLabel = nullptr;
QVBoxLayout* main_layout;
QPixmap lock;
QPixmap checkmark;
QPixmap circled_slash;
QVector<QPixmap> strengths;
ListWidget *wifi_list_widget = nullptr;
std::vector<WifiItem*> wifi_items;
signals:
void connectToNetwork(const Network &n);
@ -65,10 +82,8 @@ private:
QStackedLayout* main_layout = nullptr;
QWidget* wifiScreen = nullptr;
AdvancedNetworking* an = nullptr;
WifiUI* wifiWidget;
protected:
void showEvent(QShowEvent* event) override;
void hideEvent(QHideEvent* event) override;

@ -51,19 +51,6 @@ QMap<QString, QString> getSupportedLanguages() {
return map;
}
void clearLayout(QLayout* layout) {
while (layout->count() > 0) {
QLayoutItem* item = layout->takeAt(0);
if (QWidget* widget = item->widget()) {
widget->deleteLater();
}
if (QLayout* childLayout = item->layout()) {
clearLayout(childLayout);
}
delete item;
}
}
QString timeAgo(const QDateTime &date) {
int diff = date.secsTo(QDateTime::currentDateTimeUtc());

@ -4,7 +4,6 @@
#include <QDateTime>
#include <QFileSystemWatcher>
#include <QLayout>
#include <QPainter>
#include <QPixmap>
#include <QSurfaceFormat>
@ -18,7 +17,6 @@ QString getBrand();
QString getUserAgent();
std::optional<QString> getDongleId();
QMap<QString, QString> getSupportedLanguages();
void clearLayout(QLayout* layout);
void setQtSurfaceFormat();
void sigTermHandler(int s);
QString timeAgo(const QDateTime &date);

@ -7,6 +7,20 @@
#include "selfdrive/ui/qt/util.h"
// TODO: remove clearLayout
static void clearLayout(QLayout* layout) {
while (layout->count() > 0) {
QLayoutItem* item = layout->takeAt(0);
if (QWidget* widget = item->widget()) {
widget->deleteLater();
}
if (QLayout* childLayout = item->layout()) {
clearLayout(childLayout);
}
delete item;
}
}
PandaStream::PandaStream(QObject *parent, PandaStreamConfig config_) : config(config_), LiveStream(parent) {
if (config.serial.isEmpty()) {
auto serials = Panda::list();

Loading…
Cancel
Save