From 11787ea278bc6ff6d5bc797b597df3f26e2ec9b4 Mon Sep 17 00:00:00 2001 From: Daniel Teichmann Date: Tue, 6 Jul 2021 19:55:13 +0200 Subject: Introduce DBusAPI and RWAHost classes --- src/session.cpp | 270 ++++++++++++++------------------------------------------ 1 file changed, 66 insertions(+), 204 deletions(-) (limited to 'src/session.cpp') diff --git a/src/session.cpp b/src/session.cpp index f3aa168..1ee4eef 100644 --- a/src/session.cpp +++ b/src/session.cpp @@ -26,51 +26,74 @@ #include "session.h" -Session::Session(QObject *parent, MainQMLAdaptor* main_gui) : QObject(parent) { - _initDBus(); +Session::Session(QObject *parent, MainQMLAdaptor* main_gui, RWAHost *host) : QObject(parent) { + Q_ASSERT(main_gui != nullptr); + Q_ASSERT(host != nullptr); + _dbus_api = new DBusAPI(); _main_gui = main_gui; + _host = host; // QML -> MainQMLAdaptor::handleConnectButtonClick --onConnectButtonClick--> this::handleConnectButtonClick QObject::connect(_main_gui, - SIGNAL(onConnectButtonClick(bool)), - this, - SLOT(handleConnectButtonClick(bool))); + SIGNAL(onConnectButtonClick(bool)), + this, + SLOT(handleConnectButtonClick(bool))); // session::setPin --pinChanged--> MainQMLAdaptor::setPin --pinChanged--> QML QObject::connect(this, - SIGNAL(pinChanged(QString)), - main_gui, - SLOT(setPin(QString))); + SIGNAL(pinChanged(QString)), + main_gui, + SLOT(setPin(QString))); + // session::setURL --urlChanged--> MainQMLAdaptor::setURL --urlChanged--> QML QObject::connect(this, - SIGNAL(urlChanged(QString)), - main_gui, - SLOT(setURL(QString))); + SIGNAL(urlChanged(QString)), + main_gui, + SLOT(setURL(QString))); + // session::setSessionID --sessionIDChanged--> MainQMLAdaptor::setSessionID --sessionIDChanged--> QML QObject::connect(this, - SIGNAL(sessionIDChanged(QString)), - main_gui, - SLOT(setSessionID(QString))); + SIGNAL(sessionIDChanged(QString)), + main_gui, + SLOT(setSessionID(QString))); // QML -> MainQMLAdaptor::onCloseHandler --onCloseSignal--> session::onCloseHandler QObject::connect(main_gui, - SIGNAL(onCloseSignal()), - this, - SLOT(onCloseHandler())); + SIGNAL(onCloseSignal()), + this, + SLOT(onCloseHandler())); + + // _dbus_api --sessionStartResponse-> this.start_response() + QObject::connect(_dbus_api, + SIGNAL(serviceStartResponse(QJsonDocument*)), + this, + SLOT(start_response(QJsonDocument*))); + + // _dbus_api --sessionStopResponse-> this.stop_response() + QObject::connect(_dbus_api, + SIGNAL(serviceStopResponse(QJsonDocument*)), + this, + SLOT(stop_response(QJsonDocument*))); + + // _dbus_api --sessionStatusResponse-> this.status_response() + QObject::connect(_dbus_api, + SIGNAL(serviceStatusResponse(QJsonDocument*)), + this, + SLOT(status_response(QJsonDocument*))); + this->init_vars(); } void Session::statusTimerEvent() { - qDebug() << "Status timer event triggered"; - this->refresh_status_request_dbus(this->getHostID(), this->getID()); + qDebug() << "Status timer event got triggered just now."; + this->status(); } void Session::init_vars() { setPin("-----"); setSessionID("-----"); - setID("-----"); setURL(tr("Not available yet")); setStatus("unknown"); @@ -89,18 +112,10 @@ QString Session::getURL() { return _url; } -QString Session::getID() { - return QString(_id); -} - QString Session::getSessionID() { return QString(_session_id); } -QString Session::getHostID() { - return QString(_host_id); -} - QString Session::getPin() { return _pin; } @@ -201,11 +216,6 @@ void Session::setURL(QString url) { emit urlChanged(url); } -void Session::setID(QString id) { - _id = id; - emit idChanged(id); -} - void Session::setSessionID(QString session_id) { _session_id = session_id; emit sessionIDChanged(session_id); @@ -218,79 +228,33 @@ void Session::setPin(QString pin) { void Session::handleConnectButtonClick(bool checked) { qDebug() << "-----Connect button handler-----" << - "\nCurrent service-session #" << this->getID() << - "\nCurrent support-session #" << this->getSessionID(); + "\nCurrent session #" << this->getSessionID(); // Stopping even if nothing is running - this->stop_request_dbus(this->getID()); + _dbus_api->stop_request(_host, this->getSessionID()); if (checked) { // Start the Session again - this->start_request_dbus(getHostID()); + _dbus_api->start_request(_host); } qDebug() << "-----\\Connect button handler-----"; } -void Session::_initDBus() { - if (!QDBusConnection::sessionBus().isConnected()) { - qCritical() << "Cannot connect to the D-Bus session bus."; - } - - // Create DBus object - _dbus_rwa = new OrgArcticaProjectRWASupportSessionServiceInterface("org.ArcticaProject.RWASupportSessionService", "/RWASupportSessionService", - QDBusConnection::sessionBus(), this->parent()); - - qDebug("Initialized DBus object!"); -} - -void Session::start_request_dbus(QString host_id) { - qDebug() << "Requesting D-Bus session service to start a new session on host: " << host_id; - bool ok; - host_id.toLongLong(&ok); - if(ok == false){ - qErrnoWarning("Unable to convert id to "); - return; - } - - // Make an asynchrous 'start' call (Response will be sent to 'start_dbus_replied') - QDBusPendingCall async = _dbus_rwa->asyncCall("start", host_id); - QDBusPendingCallWatcher *watcher = new QDBusPendingCallWatcher(async, this); - - QObject::connect(watcher, SIGNAL(finished(QDBusPendingCallWatcher*)), - this, SLOT(start_dbus_replied(QDBusPendingCallWatcher*))); - +void Session::start() { // Disable connect button to reduce spam. // And don't enable it as long there is no status update. // (Or something fails) _main_gui->setConnectButtonEnabled(false); this->setStatus("waiting_start_request_answer"); -} -void Session::start_dbus_replied(QDBusPendingCallWatcher *call) { - QString result = ""; - - QDBusPendingReply reply = *call; - if (reply.isError()) { - qDebug() << "D-Bus 'start' request failed, this was the reply:"; - qDebug() << reply.error(); - - // The user should have the oportunity to try again. - this->init_vars(); - - qCritical() << "An error occured while creating a new session!"; - this->setStatus("start_session_error"); - - return; - } else { - result = reply.argumentAt<0>(); - } - call->deleteLater(); + _dbus_api->start_request(_host); +} - qDebug() << "Raw JSON from starting session is:" << result; - QJsonDocument doc = QJsonDocument::fromJson(result.toUtf8()); +void Session::start_response(QJsonDocument *doc) { + Q_ASSERT(doc != nullptr); // Get the QJsonObject - QJsonObject jObject = doc.object(); + QJsonObject jObject = doc->object(); QVariantMap mainMap = jObject.toVariantMap(); // Status of request @@ -308,16 +272,7 @@ void Session::start_dbus_replied(QDBusPendingCallWatcher *call) { return; } - // Service ID == PID bool ok; - long long service_id = mainMap["id"].toLongLong(&ok); - this->setID(QString::number(service_id)); - // Sanity Check - if(ok == false){ - qErrnoWarning("Unable to parse out of dbus answer!"); - init_vars(); - return; - } // URL of remote web app frontend QString url = mainMap["url"].toString(); @@ -343,37 +298,17 @@ void Session::start_dbus_replied(QDBusPendingCallWatcher *call) { return; } - qDebug() << "Got service_id:" << service_id << - "\nGot session_id:" << session_id << + qDebug() << "Got session_id:" << session_id << "\nGot url:" << url << "\nGot pin:" << pin; emit pinChanged(QString::number(pin)); emit urlChanged(url); - emit idChanged(QString::number(service_id)); emit sessionIDChanged(QString::number(session_id)); } -void Session::stop_request_dbus(QString id) { - bool ok; - if (id.toLongLong(&ok) == 0 ){ - qDebug() << "Won't send a request to D-Bus service to stop a session when session ID == 0"; - return; - } - if(ok == false){ - qErrnoWarning("Unable to convert id to "); - return; - } - - // Stopping now. - qDebug() << "Requesting D-Bus session service to stop session #" << id; - - // Make an asynchrous 'stop' call (Response will be sent to 'stop_dbus_replied') - QDBusPendingCall async = _dbus_rwa->asyncCall("stop", id); - QDBusPendingCallWatcher *watcher = new QDBusPendingCallWatcher(async, this); - - QObject::connect(watcher, SIGNAL(finished(QDBusPendingCallWatcher*)), - this, SLOT(stop_dbus_replied(QDBusPendingCallWatcher*))); +void Session::stop() { + _dbus_api->stop_request(_host, this->getSessionID()); // Clear current variables this->init_vars(); @@ -384,30 +319,14 @@ void Session::stop_request_dbus(QString id) { _main_gui->setConnectButtonEnabled(false); } -void Session::stop_dbus_replied(QDBusPendingCallWatcher *call) { - QString result = ""; - - QDBusPendingReply reply = *call; - if (reply.isError()) { - qDebug() << "D-Bus 'stop' request failed, this was the reply:"; - qDebug() << reply.error(); - - this->init_vars(); - this->setStatus("stop_session_error"); - - return; - } else { - result = reply.argumentAt<0>(); - } - call->deleteLater(); +void Session::stop_response(QJsonDocument *doc) { + Q_ASSERT(doc != nullptr); - // Get the QJsonObject - QJsonDocument doc = QJsonDocument::fromJson(result.toUtf8()); - QJsonObject jObject = doc.object(); + QJsonObject jObject = doc->object(); QVariantMap mainMap = jObject.toVariantMap(); QString new_status = mainMap["status"].toString(); - qDebug() << "stop_dbus_replied(): Refreshed status:" << new_status; + qDebug() << "stop_response() retrieved json. Status now:" << new_status; // Clear current variables this->init_vars(); @@ -416,74 +335,17 @@ void Session::stop_dbus_replied(QDBusPendingCallWatcher *call) { this->setStatus(new_status); } -void Session::status_request_dbus(QString id) { - bool ok; - if (id.toLongLong(&ok) == 0 ){ - qDebug() << "Won't send a request to D-Bus service of a session's status when session ID == 0"; - return; - } - if(ok == false){ - qErrnoWarning("Unable to convert id to "); - return; - } - - // Requesting status now. - qDebug() << "Requesting status for session #" << id; - - // Make an asynchrous 'status' call (Response will be sent to 'status_dbus_replied') - QDBusPendingCall async = _dbus_rwa->asyncCall("status", id); - QDBusPendingCallWatcher *watcher = new QDBusPendingCallWatcher(async, this); - - QObject::connect(watcher, SIGNAL(finished(QDBusPendingCallWatcher*)), - this, SLOT(stop_dbus_replied(QDBusPendingCallWatcher*))); +void Session::status() { + _dbus_api->status_request(_host, this->getSessionID()); } -void Session::refresh_status_request_dbus(QString host_id, QString id) { - bool ok; - if (id.toLongLong(&ok) == 0){ - qDebug() << "Won't send a request to D-Bus service to refresh the status of a session when session ID == 0"; - return; - } - if(ok == false){ - qErrnoWarning("Unable to convert id to "); - return; - } - - // Refreshing status - qDebug() << "Requesting status refresh for session #" << id; - - // Make an asynchrous 'refresh_status' call (Response will be sent to 'status_dbus_replied') - QDBusPendingCall async = _dbus_rwa->asyncCall("refresh_status", host_id, id); - QDBusPendingCallWatcher *watcher = new QDBusPendingCallWatcher(async, this); - - QObject::connect(watcher, SIGNAL(finished(QDBusPendingCallWatcher*)), - this, SLOT(status_dbus_replied(QDBusPendingCallWatcher*))); -} +void Session::status_response(QJsonDocument *doc) { + Q_ASSERT(doc != nullptr); -void Session::status_dbus_replied(QDBusPendingCallWatcher *call) { - QString result = ""; - - QDBusPendingReply reply = *call; - if (reply.isError()) { - qDebug() << "D-Bus '(refresh_)status' request failed, this was the reply:"; - qDebug() << reply.error(); - - this->init_vars(); - - this->setStatus("status_session_error"); - - return; - } else { - result = reply.argumentAt<0>(); - } - call->deleteLater(); - - // Get the QJsonObject - QJsonDocument doc = QJsonDocument::fromJson(result.toUtf8()); - QJsonObject jObject = doc.object(); + QJsonObject jObject = doc->object(); QVariantMap mainMap = jObject.toVariantMap(); QString new_status = mainMap["status"].toString(); - qDebug() << "status_dbus_replied(): Refreshed status:" << new_status; + qDebug() << "status_response() retrieved json. Status:" << new_status; // Enable (dis)connect button _main_gui->setConnectButtonEnabled(true); @@ -498,5 +360,5 @@ void Session::status_dbus_replied(QDBusPendingCallWatcher *call) { void Session::onCloseHandler() { // To cleanup things here - this->stop_request_dbus(this->getID()); + _dbus_api->stop_request(_host, this->getSessionID()); } -- cgit v1.2.3 From 98049d1507a6f2ae232782fd79f4f753ad53eead Mon Sep 17 00:00:00 2001 From: Daniel Teichmann Date: Tue, 6 Jul 2021 20:02:31 +0200 Subject: Fix copyright headers --- qtquickcontrols2.conf | 4 ++-- src/DBusAPI.cpp | 25 +++++++++++++++++++++++++ src/DBusAPI.h | 25 +++++++++++++++++++++++++ src/ListItem.qml | 25 +++++++++++++++++++++++++ src/RWADBusAdaptor.cpp | 25 +++++++++++++++++++++++++ src/RWADBusAdaptor.h | 25 +++++++++++++++++++++++++ src/Toast.qml | 4 ++-- src/ToastManager.qml | 4 ++-- src/main.cpp | 4 ++-- src/main.qml | 4 ++-- src/main_qmladaptor.cpp | 4 ++-- src/main_qmladaptor.h | 4 ++-- src/session.cpp | 4 ++-- src/session.h | 4 ++-- 14 files changed, 143 insertions(+), 18 deletions(-) (limited to 'src/session.cpp') diff --git a/qtquickcontrols2.conf b/qtquickcontrols2.conf index e646650..8bcc85b 100644 --- a/qtquickcontrols2.conf +++ b/qtquickcontrols2.conf @@ -1,7 +1,7 @@ # This file is part of Remote Support Desktop # https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp -# Copyright 2020-2021 Daniel Teichmann -# Copyright 2020-2021 Mike Gabriel +# Copyright 2020, 2021 Daniel Teichmann +# Copyright 2020, 2021 Mike Gabriel # SPDX-License-Identifier: GPL-2.0-or-later # # This program is free software; you can redistribute it and/or modify diff --git a/src/DBusAPI.cpp b/src/DBusAPI.cpp index 0809a51..c133910 100644 --- a/src/DBusAPI.cpp +++ b/src/DBusAPI.cpp @@ -1,3 +1,28 @@ +/* + * This file is part of Remote Support Desktop + * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp + * Copyright 2021 Daniel Teichmann + * SPDX-License-Identifier: GPL-2.0-or-later + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the + * Free Software Foundation, Inc., + * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + #include "DBusAPI.h" /*! diff --git a/src/DBusAPI.h b/src/DBusAPI.h index 1564f57..632a90b 100644 --- a/src/DBusAPI.h +++ b/src/DBusAPI.h @@ -1,3 +1,28 @@ +/* + * This file is part of Remote Support Desktop + * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp + * Copyright 2021 Daniel Teichmann + * SPDX-License-Identifier: GPL-2.0-or-later + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the + * Free Software Foundation, Inc., + * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + #ifndef DBUSAPI_H #define DBUSAPI_H diff --git a/src/ListItem.qml b/src/ListItem.qml index c69af4b..fa83f4b 100644 --- a/src/ListItem.qml +++ b/src/ListItem.qml @@ -1,3 +1,28 @@ +/* + * This file is part of Remote Support Desktop + * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp + * Copyright 2021 Daniel Teichmann + * SPDX-License-Identifier: GPL-2.0-or-later + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the + * Free Software Foundation, Inc., + * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + import QtQuick 2.0 import QtQuick.Controls.Material 2.3 import QtQuick.Controls 2.2 diff --git a/src/RWADBusAdaptor.cpp b/src/RWADBusAdaptor.cpp index 381faca..6c1504e 100644 --- a/src/RWADBusAdaptor.cpp +++ b/src/RWADBusAdaptor.cpp @@ -1,3 +1,28 @@ +/* + * This file is part of Remote Support Desktop + * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp + * Copyright 2020, 2021 Daniel Teichmann + * SPDX-License-Identifier: GPL-2.0-or-later + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the + * Free Software Foundation, Inc., + * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + /* * This file was generated by qdbusxml2cpp version 0.8 * Command line was: qdbusxml2cpp -i src/RWADBusAdaptor.h -p :src/RWADBusAdaptor.cpp rwa.xml diff --git a/src/RWADBusAdaptor.h b/src/RWADBusAdaptor.h index 741687f..77f4b6c 100644 --- a/src/RWADBusAdaptor.h +++ b/src/RWADBusAdaptor.h @@ -1,3 +1,28 @@ +/* + * This file is part of Remote Support Desktop + * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp + * Copyright 2020, 2021 Daniel Teichmann + * SPDX-License-Identifier: GPL-2.0-or-later + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the + * Free Software Foundation, Inc., + * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + /* * This file was generated by qdbusxml2cpp version 0.8 * Command line was: qdbusxml2cpp -p src/RWADBusAdaptor.h: rwa.xml diff --git a/src/Toast.qml b/src/Toast.qml index eb65b20..a427d10 100644 --- a/src/Toast.qml +++ b/src/Toast.qml @@ -1,8 +1,8 @@ /* * This file is part of Remote Support Desktop * https://gitlab.das-netzwerkteam.de/RemoteWebApp/remote-support-desktop - * Copyright 2020-2021 Daniel Teichmann - * Copyright 2020-2021 Mike Gabriel + * Copyright 2020, 2021 Daniel Teichmann + * Copyright 2020, 2021 Mike Gabriel * SPDX-License-Identifier: GPL-2.0-or-later * * This program is free software; you can redistribute it and/or modify diff --git a/src/ToastManager.qml b/src/ToastManager.qml index b448905..1acf8d5 100644 --- a/src/ToastManager.qml +++ b/src/ToastManager.qml @@ -1,8 +1,8 @@ /* * This file is part of Remote Support Desktop * https://gitlab.das-netzwerkteam.de/RemoteWebApp/remote-support-desktop - * Copyright 2020-2021 Daniel Teichmann - * Copyright 2020-2021 Mike Gabriel + * Copyright 2020, 2021 Daniel Teichmann + * Copyright 2020, 2021 Mike Gabriel * SPDX-License-Identifier: GPL-2.0-or-later * * This program is free software; you can redistribute it and/or modify diff --git a/src/main.cpp b/src/main.cpp index f23e2c9..213a591 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1,8 +1,8 @@ /* * This file is part of Remote Support Desktop * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp - * Copyright 2020-2021 Daniel Teichmann - * Copyright 2020-2021 Mike Gabriel + * Copyright 2020, 2021 Daniel Teichmann + * Copyright 2020, 2021 Mike Gabriel * SPDX-License-Identifier: GPL-2.0-or-later * * This program is free software; you can redistribute it and/or modify diff --git a/src/main.qml b/src/main.qml index 1981f4f..a9bbed7 100644 --- a/src/main.qml +++ b/src/main.qml @@ -1,8 +1,8 @@ /* * This file is part of Remote Support Desktop * https://gitlab.das-netzwerkteam.de/RemoteWebApp/remote-support-desktop - * Copyright 2020-2021 Daniel Teichmann - * Copyright 2020-2021 Mike Gabriel + * Copyright 2020, 2021 Daniel Teichmann + * Copyright 2020, 2021 Mike Gabriel * SPDX-License-Identifier: GPL-2.0-or-later * * This program is free software; you can redistribute it and/or modify diff --git a/src/main_qmladaptor.cpp b/src/main_qmladaptor.cpp index 8a54eb3..731efaf 100644 --- a/src/main_qmladaptor.cpp +++ b/src/main_qmladaptor.cpp @@ -1,8 +1,8 @@ /* * This file is part of Remote Support Desktop * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp - * Copyright 2020-2021 Daniel Teichmann - * Copyright 2020-2021 Mike Gabriel + * Copyright 2020, 2021 Daniel Teichmann + * Copyright 2020, 2021 Mike Gabriel * SPDX-License-Identifier: GPL-2.0-or-later * * This program is free software; you can redistribute it and/or modify diff --git a/src/main_qmladaptor.h b/src/main_qmladaptor.h index 4619968..3c6e75b 100644 --- a/src/main_qmladaptor.h +++ b/src/main_qmladaptor.h @@ -1,8 +1,8 @@ /* * This file is part of Remote Support Desktop * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp - * Copyright 2020-2021 Daniel Teichmann - * Copyright 2020-2021 Mike Gabriel + * Copyright 2020, 2021 Daniel Teichmann + * Copyright 2020, 2021 Mike Gabriel * SPDX-License-Identifier: GPL-2.0-or-later * * This program is free software; you can redistribute it and/or modify diff --git a/src/session.cpp b/src/session.cpp index 1ee4eef..4640786 100644 --- a/src/session.cpp +++ b/src/session.cpp @@ -1,8 +1,8 @@ /* * This file is part of Remote Support Desktop * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp - * Copyright 2020-2021 Daniel Teichmann - * Copyright 2020-2021 Mike Gabriel + * Copyright 2020, 2021 Daniel Teichmann + * Copyright 2020, 2021 Mike Gabriel * SPDX-License-Identifier: GPL-2.0-or-later * * This program is free software; you can redistribute it and/or modify diff --git a/src/session.h b/src/session.h index 2c534f4..5935919 100644 --- a/src/session.h +++ b/src/session.h @@ -1,8 +1,8 @@ /* * This file is part of Remote Support Desktop * https://gitlab.das-netzwerkteam.de/RemoteWebApp/rwa.support.desktopapp - * Copyright 2020-2021 Daniel Teichmann - * Copyright 2020-2021 Mike Gabriel + * Copyright 2020, 2021 Daniel Teichmann + * Copyright 2020, 2021 Mike Gabriel * SPDX-License-Identifier: GPL-2.0-or-later * * This program is free software; you can redistribute it and/or modify -- cgit v1.2.3 From 61b4ee3b8f1d4c5d85b7a561551167fa41b12400 Mon Sep 17 00:00:00 2001 From: Daniel Teichmann Date: Tue, 6 Jul 2021 20:04:48 +0200 Subject: Tidy up some debug statements or long strings --- src/Toast.qml | 1 - src/main.cpp | 14 +++++++------- src/main.qml | 9 +++++++-- src/scenes/Scene_placeholder.qml | 2 +- src/session.cpp | 18 +++++++++++++----- 5 files changed, 28 insertions(+), 16 deletions(-) (limited to 'src/session.cpp') diff --git a/src/Toast.qml b/src/Toast.qml index a427d10..60e238c 100644 --- a/src/Toast.qml +++ b/src/Toast.qml @@ -58,7 +58,6 @@ Control { else { time = defaultTime; } - console.log("Showing a new toast with display time: " + time); animation.start(); } diff --git a/src/main.cpp b/src/main.cpp index 213a591..3339840 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -55,12 +55,12 @@ int main(int argc, char *argv[]) { tmpDir.mkpath("."); } QLockFile lockFile(tmpFilePath); - qDebug() << "Checking for a lockfile at: " + tmpFilePath; + qDebug().noquote() << QString("Checking for a lockfile at: '%0'").arg(tmpFilePath); if(!lockFile.tryLock(100)){ - qDebug() << QObject::tr("You already have this app running."); - qDebug() << QObject::tr("Only one instance is allowed."); - qDebug() << QObject::tr("Closing application now with an error."); + qDebug().noquote() << "You already have this app running.\n" + << "Only one instance is allowed.\n" + << "Closing application now with an error."; return 1; } @@ -71,12 +71,12 @@ int main(int argc, char *argv[]) { QQuickStyle::setStyle("Material"); QTranslator translator; - qDebug() << "Loading locale: qrc:/locales/bin/" + QLocale::system().name(); + qDebug().noquote() << QString("Locales: Loading locale: qrc:/locales/bin/%0").arg(QLocale::system().name()); if(translator.load(":/locales/bin/" + QLocale::system().name())) { app.installTranslator(&translator); - qDebug() << "Loaded: " + QLocale::system().name() + " locale!"; + qDebug().noquote() << "Locales: Loaded: " + QLocale::system().name() + " locale!"; } else { - qDebug() << "Unable to load translation"; + qWarning() << "Locales: Unable to load translation!"; } QQmlApplicationEngine engine(&app); diff --git a/src/main.qml b/src/main.qml index a9bbed7..3574a8c 100644 --- a/src/main.qml +++ b/src/main.qml @@ -32,7 +32,6 @@ import QtQuick.Controls.Styles 1.4 import QtQuick.Dialogs 1.2 import QtQuick.Controls.Material 2.3 import "scenes" as Scenes -//import "ListItem.qml" /*! The main.qml file contains the window, with its header, sidebar, toast and main_content. @@ -59,7 +58,7 @@ ApplicationWindow { function minimizeWindow() { showMinimized(); - console.log("Miniming window now..."); + console.log("Minimizing window now..."); } function showWindow() { @@ -225,6 +224,7 @@ ApplicationWindow { VisualItemModel { id: mainModel + ListItem { text: " " + qsTr("Remote Control") scene_url: "scenes/Scene_remote_control.qml" @@ -362,3 +362,8 @@ ApplicationWindow { } } } + +/*##^## Designer { + D{i:14;anchors_width:650} +} + ##^##*/ diff --git a/src/scenes/Scene_placeholder.qml b/src/scenes/Scene_placeholder.qml index a5ceac9..29e15a9 100644 --- a/src/scenes/Scene_placeholder.qml +++ b/src/scenes/Scene_placeholder.qml @@ -43,7 +43,7 @@ Item { anchors.right: parent.right wrapMode: Text.WordWrap - text: qsTr("The feature you expected here are not yet implemented.") + text: qsTr("The features you expected here are not yet implemented.") horizontalAlignment: Text.AlignHCenter } } diff --git a/src/session.cpp b/src/session.cpp index 4640786..14b6575 100644 --- a/src/session.cpp +++ b/src/session.cpp @@ -158,7 +158,8 @@ void Session::setStatus(QString status) { emit _main_gui->showWindow(); - _main_gui->showToast(tr("Remote Support session was stopped ungracefully"), 5000); + _main_gui->showToast(tr("Remote Support session was " + "stopped ungracefully"), 5000); } else if (status == "stopped") { /* Session is stopped */ guiString = tr("Remote Support session was stopped"); @@ -183,24 +184,29 @@ void Session::setStatus(QString status) { guiString = tr("Remote Support session couldn't be started!"); _main_gui->setStatusIndicator(true, QColor(255, 0, 0, 127)); - _main_gui->showToast(tr("An error occured while trying to start a session!"), 5000); + _main_gui->showToast(tr("An error occured while trying " + "to start a session!"), 5000); } else if (status == "start_session_success") { /* Session successfully started */ guiString = tr("Remote Support session successfully started!"); _main_gui->setStatusIndicator(true, QColor(255, 255, 0, 127)); - _main_gui->showToast(tr("Session was started successfully")); + _main_gui->showToast(QString(tr("Session was started " + "on '%0' successfully")) + .arg(_host->alias())); } else if (status == "status_session_error") { /* Session's status couldn't be refreshed */ _main_gui->showToast(tr("Session status could not be refreshed!"), 5000); - guiString = tr("Session status could not be refreshed!") + "\n" + tr("remote support partner could still be connected!"); + guiString = tr("Session status could not be refreshed!") + "\n" + + tr("remote support partner could still be connected!"); _main_gui->setStatusIndicator(true, QColor(255, 0, 0, 127)); emit _main_gui->showWindow(); } else if (status == "stop_session_error") { /* Session couldn't be stopped */ _main_gui->showToast(tr("Session could not be stopped!"), 5000); - guiString = tr("Session could not be stopped!") + "\n" + tr("remote support partner could still be connected!"); + guiString = tr("Session could not be stopped!") + "\n" + + tr("remote support partner could still be connected!"); _main_gui->setStatusIndicator(true, QColor(255, 0, 0, 127)); emit _main_gui->showWindow(); @@ -353,6 +359,8 @@ void Session::status_response(QJsonDocument *doc) { this->setStatus(new_status); if (this->isSessionAliveOrRunning(new_status)) { + qDebug() << "Session is still alive or running. -> Restarting the status timer."; + // Ask status every 1000 millisecond QTimer::singleShot(1000, this, &Session::statusTimerEvent); } -- cgit v1.2.3 From 54249d9c37ce3994b03123ee6367c7f5519d3b40 Mon Sep 17 00:00:00 2001 From: Daniel Teichmann Date: Wed, 7 Jul 2021 15:03:13 +0200 Subject: Introduce RWAHostModel. RWAHost's are now loaded on start. Scene_remote_{view, control} are no longer available if no host is selected. --- qml.qrc | 2 + rwa-support-desktopapp.pro | 4 +- src/RWAHostModel.cpp | 37 +++++++++ src/RWAHostModel.h | 23 ++++++ src/main.cpp | 14 +++- src/main.qml | 27 ++++++- src/main_qmladaptor.cpp | 94 ++++++++++++++++++++++ src/main_qmladaptor.h | 18 +++++ src/scenes/add_server_wizard/add_server_wizard.cpp | 10 +-- src/scenes/add_server_wizard/add_server_wizard.h | 5 +- src/session.cpp | 1 - 11 files changed, 225 insertions(+), 10 deletions(-) create mode 100644 src/RWAHostModel.cpp create mode 100644 src/RWAHostModel.h (limited to 'src/session.cpp') diff --git a/qml.qrc b/qml.qrc index 5c8d030..07b6bd2 100644 --- a/qml.qrc +++ b/qml.qrc @@ -17,6 +17,8 @@ src/session.h src/RWAHost.h src/RWAHost.cpp + src/RWAHostModel.h + src/RWAHostModel.cpp src/DBusAPI.h src/DBusAPI.cpp src/ListItem.qml diff --git a/rwa-support-desktopapp.pro b/rwa-support-desktopapp.pro index 5c3f24d..a15c4bd 100644 --- a/rwa-support-desktopapp.pro +++ b/rwa-support-desktopapp.pro @@ -48,14 +48,16 @@ SOURCES += src/main.cpp \ src/RWADBusAdaptor.cpp \ src/session.cpp \ src/scenes/add_server_wizard/add_server_wizard.cpp \ + src/RWAHostModel.cpp \ src/RWAHost.cpp \ - src/DBusAPI.cpp + src/DBusAPI.cpp \ HEADERS += src/RWADBusAdaptor.h \ src/main_qmladaptor.h \ src/RWADBusAdaptor.h \ src/session.h \ src/scenes/add_server_wizard/add_server_wizard.h \ + src/RWAHostModel.h \ src/RWAHost.h \ src/DBusAPI.h diff --git a/src/RWAHostModel.cpp b/src/RWAHostModel.cpp new file mode 100644 index 0000000..5f62adc --- /dev/null +++ b/src/RWAHostModel.cpp @@ -0,0 +1,37 @@ +#include "RWAHostModel.h" + +RWAHostModel::RWAHostModel(QObject *parent) { + Q_UNUSED(parent) +} + +int RWAHostModel::rowCount(const QModelIndex& parent) const { + Q_UNUSED(parent); + return mDatas.size(); +} + +int RWAHostModel::columnCount(const QModelIndex& parent) const { + Q_UNUSED(parent); + return 1; +} + +QVariant RWAHostModel::data(const QModelIndex &index, int role) const + { + if (!index.isValid()) + return QVariant(); + if ( role == Qt::DisplayRole) { + return mDatas[index.row()]; + } + return QVariant(); +} + +void RWAHostModel::populate() { + beginResetModel(); + mDatas.clear(); + RWAHost *host1 = new RWAHost("uuid-1", "Erster Server", "url1"); + RWAHost *host2 = new RWAHost("uuid-2", "Zweiter Server", "url2"); + RWAHost *host3 = new RWAHost("uuid-3", "Dritter Server", "url3"); + mDatas.append(host1->alias()); + mDatas.append(host2->alias()); + mDatas.append(host3->alias()); + endResetModel(); +} diff --git a/src/RWAHostModel.h b/src/RWAHostModel.h new file mode 100644 index 0000000..8697df2 --- /dev/null +++ b/src/RWAHostModel.h @@ -0,0 +1,23 @@ +#ifndef RWAHOSTMODEL_H +#define RWAHOSTMODEL_H + +#include +#include + +#include "RWAHost.h" + +class RWAHostModel : public QAbstractListModel { + Q_OBJECT + +public: + explicit RWAHostModel(QObject * parent = nullptr); + int rowCount(const QModelIndex& parent = QModelIndex()) const; + int columnCount(const QModelIndex& parent = QModelIndex()) const; + QVariant data(const QModelIndex & index, int role = Qt::DisplayRole) const; + void populate(); + +private: + QStringList mDatas; +}; + +#endif // RWAHOSTMODEL_H diff --git a/src/main.cpp b/src/main.cpp index 3339840..b85c3fc 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -39,6 +39,7 @@ #include "RWADBusAdaptor.cpp" #include "session.h" #include "scenes/add_server_wizard/add_server_wizard.h" +#include "RWAHostModel.h" #include "RWAHost.h" #define BUILD_TIME __DATE__ " " __TIME__ @@ -86,6 +87,13 @@ int main(int argc, char *argv[]) { // Make mainqmladaptor available to QML engine.rootContext()->setContextProperty("mainqmladaptor", main_gui.data()); + QScopedPointer _dbus_api (new DBusAPI()); + QObject::connect(_dbus_api.data(), + SIGNAL(serviceGetWebAppHostsResponse(QJsonDocument*)), + main_gui.data(), + SLOT(get_web_app_hosts_response(QJsonDocument*))); + _dbus_api.data()->get_web_app_hosts_request(); + engine.load(QUrl(QStringLiteral("qrc:/src/main.qml"))); if (engine.rootObjects().isEmpty()) return -1; @@ -102,9 +110,13 @@ int main(int argc, char *argv[]) { engine.rootObjects().takeFirst(), SLOT(showWindow())); - QScopedPointer wizard (new Add_Server_wizard(&app)); + QObject::connect(engine.rootObjects().takeFirst()->findChild("sidebar_drawer"), + SIGNAL(rwaHostSelected(QString)), + main_gui.data(), + SLOT(onRwaHostSelected(QString))); // Make add_server_wizard available to QML + QScopedPointer wizard (new Add_Server_wizard(&app, main_gui.data())); engine.rootContext()->setContextProperty("add_server_wizard", wizard.data()); return app.exec(); diff --git a/src/main.qml b/src/main.qml index 3574a8c..8a19d54 100644 --- a/src/main.qml +++ b/src/main.qml @@ -182,8 +182,9 @@ ApplicationWindow { */ Drawer { id: sidebar_drawer - y: top_menu_bar_frame.height + objectName: "sidebar_drawer" + y: top_menu_bar_frame.height width: !inPortrait ? Math.min(300, Math.max(200, window.width * 0.333)) : (window.width * 0.5) height: window.height - top_menu_bar_frame.height @@ -194,6 +195,9 @@ ApplicationWindow { margins: -2 visible: !inPortrait + signal rwaHostSelected(string host_uuid) + property bool rwaHostIsSelected: false + ListView { id: sidebar_listview boundsBehavior: Flickable.StopAtBounds @@ -202,6 +206,21 @@ ApplicationWindow { anchors.fill: parent model: mainModel + header: ComboBox { + id: server_chooser + objectName: "server_chooser" + width: parent.width + height: 50 + model: mainqmladaptor.rwaHostModel + + textRole: "alias" + onCurrentIndexChanged: { + var rwa_host = mainqmladaptor.rwaHostModel + sidebar_drawer.rwaHostSelected(rwa_host[currentIndex].uuid) + sidebar_drawer.rwaHostIsSelected = true + } + } + footer: ItemDelegate { id: footer text: " " + qsTr("Settings") @@ -234,6 +253,9 @@ ApplicationWindow { main_content_replace(scene_url, StackView.Transition) } + + // Disabled till a RWAHost object is selected. + enabled: sidebar_drawer.rwaHostIsSelected } ListItem { text: " " + qsTr("Remote View") @@ -244,6 +266,9 @@ ApplicationWindow { main_content_replace(scene_url, StackView.Transition) } + + // Disabled till a RWAHost object is selected. + enabled: sidebar_drawer.rwaHostIsSelected } ListItem { text: " " + qsTr("Add RWA-Server") diff --git a/src/main_qmladaptor.cpp b/src/main_qmladaptor.cpp index b34c9d4..d75b15c 100644 --- a/src/main_qmladaptor.cpp +++ b/src/main_qmladaptor.cpp @@ -30,6 +30,100 @@ MainQMLAdaptor::MainQMLAdaptor(QObject *parent, QQmlApplicationEngine* engine) : Q_ASSERT(engine != nullptr); _engine = engine; + _rwaHostModel = new QList; +} + +void MainQMLAdaptor::onRwaHostSelected(QString host_uuid) { + Q_ASSERT(host_uuid != ""); + + RWAHost *_host = nullptr; + for (int i = 0; i < getRWAHostModel().size(); i++) { + QObject *obj = getRWAHostModel().value(i); + RWAHost *host = qobject_cast(obj); + Q_ASSERT(host != nullptr); + + if (host->uuid() == host_uuid) { + _host = host; + } + } + Q_ASSERT(_host != nullptr); + + qDebug() << "RWAHost was selected!" << _host->uuid() << "aka" << _host->alias(); +} + +void MainQMLAdaptor::setRWAHostModel(QList rwa_hosts) { + + _rwaHostModel = &rwa_hosts; + emit rwaHostModelChanged(rwa_hosts); +} + +void MainQMLAdaptor::addRWAHost(RWAHost *rwa_host) { + _rwaHostModel->append(rwa_host); + emit rwaHostModelChanged(*_rwaHostModel); +} + +QList MainQMLAdaptor::getRWAHostModel() { + return *_rwaHostModel; +} + +void MainQMLAdaptor::get_web_app_hosts_response(QJsonDocument *doc) { + Q_ASSERT(doc != nullptr); + + // Get the QJsonObject + QJsonObject jObject = doc->object(); + QVariantMap mainMap = jObject.toVariantMap(); + + // Status of request + QString request_status = mainMap["status"].toString(); + if (request_status == "success") { + // Building host_objects + QJsonArray host_objects = jObject.value("hosts").toArray(); + + foreach (const QJsonValue &host_object, host_objects) { + QString host_uuid = host_object["uuid"].toString(); + QString host_alias = host_object["alias"].toString(); + QString host_url = host_object["url"].toString(); + + if (host_url == "" || host_uuid == "") { + // This two values are required and can't be omitted. + QString reason = tr("A host object in the response of D-Bus " + "service lacks a necessary value. (host_url or host_uuid)"); + qCritical().noquote() << tr("An error occured while adding a new host:") + << reason; + //emit step1Failed(reason); + + return; + } + + if (host_alias == "") { + qDebug().noquote() << QString("An alias for the host wasn't delivered " + "so just use '%0' as alias.").arg(host_url); + host_alias = host_url; + } + + // Now built RWAHost object. + RWAHost *rwa_host = new RWAHost(host_uuid, host_alias, host_url); + addRWAHost(rwa_host); + + qInfo().noquote() << QString(tr("Successfully added new RWAHost '%0'")).arg(rwa_host->alias()); + } + } else { + QString reason = tr("An error occured while adding a new host:"); + qCritical().noquote() << reason; + + QString type = mainMap["type"].toString(); + if (type != "") { + reason = QString(tr("The error is not clear. The session service " + "responded with status type '%0'")).arg(type); + qCritical().noquote() << reason; + } else { + reason = QString(tr("The error is not clear. The session service " + "responded with no status type!")); + qCritical().noquote() << reason; + } + + return; + } } bool MainQMLAdaptor::setConnectButtonEnabled(bool enabled) { diff --git a/src/main_qmladaptor.h b/src/main_qmladaptor.h index 3c6e75b..8701fc9 100644 --- a/src/main_qmladaptor.h +++ b/src/main_qmladaptor.h @@ -32,11 +32,18 @@ #include #include #include +#include +#include +#include + +#include "RWAHost.h" class MainQMLAdaptor : public QObject { Q_OBJECT // this makes url available as a QML property + Q_PROPERTY(QList rwaHostModel READ getRWAHostModel WRITE setRWAHostModel NOTIFY rwaHostModelChanged) + // this makes url available as a QML property Q_PROPERTY(QString url READ getURL WRITE setURL NOTIFY urlChanged) // this makes pin available as a QML property Q_PROPERTY(QString pin READ getPin WRITE setPin NOTIFY pinChanged) @@ -67,6 +74,7 @@ public: QString getMessageDialogText(); QMessageBox::Icon getMessageDialogIcon(); bool getShowMessageDialog(); + signals: void showMessageDialogChanged(bool show); void messageDialogTextChanged(QString text); @@ -82,6 +90,8 @@ signals: void urlChanged(QString URL); void sessionIDChanged(QString session_id); + void rwaHostModelChanged(QList); + void onCloseSignal(); void showToastSignal(QString text, QString durationMs); @@ -90,6 +100,8 @@ protected: QString _url; QString _pin; QString _session_id; + QList* _rwaHostModel; + private: QQmlApplicationEngine* _engine; @@ -102,13 +114,19 @@ public slots: void handleCopyToClipboardButtonClick(QString copy_data); void handleConnectButtonClick(bool checked); + void get_web_app_hosts_response(QJsonDocument *doc); + void setPin(QString pin); void setURL(QString URL); void setSessionID(QString session_id); + void setRWAHostModel(QList); + void addRWAHost(RWAHost *rwa_host); QString getURL(); QString getPin(); QString getSessionID(); + QList getRWAHostModel(); + void onRwaHostSelected(QString host_uuid); void onCloseHandler(); void showToast(QString text, uint durationMs = 3000); diff --git a/src/scenes/add_server_wizard/add_server_wizard.cpp b/src/scenes/add_server_wizard/add_server_wizard.cpp index bd1dd3c..d06108c 100644 --- a/src/scenes/add_server_wizard/add_server_wizard.cpp +++ b/src/scenes/add_server_wizard/add_server_wizard.cpp @@ -23,16 +23,15 @@ * along with this program. If not, see . */ -#include -#include -#include - #include "add_server_wizard.h" #include "../../RWADBusAdaptor.h" #include "../../RWAHost.h" -Add_Server_wizard::Add_Server_wizard(QObject *parent) : QObject(parent) { +Add_Server_wizard::Add_Server_wizard(QObject *parent, MainQMLAdaptor *main_gui) : QObject(parent) { + Q_ASSERT(main_gui != nullptr); + _dbus_api = new DBusAPI(); + _main_gui = main_gui; // _dbus_api --serviceAddWebAppHostResponse-> this.add_web_app_host_response() QObject::connect(_dbus_api, @@ -96,6 +95,7 @@ void Add_Server_wizard::add_web_app_host_response(QJsonDocument *doc) { // Now built RWAHost object. QScopedPointer rwa_host (new RWAHost(host_uuid, host_alias, host_url)); + _main_gui->addRWAHost(rwa_host.data()); qInfo() << "Successfully added a new RWAHost."; emit step1Success(); diff --git a/src/scenes/add_server_wizard/add_server_wizard.h b/src/scenes/add_server_wizard/add_server_wizard.h index 554f6af..e4d62df 100644 --- a/src/scenes/add_server_wizard/add_server_wizard.h +++ b/src/scenes/add_server_wizard/add_server_wizard.h @@ -30,16 +30,19 @@ #include "../../RWADBusAdaptor.h" #include "../../DBusAPI.h" +#include "../../main_qmladaptor.h" class Add_Server_wizard : public QObject { Q_OBJECT public: - explicit Add_Server_wizard(QObject *parent = nullptr); + explicit Add_Server_wizard(QObject *parent = nullptr, + MainQMLAdaptor *main_gui = nullptr); void add_server(QString host_url); private: DBusAPI *_dbus_api; + MainQMLAdaptor *_main_gui; signals: void step1Success(); diff --git a/src/session.cpp b/src/session.cpp index 14b6575..32aca7d 100644 --- a/src/session.cpp +++ b/src/session.cpp @@ -82,7 +82,6 @@ Session::Session(QObject *parent, MainQMLAdaptor* main_gui, RWAHost *host) : QOb this, SLOT(status_response(QJsonDocument*))); - this->init_vars(); } -- cgit v1.2.3 From 766a90125df68f065495354c20412faf9e1df77a Mon Sep 17 00:00:00 2001 From: Daniel Teichmann Date: Sun, 1 Aug 2021 02:19:15 +0200 Subject: move scenes/Scene_remote_control.qml into scenes/remote_control/Scene_remote_control.qml --- src/DBusAPI.cpp | 2 +- src/main.qml | 2 +- src/main_qmladaptor.cpp | 57 +----- src/main_qmladaptor.h | 7 +- src/scenes/Scene_remote_control.qml | 368 ------------------------------------ src/session.cpp | 34 +++- 6 files changed, 34 insertions(+), 436 deletions(-) delete mode 100644 src/scenes/Scene_remote_control.qml (limited to 'src/session.cpp') diff --git a/src/DBusAPI.cpp b/src/DBusAPI.cpp index 83f38cb..9a0f8de 100644 --- a/src/DBusAPI.cpp +++ b/src/DBusAPI.cpp @@ -116,7 +116,7 @@ void DBusAPI::stop_request(RWAHost *host, QString session_id) { // Sanity Check if(ok == false){ - qWarning() << QString("Unable to parse '%0' as long long!").arg(session_id); + qWarning().noquote() << QString("Unable to parse session_id '%0' as long long!").arg(session_id); return; } diff --git a/src/main.qml b/src/main.qml index 03f9c5f..4782f4b 100644 --- a/src/main.qml +++ b/src/main.qml @@ -264,7 +264,7 @@ ApplicationWindow { ListItem { text: " " + qsTr("Remote Control") - scene_url: "scenes/Scene_remote_control.qml" + scene_url: "scenes/remote_control/Scene_remote_control.qml" onListItemClick: { header_text.text = qsTr("Allow remote control") if (inPortrait) sidebar_drawer.close() diff --git a/src/main_qmladaptor.cpp b/src/main_qmladaptor.cpp index 7e85157..5da0abb 100644 --- a/src/main_qmladaptor.cpp +++ b/src/main_qmladaptor.cpp @@ -81,16 +81,20 @@ QList MainQMLAdaptor::getRWAHostModel() { void MainQMLAdaptor::setRWAHostSelected(bool value) { // Find item via 'objectName' - QObject *sidebar_drawer = _engine->rootObjects().takeFirst()->findChild("sidebar_drawer"); + QObject *sidebar_drawer = _engine->rootObjects().takeFirst()-> + findChild("sidebar_drawer"); if (sidebar_drawer) { sidebar_drawer->setProperty("rwaHostIsSelected", value); } else { qWarning() << "Unable to find 'sidebar_drawer' Item!"; } - QObject *server_chooser = _engine->rootObjects().takeFirst()->findChild("server_chooser"); + QObject *server_chooser = _engine->rootObjects().takeFirst()-> + findChild("server_chooser"); if (server_chooser) { - server_chooser->setProperty("displayText", value ? server_chooser->property("currentText") : tr("No RWA host available!")); + server_chooser->setProperty("displayText", value ? + server_chooser->property("currentText") : + tr("No RWA host available!")); server_chooser->setProperty("enabled", value); } else { qWarning() << "Unable to find 'server_chooser' Item!"; @@ -273,53 +277,6 @@ void MainQMLAdaptor::main_content_replace(QString scene) { } } -bool MainQMLAdaptor::setConnectButtonEnabled(bool enabled) { - // Find item via 'objectName' - QQuickItem *scene_remote_control = _engine->rootObjects().takeFirst()->findChild("Scene_remote_control"); - QQuickItem *item = scene_remote_control->findChild("start_support_button"); - if (item) { - item->setProperty("enabled", enabled); - if (item->property("checked").toBool()) { - item->setProperty("text", tr("Stop remote support session")); - } else { - item->setProperty("text", tr("Start remote support session")); - } - } else { - qWarning() << "Unable to find 'start_support_button' Item!"; - return false; - } - - return true; -} - -bool MainQMLAdaptor::setConnectButtonChecked(bool checked) { - // Find item via 'objectName' - QQuickItem *scene_remote_control = _engine->rootObjects().at(0)->findChild("Scene_remote_control"); - QQuickItem *item = scene_remote_control->findChild("start_support_button"); - if (item) { - item->setProperty("checked", checked); - } else { - qWarning() << "Unable to find 'start_support_button' Item!"; - return false; - } - - return true; -} - -bool MainQMLAdaptor::setStatus(QString status) { - // Find item via 'objectName' - QQuickItem *scene_remote_control = _engine->rootObjects().at(0)->findChild("Scene_remote_control"); - QQuickItem *item = scene_remote_control->findChild("dbus_api_status_text"); - if (item) { - item->setProperty("text", status); - } else { - qWarning() << "Unable to find 'dbus_api_status_text' Item!"; - return false; - } - - return true; -} - bool MainQMLAdaptor::openMessageDialog(QString title, QString text, QMessageBox::Icon icon) { _messageDialogText = text; _messageDialogTitle = title; diff --git a/src/main_qmladaptor.h b/src/main_qmladaptor.h index d7f1783..9a2f7c3 100644 --- a/src/main_qmladaptor.h +++ b/src/main_qmladaptor.h @@ -59,22 +59,17 @@ class MainQMLAdaptor : public QObject // this makes showMessageDialogIcon available as a QML property Q_PROPERTY(QMessageBox::Icon _messageDialogIcon READ getMessageDialogIcon NOTIFY messageDialogIconChanged) + public: explicit MainQMLAdaptor(QObject *parent, QQmlApplicationEngine *engine = nullptr, DBusAPI *dbus_api = nullptr); void setRWAHostModel(QList *rwa_hosts); - bool setConnectButtonEnabled(bool enabled); - bool setConnectButtonChecked(bool checked); - void main_content_push(QString); void main_content_pop(QString); void main_content_replace(QString); - bool setStatusIndicator(bool active, QColor color = QColor(255,255,255)); - bool setStatus(QString status); - bool openMessageDialog(QString title, QString text, QMessageBox::Icon); QString getMessageDialogTitle(); QString getMessageDialogText(); diff --git a/src/scenes/Scene_remote_control.qml b/src/scenes/Scene_remote_control.qml deleted file mode 100644 index ea59ea7..0000000 --- a/src/scenes/Scene_remote_control.qml +++ /dev/null @@ -1,368 +0,0 @@ -import QtQuick 2.9 -import QtQuick.Window 2.2 -import QtQuick.Extras 1.4 -import QtQuick.Controls 2.2 -import QtQuick.Dialogs 1.2 -import QtQuick.Controls.Material 2.3 - -Item { - id: scene_remote_control - objectName: "Scene_remote_control" - - Label { - id: dbus_api_status_text - text: "Unknown state of Service" - anchors.leftMargin: 10 + 5 + dbus_api_status_indicator.width - anchors.bottom: parent.bottom - anchors.bottomMargin: 10 - wrapMode: Text.WrapAtWordBoundaryOrAnywhere - verticalAlignment: Text.AlignVCenter - font.pointSize: 11 - fontSizeMode: Text.Fit - objectName: "dbus_api_status_text" - anchors.left: parent.left - - StatusIndicator { - id: dbus_api_status_indicator - width: height - height: parent.height - objectName: "dbus_api_status_indicator" - color: "#73d216" - anchors.verticalCenter: parent.verticalCenter - anchors.right: parent.left - anchors.rightMargin: 5 - active: false - } - } - - Label { - id: explain_function_label - text: qsTr("Please tell your remote support partner your access address and your access-PIN to let your partner connect to this computer.") - font.pixelSize: 18 - fontSizeMode: Text.VerticalFit - wrapMode: Text.WordWrap - anchors.left: parent.left - anchors.leftMargin: 10 - anchors.top: parent.top - anchors.topMargin: 10 - anchors.right: parent.right - anchors.rightMargin: 10 - horizontalAlignment: Text.AlignLeft - enabled: false - - color: Material.theme == Material.Light ? "#000000" : "#FFFFFF" - } - - Rectangle { - id: dbus_api_status_line - y: 379 - height: 1 - radius: 1 - anchors.right: parent.right - anchors.rightMargin: 10 - anchors.bottom: dbus_api_status_text.top - anchors.bottomMargin: 10 - opacity: 0.3 - gradient: Gradient { - GradientStop { - position: 0.391 - color: "#ffffff" - } - - GradientStop { - position: 0.975 - color: "#8b8b8b" - } - } - border.width: 1 - border.color: "#00000000" - anchors.left: parent.left - anchors.leftMargin: 10 - } - - Column { - id: column - spacing: 6 - anchors.right: parent.right - anchors.rightMargin: 10 - anchors.left: parent.left - anchors.leftMargin: 10 - anchors.bottom: dbus_api_status_line.top - anchors.bottomMargin: 10 - anchors.top: explain_function_label.bottom - anchors.topMargin: 10 - - Column { - id: url_group - width: parent.width - height: parent.height * 0.25 - spacing: 5 - - Label { - id: your_url_text - height: parent.height/2 - text: qsTr("Remote Support Address") - font.weight: Font.Bold - font.bold: true - verticalAlignment: Text.AlignBottom - horizontalAlignment: Text.AlignLeft - font.pointSize: 14 - fontSizeMode: Text.Fit - } - - TextEdit { - id: url_text - height: parent.height/2 - text: mainqmladaptor.url - anchors.rightMargin: 10 + copy_url_to_clipboard_button.width - anchors.right: parent.right - wrapMode: Text.WrapAtWordBoundaryOrAnywhere - anchors.leftMargin: 10 - verticalAlignment: Text.AlignVCenter - horizontalAlignment: Text.AlignLeft - font.pointSize: 15 - - readOnly: true - color: Material.foreground - selectByMouse: true - anchors.left: parent.left - - leftPadding: 5 - Rectangle { - radius: 5 - color: Material.theme == Material.Light ? "#F0F0F0" : "#383838" - height: url_text.height - // whole line + copy-into-clipboard button + some margin - width: url_text.width + copy_url_to_clipboard_button.width + 5 + 5 - x: 0; y: 0 - z: -1 - } - - Button { - id: copy_url_to_clipboard_button - width: copy_url_to_clipboard_image.width + 6 - height: copy_url_to_clipboard_image.height + 6 + 10 - anchors.verticalCenter: parent.verticalCenter - display: AbstractButton.IconOnly - anchors.leftMargin: 5 - anchors.left: url_text.right - highlighted: false - flat: true - - Image { - id: copy_url_to_clipboard_image - x: 0 - y: -26 - anchors.horizontalCenter: parent.horizontalCenter - anchors.verticalCenter: parent.verticalCenter - source: "../../images/into-clipboard.svg" - opacity: 0.65 - } - - onClicked: { - mainqmladaptor.handleCopyToClipboardButtonClick(url_text.text); - toast.show(qsTr("Copied access address into clipboard!"), "1000"); - } - - ToolTip.text: qsTr("Copy the access address into the clipboard") - hoverEnabled: true - - ToolTip.delay: 1000 - ToolTip.timeout: 5000 - ToolTip.visible: hovered - } - } - } - - Column { - id: session_id_group - width: parent.width - height: parent.height * 0.25 - spacing: 5 - - Label { - id: your_session_id_text - height: parent.height/2 - text: qsTr("Session-ID") - font.weight: Font.Bold - font.bold: true - anchors.right: parent.right - anchors.rightMargin: 0 - anchors.left: parent.left - anchors.leftMargin: 0 - font.pointSize: 14 - verticalAlignment: Text.AlignBottom - horizontalAlignment: Text.AlignLeft - fontSizeMode: Text.Fit - } - - TextEdit { - objectName: "session_id_text" - id: session_id_text - height: parent.height/2 - text: mainqmladaptor.session_id - font.letterSpacing: 10 - anchors.rightMargin: 10 + copy_session_id_to_clipboard_button.width - anchors.right: parent.right - font.pointSize: 15 - anchors.left: parent.left - anchors.leftMargin: 10 - horizontalAlignment: Text.AlignLeft - verticalAlignment: Text.AlignVCenter - - leftPadding: 5 - Rectangle { - radius: 5 - color: Material.theme == Material.Light ? "#F0F0F0" : "#383838" - height: url_text.height - // whole line + copy-into-clipboard button + some margin - width: url_text.width + copy_url_to_clipboard_button.width + 5 + 5 - x: 0; y: 0 - z: -1 - } - - readOnly: true - color: Material.foreground - wrapMode: Text.WordWrap - selectByMouse: true - - Button { - id: copy_session_id_to_clipboard_button - width: copy_session_id_to_clipboard_image.width + 6 - height: copy_session_id_to_clipboard_image.height + 6 + 10 - anchors.verticalCenter: parent.verticalCenter - flat: true - display: AbstractButton.IconOnly - anchors.left: session_id_text.right - anchors.leftMargin: 5 - - Image { - id: copy_session_id_to_clipboard_image - anchors.horizontalCenter: parent.horizontalCenter - opacity: 0.65 - anchors.verticalCenter: parent.verticalCenter - source: "../../images/into-clipboard.svg" - fillMode: Image.PreserveAspectFit - } - - onClicked: { - mainqmladaptor.handleCopyToClipboardButtonClick(pin_text.text); - toast.show(qsTr("Copied session-ID into clipboard!"), "1000"); - } - - ToolTip.text: qsTr("Copy the session-ID into the clipboard") - hoverEnabled: true - - ToolTip.delay: 1000 - ToolTip.timeout: 5000 - ToolTip.visible: hovered - } - } - } - - Column { - id: pin_group - width: parent.width - height: parent.height * 0.25 - spacing: 5 - - Label { - id: your_pin_text - height: parent.height/2 - text: qsTr("Access-PIN") - font.weight: Font.Bold - font.bold: true - anchors.right: parent.right - anchors.rightMargin: 0 - anchors.left: parent.left - anchors.leftMargin: 0 - font.pointSize: 14 - verticalAlignment: Text.AlignBottom - horizontalAlignment: Text.AlignLeft - } - - TextEdit { - objectName: "pin_text" - id: pin_text - height: parent.height/2 - text: mainqmladaptor.pin - anchors.rightMargin: 10 + copy_pin_to_clipboard_button.width - anchors.right: parent.right - font.pointSize: 15 - anchors.left: parent.left - anchors.leftMargin: 10 - font.letterSpacing: 10 - horizontalAlignment: Text.AlignLeft - verticalAlignment: Text.AlignVCenter - - leftPadding: 5 - Rectangle { - radius: 5 - color: Material.theme == Material.Light ? "#F0F0F0" : "#383838" - height: url_text.height - // whole line + copy-into-clipboard button + some margin - width: url_text.width + copy_url_to_clipboard_button.width + 5 + 5 - x: 0; y: 0 - z: -1 - } - - readOnly: true - color: Material.foreground - wrapMode: Text.WordWrap - selectByMouse: true - - Button { - id: copy_pin_to_clipboard_button - width: copy_pin_to_clipboard_image.width + 6 - height: copy_pin_to_clipboard_image.height + 6 + 10 - anchors.verticalCenter: parent.verticalCenter - flat: true - display: AbstractButton.IconOnly - anchors.left: pin_text.right - anchors.leftMargin: 5 - - Image { - id: copy_pin_to_clipboard_image - anchors.verticalCenter: parent.verticalCenter - opacity: 0.65 - anchors.horizontalCenter: parent.horizontalCenter - source: "../../images/into-clipboard.svg" - fillMode: Image.PreserveAspectFit - } - - onClicked: { - mainqmladaptor.handleCopyToClipboardButtonClick(pin_text.text); - toast.show(qsTr("Copied PIN into clipboard!"), "1000"); - } - - ToolTip.text: qsTr("Copy the pin into the clipboard") - hoverEnabled: true - - ToolTip.delay: 1000 - ToolTip.timeout: 5000 - ToolTip.visible: hovered - } - } - } - - } - - Button { - id: start_support_button - height: Math.min(50) - objectName: "start_support_button" - text: qsTr("Start remote support session") - anchors.rightMargin: column.anchors.leftMargin - anchors.bottom: dbus_api_status_line.top - anchors.bottomMargin: 10 - anchors.right: parent.right - checkable: true - - onClicked: mainqmladaptor.handleConnectButtonClick(checked); - } -} - -/*##^## Designer { - D{i:0;autoSize:true;height:480;width:640} -} - ##^##*/ diff --git a/src/session.cpp b/src/session.cpp index 32aca7d..a524afe 100644 --- a/src/session.cpp +++ b/src/session.cpp @@ -310,22 +310,36 @@ void Session::start_response(QJsonDocument *doc) { emit pinChanged(QString::number(pin)); emit urlChanged(url); emit sessionIDChanged(QString::number(session_id)); -} -void Session::stop() { - _dbus_api->stop_request(_host, this->getSessionID()); + started = true; - // Clear current variables - this->init_vars(); + // Ask status every 1000 millisecond - // Disable connect button to reduce spam. - // And don't enable it as long there is no status update. - // (Or something fails) - _main_gui->setConnectButtonEnabled(false); + QTimer *timer = new QTimer(this); + connect(timer, &QTimer::timeout, this, + QOverload<>::of(&Session::statusTimerEvent)); + timer->start(1000); + + qDebug() << "Successfully started a session."; + this->setStatus("start_session_success"); + + emit startSucceeded(); +} + +void Session::stop() { + if (started) + _dbus_api->stop_request(getHost(), getSessionID()); } void Session::stop_response(QJsonDocument *doc) { - Q_ASSERT(doc != nullptr); + // Q_ASSERT lets the program crash immediatly after method call + // when the session service is not started. + // Don't use Q_ASSERT(doc != nullptr); instead use: + if (doc == nullptr) { + emit stopFailed(tr("Can't connect to underlying session service! " + "Is the session service started?")); + return; + } QJsonObject jObject = doc->object(); QVariantMap mainMap = jObject.toVariantMap(); -- cgit v1.2.3 From 35343e5158ca441f8001c0a91685f4e93b53cb03 Mon Sep 17 00:00:00 2001 From: Daniel Teichmann Date: Sun, 1 Aug 2021 02:22:57 +0200 Subject: Toast: Add a variety of new toast colors; Session complete rewrite; A lot of bugfixing; New available toast colors/types: ToastType.Standard, ToastType.Info, ToastType.Warning ToastType.Success, ToastType.Error --- src/Toast.qml | 26 +- src/ToastManager.qml | 19 +- src/main.qml | 4 +- src/main_qmladaptor.cpp | 84 ++---- src/main_qmladaptor.h | 63 ++-- src/scenes/add_server_wizard/Scene_step_1.qml | 1 + src/scenes/add_server_wizard/add_server_wizard.cpp | 17 +- src/scenes/add_server_wizard/add_server_wizard.h | 4 +- src/session.cpp | 320 +++++++-------------- src/session.h | 52 ++-- 10 files changed, 248 insertions(+), 342 deletions(-) (limited to 'src/session.cpp') diff --git a/src/Toast.qml b/src/Toast.qml index 0de53a9..7a18dc8 100644 --- a/src/Toast.qml +++ b/src/Toast.qml @@ -27,6 +27,7 @@ import QtQuick 2.0 import QtQuick.Controls 2.0 import QtQuick.Controls.Material 2.3 +import rwa.toast.type 1.0 /** * adapted from StackOverflow: @@ -50,8 +51,11 @@ Control { * * @param {string} text Text to show * @param {real} duration Duration to show in milliseconds, defaults to 3000 + * @param {enum} type Type of toast. Available is: + * ToastType.Standard, ToastType.Info, ToastType.Warning + * ToastType.Success, ToastType.Error */ - function show(text, duration) { + function show(text, duration, type) { message.text = text; // checks if parameter was passed @@ -60,6 +64,23 @@ Control { } else { time = defaultTime; } + + if (typeof type !== "undefined" ) { + if (type === ToastType.ToastStandard) { + selectedColor = "#dcdedc"; + } else if (type === ToastType.ToastInfo) { + selectedColor = "#0d5eaf"; + } else if (type === ToastType.ToastSuccess) { + selectedColor = "#0daf36"; + } else if (type === ToastType.ToastWarning) { + selectedColor = "#efef2a"; + } else if (type === ToastType.ToastError) { + selectedColor = "#ed1212"; + } + } else { + selectedColor = "#dcdedc"; + } + animation.start(); } @@ -72,6 +93,7 @@ Control { id: root + property color selectedColor: "#dcdedc" readonly property real defaultTime: 3000 property real time: defaultTime readonly property real fadeTime: 300 @@ -88,6 +110,8 @@ Control { background: Rectangle { color: (Material.theme == Material.Dark) ? "#212121" : "#dcdedc" + border.color: selectedColor + border.width: 1.5 radius: margin } diff --git a/src/ToastManager.qml b/src/ToastManager.qml index 1acf8d5..2f1600f 100644 --- a/src/ToastManager.qml +++ b/src/ToastManager.qml @@ -42,9 +42,12 @@ ListView { * * @param {string} text Text to show * @param {real} duration Duration to show in milliseconds, defaults to 3000 + * @param {enum} type Type of toast. Available is: + * ToastType.Standard, ToastType.Info, ToastType.Warning + * ToastType.Success, ToastType.Error */ - function show(text, duration) { - model.insert(0, {text: text, duration: duration}); + function show(text, duration, type) { + model.insert(0, {text: text, duration: duration, type: type}); } /** @@ -71,11 +74,13 @@ ListView { delegate: Toast { Component.onCompleted: { - if (typeof duration === "undefined") { - show(text); - } - else { - show(text, duration); + if (typeof duration === "undefined" && typeof type === "undefined") { + show(text, ToastType.ToastStandard); + } else if (typeof duration === "undefined" && + typeof type !== "undefined") { + show(text, type); + } else { + show(text, duration, type); } } } diff --git a/src/main.qml b/src/main.qml index 4782f4b..af41dd1 100644 --- a/src/main.qml +++ b/src/main.qml @@ -107,8 +107,8 @@ ApplicationWindow { Connections { target: mainqmladaptor - onShowToastSignal: { - toast.show(text, durationMs) + function onShowToastSignal(text, durationMs, type) { + toast.show(text, durationMs, type) } } diff --git a/src/main_qmladaptor.cpp b/src/main_qmladaptor.cpp index 5da0abb..d30243d 100644 --- a/src/main_qmladaptor.cpp +++ b/src/main_qmladaptor.cpp @@ -33,11 +33,22 @@ MainQMLAdaptor::MainQMLAdaptor(QObject *parent, QQmlApplicationEngine* engine, _engine = engine; _dbus_api = dbus_api; + _selected_rwa_host = nullptr; _rwaHostModel = new QList; QTimer *timer = new QTimer(this); - connect(timer, &QTimer::timeout, _dbus_api, QOverload<>::of(&DBusAPI::get_web_app_hosts_request)); + connect(timer, &QTimer::timeout, _dbus_api, + QOverload<>::of(&DBusAPI::get_web_app_hosts_request)); timer->start(10000); + + qmlRegisterUncreatableMetaObject( + Toast::staticMetaObject, // meta object created by Q_NAMESPACE macro + "rwa.toast.type", // import statement (can be any string) + 1, 0, // major and minor version of the import + "ToastType", // name in QML (does not have to match C++ name) + "Error: only enums" // error if someone tries to create a ToastType object + ); + } void MainQMLAdaptor::onRwaHostSelected(QString host_uuid) { @@ -55,11 +66,19 @@ void MainQMLAdaptor::onRwaHostSelected(QString host_uuid) { } Q_ASSERT(_host != nullptr); - qDebug() << "RWAHost was selected!" << _host->uuid() << "aka" << _host->alias(); + _selected_rwa_host = _host; + qDebug() << "RWAHost was selected!" << + _selected_rwa_host->uuid() << + "aka" << + _selected_rwa_host->alias(); setRWAHostSelected(true); } +RWAHost* MainQMLAdaptor::getSelectedRWAHost() { + return _selected_rwa_host; +} + void MainQMLAdaptor::setRWAHostModel(QList *rwa_hosts) { _rwaHostModel = rwa_hosts; emit rwaHostModelChanged(*rwa_hosts); @@ -108,7 +127,13 @@ void MainQMLAdaptor::get_web_app_hosts_response(QJsonDocument *doc) { if (doc == nullptr) { setRWAHostSelected(false); - showToast(tr("Can't connect to underlying session service!"), 9800); + showToast(tr("Can't connect to underlying session service!"), + 9800, + Toast::ToastError); + + // Go to the first page on the stack. + main_content_pop(nullptr); + return; } @@ -308,59 +333,12 @@ bool MainQMLAdaptor::getShowMessageDialog() { return _showMessageDialog; } -bool MainQMLAdaptor::setStatusIndicator(bool active, QColor color) { - // Find item via 'objectName' - QQuickItem *scene_remote_control = _engine->rootObjects().at(0)->findChild("Scene_remote_control"); - QQuickItem *item = scene_remote_control->findChild("dbus_api_status_indicator"); - if (item) { - item->setProperty("active", active); - item->setProperty("color", color); - } else { - qWarning() << "Unable to find 'dbus_api_status_indicator' Item!"; - return false; - } - - return true; -} - -void MainQMLAdaptor::handleCopyToClipboardButtonClick(QString copy_data) { - QClipboard *clipboard = QApplication::clipboard(); - QString originalText = clipboard->text(); - clipboard->setText(copy_data); - qDebug() << "Copied into clipboard:" << copy_data; -} - -void MainQMLAdaptor::handleConnectButtonClick(bool checked) { - emit onConnectButtonClick(checked); -} - -void MainQMLAdaptor::setPin(QString pin) { - _pin = pin; - emit pinChanged(pin); -} -void MainQMLAdaptor::setURL(QString URL) { - _url = URL; - emit urlChanged(URL); -} -void MainQMLAdaptor::setSessionID(QString session_id) { - _session_id = session_id; - emit sessionIDChanged(session_id); -} -QString MainQMLAdaptor::getURL() { - return _url; -} -QString MainQMLAdaptor::getPin() { - return _pin; -} -QString MainQMLAdaptor::getSessionID() { - return _session_id; -} - void MainQMLAdaptor::onCloseHandler() { // Do cleanup things here... emit onCloseSignal(); } -void MainQMLAdaptor::showToast(QString text, uint durationMs) { - emit showToastSignal(text, QString::number(durationMs)); +void MainQMLAdaptor::showToast(QString text, uint durationMs, uint type) { + // type is actually Toast::ToastType + emit showToastSignal(text, QString::number(durationMs), type); } diff --git a/src/main_qmladaptor.h b/src/main_qmladaptor.h index 9a2f7c3..70c075b 100644 --- a/src/main_qmladaptor.h +++ b/src/main_qmladaptor.h @@ -39,17 +39,34 @@ #include "RWAHost.h" #include "DBusAPI.h" -class MainQMLAdaptor : public QObject +namespace Toast { + Q_NAMESPACE + enum ToastType { + ToastStandard, + ToastInfo, + ToastSuccess, + ToastWarning, + ToastError + }; + Q_ENUM_NS(ToastType) +} + +/*#include +namespace MyNamespace { + Q_NAMESPACE // required for meta object creation + enum EnStyle { + STYLE_RADIAL, + STYLE_ENVELOPE, + STYLE_FILLED + }; + Q_ENUM_NS(EnStyle) // register the enum in meta object data +}*/ + +class MainQMLAdaptor : public QObject { Q_OBJECT - // this makes url available as a QML property + // this makes rwaHostModel available as a QML property Q_PROPERTY(QList rwaHostModel READ getRWAHostModel NOTIFY rwaHostModelChanged) - // this makes url available as a QML property - Q_PROPERTY(QString url READ getURL WRITE setURL NOTIFY urlChanged) - // this makes pin available as a QML property - Q_PROPERTY(QString pin READ getPin WRITE setPin NOTIFY pinChanged) - // this makes session_id available as a QML property - Q_PROPERTY(QString session_id READ getSessionID WRITE setSessionID NOTIFY sessionIDChanged) // this makes showMessageDialog available as a QML property Q_PROPERTY(bool showMessageDialog READ getShowMessageDialog NOTIFY showMessageDialogChanged) // this makes showMessageDialogTitle available as a QML property @@ -85,27 +102,19 @@ signals: void minimizeWindow(); void showWindow(); - void onConnectButtonClick(bool checked); - - void pinChanged(QString pin); - void urlChanged(QString URL); - void sessionIDChanged(QString session_id); - void rwaHostModelChanged(QList); void onCloseSignal(); - void showToastSignal(QString text, QString durationMs); + void showToastSignal(QString text, QString durationMs, int type); protected: - QString _url; - QString _pin; - QString _session_id; DBusAPI *_dbus_api; QList *_rwaHostModel; private: - QQmlApplicationEngine* _engine; + QQmlApplicationEngine *_engine; + RWAHost *_selected_rwa_host; bool _showMessageDialog; QString _messageDialogTitle; @@ -113,27 +122,23 @@ private: QMessageBox::Icon _messageDialogIcon; public slots: - void handleCopyToClipboardButtonClick(QString copy_data); - void handleConnectButtonClick(bool checked); - void get_web_app_hosts_response(QJsonDocument *doc); - void setPin(QString pin); - void setURL(QString URL); - void setSessionID(QString session_id); void addRWAHost(RWAHost *rwa_host); void removeRWAHost(RWAHost *rwa_host); void setRWAHostSelected(bool value); - QString getURL(); - QString getPin(); - QString getSessionID(); // No pointer because QML doesn't // like this type much with pointer QList getRWAHostModel(); + RWAHost *getSelectedRWAHost(); + void onRwaHostSelected(QString host_uuid); void onCloseHandler(); - void showToast(QString text, uint durationMs = 3000); + // arg type is actually Toast::ToastType + void showToast(QString text, + uint durationMs = 3000, + uint type = 0); }; diff --git a/src/scenes/add_server_wizard/Scene_step_1.qml b/src/scenes/add_server_wizard/Scene_step_1.qml index e57f8a4..bfbe2ae 100644 --- a/src/scenes/add_server_wizard/Scene_step_1.qml +++ b/src/scenes/add_server_wizard/Scene_step_1.qml @@ -3,6 +3,7 @@ import QtQuick.Window 2.2 import QtQuick.Extras 1.4 import QtQuick.Controls 2.2 import QtQuick.Controls.Material 2.3 +import rwa.toast.type 1.0 /*! * This .qml file is a Scene which can be loaded through for diff --git a/src/scenes/add_server_wizard/add_server_wizard.cpp b/src/scenes/add_server_wizard/add_server_wizard.cpp index 9b67ebc..caac344 100644 --- a/src/scenes/add_server_wizard/add_server_wizard.cpp +++ b/src/scenes/add_server_wizard/add_server_wizard.cpp @@ -47,7 +47,7 @@ void Add_Server_wizard::processStep1(QString host_url, QString host_alias) { if(host_alias == "" || host_url == "") { QString reason = tr("Both textfields can't be empty!"); - emit step1Failed(reason); + emit step1Failed(reason, Toast::ToastType::ToastWarning); qDebug().noquote() << reason; return; } @@ -57,7 +57,7 @@ void Add_Server_wizard::processStep1(QString host_url, QString host_alias) { void Add_Server_wizard::processStep2() { qDebug() << "Processing Step 2 with args: No Args."; - emit step2Failed(tr("The features you expected here are not yet implemented.")); + emit step2Failed(tr("The features you expected here are not yet implemented."), Toast::ToastType::ToastWarning); // Just show placeholder scene now. emit step2Success(); } @@ -72,7 +72,9 @@ void Add_Server_wizard::add_web_app_host_response(QJsonDocument *doc) { // Don't use Q_ASSERT(doc != nullptr); instead use: if (doc == nullptr) { _main_gui->setRWAHostSelected(false); - _main_gui->showToast(tr("Can't connect to underlying session service!"), 9800); + _main_gui->showToast(tr("Can't connect to underlying session service!"), + 9800, + Toast::ToastType::ToastError); return; } @@ -90,25 +92,32 @@ void Add_Server_wizard::add_web_app_host_response(QJsonDocument *doc) { } else { qCritical().noquote() << tr("An error occured while adding a new host!"); + uint toast_type = Toast::ToastType::ToastStandard; QString reason = tr("An error occured while adding a new host!"); QString type = mainMap["type"].toString(); + if(type == "connection"){ reason = tr("Couldn't connect to the specified host!"); + toast_type = Toast::ToastType::ToastError; qCritical().noquote() << reason; } else if (type == "duplicate") { reason = tr("The specified host was already added!"); + toast_type = Toast::ToastType::ToastWarning; qCritical().noquote() << reason; } else if (type == "invalid_url") { reason = tr("The specified host address is not valid!"); + toast_type = Toast::ToastType::ToastWarning; qCritical().noquote() << reason; } else if (type == "permission_denied") { reason = tr("The specified host address does not grant access!"); + toast_type = Toast::ToastType::ToastError; qCritical().noquote() << reason; } else if (type == "unsupported_server") { reason = tr("The specified host address is not supported!"); + toast_type = Toast::ToastType::ToastError; qCritical().noquote() << reason; } - emit step1Failed(reason); + emit step1Failed(reason, toast_type); return; } diff --git a/src/scenes/add_server_wizard/add_server_wizard.h b/src/scenes/add_server_wizard/add_server_wizard.h index 03af824..dc205d1 100644 --- a/src/scenes/add_server_wizard/add_server_wizard.h +++ b/src/scenes/add_server_wizard/add_server_wizard.h @@ -47,9 +47,9 @@ private: signals: void step1Success(); - void step1Failed(QString reason); + void step1Failed(QString reason, uint toast_type); void step2Success(); - void step2Failed(QString reason); + void step2Failed(QString reason, uint toast_type); public slots: void processStep1(QString host_url, QString host_alias); diff --git a/src/session.cpp b/src/session.cpp index a524afe..25a8512 100644 --- a/src/session.cpp +++ b/src/session.cpp @@ -26,194 +26,60 @@ #include "session.h" -Session::Session(QObject *parent, MainQMLAdaptor* main_gui, RWAHost *host) : QObject(parent) { - Q_ASSERT(main_gui != nullptr); +Session::Session(DBusAPI *dbus_api, RWAHost *host) : QObject() { Q_ASSERT(host != nullptr); + Q_ASSERT(dbus_api != nullptr); - _dbus_api = new DBusAPI(); - _main_gui = main_gui; + _dbus_api = dbus_api; _host = host; - // QML -> MainQMLAdaptor::handleConnectButtonClick --onConnectButtonClick--> this::handleConnectButtonClick - QObject::connect(_main_gui, - SIGNAL(onConnectButtonClick(bool)), - this, - SLOT(handleConnectButtonClick(bool))); - - // session::setPin --pinChanged--> MainQMLAdaptor::setPin --pinChanged--> QML - QObject::connect(this, - SIGNAL(pinChanged(QString)), - main_gui, - SLOT(setPin(QString))); - - // session::setURL --urlChanged--> MainQMLAdaptor::setURL --urlChanged--> QML - QObject::connect(this, - SIGNAL(urlChanged(QString)), - main_gui, - SLOT(setURL(QString))); - - // session::setSessionID --sessionIDChanged--> MainQMLAdaptor::setSessionID --sessionIDChanged--> QML - QObject::connect(this, - SIGNAL(sessionIDChanged(QString)), - main_gui, - SLOT(setSessionID(QString))); - - // QML -> MainQMLAdaptor::onCloseHandler --onCloseSignal--> session::onCloseHandler - QObject::connect(main_gui, - SIGNAL(onCloseSignal()), - this, - SLOT(onCloseHandler())); - - // _dbus_api --sessionStartResponse-> this.start_response() - QObject::connect(_dbus_api, - SIGNAL(serviceStartResponse(QJsonDocument*)), - this, - SLOT(start_response(QJsonDocument*))); - - // _dbus_api --sessionStopResponse-> this.stop_response() - QObject::connect(_dbus_api, - SIGNAL(serviceStopResponse(QJsonDocument*)), - this, - SLOT(stop_response(QJsonDocument*))); - - // _dbus_api --sessionStatusResponse-> this.status_response() - QObject::connect(_dbus_api, - SIGNAL(serviceStatusResponse(QJsonDocument*)), - this, - SLOT(status_response(QJsonDocument*))); - - this->init_vars(); -} - -void Session::statusTimerEvent() { - qDebug() << "Status timer event got triggered just now."; - this->status(); -} - -void Session::init_vars() { setPin("-----"); setSessionID("-----"); setURL(tr("Not available yet")); setStatus("unknown"); - - _main_gui->setConnectButtonChecked(false); - _main_gui->setConnectButtonEnabled(true); - _main_gui->setStatusIndicator(false); - - _minimizedBefore = false; + started = false; } -QString Session::getStatus() { - return _status; +Session::~Session() { + qDebug().noquote() << QString("Session #'%0' on host '%1' will be deconstructed.") + .arg(getSessionID()) + .arg(getHost()->alias()); + stop(); + disconnect(); } -QString Session::getURL() { - return _url; -} - -QString Session::getSessionID() { - return QString(_session_id); -} +void Session::statusTimerEvent() { + qDebug() << "Status timer event triggered"; -QString Session::getPin() { - return _pin; + refresh_status(); } -bool Session::isSessionAliveOrRunning(QString status) { - if (status == "running" || status == "active") { +bool Session::isSessionAliveOrRunning() { + if (getStatus() == "running" || getStatus() == "active") { return true; } else { return false; } } -void Session::minimizeWindow() { - if (!_minimizedBefore) { - qDebug() << "Minimizing window now..."; - emit _main_gui->minimizeWindow(); - _minimizedBefore = true; - } +RWAHost* Session::getHost() { + return _host; } -void Session::setStatus(QString status) { - _status = status; +QString Session::getStatus() { + return _status; +} - QString guiString = tr("Unknown state of service"); - _main_gui->setStatusIndicator(false); - - qDebug() << "setStatus(): Setting status to " << status; - - if (status == "running") { - /* Session is running but no one is connected yet */ - guiString = tr("Remote Support session is ready to be connected to"); - _main_gui->setStatusIndicator(true, QColor(255, 255, 0, 127)); - } else if (status == "dead") { - /* Session died */ - guiString = tr("Remote Support session was stopped ungracefully"); - - // Clear current variables - this->init_vars(); - _main_gui->setStatusIndicator(true, QColor(255, 0, 0, 127)); - - emit _main_gui->showWindow(); - - _main_gui->showToast(tr("Remote Support session was " - "stopped ungracefully"), 5000); - } else if (status == "stopped") { - /* Session is stopped */ - guiString = tr("Remote Support session was stopped"); - - // Clear current variables - this->init_vars(); - - emit _main_gui->showWindow(); - - _main_gui->showToast(tr("Remote Support session was stopped"), 5000); - } else if (status == "active") { - /* Partner is connected */ - QTimer::singleShot(1000, this, &Session::minimizeWindow); - guiString = tr("Your partner is connected to the Remote Support session"); - _main_gui->setStatusIndicator(true, QColor(0, 255, 0, 127)); - - } else if (status == "waiting_start_request_answer") { - /* When pressing on start button display following message while waiting */ - guiString = tr("Trying to reach session service..."); - } else if (status == "start_session_error") { - /* Session couldn't be started */ - guiString = tr("Remote Support session couldn't be started!"); - _main_gui->setStatusIndicator(true, QColor(255, 0, 0, 127)); - - _main_gui->showToast(tr("An error occured while trying " - "to start a session!"), 5000); - } else if (status == "start_session_success") { - /* Session successfully started */ - guiString = tr("Remote Support session successfully started!"); - _main_gui->setStatusIndicator(true, QColor(255, 255, 0, 127)); - - _main_gui->showToast(QString(tr("Session was started " - "on '%0' successfully")) - .arg(_host->alias())); - } else if (status == "status_session_error") { - /* Session's status couldn't be refreshed */ - _main_gui->showToast(tr("Session status could not be refreshed!"), 5000); - guiString = tr("Session status could not be refreshed!") + "\n" + - tr("remote support partner could still be connected!"); - _main_gui->setStatusIndicator(true, QColor(255, 0, 0, 127)); - - emit _main_gui->showWindow(); - } else if (status == "stop_session_error") { - /* Session couldn't be stopped */ - _main_gui->showToast(tr("Session could not be stopped!"), 5000); - guiString = tr("Session could not be stopped!") + "\n" + - tr("remote support partner could still be connected!"); - _main_gui->setStatusIndicator(true, QColor(255, 0, 0, 127)); - - emit _main_gui->showWindow(); - } +QString Session::getURL() { + return _url; +} - _main_gui->setStatus(guiString); +QString Session::getSessionID() { + return _session_id; +} - emit statusChanged(_status); +QString Session::getPin() { + return _pin; } void Session::setURL(QString url) { @@ -231,49 +97,62 @@ void Session::setPin(QString pin) { emit pinChanged(pin); } -void Session::handleConnectButtonClick(bool checked) { - qDebug() << "-----Connect button handler-----" << - "\nCurrent session #" << this->getSessionID(); - - // Stopping even if nothing is running - _dbus_api->stop_request(_host, this->getSessionID()); +void Session::setHost(RWAHost *host) { + _host = host; + emit hostChanged(host); +} - if (checked) { - // Start the Session again - _dbus_api->start_request(_host); - } - qDebug() << "-----\\Connect button handler-----"; +void Session::setStatus(QString status) { + _status = status; + emit statusChanged(status); } void Session::start() { - // Disable connect button to reduce spam. - // And don't enable it as long there is no status update. - // (Or something fails) - _main_gui->setConnectButtonEnabled(false); - this->setStatus("waiting_start_request_answer"); - _dbus_api->start_request(_host); } void Session::start_response(QJsonDocument *doc) { - Q_ASSERT(doc != nullptr); + // Q_ASSERT lets the program crash immediatly after method call + // when the session service is not started. + // Don't use Q_ASSERT(doc != nullptr); instead use: + if (doc == nullptr) { + emit startFailed(tr("Can't connect to underlying session service! " + "Is the session service started?")); + return; + } // Get the QJsonObject QJsonObject jObject = doc->object(); QVariantMap mainMap = jObject.toVariantMap(); // Status of request - QString request_status = mainMap["status"].toString(); - if (request_status == "success") { - qDebug() << "Successfully started a Session."; - this->setStatus("start_session_success"); - - // Immediately ask for the status of the session - QTimer::singleShot(0, this, &Session::statusTimerEvent); - } else { - qCritical() << "An error occured while creating a new session!"; - this->init_vars(); - this->setStatus("start_session_error"); + QString status = mainMap["status"].toString(); + if (status != "success") { + QString type = mainMap["type"].toString(); + QString error_message = tr("An error occured while creating a new session!"); + + if (type == "multiple") { + // TODO: Ask to stop other session via a message dialog. + error_message = tr("The session service is configured " + "to not support multiple sessions " + "and there is already a session running."); + } else if (type == "connection") { + error_message = tr("Couldn't connect to host '%0'.") + .arg(getHost()->alias()); + } else if (type == "host_not_found") { + error_message = tr("The RWA host '%0' couldn't be found.") + .arg(getHost()->alias()); + } else if (type == "permission_denid") { + error_message = tr("The RWA host '%0' doesn't grant access.") + .arg(getHost()->alias()); + } else if (type == "unsupported_server") { + error_message = tr("The RWA host '%0' is not supported.") + .arg(getHost()->alias()); + } + + setStatus("start_session_error"); + qCritical().noquote() << error_message; + emit startFailed(error_message); return; } @@ -285,23 +164,25 @@ void Session::start_response(QJsonDocument *doc) { // PIN long long pin = mainMap["pin"].toLongLong(&ok); - this->setPin(QString::number(pin)); // Sanity Check if(ok == false){ - qErrnoWarning("Unable to parse out of dbus answer!"); - init_vars(); + QString error_message = "Unable to parse into longo long out of dbus answer!"; + qCritical().noquote() << error_message; + emit startFailed(error_message); return; } + this->setPin(QString::number(pin)); // session_id = remote support id from the rwa-server long long session_id = mainMap["session_id"].toLongLong(); - this->setSessionID(QString::number(session_id)); // Sanity Check if(ok == false){ - qErrnoWarning("Unable to parse out of dbus answer!"); - init_vars(); + QString error_message = "Unable to parse into long long out of dbus answer!"; + qCritical().noquote() << error_message; + emit startFailed(error_message); return; } + this->setSessionID(QString::number(session_id)); qDebug() << "Got session_id:" << session_id << "\nGot url:" << url << @@ -347,39 +228,44 @@ void Session::stop_response(QJsonDocument *doc) { QString new_status = mainMap["status"].toString(); qDebug() << "stop_response() retrieved json. Status now:" << new_status; - // Clear current variables - this->init_vars(); + started = false; - // But the status indicator should display that the Session has stopped this->setStatus(new_status); + + emit stopSucceeded(); } void Session::status() { - _dbus_api->status_request(_host, this->getSessionID()); + _dbus_api->status_request(getHost(), this->getSessionID()); +} + +void Session::refresh_status() { + _dbus_api->refresh_status_request(getHost(), this->getSessionID()); } void Session::status_response(QJsonDocument *doc) { - Q_ASSERT(doc != nullptr); + // Q_ASSERT lets the program crash immediatly after method call, + // when the session service is not started. + // Don't use Q_ASSERT(doc != nullptr); instead use: + if (doc == nullptr) { + if (!_emitted_status_error_already) { + emit statusFailed(tr("Can't connect to underlying session service! " + "Is the session service started?")); + + _emitted_status_error_already = true; + } + + return; + } + + _emitted_status_error_already = false; QJsonObject jObject = doc->object(); QVariantMap mainMap = jObject.toVariantMap(); QString new_status = mainMap["status"].toString(); qDebug() << "status_response() retrieved json. Status:" << new_status; - // Enable (dis)connect button - _main_gui->setConnectButtonEnabled(true); - - this->setStatus(new_status); - - if (this->isSessionAliveOrRunning(new_status)) { - qDebug() << "Session is still alive or running. -> Restarting the status timer."; - - // Ask status every 1000 millisecond - QTimer::singleShot(1000, this, &Session::statusTimerEvent); - } -} + setStatus(new_status); -void Session::onCloseHandler() { - // To cleanup things here - _dbus_api->stop_request(_host, this->getSessionID()); + emit statusSucceeded(); } diff --git a/src/session.h b/src/session.h index 5935919..e1c924f 100644 --- a/src/session.h +++ b/src/session.h @@ -33,48 +33,41 @@ #include #include -#include "main_qmladaptor.h" #include "RWAHost.h" #include "DBusAPI.h" -class Session : public QObject -{ +class Session : public QObject { Q_OBJECT - // this makes status available as a QML property - Q_PROPERTY(QString status READ getStatus NOTIFY statusChanged) - // this makes session_id available as a QML property - Q_PROPERTY(QString session_id READ getSessionID NOTIFY sessionIDChanged) - // this makes url available as a QML property - Q_PROPERTY(QString url READ getURL NOTIFY urlChanged) - // this makes pin available as a QML property - Q_PROPERTY(QString pin READ getPin NOTIFY pinChanged) public: - explicit Session(QObject *parent, MainQMLAdaptor *main_gui = nullptr, + explicit Session(DBusAPI *dbus_api = nullptr, RWAHost *host = nullptr); + ~Session(); QString getStatus(); QString getURL(); QString getSessionID(); QString getPin(); + RWAHost* getHost(); void setStatus(QString status); void setURL(QString url); void setSessionID(QString session_id); void setPin(QString pin); + void setHost(RWAHost *host); void start(); void stop(); void status(); void refresh_status(); -protected: - QString _status; - void statusTimerEvent(); - void init_vars(); + bool started; private: - MainQMLAdaptor *_main_gui; + void statusTimerEvent(); + + bool _emitted_status_error_already; + QString _status; RWAHost *_host; DBusAPI *_dbus_api; @@ -82,25 +75,30 @@ private: QString _url; QString _pin; - // Returns true if a session is somewhat usable (Running, Alive, etc..) - bool isSessionAliveOrRunning(QString status); - bool _minimizedBefore = false; - void minimizeWindow(); + signals: - void finished(); void statusChanged(QString); void sessionIDChanged(QString); void urlChanged(QString); void pinChanged(QString); + void hostChanged(RWAHost*); + + void startFailed(QString error_message); + void stopFailed(QString error_message); + void statusFailed(QString error_message); + + void startSucceeded(); + void stopSucceeded(); + void statusSucceeded(); public slots: - void handleConnectButtonClick(bool checked); - void onCloseHandler(); + // Returns true if a session is somewhat usable (Running, Alive, etc..) + bool isSessionAliveOrRunning(); - void start_response(QJsonDocument *doc); - void stop_response(QJsonDocument *doc); - void status_response(QJsonDocument *doc); + void start_response(QJsonDocument*); + void stop_response(QJsonDocument*); + void status_response(QJsonDocument*); }; #endif // SESSION_H -- cgit v1.2.3