Browse Source

gui update db and connection

chatgui
jeka 3 months ago
parent
commit
861d81815f
  1. 171
      tools/chatgui/src/joindialog.cpp
  2. 36
      tools/chatgui/src/joindialog.h

171
tools/chatgui/src/joindialog.cpp

@ -0,0 +1,171 @@
#include "joindialog.h"
#include "invite_link.h"
#include "debug_ui.h"
#include "../transport/utun_node.h"
#include "../transport/gui_bridge.h"
#include "../transport/chat_sync.h"
#include "../db/db_manager.h"
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QPushButton>
#include <QTimer>
#include <QMessageBox>
#include <QApplication>
#include <cstring>
extern "C" {
#include "../../../lib/sha256.h"
}
JoinDialog::JoinDialog(UtunNode* node, DbManager* db, QWidget* parent)
: QDialog(parent)
, m_node(node)
, m_db(db)
{
setWindowTitle("Join Channel");
setMinimumWidth(420);
setModal(true);
auto *layout = new QVBoxLayout(this);
layout->setSpacing(12);
layout->setContentsMargins(20, 16, 20, 16);
auto *titleLabel = new QLabel("Paste invite link:", this);
titleLabel->setStyleSheet("font-weight: bold; font-size: 13px;");
layout->addWidget(titleLabel);
m_linkEdit = new QLineEdit(this);
m_linkEdit->setPlaceholderText("utun://...");
m_linkEdit->setStyleSheet(
"QLineEdit { border: 1px solid palette(mid); border-radius: 6px;"
" padding: 8px 12px; font-size: 13px; background: palette(base); }");
layout->addWidget(m_linkEdit);
m_statusLabel = new QLabel(this);
m_statusLabel->setWordWrap(true);
m_statusLabel->setStyleSheet("color: gray; font-size: 12px; padding: 4px 0;");
layout->addWidget(m_statusLabel);
layout->addStretch();
auto *btnLayout = new QHBoxLayout();
btnLayout->setSpacing(8);
btnLayout->addStretch();
m_cancelBtn = new QPushButton("Cancel", this);
m_cancelBtn->setFixedWidth(90);
m_cancelBtn->setStyleSheet(
"QPushButton { border: 1px solid palette(mid); border-radius: 4px;"
" padding: 6px 16px; font-size: 13px; background: palette(button); }"
"QPushButton:hover { background: palette(light); }");
connect(m_cancelBtn, &QPushButton::clicked, this, &QDialog::reject);
btnLayout->addWidget(m_cancelBtn);
m_connectBtn = new QPushButton("Connect", this);
m_connectBtn->setFixedWidth(90);
m_connectBtn->setDefault(true);
m_connectBtn->setStyleSheet(
"QPushButton { border: none; border-radius: 4px;"
" padding: 6px 16px; font-size: 13px; font-weight: bold;"
" background: #3390EC; color: white; }"
"QPushButton:hover { background: #2B7ED4; }"
"QPushButton:disabled { background: palette(mid); color: palette(midlight); }");
connect(m_connectBtn, &QPushButton::clicked, this, &JoinDialog::onConnectClicked);
btnLayout->addWidget(m_connectBtn);
layout->addLayout(btnLayout);
connect(m_linkEdit, &QLineEdit::returnPressed, this, &JoinDialog::onConnectClicked);
gui_bridge_set_connect_result_cb([](uint64_t nodeId, int result) {
JoinDialog* dlg = qobject_cast<JoinDialog*>(QApplication::activeModalWidget());
if (dlg) dlg->onConnectResult(nodeId, result);
});
}
JoinDialog::~JoinDialog() {
gui_bridge_set_connect_result_cb(nullptr);
}
void JoinDialog::setStatus(const QString& text, bool isError) {
if (isError)
m_statusLabel->setStyleSheet("color: #D0021B; font-size: 12px; padding: 4px 0;");
else
m_statusLabel->setStyleSheet("color: gray; font-size: 12px; padding: 4px 0;");
m_statusLabel->setText(text);
}
void JoinDialog::onConnectClicked() {
if (m_connecting) return;
QString link = m_linkEdit->text().trimmed();
if (link.isEmpty()) {
setStatus("Enter an invite link.", true);
return;
}
setStatus("Parsing link...");
InviteData d = decodeInviteLink(link);
if (d.channelId.isEmpty() || d.pubkey.size() != 32) {
setStatus("Invalid invite link.", true);
return;
}
if (d.addrs.isEmpty()) {
setStatus("No peer addresses in the invite link.", true);
return;
}
uint8_t hash[32];
SC_SHA256_CTX ctx;
sc_sha256_init(&ctx);
sc_sha256_update(&ctx, (const uint8_t*)d.pubkey.constData(), 32);
sc_sha256_final(&ctx, hash);
uint64_t nodeId;
memcpy(&nodeId, hash, sizeof(nodeId));
nodeId &= 0x7FFFFFFFFFFFFFFFULL;
m_pendingNodeId = nodeId;
m_connecting = true;
m_connectBtn->setEnabled(false);
m_linkEdit->setReadOnly(true);
setStatus("Connecting to peer...");
QByteArray addrsBuf;
for (const auto& a : d.addrs) {
addrsBuf.append(static_cast<char>(a.family));
addrsBuf.append(a.address);
addrsBuf.append(static_cast<char>((a.port >> 8) & 0xFF));
addrsBuf.append(static_cast<char>(a.port & 0xFF));
}
QByteArray chId = d.channelId.toUtf8();
int addrCount = d.addrs.size();
chat_sync_connect_from_invite(nodeId,
(const uint8_t*)d.pubkey.constData(),
(const uint8_t*)addrsBuf.constData(), addrCount,
(const uint8_t*)chId.constData(), chId.size());
}
void JoinDialog::onConnectResult(uint64_t nodeId, int result) {
if (!m_connecting || nodeId != m_pendingNodeId) return;
if (result == 0) {
setStatus("Connected successfully!");
QTimer::singleShot(800, this, [this] { accept(); });
} else {
m_connecting = false;
m_connectBtn->setEnabled(true);
m_linkEdit->setReadOnly(false);
m_connectBtn->setFocus();
const char* errMsg = "Unknown error.";
switch (result) {
case -3: errMsg = "Connection timed out."; break;
case -4: errMsg = "Peer is unreachable."; break;
case -6: errMsg = "Already connected to this peer."; break;
default: break;
}
setStatus(QString("Connection failed: %1").arg(errMsg), true);
}
}

36
tools/chatgui/src/joindialog.h

@ -0,0 +1,36 @@
#pragma once
#include <QDialog>
#include <QLineEdit>
#include <QLabel>
#include <QPushButton>
#include <cstdint>
class UtunNode;
class DbManager;
class JoinDialog : public QDialog {
Q_OBJECT
public:
explicit JoinDialog(UtunNode* node, DbManager* db, QWidget* parent = nullptr);
~JoinDialog() override;
signals:
void joined(const QString& channelId);
private slots:
void onConnectClicked();
private:
void setStatus(const QString& text, bool isError = false);
void onConnectResult(uint64_t nodeId, int result);
UtunNode* m_node;
DbManager* m_db;
QLineEdit* m_linkEdit;
QLabel* m_statusLabel;
QPushButton* m_connectBtn;
QPushButton* m_cancelBtn;
bool m_connecting = false;
uint64_t m_pendingNodeId = 0;
};
Loading…
Cancel
Save