implement drop file/text/image &&

add import from file option
This commit is contained in:
Nova 2025-10-06 02:25:40 +03:30
parent 930ed61f7e
commit ea73f7d28f
4 changed files with 108 additions and 19 deletions

View File

@ -17,15 +17,15 @@ namespace Configs {
// Amnezia Options
bool enable_amnezia = false;
int junk_packet_count;
int junk_packet_min_size;
int junk_packet_max_size;
int init_packet_junk_size;
int response_packet_junk_size;
int init_packet_magic_header;
int response_packet_magic_header;
int underload_packet_magic_header;
int transport_packet_magic_header;
int junk_packet_count = 0;
int junk_packet_min_size = 0;
int junk_packet_max_size = 0;
int init_packet_junk_size = 0;
int response_packet_junk_size = 0;
int init_packet_magic_header = 0;
int response_packet_magic_header = 0;
int underload_packet_magic_header = 0;
int transport_packet_magic_header = 0;
WireguardBean() : AbstractBean(0) {
_add(new configItem("private_key", &privateKey, itemType::string));

View File

@ -232,10 +232,16 @@ private:
void refresh_table_item(int row, const std::shared_ptr<Configs::ProxyEntity>& profile, bool stopping);
void parseQrImage(const QPixmap *image);
void keyPressEvent(QKeyEvent *event) override;
void closeEvent(QCloseEvent *event) override;
void dragEnterEvent(QDragEnterEvent *event);
void dropEvent(QDropEvent* event) override;
//
void HotkeyEvent(const QString &key);

View File

@ -557,7 +557,7 @@
<x>0</x>
<y>0</y>
<width>800</width>
<height>17</height>
<height>25</height>
</rect>
</property>
<widget class="QMenu" name="menu_program">
@ -575,6 +575,7 @@
<addaction name="actionHide_window"/>
<addaction name="separator"/>
<addaction name="menu_add_from_clipboard2"/>
<addaction name="actionAdd_profile_from_File"/>
<addaction name="menu_scan_qr"/>
<addaction name="separator"/>
<addaction name="actionStart_with_system"/>
@ -1052,6 +1053,11 @@
<string>Hide window</string>
</property>
</action>
<action name="actionAdd_profile_from_File">
<property name="text">
<string>Add profile from File</string>
</property>
</action>
</widget>
<customwidgets>
<customwidget>

View File

@ -49,7 +49,9 @@
#if QT_VERSION >= QT_VERSION_CHECK(6, 5, 0)
#include <QStyleHints>
#endif
#include <QFileDialog>
#include <QToolTip>
#include <QMimeData>
#include <random>
#include <3rdparty/QHotkey/qhotkey.h>
#include <3rdparty/qv2ray/v2/proxy/QvProxyConfigurator.hpp>
@ -66,6 +68,7 @@ void UI_InitMainWindow() {
MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent), ui(new Ui::MainWindow) {
mainwindow = this;
setAcceptDrops(true);
MW_dialog_message = [=,this](const QString &a, const QString &b) {
runOnUiThread([=,this]
{
@ -588,6 +591,25 @@ MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent), ui(new Ui::MainWi
ui->menu_export_config->setVisible(name == software_core_name);
ui->menu_export_config->setText(tr("Export %1 config").arg(name));
});
connect(ui->actionAdd_profile_from_File, &QAction::triggered, this, [=,this]()
{
auto path = QFileDialog::getOpenFileName();
if (path.isEmpty())
{
return;
}
auto file = QFile(path);
if (!file.exists()) return;
if (file.size() > 50 * 1024 * 1024)
{
MW_show_log("File too large, will not process it");
return;
}
file.open(QIODevice::ReadOnly);
auto contents = file.readAll();
file.close();
Subscription::groupUpdater->AsyncUpdate(contents);
});
connect(qApp, &QGuiApplication::commitDataRequest, this, &MainWindow::on_commitDataRequest);
@ -622,6 +644,55 @@ void MainWindow::closeEvent(QCloseEvent *event) {
}
}
void MainWindow::dragEnterEvent(QDragEnterEvent *event)
{
if (event->mimeData()->hasUrls() || event->mimeData()->hasText()) {
event->acceptProposedAction();
} else {
event->ignore();
}
}
void MainWindow::dropEvent(QDropEvent* event)
{
auto mimeData = event->mimeData();
if (mimeData->hasUrls()) {
QList<QUrl> urlList = mimeData->urls();
for (const QUrl &url : urlList) {
if (url.isLocalFile()) {
if (auto qpx = QPixmap(url.toLocalFile()); !qpx.isNull())
{
parseQrImage(&qpx);
} else if (auto file = QFile(url.toLocalFile()); file.exists())
{
file.open(QFile::ReadOnly);
if (file.size() > 50 * 1024 * 1024)
{
file.close();
MW_show_log("File size is larger than 50MB, will not parse it");
event->acceptProposedAction();
return;
}
auto contents = file.readAll();
file.close();
Subscription::groupUpdater->AsyncUpdate(contents);
}
}
}
event->acceptProposedAction();
return;
}
if (mimeData->hasText()) {
Subscription::groupUpdater->AsyncUpdate(mimeData->text());
event->acceptProposedAction();
return;
}
event->ignore();
}
MainWindow::~MainWindow() {
delete ui;
}
@ -1898,6 +1969,19 @@ QPixmap grabScreen(QScreen* screen, bool& ok)
return screen->grabWindow(0, geom.x(), geom.y(), geom.width(), geom.height());
}
void MainWindow::parseQrImage(const QPixmap *image)
{
const QVector<QString> texts = QrDecoder().decode(image->toImage().convertToFormat(QImage::Format_Grayscale8));
if (texts.isEmpty()) {
MessageBoxInfo(software_name, tr("QR Code not found"));
} else {
for (const QString &text : texts) {
show_log_impl("QR Code Result:\n" + text);
Subscription::groupUpdater->AsyncUpdate(text);
}
}
}
void MainWindow::on_menu_scan_qr_triggered() {
hide();
QThread::sleep(1);
@ -1907,15 +1991,7 @@ void MainWindow::on_menu_scan_qr_triggered() {
show();
if (ok) {
const QVector<QString> texts = QrDecoder().decode(qpx.toImage().convertToFormat(QImage::Format_Grayscale8));
if (texts.isEmpty()) {
MessageBoxInfo(software_name, tr("QR Code not found"));
} else {
for (const QString &text : texts) {
show_log_impl("QR Code Result:\n" + text);
Subscription::groupUpdater->AsyncUpdate(text);
}
}
parseQrImage(&qpx);
}
else {
MessageBoxInfo(software_name, tr("Unable to capture screen"));
@ -2370,6 +2446,7 @@ void MainWindow::setActionsData()
ui->actionUrl_Test_Group->setData(QString("m21"));
ui->actionUrl_Test_Selected->setData(QString("m22"));
ui->actionHide_window->setData(QString("m23"));
ui->actionAdd_profile_from_File->setData(QString("m24"));
}
QList<QAction*> MainWindow::getActionsForShortcut()