Jelajahi Sumber

Merge branch 'us36-gui-refactor' into 'develop'

US36: GUI Code Refactor

See merge request tobias.wach/ccats!63
Sander, Paul 4 tahun lalu
induk
melakukan
3e0b8e0729

+ 1 - 1
gui/CMakeLists.txt

@@ -16,7 +16,7 @@ pkg_check_modules(JSONCPP REQUIRED jsoncpp)
 
 add_definitions(-DQT_NO_DEBUG_OUTPUT)
 
-add_executable(${PROJECT_NAME} src/main.cpp src/qmlhandler.cpp src/qml.qrc src/config.cpp)
+add_executable(${PROJECT_NAME} src/main.cpp src/cmdmanager.cpp src/qmlhandler.cpp src/jsonhandler.cpp src/qml.qrc src/config.cpp include/qmlhandler.h)
 
 include_directories(${Boost_INCLUDE_DIR} ${JSONCPP_INCLUDEDIR} include)
 target_link_libraries(${PROJECT_NAME} PRIVATE ${CMAKE_THREAD_LIBS_INIT} ${JSONCPP_LIBRARIES} ${Boost_LIBRARIES} Qt5::Core Qt5::Quick)

+ 33 - 0
gui/include/cmdmanager.h

@@ -0,0 +1,33 @@
+#ifndef CMDMANAGER_H
+#define CMDMANAGER_H
+
+#include "qmlhandler.h"
+
+#include <json/json.h>
+
+#include <map>
+#include <string>
+#include <vector>
+
+namespace CmdManager {
+void init();
+void setQmlHandler(QMLHandler *q);
+
+void executeCmd(std::string cmd, Json::Value root);
+
+void handleStatus(Json::Value root);
+void handleClose(Json::Value root);
+void handleList(Json::Value root);
+void handleConnect(Json::Value root);
+void handleVersion(Json::Value root);
+void handleLogin(Json::Value root);
+void handleSignup(Json::Value root);
+void handlePut(Json::Value root);
+void handlePutData(Json::Value root);
+void handleGet(Json::Value root);
+void handleGetData(Json::Value root);
+void handleDeleteMe(Json::Value root);
+void handleDeleteFile(Json::Value root);
+} // namespace CmdManager
+
+#endif // CMDMANAGER_H

+ 0 - 0
gui/src/config.h → gui/include/config.h


+ 11 - 0
gui/include/jsonhandler.h

@@ -0,0 +1,11 @@
+#ifndef JSONHANDLER_H
+#define JSONHANDLER_H
+
+#include "qmlhandler.h"
+#include <json/json.h>
+
+namespace JsonHandler {
+void parseJSON(std::string buffer);
+} // namespace JsonHandler
+
+#endif // JSONHANDLER_H

+ 7 - 4
gui/src/qmlhandler.h → gui/include/qmlhandler.h

@@ -10,16 +10,19 @@ class QMLHandler : public QObject {
 	Q_OBJECT
 
 private:
-	void handleJSON(std::string buffer);
 	void readPipeLoop();
-	void reopenCLI(QString ip);
-	void closeCLI();
 	void fileExists(std::string name);
-	void loadSettingsToGUI();
 
 public:
 	explicit QMLHandler(QObject *parent = 0);
 	void onExit();
+	void setProgramActive(bool active);
+	void reopenCLI(QString ip);
+	void closeCLI();
+	void writeToCLI(QString command);
+	void loadSettingsToGUI();
+	QString getIP();
+	void setRestart(bool restart);
 
 	// C++ -> QML
 signals:

+ 0 - 0
gui/src/IpPopup.ui.qml → gui/src/Forms/Connect/IpPopup.ui.qml


+ 0 - 0
gui/src/LoginForm.ui.qml → gui/src/Forms/Connect/LoginForm.ui.qml


+ 2 - 4
gui/src/LoginSignupPopup.ui.qml → gui/src/Forms/Connect/LoginSignupPopup.ui.qml

@@ -19,7 +19,7 @@ Popup {
             popup.close()
         }
         onLoginSignupPopupOpen: {
-          popup.open()
+            popup.open()
         }
     }
 
@@ -47,16 +47,14 @@ Popup {
             clip: true
 
             LoginForm {
-
             }
 
             SignupForm {
-
             }
         }
     }
 
     Component.onCompleted: {
-      swipeView.interactive = false
+        swipeView.interactive = false
     }
 }

+ 0 - 0
gui/src/SignupForm.ui.qml → gui/src/Forms/Connect/SignupForm.ui.qml


+ 0 - 0
gui/src/HelpForm.ui.qml → gui/src/Forms/Help/HelpForm.ui.qml


+ 0 - 0
gui/src/FooterForm.ui.qml → gui/src/Forms/Main/FooterForm.ui.qml


+ 0 - 0
gui/src/InvalidCliPathPopup.ui.qml → gui/src/Forms/Main/InvalidCliPathPopup.ui.qml


+ 0 - 0
gui/src/InvalidConfigPopup.ui.qml → gui/src/Forms/Main/InvalidConfigPopup.ui.qml


+ 0 - 0
gui/src/NoConfigFoundPopup.ui.qml → gui/src/Forms/Main/NoConfigFoundPopup.ui.qml


+ 6 - 0
gui/src/main.qml → gui/src/Forms/Main/main.qml

@@ -1,5 +1,11 @@
 import QtQuick 2.12
 import QtQuick.Controls 2.5
+import "../Sending"
+import "../Receiving"
+import "../Messages"
+import "../Settings"
+import "../Help"
+import "../Connect"
 
 ApplicationWindow {
     id: window

+ 0 - 0
gui/src/MessagesForm.ui.qml → gui/src/Forms/Messages/MessagesForm.ui.qml


+ 0 - 0
gui/src/ReceivingFileTemplate.ui.qml → gui/src/Forms/Receiving/ReceivingFileTemplate.ui.qml


+ 0 - 0
gui/src/ReceivingFileTemplateDeletePopup.ui.qml → gui/src/Forms/Receiving/ReceivingFileTemplateDeletePopup.ui.qml


+ 0 - 0
gui/src/ReceivingForm.ui.qml → gui/src/Forms/Receiving/ReceivingForm.ui.qml


+ 0 - 0
gui/src/SendingForm.ui.qml → gui/src/Forms/Sending/SendingForm.ui.qml


+ 0 - 0
gui/src/DeleteMePopup.ui.qml → gui/src/Forms/Settings/DeleteMePopup.ui.qml


+ 0 - 0
gui/src/SettingsForm.ui.qml → gui/src/Forms/Settings/SettingsForm.ui.qml


+ 146 - 0
gui/src/cmdmanager.cpp

@@ -0,0 +1,146 @@
+#include <QDebug>
+#include <QGuiApplication>
+
+#include "../include/cmdmanager.h"
+#include "../include/config.h"
+#include <boost/asio.hpp>
+#include <boost/filesystem.hpp>
+#include <boost/lexical_cast.hpp>
+#include <json/json.h>
+
+using boost::lexical_cast;
+using boost::asio::buffer;
+using namespace std;
+
+namespace CmdManager {
+QMLHandler *qmlHandler;
+map<string, void (*)(Json::Value root)> cmdmap;
+} // namespace CmdManager
+
+void CmdManager::init() {
+	cmdmap["status"] = &CmdManager::handleStatus;
+	cmdmap["close"] = &CmdManager::handleClose;
+	cmdmap["list"] = &CmdManager::handleList;
+	cmdmap["connect"] = &CmdManager::handleConnect;
+	cmdmap["version"] = &CmdManager::handleVersion;
+	cmdmap["login"] = &CmdManager::handleLogin;
+	cmdmap["signup"] = &CmdManager::handleSignup;
+	cmdmap["put"] = &CmdManager::handlePut;
+	cmdmap["putdata"] = &CmdManager::handlePutData;
+	cmdmap["get"] = &CmdManager::handleGet;
+	cmdmap["getdata"] = &CmdManager::handleGetData;
+	cmdmap["deleteme"] = &CmdManager::handleDeleteMe;
+	cmdmap["deletefile"] = &CmdManager::handleDeleteFile;
+}
+
+void CmdManager::setQmlHandler(QMLHandler *q) { qmlHandler = q; }
+
+void CmdManager::executeCmd(string cmd, Json::Value root) { cmdmap[cmd](root); }
+
+void CmdManager::handleStatus(Json::Value root) { emit qmlHandler->footerSetStatus(root["response"].asString().c_str()); }
+
+void CmdManager::handleClose(Json::Value root) { qmlHandler->setProgramActive(false); }
+
+void CmdManager::handleList(Json::Value root) {
+	if (root["accept"] == true) {
+		emit qmlHandler->receivingClearFileList();
+
+		// Get the array of file Names
+		auto fileNames = root["names"];
+		for (int i = 0; i < fileNames.size(); i++) {
+			emit qmlHandler->receivingListFile(QString::fromStdString(fileNames[i].asString().c_str()), boost::filesystem::exists(fileNames[i].asString()));
+		}
+	} else {
+		emit qmlHandler->log(root["error"].asString().c_str());
+	}
+}
+
+void CmdManager::handleConnect(Json::Value root) {
+	if (!root["accept"].asBool()) {
+		emit qmlHandler->ipPopupSetStatus(root["error"].asString().c_str());
+		qmlHandler->closeCLI();
+		emit qmlHandler->ipPopupEnableConnectButton();
+	}
+}
+
+void CmdManager::handleVersion(Json::Value root) {
+	if (root["accept"] == true) {
+		emit qmlHandler->ipPopupClose();
+		emit qmlHandler->loginSignupPopupOpen();
+	} else {
+		QString errorMessage =
+		    QString::fromStdString(string("Version mismatch: \nClient: " + root["clientversion"].asString() + "\nServer: " + root["serverversion"].asString()));
+		emit qmlHandler->ipPopupSetStatus(errorMessage);
+		qmlHandler->closeCLI();
+		emit qmlHandler->ipPopupEnableConnectButton();
+	}
+}
+
+void CmdManager::handleLogin(Json::Value root) {
+	if (root["accept"] == true) {
+		emit qmlHandler->loginSignupPopupClose();
+		qmlHandler->writeToCLI("list\n");
+		qmlHandler->loadSettingsToGUI();
+	} else {
+		emit qmlHandler->loginSetStatus(root["error"].asString().c_str());
+		qmlHandler->reopenCLI(qmlHandler->getIP());
+		emit qmlHandler->loginEnableLoginButton();
+	}
+}
+
+void CmdManager::handleSignup(Json::Value root) {
+	if (root["accept"] == true) {
+		emit qmlHandler->loginSignupPopupClose();
+	} else {
+		emit qmlHandler->signupSetStatus(root["error"].asString().c_str());
+		qmlHandler->reopenCLI(qmlHandler->getIP());
+		emit qmlHandler->signupEnableRegisterButton();
+	}
+}
+
+void CmdManager::handlePut(Json::Value root) {
+	if (root["accept"] == false) {
+		QString errorMessage = QString::fromStdString(string("Error when uploading file " + root["file"].asString() + ":\n" + root["error"].asString()));
+		emit qmlHandler->log(errorMessage);
+	}
+}
+
+void CmdManager::handlePutData(Json::Value root) {
+	// TODO: Show speed and handle Error
+}
+
+void CmdManager::handleGet(Json::Value root) {
+	if (root["accept"] == false) {
+		QString errorMessage = QString::fromStdString(string("Error when downloading file " + root["file"].asString() + ":\n" + root["error"].asString()));
+		emit qmlHandler->log(errorMessage);
+	} else {
+		string fileName = root["file"].asString();
+		// TODO: Only do this in getdata when remaining is 0 (when the file is fully downloaded) - maybe set text to "downloading.." in between
+		emit qmlHandler->receivingDisableDownloadButton(QString::fromStdString(fileName));
+	}
+}
+
+void CmdManager::handleGetData(Json::Value root) {
+	// TODO: Show speed and handle Error
+}
+
+void CmdManager::handleDeleteMe(Json::Value root) {
+	if (root["accept"] == true) {
+		qmlHandler->setRestart(true);
+		emit qmlHandler->closeWindow();
+	} else {
+		QString errorMessage = QString::fromStdString(root["error"].asString());
+		emit qmlHandler->deleteMePopupSetStatus(errorMessage);
+	}
+}
+
+void CmdManager::handleDeleteFile(Json::Value root) {
+	emit qmlHandler->receivingCloseConfirmDeletePopup();
+	if (root["accept"] == false) {
+		QString errorMessage = QString::fromStdString(string("Error when deleting file " + root["file"].asString() + ":\n" + root["error"].asString()));
+		emit qmlHandler->log(errorMessage);
+	} else {
+		QString message = QString::fromStdString(string("Deleted file " + root["file"].asString() + " from the server!"));
+		emit qmlHandler->log(message);
+	}
+}

+ 26 - 0
gui/src/jsonhandler.cpp

@@ -0,0 +1,26 @@
+#include "../include/jsonhandler.h"
+#include "../include/cmdmanager.h"
+
+using namespace std;
+
+// This method gets a string and tries to read it as Json
+// If it fails to do so, return and do nothing, else handle the content
+void JsonHandler::parseJSON(string buffer) {
+	Json::Value root;
+	Json::CharReaderBuilder builder;
+	Json::CharReader *reader = builder.newCharReader();
+	string jsonError;
+
+	// Try to parse the string as Json and store the result of the pasring in a
+	// boolean
+	bool parsingSuccessful = reader->parse(buffer.c_str(), buffer.c_str() + buffer.size(), &root, &jsonError);
+
+	// If the string is not correct Json, return
+	if (!parsingSuccessful) {
+		return;
+	}
+
+	string cmd = root["command"].asString();
+
+	CmdManager::executeCmd(cmd, root);
+}

+ 6 - 2
gui/src/main.cpp

@@ -13,7 +13,9 @@
 #include <thread>
 #include <unistd.h>
 
-#include "qmlhandler.h"
+#include "../include/cmdmanager.h"
+#include "../include/jsonhandler.h"
+#include "../include/qmlhandler.h"
 
 using namespace std;
 
@@ -28,13 +30,15 @@ int main(int argc, char *argv[]) {
 	QQmlApplicationEngine engine;
 
 	QMLHandler qmlHandler;
+	CmdManager::setQmlHandler(&qmlHandler);
+	CmdManager::init();
 
 	// Set the context for the window, so that the qml files can be connected to
 	// the qmlHandler
 	engine.rootContext()->setContextProperty("_qmlHandler", &qmlHandler);
 
 	// Load the main window
-	QQmlComponent component(&engine, QUrl(QStringLiteral("qrc:/main.qml")));
+	QQmlComponent component(&engine, QUrl(QStringLiteral("qrc:/Forms/Main/main.qml")));
 
 	QObject *object = component.create();
 

+ 24 - 17
gui/src/qml.qrc

@@ -1,22 +1,29 @@
 <RCC>
     <qresource prefix="/">
-        <file>main.qml</file>
-        <file>SendingForm.ui.qml</file>
-        <file>ReceivingForm.ui.qml</file>
-        <file>SettingsForm.ui.qml</file>
-        <file>MessagesForm.ui.qml</file>
         <file>qtquickcontrols2.conf</file>
-        <file>LoginSignupPopup.ui.qml</file>
-        <file>HelpForm.ui.qml</file>
-        <file>FooterForm.ui.qml</file>
-        <file>IpPopup.ui.qml</file>
-        <file>LoginForm.ui.qml</file>
-        <file>SignupForm.ui.qml</file>
-        <file>ReceivingFileTemplate.ui.qml</file>
-        <file>ReceivingFileTemplateDeletePopup.ui.qml</file>
-        <file>NoConfigFoundPopup.ui.qml</file>
-        <file>InvalidCliPathPopup.ui.qml</file>
-        <file>InvalidConfigPopup.ui.qml</file>
-        <file>DeleteMePopup.ui.qml</file>
+
+        <file>Forms/Main/main.qml</file>
+        <file>Forms/Main/FooterForm.ui.qml</file>
+        <file>Forms/Main/NoConfigFoundPopup.ui.qml</file>
+        <file>Forms/Main/InvalidCliPathPopup.ui.qml</file>
+        <file>Forms/Main/InvalidConfigPopup.ui.qml</file>
+
+        <file>Forms/Connect/LoginForm.ui.qml</file>
+        <file>Forms/Connect/IpPopup.ui.qml</file>
+        <file>Forms/Connect/LoginSignupPopup.ui.qml</file>
+        <file>Forms/Connect/SignupForm.ui.qml</file>
+
+        <file>Forms/Sending/SendingForm.ui.qml</file>
+
+        <file>Forms/Receiving/ReceivingForm.ui.qml</file>
+        <file>Forms/Receiving/ReceivingFileTemplate.ui.qml</file>
+        <file>Forms/Receiving/ReceivingFileTemplateDeletePopup.ui.qml</file>
+
+        <file>Forms/Messages/MessagesForm.ui.qml</file>
+
+        <file>Forms/Settings/DeleteMePopup.ui.qml</file>
+        <file>Forms/Settings/SettingsForm.ui.qml</file>
+
+        <file>Forms/Help/HelpForm.ui.qml</file>
     </qresource>
 </RCC>

+ 13 - 138
gui/src/qmlhandler.cpp

@@ -12,8 +12,9 @@
 #include <thread>
 #include <unistd.h>
 
-#include "config.h"
-#include "qmlhandler.h"
+#include "../include/config.h"
+#include "../include/jsonhandler.h"
+#include "../include/qmlhandler.h"
 #include <boost/asio.hpp>
 #include <boost/filesystem.hpp>
 #include <boost/lexical_cast.hpp>
@@ -100,141 +101,6 @@ std::vector<std::string> tokenizeByNewlines(std::string in) {
 
 void QMLHandler::onExit() { write(outpipefd[1], "disconnect\n", strlen("disconnect\n")); }
 
-// This method gets a string and tries to read it as Json
-// If it fails to do so, return and do nothing, else handle the content
-void QMLHandler::handleJSON(string buffer) {
-	Json::Value root;
-	Json::CharReaderBuilder builder;
-	Json::CharReader *reader = builder.newCharReader();
-	string jsonError;
-
-	// Try to parse the string as Json and store the result of the pasring in a
-	// boolean
-	bool parsingSuccessful = reader->parse(buffer.c_str(), buffer.c_str() + buffer.size(), &root, &jsonError);
-
-	// If the string is not correct Json, return
-	if (!parsingSuccessful) {
-		return;
-	}
-
-	const Json::Value command = root["command"];
-	string cmd = command.asString();
-	qInfo() << QString::fromStdString("Received command " + cmd);
-
-	if (!cmd.compare("status")) {
-		emit footerSetStatus(root["response"].asString().c_str());
-	}
-
-	else if (!cmd.compare("close")) {
-		programActive = false;
-	}
-
-	else if (!cmd.compare("list")) {
-		if (root["accept"] == true) {
-			emit receivingClearFileList();
-
-			// Get the array of file Names
-			auto fileNames = root["names"];
-			for (int i = 0; i < fileNames.size(); i++) {
-				emit receivingListFile(QString::fromStdString(fileNames[i].asString().c_str()), boost::filesystem::exists(fileNames[i].asString()));
-			}
-		} else {
-			emit log(root["error"].asString().c_str());
-		}
-	}
-
-	else if (!cmd.compare("connect")) {
-		if (root["accept"].asBool()) {
-		} else {
-			emit ipPopupSetStatus(root["error"].asString().c_str());
-			closeCLI();
-			emit ipPopupEnableConnectButton();
-		}
-	}
-
-	else if (!cmd.compare("version")) {
-		if (root["accept"] == true) {
-			emit ipPopupClose();
-			emit loginSignupPopupOpen();
-		} else {
-			QString errorMessage = QString::fromStdString(
-			    string("Version mismatch: \nClient: " + root["clientversion"].asString() + "\nServer: " + root["serverversion"].asString()));
-			emit ipPopupSetStatus(errorMessage);
-			closeCLI();
-			emit ipPopupEnableConnectButton();
-		}
-	}
-
-	else if (!cmd.compare("login")) {
-		if (root["accept"] == true) {
-			emit loginSignupPopupClose();
-			write(outpipefd[1], "list\n", strlen("list\n"));
-			loadSettingsToGUI();
-		} else {
-			emit loginSetStatus(root["error"].asString().c_str());
-			reopenCLI(_IP);
-			emit loginEnableLoginButton();
-		}
-	}
-
-	else if (!cmd.compare("signup")) {
-		if (root["accept"] == true) {
-			emit loginSignupPopupClose();
-		} else {
-			emit signupSetStatus(root["error"].asString().c_str());
-			reopenCLI(_IP);
-			emit signupEnableRegisterButton();
-		}
-	}
-
-	else if (!cmd.compare("put")) {
-		if (root["accept"] == false) {
-			QString errorMessage = QString::fromStdString(string("Error when uploading file " + root["file"].asString() + ":\n" + root["error"].asString()));
-			emit log(errorMessage);
-		}
-	}
-
-	else if (!cmd.compare("putdata")) {
-		// TODO: Show speed and handle Error
-	}
-
-	else if (!cmd.compare("get")) {
-		if (root["accept"] == false) {
-			QString errorMessage = QString::fromStdString(string("Error when downloading file " + root["file"].asString() + ":\n" + root["error"].asString()));
-			emit log(errorMessage);
-		} else {
-			string fileName = root["file"].asString();
-			// TODO: Only do this in getdata when remaining is 0 (when the file is fully downloaded) - maybe set text to "downloading.." in between
-			emit receivingDisableDownloadButton(QString::fromStdString(fileName));
-		}
-	}
-
-	else if (!cmd.compare("getdata")) {
-		// TODO: Show speed and handle Error
-	}
-
-	else if (!cmd.compare("deleteme")) {
-		if (root["accept"] == true) {
-			_RESTART = true;
-			emit closeWindow();
-		} else {
-			QString errorMessage = QString::fromStdString(root["error"].asString());
-			emit deleteMePopupSetStatus(errorMessage);
-		}
-	}
-
-	else if (!cmd.compare("deletefile")) {
-		emit receivingCloseConfirmDeletePopup();
-		if (root["accept"] == false) {
-			QString errorMessage = QString::fromStdString(string("Error when deleting file " + root["file"].asString() + ":\n" + root["error"].asString()));
-			emit log(errorMessage);
-		} else {
-			QString message = QString::fromStdString(string("Deleted file " + root["file"].asString() + " from the server!"));
-			emit log(message);
-		}
-	}
-}
-
 // This method is a loop which runs in a seperate thread.
 // If will read the Input Pipe, which containts the string that get printed
 // on stdout by the CLI/Server, and calls handleJSON with the read content
@@ -266,7 +132,8 @@ void QMLHandler::readPipeLoop() {
 			for (string s : inputs) {
 				emit log(QString::fromStdString(s));
 				qInfo() << QString::fromStdString(s);
-				handleJSON(s);
+				// handleJSON(s);
+				JsonHandler::parseJSON(s);
 			}
 			pipeInput = string();
 			memset(buf, 0, 1025);
@@ -448,3 +315,11 @@ void QMLHandler::onSignupRegisterButton(QString username, QString passwordOne, Q
 
 // Footer
 void QMLHandler::onFooterGetStatusButton() { write(outpipefd[1], "status\n", strlen("status\n")); }
+
+void QMLHandler::setProgramActive(bool active) { programActive = active; }
+
+void QMLHandler::writeToCLI(QString command) { write(outpipefd[1], command.toUtf8().constData(), strlen(command.toUtf8().constData())); }
+
+QString QMLHandler::getIP() { return _IP; }
+
+void QMLHandler::setRestart(bool restart) { _RESTART = restart; }