Changed language to C++ and started real development

This commit is contained in:
Blue Fox 2023-09-07 00:57:13 +02:00
parent c557ce7e0e
commit 0cb0f71310
10 changed files with 183 additions and 275 deletions

2
.gitignore vendored
View File

@ -1,2 +1,4 @@
Scorganizr.pyproject.user*
CMakeLists.txt.user
build*/
__pycache__/

37
CMakeLists.txt Normal file
View File

@ -0,0 +1,37 @@
cmake_minimum_required(VERSION 3.16)
project(Scorganizr VERSION 0.1 LANGUAGES CXX)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
find_package(Qt6 6.4 REQUIRED COMPONENTS Quick)
qt_standard_project_setup()
qt_add_executable(appScorganizr
main.cpp
)
qt_add_qml_module(appScorganizr
URI Scorganizr
VERSION 1.0
QML_FILES Main.qml SiteInConstruction.qml Icon.qml
)
set_target_properties(appScorganizr PROPERTIES
MACOSX_BUNDLE_GUI_IDENTIFIER my.example.com
MACOSX_BUNDLE_BUNDLE_VERSION ${PROJECT_VERSION}
MACOSX_BUNDLE_SHORT_VERSION_STRING ${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}
MACOSX_BUNDLE TRUE
WIN32_EXECUTABLE TRUE
)
target_link_libraries(appScorganizr
PRIVATE Qt6::Quick
)
install(TARGETS appScorganizr
BUNDLE DESTINATION .
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
)

21
Icon.qml Normal file
View File

@ -0,0 +1,21 @@
import QtQuick
import Qt5Compat.GraphicalEffects
Image {
id: icon
property string color: ""
property string path: ""
fillMode: Image.PreserveAspectFit
source: path
layer{
enabled: color != ""
effect: ColorOverlay {
color: icon.color
}
}
sourceSize: Qt.size(width*3, height*3) // for better resolution when loading svg files
}

66
Main.qml Normal file
View File

@ -0,0 +1,66 @@
import QtQuick
import QtQuick.Window
import QtQuick.Controls
import QtQuick.Controls.Material
ApplicationWindow {
width: Screen.width/2
height: Screen.height/2
visible: true
title: "Scorganizr"
Material.theme: Material.System
Material.accent: Material.Pink
Page {
id: window
anchors.fill: parent
Keys.onPressed: (event)=> {
if (event.key === Qt.Key_1) tabBar.currentIndex = 0;
if (event.key === Qt.Key_2) tabBar.currentIndex = 1;
if (event.key === Qt.Key_3) tabBar.currentIndex = 2;
if (event.key === Qt.Key_4) tabBar.currentIndex = 3;
if (event.key === Qt.Key_5) tabBar.currentIndex = 4;
}
focus: true
SwipeView {
id: swipeView
anchors.fill: parent
currentIndex: tabBar.currentIndex
Repeater {
model: 5
Pane {
width: SwipeView.view.width
height: SwipeView.view.height
SiteInConstruction {}
}
}
}
footer: TabBar {
id: tabBar
currentIndex: swipeView.currentIndex
TabButton {
text: qsTr("Notes")
}
TabButton {
text: qsTr("Grades")
}
TabButton {
text: qsTr("Tasks")
}
TabButton {
text: qsTr("Calendar")
}
TabButton {
text: qsTr("Learn")
}
}
}
}

View File

@ -1,3 +0,0 @@
{
"files": ["main.ui","main.py","utils.py"]
}

39
SiteInConstruction.qml Normal file
View File

@ -0,0 +1,39 @@
import QtQuick
import QtQuick.Controls.Material
Item {
id: siteInConstruction
anchors.fill: parent
property string inDevIconDataURI: `data:image/svg+xml;utf8,
<svg xmlns="http://www.w3.org/2000/svg">
<path d="M10.478 1.647a.5.5 0 1 0-.956-.294l-4 13a.5.5 0 0 0 .956.294l4-13zM4.854 4.146a.5.5 0 0 1 0 .708L1.707 8l3.147 3.146a.5.5 0 0 1-.708.708l-3.5-3.5a.5.5 0 0 1 0-.708l3.5-3.5a.5.5 0 0 1 .708 0zm6.292 0a.5.5 0 0 0 0 .708L14.293 8l-3.147 3.146a.5.5 0 0 0 .708.708l3.5-3.5a.5.5 0 0 0 0-.708l-3.5-3.5a.5.5 0 0 0-.708 0z"/>
</svg>`
property string subtitle: ""
// workaround to prevent the error "Point size [...] must be greater than 0"
function getFontSize(s) {
return s === 0 ? 1 : s;
}
children: [
Icon {
id: inDevIcon
anchors.verticalCenter: parent.verticalCenter
anchors.horizontalCenter: parent.horizontalCenter
path: parent.inDevIconDataURI
width: parent.width/5
height: width
color: "white"
},
Text {
id: inDevText
anchors.verticalCenter: parent.verticalCenter
anchors.horizontalCenter: parent.horizontalCenter
anchors.top: inDevIcon.bottom
anchors.margins: inDevIcon.width/10
font.pointSize: getFontSize(inDevIcon.width/8)
text: "Site in construction!"
color: Material.foreground
}
]
}

18
main.cpp Normal file
View File

@ -0,0 +1,18 @@
#include <QGuiApplication>
#include <QQmlApplicationEngine>
int main(int argc, char *argv[])
{
qputenv("QT_IM_MODULE", QByteArray("qtvirtualkeyboard"));
QGuiApplication app(argc, argv);
QQmlApplicationEngine engine;
QObject::connect(&engine, &QQmlApplicationEngine::objectCreationFailed,
&app, []() { QCoreApplication::exit(-1); },
Qt::QueuedConnection);
engine.load( QUrl("qrc:/Scorganizr/Main.qml") );
return app.exec();
}

45
main.py
View File

@ -1,45 +0,0 @@
"""
Main application
Copyright (C) 2023 Benjamin Burkhardt
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 3 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, see <https://www.gnu.org/licenses/>.
"""
import sys
from PySide6.QtWidgets import QApplication
from PySide6.QtCore import QFile, QIODevice
from PySide6.QtUiTools import QUiLoader
from utils import Logger
if __name__ == "__main__":
# needed variables
app = QApplication(sys.argv)
logger = Logger()
ui_file_name = "main.ui"
# create the window
ui_file = QFile(ui_file_name)
if not ui_file.open(QIODevice.ReadOnly):
logger.log(f"Cannot open {ui_file_name}: {ui_file.errorString()}. Exiting.", 1)
sys.exit(-1)
window = QUiLoader().load(ui_file)
ui_file.close()
if not window:
logger.log(loader.errorString(), 1)
sys.exit(-1)
window.show()
# run as long as the app is executing
sys.exit(app.exec())

84
main.ui
View File

@ -1,84 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>MainWindow</class>
<widget class="QMainWindow" name="MainWindow">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>718</width>
<height>408</height>
</rect>
</property>
<property name="windowTitle">
<string>Scorganizr</string>
</property>
<property name="windowIcon">
<iconset theme="insert-image">
<normaloff>.</normaloff>.</iconset>
</property>
<property name="animated">
<bool>true</bool>
</property>
<property name="documentMode">
<bool>false</bool>
</property>
<property name="tabShape">
<enum>QTabWidget::Rounded</enum>
</property>
<widget class="QWidget" name="centralwidget"/>
<widget class="QMenuBar" name="menubar">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>718</width>
<height>20</height>
</rect>
</property>
<widget class="QMenu" name="menuFile">
<property name="tearOffEnabled">
<bool>false</bool>
</property>
<property name="title">
<string>File</string>
</property>
<property name="separatorsCollapsible">
<bool>false</bool>
</property>
<property name="toolTipsVisible">
<bool>false</bool>
</property>
<addaction name="actionQuit"/>
</widget>
<addaction name="menuFile"/>
</widget>
<action name="actionQuit">
<property name="text">
<string>Quit</string>
</property>
<property name="shortcut">
<string>Ctrl+Q</string>
</property>
</action>
</widget>
<resources/>
<connections>
<connection>
<sender>actionQuit</sender>
<signal>triggered()</signal>
<receiver>MainWindow</receiver>
<slot>close()</slot>
<hints>
<hint type="sourcelabel">
<x>-1</x>
<y>-1</y>
</hint>
<hint type="destinationlabel">
<x>358</x>
<y>203</y>
</hint>
</hints>
</connection>
</connections>
</ui>

143
utils.py
View File

@ -1,143 +0,0 @@
"""
Utility classes and functions
Copyright (C) 2023 Benjamin Burkhardt
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 3 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, see <https://www.gnu.org/licenses/>.
"""
# Logger class that has 7 log levels: trace/all (6), debug (5), info(4), warning (3), error (2), fatal (1), off (0)
# log "level" -1 is always printed out ("On")
LOG_LVL_FALLBACK = 4 # the default level for logging
class Logger:
def __init__(self, log_level=LOG_LVL_FALLBACK):
self.mappings = { # mappings for the color and syntax of the log
-1: {
"prefix": "",
"space_between": "",
"prefix_colors": ShellColors.F_Default + ShellColors.B_Default,
"text_colors": ShellColors.F_Default + ShellColors.B_Default,
},
1: {
"prefix": "[FATAL]",
"space_between": " ",
"prefix_colors": ShellColors.F_White + ShellColors.B_Red,
"text_colors": ShellColors.B_Red + ShellColors.F_White,
},
2: {
"prefix": "[ERROR]",
"space_between": " ",
"prefix_colors": ShellColors.F_White + ShellColors.B_Red,
"text_colors": ShellColors.B_Red + ShellColors.F_White,
},
3: {
"prefix": "[WARN]",
"space_between": " ",
"prefix_colors": ShellColors.F_LightRed + ShellColors.B_Default,
"text_colors": ShellColors.F_Default + ShellColors.B_Default,
},
4: {
"prefix": "[INFO]",
"space_between": " ",
"prefix_colors": ShellColors.F_Green + ShellColors.B_Default,
"text_colors": ShellColors.F_Default + ShellColors.B_Default,
},
5: {
"prefix": "[DEBUG]",
"space_between": " ",
"prefix_colors": ShellColors.F_LightGray + ShellColors.B_Default,
"text_colors": ShellColors.F_Default + ShellColors.B_Default,
},
6: {
"prefix": "[TRACE]",
"space_between": " ",
"prefix_colors": ShellColors.F_Default + ShellColors.B_Default,
"text_colors": ShellColors.F_Default + ShellColors.B_Default,
},
}
if -1 <= log_level <= 6:
self.log_level = log_level
else: # if the given level exeeds the allowed scope
self.log_level = LOG_LVL_FALLBACK
self.log(f"The log level exeeds the allowed scope. Defaulting to {LOG_LVL_FALLBACK}", 3)
def log(self, message, log_level=4):
if log_level <= self.log_level: # only log when supposed to (if the given lvl is lower/equal (than) the maximum wanted)
prefix_colors = self.mappings[log_level]['prefix_colors']
prefix = self.mappings[log_level]['prefix']
space_between = self.mappings[log_level]['space_between']
text_colors = self.mappings[log_level]['text_colors']
end_color = ShellColors.Reset
print(f"{prefix_colors}{prefix}{text_colors}{space_between}{message}{end_color}")
# just for prettier shell outputs (especially log)
# source: https://stackoverflow.com/questions/39473297/how-do-i-print-colored-output-with-python-3
class ShellColors:
# Foreground
F_Default = "\x1b[39m"
F_Black = "\x1b[30m"
F_Red = "\x1b[31m"
F_Green = "\x1b[32m"
F_Yellow = "\x1b[33m"
F_Blue = "\x1b[34m"
F_Magenta = "\x1b[35m"
F_Cyan = "\x1b[36m"
F_LightGray = "\x1b[37m"
F_DarkGray = "\x1b[90m"
F_LightRed = "\x1b[91m"
F_LightGreen = "\x1b[92m"
F_LightYellow = "\x1b[93m"
F_LightBlue = "\x1b[94m"
F_LightMagenta = "\x1b[95m"
F_LightCyan = "\x1b[96m"
F_White = "\x1b[97m"
# Background
B_Default = "\x1b[49m"
B_Black = "\x1b[40m"
B_Red = "\x1b[41m"
B_Green = "\x1b[42m"
B_Yellow = "\x1b[43m"
B_Blue = "\x1b[44m"
B_Magenta = "\x1b[45m"
B_Cyan = "\x1b[46m"
B_LightGray = "\x1b[47m"
B_DarkGray = "\x1b[100m"
B_LightRed = "\x1b[101m"
B_LightGreen = "\x1b[102m"
B_LightYellow = "\x1b[103m"
B_LightBlue = "\x1b[104m"
B_LightMagenta = "\x1b[105m"
B_LightCyan = "\x1b[106m"
B_White = "\x1b[107m"
# Formatting
Bold = "\x1b[1m"
Dim = "\x1b[2m"
Italic = "\x1b[3m"
Underlined = "\x1b[4m"
Blink = "\x1b[5m"
Reverse = "\x1b[7m"
Hidden = "\x1b[8m"
# Reset part
Reset = "\x1b[0m"
Reset_Bold = "\x1b[21m"
Reset_Dim = "\x1b[22m"
Reset_Italic = "\x1b[23m"
Reset_Underlined = "\x1b[24"
Reset_Blink = "\x1b[25m"
Reset_Reverse = "\x1b[27m"
Reset_Hidden = "\x1b[28m"