From 69daff454353acbf22eb248b7655fe9daf1963c7 Mon Sep 17 00:00:00 2001 From: Victor Tran Date: Wed, 28 Jul 2021 16:25:10 +1000 Subject: [PATCH] Fix build issues --- shell/endsessionwait.cpp | 193 +- shell/endsessionwait.h | 109 +- shell/infopanedropdown.cpp | 4169 ++++++++++++++++++++- shell/infopanedropdown.ui | 6990 +++++++++++++++++++++++++++++++++++- shell/menu.cpp | 141 +- shell/menu.h | 27 +- shell/newmedia.cpp | 35 +- shell/newmedia.h | 37 +- shell/shell.pro | 2 +- shell/systrayicons.cpp | 19 +- theShell.pro.user | 322 +- 11 files changed, 11620 insertions(+), 424 deletions(-) diff --git a/shell/endsessionwait.cpp b/shell/endsessionwait.cpp index 9b9dde2..af6ee8d 100644 --- a/shell/endsessionwait.cpp +++ b/shell/endsessionwait.cpp @@ -24,17 +24,16 @@ extern float getDPIScaling(); extern void sendMessageToRootWindow(const char* message, Window window, long data0 = 0, long data1 = 0, long data2 = 0, long data3 = 0, long data4 = 0); -EndSessionWait::EndSessionWait(shutdownType type, QWidget *parent) : +EndSessionWait::EndSessionWait(shutdownType type, QWidget* parent) : QDialog(parent), - ui(new Ui::EndSessionWait) -{ + ui(new Ui::EndSessionWait) { ui->setupUi(this); ui->cancelButton->setFixedHeight(0); ui->killAllButton->setFixedHeight(0); tbManager = new TaskbarManager(); - connect(tbManager, &TaskbarManager::deleteWindow, [=] { + connect(tbManager, &TaskbarManager::deleteWindow, [ = ] { if (tbManager->Windows().count() - 1 == 0) { tbTimer->stop(); if (performEndSessionWhenAllAppsClosed) { @@ -51,11 +50,11 @@ EndSessionWait::EndSessionWait(shutdownType type, QWidget *parent) : powerOffTimer->setStartValue(0); powerOffTimer->setEndValue(300); powerOffTimer->setDuration(30000); - connect(powerOffTimer, &QVariantAnimation::valueChanged, [=](QVariant value) { + connect(powerOffTimer, &QVariantAnimation::valueChanged, [ = ](QVariant value) { ui->idleProgressBar->setValue(value.toInt()); ui->idleWarning->setText(tr("If you don't do anything, we'll power off for you in %1 seconds.").arg(QString::number(30 - (value.toInt() / 10)))); }); - connect(powerOffTimer, &QVariantAnimation::finished, [=]() { + connect(powerOffTimer, &QVariantAnimation::finished, [ = ]() { //Power off the device this->type = powerOff; ui->powerType->setText(tr("Power Off")); @@ -64,7 +63,7 @@ EndSessionWait::EndSessionWait(shutdownType type, QWidget *parent) : QTimer* invokeTimer = new QTimer(); invokeTimer->setInterval(0); invokeTimer->setSingleShot(true); - connect(invokeTimer, &QTimer::timeout, [=]() { + connect(invokeTimer, &QTimer::timeout, [ = ]() { invokeTimer->deleteLater(); this->showFullScreen(); }); @@ -104,8 +103,7 @@ EndSessionWait::EndSessionWait(shutdownType type, QWidget *parent) : this->type = type; } -EndSessionWait::~EndSessionWait() -{ +EndSessionWait::~EndSessionWait() { delete ui; } @@ -117,7 +115,7 @@ void EndSessionWait::close() { anim->setDuration(250); anim->setEasingCurve(QEasingCurve::InCubic); connect(anim, SIGNAL(finished()), anim, SLOT(deleteLater())); - connect(anim, &tPropertyAnimation::finished, [=] { + connect(anim, &tPropertyAnimation::finished, [ = ] { this->reject(); }); anim->start(); @@ -187,9 +185,9 @@ void EndSessionWait::showFullScreen() { { //Animate the "End Session" dialog out - QGraphicsOpacityEffect *fadeEffect = new QGraphicsOpacityEffect(this); + QGraphicsOpacityEffect* fadeEffect = new QGraphicsOpacityEffect(this); ui->askWhatToDo->setGraphicsEffect(fadeEffect); - QPropertyAnimation *a = new QPropertyAnimation(fadeEffect, "opacity"); + QPropertyAnimation* a = new QPropertyAnimation(fadeEffect, "opacity"); a->setDuration(250); a->setStartValue(1); a->setEndValue(0); @@ -198,16 +196,16 @@ void EndSessionWait::showFullScreen() { { //Animate the "Ending Session" dialog in - QGraphicsOpacityEffect *fadeEffect = new QGraphicsOpacityEffect(this); + QGraphicsOpacityEffect* fadeEffect = new QGraphicsOpacityEffect(this); ui->poweringOff->setGraphicsEffect(fadeEffect); - QPropertyAnimation *a = new QPropertyAnimation(fadeEffect, "opacity"); + QPropertyAnimation* a = new QPropertyAnimation(fadeEffect, "opacity"); a->setDuration(250); a->setStartValue(0); a->setEndValue(1); animGroup->addAnimation(a); } - connect(animGroup, &QSequentialAnimationGroup::currentAnimationChanged, [=](QAbstractAnimation* current) { + connect(animGroup, &QSequentialAnimationGroup::currentAnimationChanged, [ = ](QAbstractAnimation * current) { if (animGroup->indexOfAnimation(current) == 1) { ui->askWhatToDo->setVisible(false); ui->poweringOff->setVisible(true); @@ -240,11 +238,11 @@ void EndSessionWait::showFullScreen() { Atom WindowListType; int format; unsigned long items, bytes; - unsigned char *data; + unsigned char* data; XGetWindowProperty(d, RootWindow(d, 0), XInternAtom(d, "_NET_CLIENT_LIST", true), 0L, (~0L), - False, AnyPropertyType, &WindowListType, &format, &items, &bytes, &data); + False, AnyPropertyType, &WindowListType, &format, &items, &bytes, &data); - quint64 *windows = (quint64*) data; + quint64* windows = (quint64*) data; for (unsigned long i = 0; i < items; i++) { TopWindows.append((Window) windows[i]); @@ -256,15 +254,15 @@ void EndSessionWait::showFullScreen() { int retval = XGetWindowAttributes(d, win, &attributes); unsigned long items, bytes; - unsigned char *netWmName; + unsigned char* netWmName; XTextProperty wmName; int format; Atom ReturnType; retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_VISIBLE_NAME", False), 0, 1024, False, - XInternAtom(d, "UTF8_STRING", False), &ReturnType, &format, &items, &bytes, &netWmName); + XInternAtom(d, "UTF8_STRING", False), &ReturnType, &format, &items, &bytes, &netWmName); if (retval != 0 || netWmName == 0x0) { retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_NAME", False), 0, 1024, False, - AnyPropertyType, &ReturnType, &format, &items, &bytes, &netWmName); + AnyPropertyType, &ReturnType, &format, &items, &bytes, &netWmName); if (retval != 0) { retval = XGetWMName(d, win, &wmName); if (retval == 1) { @@ -280,19 +278,19 @@ void EndSessionWait::showFullScreen() { QString title; if (netWmName) { - title = QString::fromLocal8Bit((char *) netWmName); + title = QString::fromLocal8Bit((char*) netWmName); XFree(netWmName); } else if (wmName.value) { - title = QString::fromLatin1((char *) wmName.value); + title = QString::fromLatin1((char*) wmName.value); //XFree(wmName); } - unsigned long *pidPointer; + unsigned long* pidPointer; unsigned long pitems, pbytes; int pformat; Atom pReturnType; int retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_PID", False), 0, 1024, False, - XA_CARDINAL, &pReturnType, &pformat, &pitems, &pbytes, (unsigned char**) &pidPointer); + XA_CARDINAL, &pReturnType, &pformat, &pitems, &pbytes, (unsigned char**) &pidPointer); if (retval == 0) { if (pidPointer != 0) { unsigned long pid = *pidPointer; @@ -329,14 +327,14 @@ void EndSessionWait::showFullScreen() { tbTimer->start(); performEndSessionWhenAllAppsClosed = true; - QTimer::singleShot(5000, [=] { - auto animateResize = [=](QWidget* widget) { + QTimer::singleShot(5000, [ = ] { + auto animateResize = [ = ](QWidget * widget) { tVariantAnimation* anim = new tVariantAnimation(); anim->setStartValue(widget->height()); anim->setEndValue(widget->sizeHint().height()); anim->setEasingCurve(QEasingCurve::OutCubic); anim->setDuration(500); - connect(anim, &tVariantAnimation::valueChanged, [=](QVariant value) { + connect(anim, &tVariantAnimation::valueChanged, [ = ](QVariant value) { widget->setFixedHeight(value.toInt()); }); connect(anim, SIGNAL(finished()), anim, SLOT(deleteLater())); @@ -350,14 +348,14 @@ void EndSessionWait::showFullScreen() { }); } } else if (this->type == dummy) { - QTimer::singleShot(5000, [=] { - auto animateResize = [=](QWidget* widget) { + QTimer::singleShot(5000, [ = ] { + auto animateResize = [ = ](QWidget * widget) { tVariantAnimation* anim = new tVariantAnimation(); anim->setStartValue(widget->height()); anim->setEndValue(widget->sizeHint().height()); anim->setEasingCurve(QEasingCurve::OutCubic); anim->setDuration(500); - connect(anim, &tVariantAnimation::valueChanged, [=](QVariant value) { + connect(anim, &tVariantAnimation::valueChanged, [ = ](QVariant value) { widget->setFixedHeight(value.toInt()); }); connect(anim, SIGNAL(finished()), anim, SLOT(deleteLater())); @@ -373,8 +371,7 @@ void EndSessionWait::showFullScreen() { } } -void EndSessionWait::on_killAllButton_clicked() -{ +void EndSessionWait::on_killAllButton_clicked() { QProcess p; p.start("wmctrl -lp"); p.waitForStarted(); @@ -419,7 +416,7 @@ void EndSessionWait::performEndSession() { QMediaPlayer* sound = new QMediaPlayer(); connect(sound, SIGNAL(error(QMediaPlayer::Error)), this, SLOT(EndSessionNow())); - connect(sound, &QMediaPlayer::stateChanged, [=]() { + connect(sound, &QMediaPlayer::stateChanged, [ = ]() { if (sound->state() == QMediaPlayer::StoppedState) { EndSessionNow(); } @@ -429,9 +426,9 @@ void EndSessionWait::performEndSession() { sound->play(); QParallelAnimationGroup* animGroup = new QParallelAnimationGroup(); - QGraphicsOpacityEffect *fadeEffect = new QGraphicsOpacityEffect(this); + QGraphicsOpacityEffect* fadeEffect = new QGraphicsOpacityEffect(this); ui->poweringOff->setGraphicsEffect(fadeEffect); - QPropertyAnimation *a = new QPropertyAnimation(fadeEffect, "opacity"); + QPropertyAnimation* a = new QPropertyAnimation(fadeEffect, "opacity"); a->setDuration(500); a->setStartValue(1); a->setEndValue(0); @@ -445,7 +442,7 @@ void EndSessionWait::performEndSession() { animGroup->start(); - connect(a, &QPropertyAnimation::finished, [=]() { + connect(a, &QPropertyAnimation::finished, [ = ]() { ui->poweringOff->setVisible(false); }); } @@ -455,58 +452,52 @@ void EndSessionWait::EndSessionNow() { QList arguments; arguments.append(true); switch (type) { - case powerOff: - //Power off the PC - message = QDBusMessage::createMethodCall("org.freedesktop.login1", "/org/freedesktop/login1", "org.freedesktop.login1.Manager", "PowerOff"); - message.setArguments(arguments); - QDBusConnection::systemBus().send(message); - - break; - case reboot: - //Reboot the PC - message = QDBusMessage::createMethodCall("org.freedesktop.login1", "/org/freedesktop/login1", "org.freedesktop.login1.Manager", "Reboot"); - message.setArguments(arguments); - QDBusConnection::systemBus().send(message); - break; - case logout: - QApplication::exit(0); + case powerOff: + //Power off the PC + message = QDBusMessage::createMethodCall("org.freedesktop.login1", "/org/freedesktop/login1", "org.freedesktop.login1.Manager", "PowerOff"); + message.setArguments(arguments); + QDBusConnection::systemBus().send(message); + + break; + case reboot: + //Reboot the PC + message = QDBusMessage::createMethodCall("org.freedesktop.login1", "/org/freedesktop/login1", "org.freedesktop.login1.Manager", "Reboot"); + message.setArguments(arguments); + QDBusConnection::systemBus().send(message); + break; + case logout: + QApplication::exit(0); } } -void EndSessionWait::on_cancelButton_clicked() -{ +void EndSessionWait::on_cancelButton_clicked() { performEndSessionWhenAllAppsClosed = false; this->close(); } -void EndSessionWait::on_CancelAsk_clicked() -{ +void EndSessionWait::on_CancelAsk_clicked() { this->close(); } -void EndSessionWait::on_PowerOff_clicked() -{ +void EndSessionWait::on_PowerOff_clicked() { this->type = powerOff; ui->powerType->setText(tr("Power Off")); this->showFullScreen(); } -void EndSessionWait::on_Reboot_clicked() -{ +void EndSessionWait::on_Reboot_clicked() { this->type = reboot; ui->powerType->setText(tr("Reboot")); this->showFullScreen(); } -void EndSessionWait::on_LogOut_clicked() -{ +void EndSessionWait::on_LogOut_clicked() { this->type = logout; ui->powerType->setText(tr("Log Out")); this->showFullScreen(); } -void EndSessionWait::on_Suspend_clicked() -{ +void EndSessionWait::on_Suspend_clicked() { QList arguments; arguments.append(true); @@ -516,8 +507,7 @@ void EndSessionWait::on_Suspend_clicked() this->close(); } -void EndSessionWait::on_terminateApp_clicked() -{ +void EndSessionWait::on_terminateApp_clicked() { powerOffTimer->stop(); powerOffTimer->setCurrentTime(0); QParallelAnimationGroup* group = new QParallelAnimationGroup(); @@ -527,7 +517,7 @@ void EndSessionWait::on_terminateApp_clicked() topAnim->setEndValue(0); topAnim->setEasingCurve(QEasingCurve::OutCubic); topAnim->setDuration(250); - connect(topAnim, &QVariantAnimation::valueChanged, [=](QVariant value) { + connect(topAnim, &QVariantAnimation::valueChanged, [ = ](QVariant value) { ui->ExitFrameTop->setFixedHeight(value.toInt()); }); @@ -536,7 +526,7 @@ void EndSessionWait::on_terminateApp_clicked() bottomAnim->setEndValue(0); bottomAnim->setEasingCurve(QEasingCurve::OutCubic); bottomAnim->setDuration(250); - connect(bottomAnim, &QVariantAnimation::valueChanged, [=](QVariant value) { + connect(bottomAnim, &QVariantAnimation::valueChanged, [ = ](QVariant value) { ui->ExitFrameBottom->setFixedHeight(value.toInt()); }); @@ -545,7 +535,7 @@ void EndSessionWait::on_terminateApp_clicked() midAnim->setEndValue(ui->terminateAppFrame->sizeHint().height()); midAnim->setEasingCurve(QEasingCurve::OutCubic); midAnim->setDuration(250); - connect(midAnim, &QVariantAnimation::valueChanged, [=](QVariant value) { + connect(midAnim, &QVariantAnimation::valueChanged, [ = ](QVariant value) { ui->terminateAppFrame->setFixedHeight(value.toInt()); }); @@ -555,7 +545,7 @@ void EndSessionWait::on_terminateApp_clicked() group->start(); - connect(group, &QParallelAnimationGroup::finished, [=]() { + connect(group, &QParallelAnimationGroup::finished, [ = ]() { ui->terminateAppFrame->setFixedHeight(ui->terminateAppFrame->sizeHint().height()); ui->ExitFrameTop->setFixedHeight(0); ui->ExitFrameBottom->setFixedHeight(0); @@ -574,11 +564,11 @@ void EndSessionWait::reloadAppList() { Atom WindowListType; int format; unsigned long items, bytes; - unsigned char *data; + unsigned char* data; XGetWindowProperty(d, RootWindow(d, 0), XInternAtom(d, "_NET_CLIENT_LIST", true), 0L, (~0L), - False, AnyPropertyType, &WindowListType, &format, &items, &bytes, &data); + False, AnyPropertyType, &WindowListType, &format, &items, &bytes, &data); - quint64 *windows = (quint64*) data; + quint64* windows = (quint64*) data; for (unsigned long i = 0; i < items; i++) { TopWindows.append((Window) windows[i]); @@ -591,15 +581,15 @@ void EndSessionWait::reloadAppList() { int retval = XGetWindowAttributes(d, win, &attributes); unsigned long items, bytes; - unsigned char *netWmName; + unsigned char* netWmName; XTextProperty wmName; int format; Atom ReturnType; retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_VISIBLE_NAME", False), 0, 1024, False, - XInternAtom(d, "UTF8_STRING", False), &ReturnType, &format, &items, &bytes, &netWmName); + XInternAtom(d, "UTF8_STRING", False), &ReturnType, &format, &items, &bytes, &netWmName); if (retval != 0 || netWmName == 0x0) { retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_NAME", False), 0, 1024, False, - AnyPropertyType, &ReturnType, &format, &items, &bytes, &netWmName); + AnyPropertyType, &ReturnType, &format, &items, &bytes, &netWmName); if (retval != 0) { retval = XGetWMName(d, win, &wmName); if (retval == 1) { @@ -615,19 +605,19 @@ void EndSessionWait::reloadAppList() { QString title; if (netWmName) { - title = QString::fromLocal8Bit((char *) netWmName); + title = QString::fromLocal8Bit((char*) netWmName); XFree(netWmName); } else if (wmName.value) { - title = QString::fromLatin1((char *) wmName.value); + title = QString::fromLatin1((char*) wmName.value); //XFree(wmName); } - unsigned long *pidPointer; + unsigned long* pidPointer; unsigned long pitems, pbytes; int pformat; Atom pReturnType; int retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_PID", False), 0, 1024, False, - XA_CARDINAL, &pReturnType, &pformat, &pitems, &pbytes, (unsigned char**) &pidPointer); + XA_CARDINAL, &pReturnType, &pformat, &pitems, &pbytes, (unsigned char**) &pidPointer); if (retval == 0) { if (pidPointer != 0) { unsigned long pid = *pidPointer; @@ -641,16 +631,16 @@ void EndSessionWait::reloadAppList() { { bool noIcon = false; unsigned long icItems, icBytes; - unsigned char *icon; + unsigned char* icon; int icFormat; Atom icReturnType; - unsigned char *ret; + unsigned char* ret; int width, height; retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_ICON", False), 0, 1, False, - XA_CARDINAL, &icReturnType, &icFormat, &icItems, &icBytes, &ret); + XA_CARDINAL, &icReturnType, &icFormat, &icItems, &icBytes, &ret); if (ret == 0x0) { noIcon = true; } else { @@ -659,7 +649,7 @@ void EndSessionWait::reloadAppList() { } retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_ICON", False), 1, 1, False, - XA_CARDINAL, &icReturnType, &icFormat, &icItems, &icBytes, &ret); + XA_CARDINAL, &icReturnType, &icFormat, &icItems, &icBytes, &ret); if (ret == 0x0) { noIcon = true; @@ -670,7 +660,7 @@ void EndSessionWait::reloadAppList() { if (!noIcon) { retval = XGetWindowProperty(d, win, XInternAtom(d, "_NET_WM_ICON", False), 2, width * height * 4, False, - XA_CARDINAL, &icReturnType, &icFormat, &icItems, &icBytes, &icon); + XA_CARDINAL, &icReturnType, &icFormat, &icItems, &icBytes, &icon); QImage image(width, height, QImage::Format_ARGB32); @@ -715,8 +705,7 @@ void EndSessionWait::reloadAppList() { } } -void EndSessionWait::on_exitTerminate_clicked() -{ +void EndSessionWait::on_exitTerminate_clicked() { powerOffTimer->start(); QParallelAnimationGroup* group = new QParallelAnimationGroup(); @@ -726,7 +715,7 @@ void EndSessionWait::on_exitTerminate_clicked() topAnim->setEasingCurve(QEasingCurve::OutCubic); topAnim->setDuration(500); topAnim->setKeyValueAt(0.5, 0); - connect(topAnim, &QVariantAnimation::valueChanged, [=](QVariant value) { + connect(topAnim, &QVariantAnimation::valueChanged, [ = ](QVariant value) { ui->ExitFrameTop->setFixedHeight(value.toInt()); }); @@ -736,7 +725,7 @@ void EndSessionWait::on_exitTerminate_clicked() bottomAnim->setEasingCurve(QEasingCurve::OutCubic); bottomAnim->setDuration(500); bottomAnim->setKeyValueAt(0.5, 0); - connect(bottomAnim, &QVariantAnimation::valueChanged, [=](QVariant value) { + connect(bottomAnim, &QVariantAnimation::valueChanged, [ = ](QVariant value) { ui->ExitFrameBottom->setFixedHeight(value.toInt()); }); @@ -745,7 +734,7 @@ void EndSessionWait::on_exitTerminate_clicked() midAnim->setEndValue(0); midAnim->setEasingCurve(QEasingCurve::OutCubic); midAnim->setDuration(500); - connect(midAnim, &QVariantAnimation::valueChanged, [=](QVariant value) { + connect(midAnim, &QVariantAnimation::valueChanged, [ = ](QVariant value) { ui->terminateAppFrame->setFixedHeight(value.toInt()); }); @@ -755,7 +744,7 @@ void EndSessionWait::on_exitTerminate_clicked() group->start(); - connect(group, &QParallelAnimationGroup::finished, [=]() { + connect(group, &QParallelAnimationGroup::finished, [ = ]() { ui->terminateAppFrame->setFixedHeight(0); ui->ExitFrameTop->setFixedHeight(ui->ExitFrameTop->sizeHint().height()); ui->ExitFrameBottom->setFixedHeight(ui->ExitFrameBottom->sizeHint().height()); @@ -763,24 +752,21 @@ void EndSessionWait::on_exitTerminate_clicked() }); } -void EndSessionWait::on_pushButton_5_clicked() -{ +void EndSessionWait::on_pushButton_5_clicked() { //Send SIGTERM to app kill(ui->listWidget->selectedItems().first()->data(Qt::UserRole).value(), SIGTERM); QThread::sleep(1); reloadAppList(); } -void EndSessionWait::on_pushButton_4_clicked() -{ +void EndSessionWait::on_pushButton_4_clicked() { //Send SIGKILL to app kill(ui->listWidget->selectedItems().first()->data(Qt::UserRole).value(), SIGKILL); QThread::sleep(1); reloadAppList(); } -void EndSessionWait::on_listWidget_currentRowChanged(int currentRow) -{ +void EndSessionWait::on_listWidget_currentRowChanged(int currentRow) { if (currentRow == -1) { ui->pushButton_5->setEnabled(false); ui->pushButton_4->setEnabled(false); @@ -790,8 +776,7 @@ void EndSessionWait::on_listWidget_currentRowChanged(int currentRow) } } -void EndSessionWait::on_DummyExit_clicked() -{ +void EndSessionWait::on_DummyExit_clicked() { //Fake Exit this->type = dummy; ui->powerType->setText(tr("Dummy")); @@ -806,14 +791,14 @@ void EndSessionWait::reject() { anim->setDuration(250); anim->setStartValue(this->windowOpacity()); anim->setEndValue(0.0); - connect(anim, &QPropertyAnimation::finished, [=]() { + connect(anim, &QPropertyAnimation::finished, [ = ]() { QDialog::reject(); anim->deleteLater(); }); anim->start(); } -void EndSessionWait::paintEvent(QPaintEvent *event) { +void EndSessionWait::paintEvent(QPaintEvent* event) { QPainter painter(this); if (this->type == slideOff) { int alpha; @@ -830,7 +815,7 @@ void EndSessionWait::paintEvent(QPaintEvent *event) { } } -void EndSessionWait::mousePressEvent(QMouseEvent *event) { +void EndSessionWait::mousePressEvent(QMouseEvent* event) { Q_UNUSED(event) if (this->type == slideOff) { @@ -838,7 +823,7 @@ void EndSessionWait::mousePressEvent(QMouseEvent *event) { } } -bool EndSessionWait::eventFilter(QObject *obj, QEvent *eve) { +bool EndSessionWait::eventFilter(QObject* obj, QEvent* eve) { if (obj == ui->slideOffFrame) { if (eve->type() == QEvent::MouseButtonPress) { QMouseEvent* event = (QMouseEvent*) eve; @@ -860,7 +845,7 @@ bool EndSessionWait::eventFilter(QObject *obj, QEvent *eve) { anim->setEasingCurve(QEasingCurve::InCubic); connect(anim, SIGNAL(finished()), anim, SLOT(deleteLater())); connect(anim, SIGNAL(finished()), this, SLOT(update())); - connect(anim, &tPropertyAnimation::finished, [=] { + connect(anim, &tPropertyAnimation::finished, [ = ] { this->type = powerOff; this->setAttribute(Qt::WA_TranslucentBackground, false); diff --git a/shell/endsessionwait.h b/shell/endsessionwait.h index 2799fca..7a03c4e 100644 --- a/shell/endsessionwait.h +++ b/shell/endsessionwait.h @@ -38,6 +38,8 @@ #undef FocusOut #undef CursorShape #undef Unsorted +#undef False +#undef True #include #include @@ -71,87 +73,90 @@ #include + namespace Ui { -class EndSessionWait; + class EndSessionWait; } -class EndSessionWait : public QDialog -{ - Q_OBJECT +class EndSessionWait : public QDialog { + Q_OBJECT -public: - enum shutdownType { - powerOff, - reboot, - logout, + public: + enum shutdownType { + powerOff, + reboot, + logout, - slideOff, //For tablet mode + slideOff, //For tablet mode - //These should not be shown. - suspend, - hibernate, - ask, - screenOff, - dummy //FOR TESTING - }; + //These should not be shown. + suspend, + hibernate, + ask, + screenOff, + dummy //FOR TESTING + }; - explicit EndSessionWait(shutdownType type, QWidget *parent = 0); - ~EndSessionWait(); + explicit EndSessionWait(shutdownType type, QWidget* parent = 0); + ~EndSessionWait(); - void showFullScreen(); - void reject(); + void showFullScreen(); + void reject(); -private slots: - void on_killAllButton_clicked(); + private slots: + void on_killAllButton_clicked(); - void on_cancelButton_clicked(); + void on_cancelButton_clicked(); - void EndSessionNow(); - void on_CancelAsk_clicked(); + void EndSessionNow(); + void on_CancelAsk_clicked(); - void on_PowerOff_clicked(); + void on_PowerOff_clicked(); - void on_Reboot_clicked(); + void on_Reboot_clicked(); - void on_LogOut_clicked(); + void on_LogOut_clicked(); - void on_Suspend_clicked(); + void on_Suspend_clicked(); - void on_terminateApp_clicked(); + void on_terminateApp_clicked(); - void on_exitTerminate_clicked(); + void on_exitTerminate_clicked(); - void reloadAppList(); + void reloadAppList(); - void on_pushButton_5_clicked(); + void on_pushButton_5_clicked(); - void on_pushButton_4_clicked(); + void on_pushButton_4_clicked(); - void on_listWidget_currentRowChanged(int currentRow); + void on_listWidget_currentRowChanged(int currentRow); - void on_DummyExit_clicked(); + void on_DummyExit_clicked(); -public slots: - void close(); + public slots: + void close(); -private: - Ui::EndSessionWait *ui; + private: + Ui::EndSessionWait* ui; - void performEndSession(); - shutdownType type; - bool alreadyShowing = false; + void performEndSession(); + shutdownType type; + bool alreadyShowing = false; - QVariantAnimation* powerOffTimer; + QVariantAnimation* powerOffTimer; - TaskbarManager* tbManager; - bool performEndSessionWhenAllAppsClosed = false; - QTimer* tbTimer; + TaskbarManager* tbManager; + bool performEndSessionWhenAllAppsClosed = false; + QTimer* tbTimer; - int pressLocation; + int pressLocation; - void paintEvent(QPaintEvent* event); - void mousePressEvent(QMouseEvent* event); - bool eventFilter(QObject *obj, QEvent *eve); + void paintEvent(QPaintEvent* event); + void mousePressEvent(QMouseEvent* event); + bool eventFilter(QObject* obj, QEvent* eve); }; +#define False 0 +#define True 1 + #endif // ENDSESSIONWAIT_H diff --git a/shell/infopanedropdown.cpp b/shell/infopanedropdown.cpp index 00403e2..140c2dd 100644 --- a/shell/infopanedropdown.cpp +++ b/shell/infopanedropdown.cpp @@ -1 +1,4168 @@ -/**************************************** * * theShell - Desktop Environment * Copyright (C) 2018 Victor Tran * * 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 . * * *************************************/ #include "infopanedropdown.h" #include "ui_infopanedropdown.h" #include "internationalisation.h" extern void playSound(QUrl, bool = false); extern QIcon getIconFromTheme(QString name, QColor textColor); extern void EndSession(EndSessionWait::shutdownType type); extern QString calculateSize(quint64 size); extern AudioManager* AudioMan; extern NativeEventFilter* NativeFilter; extern QTranslator *qtTranslator, *tsTranslator; extern float getDPIScaling(); extern QDBusServiceWatcher* dbusServiceWatcher; extern QDBusServiceWatcher* dbusServiceWatcherSystem; extern UPowerDBus* updbus; extern NotificationsDBusAdaptor* ndbus; extern DBusSignals* dbusSignals; extern LocationServices* locationServices; #define LOWER_INFOPANE InfoPaneNotOnTopLocker locker(this); InfoPaneDropdown::InfoPaneDropdown(WId MainWindowId, QWidget *parent) : QDialog(parent), ui(new Ui::InfoPaneDropdown) { if (false) { Q_UNUSED(QT_TR_NOOP("Location")); } ui->setupUi(this); this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowStaysOnTopHint); ui->settingsList->setIconSize(QSize(32 * getDPIScaling(), 32 * getDPIScaling())); ui->settingsListStack->setFixedWidth(250 * getDPIScaling()); startTime.start(); ui->copyrightNotice->setText(tr("Copyright © Victor Tran %1. Licensed under the terms of the GNU General Public License, version 3 or later.").arg("2018")); ui->dstIcon->setPixmap(QIcon::fromTheme("chronometer").pixmap(16 * getDPIScaling(), 16 * getDPIScaling())); ui->usesLocation->setPixmap(QIcon::fromTheme("gps").pixmap(16 * getDPIScaling(), 16 * getDPIScaling())); connect(this, SIGNAL(flightModeChanged(bool)), ui->NetworkManager, SLOT(flightModeChanged(bool))); connect(this, SIGNAL(flightModeChanged(bool)), ui->networkManagerSettings, SLOT(flightModeChanged(bool))); if (settings.value("flightmode/on", false).toBool()) { ui->FlightSwitch->setChecked(true); } this->MainWindowId = MainWindowId; //ndbus->setDropdownPane(this); /*connect(ndbus, SIGNAL(newNotification(int,QString,QString,QIcon)), this, SLOT(newNotificationReceived(int,QString,QString,QIcon))); connect(ndbus, SIGNAL(removeNotification(int)), this, SLOT(removeNotification(int))); connect(ndbus, SIGNAL(NotificationClosed(uint,uint)), this, SLOT(notificationClosed(uint,uint)));*/ //connect(this, SIGNAL(closeNotification(int)), ndbus, SLOT(CloseNotificationUserInitiated(int))); connect(ndbus, SIGNAL(NotificationClosed(uint,uint)), this, SLOT(notificationClosed(uint,uint))); connect(ndbus, SIGNAL(ActionInvoked(uint,QString)), this, SLOT(notificationAction(uint,QString))); connect(ui->notificationsWidget, SIGNAL(numNotificationsChanged(int)), this, SIGNAL(numNotificationsChanged(int))); connect(dbusServiceWatcher, SIGNAL(serviceRegistered(QString)), this, SLOT(DBusServiceRegistered(QString))); connect(dbusServiceWatcher, SIGNAL(serviceUnregistered(QString)), this, SLOT(DBusServiceUnregistered(QString))); connect(dbusServiceWatcherSystem, SIGNAL(serviceRegistered(QString)), this, SLOT(DBusServiceRegistered(QString))); connect(dbusServiceWatcherSystem, SIGNAL(serviceUnregistered(QString)), this, SLOT(DBusServiceUnregistered(QString))); QTimer *timer = new QTimer(this); connect(timer, SIGNAL(timeout()), this, SLOT(timerTick())); connect(timer, SIGNAL(timeout()), this, SLOT(updateSysInfo())); //connect(timer, SIGNAL(timeout()), this, SLOT(updateKdeconnect())); connect(timer, &QTimer::timeout, [=]() { //Run the timer faster when a stopwatch is running. if (stopwatchRunning) { timer->setInterval(100); } else { timer->setInterval(1000); } }); timer->setInterval(1000); timer->start(); connect(updbus, &UPowerDBus::powerStretchChanged, [=](bool isOn) { ui->PowerStretchSwitch->setChecked(isOn); emit batteryStretchChanged(isOn); doNetworkCheck(); if (isOn) { slice1.pause(); slice2.pause(); } else { slice1.resume(); slice2.resume(); } }); ui->PowerStretchSwitch->setChecked(updbus->powerStretch()); emit batteryStretchChanged(updbus->powerStretch()); ui->label_7->setVisible(false); ui->pushButton_3->setVisible(false); ui->BatteryChargeScrollBar->setVisible(false); ui->appNotificationsConfigureLock->setVisible(false); ui->dstPanel->setVisible(false); ui->quietModeExtras->setFixedHeight(0); //ui->networkKey->setVisible(false); //ui->networkConnect->setVisible(false); ui->resetButton->setProperty("type", "destructive"); ui->userSettingsDeleteUser->setProperty("type", "destructive"); ui->userSettingsDeleteUserAndData->setProperty("type", "destructive"); ui->userSettingsDeleteUserOnly->setProperty("type", "destructive"); ui->resetDeviceButton->setProperty("type", "destructive"); ui->partFrame->installEventFilter(this); QPalette powerStretchPalette = ui->PowerStretchSwitch->palette(); QPalette flightModePalette = ui->FlightSwitch->palette(); QColor background = this->palette().color(QPalette::Background); int averageCol = (background.red() + background.green() + background.blue()) / 3; if (averageCol < 127) { powerStretchPalette.setColor(QPalette::Highlight, QColor(255, 100, 0)); powerStretchPalette.setColor(QPalette::WindowText, Qt::white); flightModePalette.setColor(QPalette::Highlight, QColor(0, 0, 200)); flightModePalette.setColor(QPalette::WindowText, Qt::white); } else { powerStretchPalette.setColor(QPalette::Highlight, QColor(255, 200, 0)); powerStretchPalette.setColor(QPalette::WindowText, Qt::black); flightModePalette.setColor(QPalette::Highlight, QColor(100, 200, 255)); flightModePalette.setColor(QPalette::WindowText, Qt::black); } ui->PowerStretchSwitch->setPalette(powerStretchPalette); ui->FlightSwitch->setPalette(flightModePalette); //Set up battery chart batteryChart = new QChart(); batteryChart->setBackgroundVisible(false); batteryChart->legend()->hide(); QChartView* batteryChartView = new QChartView(batteryChart); batteryChartView->setRenderHint(QPainter::Antialiasing); ((QBoxLayout*) ui->batteryGraph->layout())->insertWidget(1, batteryChartView); updateBatteryChart(); //Check Redshift QProcess* redshiftQuery = new QProcess; redshiftQuery->start("redshift -V"); connect(redshiftQuery, QOverload::of(&QProcess::finished), [=](int exitCode, QProcess::ExitStatus exitStatus) { QString output = redshiftQuery->readAll().trimmed(); output.remove("redshift "); QStringList parts = output.split("."); for (int i = 0; i < parts.count(); i++) { int version = parts.at(i).toInt(); if (i == 0) { if (version > 1) { break; } else if (version < 1) { isNewRedshift = false; break; } } else if (i == 1) { if (version < 11) { isNewRedshift = false; } break; } } redshiftQuery->deleteLater(); }); //Set up KDE Connect if (!QFile("/usr/lib/kdeconnectd").exists()) { //If KDE Connect is not installed, hide the KDE Connect option ui->kdeconnectLabel->setVisible(false); } if (!QFile("/usr/bin/scallop").exists()) { ui->resetDeviceButton->setVisible(false); } //Set up networking QDBusInterface networkInterface("org.freedesktop.NetworkManager", "/org/freedesktop/NetworkManager", "org.freedesktop.NetworkManager", QDBusConnection::systemBus(), this); connect(ui->NetworkManager, SIGNAL(updateBarDisplay(QString,QIcon)), this, SIGNAL(networkLabelChanged(QString,QIcon))); ui->WifiSwitch->setChecked(networkInterface.property("WirelessEnabled").toBool()); { QDBusInterface interface("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", QDBusConnection::sessionBus()); QDBusConnection::sessionBus().connect("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", "BluetoothEnabledChanged", this, SLOT(bluetoothEnabledChanged())); if (interface.isValid()) { DBusServiceRegistered("org.thesuite.tsbt"); } else { DBusServiceUnregistered("org.thesuite.tsbt"); } dbusServiceWatcher->addWatchedService("org.thesuite.tsbt"); } //Load icons into icon theme box { QString currentIconTheme = themeSettings->value("icons/theme", "contemporary").toString(); QDir iconPath("/usr/share/icons"); for (QString iconDir : iconPath.entryList(QDir::NoDotAndDotDot | QDir::Dirs)) { QFile themeFile("/usr/share/icons/" + iconDir + "/index.theme"); if (themeFile.exists()) { themeFile.open(QFile::ReadOnly); QString iconThemeName = ""; while (!themeFile.atEnd()) { QString line = themeFile.readLine(); if (line.startsWith("Name")) { iconThemeName = line.mid(line.indexOf("=") + 1).remove("\n"); break; } } themeFile.close(); if (iconThemeName != "") { ui->systemIconTheme->addItem(iconThemeName); ui->systemIconTheme->setItemData(ui->systemIconTheme->count() - 1, iconDir); if (currentIconTheme == iconDir) { ui->systemIconTheme->setCurrentIndex(ui->systemIconTheme->count() - 1); } } } } } //Load widget themes into widget theme box { ui->systemWidgetTheme->blockSignals(true); QString currentWidgetTheme = themeSettings->value("style/name", "contemporary").toString(); QStringList keys = QStyleFactory::keys(); for (QString key : keys) { ui->systemWidgetTheme->addItem(key); ui->systemWidgetTheme->setItemData(ui->systemWidgetTheme->count() - 1, key); if (key.toLower() == currentWidgetTheme.toLower()) { ui->systemWidgetTheme->setCurrentIndex(ui->systemWidgetTheme->count() - 1); } } ui->systemWidgetTheme->blockSignals(false); } //Load GTK3 themes into GTK3 theme box { ui->systemGTK3Theme->blockSignals(true); QString currentWidgetTheme = gtk3Settings->value("Settings/gtk-theme-name", "Contemporary").toString(); QStringList themes; QString themeSearchDirectory = "/usr/share/themes/"; QDir themeDir(themeSearchDirectory); QStringList themeDirEntries = themeDir.entryList(QDir::Dirs | QDir::NoDotAndDotDot); for (QString entry : themeDirEntries) { if (QDir(themeSearchDirectory + entry + "/gtk-3.0/").exists()) { themes.append(entry); } } for (QString theme : themes) { ui->systemGTK3Theme->addItem(theme); ui->systemGTK3Theme->setItemData(ui->systemGTK3Theme->count() - 1, theme); if (theme.toLower() == currentWidgetTheme.toLower()) { ui->systemGTK3Theme->setCurrentIndex(ui->systemGTK3Theme->count() - 1); } } ui->systemGTK3Theme->blockSignals(false); } QString redshiftStart = settings.value("display/redshiftStart", "").toString(); if (redshiftStart == "") { redshiftStart = ui->startRedshift->time().toString(); settings.setValue("display/redshiftStart", redshiftStart); } ui->startRedshift->setTime(QTime::fromString(redshiftStart)); QString redshiftEnd = settings.value("display/redshiftEnd", "").toString(); if (redshiftEnd == "") { redshiftEnd = ui->endRedshift->time().toString(); settings.setValue("display/redshiftEnd", redshiftEnd); } ui->endRedshift->setTime(QTime::fromString(redshiftEnd)); QString redshiftVal = settings.value("display/redshiftIntensity", "").toString(); if (redshiftVal == "") { redshiftVal = ui->endRedshift->time().toString(); settings.setValue("display/redshiftIntensity", redshiftVal); } ui->redshiftIntensity->setValue(redshiftVal.toInt()); if (settings.value("ui/useFullScreenEndSession", false).toBool()) { ui->endSessionConfirmFullScreen->setChecked(true); ui->endSessionConfirmInMenu->setChecked(false); } else { ui->endSessionConfirmFullScreen->setChecked(false); ui->endSessionConfirmInMenu->setChecked(true); } if (settings.contains("notifications/lockScreen")) { if (settings.value("notifications/lockScreen").toString() == "contents") { ui->showNotificationsContents->setChecked(true); } else if (settings.value("notifications/lockScreen").toString() == "none") { ui->showNotificationsNo->setChecked(true); } else { ui->showNotificationsOnly->setChecked(true); } } else { ui->showNotificationsOnly->setChecked(true); } QString themeType = themeSettings->value("color/type", "dark").toString(); if (themeType == "light") { ui->lightColorThemeRadio->setChecked(true); } else if (themeType == "dark") { ui->darkColorThemeRadio->setChecked(true); } else if (themeType == "gray") { ui->grayColorThemeRadio->setChecked(true); } else if (themeType == "decorative") { ui->decorativeColorThemeRadio->setChecked(true); } int dpi = sessionSettings->value("screen/dpi", 96).toInt(); switch (dpi) { case 96: ui->dpi100->setChecked(true); break; case 144: ui->dpi150->setChecked(true); break; case 192: ui->dpi200->setChecked(true); break; case 288: ui->dpi300->setChecked(true); break; } //Populate the language box Internationalisation::fillLanguageBox(ui->localeList); ui->lockScreenBackground->setText(lockScreenSettings->value("background", "/usr/share/tsscreenlock/triangles.svg").toString()); //ui->lineEdit_2->setText(settings.value("startup/autostart", "").toString()); ui->redshiftPause->setChecked(!settings.value("display/redshiftPaused", true).toBool()); ui->TouchFeedbackSwitch->setChecked(settings.value("input/touchFeedbackSound", false).toBool()); ui->SuperkeyGatewaySwitch->setChecked(settings.value("input/superkeyGateway", true).toBool()); ui->TextSwitch->setChecked(settings.value("bar/showText", true).toBool()); ui->windowManager->setText(settings.value("startup/WindowManagerCommand", "kwin_x11").toString()); ui->barDesktopsSwitch->setChecked(settings.value("bar/showWindowsFromOtherDesktops", true).toBool()); ui->MediaSwitch->setChecked(settings.value("notifications/mediaInsert", true).toBool()); ui->StatusBarSwitch->setChecked(settings.value("bar/statusBar", false).toBool()); ui->TouchInputSwitch->setChecked(settings.value("input/touch", false).toBool()); ui->SuspendLockScreen->setChecked(settings.value("lockScreen/showOnSuspend", true).toBool()); ui->LargeTextSwitch->setChecked(themeSettings->value("accessibility/largeText", false).toBool()); ui->HighContrastSwitch->setChecked(themeSettings->value("accessibility/highcontrast", false).toBool()); ui->systemAnimationsAccessibilitySwitch->setChecked(themeSettings->value("accessibility/systemAnimations", true).toBool()); ui->CapsNumLockBellSwitch->setChecked(themeSettings->value("accessibility/bellOnCapsNumLock", false).toBool()); ui->TwentyFourHourSwitch->setChecked(settings.value("time/use24hour", true).toBool()); ui->AttenuateSwitch->setChecked(settings.value("notifications/attenuate", true).toBool()); ui->BarOnBottom->setChecked(!settings.value("bar/onTop", true).toBool()); ui->AutoShowBarSwitch->setChecked(settings.value("bar/autoshow", true).toBool()); ui->SoundFeedbackSoundSwitch->setChecked(settings.value("sound/feedbackSound", true).toBool()); ui->VolumeOverdriveSwitch->setChecked(settings.value("sound/volumeOverdrive", true).toBool()); ui->batteryScreenOff->setValue(settings.value("power/batteryScreenOff", 15).toInt()); ui->batterySuspend->setValue(settings.value("power/batterySuspend", 30).toInt()); ui->powerScreenOff->setValue(settings.value("power/powerScreenOff", 30).toInt()); ui->powerSuspend->setValue(settings.value("power/powerSuspend", 90).toInt()); ui->sunlightRedshift->setChecked(settings.value("display/redshiftSunlightCycle", false).toBool()); ui->EmphasiseAppSwitch->setChecked(settings.value("notifications/emphasiseApp", true).toBool()); ui->CompactBarSwitch->setChecked(settings.value("bar/compact", false).toBool()); ui->LocationMasterSwitch->setChecked(locationSettings->value("master/master", true).toBool()); updateAccentColourBox(); updateRedshiftTime(); on_StatusBarSwitch_toggled(ui->StatusBarSwitch->isChecked()); if (QFile(QDir::homePath() + "/.theshell/mousepassword").exists()) { ui->removeMousePassword->setVisible(true); } else { ui->removeMousePassword->setVisible(false); } QString defaultFont; if (QFontDatabase().families().contains("Contemporary")) { defaultFont = "Contemporary"; } else { defaultFont = "Noto Sans"; } ui->systemFont->setCurrentFont(QFont(themeSettings->value("fonts/defaultFamily", defaultFont).toString(), themeSettings->value("font/defaultSize", 10).toInt())); ui->systemFontSize->setValue(themeSettings->value("font/defaultSize", 10).toInt()); QString gtk3FontString = gtk3Settings->value("Settings/gtk-font-name", "Contemporary 10").toString(); QString gtk3FontFamily = gtk3FontString.left(gtk3FontString.lastIndexOf(" ")); QString gtk3FontSize = gtk3FontString.mid(gtk3FontString.lastIndexOf(" ") + 1); ui->systemGTK3Font->setCurrentFont(QFont(gtk3FontFamily, gtk3FontSize.toInt())); ui->systemGTK3FontSize->setValue(gtk3FontSize.toInt()); eventTimer = new QTimer(this); eventTimer->setInterval(1000); connect(eventTimer, SIGNAL(timeout()), this, SLOT(processTimer())); eventTimer->start(); networkCheckTimer = new QTimer(this); networkCheckTimer->setInterval(60000); connect(networkCheckTimer, SIGNAL(timeout()), this, SLOT(doNetworkCheck())); networkCheckTimer->start(); doNetworkCheck(); QObjectList allObjects; allObjects.append(this); ui->notificationSoundBox->blockSignals(true); ui->notificationSoundBox->addItem("Triple Ping"); ui->notificationSoundBox->addItem("Upside Down"); ui->notificationSoundBox->addItem("Echo"); QString notificationSound = settings.value("notifications/sound", "tripleping").toString(); if (notificationSound == "tripleping") { ui->notificationSoundBox->setCurrentIndex(0); } else if (notificationSound == "upsidedown") { ui->notificationSoundBox->setCurrentIndex(1); } else if (notificationSound == "echo") { ui->notificationSoundBox->setCurrentIndex(2); } ui->notificationSoundBox->blockSignals(false); //Don't forget to change settings pane setup things ui->settingsList->item(ui->settingsList->count() - 1)->setSelected(true); ui->settingsTabs->setCurrentIndex(ui->settingsTabs->count() - 1); //Get distribution information { QString osreleaseFile = ""; if (QFile("/etc/os-release").exists()) { osreleaseFile = "/etc/os-release"; } else if (QFile("/usr/lib/os-release").exists()) { osreleaseFile = "/usr/lib/os-release"; } if (osreleaseFile != "") { QFile information(osreleaseFile); information.open(QFile::ReadOnly); while (!information.atEnd()) { QString line = information.readLine(); if (line.startsWith("pretty_name=", Qt::CaseInsensitive)) { ui->distroName->setText(line.remove("pretty_name=", Qt::CaseInsensitive).remove("\"").remove("\n")); } else if (line.startsWith("home_url=", Qt::CaseInsensitive)) { ui->distroWebpage->setText(line.remove("home_url=", Qt::CaseInsensitive).remove("\"").remove("\n")); } else if (line.startsWith("support_url=", Qt::CaseInsensitive)) { ui->distroSupport->setText(line.remove("support_url=", Qt::CaseInsensitive).remove("\"").remove("\n")); } } information.close(); } struct sysinfo* info = new struct sysinfo; if (sysinfo(info) == 0) { ui->availableMemory->setText(calculateSize(info->totalram)); ui->availableSwap->setText(calculateSize(info->totalswap)); } else { } delete info; ui->kernelVersion->setText(QSysInfo::kernelVersion()); ui->qtVersion->setText(qVersion()); QFile cpuInfoFile("/proc/cpuinfo"); cpuInfoFile.open(QFile::ReadOnly); QByteArray cpuInfoBuf = cpuInfoFile.readAll(); QBuffer cpuInfo(&cpuInfoBuf); cpuInfo.open(QBuffer::ReadOnly); QStringList knownCpus; while (!cpuInfo.atEnd()) { QString line = cpuInfo.readLine(); if (line.startsWith("model name")) { QString cpu = line.mid(line.indexOf(":") + 1).trimmed(); knownCpus.append(cpu); } } QStringList shownCpus; while (knownCpus.length() > 0) { QString cpu = knownCpus.value(0); int numberOfThisCpu = knownCpus.count(cpu); knownCpus.removeAll(cpu); if (numberOfThisCpu == 1) { shownCpus.append(cpu); } else { shownCpus.append(QString::number(numberOfThisCpu) + " × " + cpu); } } if (shownCpus.length() == 0) { ui->processorType->setText(tr("Unknown")); } else { ui->processorType->setText(shownCpus.join(" · ")); } } #ifdef BLUEPRINT ui->tsVersion->setText(tr("theShell %1 - Blueprint").arg(TS_VERSION)); ui->compileDate->setText(tr("You compiled theShell on %1").arg(__DATE__)); #elif defined(CONSTRUCTION) ui->tsVersion->setText(tr("theShell %1 - Construction").arg(TS_VERSION)); ui->compileDate->setText(tr("You compiled theShell on %1").arg(__DATE__)); #else ui->tsVersion->setText(tr("theShell %1").arg(TS_VERSION)); ui->compileDate->setVisible(false); #endif //Update keyboard layouts struct KeyboardLayoutReturn { QMap availableKeyboardLayout; QStringList currentKeyboardLayout; }; QFuture keyboardLayouts = QtConcurrent::run([=]() -> KeyboardLayoutReturn { KeyboardLayoutReturn retval; QDir xkbLayouts("/usr/share/X11/xkb/symbols"); for (QFileInfo layoutInfo : xkbLayouts.entryInfoList()) { if (layoutInfo.isDir()) continue; QString layout = layoutInfo.baseName(); QFile file(layoutInfo.filePath()); file.open(QFile::ReadOnly); QString currentSubLayout = ""; while (!file.atEnd()) { QString line = file.readLine().trimmed(); if (line.startsWith("xkb_symbols") && line.endsWith("{")) { QRegExp lineRx("\".+\""); lineRx.indexIn(line); if (lineRx.capturedTexts().count() != 0) { currentSubLayout = lineRx.capturedTexts().first().remove("\""); } else { currentSubLayout = ""; } } else if (line.startsWith("name")) { QRegExp lineRx("\".+\""); lineRx.indexIn(line); if (lineRx.capturedTexts().count() != 0 && currentSubLayout != "") { retval.availableKeyboardLayout.insert(layout + "(" + currentSubLayout + ")", lineRx.capturedTexts().first().remove("\"")); } else { currentSubLayout = ""; } } } file.close(); } retval.currentKeyboardLayout = settings.value("input/layout", "us(basic)").toString().split(","); return retval; }); QFutureWatcher* keyboardLayoutWatcher = new QFutureWatcher(); connect(keyboardLayoutWatcher, &QFutureWatcher::finished, [=] { keyboardLayoutWatcher->deleteLater(); KeyboardLayoutReturn layouts = keyboardLayouts.result(); for (QString key : layouts.availableKeyboardLayout.keys()) { QString value = layouts.availableKeyboardLayout.value(key); QListWidgetItem* item = new QListWidgetItem(); item->setText(value); item->setData(Qt::UserRole, key); ui->availableKeyboardLayouts->addItem(item); } for (QString layout : layouts.currentKeyboardLayout) { QListWidgetItem* item = new QListWidgetItem(); item->setText(layouts.availableKeyboardLayout.value(layout, layout)); item->setData(Qt::UserRole, layout); ui->selectedLayouts->addItem(item); } ui->availableKeyboardLayouts->sortItems(); connect(ui->selectedLayouts->model(), SIGNAL(layoutChanged(QList,QAbstractItemModel::LayoutChangeHint)), this, SLOT(KeyboardLayoutsMoved())); setKeyboardLayout(settings.value("input/currentLayout", "us(basic)").toString()); }); keyboardLayoutWatcher->setFuture(keyboardLayouts); //Set up timer ringtones ringtone = new QMediaPlayer(this, QMediaPlayer::LowLatency); connect(AudioMan, &AudioManager::QuietModeChanged, [=](AudioManager::quietMode mode) { ui->quietModeSound->setChecked(false); ui->quietModeCriticalOnly->setChecked(false); ui->quietModeNotification->setChecked(false); ui->quietModeMute->setChecked(false); ui->quietModeForeverButton->setEnabled(true); ui->quietModeTurnOffAt->setEnabled(true); ui->quietModeTurnOffIn->setEnabled(true); if (mode == AudioManager::none) { ui->quietModeSound->setChecked(true); ui->quietModeForeverButton->setEnabled(false); ui->quietModeTurnOffAt->setEnabled(false); ui->quietModeTurnOffIn->setEnabled(false); ui->quietModeForeverButton->setChecked(true); } else if (mode == AudioManager::notifications) { ui->quietModeNotification->setChecked(true); } else if (mode == AudioManager::critical) { ui->quietModeCriticalOnly->setChecked(true); } else { ui->quietModeMute->setChecked(true); } ui->quietModeDescription->setText(AudioMan->getCurrentQuietModeDescription()); }); ui->quietModeForeverButton->setChecked(true); ui->quietModeForeverButton->setEnabled(false); ui->quietModeTurnOffAt->setEnabled(false); ui->quietModeTurnOffIn->setEnabled(false); ui->quietModeDescription->setText(AudioMan->getCurrentQuietModeDescription()); ui->RemindersList->setModel(new RemindersListModel); ui->RemindersList->setItemDelegate(new RemindersDelegate); slice1.setStartValue((float) (this->width() - 250 * getDPIScaling())); slice1.setEndValue((float) (this->width() - 300 * getDPIScaling())); slice1.setEasingCurve(QEasingCurve::OutCubic); slice1.setDuration(15000); connect(&slice1, &tVariantAnimation::finished, [=] { slice1.setStartValue(slice1.endValue()); if (slice1.endValue() == this->width() - 300 * getDPIScaling()) { slice1.setEndValue(this->width() - 250 * getDPIScaling()); } else { slice1.setEndValue(this->width() - 300 * getDPIScaling()); } slice1.setEasingCurve(QEasingCurve::InOutCubic); slice1.start(); }); connect(&slice1, SIGNAL(valueChanged(QVariant)), ui->partFrame, SLOT(repaint())); slice1.start(); QTimer::singleShot(2500, [=] { slice2.setStartValue((float) (this->width() - 300 * getDPIScaling())); slice2.setEndValue((float) (this->width() - 350 * getDPIScaling())); slice2.setEasingCurve(QEasingCurve::OutCubic); slice2.setDuration(15000); connect(&slice2, &tVariantAnimation::finished, [=] { slice2.setStartValue(slice2.endValue()); if (slice2.endValue() == this->width() - 350 * getDPIScaling()) { slice2.setEndValue(this->width() - 300 * getDPIScaling()); } else { slice2.setEndValue(this->width() - 350 * getDPIScaling()); } slice2.setEasingCurve(QEasingCurve::InOutCubic); slice2.start(); }); slice2.start(); }); updateStruts(); updateAutostart(); updateDSTNotification(); } InfoPaneDropdown::~InfoPaneDropdown() { delete ui; } InfoPaneNotOnTopLocker::InfoPaneNotOnTopLocker(InfoPaneDropdown *infoPane) { this->infoPane = infoPane; infoPane->setWindowFlags(Qt::FramelessWindowHint); } InfoPaneNotOnTopLocker::~InfoPaneNotOnTopLocker() { infoPane->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowStaysOnTopHint); infoPane->showNoAnimation(); } void InfoPaneDropdown::DBusServiceRegistered(QString serviceName) { if (serviceName == "org.thesuite.tsbt") { QDBusInterface interface("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", QDBusConnection::sessionBus()); ui->BluetoothSwitch->setEnabled(true); ui->BluetoothSwitch->setChecked(interface.property("BluetoothEnabled").toBool()); } } void InfoPaneDropdown::DBusServiceUnregistered(QString serviceName) { if (serviceName == "org.thesuite.tsbt") { ui->BluetoothSwitch->setEnabled(false); } } void InfoPaneDropdown::bluetoothEnabledChanged() { ui->BluetoothSwitch->setChecked(QDBusInterface("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", QDBusConnection::sessionBus()).property("BluetoothEnabled").toBool()); } void InfoPaneDropdown::newNetworkDevice(QDBusObjectPath device) { QDBusInterface *i = new QDBusInterface("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device", QDBusConnection::systemBus(), this); if (i->property("DeviceType").toInt() == 2) { //WiFi Device QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device.Wireless", "AccessPointAdded", this, SLOT(getNetworks())); QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device.Wireless", "AccessPointRemoved", this, SLOT(getNetworks())); QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device", "StateChanged", this, SLOT(getNetworks())); } else if (i->property("DeviceType").toInt() == 1) { //Wired Device QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device.Wired", "PropertiesChanged", this, SLOT(getNetworks())); } QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.DBus.Properties", "PropertiesChanged", this, SLOT(getNetworks())); QDBusInterface *stats = new QDBusInterface("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device.Statistics", QDBusConnection::systemBus(), this); stats->setProperty("RefreshRateMs", (uint) 1000); getNetworks(); stats->deleteLater(); i->deleteLater(); } void InfoPaneDropdown::on_WifiSwitch_toggled(bool checked) { QDBusInterface *i = new QDBusInterface("org.freedesktop.NetworkManager", "/org/freedesktop/NetworkManager", "org.freedesktop.NetworkManager", QDBusConnection::systemBus(), this); if (i->property("WirelessEnabled").toBool() != checked) { i->setProperty("WirelessEnabled", checked); } if (i->property("WirelessEnabled").toBool()) { ui->WifiSwitch->setChecked(true); } else { ui->WifiSwitch->setChecked(false); } i->deleteLater(); } void InfoPaneDropdown::processTimer() { QTime time = QTime::currentTime(); { int currentMsecs = time.msecsSinceStartOfDay(); int startMsecs = ui->startRedshift->time().msecsSinceStartOfDay(); int endMsecs = ui->endRedshift->time().msecsSinceStartOfDay(); int endIntensity = ui->redshiftIntensity->value(); const int oneHour = 3600000; QString redshiftCommand; if (ui->redshiftPause->isChecked()) { //Calculate redshift value //Transition to redshift is 1 hour from the start. int intensity; if (startMsecs > endMsecs) { //Start time is later then end time if (currentMsecs < endMsecs || currentMsecs > startMsecs) { intensity = endIntensity; } else if (currentMsecs < startMsecs && currentMsecs > startMsecs - oneHour) { int timeFrom = currentMsecs - (startMsecs - oneHour); float percentage = ((float) timeFrom / (float) oneHour); int progress = (6500 - endIntensity) * percentage; intensity = 6500 - progress; } else if (currentMsecs > endMsecs && currentMsecs < endMsecs + oneHour) { int timeFrom = endMsecs - (currentMsecs - oneHour); float percentage = ((float) timeFrom / (float) oneHour); int progress = (6500 - endIntensity) * percentage; intensity = 6500 - progress; } else { intensity = 6500; } } else { //Start time is earlier then end time if (currentMsecs < endMsecs && currentMsecs > startMsecs) { intensity = endIntensity; } else if (currentMsecs < startMsecs && currentMsecs > startMsecs - oneHour) { int timeFrom = currentMsecs - (startMsecs - oneHour); float percentage = ((float) timeFrom / (float) oneHour); int progress = (6500 - endIntensity) * percentage; intensity = 6500 - progress; } else if (currentMsecs > endMsecs && currentMsecs < endMsecs + oneHour) { int timeFrom = endMsecs - (currentMsecs - oneHour); float percentage = ((float) timeFrom / (float) oneHour); int progress = (6500 - endIntensity) * percentage; intensity = 6500 - progress; } else { intensity = 6500; } } //Check Redshift override if (overrideRedshift != 0) { if (intensity == 6500 && overrideRedshift == 1) { overrideRedshift = 0; //Reset Redshift override } else if (intensity != 6500 && overrideRedshift == 2) { overrideRedshift = 0; //Reset Redshift override } else { if (overrideRedshift == 1) { intensity = 6500; } else { intensity = endIntensity; } } } redshiftCommand = "redshift -O " + QString::number(intensity); isRedshiftOn = true; if (intensity == 6500 && effectiveRedshiftOn) { effectiveRedshiftOn = false; ui->redshiftSwitch->setChecked(false); emit redshiftEnabledChanged(false); } else if (intensity != 6500 && !effectiveRedshiftOn) { effectiveRedshiftOn = true; ui->redshiftSwitch->setChecked(true); emit redshiftEnabledChanged(true); } } else { //Check Redshift Override if (overrideRedshift == 2) { redshiftCommand = "redshift -O " + QString::number(endIntensity); } else { redshiftCommand = "redshift -O 6500"; } if (isRedshiftOn) { isRedshiftOn = false; effectiveRedshiftOn = false; ui->redshiftSwitch->setChecked(false); emit redshiftEnabledChanged(false); } } if (isNewRedshift) { redshiftCommand += " -P"; } QProcess* redshiftAdjust = new QProcess(); redshiftAdjust->start(redshiftCommand); connect(redshiftAdjust, SIGNAL(finished(int)), redshiftAdjust, SLOT(deleteLater())); } /*{ cups_dest_t *destinations; int destinationCount = cupsGetDests(&destinations); for (int i = 0; i < destinationCount; i++) { cups_dest_t currentDestination = destinations[i]; if (!printersFrames.keys().contains(currentDestination.name)) { QFrame* frame = new QFrame(); QHBoxLayout* layout = new QHBoxLayout(); layout->setMargin(0); frame->setLayout(layout); QFrame* statFrame = new QFrame(); QHBoxLayout* statLayout = new QHBoxLayout(); statLayout->setMargin(0); statFrame->setLayout(statLayout); layout->addWidget(statFrame); QLabel* iconLabel = new QLabel(); QPixmap icon = QIcon::fromTheme("printer").pixmap(22 * getDPIScaling(), 22 * getDPIScaling()); if (currentDestination.is_default) { QPainter *p = new QPainter(); p->begin(&icon); p->drawPixmap(10 * getDPIScaling(), 10 * getDPIScaling(), 12 * getDPIScaling(), 12 * getDPIScaling(), QIcon::fromTheme("emblem-checked").pixmap(12 * getDPIScaling(), 12 * getDPIScaling())); p->end(); } iconLabel->setPixmap(icon); statLayout->addWidget(iconLabel); QLabel* nameLabel = new QLabel(); nameLabel->setText(currentDestination.name); QFont font = nameLabel->font(); font.setBold(true); nameLabel->setFont(font); statLayout->addWidget(nameLabel); QLabel* statLabel = new QLabel(); statLabel->setText(tr("Idle")); statLabel->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); statLayout->addWidget(statLabel); /*QPushButton* button = new QPushButton(); button->setIcon(QIcon::fromTheme("window-close")); connect(button, &QPushButton::clicked, [=]() { emit closeNotification(id); }); layout->addWidget(button); ui->printersList->layout()->addWidget(frame); printersFrames.insert(currentDestination.name, frame); printersStatFrames.insert(currentDestination.name, frame); printersStats.insert(currentDestination.name, statLabel); } QString state = ""; QString stateReasons = ""; for (int i = 0; i < currentDestination.num_options; i++) { cups_option_t currentOption = currentDestination.options[i]; if (strncmp(currentOption.name, "printer-state", strlen(currentOption.name)) == 0) { if (strncmp(currentOption.value, "3", 1) == 0) { state = tr("Idle"); printersStatFrames.value(currentDestination.name)->setEnabled(true); } else if (strncmp(currentOption.value, "4", 1) == 0) { state = tr("Printing"); printersStatFrames.value(currentDestination.name)->setEnabled(true); } else if (strncmp(currentOption.value, "5", 1) == 0) { state = tr("Stopped"); printersStatFrames.value(currentDestination.name)->setEnabled(false); } } else if (strncmp(currentOption.name, "printer-state-reasons", strlen(currentOption.name)) == 0) { stateReasons = QString::fromUtf8(currentOption.value, strlen(currentOption.value)); } } printersStats.value(currentDestination.name)->setText(state + " / " + stateReasons); } cupsFreeDests(destinationCount, destinations); }*/ } void InfoPaneDropdown::timerTick() { ui->date->setText(QLocale().toString(QDateTime::currentDateTime(), "ddd dd MMM yyyy")); ui->time->setText(QDateTime::currentDateTime().toString("hh:mm:ss")); //Also update the stopwatch QTime stopwatchTime = QTime::fromMSecsSinceStartOfDay(0); stopwatchTime = stopwatchTime.addMSecs(stopwatchTimeAdd); if (stopwatchRunning) { stopwatchTime = stopwatchTime.addMSecs(this->stopwatchTime.elapsed()); } ui->stopwatchLabel->setText(stopwatchTime.toString("hh:mm:ss.zzz")); updateTimers(); //Also check for reminders { QList> ReminderData; QSettings reminders("theSuite/theShell.reminders"); reminders.beginGroup("reminders"); int count = reminders.beginReadArray("reminders"); for (int i = 0; i < count; i++) { reminders.setArrayIndex(i); QPair data; data.first = reminders.value("title").toString(); data.second = reminders.value("date").toDateTime(); ReminderData.append(data); } reminders.endArray(); bool dataChanged = false; for (int i = 0; i < ReminderData.count(); i++) { QPair data = ReminderData.at(i); if (data.second.msecsTo(QDateTime::currentDateTime()) > 0) { QVariantMap hints; hints.insert("category", "reminder.activate"); hints.insert("sound-file", "qrc:/sounds/notifications/reminder.wav"); ndbus->Notify("theShell", 0, "theshell", "Reminder", data.first, QStringList(), hints, 30000); ReminderData.removeAt(i); i--; dataChanged = true; } } if (dataChanged) { reminders.beginWriteArray("reminders"); int i = 0; for (QPair data : ReminderData) { reminders.setArrayIndex(i); reminders.setValue("title", data.first); reminders.setValue("date", data.second); i++; } reminders.endArray(); reminders.endGroup(); ((RemindersListModel*) ui->RemindersList->model())->updateData(); } } } void InfoPaneDropdown::show(dropdownType showWith) { changeDropDown(showWith, false); if (!this->isVisible()) { QRect screenGeometry = QApplication::desktop()->screenGeometry(); if (settings.value("bar/onTop", true).toBool()) { this->setGeometry(screenGeometry.x(), screenGeometry.y() - screenGeometry.height(), screenGeometry.width(), screenGeometry.height() + 1); } else { this->setGeometry(screenGeometry.x(), screenGeometry.bottom(), screenGeometry.width(), screenGeometry.height() + 1); } Atom DesktopWindowTypeAtom; DesktopWindowTypeAtom = XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE_NORMAL", False); XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE", False), XA_ATOM, 32, PropModeReplace, (unsigned char*) &DesktopWindowTypeAtom, 1); //Change Window Type unsigned long desktop = 0xFFFFFFFF; XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_DESKTOP", False), XA_CARDINAL, 32, PropModeReplace, (unsigned char*) &desktop, 1); //Set visible on all desktops QDialog::show(); this->setFixedWidth(screenGeometry.width()); this->setFixedHeight(screenGeometry.height() + 1); if (settings.value("bar/onTop", true).toBool()) { previousDragY = -1; } else { previousDragY = screenGeometry.bottom(); } completeDragDown(); } //Get Current Brightness QProcess* backlight = new QProcess(this); backlight->start("xbacklight -get"); backlight->waitForFinished(); float output = ceil(QString(backlight->readAll()).toFloat()); delete backlight; ui->brightnessSlider->setValue((int) output); //Update the reminders list ((RemindersListModel*) ui->RemindersList->model())->updateData(); } void InfoPaneDropdown::showNoAnimation() { QDialog::show(); previousDragY = -1; completeDragDown(); } void InfoPaneDropdown::close() { QRect screenGeometry = QApplication::desktop()->screenGeometry(); tPropertyAnimation* a = new tPropertyAnimation(this, "geometry"); a->setStartValue(this->geometry()); if (settings.value("bar/onTop", true).toBool()) { a->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - screenGeometry.height() + 1, this->width(), this->height())); } else { a->setEndValue(QRect(screenGeometry.x(), screenGeometry.bottom() + 1, this->width(), this->height())); } a->setEasingCurve(QEasingCurve::OutCubic); a->setDuration(500); connect(a, &tPropertyAnimation::finished, [=]() { QDialog::hide(); }); connect(a, SIGNAL(finished()), a, SLOT(deleteLater())); a->start(); if (ui->quietModeExtras->height() != 0) { ui->quietModeExpandButton->click(); } } void InfoPaneDropdown::changeDropDown(dropdownType changeTo, bool doAnimation) { this->currentDropDown = changeTo; //Switch to the requested frame switch (changeTo) { case Clock: ui->pageStack->setCurrentWidget(ui->clockFrame, doAnimation); if (ui->lightColorThemeRadio->isChecked()) { setHeaderColour(QColor(0, 150, 0)); } else { setHeaderColour(QColor(0, 50, 0)); } break; case Battery: ui->pageStack->setCurrentWidget(ui->statusFrame, doAnimation); updateBatteryChart(); if (ui->lightColorThemeRadio->isChecked()) { setHeaderColour(QColor(200, 150, 0)); } else { setHeaderColour(QColor(100, 50, 0)); } break; case Notifications: ui->pageStack->setCurrentWidget(ui->notificationsFrame, doAnimation); if (ui->lightColorThemeRadio->isChecked()) { setHeaderColour(QColor(200, 50, 100)); } else { setHeaderColour(QColor(100, 25, 50)); } break; case Network: ui->pageStack->setCurrentWidget(ui->networkFrame, doAnimation); if (ui->lightColorThemeRadio->isChecked()) { setHeaderColour(QColor(100, 100, 255)); } else { setHeaderColour(QColor(50, 50, 100)); } break; case KDEConnect: ui->pageStack->setCurrentWidget(ui->kdeConnectFrame, doAnimation); if (ui->lightColorThemeRadio->isChecked()) { setHeaderColour(QColor(200, 100, 255)); } else { setHeaderColour(QColor(50, 0, 100)); } break; /*case Print: ui->pageStack->setCurrentWidget(ui->printFrame, doAnimation); break;*/ case Settings: ui->pageStack->setCurrentWidget(ui->settingsFrame, doAnimation); if (ui->lightColorThemeRadio->isChecked()) { setHeaderColour(QColor(0, 150, 255)); } else { setHeaderColour(QColor(0, 50, 100)); } break; } if (changeTo == Clock) { ui->pushButton_5->setEnabled(false); ui->pushButton_6->setEnabled(true); } else if ((ui->kdeconnectLabel->isVisible() && changeTo == KDEConnect) || (changeTo == Notifications && !ui->kdeconnectLabel->isVisible())) { //Print) { ui->pushButton_5->setEnabled(true); ui->pushButton_6->setEnabled(false); } else if (changeTo == Settings) { ui->pushButton_5->setEnabled(false); ui->pushButton_6->setEnabled(false); } else { ui->pushButton_5->setEnabled(true); ui->pushButton_6->setEnabled(true); } } void InfoPaneDropdown::on_pushButton_clicked() { this->close(); } void InfoPaneDropdown::getNetworks() { ui->NetworkManager->updateGlobals(); } void InfoPaneDropdown::on_pushButton_5_clicked() { changeDropDown(dropdownType(currentDropDown - 1)); } void InfoPaneDropdown::on_pushButton_6_clicked() { changeDropDown(dropdownType(currentDropDown + 1)); } void InfoPaneDropdown::on_clockLabel_clicked() { changeDropDown(Clock); } void InfoPaneDropdown::on_batteryLabel_clicked() { changeDropDown(Battery); } void InfoPaneDropdown::on_networkLabel_clicked() { changeDropDown(Network); } void InfoPaneDropdown::on_notificationsLabel_clicked() { changeDropDown(Notifications); } void InfoPaneDropdown::startTimer(QTime time) { if (timer != NULL) { //Check for already running timer timer->stop(); delete timer; timer = NULL; ui->timeEdit->setVisible(true); ui->label_7->setVisible(false); ui->label_7->setEnabled(true); ui->pushButton_2->setText(tr("Start")); ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-start")); ui->pushButton_3->setVisible(false); emit timerVisibleChanged(false); emit timerEnabledChanged(true); } ui->pushButton_2->setText(tr("Pause")); ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-pause")); timeUntilTimeout = time; lastTimer = time; ui->label_7->setText(ui->timeEdit->text()); ui->timeEdit->setVisible(false); ui->label_7->setVisible(true); timer = new QTimer(); timer->setInterval(1000); connect(timer, &QTimer::timeout, [=]() { timeUntilTimeout = timeUntilTimeout.addSecs(-1); if (timeUntilTimeout == QTime(0, 0, 0)) { if (timerNotificationId != 0) { ndbus->CloseNotification(timerNotificationId); } timer->stop(); delete timer; timer = NULL; if (AudioMan->QuietMode() != AudioManager::notifications && AudioMan->QuietMode() != AudioManager::mute) { //Check if we should show the notification so the user isn't stuck listening to the tone QStringList actions; actions << "restart" << "Restart Timer"; actions << "+0.5" << "+30 sec"; actions << "+1" << "+1 min"; actions << "+2" << "+2 min"; actions << "+5" << "+5 min"; actions << "+10" << "+10 min"; QVariantMap hints; hints.insert("x-thesuite-timercomplete", true); hints.insert("suppress-sound", true); timerNotificationId = ndbus->Notify("theShell", 0, "", tr("Timer Elapsed"), tr("Your timer has completed."), actions, hints, 0); ui->timeEdit->setVisible(true); ui->label_7->setVisible(false); ui->pushButton_2->setText("Start"); ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-start")); QMediaPlaylist* playlist = new QMediaPlaylist(); #ifdef BLUEPRINT QString ringtonesPath = "/usr/share/sounds/theshellb/tones/"; #elif defined(CONSTRUCTION) QString ringtonesPath = "/usr/share/sounds/theshellc/tones/"; #else QString ringtonesPath = "/usr/share/sounds/theshell/tones/"; #endif if (ui->timerToneSelect->currentText() == tr("Happy Bee")) { playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "happybee.ogg"))); } else if (ui->timerToneSelect->currentText() == tr("Playing in the Dark")) { playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "playinginthedark.ogg"))); } else if (ui->timerToneSelect->currentText() == tr("Ice Cream Truck")) { playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "icecream.ogg"))); } else if (ui->timerToneSelect->currentText() == tr("Party Complex")) { playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "party.ogg"))); } else if (ui->timerToneSelect->currentText() == tr("Salty Ditty")) { playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "saltyditty.ogg"))); } playlist->setPlaybackMode(QMediaPlaylist::Loop); ringtone->setPlaylist(playlist); ringtone->play(); AudioMan->attenuateStreams(); } updateTimers(); } else { ui->label_7->setText(timeUntilTimeout.toString("HH:mm:ss")); updateTimers(); } }); timer->start(); updateTimers(); } void InfoPaneDropdown::updateTimers() { QStringList parts; if (timer != NULL) { parts.append(timeUntilTimeout.toString("HH:mm:ss")); } if (stopwatchRunning) { QTime stopwatchTime = QTime::fromMSecsSinceStartOfDay(0); stopwatchTime = stopwatchTime.addMSecs(stopwatchTimeAdd); stopwatchTime = stopwatchTime.addMSecs(this->stopwatchTime.elapsed()); parts.append(stopwatchTime.toString("hh:mm:ss")); } if (parts.count() != 0) { emit timerVisibleChanged(true); emit timerChanged(parts.join(" · ")); } else { emit timerVisibleChanged(false); } } void InfoPaneDropdown::notificationClosed(uint id, uint reason) { Q_UNUSED(reason) if (id == timerNotificationId) { ringtone->stop(); AudioMan->restoreStreams(); timerNotificationId = 0; } } void InfoPaneDropdown::on_pushButton_2_clicked() { if (timer == NULL) { startTimer(ui->timeEdit->time()); } else { if (timer->isActive()) { timer->stop(); ui->pushButton_3->setVisible(true); ui->label_7->setEnabled(false); ui->pushButton_2->setText(tr("Resume")); ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-start")); } else { timer->start(); ui->pushButton_3->setVisible(false); ui->label_7->setEnabled(true); ui->pushButton_2->setText(tr("Pause")); ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-pause")); } } } void InfoPaneDropdown::on_pushButton_3_clicked() { delete timer; timer = NULL; ui->timeEdit->setVisible(true); ui->label_7->setVisible(false); ui->label_7->setEnabled(true); ui->pushButton_2->setText(tr("Start")); ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-start")); ui->pushButton_3->setVisible(false); emit timerVisibleChanged(false); emit timerEnabledChanged(true); } void InfoPaneDropdown::on_pushButton_7_clicked() { changeDropDown(Settings); } void InfoPaneDropdown::setGeometry(int x, int y, int w, int h) { //Use wmctrl command because KWin has a problem with moving windows offscreen. QDialog::setGeometry(x, y, w, h); QProcess::execute("wmctrl -r " + this->windowTitle() + " -e 0," + QString::number(x) + "," + QString::number(y) + "," + QString::number(w) + "," + QString::number(h)); } void InfoPaneDropdown::setGeometry(QRect geometry) { this->setGeometry(geometry.x(), geometry.y(), geometry.width(), geometry.height()); } void InfoPaneDropdown::on_lineEdit_2_editingFinished() { //settings.setValue("startup/autostart", ui->lineEdit_2->text()); } void InfoPaneDropdown::on_resolutionButton_clicked() { QProcess::startDetached("kcmshell5 kcm_kscreen"); this->close(); } void InfoPaneDropdown::on_startRedshift_timeChanged(const QTime &time) { settings.setValue("display/redshiftStart", time.toString()); processTimer(); } void InfoPaneDropdown::on_endRedshift_timeChanged(const QTime &time) { settings.setValue("display/redshiftEnd", time.toString()); processTimer(); } void InfoPaneDropdown::on_redshiftIntensity_sliderMoved(int position) { if (isNewRedshift) { QProcess::startDetached("redshift -P -O " + QString::number(position)); } else { QProcess::startDetached("redshift -O " + QString::number(position)); } } void InfoPaneDropdown::on_redshiftIntensity_sliderReleased() { if (!isRedshiftOn) { if (isNewRedshift) { QProcess::startDetached("redshift -P -O 6500"); } else { QProcess::startDetached("redshift -O 6500"); } } } void InfoPaneDropdown::on_redshiftIntensity_valueChanged(int value) { settings.setValue("display/redshiftIntensity", value); } void InfoPaneDropdown::newNotificationReceived(int id, QString summary, QString body, QIcon icon) { if (notificationFrames.keys().contains(id)) { //Notification already exists, update it. QFrame* frame = notificationFrames.value(id); frame->property("summaryLabel").value()->setText(summary); frame->property("bodyLabel").value()->setText(body); } else { QFrame* frame = new QFrame(); QHBoxLayout* layout = new QHBoxLayout(); layout->setMargin(0); frame->setLayout(layout); QLabel* iconLabel = new QLabel(); iconLabel->setPixmap(icon.pixmap(22 * getDPIScaling(), 22 * getDPIScaling())); layout->addWidget(iconLabel); QLabel* sumLabel = new QLabel(); sumLabel->setText(summary); QFont font = sumLabel->font(); font.setBold(true); sumLabel->setFont(font); layout->addWidget(sumLabel); QLabel* bodyLabel = new QLabel(); bodyLabel->setText(body); bodyLabel->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); layout->addWidget(bodyLabel); QLabel* dateLabel = new QLabel(); dateLabel->setText(QDateTime::currentDateTime().toString("HH:mm:ss")); layout->addWidget(dateLabel); QPushButton* button = new QPushButton(); button->setIcon(QIcon::fromTheme("window-close")); connect(button, &QPushButton::clicked, [=]() { emit closeNotification(id); }); layout->addWidget(button); //ui->notificationsList->layout()->addWidget(frame); //ui->noNotifications->setVisible(false); //ui->clearAllNotifications->setVisible(true); frame->setProperty("summaryLabel", QVariant::fromValue(sumLabel)); frame->setProperty("bodyLabel", QVariant::fromValue(bodyLabel)); notificationFrames.insert(id, frame); emit numNotificationsChanged(notificationFrames.count()); } } void InfoPaneDropdown::removeNotification(int id) { if (notificationFrames.keys().contains(id)) { delete notificationFrames.value(id); notificationFrames.remove(id); } emit numNotificationsChanged(notificationFrames.count()); if (notificationFrames.count() == 0) { //ui->noNotifications->setVisible(true); //ui->clearAllNotifications->setVisible(false); } } void InfoPaneDropdown::on_clearAllNotifications_clicked() { for (int id : notificationFrames.keys()) { emit closeNotification(id); } } void InfoPaneDropdown::on_redshiftPause_toggled(bool checked) { processTimer(); settings.setValue("display/redshiftPaused", !checked); } void InfoPaneDropdown::updateSysInfo() { ui->currentBattery->setText(tr("Current Battery Percentage: %1").arg(QString::number(updbus->currentBattery()).append("%"))); QTime uptime(0, 0); uptime = uptime.addMSecs(startTime.elapsed()); ui->theshellUptime->setText(tr("theShell Uptime: %1").arg(uptime.toString("hh:mm:ss"))); struct sysinfo* info = new struct sysinfo; if (sysinfo(info) == 0) { QTime sysUptime(0, 0); sysUptime = sysUptime.addSecs(info->uptime); QString uptimeString; if (info->uptime > 86400) { int days = info->uptime / 86400; uptimeString = tr("%n days", NULL, days) + " " + sysUptime.toString("hh:mm:ss"); } else { uptimeString = sysUptime.toString("hh:mm:ss"); } ui->systemUptime->setText(tr("System Uptime: %1").arg(uptimeString)); } else { ui->systemUptime->setText(tr("Couldn't get system uptime")); } delete info; } void InfoPaneDropdown::on_printLabel_clicked() { //changeDropDown(Print); } void InfoPaneDropdown::on_resetButton_clicked() { if (QMessageBox::warning(this, tr("Reset theShell"), tr("All settings will be reset to default, and you will be logged out. " "Are you sure you want to do this?"), QMessageBox::Yes | QMessageBox::No, QMessageBox::No) == QMessageBox::Yes) { settings.clear(); EndSession(EndSessionWait::logout); } } bool InfoPaneDropdown::isTimerRunning() { if (timer == NULL) { return false; } else { return true; } } void InfoPaneDropdown::mousePressEvent(QMouseEvent *event) { mouseClickPoint = event->localPos().toPoint().y(); initialPoint = mouseClickPoint; dragRect = this->geometry(); mouseMovedUp = false; draggingInfoPane = true; event->accept(); } void InfoPaneDropdown::mouseMoveEvent(QMouseEvent *event) { if (draggingInfoPane) { QRect screenGeometry = QApplication::desktop()->screenGeometry(); if (event->globalY() < mouseClickPoint) { mouseMovedUp = true; } else { mouseMovedUp = false; } //dragRect.translate(0, event->localPos().toPoint().y() - mouseClickPoint + this->y()); dragRect = screenGeometry; dragRect.translate(0, event->globalY() - (initialPoint + screenGeometry.top())); //innerRect.translate(event->localPos().toPoint().y() - mouseClickPoint, 0); if (settings.value("bar/onTop", true).toBool()) { if (dragRect.bottom() >= screenGeometry.bottom()) { dragRect.moveTo(screenGeometry.left(), screenGeometry.top()); } } else { if (dragRect.top() <= screenGeometry.top() - 1) { dragRect.moveTo(screenGeometry.left(), screenGeometry.top() - 1); } } this->setGeometry(dragRect); mouseClickPoint = event->globalY(); event->accept(); } } void InfoPaneDropdown::mouseReleaseEvent(QMouseEvent *event) { if (draggingInfoPane) { QRect screenGeometry = QApplication::desktop()->screenGeometry(); if (initialPoint - 5 > mouseClickPoint && initialPoint + 5 < mouseClickPoint) { tPropertyAnimation* a = new tPropertyAnimation(this, "geometry"); a->setStartValue(this->geometry()); a->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - (settings.value("bar/onTop", true).toBool() ? 0 : 1), this->width(), this->height())); a->setEasingCurve(QEasingCurve::OutCubic); a->setDuration(500); connect(a, SIGNAL(finished()), a, SLOT(deleteLater())); a->start(); } else { /*if ((mouseMovedUp && settings.value("bar/onTop", true).toBool()) || (!mouseMovedUp && !settings.value("bar/onTop", true).toBool())) {*/ if (mouseMovedUp == settings.value("bar/onTop", true).toBool()) { this->close(); } else { tPropertyAnimation* a = new tPropertyAnimation(this, "geometry"); a->setStartValue(this->geometry()); a->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - (settings.value("bar/onTop", true).toBool() ? 0 : 1), this->width(), this->height())); a->setEasingCurve(QEasingCurve::OutCubic); a->setDuration(500); connect(a, SIGNAL(finished()), a, SLOT(deleteLater())); a->start(); } } event->accept(); initialPoint = 0; draggingInfoPane = false; } } void InfoPaneDropdown::on_TouchFeedbackSwitch_toggled(bool checked) { settings.setValue("input/touchFeedbackSound", checked); } void InfoPaneDropdown::on_brightnessSlider_sliderMoved(int position) { QProcess* backlight = new QProcess(this); backlight->start("xbacklight -set " + QString::number(position)); connect(backlight, SIGNAL(finished(int)), backlight, SLOT(deleteLater())); } void InfoPaneDropdown::on_brightnessSlider_valueChanged(int value) { on_brightnessSlider_sliderMoved(value); } void InfoPaneDropdown::on_settingsList_currentRowChanged(int currentRow) { ui->settingsTabs->setCurrentIndex(currentRow); //Set up settings if (ui->settingsTabs->currentWidget() == ui->NotificationsSettings) { //Notifications setupNotificationsSettingsPane(); } else if (currentRow == 6) { //Location setupLocationSettingsPane(); } else if (ui->settingsTabs->currentWidget() == ui->UserSettings) { //Users setupUsersSettingsPane(); } else if (ui->settingsTabs->currentWidget() == ui->DateTimeSettings) { //Date and Time setupDateTimeSettingsPane(); } } void InfoPaneDropdown::setupNotificationsSettingsPane() { ui->AppNotifications->clear(); QStringList knownApplications; int amount = notificationAppSettings->beginReadArray("notifications/knownApplications"); for (int i = 0; i < amount; i++) { notificationAppSettings->setArrayIndex(i); knownApplications.append(notificationAppSettings->value("appname").toString()); } notificationAppSettings->endArray(); for (QString app : knownApplications) { QListWidgetItem* item = new QListWidgetItem(); item->setText(app); ui->AppNotifications->addItem(item); } } void InfoPaneDropdown::on_settingsTabs_currentChanged(int arg1) { ui->settingsList->item(arg1)->setSelected(true); } void InfoPaneDropdown::on_lockScreenBackgroundBrowse_clicked() { QFileDialog dialog(this); dialog.setAcceptMode(QFileDialog::AcceptOpen); dialog.setNameFilter("Images (*.jpg *.jpeg *.bmp *.png *.gif *.svg)"); if (dialog.exec() == QDialog::Accepted) { lockScreenSettings->setValue("background", dialog.selectedFiles().first()); ui->lockScreenBackground->setText(dialog.selectedFiles().first()); } } void InfoPaneDropdown::on_lockScreenBackground_textEdited(const QString &arg1) { lockScreenSettings->setValue("background", arg1); } void InfoPaneDropdown::on_TextSwitch_toggled(bool checked) { settings.setValue("bar/showText", checked); } void InfoPaneDropdown::on_windowManager_textEdited(const QString &arg1) { settings.setValue("startup/WindowManagerCommand", arg1); } void InfoPaneDropdown::on_barDesktopsSwitch_toggled(bool checked) { settings.setValue("bar/showWindowsFromOtherDesktops", checked); } void InfoPaneDropdown::on_BluetoothSwitch_toggled(bool checked) { QDBusInterface("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", QDBusConnection::sessionBus()).setProperty("BluetoothEnabled", checked); } void InfoPaneDropdown::on_SuperkeyGatewaySwitch_toggled(bool checked) { settings.setValue("input/superkeyGateway", checked); } void InfoPaneDropdown::reject() { this->close(); } void InfoPaneDropdown::on_kdeconnectLabel_clicked() { changeDropDown(KDEConnect); } void InfoPaneDropdown::on_endSessionConfirmFullScreen_toggled(bool checked) { if (checked) { settings.setValue("ui/useFullScreenEndSession", true); } } void InfoPaneDropdown::on_endSessionConfirmInMenu_toggled(bool checked) { if (checked) { settings.setValue("ui/useFullScreenEndSession", false); } } void InfoPaneDropdown::on_pageStack_switchingFrame(int switchTo) { QWidget* switchingWidget = ui->pageStack->widget(switchTo); ui->clockLabel->setShowDisabled(true); ui->batteryLabel->setShowDisabled(true); ui->notificationsLabel->setShowDisabled(true); ui->networkLabel->setShowDisabled(true); //ui->printLabel->setShowDisabled(true); ui->kdeconnectLabel->setShowDisabled(true); if (switchingWidget == ui->clockFrame) { ui->clockLabel->setShowDisabled(false); } else if (switchingWidget == ui->statusFrame) { ui->batteryLabel->setShowDisabled(false); } else if (switchingWidget == ui->notificationsFrame) { ui->notificationsLabel->setShowDisabled(false); } else if (switchingWidget == ui->networkFrame) { ui->networkLabel->setShowDisabled(false); /*} else if (switchingWidget == ui->printFrame) { ui->printLabel->setShowDisabled(false);*/ } else if (switchingWidget == ui->kdeConnectFrame) { ui->kdeconnectLabel->setShowDisabled(false); } } void InfoPaneDropdown::on_showNotificationsContents_toggled(bool checked) { if (checked) { settings.setValue("notifications/lockScreen", "contents"); } } void InfoPaneDropdown::on_showNotificationsOnly_toggled(bool checked) { if (checked) { settings.setValue("notifications/lockScreen", "noContents"); } } void InfoPaneDropdown::on_showNotificationsNo_toggled(bool checked) { if (checked) { settings.setValue("notifications/lockScreen", "none"); } } void InfoPaneDropdown::on_stopwatchStart_clicked() { if (stopwatchRunning) { stopwatchRunning = false; stopwatchTimeAdd += stopwatchTime.elapsed(); ui->stopwatchReset->setVisible(true); ui->stopwatchStart->setText(tr("Start")); ui->stopwatchStart->setIcon(QIcon::fromTheme("chronometer-start")); } else { stopwatchTime.restart(); stopwatchRunning = true; ui->stopwatchReset->setVisible(false); ui->stopwatchStart->setText(tr("Stop")); ui->stopwatchStart->setIcon(QIcon::fromTheme("chronometer-pause")); } } void InfoPaneDropdown::on_stopwatchReset_clicked() { stopwatchTimeAdd = 0; } void InfoPaneDropdown::on_calendarTodayButton_clicked() { ui->calendarWidget->setSelectedDate(QDate::currentDate()); } void InfoPaneDropdown::on_MediaSwitch_toggled(bool checked) { settings.setValue("notifications/mediaInsert", checked); } void InfoPaneDropdown::on_lightColorThemeRadio_toggled(bool checked) { if (checked) { themeSettings->setValue("color/type", "light"); updateAccentColourBox(); resetStyle(); changeDropDown(Settings, false); } } void InfoPaneDropdown::on_darkColorThemeRadio_toggled(bool checked) { if (checked) { themeSettings->setValue("color/type", "dark"); updateAccentColourBox(); resetStyle(); changeDropDown(Settings, false); } } void InfoPaneDropdown::on_themeButtonColor_currentIndexChanged(int index) { themeSettings->setValue("color/accent", index); resetStyle(); } void InfoPaneDropdown::on_systemFont_currentFontChanged(const QFont &f) { themeSettings->setValue("fonts/defaultFamily", f.family()); themeSettings->setValue("fonts/smallFamily", f.family()); ui->systemFontSize->setValue(themeSettings->value("font/defaultSize", 10).toInt()); //ui->systemFont->setFont(QFont(themeSettings->value("font/defaultFamily", defaultFont).toString(), themeSettings->value("font/defaultSize", 10).toInt())); } void InfoPaneDropdown::on_batteryChartUpdateButton_clicked() { updateBatteryChart(); } //DBus Battery Info Structure struct BatteryInfo { uint time, state; double value; }; Q_DECLARE_METATYPE(BatteryInfo) const QDBusArgument &operator<<(QDBusArgument &argument, const BatteryInfo &info) { argument.beginStructure(); argument << info.time << info.value << info.state; argument.endStructure(); return argument; } const QDBusArgument &operator>>(const QDBusArgument &argument, BatteryInfo &info) { argument.beginStructure(); argument >> info.time >> info.value >> info.state; argument.endStructure(); return argument; } //DBus WakeupsInfo Structure struct WakeupsInfo { bool process = false; uint pid; double wakeups; QString path, description; }; Q_DECLARE_METATYPE(WakeupsInfo) const QDBusArgument &operator<<(QDBusArgument &argument, const WakeupsInfo &info) { argument.beginStructure(); argument << info.process << info.pid << info.wakeups << info.path << info.description; argument.endStructure(); return argument; } const QDBusArgument &operator>>(const QDBusArgument &argument, WakeupsInfo &info) { argument.beginStructure(); argument >> info.process >> info.pid >> info.wakeups >> info.path >> info.description; argument.endStructure(); return argument; } void InfoPaneDropdown::updateBatteryChart() { if (ui->appsGraphButton->isChecked()) { QDBusMessage dataMessage = QDBusMessage::createMethodCall("org.freedesktop.UPower", "/org/freedesktop/UPower/Wakeups", "org.freedesktop.UPower.Wakeups", "GetData"); QDBusReply dataMessageArgument = QDBusConnection::systemBus().call(dataMessage); QList wakeups; if (dataMessageArgument.isValid()) { QDBusArgument arrayArgument = dataMessageArgument.value(); arrayArgument.beginArray(); while (!arrayArgument.atEnd()) { WakeupsInfo info; arrayArgument >> info; if (info.process) { int min = 0, max = wakeups.count(); int insertIndex; while (max != min) { insertIndex = ((max - min) / 2) + min; if (wakeups.at(insertIndex).wakeups == info.wakeups) { //Goes here break; } else if (wakeups.at(insertIndex).wakeups < info.wakeups) { //Needs to go on left hand side max = insertIndex - 1; } else if (wakeups.at(insertIndex).wakeups > info.wakeups) { //Needs to go on right hand side min = insertIndex + 1; } } wakeups.insert(insertIndex, info); } } arrayArgument.endArray(); ui->appsGraph->clear(); for (WakeupsInfo wakeup : wakeups) { QListWidgetItem* item = new QListWidgetItem; item->setText("[" + QString::number(wakeup.pid) + "] " + wakeup.path + " (" + wakeup.description + ")"); ui->appsGraph->insertItem(0, item); } } } else { for (QAbstractAxis* axis : batteryChart->axes()) { batteryChart->removeAxis(axis); axis->deleteLater(); } QDBusMessage historyMessage = QDBusMessage::createMethodCall("org.freedesktop.UPower", updbus->defaultBattery().path(), "org.freedesktop.UPower.Device", "GetHistory"); QVariantList historyMessageArguments; if (ui->chargeGraphButton->isChecked()) { historyMessageArguments.append("charge"); } else { historyMessageArguments.append("rate"); } historyMessageArguments.append((uint) 0); //Get surplus data so we can plot some data off the left of the graph historyMessageArguments.append((uint) 10000); historyMessage.setArguments(historyMessageArguments); QDBusReply historyArgument = QDBusConnection::systemBus().call(historyMessage); QLineSeries* batteryChartData = new QLineSeries; QPen dataPen; dataPen.setColor(this->palette().color(QPalette::Highlight)); dataPen.setWidth(2 * getDPIScaling()); batteryChartData->setPen(dataPen); QLineSeries* batteryChartTimeRemainingData = new QLineSeries; //batteryChartTimeRemainingData->setColor(this->palette().color(QPalette::Disabled, QPalette::WindowText)); batteryChartTimeRemainingData->setBrush(QBrush(this->palette().color(QPalette::Disabled, QPalette::WindowText))); QPen remainingTimePen; remainingTimePen.setColor(this->palette().color(QPalette::Disabled, QPalette::Highlight)); remainingTimePen.setDashPattern(QVector() << 3 << 3); remainingTimePen.setDashOffset(3); remainingTimePen.setWidth(2 * getDPIScaling()); batteryChartTimeRemainingData->setPen(remainingTimePen); QDateTime remainingTime = updbus->batteryTimeRemaining(); int firstDateTime = QDateTime::currentSecsSinceEpoch() / 60; qint64 msecsSinceFull = -1; uint lastState = -1; bool takeNextSinceLastFull = false; if (historyArgument.isValid()) { QDBusArgument arrayArgument = historyArgument.value(); arrayArgument.beginArray(); while (!arrayArgument.atEnd()) { BatteryInfo info; arrayArgument >> info; qint64 msecs = info.time; msecs = msecs * 1000; if (info.value >= 90 && info.state == 2 && lastState == 1 && msecsSinceFull < msecs) { takeNextSinceLastFull = true; } else if (takeNextSinceLastFull) { takeNextSinceLastFull = false; msecsSinceFull = msecs; } lastState = info.state; if (info.value != 0 && info.state != 0) { batteryChartData->append(msecs, info.value); if (firstDateTime > info.time / 60) { firstDateTime = info.time / 60; } } } arrayArgument.endArray(); batteryChartData->append(QDateTime::currentMSecsSinceEpoch(), batteryChartData->at(batteryChartData->count() - 1).y()); if (remainingTime.isValid() && ui->batteryChartShowProjected->isChecked() && ui->chargeGraphButton->isChecked()) { QDateTime lastDateTime = QDateTime::fromMSecsSinceEpoch(batteryChartData->at(batteryChartData->count() - 1).x()); batteryChartTimeRemainingData->append(batteryChartData->at(batteryChartData->count() - 1)); QDateTime endDateTime = lastDateTime.addMSecs(remainingTime.toMSecsSinceEpoch()); if (updbus->charging()) { batteryChartTimeRemainingData->append(endDateTime.toMSecsSinceEpoch(), 100); } else { batteryChartTimeRemainingData->append(endDateTime.toMSecsSinceEpoch(), 0); } } } batteryChart->removeAllSeries(); batteryChart->addSeries(batteryChartData); batteryChart->addSeries(batteryChartTimeRemainingData); xAxis = new QDateTimeAxis; if (ui->chargeGraphButton->isChecked()) { if (remainingTime.isValid() && ui->batteryChartShowProjected->isChecked()) { xAxis->setMax(QDateTime::fromMSecsSinceEpoch(batteryChartData->at(batteryChartData->count() - 1).x()).addMSecs(remainingTime.toMSecsSinceEpoch())); } else { xAxis->setMax(QDateTime::currentDateTime()); } QDateTime oneDay = xAxis->max().addDays(-1); if (msecsSinceFull == -1 || msecsSinceFull < oneDay.toMSecsSinceEpoch()) { xAxis->setMin(oneDay); } else { xAxis->setMin(QDateTime::fromMSecsSinceEpoch(msecsSinceFull)); } } else { xAxis->setMax(QDateTime::currentDateTime()); xAxis->setMin(xAxis->max().addSecs(-43200)); //Half a day } batteryChart->addAxis(xAxis, Qt::AlignBottom); xAxis->setLabelsColor(this->palette().color(QPalette::WindowText)); xAxis->setFormat("hh:mm"); xAxis->setTickCount(9); batteryChartData->attachAxis(xAxis); batteryChartTimeRemainingData->attachAxis(xAxis); /*connect(xAxis, &QDateTimeAxis::rangeChanged, [=](QDateTime min, QDateTime max) { ui->BatteryChargeScrollBar->setMaximum(max.toMSecsSinceEpoch() - min.toMSecsSinceEpoch()); });*/ chartScrolling = true; int currentSecsSinceEpoch = QDateTime::currentSecsSinceEpoch(); ui->BatteryChargeScrollBar->setMinimum(0); ui->BatteryChargeScrollBar->setMaximum(currentSecsSinceEpoch / 60 - firstDateTime); ui->BatteryChargeScrollBar->setValue(currentSecsSinceEpoch / 60 - firstDateTime); startValue = currentSecsSinceEpoch / 60 - firstDateTime; chartScrolling = false; QValueAxis* yAxis = new QValueAxis; if (ui->chargeGraphButton->isChecked()) { yAxis->setLabelFormat("%i%%"); yAxis->setMax(100); } else { yAxis->setLabelFormat("%i W"); yAxis->setMax(40); } yAxis->setMin(0); yAxis->setLabelsColor(this->palette().color(QPalette::WindowText)); batteryChart->addAxis(yAxis, Qt::AlignLeft); batteryChartData->attachAxis(yAxis); batteryChartTimeRemainingData->attachAxis(yAxis); ui->batteryChartLastUpdate->setText(tr("Last updated %1").arg(QDateTime::currentDateTime().toString("hh:mm:ss"))); } } void InfoPaneDropdown::on_batteryChartShowProjected_toggled(bool checked) { Q_UNUSED(checked) updateBatteryChart(); } void InfoPaneDropdown::on_upArrow_clicked() { this->close(); } void InfoPaneDropdown::on_PowerStretchSwitch_toggled(bool checked) { updbus->setPowerStretch(checked); emit batteryStretchChanged(checked); } void InfoPaneDropdown::doNetworkCheck() { if (updbus->powerStretch()) { //Always set networkOk to ok because we don't update when power stretch is on networkOk = Ok; } else { //Do some network checks to see if network is working QDBusInterface i("org.freedesktop.NetworkManager", "/org/freedesktop/NetworkManager", "org.freedesktop.NetworkManager", QDBusConnection::systemBus(), this); int connectivity = i.property("Connectivity").toUInt(); if (connectivity == 2) { if (networkOk != BehindPortal) { //Notify user that they are behind a portal. //Wait 10 seconds for startup or for connection notification QTimer::singleShot(10000, [=] { QStringList actions; actions.append("login"); actions.append(tr("Log in to network")); QVariantMap hints; hints.insert("category", "network.connected"); hints.insert("transient", true); uint notificationId = ndbus->Notify("theShell", 0, "", tr("Network Login"), tr("Your connection to the internet is blocked by a login page."), actions, hints, 30000); connect(ndbus, &NotificationsDBusAdaptor::ActionInvoked, [=](uint id, QString key) { if (notificationId == id && key == "login") { QProcess::startDetached("xdg-open http://nmcheck.gnome.org/"); } }); }); } networkOk = BehindPortal; //Reload the connectivity status i.asyncCall("CheckConnectivity"); return; } else if (connectivity == 3) { networkOk = Unspecified; //Reload the connectivity status i.asyncCall("CheckConnectivity"); return; } else { networkOk = Ok; } QNetworkAccessManager* manager = new QNetworkAccessManager; if (manager->networkAccessible() == QNetworkAccessManager::NotAccessible) { networkOk = Unspecified; manager->deleteLater(); //Reload the connectivity status i.asyncCall("CheckConnectivity"); return; } manager->deleteLater(); //For some reason this crashes theShell so let's not do this (for now) /*connect(manager, &QNetworkAccessManager::finished, [=](QNetworkReply* reply) { if (reply->error() != QNetworkReply::NoError) { networkOk = false; } else { networkOk = true; } manager->deleteLater(); }); manager->get(QNetworkRequest(QUrl("http://vicr123.github.io/")));*/ //Reload the connectivity status i.asyncCall("CheckConnectivity"); } } void InfoPaneDropdown::dragDown(dropdownType showWith, int y) { changeDropDown(showWith, false); QRect screenGeometry = QApplication::desktop()->screenGeometry(); if (settings.value("bar/onTop", true).toBool()) { this->setGeometry(screenGeometry.x(), screenGeometry.y() - screenGeometry.height() + y, screenGeometry.width(), screenGeometry.height() + 1); } else { this->setGeometry(screenGeometry.x(), screenGeometry.top() + y + screenGeometry.y(), screenGeometry.width(), screenGeometry.height() + 1); } Atom DesktopWindowTypeAtom; DesktopWindowTypeAtom = XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE_NORMAL", False); XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE", False), XA_ATOM, 32, PropModeReplace, (unsigned char*) &DesktopWindowTypeAtom, 1); //Change Window Type unsigned long desktop = 0xFFFFFFFF; XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_DESKTOP", False), XA_CARDINAL, 32, PropModeReplace, (unsigned char*) &desktop, 1); //Set visible on all desktops QDialog::show(); this->setFixedWidth(screenGeometry.width()); this->setFixedHeight(screenGeometry.height()); //Get Current Brightness QProcess* backlight = new QProcess(this); backlight->start("xbacklight -get"); backlight->waitForFinished(); float output = ceil(QString(backlight->readAll()).toFloat()); delete backlight; ui->brightnessSlider->setValue((int) output); previousDragY = y; } void InfoPaneDropdown::completeDragDown() { QRect screenGeometry = QApplication::desktop()->screenGeometry(); if ((QCursor::pos().y() - screenGeometry.top() < previousDragY && settings.value("bar/onTop", true).toBool()) || (QCursor::pos().y() - screenGeometry.top() > previousDragY && !settings.value("bar/onTop", true).toBool())) { this->close(); } else { tPropertyAnimation* a = new tPropertyAnimation(this, "geometry"); a->setStartValue(this->geometry()); a->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - (settings.value("bar/onTop", true).toBool() ? 0 : 1), this->width(), screenGeometry.height() + 1)); a->setEasingCurve(QEasingCurve::OutCubic); a->setDuration(500); connect(a, SIGNAL(finished()), a, SLOT(deleteLater())); a->start(); } } void InfoPaneDropdown::on_notificationSoundBox_currentIndexChanged(int index) { QSoundEffect* sound = new QSoundEffect(); switch (index) { case 0: settings.setValue("notifications/sound", "tripleping"); sound->setSource(QUrl("qrc:/sounds/notifications/tripleping.wav")); break; case 1: settings.setValue("notifications/sound", "upsidedown"); sound->setSource(QUrl("qrc:/sounds/notifications/upsidedown.wav")); break; case 2: settings.setValue("notifications/sound", "echo"); sound->setSource(QUrl("qrc:/sounds/notifications/echo.wav")); break; } sound->play(); connect(sound, SIGNAL(playingChanged()), sound, SLOT(deleteLater())); } void InfoPaneDropdown::setupUsersSettingsPane() { ui->availableUsersWidget->clear(); QDBusMessage getUsersMessage = QDBusMessage::createMethodCall("org.freedesktop.Accounts", "/org/freedesktop/Accounts", "org.freedesktop.Accounts", "ListCachedUsers"); QDBusReply> allUsers = QDBusConnection::systemBus().call(getUsersMessage); if (allUsers.isValid()) { for (QDBusObjectPath obj : allUsers.value()) { QDBusInterface interface("org.freedesktop.Accounts", obj.path(), "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); QListWidgetItem* item = new QListWidgetItem(); QString name = interface.property("RealName").toString(); if (name == "") { name = interface.property("UserName").toString(); } item->setText(name); item->setIcon(QIcon::fromTheme("user")); item->setData(Qt::UserRole, obj.path()); ui->availableUsersWidget->addItem(item); } QListWidgetItem* item = new QListWidgetItem(); item->setIcon(QIcon::fromTheme("list-add")); item->setText(tr("Add New User")); item->setData(Qt::UserRole, "new"); ui->availableUsersWidget->addItem(item); } } void InfoPaneDropdown::on_userSettingsNextButton_clicked() { if (ui->availableUsersWidget->selectedItems().count() != 0) { //Check Polkit authorization PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.freedesktop.accounts.user-administration", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::None); if (r == PolkitQt1::Authority::No) { QMessageBox::warning(this, tr("Unauthorized"), tr("Polkit does not allow you to manage users on the system."), QMessageBox::Ok, QMessageBox::Ok); return; } else if (r == PolkitQt1::Authority::Challenge) { LOWER_INFOPANE PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.freedesktop.accounts.user-administration", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::AllowUserInteraction); if (r != PolkitQt1::Authority::Yes) { return; } } editingUserPath = ui->availableUsersWidget->selectedItems().first()->data(Qt::UserRole).toString(); if (editingUserPath == "new") { ui->userSettingsEditUserLabel->setText(tr("New User")); ui->userSettingsFullName->setText(""); ui->userSettingsUserName->setText(""); ui->userSettingsPassword->setPlaceholderText(tr("(none)")); ui->userSettingsPasswordCheck->setPlaceholderText(tr("(none)")); ui->userSettingsDeleteUser->setVisible(false); ui->userSettingsStandardAccount->setChecked(true); ui->userSettingsAdminAccount->setChecked(false); } else { ui->userSettingsEditUserLabel->setText(tr("Edit User")); QDBusInterface interface("org.freedesktop.Accounts", editingUserPath, "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); int passwordMode = interface.property("PasswordMode").toInt(); if (passwordMode == 0) { ui->userSettingsPassword->setPlaceholderText(tr("(unchanged)")); ui->userSettingsPasswordCheck->setPlaceholderText(tr("(unchanged)")); } else if (passwordMode == 1) { ui->userSettingsPassword->setPlaceholderText(tr("(set at next login)")); ui->userSettingsPasswordCheck->setPlaceholderText(tr("(set at next login)")); } else { ui->userSettingsPassword->setPlaceholderText(tr("(none)")); ui->userSettingsPasswordCheck->setPlaceholderText(tr("(none)")); } if (interface.property("AccountType").toInt() == 0) { ui->userSettingsStandardAccount->setChecked(true); ui->userSettingsAdminAccount->setChecked(false); } else { ui->userSettingsStandardAccount->setChecked(false); ui->userSettingsAdminAccount->setChecked(true); } ui->userSettingsFullName->setText(interface.property("RealName").toString()); ui->userSettingsUserName->setText(interface.property("UserName").toString()); ui->userSettingsPasswordHint->setText(interface.property("PasswordHint").toString()); ui->userSettingsDeleteUser->setVisible(true); } ui->userSettingsPassword->setText(""); ui->userSettingsPasswordCheck->setText(""); ui->userSettingsStackedWidget->setCurrentIndex(1); } } void InfoPaneDropdown::on_userSettingsCancelButton_clicked() { ui->userSettingsStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::on_userSettingsApplyButton_clicked() { if (ui->userSettingsPasswordCheck->text() != ui->userSettingsPassword->text()) { QMessageBox::warning(this, tr("Password Check"), tr("The passwords don't match."), QMessageBox::Ok, QMessageBox::Ok); return; } if (ui->userSettingsUserName->text().contains(" ")) { QMessageBox::warning(this, tr("Username"), tr("The username must not contain spaces."), QMessageBox::Ok, QMessageBox::Ok); return; } if (ui->userSettingsUserName->text().toLower() != ui->userSettingsUserName->text()) { QMessageBox::warning(this, tr("Username"), tr("The username must not contain capital letters."), QMessageBox::Ok, QMessageBox::Ok); return; } if (editingUserPath == "new") { QDBusMessage createMessage = QDBusMessage::createMethodCall("org.freedesktop.Accounts", "/org/freedesktop/Accounts", "org.freedesktop.Accounts", "CreateUser"); QVariantList args; args.append(ui->userSettingsUserName->text()); args.append(ui->userSettingsFullName->text()); args.append(0); createMessage.setArguments(args); QDBusReply newUser = QDBusConnection::systemBus().call(createMessage); if (newUser.error().isValid()) { tToast* toast = new tToast(); toast->setTitle("Couldn't create user"); toast->setText(newUser.error().message()); connect(toast, SIGNAL(dismissed()), toast, SLOT(deleteLater())); toast->show(this); return; } else { editingUserPath = newUser.value().path(); } } QDBusInterface interface("org.freedesktop.Accounts", editingUserPath, "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); QDBusMessage setUserNameMessage = interface.call("SetUserName", ui->userSettingsUserName->text()); if (setUserNameMessage.errorMessage() != "") { tToast* toast = new tToast(); toast->setTitle("Couldn't create user"); toast->setText(setUserNameMessage.errorMessage()); connect(toast, SIGNAL(dismissed()), toast, SLOT(deleteLater())); toast->show(this); return; } interface.call("SetRealName", ui->userSettingsFullName->text()); if (ui->userSettingsAdminAccount->isChecked()) { interface.call("SetAccountType", 1); } else { interface.call("SetAccountType", 0); } if (ui->userSettingsPassword->text() != "") { interface.call("SetPasswordMode", 0); //Crypt password QByteArray characters = "0123456789ABCDEFGHIJKLMNOPQRSTUVXYZabcdefghijklmnopqrstuvxyz./"; QByteArray salt("$6$"); for (int i = 0; i < 16; i++) { salt.append(characters.at((qrand() % characters.count()))); } QString cryptedPassword = QString::fromLatin1(crypt(ui->userSettingsPassword->text().toUtf8(), salt.constData())); interface.call("SetPassword", cryptedPassword, ui->userSettingsPasswordHint->text()); } else { if (editingUserPath == "new") { interface.call("SetPasswordMode", 2); interface.call("SetPasswordHint", ui->userSettingsPasswordHint->text()); } } setupUsersSettingsPane(); ui->userSettingsStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::on_userSettingsFullName_textEdited(const QString &arg1) { ui->userSettingsUserName->setText(arg1.toLower().split(" ").first()); } void InfoPaneDropdown::on_userSettingsDeleteUser_clicked() { ui->userSettingsStackedWidget->setCurrentIndex(2); } void InfoPaneDropdown::on_userSettingsCancelDeleteUser_clicked() { ui->userSettingsStackedWidget->setCurrentIndex(1); } void InfoPaneDropdown::on_userSettingsDeleteUserOnly_clicked() { QDBusInterface interface("org.freedesktop.Accounts", editingUserPath, "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); qlonglong uid = interface.property("Uid").toLongLong(); QDBusMessage deleteMessage = QDBusMessage::createMethodCall("org.freedesktop.Accounts", "/org/freedesktop/Accounts", "org.freedesktop.Accounts", "DeleteUser"); QVariantList args; args.append(uid); args.append(false); deleteMessage.setArguments(args); QDBusConnection::systemBus().call(deleteMessage); setupUsersSettingsPane(); ui->userSettingsStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::on_userSettingsDeleteUserAndData_clicked() { QDBusInterface interface("org.freedesktop.Accounts", editingUserPath, "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); qlonglong uid = interface.property("Uid").toLongLong(); QDBusMessage deleteMessage = QDBusMessage::createMethodCall("org.freedesktop.Accounts", "/org/freedesktop/Accounts", "org.freedesktop.Accounts", "DeleteUser"); QVariantList args; args.append(uid); args.append(true); deleteMessage.setArguments(args); QDBusConnection::systemBus().call(deleteMessage); setupUsersSettingsPane(); ui->userSettingsStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::setupDateTimeSettingsPane() { launchDateTimeService(); QDateTime current = QDateTime::currentDateTime(); ui->dateTimeSetDate->setSelectedDate(current.date()); ui->dateTimeSetTime->setTime(current.time()); QDBusInterface dateTimeInterface("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", QDBusConnection::systemBus()); bool isNTPEnabled = dateTimeInterface.property("NTP").toBool(); ui->DateTimeNTPSwitch->setChecked(isNTPEnabled); } void InfoPaneDropdown::launchDateTimeService() { QDBusMessage getMessage = QDBusMessage::createMethodCall("org.freedesktop.DBus", "/", "org.freedesktop.DBus", "ListActivatableNames"); QDBusReply reply = QDBusConnection::systemBus().call(getMessage); if (!reply.value().contains("org.freedesktop.timedate1")) { qDebug() << "Can't set date and time"; return; } /*QDBusMessage launchMessage = QDBusMessage::createMethodCall("org.freedesktop.DBus", "/", "org.freedesktop.DBus", "StartServiceByName"); QVariantList args; args.append("org.freedesktop.timedate1"); args.append((uint) 0); launchMessage.setArguments(args); QDBusConnection::systemBus().call(launchMessage);*/ QDBusConnection::systemBus().interface()->startService("org.freedesktop.timedate1"); } void InfoPaneDropdown::on_dateTimeSetDateTimeButton_clicked() { QDateTime newTime; newTime.setDate(ui->dateTimeSetDate->selectedDate()); newTime.setTime(ui->dateTimeSetTime->time()); qlonglong time = newTime.toMSecsSinceEpoch() * 1000; launchDateTimeService(); QDBusMessage setMessage = QDBusMessage::createMethodCall("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "SetTime"); QVariantList args; args.append(time); args.append(false); args.append(true); setMessage.setArguments(args); QDBusConnection::systemBus().call(setMessage); setupDateTimeSettingsPane(); updateDSTNotification(); } void InfoPaneDropdown::on_DateTimeNTPSwitch_toggled(bool checked) { if (checked) { ui->dateTimeSetDate->setEnabled(false); ui->dateTimeSetTime->setEnabled(false); ui->dateTimeSetDateTimeButton->setEnabled(false); } else { ui->dateTimeSetDate->setEnabled(true); ui->dateTimeSetTime->setEnabled(true); ui->dateTimeSetDateTimeButton->setEnabled(true); } launchDateTimeService(); QDBusMessage setMessage = QDBusMessage::createMethodCall("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "SetNTP"); QVariantList args; args.append(checked); args.append(true); setMessage.setArguments(args); QDBusConnection::systemBus().call(setMessage); setupDateTimeSettingsPane(); } void InfoPaneDropdown::on_localeList_currentRowChanged(int currentRow) { //Show the splash screen (if available) emit dbusSignals->ShowSplash(); switch (currentRow) { case Internationalisation::enUS: settings.setValue("locale/language", "en_US"); break; case Internationalisation::enGB: settings.setValue("locale/language", "en_GB"); break; case Internationalisation::enAU: settings.setValue("locale/language", "en_AU"); break; case Internationalisation::enNZ: settings.setValue("locale/language", "en_NZ"); break; case Internationalisation::viVN: settings.setValue("locale/language", "vi_VN"); break; case Internationalisation::daDK: settings.setValue("locale/language", "da_DK"); break; case Internationalisation::ptBR: settings.setValue("locale/language", "pt_BR"); break; case Internationalisation::arSA: settings.setValue("locale/language", "ar_SA"); break; case Internationalisation::zhCN: settings.setValue("locale/language", "zh_CN"); break; case Internationalisation::nlNL: settings.setValue("locale/language", "nl_NL"); break; case Internationalisation::miNZ: settings.setValue("locale/language", "mi_NZ"); break; case Internationalisation::jaJP: settings.setValue("locale/language", "ja_JP"); break; case Internationalisation::deDE: settings.setValue("locale/language", "de_DE"); break; case Internationalisation::esES: settings.setValue("locale/language", "es_ES"); break; case Internationalisation::ruRU: settings.setValue("locale/language", "ru_RU"); break; case Internationalisation::svSE: settings.setValue("locale/language", "sv_SE"); break; case Internationalisation::ltLT: settings.setValue("locale/language", "lt_LT"); break; case Internationalisation::idID: settings.setValue("locale/language", "id_ID"); break; case Internationalisation::auAU: settings.setValue("locale/language", "au_AU"); break; case Internationalisation::nbNO: settings.setValue("locale/language", "nb_NO"); break; case Internationalisation::arEG: settings.setValue("locale/language", "ar_EG"); break; } QString localeName = settings.value("locale/language", "en_US").toString(); qputenv("LANG", localeName.toUtf8()); QLocale defaultLocale(localeName); QLocale::setDefault(defaultLocale); QApplication::setLayoutDirection(defaultLocale.textDirection()); qtTranslator->load("qt_" + defaultLocale.name(), QLibraryInfo::location(QLibraryInfo::TranslationsPath)); QApplication::installTranslator(qtTranslator); if (defaultLocale.name() == "C") { tsTranslator->load(localeName, QString(SHAREDIR) + "translations"); } else { tsTranslator->load(defaultLocale.name(), QString(SHAREDIR) + "translations"); } QApplication::installTranslator(tsTranslator); //Fill locale box Internationalisation::fillLanguageBox(ui->localeList); //Process all events QApplication::processEvents(); //Hide the splash screen since the language change is complete emit dbusSignals->HideSplash(); } void InfoPaneDropdown::on_StatusBarSwitch_toggled(bool checked) { settings.setValue("bar/statusBar", checked); updateStruts(); ui->AutoShowBarLabel->setEnabled(checked); ui->AutoShowBarSwitch->setEnabled(checked); ui->AutoShowBarExplanation->setEnabled(checked); } void InfoPaneDropdown::on_TouchInputSwitch_toggled(bool checked) { settings.setValue("input/touch", checked); } void InfoPaneDropdown::on_quietModeSound_clicked() { AudioMan->setQuietMode(AudioManager::none); ui->quietModeSound->setChecked(true); } void InfoPaneDropdown::on_quietModeNotification_clicked() { AudioMan->setQuietMode(AudioManager::notifications); ui->quietModeNotification->setChecked(true); } void InfoPaneDropdown::on_quietModeMute_clicked() { AudioMan->setQuietMode(AudioManager::mute); ui->quietModeMute->setChecked(true); } RemindersListModel::RemindersListModel(QObject *parent) : QAbstractListModel(parent) { RemindersData = new QSettings("theSuite/theShell.reminders"); RemindersData->beginGroup("reminders"); } RemindersListModel::~RemindersListModel() { RemindersData->endGroup(); RemindersData->deleteLater(); } int RemindersListModel::rowCount(const QModelIndex &parent) const { Q_UNUSED(parent) int count = RemindersData->beginReadArray("reminders"); RemindersData->endArray(); return count; } QVariant RemindersListModel::data(const QModelIndex &index, int role) const { QVariant returnValue; RemindersData->beginReadArray("reminders"); RemindersData->setArrayIndex(index.row()); if (role == Qt::DisplayRole) { returnValue = RemindersData->value("title"); } else if (role == Qt::UserRole) { QDateTime activation = RemindersData->value("date").toDateTime(); if (activation.daysTo(QDateTime::currentDateTime()) == 0) { returnValue = activation.toString("hh:mm"); } else if (activation.daysTo(QDateTime::currentDateTime()) < 7) { returnValue = activation.toString("dddd"); } else { returnValue = activation.toString("ddd, dd MMM yyyy"); } } RemindersData->endArray(); return returnValue; } void RemindersListModel::updateData() { emit dataChanged(index(0), index(rowCount())); } RemindersDelegate::RemindersDelegate(QWidget *parent) : QStyledItemDelegate(parent) { } void RemindersDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const { painter->setFont(option.font); QRect textRect; textRect.setLeft(6 * getDPIScaling()); textRect.setTop(option.rect.top() + 6 * getDPIScaling()); textRect.setBottom(option.rect.top() + option.fontMetrics.height() + 6 * getDPIScaling()); textRect.setRight(option.rect.right()); QRect dateRect; dateRect.setLeft(6 * getDPIScaling()); dateRect.setTop(option.rect.top() + option.fontMetrics.height() + 8 * getDPIScaling()); dateRect.setBottom(option.rect.top() + option.fontMetrics.height() * 2 + 6 * getDPIScaling()); dateRect.setRight(option.rect.right()); if (option.state & QStyle::State_Selected) { painter->setPen(Qt::transparent); painter->setBrush(option.palette.color(QPalette::Highlight)); painter->drawRect(option.rect); painter->setBrush(Qt::transparent); painter->setPen(option.palette.color(QPalette::HighlightedText)); painter->drawText(textRect, index.data().toString()); painter->drawText(dateRect, index.data(Qt::UserRole).toString()); } else if (option.state & QStyle::State_MouseOver) { QColor col = option.palette.color(QPalette::Highlight); col.setAlpha(127); painter->setBrush(col); painter->setPen(Qt::transparent); painter->drawRect(option.rect); painter->setBrush(Qt::transparent); painter->setPen(option.palette.color(QPalette::WindowText)); painter->drawText(textRect, index.data().toString()); painter->setPen(option.palette.color(QPalette::Disabled, QPalette::WindowText)); painter->drawText(dateRect, index.data(Qt::UserRole).toString()); } else { painter->setPen(option.palette.color(QPalette::WindowText)); painter->drawText(textRect, index.data().toString()); painter->setPen(option.palette.color(QPalette::Disabled, QPalette::WindowText)); painter->drawText(dateRect, index.data(Qt::UserRole).toString()); } } QSize RemindersDelegate::sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const { return QSize(option.fontMetrics.width(index.data().toString()), option.fontMetrics.height() * 2 + 14 * getDPIScaling()); } void InfoPaneDropdown::on_ReminderCancel_clicked() { ui->RemindersStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::on_ReminderNew_clicked() { ui->ReminderTitle->setText(""); ui->ReminderDate->setDateTime(QDateTime::currentDateTime().addSecs(3600)); //Current date + 1 hour ui->RemindersStackedWidget->setCurrentIndex(1); } void InfoPaneDropdown::on_ReminderCreate_clicked() { if (ui->ReminderTitle->text() == "") { return; } QList> ReminderData; QSettings reminders("theSuite/theShell.reminders"); reminders.beginGroup("reminders"); int count = reminders.beginReadArray("reminders"); for (int i = 0; i < count; i++) { reminders.setArrayIndex(i); QPair data; data.first = reminders.value("title").toString(); data.second = reminders.value("date").toDateTime(); ReminderData.append(data); } QPair newData; newData.first = ui->ReminderTitle->text(); newData.second = ui->ReminderDate->dateTime().addSecs(-ui->ReminderDate->dateTime().time().second()); ReminderData.append(newData); reminders.endArray(); reminders.beginWriteArray("reminders"); int i = 0; for (QPair data : ReminderData) { reminders.setArrayIndex(i); reminders.setValue("title", data.first); reminders.setValue("date", data.second); i++; } reminders.endArray(); reminders.endGroup(); ((RemindersListModel*) ui->RemindersList->model())->updateData(); ui->RemindersStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::on_SuspendLockScreen_toggled(bool checked) { settings.setValue("lockScreen/showOnSuspend", checked); } void InfoPaneDropdown::on_BatteryChargeScrollBar_valueChanged(int value) { if (!chartScrolling) { chartScrolling = true; batteryChart->scroll(value - startValue, 0); startValue = value; chartScrolling = false; } } void InfoPaneDropdown::on_chargeGraphButton_clicked() { ui->chargeGraphButton->setChecked(true); ui->rateGraphButton->setChecked(false); ui->appsGraphButton->setChecked(false); ui->batteryGraphStack->setCurrentIndex(0); ui->batteryChartHeader->setText(tr("Charge History")); ui->batteryChartShowProjected->setVisible(true); updateBatteryChart(); } void InfoPaneDropdown::on_rateGraphButton_clicked() { ui->chargeGraphButton->setChecked(false); ui->rateGraphButton->setChecked(true); ui->appsGraphButton->setChecked(false); ui->batteryGraphStack->setCurrentIndex(0); ui->batteryChartHeader->setText(tr("Rate History")); ui->batteryChartShowProjected->setVisible(false); updateBatteryChart(); } void InfoPaneDropdown::on_appsGraphButton_clicked() { ui->chargeGraphButton->setChecked(false); ui->rateGraphButton->setChecked(false); ui->appsGraphButton->setChecked(true); ui->batteryGraphStack->setCurrentIndex(1); ui->batteryChartHeader->setText(tr("Application Power Usage")); ui->batteryChartShowProjected->setVisible(false); updateBatteryChart(); } void InfoPaneDropdown::on_LargeTextSwitch_toggled(bool checked) { themeSettings->setValue("accessibility/largeText", checked); } void InfoPaneDropdown::on_HighContrastSwitch_toggled(bool checked) { themeSettings->setValue("accessibility/highcontrast", checked); setHeaderColour(QColor(0, 100, 255)); } void InfoPaneDropdown::on_systemAnimationsAccessibilitySwitch_toggled(bool checked) { themeSettings->setValue("accessibility/systemAnimations", checked); } void InfoPaneDropdown::on_CapsNumLockBellSwitch_toggled(bool checked) { themeSettings->setValue("accessibility/bellOnCapsNumLock", checked); } void InfoPaneDropdown::on_FlightSwitch_toggled(bool checked) { QDBusInterface i("org.freedesktop.NetworkManager", "/org/freedesktop/NetworkManager", "org.freedesktop.NetworkManager", QDBusConnection::systemBus(), this); //Set flags that persist between changes settings.setValue("flightmode/on", checked); if (checked) { settings.setValue("flightmode/wifi", ui->WifiSwitch->isChecked()); settings.setValue("flightmode/bt", ui->BluetoothSwitch->isChecked()); //Disable bluetooth and WiFi. ui->WifiSwitch->setChecked(false); ui->BluetoothSwitch->setChecked(false); //Disable WiMAX and mobile networking i.setProperty("WwanEnabled", false); i.setProperty("WimaxEnabled", false); } else { //Enable bluetooth and WiFi. ui->WifiSwitch->setChecked(settings.value("flightmode/wifi", true).toBool()); ui->BluetoothSwitch->setChecked(settings.value("flightmode/bt", true).toBool()); //Enable WiMAX and mobile networking i.setProperty("WwanEnabled", true); i.setProperty("WimaxEnabled", true); } emit flightModeChanged(checked); //Don't disable the switch as they may be switched on during flight } void InfoPaneDropdown::on_TwentyFourHourSwitch_toggled(bool checked) { settings.setValue("time/use24hour", checked); } void InfoPaneDropdown::on_systemIconTheme_currentIndexChanged(int index) { themeSettings->setValue("icons/theme", ui->systemIconTheme->itemData(index).toString()); } void InfoPaneDropdown::on_ReminderDelete_clicked() { if (ui->RemindersList->selectionModel()->selectedRows().count() != 0) { //Show delete screen ui->RemindersStackedWidget->setCurrentIndex(2); ui->deleteReminderText->setText(ui->RemindersList->model()->data(ui->RemindersList->selectionModel()->selectedRows().first()).toString()); ui->deleteReminderTime->setText(ui->RemindersList->model()->data(ui->RemindersList->selectionModel()->selectedRows().first(), Qt::UserRole).toString()); } } void InfoPaneDropdown::on_RemindersStackedWidget_currentChanged(int arg1) { tVariantAnimation* height = new tVariantAnimation(); height->setDuration(250); height->setEasingCurve(QEasingCurve::InOutCubic); height->setStartValue(ui->RemindersStackedWidget->height()); if (arg1 == 0) { height->setEndValue((int) (300 * getDPIScaling() - 10)); //ui->ClockScrollArea->verticalScrollBar()->setEnabled(true); ui->ClockScrollArea->setVerticalScrollBarPolicy(Qt::ScrollBarAsNeeded); } else { height->setEndValue(ui->ClockScrollArea->height() - 10); //ui->ClockScrollArea->verticalScrollBar()->setEnabled(false); ui->ClockScrollArea->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff); } connect(height, &tVariantAnimation::valueChanged, [=](QVariant value) { ui->RemindersStackedWidget->setFixedHeight(value.toInt()); ui->ClockScrollArea->verticalScrollBar()->setValue(ui->ClockScrollArea->verticalScrollBar()->maximum()); }); connect(height, &tVariantAnimation::finished, [=] { ui->ClockScrollArea->verticalScrollBar()->setValue(ui->ClockScrollArea->verticalScrollBar()->maximum()); }); connect(height, SIGNAL(finished()), height, SLOT(deleteLater())); height->start(); } void InfoPaneDropdown::on_ReminderDeleteCancel_clicked() { //Go back to normal screen ui->RemindersStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::on_ReminderDeleteButton_clicked() { QList> ReminderData; QSettings reminders("theSuite/theShell.reminders"); reminders.beginGroup("reminders"); int count = reminders.beginReadArray("reminders"); for (int i = 0; i < count; i++) { reminders.setArrayIndex(i); QPair data; data.first = reminders.value("title").toString(); data.second = reminders.value("date").toDateTime(); ReminderData.append(data); } reminders.endArray(); ReminderData.removeAt(ui->RemindersList->selectionModel()->selectedIndexes().at(0).row()); reminders.beginWriteArray("reminders"); int i = 0; for (QPair data : ReminderData) { reminders.setArrayIndex(i); reminders.setValue("title", data.first); reminders.setValue("date", data.second); i++; } reminders.endArray(); reminders.endGroup(); ((RemindersListModel*) ui->RemindersList->model())->updateData(); ui->RemindersStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::on_AttenuateSwitch_toggled(bool checked) { settings.setValue("notifications/attenuate", checked); } void InfoPaneDropdown::on_BarOnBottom_toggled(bool checked) { settings.setValue("bar/onTop", !checked); updateStruts(); } void InfoPaneDropdown::updateStruts() { emit updateStrutsSignal(); if (settings.value("bar/onTop", true).toBool()) { ((QBoxLayout*) this->layout())->setDirection(QBoxLayout::TopToBottom); ((QBoxLayout*) ui->partFrame->layout())->setDirection(QBoxLayout::TopToBottom); ((QBoxLayout*) ui->settingsFrame->layout())->setDirection(QBoxLayout::TopToBottom); ((QBoxLayout*) ui->kdeConnectFrame->layout())->setDirection(QBoxLayout::TopToBottom); ui->upArrow->setPixmap(QIcon::fromTheme("go-up").pixmap(16 * getDPIScaling(), 16 * getDPIScaling())); } else { ((QBoxLayout*) this->layout())->setDirection(QBoxLayout::BottomToTop); ((QBoxLayout*) ui->partFrame->layout())->setDirection(QBoxLayout::BottomToTop); ((QBoxLayout*) ui->settingsFrame->layout())->setDirection(QBoxLayout::BottomToTop); ((QBoxLayout*) ui->kdeConnectFrame->layout())->setDirection(QBoxLayout::BottomToTop); ui->upArrow->setPixmap(QIcon::fromTheme("go-down").pixmap(16 * getDPIScaling(), 16 * getDPIScaling())); } } void InfoPaneDropdown::on_systemWidgetTheme_currentIndexChanged(int index) { themeSettings->setValue("style/name", ui->systemWidgetTheme->itemData(index).toString()); resetStyle(); } void InfoPaneDropdown::resetStyle() { emit dbusSignals->ThemeChanged(); } void InfoPaneDropdown::on_decorativeColorThemeRadio_toggled(bool checked) { if (checked) { themeSettings->setValue("color/type", "decorative"); updateAccentColourBox(); resetStyle(); } } void InfoPaneDropdown::on_SoundFeedbackSoundSwitch_toggled(bool checked) { settings.setValue("sound/feedbackSound", checked); } void InfoPaneDropdown::on_VolumeOverdriveSwitch_toggled(bool checked) { settings.setValue("sound/volumeOverdrive", checked); } void InfoPaneDropdown::updateAccentColourBox() { //Set up theme button combo box int themeAccentColorIndex = themeSettings->value("color/accent", 0).toInt(); ui->themeButtonColor->clear(); if (themeSettings->value("color/type", "dark") == "decorative") { if (themeAccentColorIndex > 1) themeAccentColorIndex = 0; ui->themeButtonColor->addItem(tr("Oxygen")); ui->themeButtonColor->addItem(tr("Breeze")); } else { if (themeAccentColorIndex > 4) themeAccentColorIndex = 0; ui->themeButtonColor->addItem(tr("Blue")); ui->themeButtonColor->addItem(tr("Green")); ui->themeButtonColor->addItem(tr("Orange")); ui->themeButtonColor->addItem(tr("Pink")); ui->themeButtonColor->addItem(tr("Turquoise")); ui->themeButtonColor->setCurrentIndex(themeAccentColorIndex); } } void InfoPaneDropdown::on_dpi100_toggled(bool checked) { if (checked) { sessionSettings->setValue("screen/dpi", 96); } } void InfoPaneDropdown::on_dpi150_toggled(bool checked) { if (checked) { sessionSettings->setValue("screen/dpi", 144); } } void InfoPaneDropdown::on_dpi200_toggled(bool checked) { if (checked) { sessionSettings->setValue("screen/dpi", 192); } } void InfoPaneDropdown::on_dpi300_toggled(bool checked) { if (checked) { sessionSettings->setValue("screen/dpi", 288); } } void InfoPaneDropdown::on_AutoShowBarSwitch_toggled(bool checked) { settings.setValue("bar/autoshow", checked); } void InfoPaneDropdown::on_userSettingsAdminAccount_toggled(bool checked) { if (checked) { ui->userSettingsStandardAccount->setChecked(false); ui->userSettingsAdminAccount->setChecked(true); } } void InfoPaneDropdown::on_userSettingsStandardAccount_toggled(bool checked) { if (checked) { ui->userSettingsStandardAccount->setChecked(true); ui->userSettingsAdminAccount->setChecked(false); } } void InfoPaneDropdown::notificationAction(uint id, QString action) { if (id == timerNotificationId) { //Preserve old timer in case user wants to restart it QTime lastTimer = this->lastTimer; ringtone->stop(); AudioMan->restoreStreams(); timerNotificationId = 0; if (action == "+0.5") { startTimer(QTime(0, 0, 30)); } else if (action == "+1") { startTimer(QTime(0, 1)); } else if (action == "+2") { startTimer(QTime(0, 2)); } else if (action == "+5") { startTimer(QTime(0, 5)); } else if (action == "+10") { startTimer(QTime(0, 10)); } else if (action == "restart") { startTimer(lastTimer); } this->lastTimer = lastTimer; } } void InfoPaneDropdown::updateAutostart() { ui->autostartList->clear(); QDir autostartDir(QDir::homePath() + "/.config/autostart"); for (QString fileName : autostartDir.entryList(QDir::NoDotAndDotDot | QDir::Files)) { QString file = QDir::homePath() + "/.config/autostart/" + fileName; QFile autostartFile(file); autostartFile.open(QFile::ReadOnly); QString data = autostartFile.readAll(); autostartFile.close(); QString name = fileName; QString icon = ""; bool enabled = true; bool validEntry = true; for (QString line : data.split("\n")) { QString data = line.mid(line.indexOf("=") + 1); if (line.startsWith("name=", Qt::CaseInsensitive)) { name = data; } else if (line.startsWith("onlyshowin=", Qt::CaseInsensitive)) { if (!data.contains("theshell", Qt::CaseInsensitive)) { validEntry = false; } } else if (line.startsWith("notshowin=", Qt::CaseInsensitive)) { if (data.contains("theshell", Qt::CaseInsensitive)) { validEntry = false; } } else if (line.startsWith("hidden=", Qt::CaseInsensitive)) { if (data.toLower() == "true") { enabled = false; } } else if (line.startsWith("icon=")) { icon = data; } } if (validEntry) { QListWidgetItem* item = new QListWidgetItem(); item->setFlags(item->flags() | Qt::ItemIsUserCheckable); if (enabled) { item->setCheckState(Qt::Checked); } else { item->setCheckState(Qt::Unchecked); } if (icon != "") { item->setIcon(QIcon::fromTheme(icon)); } item->setText(name); item->setData(Qt::UserRole, file); ui->autostartList->addItem(item); } } } void InfoPaneDropdown::on_autostartList_itemChanged(QListWidgetItem *item) { QFile file(item->data(Qt::UserRole).toString()); file.open(QFile::ReadOnly); QString data = file.readAll(); file.close(); QString rewriteData; for (QString line : data.split("\n")) { if (!line.startsWith("hidden", Qt::CaseInsensitive)) { rewriteData.append(line + "\n"); } } if (item->checkState() == Qt::Unchecked) { rewriteData.append("Hidden=true\n"); } file.open(QFile::WriteOnly); file.write(rewriteData.toUtf8()); file.close(); this->updateAutostart(); } void InfoPaneDropdown::on_backAutoStartApps_clicked() { ui->startupStack->setCurrentIndex(0); } void InfoPaneDropdown::on_pushButton_4_clicked() { ui->startupStack->setCurrentIndex(1); AppsListModel* appsListModel = new AppsListModel(); ui->autostartAppList->setModel(appsListModel); ui->autostartAppList->setItemDelegate(new AppsDelegate(nullptr, false)); } void InfoPaneDropdown::on_backAutoStartNewApp_clicked() { ui->startupStack->setCurrentIndex(1); } void InfoPaneDropdown::on_autostartAppList_clicked(const QModelIndex &index) { App app = index.data(Qt::UserRole + 3).value(); ui->autostartAppName->setText(app.name()); ui->autostartAppCommand->setText(app.command().trimmed()); ui->autostartInTheshell->setChecked(false); ui->startupStack->setCurrentIndex(2); } void InfoPaneDropdown::on_enterCommandAutoStartApps_clicked() { ui->autostartAppName->setText(""); ui->autostartAppCommand->setText(""); ui->autostartInTheshell->setChecked(false); ui->startupStack->setCurrentIndex(2); } void InfoPaneDropdown::on_addAutostartApp_clicked() { QString desktopEntryData; desktopEntryData.append("[Desktop Entry]\n"); desktopEntryData.append("Type=Application\n"); desktopEntryData.append("Version=1.0\n"); desktopEntryData.append("Name=" + ui->autostartAppName->text() + "\n"); desktopEntryData.append("Exec=" + ui->autostartAppCommand->text() + "\n"); desktopEntryData.append("Terminal=false\n"); if (ui->autostartInTheshell->isChecked()) { desktopEntryData.append("OnlyShowIn=theshell;"); } QFile desktopEntry(QDir::homePath() + "/.config/autostart/" + ui->autostartAppName->text().toLower().replace(" ", "_").append(".desktop")); if (desktopEntry.exists()) { if (QMessageBox::warning(this, "Autostart Definition", "There is already an autostart definition for this app. Do you want to overwrite it?", QMessageBox::Yes | QMessageBox::No, QMessageBox::No) == QMessageBox::No) { return; } } desktopEntry.open(QFile::WriteOnly); desktopEntry.write(desktopEntryData.toUtf8()); desktopEntry.close(); updateAutostart(); ui->startupStack->setCurrentIndex(0); } void InfoPaneDropdown::on_redshiftSwitch_toggled(bool checked) { if (effectiveRedshiftOn) { if (checked) { //Turn Redshift back on overrideRedshift = 0; } else { //Temporarily disable Redshift overrideRedshift = 1; } } else { if (checked) { //Temporarily enable Redshift overrideRedshift = 2; } else { //Turn Redshift back off overrideRedshift = 0; } } } void InfoPaneDropdown::on_grayColorThemeRadio_toggled(bool checked) { if (checked) { themeSettings->setValue("color/type", "gray"); updateAccentColourBox(); resetStyle(); changeDropDown(Settings, false); } } void InfoPaneDropdown::on_AppNotifications_currentItemChanged(QListWidgetItem *current, QListWidgetItem *previous) { if (current == NULL) { ui->appNotificationsPane->setEnabled(false); ui->appNotificationsConfigureLock->setVisible(false); } else { ui->appNotificationsTitle->setText(tr("Notifications for %1").arg(current->text())); ui->appAllowNotifications->setChecked(notificationAppSettings->value(current->text() + "/allow", true).toBool()); ui->appAllowSounds->setChecked(notificationAppSettings->value(current->text() + "/sounds", true).toBool()); ui->appAllowPopup->setChecked(notificationAppSettings->value(current->text() + "/popup", true).toBool()); ui->appBypassQuiet->setChecked(notificationAppSettings->value(current->text() + "/bypassQuiet", false).toBool()); if (current->text() == "theShell") { ui->appNotificationsPane->setEnabled(false); ui->appNotificationsConfigureLock->setText(tr("You can't configure notifications for %1").arg(current->text())); ui->appNotificationsConfigureLock->setVisible(true); } else { ui->appNotificationsPane->setEnabled(true); ui->appNotificationsConfigureLock->setVisible(false); } } } void InfoPaneDropdown::on_appAllowNotifications_toggled(bool checked) { if (ui->AppNotifications->currentItem() != NULL) { notificationAppSettings->setValue(ui->AppNotifications->currentItem()->text() + "/allow", checked); } } void InfoPaneDropdown::on_appAllowSounds_toggled(bool checked) { if (ui->AppNotifications->currentItem() != NULL) { notificationAppSettings->setValue(ui->AppNotifications->currentItem()->text() + "/sounds", checked); } } void InfoPaneDropdown::on_appAllowPopup_toggled(bool checked) { if (ui->AppNotifications->currentItem() != NULL) { notificationAppSettings->setValue(ui->AppNotifications->currentItem()->text() + "/popup", checked); } } void InfoPaneDropdown::on_appBypassQuiet_toggled(bool checked) { if (ui->AppNotifications->currentItem() != NULL) { notificationAppSettings->setValue(ui->AppNotifications->currentItem()->text() + "/bypassQuiet", checked); } } void InfoPaneDropdown::on_SetSystemTimezoneButton_clicked() { ui->TimezoneStackedWidget->setCurrentIndex(1); launchDateTimeService(); QDBusInterface dateTimeInterface("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", QDBusConnection::systemBus()); QString currentTimezone = dateTimeInterface.property("Timezone").toString(); timezoneData = QJsonObject(); ui->timezoneList->clear(); QFile tzInfo("/usr/share/zoneinfo/zone.tab"); tzInfo.open(QFile::ReadOnly); while (!tzInfo.atEnd()) { QString tzLine = tzInfo.readLine(); if (!tzLine.startsWith("#")) { QStringList parts = tzLine.trimmed().split("\t", QString::SkipEmptyParts); if (parts.length() >= 3) { QString region = parts.at(2).left(parts.at(2).indexOf("/")); QString city = parts.at(2).mid(parts.at(2).indexOf("/") + 1); if (!timezoneData.contains(region)) { QListWidgetItem* i = new QListWidgetItem(); i->setText(region); ui->timezoneList->addItem(i); timezoneData.insert(region, QJsonArray()); } QJsonObject cityData; cityData.insert("name", city); cityData.insert("country", parts.at(0).toLower()); cityData.insert("descriptor", parts.at(2)); if (parts.at(2) == currentTimezone) { cityData.insert("selected", true); } else { cityData.insert("selected", false); } QJsonArray a = timezoneData.value(region).toArray(); a.append(cityData); timezoneData.insert(region, a); } } } tzInfo.close(); ui->setTimezoneButton->setEnabled(false); ui->timezoneCityList->clear(); } void InfoPaneDropdown::on_backTimezone_clicked() { ui->TimezoneStackedWidget->setCurrentIndex(0); } void InfoPaneDropdown::on_setTimezoneButton_clicked() { ui->TimezoneStackedWidget->setCurrentIndex(0); //Set the timezone LOWER_INFOPANE launchDateTimeService(); QDBusInterface dateTimeInterface("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", QDBusConnection::systemBus()); QDBusPendingCallWatcher* w = new QDBusPendingCallWatcher(dateTimeInterface.asyncCall("SetTimezone", ui->timezoneCityList->currentItem()->data(Qt::UserRole), true)); connect(w, SIGNAL(finished(QDBusPendingCallWatcher*)), w, SLOT(deleteLater())); connect(w, SIGNAL(finished(QDBusPendingCallWatcher*)), this, SLOT(updateDSTNotification())); } void InfoPaneDropdown::on_timezoneList_currentItemChanged(QListWidgetItem *current, QListWidgetItem *previous) { ui->timezoneCityList->clear(); if (current != NULL) { QJsonArray a = timezoneData.value(current->text()).toArray(); for (QJsonValue v : a) { QListWidgetItem* i = new QListWidgetItem(); QJsonObject cityData = v.toObject(); i->setText(cityData.value("name").toString().replace("_", " ")); i->setData(Qt::UserRole, cityData.value("descriptor").toString()); i->setIcon(QIcon::fromTheme("flag-" + cityData.value("country").toString(), QIcon::fromTheme("flag"))); ui->timezoneCityList->addItem(i); if (cityData.value("selected").toBool()) { i->setSelected(true); } } } } void InfoPaneDropdown::on_timezoneCityList_currentRowChanged(int currentRow) { if (currentRow == -1) { ui->setTimezoneButton->setEnabled(false); } else { ui->setTimezoneButton->setEnabled(true); } } void InfoPaneDropdown::on_batteryScreenOff_valueChanged(int value) { settings.setValue("power/batteryScreenOff", value); if (value == 121) { ui->batteryScreenOffLabel->setText(tr("Never")); } else { ui->batteryScreenOffLabel->setText(tr("%n min(s)", NULL, value).arg(QString::number(value))); } } void InfoPaneDropdown::on_batterySuspend_valueChanged(int value) { settings.setValue("power/batterySuspend", value); if (value == 121) { ui->batterySuspendLabel->setText(tr("Never")); } else { ui->batterySuspendLabel->setText(tr("%n min(s)", NULL, value).arg(QString::number(value))); } } void InfoPaneDropdown::on_powerScreenOff_valueChanged(int value) { settings.setValue("power/powerScreenOff", value); if (value == 121) { ui->powerScreenOffLabel->setText(tr("Never")); } else { ui->powerScreenOffLabel->setText(tr("%n min(s)", NULL, value).arg(QString::number(value))); } } void InfoPaneDropdown::on_powerSuspend_valueChanged(int value) { settings.setValue("power/powerSuspend", value); if (value == 121) { ui->powerSuspendLabel->setText(tr("Never")); } else { ui->powerSuspendLabel->setText(tr("%n min(s)", NULL, value).arg(QString::number(value))); } } void InfoPaneDropdown::on_quietModeExpandButton_clicked() { tVariantAnimation* anim = new tVariantAnimation(); anim->setStartValue(ui->quietModeExtras->height()); if (ui->quietModeExtras->height() == 0) { anim->setEndValue(ui->quietModeExtras->sizeHint().height()); ui->quietModeExpandButton->setIcon(QIcon::fromTheme("go-up")); } else { anim->setEndValue(0); ui->quietModeExpandButton->setIcon(QIcon::fromTheme("go-down")); } anim->setDuration(500); anim->setEasingCurve(QEasingCurve::OutCubic); connect(anim, SIGNAL(finished()), anim, SLOT(deleteLater())); connect(anim, &tVariantAnimation::valueChanged, [=](QVariant value) { ui->quietModeExtras->setFixedHeight(value.toInt()); }); anim->start(); } void InfoPaneDropdown::on_quietModeForeverButton_toggled(bool checked) { if (checked) { ui->quietModeTurnOffAtTimer->setVisible(false); ui->quietModeTurnOffInTimer->setVisible(false); AudioMan->setQuietModeResetTime(QDateTime::fromString("")); } } void InfoPaneDropdown::on_quietModeTurnOffIn_toggled(bool checked) { if (checked) { ui->quietModeTurnOffAtTimer->setVisible(false); ui->quietModeTurnOffInTimer->setVisible(true); QDateTime oneHour = QDateTime::currentDateTime().addSecs(3600); AudioMan->setQuietModeResetTime(oneHour); ui->quietModeTurnOffInTimer->setTime(QTime(1, 0)); } } void InfoPaneDropdown::on_quietModeTurnOffAt_toggled(bool checked) { if (checked) { ui->quietModeTurnOffAtTimer->setVisible(true); ui->quietModeTurnOffInTimer->setVisible(false); QDateTime oneHour = QDateTime::currentDateTime().addSecs(3600); AudioMan->setQuietModeResetTime(oneHour); ui->quietModeTurnOffAtTimer->setDateTime(oneHour); } } void InfoPaneDropdown::on_quietModeTurnOffAtTimer_editingFinished() { AudioMan->setQuietModeResetTime(ui->quietModeTurnOffAtTimer->dateTime()); } void InfoPaneDropdown::on_quietModeTurnOffInTimer_editingFinished() { QDateTime timeout = QDateTime::currentDateTime().addMSecs(ui->quietModeTurnOffInTimer->time().msecsSinceStartOfDay()); AudioMan->setQuietModeResetTime(timeout); } void InfoPaneDropdown::on_removeAutostartButton_clicked() { if (ui->autostartList->currentItem() != nullptr) { tToast* toast = new tToast(); toast->setText("Autostart item has been removed."); toast->setTitle("Remove Autostart Item"); QMap actions; actions.insert("undo", "Undo"); toast->setActions(actions); QListWidgetItem* i = ui->autostartList->takeItem(ui->autostartList->currentIndex().row()); bool* deleteItem = new bool(true); connect(toast, &tToast::dismissed, [=] { if (*deleteItem) { QFile(i->data(Qt::UserRole).toString()).remove(); delete i; } delete deleteItem; toast->deleteLater(); }); connect(toast, &tToast::actionClicked, [=](QString key) { *deleteItem = false; ui->autostartList->addItem(i); }); toast->show(this); } } void InfoPaneDropdown::on_resetDeviceButton_clicked() { QProcess::startDetached("scallop --reset"); this->close(); } void InfoPaneDropdown::changeEvent(QEvent *event) { if (event->type() == QEvent::LanguageChange) { ui->retranslateUi(this); } QDialog::changeEvent(event); } void InfoPaneDropdown::on_sunlightRedshift_toggled(bool checked) { settings.setValue("display/redshiftSunlightCycle", checked); updateRedshiftTime(); } void InfoPaneDropdown::updateRedshiftTime() { if (!settings.value("display/redshiftSunlightCycle", false).toBool()) { //Don't grab location if user doesn't want ui->startRedshift->setEnabled(true); ui->endRedshift->setEnabled(true); return; } ui->startRedshift->setEnabled(false); ui->endRedshift->setEnabled(false); QDBusMessage getMessage = QDBusMessage::createMethodCall("org.freedesktop.DBus", "/", "org.freedesktop.DBus", "ListActivatableNames"); QDBusReply reply = QDBusConnection::systemBus().call(getMessage); if (!reply.value().contains("org.freedesktop.GeoClue2")) { qDebug() << "Can't start GeoClue"; return; } QDBusMessage launchMessage = QDBusMessage::createMethodCall("org.freedesktop.DBus", "/", "org.freedesktop.DBus", "StartServiceByName"); QVariantList args; args.append("org.freedesktop.GeoClue2"); args.append((uint) 0); launchMessage.setArguments(args); QDBusConnection::systemBus().call(launchMessage); QDBusMessage clientMessage = QDBusMessage::createMethodCall("org.freedesktop.GeoClue2", "/org/freedesktop/GeoClue2/Manager", "org.freedesktop.GeoClue2.Manager", "GetClient"); QDBusReply clientPathReply = QDBusConnection::systemBus().call(clientMessage); geoclueClientPath = clientPathReply.value(); QDBusInterface clientInterface("org.freedesktop.GeoClue2", geoclueClientPath.path(), "org.freedesktop.GeoClue2.Client", QDBusConnection::systemBus()); clientInterface.setProperty("DesktopId", "theshell"); QDBusConnection::systemBus().connect(clientInterface.service(), geoclueClientPath.path(), clientInterface.interface(), "LocationUpdated", this, SLOT(updateGeoclueLocation())); clientInterface.call("Start"); } void InfoPaneDropdown::updateGeoclueLocation() { QDBusInterface clientInterface("org.freedesktop.GeoClue2", geoclueClientPath.path(), "org.freedesktop.GeoClue2.Client", QDBusConnection::systemBus()); QDBusObjectPath locationPath = clientInterface.property("Location").value(); QDBusInterface locationInterface("org.freedesktop.GeoClue2", locationPath.path(), "org.freedesktop.GeoClue2.Location", QDBusConnection::systemBus()); double latitude = locationInterface.property("Latitude").toDouble(); double longitude = locationInterface.property("Longitude").toDouble(); QNetworkAccessManager* manager = new QNetworkAccessManager(); QNetworkRequest sunriseApi(QUrl(QString("https://api.sunrise-sunset.org/json?lat=%1&lng=%2&formatted=0").arg(latitude).arg(longitude))); sunriseApi.setHeader(QNetworkRequest::UserAgentHeader, QString("theShell/%1").arg(TS_VERSION)); QNetworkReply* reply = manager->get(sunriseApi); connect(reply, QOverload::of(&QNetworkReply::error), [=](QNetworkReply::NetworkError code){ qDebug() << "Error"; }); connect(reply, &QNetworkReply::finished, [=] { QJsonDocument doc = QJsonDocument::fromJson(reply->readAll()); QJsonObject root = doc.object(); if (root.value("status").toString() != "OK") { qDebug() << root.value("status").toString(); return; } //The time returned should be midway into the transition period, add/remove 30 minutes to compensate QJsonObject results = root.value("results").toObject(); QDateTime sunrise = QDateTime::fromString(results.value("sunrise").toString(), Qt::ISODate).toLocalTime().addSecs(-1800); QDateTime sunset = QDateTime::fromString(results.value("sunset").toString(), Qt::ISODate).toLocalTime().addSecs(1800); ui->startRedshift->setDateTime(sunset); ui->endRedshift->setDateTime(sunrise); reply->deleteLater(); manager->deleteLater(); }); clientInterface.call("Stop"); } void InfoPaneDropdown::paintEvent(QPaintEvent *event) { QPainter painter(this); painter.setPen(this->palette().color(QPalette::WindowText)); if (settings.value("bar/onTop", true).toBool()) { painter.drawLine(0, this->height() - 1, this->width(), this->height() - 1); } else { painter.drawLine(0, 0, this->width(), 0); } event->accept(); } void InfoPaneDropdown::on_systemGTK3Theme_currentIndexChanged(int index) { gtk3Settings->setValue("Settings/gtk-theme-name", ui->systemGTK3Theme->itemText(index)); } void InfoPaneDropdown::on_systemFontSize_valueChanged(int arg1) { themeSettings->setValue("font/defaultSize", arg1); } void InfoPaneDropdown::on_systemGTK3Font_currentFontChanged(const QFont &f) { gtk3Settings->setValue("Settings/gtk-font-name", f.family() + " " + QString::number(ui->systemGTK3FontSize->value())); } void InfoPaneDropdown::on_systemGTK3FontSize_valueChanged(int arg1) { gtk3Settings->setValue("Settings/gtk-font-name", ui->systemGTK3Font->currentFont().family() + " " + QString::number(arg1)); } void InfoPaneDropdown::on_useSystemFontForGTKButton_clicked() { ui->systemGTK3Font->setCurrentFont(ui->systemFont->currentFont()); ui->systemGTK3FontSize->setValue(ui->systemFontSize->value()); } void InfoPaneDropdown::setHeaderColour(QColor col) { if (ui->HighContrastSwitch->isChecked()) { ui->partFrame->setPalette(QApplication::palette(ui->partFrame)); } else { QPalette pal = ui->partFrame->palette(); tVariantAnimation* anim = new tVariantAnimation(); anim->setStartValue(pal.color(QPalette::Window)); anim->setEndValue(col); anim->setDuration(250); anim->setEasingCurve(QEasingCurve::OutCubic); connect(anim, &tVariantAnimation::valueChanged, [=](QVariant value) { QPalette pal = ui->partFrame->palette(); QColor col = value.value(); pal.setColor(QPalette::Window, col); //if ((col.red() + col.green() + col.blue()) / 3 < 127) { pal.setColor(QPalette::WindowText, Qt::white); pal.setColor(QPalette::Disabled, QPalette::WindowText, col.lighter(150)); /*} else { pal.setColor(QPalette::WindowText, Qt::black); pal.setColor(QPalette::Disabled, QPalette::WindowText, col.darker(150)); }*/ ui->partFrame->setPalette(pal); pal.setColor(QPalette::Window, col.lighter(120)); ui->pushButton_7->setPalette(pal); ui->clockLabel->setShowDisabled(ui->clockLabel->showDisabled()); ui->batteryLabel->setShowDisabled(ui->batteryLabel->showDisabled()); ui->networkLabel->setShowDisabled(ui->networkLabel->showDisabled()); ui->notificationsLabel->setShowDisabled(ui->notificationsLabel->showDisabled()); ui->kdeconnectLabel->setShowDisabled(ui->kdeconnectLabel->showDisabled()); }); connect(anim, SIGNAL(finished()), anim, SLOT(deleteLater())); anim->start(); } } bool InfoPaneDropdown::eventFilter(QObject *obj, QEvent *e) { if (obj == ui->partFrame) { if (e->type() == QEvent::Paint) { QPainter p(ui->partFrame); QPalette pal = ui->partFrame->palette(); p.setRenderHint(QPainter::Antialiasing); p.setBrush(pal.color(QPalette::Window)); p.setPen(Qt::transparent); p.drawRect(0, 0, ui->partFrame->width(), ui->partFrame->height()); if (QApplication::layoutDirection() == Qt::RightToLeft) { int width = ui->partFrame->width(); QPolygonF firstPoly; firstPoly.append(QPointF(width - slice1.currentValue().toFloat(), 0)); firstPoly.append(QPointF(width - slice2.currentValue().toFloat(), ui->partFrame->height())); firstPoly.append(QPointF(0, ui->partFrame->height())); firstPoly.append(QPointF(0, 0)); p.setBrush(pal.color(QPalette::Window).lighter(110)); p.drawPolygon(firstPoly); QPolygonF secondPoly; secondPoly.append(QPointF(width - ui->partFrame->width() * 0.85, 0)); secondPoly.append(QPointF(width - ui->partFrame->width() * 0.825, ui->partFrame->height())); secondPoly.append(QPointF(0, ui->partFrame->height())); secondPoly.append(QPointF(0, 0)); p.setBrush(pal.color(QPalette::Window).lighter(120)); p.drawPolygon(secondPoly); } else { QPolygonF firstPoly; firstPoly.append(QPointF(slice1.currentValue().toFloat(), 0)); firstPoly.append(QPointF(slice2.currentValue().toFloat(), ui->partFrame->height())); firstPoly.append(QPointF(ui->partFrame->width(), ui->partFrame->height())); firstPoly.append(QPointF(ui->partFrame->width(), 0)); p.setBrush(pal.color(QPalette::Window).lighter(110)); p.drawPolygon(firstPoly); QPolygonF secondPoly; secondPoly.append(QPointF(ui->partFrame->width() * 0.85, 0)); secondPoly.append(QPointF(ui->partFrame->width() * 0.825, ui->partFrame->height())); secondPoly.append(QPointF(ui->partFrame->width(), ui->partFrame->height())); secondPoly.append(QPointF(ui->partFrame->width(), 0)); p.setBrush(pal.color(QPalette::Window).lighter(120)); p.drawPolygon(secondPoly); } return true; } } return false; } void InfoPaneDropdown::on_EmphasiseAppSwitch_toggled(bool checked) { settings.setValue("notifications/emphasiseApp", checked); } void InfoPaneDropdown::on_CompactBarSwitch_toggled(bool checked) { if (settings.value("bar/compact") != checked) { settings.setValue("bar/compact", checked); QMap actions; actions.insert("logout", tr("Log Out Now")); tToast* t = new tToast(); t->setTitle(tr("Logoff Required")); if (checked) { t->setText(tr("In order to enable the Compact Bar, you'll need to log out and then log back on.")); } else { t->setText(tr("In order to disable the Compact Bar, you'll need to log out and then log back on.")); } t->setActions(actions); t->setTimeout(10000); connect(t, &tToast::actionClicked, [=](QString key) { if (key == "logout") { EndSession(EndSessionWait::logout); } }); connect(t, SIGNAL(dismissed()), t, SLOT(deleteLater())); t->show(this); } } void InfoPaneDropdown::keyPressEvent(QKeyEvent *event) { } void InfoPaneDropdown::updateDSTNotification() { launchDateTimeService(); QDBusInterface dateTimeInterface("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", QDBusConnection::systemBus()); QString currentTimezone = dateTimeInterface.property("Timezone").toString(); QString timezoneInfoPath = "/usr/share/zoneinfo/" + currentTimezone; QProcess* timezoneProcess = new QProcess(); connect(timezoneProcess, QOverload::of(&QProcess::finished), [=](int exitCode, QProcess::ExitStatus exitStatus) { timezoneProcess->deleteLater(); struct Changeover { QDateTime changeoverDate; bool isDST; int gmtOffset; }; QList changeovers; while (!timezoneProcess->atEnd()) { QStringList parts = QString(timezoneProcess->readLine()).split(" ", QString::SkipEmptyParts); if (parts.length() == 16) { QStringList dateText; dateText.append(parts.at(4)); //dateText.append(parts.at(2)); //I am so sorry :( if (parts.at(2) == "Jan") { dateText.append("01"); } else if (parts.at(2) == "Feb") { dateText.append("02"); } else if (parts.at(2) == "Mar") { dateText.append("03"); } else if (parts.at(2) == "Apr") { dateText.append("04"); } else if (parts.at(2) == "May") { dateText.append("05"); } else if (parts.at(2) == "Jun") { dateText.append("06"); } else if (parts.at(2) == "Jul") { dateText.append("07"); } else if (parts.at(2) == "Aug") { dateText.append("08"); } else if (parts.at(2) == "Sep") { dateText.append("09"); } else if (parts.at(2) == "Oct") { dateText.append("10"); } else if (parts.at(2) == "Nov") { dateText.append("11"); } else if (parts.at(2) == "Dec") { dateText.append("12"); } dateText.append(parts.at(5)); dateText.append(parts.at(3)); Changeover c; QString dateConnectedText = dateText.join(" "); c.changeoverDate = QDateTime::fromString(dateConnectedText, "hh:mm:ss MM yyyy d"); c.changeoverDate.setTimeSpec(Qt::UTC); c.isDST = parts.at(14).endsWith("1"); c.gmtOffset = parts.at(15).mid(7).toInt(); changeovers.append(c); } } bool showDaylightSavingsPanel = false; Changeover changeover; QDateTime current = QDateTime::currentDateTimeUtc(); QDateTime currentLocal = QDateTime::currentDateTime(); for (int i = 0; i < changeovers.count(); i++) { Changeover c = changeovers.at(i); int days = current.daysTo(c.changeoverDate); if (days > 0 && days < 14) { if ((currentLocal.isDaylightTime() && !c.isDST) || (!currentLocal.isDaylightTime() && c.isDST)) { showDaylightSavingsPanel = true; changeover = c; } } } if (showDaylightSavingsPanel) { ui->dstPanel->setVisible(true); ui->dstLabel->setText(tr("On %1, Daylight Savings Time will %2. The clock will automatically adjust %3 by %n hour(s).", nullptr, 1) .arg(QLocale().toString(changeover.changeoverDate.toLocalTime(), "ddd dd MMM yyyy")) //: This is used during Daylight Savings notifications and will appear as "On [date], Daylight Savings Time will (begin|end)". .arg(currentLocal.isDaylightTime() ? tr("end", "Context: \"Daylight Savings Time will end.\"") : tr("begin", "Context: \"Daylight Savings Time will begin.\"")) //: This is used during Daylight Savings notifications and will appear as "The clock will automatically adjust (forwards|backwards) by [hours] hour(s).". .arg(currentLocal.isDaylightTime() ? tr("backwards", "Context: \"The clock will automatically adjust backwards\"") : tr("forwards", "Context: \"The clock will automatically adjust forwards\""))); } else { ui->dstPanel->setVisible(false); } }); timezoneProcess->start("zdump -v " + timezoneInfoPath); } void InfoPaneDropdown::on_blackColorThemeRadio_toggled(bool checked) { if (checked) { themeSettings->setValue("color/type", "black"); updateAccentColourBox(); resetStyle(); changeDropDown(Settings, false); } } void InfoPaneDropdown::changeSettingsPane(int pane) { ui->settingsList->setCurrentRow(pane); } void InfoPaneDropdown::on_allowGeoclueAgent_clicked() { //Automatically edit the geoclue file LOWER_INFOPANE QProcess::execute("pkexec sed \"/whitelist=.*/ s/$/;theshell/\" -i /etc/geoclue/geoclue.conf"); locationServices->reloadAuthorizationRequired(); QTimer::singleShot(500, [=] { on_settingsList_currentRowChanged(6); }); } void InfoPaneDropdown::on_LocationMasterSwitch_toggled(bool checked) { locationSettings->setValue("master/master", checked); } void InfoPaneDropdown::setupLocationSettingsPane() { if (locationServices->requiresAuthorization()) { ui->locationStack->setCurrentIndex(0); } else { ui->locationStack->setCurrentIndex(1); ui->LocationAppsList->clear(); QStringList availableApps = locationSettings->childGroups(); availableApps.removeOne("master"); for (QString app : availableApps) { locationSettings->beginGroup(app); bool allow = locationSettings->value("allow").toBool(); App a = App::invalidApp(); if (QFile("/usr/share/applications/" + app + ".desktop").exists()) { a = AppsListModel::readAppFile("/usr/share/applications/" + app + ".desktop"); } else if (QFile(QDir::homePath() + "/.local/share/applications" + app + ".desktop").exists()) { a = AppsListModel::readAppFile(QDir::homePath() + "/.local/share/applications" + app + ".desktop"); } QListWidgetItem* i = new QListWidgetItem(); if (a.invalid()) { i->setText(app); } else { i->setIcon(a.icon()); i->setText(a.name()); } i->setFlags(i->flags() | Qt::ItemIsUserCheckable); if (allow) { i->setCheckState(Qt::Checked); } else { i->setCheckState(Qt::Unchecked); } i->setData(Qt::UserRole, app); ui->LocationAppsList->addItem(i); locationSettings->endGroup(); } } } void InfoPaneDropdown::on_LocationAppsList_itemChanged(QListWidgetItem *item) { if (item->checkState() == Qt::Checked) { locationSettings->setValue(item->data(Qt::UserRole).toString() + "/allow", true); } else { locationSettings->setValue(item->data(Qt::UserRole).toString() + "/allow", false); } } void InfoPaneDropdown::on_backInput_clicked() { ui->InputStack->setCurrentIndex(0); } void InfoPaneDropdown::on_addLayout_clicked() { ui->InputStack->setCurrentIndex(1); } void InfoPaneDropdown::on_addKeyboardLayout_clicked() { QListWidgetItem* item = ui->availableKeyboardLayouts->currentItem(); QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); currentLayouts.append(item->data(Qt::UserRole).toString()); QListWidgetItem* newItem = new QListWidgetItem(); newItem->setText(item->text()); newItem->setData(Qt::UserRole, item->data(Qt::UserRole)); ui->selectedLayouts->addItem(newItem); settings.setValue("input/layout", currentLayouts.join(",")); ui->InputStack->setCurrentIndex(0); loadNewKeyboardLayoutMenu(); } void InfoPaneDropdown::on_removeLayout_clicked() { QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); int item = ui->selectedLayouts->currentRow(); currentLayouts.removeAt(item); QListWidgetItem* i = ui->selectedLayouts->takeItem(item); delete i; settings.setValue("input/layout", currentLayouts.join(",")); loadNewKeyboardLayoutMenu(); } void InfoPaneDropdown::on_selectedLayouts_currentItemChanged(QListWidgetItem *current, QListWidgetItem *previous) { if (current == nullptr) { ui->removeLayout->setEnabled(false); } else if (ui->selectedLayouts->count() == 1) { ui->removeLayout->setEnabled(false); } else { ui->removeLayout->setEnabled(true); } } void InfoPaneDropdown::on_availableKeyboardLayouts_currentItemChanged(QListWidgetItem *current, QListWidgetItem *previous) { if (current == nullptr) { ui->addKeyboardLayout->setEnabled(false); } else { ui->addKeyboardLayout->setEnabled(true); } } void InfoPaneDropdown::KeyboardLayoutsMoved() { //Completely recreate the selected layouts QStringList currentLayouts; for (int i = 0; i < ui->selectedLayouts->count(); i++) { QListWidgetItem* item = ui->selectedLayouts->item(i); currentLayouts.append(item->data(Qt::UserRole).toString()); } settings.setValue("input/layout", currentLayouts.join(",")); loadNewKeyboardLayoutMenu(); } void InfoPaneDropdown::on_moveLayoutDown_clicked() { int row = ui->selectedLayouts->currentRow(); if (row <= ui->selectedLayouts->count() - 1) { ui->selectedLayouts->clearSelection(); QListWidgetItem* item = ui->selectedLayouts->takeItem(row); ui->selectedLayouts->insertItem(row + 1, item); item->setSelected(true); } QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); QString layout = currentLayouts.takeAt(row); currentLayouts.insert(row + 1, layout); settings.setValue("input/layout", currentLayouts.join(",")); loadNewKeyboardLayoutMenu(); } void InfoPaneDropdown::on_moveLayoutUp_clicked() { int row = ui->selectedLayouts->currentRow(); if (row > 0) { ui->selectedLayouts->clearSelection(); QListWidgetItem* item = ui->selectedLayouts->takeItem(row); ui->selectedLayouts->insertItem(row - 1, item); item->setSelected(true); } QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); QString layout = currentLayouts.takeAt(row); currentLayouts.insert(row - 1, layout); settings.setValue("input/layout", currentLayouts.join(",")); loadNewKeyboardLayoutMenu(); } void InfoPaneDropdown::loadNewKeyboardLayoutMenu() { //Check to see if current keyboard layout is included in list, and if not, select first QString currentLayout = settings.value("input/currentLayout", "us(basic)").toString(); QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); if (!currentLayouts.contains(currentLayout)) { setKeyboardLayout(currentLayouts.first()); return; } if (ui->selectedLayouts->count() == 1) { emit newKeyboardLayoutMenuAvailable(nullptr); } else { QMenu* menu = new QMenu(); menu->addSection(tr("Keyboard Layout")); for (int i = 0; i < ui->selectedLayouts->count(); i++) { QListWidgetItem* item = ui->selectedLayouts->item(i); QAction* action = menu->addAction(item->text(), [=] { setKeyboardLayout(item->data(Qt::UserRole).toString()); }); action->setCheckable(true); if (item->data(Qt::UserRole) == currentLayout) { action->setChecked(true); } } emit newKeyboardLayoutMenuAvailable(menu); } QApplication::processEvents(); } void InfoPaneDropdown::setKeyboardLayout(QString layout) { settings.setValue("input/currentLayout", layout); QProcess::startDetached("setxkbmap " + layout); loadNewKeyboardLayoutMenu(); emit keyboardLayoutChanged(layout.split("(").first().toUpper()); } QString InfoPaneDropdown::setNextKeyboardLayout() { QString currentLayout = settings.value("input/currentLayout", "us(basic)").toString(); QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); int currentIndex = currentLayouts.indexOf(currentLayout); currentIndex++; if (currentIndex == currentLayouts.count()) currentIndex = 0; QString layout = currentLayouts.at(currentIndex); QTimer::singleShot(0, [=] { setKeyboardLayout(layout); }); for (int i = 0; i < ui->selectedLayouts->count(); i++) { if (ui->selectedLayouts->item(i)->data(Qt::UserRole) == layout) { return ui->selectedLayouts->item(i)->text(); } } } void InfoPaneDropdown::on_setupMousePassword_clicked() { //Check Polkit authorization PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.thesuite.theshell.configure-mouse-password", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::None); if (r == PolkitQt1::Authority::No) { QMessageBox::warning(this, tr("Unauthorized"), tr("Polkit does not allow you to set up a mouse password."), QMessageBox::Ok, QMessageBox::Ok); return; } else if (r == PolkitQt1::Authority::Challenge) { LOWER_INFOPANE PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.thesuite.theshell.configure-mouse-password", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::AllowUserInteraction); if (r != PolkitQt1::Authority::Yes) { return; } } ui->lockScreenStack->setCurrentIndex(1); } void InfoPaneDropdown::on_removeMousePassword_clicked() { if (QMessageBox::question(this, tr("Remove Mouse Password?"), tr("Do you want to remove the Mouse Password for this account?"), QMessageBox::Yes | QMessageBox::No, QMessageBox::No) == QMessageBox::Yes) { //Check Polkit authorization PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.thesuite.theshell.configure-mouse-password", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::None); if (r == PolkitQt1::Authority::No) { QMessageBox::warning(this, tr("Unauthorized"), tr("Polkit does not allow you to set up a mouse password."), QMessageBox::Ok, QMessageBox::Ok); return; } else if (r == PolkitQt1::Authority::Challenge) { LOWER_INFOPANE PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.thesuite.theshell.configure-mouse-password", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::AllowUserInteraction); if (r != PolkitQt1::Authority::Yes) { return; } } //Remove the mouse password QProcess* proc = new QProcess(); QDir::home().mkdir(".theshell"); QString executable = "/usr/lib/ts-mousepass-change"; #ifdef BLUEPRINT executable += "b"; #elif defined(CONSTRUCTION) executable += "c"; #endif proc->start(executable + " --remove --passfile=" + QDir::homePath() + "/.theshell/mousepassword"); proc->waitForFinished(); if (proc->exitCode() == 0) { tToast* toast = new tToast(); toast->setTitle(tr("Mouse Password")); toast->setText(tr("Mouse Password was removed successfully")); connect(toast, SIGNAL(dismissed()), toast, SLOT(deleteLater())); toast->show(this); } else { tToast* toast = new tToast(); toast->setTitle(tr("Mouse Password")); toast->setText(tr("Mouse Password couldn't be removed")); connect(toast, SIGNAL(dismissed()), toast, SLOT(deleteLater())); toast->show(this); } proc->deleteLater(); } } void InfoPaneDropdown::on_MousePasswordSetup_exit() { ui->lockScreenStack->setCurrentIndex(0); if (QFile(QDir::homePath() + "/.theshell/mousepassword").exists()) { ui->removeMousePassword->setVisible(true); } else { ui->removeMousePassword->setVisible(false); } } void InfoPaneDropdown::on_websiteButton_clicked() { QProcess::startDetached("xdg-open https://vicr123.github.io/theshell"); this->close(); } void InfoPaneDropdown::on_bugButton_clicked() { QProcess::startDetached("xdg-open https://github.com/vicr123/theshell/issues"); this->close(); } void InfoPaneDropdown::on_distroWebpage_clicked() { QProcess::startDetached("xdg-open " + ui->distroWebpage->text()); this->close(); } void InfoPaneDropdown::on_distroSupport_clicked() { QProcess::startDetached("xdg-open " + ui->distroSupport->text()); this->close(); } void InfoPaneDropdown::on_sourcesButton_clicked() { QProcess::startDetached("xdg-open https://github.com/vicr123/theshell"); this->close(); } void InfoPaneDropdown::on_quietModeCriticalOnly_clicked() { AudioMan->setQuietMode(AudioManager::critical); ui->quietModeCriticalOnly->setChecked(true); } \ No newline at end of file +/**************************************** + * + * theShell - Desktop Environment + * Copyright (C) 2018 Victor Tran + * + * 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 . + * + * *************************************/ + +#include "infopanedropdown.h" +#include "ui_infopanedropdown.h" +#include "internationalisation.h" + +extern void playSound(QUrl, bool = false); +extern QIcon getIconFromTheme(QString name, QColor textColor); +extern void EndSession(EndSessionWait::shutdownType type); +extern QString calculateSize(quint64 size); +extern AudioManager* AudioMan; +extern NativeEventFilter* NativeFilter; +extern QTranslator* qtTranslator, *tsTranslator; +extern float getDPIScaling(); +extern QDBusServiceWatcher* dbusServiceWatcher; +extern QDBusServiceWatcher* dbusServiceWatcherSystem; +extern UPowerDBus* updbus; +extern NotificationsDBusAdaptor* ndbus; +extern DBusSignals* dbusSignals; +extern LocationServices* locationServices; + +#define False 0 +#define True 1 + +#define LOWER_INFOPANE InfoPaneNotOnTopLocker locker(this); + +InfoPaneDropdown::InfoPaneDropdown(WId MainWindowId, QWidget* parent) : + QDialog(parent), + ui(new Ui::InfoPaneDropdown) { + if (false) { + Q_UNUSED(QT_TR_NOOP("Location")); + } + + ui->setupUi(this); + + this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowStaysOnTopHint); + + ui->settingsList->setIconSize(QSize(32 * getDPIScaling(), 32 * getDPIScaling())); + ui->settingsListStack->setFixedWidth(250 * getDPIScaling()); + + startTime.start(); + + ui->copyrightNotice->setText(tr("Copyright © Victor Tran %1. Licensed under the terms of the GNU General Public License, version 3 or later.").arg("2018")); + ui->dstIcon->setPixmap(QIcon::fromTheme("chronometer").pixmap(16 * getDPIScaling(), 16 * getDPIScaling())); + ui->usesLocation->setPixmap(QIcon::fromTheme("gps").pixmap(16 * getDPIScaling(), 16 * getDPIScaling())); + + connect(this, SIGNAL(flightModeChanged(bool)), ui->NetworkManager, SLOT(flightModeChanged(bool))); + connect(this, SIGNAL(flightModeChanged(bool)), ui->networkManagerSettings, SLOT(flightModeChanged(bool))); + + if (settings.value("flightmode/on", false).toBool()) { + ui->FlightSwitch->setChecked(true); + } + + this->MainWindowId = MainWindowId; + + //ndbus->setDropdownPane(this); + + /*connect(ndbus, SIGNAL(newNotification(int,QString,QString,QIcon)), this, SLOT(newNotificationReceived(int,QString,QString,QIcon))); + connect(ndbus, SIGNAL(removeNotification(int)), this, SLOT(removeNotification(int))); + connect(ndbus, SIGNAL(NotificationClosed(uint,uint)), this, SLOT(notificationClosed(uint,uint)));*/ + //connect(this, SIGNAL(closeNotification(int)), ndbus, SLOT(CloseNotificationUserInitiated(int))); + connect(ndbus, SIGNAL(NotificationClosed(uint, uint)), this, SLOT(notificationClosed(uint, uint))); + connect(ndbus, SIGNAL(ActionInvoked(uint, QString)), this, SLOT(notificationAction(uint, QString))); + connect(ui->notificationsWidget, SIGNAL(numNotificationsChanged(int)), this, SIGNAL(numNotificationsChanged(int))); + + connect(dbusServiceWatcher, SIGNAL(serviceRegistered(QString)), this, SLOT(DBusServiceRegistered(QString))); + connect(dbusServiceWatcher, SIGNAL(serviceUnregistered(QString)), this, SLOT(DBusServiceUnregistered(QString))); + connect(dbusServiceWatcherSystem, SIGNAL(serviceRegistered(QString)), this, SLOT(DBusServiceRegistered(QString))); + connect(dbusServiceWatcherSystem, SIGNAL(serviceUnregistered(QString)), this, SLOT(DBusServiceUnregistered(QString))); + + QTimer* timer = new QTimer(this); + connect(timer, SIGNAL(timeout()), this, SLOT(timerTick())); + connect(timer, SIGNAL(timeout()), this, SLOT(updateSysInfo())); + //connect(timer, SIGNAL(timeout()), this, SLOT(updateKdeconnect())); + connect(timer, &QTimer::timeout, [ = ]() { + //Run the timer faster when a stopwatch is running. + if (stopwatchRunning) { + timer->setInterval(100); + } else { + timer->setInterval(1000); + } + }); + timer->setInterval(1000); + timer->start(); + + connect(updbus, &UPowerDBus::powerStretchChanged, [ = ](bool isOn) { + ui->PowerStretchSwitch->setChecked(isOn); + emit batteryStretchChanged(isOn); + doNetworkCheck(); + + if (isOn) { + slice1.pause(); + slice2.pause(); + } else { + slice1.resume(); + slice2.resume(); + } + }); + ui->PowerStretchSwitch->setChecked(updbus->powerStretch()); + emit batteryStretchChanged(updbus->powerStretch()); + + ui->label_7->setVisible(false); + ui->pushButton_3->setVisible(false); + ui->BatteryChargeScrollBar->setVisible(false); + ui->appNotificationsConfigureLock->setVisible(false); + ui->dstPanel->setVisible(false); + ui->quietModeExtras->setFixedHeight(0); + //ui->networkKey->setVisible(false); + //ui->networkConnect->setVisible(false); + ui->resetButton->setProperty("type", "destructive"); + ui->userSettingsDeleteUser->setProperty("type", "destructive"); + ui->userSettingsDeleteUserAndData->setProperty("type", "destructive"); + ui->userSettingsDeleteUserOnly->setProperty("type", "destructive"); + ui->resetDeviceButton->setProperty("type", "destructive"); + ui->partFrame->installEventFilter(this); + + QPalette powerStretchPalette = ui->PowerStretchSwitch->palette(); + QPalette flightModePalette = ui->FlightSwitch->palette(); + + QColor background = this->palette().color(QPalette::Background); + int averageCol = (background.red() + background.green() + background.blue()) / 3; + + if (averageCol < 127) { + powerStretchPalette.setColor(QPalette::Highlight, QColor(255, 100, 0)); + powerStretchPalette.setColor(QPalette::WindowText, Qt::white); + flightModePalette.setColor(QPalette::Highlight, QColor(0, 0, 200)); + flightModePalette.setColor(QPalette::WindowText, Qt::white); + } else { + powerStretchPalette.setColor(QPalette::Highlight, QColor(255, 200, 0)); + powerStretchPalette.setColor(QPalette::WindowText, Qt::black); + flightModePalette.setColor(QPalette::Highlight, QColor(100, 200, 255)); + flightModePalette.setColor(QPalette::WindowText, Qt::black); + } + ui->PowerStretchSwitch->setPalette(powerStretchPalette); + ui->FlightSwitch->setPalette(flightModePalette); + + //Set up battery chart + batteryChart = new QChart(); + batteryChart->setBackgroundVisible(false); + batteryChart->legend()->hide(); + + QChartView* batteryChartView = new QChartView(batteryChart); + batteryChartView->setRenderHint(QPainter::Antialiasing); + ((QBoxLayout*) ui->batteryGraph->layout())->insertWidget(1, batteryChartView); + + updateBatteryChart(); + + //Check Redshift + QProcess* redshiftQuery = new QProcess; + redshiftQuery->start("redshift -V"); + connect(redshiftQuery, QOverload::of(&QProcess::finished), [ = ](int exitCode, QProcess::ExitStatus exitStatus) { + QString output = redshiftQuery->readAll().trimmed(); + output.remove("redshift "); + + QStringList parts = output.split("."); + for (int i = 0; i < parts.count(); i++) { + int version = parts.at(i).toInt(); + if (i == 0) { + if (version > 1) { + break; + } else if (version < 1) { + isNewRedshift = false; + break; + } + } else if (i == 1) { + if (version < 11) { + isNewRedshift = false; + } + break; + } + } + redshiftQuery->deleteLater(); + }); + + //Set up KDE Connect + if (!QFile("/usr/lib/kdeconnectd").exists()) { + //If KDE Connect is not installed, hide the KDE Connect option + ui->kdeconnectLabel->setVisible(false); + } + + if (!QFile("/usr/bin/scallop").exists()) { + ui->resetDeviceButton->setVisible(false); + } + + //Set up networking + QDBusInterface networkInterface("org.freedesktop.NetworkManager", "/org/freedesktop/NetworkManager", "org.freedesktop.NetworkManager", QDBusConnection::systemBus(), this); + connect(ui->NetworkManager, SIGNAL(updateBarDisplay(QString, QIcon)), this, SIGNAL(networkLabelChanged(QString, QIcon))); + + ui->WifiSwitch->setChecked(networkInterface.property("WirelessEnabled").toBool()); + + { + QDBusInterface interface("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", QDBusConnection::sessionBus()); + QDBusConnection::sessionBus().connect("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", "BluetoothEnabledChanged", this, SLOT(bluetoothEnabledChanged())); + + if (interface.isValid()) { + DBusServiceRegistered("org.thesuite.tsbt"); + } else { + DBusServiceUnregistered("org.thesuite.tsbt"); + } + + dbusServiceWatcher->addWatchedService("org.thesuite.tsbt"); + } + + //Load icons into icon theme box + { + QString currentIconTheme = themeSettings->value("icons/theme", "contemporary").toString(); + QDir iconPath("/usr/share/icons"); + for (QString iconDir : iconPath.entryList(QDir::NoDotAndDotDot | QDir::Dirs)) { + QFile themeFile("/usr/share/icons/" + iconDir + "/index.theme"); + if (themeFile.exists()) { + themeFile.open(QFile::ReadOnly); + QString iconThemeName = ""; + + while (!themeFile.atEnd()) { + QString line = themeFile.readLine(); + if (line.startsWith("Name")) { + iconThemeName = line.mid(line.indexOf("=") + 1).remove("\n"); + break; + } + } + + themeFile.close(); + + if (iconThemeName != "") { + ui->systemIconTheme->addItem(iconThemeName); + ui->systemIconTheme->setItemData(ui->systemIconTheme->count() - 1, iconDir); + + if (currentIconTheme == iconDir) { + ui->systemIconTheme->setCurrentIndex(ui->systemIconTheme->count() - 1); + } + } + } + } + } + + //Load widget themes into widget theme box + { + ui->systemWidgetTheme->blockSignals(true); + QString currentWidgetTheme = themeSettings->value("style/name", "contemporary").toString(); + QStringList keys = QStyleFactory::keys(); + for (QString key : keys) { + ui->systemWidgetTheme->addItem(key); + ui->systemWidgetTheme->setItemData(ui->systemWidgetTheme->count() - 1, key); + + if (key.toLower() == currentWidgetTheme.toLower()) { + ui->systemWidgetTheme->setCurrentIndex(ui->systemWidgetTheme->count() - 1); + } + } + ui->systemWidgetTheme->blockSignals(false); + } + + //Load GTK3 themes into GTK3 theme box + { + ui->systemGTK3Theme->blockSignals(true); + QString currentWidgetTheme = gtk3Settings->value("Settings/gtk-theme-name", "Contemporary").toString(); + QStringList themes; + + QString themeSearchDirectory = "/usr/share/themes/"; + + QDir themeDir(themeSearchDirectory); + QStringList themeDirEntries = themeDir.entryList(QDir::Dirs | QDir::NoDotAndDotDot); + for (QString entry : themeDirEntries) { + if (QDir(themeSearchDirectory + entry + "/gtk-3.0/").exists()) { + themes.append(entry); + } + } + + for (QString theme : themes) { + ui->systemGTK3Theme->addItem(theme); + ui->systemGTK3Theme->setItemData(ui->systemGTK3Theme->count() - 1, theme); + + if (theme.toLower() == currentWidgetTheme.toLower()) { + ui->systemGTK3Theme->setCurrentIndex(ui->systemGTK3Theme->count() - 1); + } + } + + ui->systemGTK3Theme->blockSignals(false); + } + + QString redshiftStart = settings.value("display/redshiftStart", "").toString(); + if (redshiftStart == "") { + redshiftStart = ui->startRedshift->time().toString(); + settings.setValue("display/redshiftStart", redshiftStart); + } + ui->startRedshift->setTime(QTime::fromString(redshiftStart)); + + QString redshiftEnd = settings.value("display/redshiftEnd", "").toString(); + if (redshiftEnd == "") { + redshiftEnd = ui->endRedshift->time().toString(); + settings.setValue("display/redshiftEnd", redshiftEnd); + } + ui->endRedshift->setTime(QTime::fromString(redshiftEnd)); + + QString redshiftVal = settings.value("display/redshiftIntensity", "").toString(); + if (redshiftVal == "") { + redshiftVal = ui->endRedshift->time().toString(); + settings.setValue("display/redshiftIntensity", redshiftVal); + } + ui->redshiftIntensity->setValue(redshiftVal.toInt()); + + if (settings.value("ui/useFullScreenEndSession", false).toBool()) { + ui->endSessionConfirmFullScreen->setChecked(true); + ui->endSessionConfirmInMenu->setChecked(false); + } else { + ui->endSessionConfirmFullScreen->setChecked(false); + ui->endSessionConfirmInMenu->setChecked(true); + } + + if (settings.contains("notifications/lockScreen")) { + if (settings.value("notifications/lockScreen").toString() == "contents") { + ui->showNotificationsContents->setChecked(true); + } else if (settings.value("notifications/lockScreen").toString() == "none") { + ui->showNotificationsNo->setChecked(true); + } else { + ui->showNotificationsOnly->setChecked(true); + } + } else { + ui->showNotificationsOnly->setChecked(true); + } + + QString themeType = themeSettings->value("color/type", "dark").toString(); + if (themeType == "light") { + ui->lightColorThemeRadio->setChecked(true); + } else if (themeType == "dark") { + ui->darkColorThemeRadio->setChecked(true); + } else if (themeType == "gray") { + ui->grayColorThemeRadio->setChecked(true); + } else if (themeType == "decorative") { + ui->decorativeColorThemeRadio->setChecked(true); + } + + int dpi = sessionSettings->value("screen/dpi", 96).toInt(); + switch (dpi) { + case 96: + ui->dpi100->setChecked(true); + break; + case 144: + ui->dpi150->setChecked(true); + break; + case 192: + ui->dpi200->setChecked(true); + break; + case 288: + ui->dpi300->setChecked(true); + break; + } + + //Populate the language box + Internationalisation::fillLanguageBox(ui->localeList); + + ui->lockScreenBackground->setText(lockScreenSettings->value("background", "/usr/share/tsscreenlock/triangles.svg").toString()); + //ui->lineEdit_2->setText(settings.value("startup/autostart", "").toString()); + ui->redshiftPause->setChecked(!settings.value("display/redshiftPaused", true).toBool()); + ui->TouchFeedbackSwitch->setChecked(settings.value("input/touchFeedbackSound", false).toBool()); + ui->SuperkeyGatewaySwitch->setChecked(settings.value("input/superkeyGateway", true).toBool()); + ui->TextSwitch->setChecked(settings.value("bar/showText", true).toBool()); + ui->windowManager->setText(settings.value("startup/WindowManagerCommand", "kwin_x11").toString()); + ui->barDesktopsSwitch->setChecked(settings.value("bar/showWindowsFromOtherDesktops", true).toBool()); + ui->MediaSwitch->setChecked(settings.value("notifications/mediaInsert", true).toBool()); + ui->StatusBarSwitch->setChecked(settings.value("bar/statusBar", false).toBool()); + ui->TouchInputSwitch->setChecked(settings.value("input/touch", false).toBool()); + ui->SuspendLockScreen->setChecked(settings.value("lockScreen/showOnSuspend", true).toBool()); + ui->LargeTextSwitch->setChecked(themeSettings->value("accessibility/largeText", false).toBool()); + ui->HighContrastSwitch->setChecked(themeSettings->value("accessibility/highcontrast", false).toBool()); + ui->systemAnimationsAccessibilitySwitch->setChecked(themeSettings->value("accessibility/systemAnimations", true).toBool()); + ui->CapsNumLockBellSwitch->setChecked(themeSettings->value("accessibility/bellOnCapsNumLock", false).toBool()); + ui->TwentyFourHourSwitch->setChecked(settings.value("time/use24hour", true).toBool()); + ui->AttenuateSwitch->setChecked(settings.value("notifications/attenuate", true).toBool()); + ui->BarOnBottom->setChecked(!settings.value("bar/onTop", true).toBool()); + ui->AutoShowBarSwitch->setChecked(settings.value("bar/autoshow", true).toBool()); + ui->SoundFeedbackSoundSwitch->setChecked(settings.value("sound/feedbackSound", true).toBool()); + ui->VolumeOverdriveSwitch->setChecked(settings.value("sound/volumeOverdrive", true).toBool()); + ui->batteryScreenOff->setValue(settings.value("power/batteryScreenOff", 15).toInt()); + ui->batterySuspend->setValue(settings.value("power/batterySuspend", 30).toInt()); + ui->powerScreenOff->setValue(settings.value("power/powerScreenOff", 30).toInt()); + ui->powerSuspend->setValue(settings.value("power/powerSuspend", 90).toInt()); + ui->sunlightRedshift->setChecked(settings.value("display/redshiftSunlightCycle", false).toBool()); + ui->EmphasiseAppSwitch->setChecked(settings.value("notifications/emphasiseApp", true).toBool()); + ui->CompactBarSwitch->setChecked(settings.value("bar/compact", false).toBool()); + ui->LocationMasterSwitch->setChecked(locationSettings->value("master/master", true).toBool()); + updateAccentColourBox(); + updateRedshiftTime(); + on_StatusBarSwitch_toggled(ui->StatusBarSwitch->isChecked()); + + if (QFile(QDir::homePath() + "/.theshell/mousepassword").exists()) { + ui->removeMousePassword->setVisible(true); + } else { + ui->removeMousePassword->setVisible(false); + } + + QString defaultFont; + if (QFontDatabase().families().contains("Contemporary")) { + defaultFont = "Contemporary"; + } else { + defaultFont = "Noto Sans"; + } + ui->systemFont->setCurrentFont(QFont(themeSettings->value("fonts/defaultFamily", defaultFont).toString(), themeSettings->value("font/defaultSize", 10).toInt())); + ui->systemFontSize->setValue(themeSettings->value("font/defaultSize", 10).toInt()); + + QString gtk3FontString = gtk3Settings->value("Settings/gtk-font-name", "Contemporary 10").toString(); + QString gtk3FontFamily = gtk3FontString.left(gtk3FontString.lastIndexOf(" ")); + QString gtk3FontSize = gtk3FontString.mid(gtk3FontString.lastIndexOf(" ") + 1); + ui->systemGTK3Font->setCurrentFont(QFont(gtk3FontFamily, gtk3FontSize.toInt())); + ui->systemGTK3FontSize->setValue(gtk3FontSize.toInt()); + + eventTimer = new QTimer(this); + eventTimer->setInterval(1000); + connect(eventTimer, SIGNAL(timeout()), this, SLOT(processTimer())); + eventTimer->start(); + + networkCheckTimer = new QTimer(this); + networkCheckTimer->setInterval(60000); + connect(networkCheckTimer, SIGNAL(timeout()), this, SLOT(doNetworkCheck())); + networkCheckTimer->start(); + doNetworkCheck(); + + QObjectList allObjects; + allObjects.append(this); + + ui->notificationSoundBox->blockSignals(true); + ui->notificationSoundBox->addItem("Triple Ping"); + ui->notificationSoundBox->addItem("Upside Down"); + ui->notificationSoundBox->addItem("Echo"); + + QString notificationSound = settings.value("notifications/sound", "tripleping").toString(); + if (notificationSound == "tripleping") { + ui->notificationSoundBox->setCurrentIndex(0); + } else if (notificationSound == "upsidedown") { + ui->notificationSoundBox->setCurrentIndex(1); + } else if (notificationSound == "echo") { + ui->notificationSoundBox->setCurrentIndex(2); + } + ui->notificationSoundBox->blockSignals(false); + + //Don't forget to change settings pane setup things + ui->settingsList->item(ui->settingsList->count() - 1)->setSelected(true); + ui->settingsTabs->setCurrentIndex(ui->settingsTabs->count() - 1); + + //Get distribution information + { + QString osreleaseFile = ""; + if (QFile("/etc/os-release").exists()) { + osreleaseFile = "/etc/os-release"; + } else if (QFile("/usr/lib/os-release").exists()) { + osreleaseFile = "/usr/lib/os-release"; + } + + if (osreleaseFile != "") { + QFile information(osreleaseFile); + information.open(QFile::ReadOnly); + while (!information.atEnd()) { + QString line = information.readLine(); + if (line.startsWith("pretty_name=", Qt::CaseInsensitive)) { + ui->distroName->setText(line.remove("pretty_name=", Qt::CaseInsensitive).remove("\"").remove("\n")); + } else if (line.startsWith("home_url=", Qt::CaseInsensitive)) { + ui->distroWebpage->setText(line.remove("home_url=", Qt::CaseInsensitive).remove("\"").remove("\n")); + } else if (line.startsWith("support_url=", Qt::CaseInsensitive)) { + ui->distroSupport->setText(line.remove("support_url=", Qt::CaseInsensitive).remove("\"").remove("\n")); + } + } + information.close(); + } + + struct sysinfo* info = new struct sysinfo; + if (sysinfo(info) == 0) { + ui->availableMemory->setText(calculateSize(info->totalram)); + ui->availableSwap->setText(calculateSize(info->totalswap)); + } else { + + } + delete info; + + ui->kernelVersion->setText(QSysInfo::kernelVersion()); + ui->qtVersion->setText(qVersion()); + + QFile cpuInfoFile("/proc/cpuinfo"); + cpuInfoFile.open(QFile::ReadOnly); + QByteArray cpuInfoBuf = cpuInfoFile.readAll(); + QBuffer cpuInfo(&cpuInfoBuf); + cpuInfo.open(QBuffer::ReadOnly); + QStringList knownCpus; + while (!cpuInfo.atEnd()) { + QString line = cpuInfo.readLine(); + if (line.startsWith("model name")) { + QString cpu = line.mid(line.indexOf(":") + 1).trimmed(); + knownCpus.append(cpu); + } + } + + QStringList shownCpus; + while (knownCpus.length() > 0) { + QString cpu = knownCpus.value(0); + int numberOfThisCpu = knownCpus.count(cpu); + + knownCpus.removeAll(cpu); + + if (numberOfThisCpu == 1) { + shownCpus.append(cpu); + } else { + shownCpus.append(QString::number(numberOfThisCpu) + " × " + cpu); + } + } + + if (shownCpus.length() == 0) { + ui->processorType->setText(tr("Unknown")); + } else { + ui->processorType->setText(shownCpus.join(" · ")); + } + } + +#ifdef BLUEPRINT + ui->tsVersion->setText(tr("theShell %1 - Blueprint").arg(TS_VERSION)); + ui->compileDate->setText(tr("You compiled theShell on %1").arg(__DATE__)); +#elif defined(CONSTRUCTION) + ui->tsVersion->setText(tr("theShell %1 - Construction").arg(TS_VERSION)); + ui->compileDate->setText(tr("You compiled theShell on %1").arg(__DATE__)); +#else + ui->tsVersion->setText(tr("theShell %1").arg(TS_VERSION)); + ui->compileDate->setVisible(false); +#endif + + //Update keyboard layouts + struct KeyboardLayoutReturn { + QMap availableKeyboardLayout; + QStringList currentKeyboardLayout; + }; + QFuture keyboardLayouts = QtConcurrent::run([ = ]() -> KeyboardLayoutReturn { + KeyboardLayoutReturn retval; + + QDir xkbLayouts("/usr/share/X11/xkb/symbols"); + for (QFileInfo layoutInfo : xkbLayouts.entryInfoList()) { + if (layoutInfo.isDir()) continue; + + QString layout = layoutInfo.baseName(); + QFile file(layoutInfo.filePath()); + file.open(QFile::ReadOnly); + + QString currentSubLayout = ""; + while (!file.atEnd()) { + QString line = file.readLine().trimmed(); + if (line.startsWith("xkb_symbols") && line.endsWith("{")) { + QRegExp lineRx("\".+\""); + lineRx.indexIn(line); + + if (lineRx.capturedTexts().count() != 0) { + currentSubLayout = lineRx.capturedTexts().first().remove("\""); + } else { + currentSubLayout = ""; + } + } else if (line.startsWith("name")) { + QRegExp lineRx("\".+\""); + lineRx.indexIn(line); + + if (lineRx.capturedTexts().count() != 0 && currentSubLayout != "") { + retval.availableKeyboardLayout.insert(layout + "(" + currentSubLayout + ")", lineRx.capturedTexts().first().remove("\"")); + } else { + currentSubLayout = ""; + } + } + } + + file.close(); + } + + retval.currentKeyboardLayout = settings.value("input/layout", "us(basic)").toString().split(","); + return retval; + }); + QFutureWatcher* keyboardLayoutWatcher = new QFutureWatcher(); + connect(keyboardLayoutWatcher, &QFutureWatcher::finished, [ = ] { + keyboardLayoutWatcher->deleteLater(); + + KeyboardLayoutReturn layouts = keyboardLayouts.result(); + for (QString key : layouts.availableKeyboardLayout.keys()) { + QString value = layouts.availableKeyboardLayout.value(key); + + QListWidgetItem* item = new QListWidgetItem(); + item->setText(value); + item->setData(Qt::UserRole, key); + ui->availableKeyboardLayouts->addItem(item); + } + + for (QString layout : layouts.currentKeyboardLayout) { + QListWidgetItem* item = new QListWidgetItem(); + item->setText(layouts.availableKeyboardLayout.value(layout, layout)); + item->setData(Qt::UserRole, layout); + ui->selectedLayouts->addItem(item); + } + + ui->availableKeyboardLayouts->sortItems(); + connect(ui->selectedLayouts->model(), SIGNAL(layoutChanged(QList, QAbstractItemModel::LayoutChangeHint)), this, SLOT(KeyboardLayoutsMoved())); + setKeyboardLayout(settings.value("input/currentLayout", "us(basic)").toString()); + }); + keyboardLayoutWatcher->setFuture(keyboardLayouts); + + //Set up timer ringtones + ringtone = new QMediaPlayer(this, QMediaPlayer::LowLatency); + + connect(AudioMan, &AudioManager::QuietModeChanged, [ = ](AudioManager::quietMode mode) { + ui->quietModeSound->setChecked(false); + ui->quietModeCriticalOnly->setChecked(false); + ui->quietModeNotification->setChecked(false); + ui->quietModeMute->setChecked(false); + ui->quietModeForeverButton->setEnabled(true); + ui->quietModeTurnOffAt->setEnabled(true); + ui->quietModeTurnOffIn->setEnabled(true); + + if (mode == AudioManager::none) { + ui->quietModeSound->setChecked(true); + + ui->quietModeForeverButton->setEnabled(false); + ui->quietModeTurnOffAt->setEnabled(false); + ui->quietModeTurnOffIn->setEnabled(false); + ui->quietModeForeverButton->setChecked(true); + } else if (mode == AudioManager::notifications) { + ui->quietModeNotification->setChecked(true); + } else if (mode == AudioManager::critical) { + ui->quietModeCriticalOnly->setChecked(true); + } else { + ui->quietModeMute->setChecked(true); + } + ui->quietModeDescription->setText(AudioMan->getCurrentQuietModeDescription()); + }); + ui->quietModeForeverButton->setChecked(true); + ui->quietModeForeverButton->setEnabled(false); + ui->quietModeTurnOffAt->setEnabled(false); + ui->quietModeTurnOffIn->setEnabled(false); + ui->quietModeDescription->setText(AudioMan->getCurrentQuietModeDescription()); + + ui->RemindersList->setModel(new RemindersListModel); + ui->RemindersList->setItemDelegate(new RemindersDelegate); + + slice1.setStartValue((float) (this->width() - 250 * getDPIScaling())); + slice1.setEndValue((float) (this->width() - 300 * getDPIScaling())); + slice1.setEasingCurve(QEasingCurve::OutCubic); + slice1.setDuration(15000); + connect(&slice1, &tVariantAnimation::finished, [ = ] { + slice1.setStartValue(slice1.endValue()); + if (slice1.endValue() == this->width() - 300 * getDPIScaling()) { + slice1.setEndValue(this->width() - 250 * getDPIScaling()); + } else { + slice1.setEndValue(this->width() - 300 * getDPIScaling()); + } + slice1.setEasingCurve(QEasingCurve::InOutCubic); + slice1.start(); + }); + connect(&slice1, SIGNAL(valueChanged(QVariant)), ui->partFrame, SLOT(repaint())); + slice1.start(); + + QTimer::singleShot(2500, [ = ] { + slice2.setStartValue((float) (this->width() - 300 * getDPIScaling())); + slice2.setEndValue((float) (this->width() - 350 * getDPIScaling())); + slice2.setEasingCurve(QEasingCurve::OutCubic); + slice2.setDuration(15000); + connect(&slice2, &tVariantAnimation::finished, [ = ] { + slice2.setStartValue(slice2.endValue()); + if (slice2.endValue() == this->width() - 350 * getDPIScaling()) { + slice2.setEndValue(this->width() - 300 * getDPIScaling()); + } else { + slice2.setEndValue(this->width() - 350 * getDPIScaling()); + } + slice2.setEasingCurve(QEasingCurve::InOutCubic); + slice2.start(); + }); + slice2.start(); + }); + + updateStruts(); + updateAutostart(); + updateDSTNotification(); +} + +InfoPaneDropdown::~InfoPaneDropdown() { + delete ui; +} + +InfoPaneNotOnTopLocker::InfoPaneNotOnTopLocker(InfoPaneDropdown* infoPane) { + this->infoPane = infoPane; + infoPane->setWindowFlags(Qt::FramelessWindowHint); +} + +InfoPaneNotOnTopLocker::~InfoPaneNotOnTopLocker() { + infoPane->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowStaysOnTopHint); + infoPane->showNoAnimation(); +} + +void InfoPaneDropdown::DBusServiceRegistered(QString serviceName) { + if (serviceName == "org.thesuite.tsbt") { + QDBusInterface interface("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", QDBusConnection::sessionBus()); + ui->BluetoothSwitch->setEnabled(true); + ui->BluetoothSwitch->setChecked(interface.property("BluetoothEnabled").toBool()); + } +} + +void InfoPaneDropdown::DBusServiceUnregistered(QString serviceName) { + if (serviceName == "org.thesuite.tsbt") { + ui->BluetoothSwitch->setEnabled(false); + } +} + +void InfoPaneDropdown::bluetoothEnabledChanged() { + ui->BluetoothSwitch->setChecked(QDBusInterface("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", QDBusConnection::sessionBus()).property("BluetoothEnabled").toBool()); +} + +void InfoPaneDropdown::newNetworkDevice(QDBusObjectPath device) { + QDBusInterface* i = new QDBusInterface("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device", QDBusConnection::systemBus(), this); + if (i->property("DeviceType").toInt() == 2) { //WiFi Device + QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device.Wireless", "AccessPointAdded", this, SLOT(getNetworks())); + QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device.Wireless", "AccessPointRemoved", this, SLOT(getNetworks())); + QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device", "StateChanged", this, SLOT(getNetworks())); + } else if (i->property("DeviceType").toInt() == 1) { //Wired Device + QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device.Wired", "PropertiesChanged", this, SLOT(getNetworks())); + } + QDBusConnection::systemBus().connect("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.DBus.Properties", "PropertiesChanged", this, SLOT(getNetworks())); + + QDBusInterface* stats = new QDBusInterface("org.freedesktop.NetworkManager", device.path(), "org.freedesktop.NetworkManager.Device.Statistics", QDBusConnection::systemBus(), this); + stats->setProperty("RefreshRateMs", (uint) 1000); + getNetworks(); + stats->deleteLater(); + i->deleteLater(); +} + +void InfoPaneDropdown::on_WifiSwitch_toggled(bool checked) { + QDBusInterface* i = new QDBusInterface("org.freedesktop.NetworkManager", "/org/freedesktop/NetworkManager", "org.freedesktop.NetworkManager", QDBusConnection::systemBus(), this); + if (i->property("WirelessEnabled").toBool() != checked) { + i->setProperty("WirelessEnabled", checked); + } + + if (i->property("WirelessEnabled").toBool()) { + ui->WifiSwitch->setChecked(true); + } else { + ui->WifiSwitch->setChecked(false); + } + + i->deleteLater(); +} + +void InfoPaneDropdown::processTimer() { + QTime time = QTime::currentTime(); + { + int currentMsecs = time.msecsSinceStartOfDay(); + int startMsecs = ui->startRedshift->time().msecsSinceStartOfDay(); + int endMsecs = ui->endRedshift->time().msecsSinceStartOfDay(); + int endIntensity = ui->redshiftIntensity->value(); + const int oneHour = 3600000; + QString redshiftCommand; + + if (ui->redshiftPause->isChecked()) { + //Calculate redshift value + //Transition to redshift is 1 hour from the start. + + int intensity; + if (startMsecs > endMsecs) { //Start time is later then end time + if (currentMsecs < endMsecs || currentMsecs > startMsecs) { + intensity = endIntensity; + } else if (currentMsecs < startMsecs && currentMsecs > startMsecs - oneHour) { + int timeFrom = currentMsecs - (startMsecs - oneHour); + float percentage = ((float) timeFrom / (float) oneHour); + int progress = (6500 - endIntensity) * percentage; + intensity = 6500 - progress; + } else if (currentMsecs > endMsecs && currentMsecs < endMsecs + oneHour) { + int timeFrom = endMsecs - (currentMsecs - oneHour); + float percentage = ((float) timeFrom / (float) oneHour); + int progress = (6500 - endIntensity) * percentage; + intensity = 6500 - progress; + } else { + intensity = 6500; + } + } else { //Start time is earlier then end time + if (currentMsecs < endMsecs && currentMsecs > startMsecs) { + intensity = endIntensity; + } else if (currentMsecs < startMsecs && currentMsecs > startMsecs - oneHour) { + int timeFrom = currentMsecs - (startMsecs - oneHour); + float percentage = ((float) timeFrom / (float) oneHour); + int progress = (6500 - endIntensity) * percentage; + intensity = 6500 - progress; + } else if (currentMsecs > endMsecs && currentMsecs < endMsecs + oneHour) { + int timeFrom = endMsecs - (currentMsecs - oneHour); + float percentage = ((float) timeFrom / (float) oneHour); + int progress = (6500 - endIntensity) * percentage; + intensity = 6500 - progress; + } else { + intensity = 6500; + } + } + + //Check Redshift override + if (overrideRedshift != 0) { + if (intensity == 6500 && overrideRedshift == 1) { + overrideRedshift = 0; //Reset Redshift override + } else if (intensity != 6500 && overrideRedshift == 2) { + overrideRedshift = 0; //Reset Redshift override + } else { + if (overrideRedshift == 1) { + intensity = 6500; + } else { + intensity = endIntensity; + } + } + } + + redshiftCommand = "redshift -O " + QString::number(intensity); + + isRedshiftOn = true; + if (intensity == 6500 && effectiveRedshiftOn) { + effectiveRedshiftOn = false; + ui->redshiftSwitch->setChecked(false); + emit redshiftEnabledChanged(false); + } else if (intensity != 6500 && !effectiveRedshiftOn) { + effectiveRedshiftOn = true; + ui->redshiftSwitch->setChecked(true); + emit redshiftEnabledChanged(true); + } + } else { + //Check Redshift Override + if (overrideRedshift == 2) { + redshiftCommand = "redshift -O " + QString::number(endIntensity); + } else { + redshiftCommand = "redshift -O 6500"; + } + + if (isRedshiftOn) { + isRedshiftOn = false; + effectiveRedshiftOn = false; + ui->redshiftSwitch->setChecked(false); + emit redshiftEnabledChanged(false); + } + } + + if (isNewRedshift) { + redshiftCommand += " -P"; + } + + QProcess* redshiftAdjust = new QProcess(); + redshiftAdjust->start(redshiftCommand); + connect(redshiftAdjust, SIGNAL(finished(int)), redshiftAdjust, SLOT(deleteLater())); + } + + /*{ + cups_dest_t *destinations; + int destinationCount = cupsGetDests(&destinations); + + for (int i = 0; i < destinationCount; i++) { + cups_dest_t currentDestination = destinations[i]; + + if (!printersFrames.keys().contains(currentDestination.name)) { + QFrame* frame = new QFrame(); + QHBoxLayout* layout = new QHBoxLayout(); + layout->setMargin(0); + frame->setLayout(layout); + + QFrame* statFrame = new QFrame(); + QHBoxLayout* statLayout = new QHBoxLayout(); + statLayout->setMargin(0); + statFrame->setLayout(statLayout); + layout->addWidget(statFrame); + + QLabel* iconLabel = new QLabel(); + QPixmap icon = QIcon::fromTheme("printer").pixmap(22 * getDPIScaling(), 22 * getDPIScaling()); + if (currentDestination.is_default) { + QPainter *p = new QPainter(); + p->begin(&icon); + p->drawPixmap(10 * getDPIScaling(), 10 * getDPIScaling(), 12 * getDPIScaling(), 12 * getDPIScaling(), QIcon::fromTheme("emblem-checked").pixmap(12 * getDPIScaling(), 12 * getDPIScaling())); + p->end(); + } + iconLabel->setPixmap(icon); + statLayout->addWidget(iconLabel); + + QLabel* nameLabel = new QLabel(); + nameLabel->setText(currentDestination.name); + QFont font = nameLabel->font(); + font.setBold(true); + nameLabel->setFont(font); + statLayout->addWidget(nameLabel); + + QLabel* statLabel = new QLabel(); + statLabel->setText(tr("Idle")); + statLabel->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + statLayout->addWidget(statLabel); + + /*QPushButton* button = new QPushButton(); + button->setIcon(QIcon::fromTheme("window-close")); + connect(button, &QPushButton::clicked, [=]() { + emit closeNotification(id); + }); + layout->addWidget(button); + + ui->printersList->layout()->addWidget(frame); + printersFrames.insert(currentDestination.name, frame); + printersStatFrames.insert(currentDestination.name, frame); + printersStats.insert(currentDestination.name, statLabel); + } + + QString state = ""; + QString stateReasons = ""; + for (int i = 0; i < currentDestination.num_options; i++) { + cups_option_t currentOption = currentDestination.options[i]; + + if (strncmp(currentOption.name, "printer-state", strlen(currentOption.name)) == 0) { + if (strncmp(currentOption.value, "3", 1) == 0) { + state = tr("Idle"); + printersStatFrames.value(currentDestination.name)->setEnabled(true); + } else if (strncmp(currentOption.value, "4", 1) == 0) { + state = tr("Printing"); + printersStatFrames.value(currentDestination.name)->setEnabled(true); + } else if (strncmp(currentOption.value, "5", 1) == 0) { + state = tr("Stopped"); + printersStatFrames.value(currentDestination.name)->setEnabled(false); + } + } else if (strncmp(currentOption.name, "printer-state-reasons", strlen(currentOption.name)) == 0) { + stateReasons = QString::fromUtf8(currentOption.value, strlen(currentOption.value)); + } + } + printersStats.value(currentDestination.name)->setText(state + " / " + stateReasons); + + } + + cupsFreeDests(destinationCount, destinations); + }*/ +} + +void InfoPaneDropdown::timerTick() { + ui->date->setText(QLocale().toString(QDateTime::currentDateTime(), "ddd dd MMM yyyy")); + ui->time->setText(QDateTime::currentDateTime().toString("hh:mm:ss")); + + //Also update the stopwatch + QTime stopwatchTime = QTime::fromMSecsSinceStartOfDay(0); + stopwatchTime = stopwatchTime.addMSecs(stopwatchTimeAdd); + if (stopwatchRunning) { + stopwatchTime = stopwatchTime.addMSecs(this->stopwatchTime.elapsed()); + } + ui->stopwatchLabel->setText(stopwatchTime.toString("hh:mm:ss.zzz")); + updateTimers(); + + //Also check for reminders + { + QList> ReminderData; + + QSettings reminders("theSuite/theShell.reminders"); + reminders.beginGroup("reminders"); + int count = reminders.beginReadArray("reminders"); + + for (int i = 0; i < count; i++) { + reminders.setArrayIndex(i); + QPair data; + data.first = reminders.value("title").toString(); + data.second = reminders.value("date").toDateTime(); + ReminderData.append(data); + } + + reminders.endArray(); + + bool dataChanged = false; + for (int i = 0; i < ReminderData.count(); i++) { + QPair data = ReminderData.at(i); + if (data.second.msecsTo(QDateTime::currentDateTime()) > 0) { + QVariantMap hints; + hints.insert("category", "reminder.activate"); + hints.insert("sound-file", "qrc:/sounds/notifications/reminder.wav"); + ndbus->Notify("theShell", 0, "theshell", "Reminder", data.first, QStringList(), hints, 30000); + ReminderData.removeAt(i); + i--; + dataChanged = true; + } + } + + + if (dataChanged) { + reminders.beginWriteArray("reminders"); + int i = 0; + for (QPair data : ReminderData) { + reminders.setArrayIndex(i); + reminders.setValue("title", data.first); + reminders.setValue("date", data.second); + i++; + } + reminders.endArray(); + reminders.endGroup(); + + ((RemindersListModel*) ui->RemindersList->model())->updateData(); + } + } +} + +void InfoPaneDropdown::show(dropdownType showWith) { + changeDropDown(showWith, false); + if (!this->isVisible()) { + QRect screenGeometry = QApplication::desktop()->screenGeometry(); + + if (settings.value("bar/onTop", true).toBool()) { + this->setGeometry(screenGeometry.x(), screenGeometry.y() - screenGeometry.height(), screenGeometry.width(), screenGeometry.height() + 1); + } else { + this->setGeometry(screenGeometry.x(), screenGeometry.bottom(), screenGeometry.width(), screenGeometry.height() + 1); + } + + Atom DesktopWindowTypeAtom; + DesktopWindowTypeAtom = XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE_NORMAL", False); + XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE", False), + XA_ATOM, 32, PropModeReplace, (unsigned char*) &DesktopWindowTypeAtom, 1); //Change Window Type + + unsigned long desktop = 0xFFFFFFFF; + XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_DESKTOP", False), + XA_CARDINAL, 32, PropModeReplace, (unsigned char*) &desktop, 1); //Set visible on all desktops + + QDialog::show(); + this->setFixedWidth(screenGeometry.width()); + this->setFixedHeight(screenGeometry.height() + 1); + + if (settings.value("bar/onTop", true).toBool()) { + previousDragY = -1; + } else { + previousDragY = screenGeometry.bottom(); + } + completeDragDown(); + } + + //Get Current Brightness + QProcess* backlight = new QProcess(this); + backlight->start("xbacklight -get"); + backlight->waitForFinished(); + float output = ceil(QString(backlight->readAll()).toFloat()); + delete backlight; + + ui->brightnessSlider->setValue((int) output); + + //Update the reminders list + ((RemindersListModel*) ui->RemindersList->model())->updateData(); +} + +void InfoPaneDropdown::showNoAnimation() { + QDialog::show(); + previousDragY = -1; + completeDragDown(); +} + +void InfoPaneDropdown::close() { + QRect screenGeometry = QApplication::desktop()->screenGeometry(); + tPropertyAnimation* a = new tPropertyAnimation(this, "geometry"); + a->setStartValue(this->geometry()); + + if (settings.value("bar/onTop", true).toBool()) { + a->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - screenGeometry.height() + 1, this->width(), this->height())); + } else { + a->setEndValue(QRect(screenGeometry.x(), screenGeometry.bottom() + 1, this->width(), this->height())); + } + a->setEasingCurve(QEasingCurve::OutCubic); + a->setDuration(500); + connect(a, &tPropertyAnimation::finished, [ = ]() { + QDialog::hide(); + }); + connect(a, SIGNAL(finished()), a, SLOT(deleteLater())); + a->start(); + + if (ui->quietModeExtras->height() != 0) { + ui->quietModeExpandButton->click(); + } +} + +void InfoPaneDropdown::changeDropDown(dropdownType changeTo, bool doAnimation) { + this->currentDropDown = changeTo; + + //Switch to the requested frame + switch (changeTo) { + case Clock: + ui->pageStack->setCurrentWidget(ui->clockFrame, doAnimation); + + if (ui->lightColorThemeRadio->isChecked()) { + setHeaderColour(QColor(0, 150, 0)); + } else { + setHeaderColour(QColor(0, 50, 0)); + } + break; + case Battery: + ui->pageStack->setCurrentWidget(ui->statusFrame, doAnimation); + updateBatteryChart(); + if (ui->lightColorThemeRadio->isChecked()) { + setHeaderColour(QColor(200, 150, 0)); + } else { + setHeaderColour(QColor(100, 50, 0)); + } + break; + case Notifications: + ui->pageStack->setCurrentWidget(ui->notificationsFrame, doAnimation); + if (ui->lightColorThemeRadio->isChecked()) { + setHeaderColour(QColor(200, 50, 100)); + } else { + setHeaderColour(QColor(100, 25, 50)); + } + break; + case Network: + ui->pageStack->setCurrentWidget(ui->networkFrame, doAnimation); + if (ui->lightColorThemeRadio->isChecked()) { + setHeaderColour(QColor(100, 100, 255)); + } else { + setHeaderColour(QColor(50, 50, 100)); + } + break; + case KDEConnect: + ui->pageStack->setCurrentWidget(ui->kdeConnectFrame, doAnimation); + if (ui->lightColorThemeRadio->isChecked()) { + setHeaderColour(QColor(200, 100, 255)); + } else { + setHeaderColour(QColor(50, 0, 100)); + } + break; + /*case Print: + ui->pageStack->setCurrentWidget(ui->printFrame, doAnimation); + break;*/ + case Settings: + ui->pageStack->setCurrentWidget(ui->settingsFrame, doAnimation); + if (ui->lightColorThemeRadio->isChecked()) { + setHeaderColour(QColor(0, 150, 255)); + } else { + setHeaderColour(QColor(0, 50, 100)); + } + break; + } + + if (changeTo == Clock) { + ui->pushButton_5->setEnabled(false); + ui->pushButton_6->setEnabled(true); + } else if ((ui->kdeconnectLabel->isVisible() && changeTo == KDEConnect) || (changeTo == Notifications && !ui->kdeconnectLabel->isVisible())) { //Print) { + ui->pushButton_5->setEnabled(true); + ui->pushButton_6->setEnabled(false); + } else if (changeTo == Settings) { + ui->pushButton_5->setEnabled(false); + ui->pushButton_6->setEnabled(false); + } else { + ui->pushButton_5->setEnabled(true); + ui->pushButton_6->setEnabled(true); + } +} + +void InfoPaneDropdown::on_pushButton_clicked() { + this->close(); +} + +void InfoPaneDropdown::getNetworks() { + ui->NetworkManager->updateGlobals(); +} + +void InfoPaneDropdown::on_pushButton_5_clicked() { + changeDropDown(dropdownType(currentDropDown - 1)); +} + +void InfoPaneDropdown::on_pushButton_6_clicked() { + changeDropDown(dropdownType(currentDropDown + 1)); +} + +void InfoPaneDropdown::on_clockLabel_clicked() { + changeDropDown(Clock); +} + +void InfoPaneDropdown::on_batteryLabel_clicked() { + changeDropDown(Battery); +} + +void InfoPaneDropdown::on_networkLabel_clicked() { + changeDropDown(Network); +} + +void InfoPaneDropdown::on_notificationsLabel_clicked() { + changeDropDown(Notifications); +} + +void InfoPaneDropdown::startTimer(QTime time) { + if (timer != NULL) { //Check for already running timer + timer->stop(); + delete timer; + timer = NULL; + ui->timeEdit->setVisible(true); + ui->label_7->setVisible(false); + ui->label_7->setEnabled(true); + ui->pushButton_2->setText(tr("Start")); + ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-start")); + ui->pushButton_3->setVisible(false); + emit timerVisibleChanged(false); + emit timerEnabledChanged(true); + } + + ui->pushButton_2->setText(tr("Pause")); + ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-pause")); + timeUntilTimeout = time; + lastTimer = time; + ui->label_7->setText(ui->timeEdit->text()); + ui->timeEdit->setVisible(false); + ui->label_7->setVisible(true); + timer = new QTimer(); + timer->setInterval(1000); + connect(timer, &QTimer::timeout, [ = ]() { + timeUntilTimeout = timeUntilTimeout.addSecs(-1); + if (timeUntilTimeout == QTime(0, 0, 0)) { + if (timerNotificationId != 0) { + ndbus->CloseNotification(timerNotificationId); + } + + timer->stop(); + delete timer; + timer = NULL; + + if (AudioMan->QuietMode() != AudioManager::notifications && AudioMan->QuietMode() != AudioManager::mute) { //Check if we should show the notification so the user isn't stuck listening to the tone + QStringList actions; + actions << "restart" << "Restart Timer"; + actions << "+0.5" << "+30 sec"; + actions << "+1" << "+1 min"; + actions << "+2" << "+2 min"; + actions << "+5" << "+5 min"; + actions << "+10" << "+10 min"; + + QVariantMap hints; + hints.insert("x-thesuite-timercomplete", true); + hints.insert("suppress-sound", true); + timerNotificationId = ndbus->Notify("theShell", 0, "", tr("Timer Elapsed"), + tr("Your timer has completed."), + actions, hints, 0); + ui->timeEdit->setVisible(true); + ui->label_7->setVisible(false); + ui->pushButton_2->setText("Start"); + ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-start")); + + QMediaPlaylist* playlist = new QMediaPlaylist(); + +#ifdef BLUEPRINT + QString ringtonesPath = "/usr/share/sounds/theshellb/tones/"; +#elif defined(CONSTRUCTION) + QString ringtonesPath = "/usr/share/sounds/theshellc/tones/"; +#else + QString ringtonesPath = "/usr/share/sounds/theshell/tones/"; +#endif + + if (ui->timerToneSelect->currentText() == tr("Happy Bee")) { + playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "happybee.ogg"))); + } else if (ui->timerToneSelect->currentText() == tr("Playing in the Dark")) { + playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "playinginthedark.ogg"))); + } else if (ui->timerToneSelect->currentText() == tr("Ice Cream Truck")) { + playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "icecream.ogg"))); + } else if (ui->timerToneSelect->currentText() == tr("Party Complex")) { + playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "party.ogg"))); + } else if (ui->timerToneSelect->currentText() == tr("Salty Ditty")) { + playlist->addMedia(QMediaContent(QUrl::fromLocalFile(ringtonesPath + "saltyditty.ogg"))); + } + playlist->setPlaybackMode(QMediaPlaylist::Loop); + ringtone->setPlaylist(playlist); + ringtone->play(); + + AudioMan->attenuateStreams(); + } + updateTimers(); + } else { + ui->label_7->setText(timeUntilTimeout.toString("HH:mm:ss")); + updateTimers(); + } + }); + timer->start(); + updateTimers(); +} + +void InfoPaneDropdown::updateTimers() { + QStringList parts; + if (timer != NULL) { + parts.append(timeUntilTimeout.toString("HH:mm:ss")); + } + + if (stopwatchRunning) { + QTime stopwatchTime = QTime::fromMSecsSinceStartOfDay(0); + stopwatchTime = stopwatchTime.addMSecs(stopwatchTimeAdd); + stopwatchTime = stopwatchTime.addMSecs(this->stopwatchTime.elapsed()); + parts.append(stopwatchTime.toString("hh:mm:ss")); + } + + if (parts.count() != 0) { + emit timerVisibleChanged(true); + emit timerChanged(parts.join(" · ")); + } else { + emit timerVisibleChanged(false); + } +} + +void InfoPaneDropdown::notificationClosed(uint id, uint reason) { + Q_UNUSED(reason) + if (id == timerNotificationId) { + ringtone->stop(); + AudioMan->restoreStreams(); + timerNotificationId = 0; + } +} + +void InfoPaneDropdown::on_pushButton_2_clicked() { + if (timer == NULL) { + startTimer(ui->timeEdit->time()); + } else { + if (timer->isActive()) { + timer->stop(); + ui->pushButton_3->setVisible(true); + ui->label_7->setEnabled(false); + ui->pushButton_2->setText(tr("Resume")); + ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-start")); + } else { + timer->start(); + ui->pushButton_3->setVisible(false); + ui->label_7->setEnabled(true); + ui->pushButton_2->setText(tr("Pause")); + ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-pause")); + } + } +} + +void InfoPaneDropdown::on_pushButton_3_clicked() { + delete timer; + timer = NULL; + ui->timeEdit->setVisible(true); + ui->label_7->setVisible(false); + ui->label_7->setEnabled(true); + ui->pushButton_2->setText(tr("Start")); + ui->pushButton_2->setIcon(QIcon::fromTheme("chronometer-start")); + ui->pushButton_3->setVisible(false); + emit timerVisibleChanged(false); + emit timerEnabledChanged(true); +} + +void InfoPaneDropdown::on_pushButton_7_clicked() { + changeDropDown(Settings); +} + +void InfoPaneDropdown::setGeometry(int x, int y, int w, int h) { //Use wmctrl command because KWin has a problem with moving windows offscreen. + QDialog::setGeometry(x, y, w, h); + QProcess::execute("wmctrl -r " + this->windowTitle() + " -e 0," + + QString::number(x) + "," + QString::number(y) + "," + + QString::number(w) + "," + QString::number(h)); +} + +void InfoPaneDropdown::setGeometry(QRect geometry) { + this->setGeometry(geometry.x(), geometry.y(), geometry.width(), geometry.height()); +} + +void InfoPaneDropdown::on_lineEdit_2_editingFinished() { + //settings.setValue("startup/autostart", ui->lineEdit_2->text()); +} + +void InfoPaneDropdown::on_resolutionButton_clicked() { + QProcess::startDetached("kcmshell5 kcm_kscreen"); + this->close(); +} + +void InfoPaneDropdown::on_startRedshift_timeChanged(const QTime& time) { + settings.setValue("display/redshiftStart", time.toString()); + processTimer(); +} + +void InfoPaneDropdown::on_endRedshift_timeChanged(const QTime& time) { + settings.setValue("display/redshiftEnd", time.toString()); + processTimer(); +} + +void InfoPaneDropdown::on_redshiftIntensity_sliderMoved(int position) { + if (isNewRedshift) { + QProcess::startDetached("redshift -P -O " + QString::number(position)); + } else { + QProcess::startDetached("redshift -O " + QString::number(position)); + } +} + +void InfoPaneDropdown::on_redshiftIntensity_sliderReleased() { + if (!isRedshiftOn) { + if (isNewRedshift) { + QProcess::startDetached("redshift -P -O 6500"); + } else { + QProcess::startDetached("redshift -O 6500"); + } + } +} + +void InfoPaneDropdown::on_redshiftIntensity_valueChanged(int value) { + settings.setValue("display/redshiftIntensity", value); +} + +void InfoPaneDropdown::newNotificationReceived(int id, QString summary, QString body, QIcon icon) { + if (notificationFrames.keys().contains(id)) { //Notification already exists, update it. + QFrame* frame = notificationFrames.value(id); + frame->property("summaryLabel").value()->setText(summary); + frame->property("bodyLabel").value()->setText(body); + } else { + QFrame* frame = new QFrame(); + QHBoxLayout* layout = new QHBoxLayout(); + layout->setMargin(0); + frame->setLayout(layout); + + QLabel* iconLabel = new QLabel(); + iconLabel->setPixmap(icon.pixmap(22 * getDPIScaling(), 22 * getDPIScaling())); + layout->addWidget(iconLabel); + + QLabel* sumLabel = new QLabel(); + sumLabel->setText(summary); + QFont font = sumLabel->font(); + font.setBold(true); + sumLabel->setFont(font); + layout->addWidget(sumLabel); + + QLabel* bodyLabel = new QLabel(); + bodyLabel->setText(body); + bodyLabel->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred); + layout->addWidget(bodyLabel); + + QLabel* dateLabel = new QLabel(); + dateLabel->setText(QDateTime::currentDateTime().toString("HH:mm:ss")); + layout->addWidget(dateLabel); + + QPushButton* button = new QPushButton(); + button->setIcon(QIcon::fromTheme("window-close")); + connect(button, &QPushButton::clicked, [ = ]() { + emit closeNotification(id); + }); + layout->addWidget(button); + + //ui->notificationsList->layout()->addWidget(frame); + //ui->noNotifications->setVisible(false); + //ui->clearAllNotifications->setVisible(true); + frame->setProperty("summaryLabel", QVariant::fromValue(sumLabel)); + frame->setProperty("bodyLabel", QVariant::fromValue(bodyLabel)); + + notificationFrames.insert(id, frame); + + emit numNotificationsChanged(notificationFrames.count()); + } +} + +void InfoPaneDropdown::removeNotification(int id) { + if (notificationFrames.keys().contains(id)) { + delete notificationFrames.value(id); + notificationFrames.remove(id); + } + + emit numNotificationsChanged(notificationFrames.count()); + + if (notificationFrames.count() == 0) { + //ui->noNotifications->setVisible(true); + //ui->clearAllNotifications->setVisible(false); + } +} + +void InfoPaneDropdown::on_clearAllNotifications_clicked() { + for (int id : notificationFrames.keys()) { + emit closeNotification(id); + } +} + + +void InfoPaneDropdown::on_redshiftPause_toggled(bool checked) { + processTimer(); + settings.setValue("display/redshiftPaused", !checked); +} + +void InfoPaneDropdown::updateSysInfo() { + ui->currentBattery->setText(tr("Current Battery Percentage: %1").arg(QString::number(updbus->currentBattery()).append("%"))); + + QTime uptime(0, 0); + uptime = uptime.addMSecs(startTime.elapsed()); + ui->theshellUptime->setText(tr("theShell Uptime: %1").arg(uptime.toString("hh:mm:ss"))); + + struct sysinfo* info = new struct sysinfo; + if (sysinfo(info) == 0) { + QTime sysUptime(0, 0); + sysUptime = sysUptime.addSecs(info->uptime); + QString uptimeString; + if (info->uptime > 86400) { + int days = info->uptime / 86400; + uptimeString = tr("%n days", NULL, days) + " " + sysUptime.toString("hh:mm:ss"); + } else { + uptimeString = sysUptime.toString("hh:mm:ss"); + } + ui->systemUptime->setText(tr("System Uptime: %1").arg(uptimeString)); + } else { + ui->systemUptime->setText(tr("Couldn't get system uptime")); + } + delete info; +} + +void InfoPaneDropdown::on_printLabel_clicked() { + //changeDropDown(Print); +} + +void InfoPaneDropdown::on_resetButton_clicked() { + if (QMessageBox::warning(this, tr("Reset theShell"), + tr("All settings will be reset to default, and you will be logged out. " + "Are you sure you want to do this?"), QMessageBox::Yes | QMessageBox::No, + QMessageBox::No) == QMessageBox::Yes) { + settings.clear(); + EndSession(EndSessionWait::logout); + } +} + +bool InfoPaneDropdown::isTimerRunning() { + if (timer == NULL) { + return false; + } else { + return true; + } +} + +void InfoPaneDropdown::mousePressEvent(QMouseEvent* event) { + mouseClickPoint = event->localPos().toPoint().y(); + initialPoint = mouseClickPoint; + dragRect = this->geometry(); + mouseMovedUp = false; + draggingInfoPane = true; + event->accept(); +} + +void InfoPaneDropdown::mouseMoveEvent(QMouseEvent* event) { + if (draggingInfoPane) { + QRect screenGeometry = QApplication::desktop()->screenGeometry(); + + if (event->globalY() < mouseClickPoint) { + mouseMovedUp = true; + } else { + mouseMovedUp = false; + } + + //dragRect.translate(0, event->localPos().toPoint().y() - mouseClickPoint + this->y()); + dragRect = screenGeometry; + dragRect.translate(0, event->globalY() - (initialPoint + screenGeometry.top())); + + //innerRect.translate(event->localPos().toPoint().y() - mouseClickPoint, 0); + + if (settings.value("bar/onTop", true).toBool()) { + if (dragRect.bottom() >= screenGeometry.bottom()) { + dragRect.moveTo(screenGeometry.left(), screenGeometry.top()); + } + } else { + if (dragRect.top() <= screenGeometry.top() - 1) { + dragRect.moveTo(screenGeometry.left(), screenGeometry.top() - 1); + } + } + this->setGeometry(dragRect); + + mouseClickPoint = event->globalY(); + event->accept(); + } +} + +void InfoPaneDropdown::mouseReleaseEvent(QMouseEvent* event) { + if (draggingInfoPane) { + QRect screenGeometry = QApplication::desktop()->screenGeometry(); + if (initialPoint - 5 > mouseClickPoint && initialPoint + 5 < mouseClickPoint) { + tPropertyAnimation* a = new tPropertyAnimation(this, "geometry"); + a->setStartValue(this->geometry()); + a->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - (settings.value("bar/onTop", true).toBool() ? 0 : 1), this->width(), this->height())); + a->setEasingCurve(QEasingCurve::OutCubic); + a->setDuration(500); + connect(a, SIGNAL(finished()), a, SLOT(deleteLater())); + a->start(); + } else { + /*if ((mouseMovedUp && settings.value("bar/onTop", true).toBool()) || + (!mouseMovedUp && !settings.value("bar/onTop", true).toBool())) {*/ + if (mouseMovedUp == settings.value("bar/onTop", true).toBool()) { + this->close(); + } else { + tPropertyAnimation* a = new tPropertyAnimation(this, "geometry"); + a->setStartValue(this->geometry()); + a->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - (settings.value("bar/onTop", true).toBool() ? 0 : 1), this->width(), this->height())); + a->setEasingCurve(QEasingCurve::OutCubic); + a->setDuration(500); + connect(a, SIGNAL(finished()), a, SLOT(deleteLater())); + a->start(); + } + } + event->accept(); + initialPoint = 0; + draggingInfoPane = false; + } +} + +void InfoPaneDropdown::on_TouchFeedbackSwitch_toggled(bool checked) { + settings.setValue("input/touchFeedbackSound", checked); +} + +void InfoPaneDropdown::on_brightnessSlider_sliderMoved(int position) { + QProcess* backlight = new QProcess(this); + backlight->start("xbacklight -set " + QString::number(position)); + connect(backlight, SIGNAL(finished(int)), backlight, SLOT(deleteLater())); +} + +void InfoPaneDropdown::on_brightnessSlider_valueChanged(int value) { + on_brightnessSlider_sliderMoved(value); +} + +void InfoPaneDropdown::on_settingsList_currentRowChanged(int currentRow) { + ui->settingsTabs->setCurrentIndex(currentRow); + + //Set up settings + if (ui->settingsTabs->currentWidget() == ui->NotificationsSettings) { //Notifications + setupNotificationsSettingsPane(); + } else if (currentRow == 6) { //Location + setupLocationSettingsPane(); + } else if (ui->settingsTabs->currentWidget() == ui->UserSettings) { //Users + setupUsersSettingsPane(); + } else if (ui->settingsTabs->currentWidget() == ui->DateTimeSettings) { //Date and Time + setupDateTimeSettingsPane(); + } +} + +void InfoPaneDropdown::setupNotificationsSettingsPane() { + ui->AppNotifications->clear(); + + QStringList knownApplications; + int amount = notificationAppSettings->beginReadArray("notifications/knownApplications"); + for (int i = 0; i < amount; i++) { + notificationAppSettings->setArrayIndex(i); + knownApplications.append(notificationAppSettings->value("appname").toString()); + } + notificationAppSettings->endArray(); + + for (QString app : knownApplications) { + QListWidgetItem* item = new QListWidgetItem(); + item->setText(app); + ui->AppNotifications->addItem(item); + } +} + +void InfoPaneDropdown::on_settingsTabs_currentChanged(int arg1) { + ui->settingsList->item(arg1)->setSelected(true); +} + +void InfoPaneDropdown::on_lockScreenBackgroundBrowse_clicked() { + QFileDialog dialog(this); + dialog.setAcceptMode(QFileDialog::AcceptOpen); + dialog.setNameFilter("Images (*.jpg *.jpeg *.bmp *.png *.gif *.svg)"); + if (dialog.exec() == QDialog::Accepted) { + lockScreenSettings->setValue("background", dialog.selectedFiles().first()); + ui->lockScreenBackground->setText(dialog.selectedFiles().first()); + } +} + +void InfoPaneDropdown::on_lockScreenBackground_textEdited(const QString& arg1) { + lockScreenSettings->setValue("background", arg1); +} + +void InfoPaneDropdown::on_TextSwitch_toggled(bool checked) { + settings.setValue("bar/showText", checked); +} + +void InfoPaneDropdown::on_windowManager_textEdited(const QString& arg1) { + settings.setValue("startup/WindowManagerCommand", arg1); +} + +void InfoPaneDropdown::on_barDesktopsSwitch_toggled(bool checked) { + settings.setValue("bar/showWindowsFromOtherDesktops", checked); +} + +void InfoPaneDropdown::on_BluetoothSwitch_toggled(bool checked) { + QDBusInterface("org.thesuite.tsbt", "/org/thesuite/tsbt", "org.thesuite.tsbt", QDBusConnection::sessionBus()).setProperty("BluetoothEnabled", checked); +} + +void InfoPaneDropdown::on_SuperkeyGatewaySwitch_toggled(bool checked) { + settings.setValue("input/superkeyGateway", checked); +} + +void InfoPaneDropdown::reject() { + this->close(); +} + +void InfoPaneDropdown::on_kdeconnectLabel_clicked() { + changeDropDown(KDEConnect); +} + +void InfoPaneDropdown::on_endSessionConfirmFullScreen_toggled(bool checked) { + if (checked) { + settings.setValue("ui/useFullScreenEndSession", true); + } +} + +void InfoPaneDropdown::on_endSessionConfirmInMenu_toggled(bool checked) { + if (checked) { + settings.setValue("ui/useFullScreenEndSession", false); + } +} + +void InfoPaneDropdown::on_pageStack_switchingFrame(int switchTo) { + QWidget* switchingWidget = ui->pageStack->widget(switchTo); + ui->clockLabel->setShowDisabled(true); + ui->batteryLabel->setShowDisabled(true); + ui->notificationsLabel->setShowDisabled(true); + ui->networkLabel->setShowDisabled(true); + //ui->printLabel->setShowDisabled(true); + ui->kdeconnectLabel->setShowDisabled(true); + + if (switchingWidget == ui->clockFrame) { + ui->clockLabel->setShowDisabled(false); + } else if (switchingWidget == ui->statusFrame) { + ui->batteryLabel->setShowDisabled(false); + } else if (switchingWidget == ui->notificationsFrame) { + ui->notificationsLabel->setShowDisabled(false); + } else if (switchingWidget == ui->networkFrame) { + ui->networkLabel->setShowDisabled(false); + /*} else if (switchingWidget == ui->printFrame) { + ui->printLabel->setShowDisabled(false);*/ + } else if (switchingWidget == ui->kdeConnectFrame) { + ui->kdeconnectLabel->setShowDisabled(false); + } +} + +void InfoPaneDropdown::on_showNotificationsContents_toggled(bool checked) { + if (checked) { + settings.setValue("notifications/lockScreen", "contents"); + } +} + +void InfoPaneDropdown::on_showNotificationsOnly_toggled(bool checked) { + if (checked) { + settings.setValue("notifications/lockScreen", "noContents"); + } +} + +void InfoPaneDropdown::on_showNotificationsNo_toggled(bool checked) { + if (checked) { + settings.setValue("notifications/lockScreen", "none"); + } +} + +void InfoPaneDropdown::on_stopwatchStart_clicked() { + if (stopwatchRunning) { + stopwatchRunning = false; + stopwatchTimeAdd += stopwatchTime.elapsed(); + + ui->stopwatchReset->setVisible(true); + ui->stopwatchStart->setText(tr("Start")); + ui->stopwatchStart->setIcon(QIcon::fromTheme("chronometer-start")); + } else { + stopwatchTime.restart(); + stopwatchRunning = true; + + ui->stopwatchReset->setVisible(false); + ui->stopwatchStart->setText(tr("Stop")); + ui->stopwatchStart->setIcon(QIcon::fromTheme("chronometer-pause")); + } +} + +void InfoPaneDropdown::on_stopwatchReset_clicked() { + stopwatchTimeAdd = 0; +} + +void InfoPaneDropdown::on_calendarTodayButton_clicked() { + ui->calendarWidget->setSelectedDate(QDate::currentDate()); +} + +void InfoPaneDropdown::on_MediaSwitch_toggled(bool checked) { + settings.setValue("notifications/mediaInsert", checked); +} + +void InfoPaneDropdown::on_lightColorThemeRadio_toggled(bool checked) { + if (checked) { + themeSettings->setValue("color/type", "light"); + updateAccentColourBox(); + resetStyle(); + changeDropDown(Settings, false); + } +} + +void InfoPaneDropdown::on_darkColorThemeRadio_toggled(bool checked) { + if (checked) { + themeSettings->setValue("color/type", "dark"); + updateAccentColourBox(); + resetStyle(); + changeDropDown(Settings, false); + } +} + +void InfoPaneDropdown::on_themeButtonColor_currentIndexChanged(int index) { + themeSettings->setValue("color/accent", index); + resetStyle(); +} + +void InfoPaneDropdown::on_systemFont_currentFontChanged(const QFont& f) { + themeSettings->setValue("fonts/defaultFamily", f.family()); + themeSettings->setValue("fonts/smallFamily", f.family()); + ui->systemFontSize->setValue(themeSettings->value("font/defaultSize", 10).toInt()); + //ui->systemFont->setFont(QFont(themeSettings->value("font/defaultFamily", defaultFont).toString(), themeSettings->value("font/defaultSize", 10).toInt())); +} + +void InfoPaneDropdown::on_batteryChartUpdateButton_clicked() { + updateBatteryChart(); +} + +//DBus Battery Info Structure +struct BatteryInfo { + uint time, state; + double value; +}; +Q_DECLARE_METATYPE(BatteryInfo) + +const QDBusArgument& operator<<(QDBusArgument& argument, const BatteryInfo& info) { + argument.beginStructure(); + argument << info.time << info.value << info.state; + argument.endStructure(); + return argument; +} + +const QDBusArgument& operator>>(const QDBusArgument& argument, BatteryInfo& info) { + argument.beginStructure(); + argument >> info.time >> info.value >> info.state; + argument.endStructure(); + return argument; +} + +//DBus WakeupsInfo Structure +struct WakeupsInfo { + bool process = false; + uint pid; + double wakeups; + QString path, description; +}; +Q_DECLARE_METATYPE(WakeupsInfo) + +const QDBusArgument& operator<<(QDBusArgument& argument, const WakeupsInfo& info) { + argument.beginStructure(); + argument << info.process << info.pid << info.wakeups << info.path << info.description; + argument.endStructure(); + return argument; +} + +const QDBusArgument& operator>>(const QDBusArgument& argument, WakeupsInfo& info) { + argument.beginStructure(); + argument >> info.process >> info.pid >> info.wakeups >> info.path >> info.description; + argument.endStructure(); + return argument; +} + +void InfoPaneDropdown::updateBatteryChart() { + if (ui->appsGraphButton->isChecked()) { + QDBusMessage dataMessage = QDBusMessage::createMethodCall("org.freedesktop.UPower", "/org/freedesktop/UPower/Wakeups", "org.freedesktop.UPower.Wakeups", "GetData"); + + QDBusReply dataMessageArgument = QDBusConnection::systemBus().call(dataMessage); + QList wakeups; + + if (dataMessageArgument.isValid()) { + QDBusArgument arrayArgument = dataMessageArgument.value(); + arrayArgument.beginArray(); + while (!arrayArgument.atEnd()) { + WakeupsInfo info; + arrayArgument >> info; + + if (info.process) { + int min = 0, max = wakeups.count(); + int insertIndex; + + while (max != min) { + insertIndex = ((max - min) / 2) + min; + if (wakeups.at(insertIndex).wakeups == info.wakeups) { //Goes here + break; + } else if (wakeups.at(insertIndex).wakeups < info.wakeups) { //Needs to go on left hand side + max = insertIndex - 1; + } else if (wakeups.at(insertIndex).wakeups > info.wakeups) { //Needs to go on right hand side + min = insertIndex + 1; + } + } + + wakeups.insert(insertIndex, info); + } + } + arrayArgument.endArray(); + + ui->appsGraph->clear(); + for (WakeupsInfo wakeup : wakeups) { + QListWidgetItem* item = new QListWidgetItem; + item->setText("[" + QString::number(wakeup.pid) + "] " + wakeup.path + " (" + wakeup.description + ")"); + ui->appsGraph->insertItem(0, item); + } + } + + } else { + for (QAbstractAxis* axis : batteryChart->axes()) { + batteryChart->removeAxis(axis); + axis->deleteLater(); + } + + QDBusMessage historyMessage = QDBusMessage::createMethodCall("org.freedesktop.UPower", updbus->defaultBattery().path(), "org.freedesktop.UPower.Device", "GetHistory"); + QVariantList historyMessageArguments; + + if (ui->chargeGraphButton->isChecked()) { + historyMessageArguments.append("charge"); + } else { + historyMessageArguments.append("rate"); + } + + historyMessageArguments.append((uint) 0); //Get surplus data so we can plot some data off the left of the graph + historyMessageArguments.append((uint) 10000); + historyMessage.setArguments(historyMessageArguments); + + QDBusReply historyArgument = QDBusConnection::systemBus().call(historyMessage); + + QLineSeries* batteryChartData = new QLineSeries; + QPen dataPen; + dataPen.setColor(this->palette().color(QPalette::Highlight)); + dataPen.setWidth(2 * getDPIScaling()); + batteryChartData->setPen(dataPen); + + QLineSeries* batteryChartTimeRemainingData = new QLineSeries; + //batteryChartTimeRemainingData->setColor(this->palette().color(QPalette::Disabled, QPalette::WindowText)); + batteryChartTimeRemainingData->setBrush(QBrush(this->palette().color(QPalette::Disabled, QPalette::WindowText))); + + QPen remainingTimePen; + remainingTimePen.setColor(this->palette().color(QPalette::Disabled, QPalette::Highlight)); + remainingTimePen.setDashPattern(QVector() << 3 << 3); + remainingTimePen.setDashOffset(3); + remainingTimePen.setWidth(2 * getDPIScaling()); + batteryChartTimeRemainingData->setPen(remainingTimePen); + + QDateTime remainingTime = updbus->batteryTimeRemaining(); + + int firstDateTime = QDateTime::currentSecsSinceEpoch() / 60; + qint64 msecsSinceFull = -1; + uint lastState = -1; + bool takeNextSinceLastFull = false; + if (historyArgument.isValid()) { + QDBusArgument arrayArgument = historyArgument.value(); + arrayArgument.beginArray(); + while (!arrayArgument.atEnd()) { + BatteryInfo info; + arrayArgument >> info; + + qint64 msecs = info.time; + msecs = msecs * 1000; + + if (info.value >= 90 && info.state == 2 && lastState == 1 && msecsSinceFull < msecs) { + takeNextSinceLastFull = true; + } else if (takeNextSinceLastFull) { + takeNextSinceLastFull = false; + msecsSinceFull = msecs; + } + lastState = info.state; + + if (info.value != 0 && info.state != 0) { + batteryChartData->append(msecs, info.value); + if (firstDateTime > info.time / 60) { + firstDateTime = info.time / 60; + } + } + } + arrayArgument.endArray(); + batteryChartData->append(QDateTime::currentMSecsSinceEpoch(), batteryChartData->at(batteryChartData->count() - 1).y()); + + if (remainingTime.isValid() && ui->batteryChartShowProjected->isChecked() && ui->chargeGraphButton->isChecked()) { + QDateTime lastDateTime = QDateTime::fromMSecsSinceEpoch(batteryChartData->at(batteryChartData->count() - 1).x()); + batteryChartTimeRemainingData->append(batteryChartData->at(batteryChartData->count() - 1)); + QDateTime endDateTime = lastDateTime.addMSecs(remainingTime.toMSecsSinceEpoch()); + if (updbus->charging()) { + batteryChartTimeRemainingData->append(endDateTime.toMSecsSinceEpoch(), 100); + } else { + batteryChartTimeRemainingData->append(endDateTime.toMSecsSinceEpoch(), 0); + } + } + } + + batteryChart->removeAllSeries(); + batteryChart->addSeries(batteryChartData); + batteryChart->addSeries(batteryChartTimeRemainingData); + + xAxis = new QDateTimeAxis; + if (ui->chargeGraphButton->isChecked()) { + if (remainingTime.isValid() && ui->batteryChartShowProjected->isChecked()) { + xAxis->setMax(QDateTime::fromMSecsSinceEpoch(batteryChartData->at(batteryChartData->count() - 1).x()).addMSecs(remainingTime.toMSecsSinceEpoch())); + } else { + xAxis->setMax(QDateTime::currentDateTime()); + } + + QDateTime oneDay = xAxis->max().addDays(-1); + if (msecsSinceFull == -1 || msecsSinceFull < oneDay.toMSecsSinceEpoch()) { + xAxis->setMin(oneDay); + } else { + xAxis->setMin(QDateTime::fromMSecsSinceEpoch(msecsSinceFull)); + } + } else { + xAxis->setMax(QDateTime::currentDateTime()); + xAxis->setMin(xAxis->max().addSecs(-43200)); //Half a day + } + batteryChart->addAxis(xAxis, Qt::AlignBottom); + xAxis->setLabelsColor(this->palette().color(QPalette::WindowText)); + xAxis->setFormat("hh:mm"); + xAxis->setTickCount(9); + batteryChartData->attachAxis(xAxis); + batteryChartTimeRemainingData->attachAxis(xAxis); + + /*connect(xAxis, &QDateTimeAxis::rangeChanged, [=](QDateTime min, QDateTime max) { + ui->BatteryChargeScrollBar->setMaximum(max.toMSecsSinceEpoch() - min.toMSecsSinceEpoch()); + });*/ + + chartScrolling = true; + int currentSecsSinceEpoch = QDateTime::currentSecsSinceEpoch(); + ui->BatteryChargeScrollBar->setMinimum(0); + ui->BatteryChargeScrollBar->setMaximum(currentSecsSinceEpoch / 60 - firstDateTime); + ui->BatteryChargeScrollBar->setValue(currentSecsSinceEpoch / 60 - firstDateTime); + startValue = currentSecsSinceEpoch / 60 - firstDateTime; + chartScrolling = false; + + QValueAxis* yAxis = new QValueAxis; + if (ui->chargeGraphButton->isChecked()) { + yAxis->setLabelFormat("%i%%"); + yAxis->setMax(100); + } else { + yAxis->setLabelFormat("%i W"); + yAxis->setMax(40); + } + + yAxis->setMin(0); + yAxis->setLabelsColor(this->palette().color(QPalette::WindowText)); + batteryChart->addAxis(yAxis, Qt::AlignLeft); + batteryChartData->attachAxis(yAxis); + batteryChartTimeRemainingData->attachAxis(yAxis); + + ui->batteryChartLastUpdate->setText(tr("Last updated %1").arg(QDateTime::currentDateTime().toString("hh:mm:ss"))); + } +} + +void InfoPaneDropdown::on_batteryChartShowProjected_toggled(bool checked) { + Q_UNUSED(checked) + updateBatteryChart(); +} + +void InfoPaneDropdown::on_upArrow_clicked() { + this->close(); +} + +void InfoPaneDropdown::on_PowerStretchSwitch_toggled(bool checked) { + updbus->setPowerStretch(checked); + emit batteryStretchChanged(checked); +} + +void InfoPaneDropdown::doNetworkCheck() { + if (updbus->powerStretch()) { + //Always set networkOk to ok because we don't update when power stretch is on + networkOk = Ok; + } else { + //Do some network checks to see if network is working + + QDBusInterface i("org.freedesktop.NetworkManager", "/org/freedesktop/NetworkManager", "org.freedesktop.NetworkManager", QDBusConnection::systemBus(), this); + int connectivity = i.property("Connectivity").toUInt(); + if (connectivity == 2) { + if (networkOk != BehindPortal) { + //Notify user that they are behind a portal. + //Wait 10 seconds for startup or for connection notification + + QTimer::singleShot(10000, [ = ] { + QStringList actions; + actions.append("login"); + actions.append(tr("Log in to network")); + + QVariantMap hints; + hints.insert("category", "network.connected"); + hints.insert("transient", true); + + uint notificationId = ndbus->Notify("theShell", 0, "", tr("Network Login"), + tr("Your connection to the internet is blocked by a login page."), + actions, hints, 30000); + connect(ndbus, &NotificationsDBusAdaptor::ActionInvoked, [ = ](uint id, QString key) { + if (notificationId == id && key == "login") { + QProcess::startDetached("xdg-open http://nmcheck.gnome.org/"); + } + }); + }); + } + + networkOk = BehindPortal; + + //Reload the connectivity status + i.asyncCall("CheckConnectivity"); + return; + } else if (connectivity == 3) { + networkOk = Unspecified; + + //Reload the connectivity status + i.asyncCall("CheckConnectivity"); + return; + } else { + networkOk = Ok; + } + + QNetworkAccessManager* manager = new QNetworkAccessManager; + if (manager->networkAccessible() == QNetworkAccessManager::NotAccessible) { + networkOk = Unspecified; + manager->deleteLater(); + + //Reload the connectivity status + i.asyncCall("CheckConnectivity"); + return; + } + manager->deleteLater(); + + //For some reason this crashes theShell so let's not do this (for now) + /*connect(manager, &QNetworkAccessManager::finished, [=](QNetworkReply* reply) { + if (reply->error() != QNetworkReply::NoError) { + networkOk = false; + } else { + networkOk = true; + } + manager->deleteLater(); + }); + manager->get(QNetworkRequest(QUrl("http://vicr123.github.io/")));*/ + + //Reload the connectivity status + i.asyncCall("CheckConnectivity"); + } +} + +void InfoPaneDropdown::dragDown(dropdownType showWith, int y) { + changeDropDown(showWith, false); + QRect screenGeometry = QApplication::desktop()->screenGeometry(); + + if (settings.value("bar/onTop", true).toBool()) { + this->setGeometry(screenGeometry.x(), screenGeometry.y() - screenGeometry.height() + y, screenGeometry.width(), screenGeometry.height() + 1); + } else { + this->setGeometry(screenGeometry.x(), screenGeometry.top() + y + screenGeometry.y(), screenGeometry.width(), screenGeometry.height() + 1); + } + + Atom DesktopWindowTypeAtom; + DesktopWindowTypeAtom = XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE_NORMAL", False); + XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE", False), + XA_ATOM, 32, PropModeReplace, (unsigned char*) &DesktopWindowTypeAtom, 1); //Change Window Type + + unsigned long desktop = 0xFFFFFFFF; + XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_DESKTOP", False), + XA_CARDINAL, 32, PropModeReplace, (unsigned char*) &desktop, 1); //Set visible on all desktops + + QDialog::show(); + + this->setFixedWidth(screenGeometry.width()); + this->setFixedHeight(screenGeometry.height()); + + //Get Current Brightness + QProcess* backlight = new QProcess(this); + backlight->start("xbacklight -get"); + backlight->waitForFinished(); + float output = ceil(QString(backlight->readAll()).toFloat()); + delete backlight; + + ui->brightnessSlider->setValue((int) output); + + previousDragY = y; +} + +void InfoPaneDropdown::completeDragDown() { + QRect screenGeometry = QApplication::desktop()->screenGeometry(); + + if ((QCursor::pos().y() - screenGeometry.top() < previousDragY && settings.value("bar/onTop", true).toBool()) || + (QCursor::pos().y() - screenGeometry.top() > previousDragY && !settings.value("bar/onTop", true).toBool())) { + this->close(); + } else { + tPropertyAnimation* a = new tPropertyAnimation(this, "geometry"); + a->setStartValue(this->geometry()); + a->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - (settings.value("bar/onTop", true).toBool() ? 0 : 1), this->width(), screenGeometry.height() + 1)); + a->setEasingCurve(QEasingCurve::OutCubic); + a->setDuration(500); + connect(a, SIGNAL(finished()), a, SLOT(deleteLater())); + a->start(); + } +} + +void InfoPaneDropdown::on_notificationSoundBox_currentIndexChanged(int index) { + QSoundEffect* sound = new QSoundEffect(); + switch (index) { + case 0: + settings.setValue("notifications/sound", "tripleping"); + sound->setSource(QUrl("qrc:/sounds/notifications/tripleping.wav")); + break; + case 1: + settings.setValue("notifications/sound", "upsidedown"); + sound->setSource(QUrl("qrc:/sounds/notifications/upsidedown.wav")); + break; + case 2: + settings.setValue("notifications/sound", "echo"); + sound->setSource(QUrl("qrc:/sounds/notifications/echo.wav")); + break; + } + sound->play(); + connect(sound, SIGNAL(playingChanged()), sound, SLOT(deleteLater())); +} + +void InfoPaneDropdown::setupUsersSettingsPane() { + ui->availableUsersWidget->clear(); + + QDBusMessage getUsersMessage = QDBusMessage::createMethodCall("org.freedesktop.Accounts", "/org/freedesktop/Accounts", "org.freedesktop.Accounts", "ListCachedUsers"); + QDBusReply> allUsers = QDBusConnection::systemBus().call(getUsersMessage); + if (allUsers.isValid()) { + for (QDBusObjectPath obj : allUsers.value()) { + QDBusInterface interface("org.freedesktop.Accounts", obj.path(), "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); + + QListWidgetItem* item = new QListWidgetItem(); + QString name = interface.property("RealName").toString(); + if (name == "") { + name = interface.property("UserName").toString(); + } + item->setText(name); + item->setIcon(QIcon::fromTheme("user")); + item->setData(Qt::UserRole, obj.path()); + ui->availableUsersWidget->addItem(item); + } + + QListWidgetItem* item = new QListWidgetItem(); + item->setIcon(QIcon::fromTheme("list-add")); + item->setText(tr("Add New User")); + item->setData(Qt::UserRole, "new"); + ui->availableUsersWidget->addItem(item); + } +} + +void InfoPaneDropdown::on_userSettingsNextButton_clicked() { + if (ui->availableUsersWidget->selectedItems().count() != 0) { + //Check Polkit authorization + PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.freedesktop.accounts.user-administration", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::None); + if (r == PolkitQt1::Authority::No) { + QMessageBox::warning(this, tr("Unauthorized"), tr("Polkit does not allow you to manage users on the system."), QMessageBox::Ok, QMessageBox::Ok); + return; + } else if (r == PolkitQt1::Authority::Challenge) { + LOWER_INFOPANE + PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.freedesktop.accounts.user-administration", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::AllowUserInteraction); + if (r != PolkitQt1::Authority::Yes) { + return; + } + } + + editingUserPath = ui->availableUsersWidget->selectedItems().first()->data(Qt::UserRole).toString(); + if (editingUserPath == "new") { + ui->userSettingsEditUserLabel->setText(tr("New User")); + ui->userSettingsFullName->setText(""); + ui->userSettingsUserName->setText(""); + ui->userSettingsPassword->setPlaceholderText(tr("(none)")); + ui->userSettingsPasswordCheck->setPlaceholderText(tr("(none)")); + ui->userSettingsDeleteUser->setVisible(false); + ui->userSettingsStandardAccount->setChecked(true); + ui->userSettingsAdminAccount->setChecked(false); + } else { + ui->userSettingsEditUserLabel->setText(tr("Edit User")); + QDBusInterface interface("org.freedesktop.Accounts", editingUserPath, "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); + int passwordMode = interface.property("PasswordMode").toInt(); + if (passwordMode == 0) { + ui->userSettingsPassword->setPlaceholderText(tr("(unchanged)")); + ui->userSettingsPasswordCheck->setPlaceholderText(tr("(unchanged)")); + } else if (passwordMode == 1) { + ui->userSettingsPassword->setPlaceholderText(tr("(set at next login)")); + ui->userSettingsPasswordCheck->setPlaceholderText(tr("(set at next login)")); + } else { + ui->userSettingsPassword->setPlaceholderText(tr("(none)")); + ui->userSettingsPasswordCheck->setPlaceholderText(tr("(none)")); + } + if (interface.property("AccountType").toInt() == 0) { + ui->userSettingsStandardAccount->setChecked(true); + ui->userSettingsAdminAccount->setChecked(false); + } else { + ui->userSettingsStandardAccount->setChecked(false); + ui->userSettingsAdminAccount->setChecked(true); + } + ui->userSettingsFullName->setText(interface.property("RealName").toString()); + ui->userSettingsUserName->setText(interface.property("UserName").toString()); + ui->userSettingsPasswordHint->setText(interface.property("PasswordHint").toString()); + ui->userSettingsDeleteUser->setVisible(true); + } + ui->userSettingsPassword->setText(""); + ui->userSettingsPasswordCheck->setText(""); + ui->userSettingsStackedWidget->setCurrentIndex(1); + } +} + +void InfoPaneDropdown::on_userSettingsCancelButton_clicked() { + ui->userSettingsStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_userSettingsApplyButton_clicked() { + if (ui->userSettingsPasswordCheck->text() != ui->userSettingsPassword->text()) { + QMessageBox::warning(this, tr("Password Check"), tr("The passwords don't match."), QMessageBox::Ok, QMessageBox::Ok); + return; + } + + if (ui->userSettingsUserName->text().contains(" ")) { + QMessageBox::warning(this, tr("Username"), tr("The username must not contain spaces."), QMessageBox::Ok, QMessageBox::Ok); + return; + } + + if (ui->userSettingsUserName->text().toLower() != ui->userSettingsUserName->text()) { + QMessageBox::warning(this, tr("Username"), tr("The username must not contain capital letters."), QMessageBox::Ok, QMessageBox::Ok); + return; + } + + if (editingUserPath == "new") { + QDBusMessage createMessage = QDBusMessage::createMethodCall("org.freedesktop.Accounts", "/org/freedesktop/Accounts", "org.freedesktop.Accounts", "CreateUser"); + QVariantList args; + args.append(ui->userSettingsUserName->text()); + args.append(ui->userSettingsFullName->text()); + args.append(0); + createMessage.setArguments(args); + + QDBusReply newUser = QDBusConnection::systemBus().call(createMessage); + if (newUser.error().isValid()) { + tToast* toast = new tToast(); + toast->setTitle("Couldn't create user"); + toast->setText(newUser.error().message()); + connect(toast, SIGNAL(dismissed()), toast, SLOT(deleteLater())); + toast->show(this); + return; + } else { + editingUserPath = newUser.value().path(); + } + } + + QDBusInterface interface("org.freedesktop.Accounts", editingUserPath, "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); + QDBusMessage setUserNameMessage = interface.call("SetUserName", ui->userSettingsUserName->text()); + if (setUserNameMessage.errorMessage() != "") { + tToast* toast = new tToast(); + toast->setTitle("Couldn't create user"); + toast->setText(setUserNameMessage.errorMessage()); + connect(toast, SIGNAL(dismissed()), toast, SLOT(deleteLater())); + toast->show(this); + return; + } + interface.call("SetRealName", ui->userSettingsFullName->text()); + + if (ui->userSettingsAdminAccount->isChecked()) { + interface.call("SetAccountType", 1); + } else { + interface.call("SetAccountType", 0); + } + + if (ui->userSettingsPassword->text() != "") { + interface.call("SetPasswordMode", 0); + + //Crypt password + QByteArray characters = "0123456789ABCDEFGHIJKLMNOPQRSTUVXYZabcdefghijklmnopqrstuvxyz./"; + QByteArray salt("$6$"); + for (int i = 0; i < 16; i++) { + salt.append(characters.at((qrand() % characters.count()))); + } + QString cryptedPassword = QString::fromLatin1(crypt(ui->userSettingsPassword->text().toUtf8(), salt.constData())); + + interface.call("SetPassword", cryptedPassword, ui->userSettingsPasswordHint->text()); + } else { + if (editingUserPath == "new") { + interface.call("SetPasswordMode", 2); + interface.call("SetPasswordHint", ui->userSettingsPasswordHint->text()); + } + } + + setupUsersSettingsPane(); + ui->userSettingsStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_userSettingsFullName_textEdited(const QString& arg1) { + ui->userSettingsUserName->setText(arg1.toLower().split(" ").first()); +} + +void InfoPaneDropdown::on_userSettingsDeleteUser_clicked() { + ui->userSettingsStackedWidget->setCurrentIndex(2); +} + +void InfoPaneDropdown::on_userSettingsCancelDeleteUser_clicked() { + ui->userSettingsStackedWidget->setCurrentIndex(1); +} + +void InfoPaneDropdown::on_userSettingsDeleteUserOnly_clicked() { + QDBusInterface interface("org.freedesktop.Accounts", editingUserPath, "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); + qlonglong uid = interface.property("Uid").toLongLong(); + + QDBusMessage deleteMessage = QDBusMessage::createMethodCall("org.freedesktop.Accounts", "/org/freedesktop/Accounts", "org.freedesktop.Accounts", "DeleteUser"); + QVariantList args; + args.append(uid); + args.append(false); + deleteMessage.setArguments(args); + QDBusConnection::systemBus().call(deleteMessage); + + setupUsersSettingsPane(); + ui->userSettingsStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_userSettingsDeleteUserAndData_clicked() { + QDBusInterface interface("org.freedesktop.Accounts", editingUserPath, "org.freedesktop.Accounts.User", QDBusConnection::systemBus()); + qlonglong uid = interface.property("Uid").toLongLong(); + + QDBusMessage deleteMessage = QDBusMessage::createMethodCall("org.freedesktop.Accounts", "/org/freedesktop/Accounts", "org.freedesktop.Accounts", "DeleteUser"); + QVariantList args; + args.append(uid); + args.append(true); + deleteMessage.setArguments(args); + QDBusConnection::systemBus().call(deleteMessage); + + setupUsersSettingsPane(); + ui->userSettingsStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::setupDateTimeSettingsPane() { + launchDateTimeService(); + + QDateTime current = QDateTime::currentDateTime(); + ui->dateTimeSetDate->setSelectedDate(current.date()); + ui->dateTimeSetTime->setTime(current.time()); + + QDBusInterface dateTimeInterface("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", QDBusConnection::systemBus()); + bool isNTPEnabled = dateTimeInterface.property("NTP").toBool(); + ui->DateTimeNTPSwitch->setChecked(isNTPEnabled); +} + +void InfoPaneDropdown::launchDateTimeService() { + QDBusMessage getMessage = QDBusMessage::createMethodCall("org.freedesktop.DBus", "/", "org.freedesktop.DBus", "ListActivatableNames"); + QDBusReply reply = QDBusConnection::systemBus().call(getMessage); + if (!reply.value().contains("org.freedesktop.timedate1")) { + qDebug() << "Can't set date and time"; + return; + } + + /*QDBusMessage launchMessage = QDBusMessage::createMethodCall("org.freedesktop.DBus", "/", "org.freedesktop.DBus", "StartServiceByName"); + QVariantList args; + args.append("org.freedesktop.timedate1"); + args.append((uint) 0); + launchMessage.setArguments(args); + + QDBusConnection::systemBus().call(launchMessage);*/ + + QDBusConnection::systemBus().interface()->startService("org.freedesktop.timedate1"); +} + +void InfoPaneDropdown::on_dateTimeSetDateTimeButton_clicked() { + QDateTime newTime; + newTime.setDate(ui->dateTimeSetDate->selectedDate()); + newTime.setTime(ui->dateTimeSetTime->time()); + + qlonglong time = newTime.toMSecsSinceEpoch() * 1000; + + launchDateTimeService(); + + QDBusMessage setMessage = QDBusMessage::createMethodCall("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "SetTime"); + QVariantList args; + args.append(time); + args.append(false); + args.append(true); + setMessage.setArguments(args); + QDBusConnection::systemBus().call(setMessage); + + setupDateTimeSettingsPane(); + updateDSTNotification(); +} + +void InfoPaneDropdown::on_DateTimeNTPSwitch_toggled(bool checked) { + if (checked) { + ui->dateTimeSetDate->setEnabled(false); + ui->dateTimeSetTime->setEnabled(false); + ui->dateTimeSetDateTimeButton->setEnabled(false); + } else { + ui->dateTimeSetDate->setEnabled(true); + ui->dateTimeSetTime->setEnabled(true); + ui->dateTimeSetDateTimeButton->setEnabled(true); + } + + launchDateTimeService(); + + QDBusMessage setMessage = QDBusMessage::createMethodCall("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", "SetNTP"); + QVariantList args; + args.append(checked); + args.append(true); + setMessage.setArguments(args); + QDBusConnection::systemBus().call(setMessage); + + setupDateTimeSettingsPane(); +} + +void InfoPaneDropdown::on_localeList_currentRowChanged(int currentRow) { + //Show the splash screen (if available) + emit dbusSignals->ShowSplash(); + + switch (currentRow) { + case Internationalisation::enUS: + settings.setValue("locale/language", "en_US"); + break; + case Internationalisation::enGB: + settings.setValue("locale/language", "en_GB"); + break; + case Internationalisation::enAU: + settings.setValue("locale/language", "en_AU"); + break; + case Internationalisation::enNZ: + settings.setValue("locale/language", "en_NZ"); + break; + case Internationalisation::viVN: + settings.setValue("locale/language", "vi_VN"); + break; + case Internationalisation::daDK: + settings.setValue("locale/language", "da_DK"); + break; + case Internationalisation::ptBR: + settings.setValue("locale/language", "pt_BR"); + break; + case Internationalisation::arSA: + settings.setValue("locale/language", "ar_SA"); + break; + case Internationalisation::zhCN: + settings.setValue("locale/language", "zh_CN"); + break; + case Internationalisation::nlNL: + settings.setValue("locale/language", "nl_NL"); + break; + case Internationalisation::miNZ: + settings.setValue("locale/language", "mi_NZ"); + break; + case Internationalisation::jaJP: + settings.setValue("locale/language", "ja_JP"); + break; + case Internationalisation::deDE: + settings.setValue("locale/language", "de_DE"); + break; + case Internationalisation::esES: + settings.setValue("locale/language", "es_ES"); + break; + case Internationalisation::ruRU: + settings.setValue("locale/language", "ru_RU"); + break; + case Internationalisation::svSE: + settings.setValue("locale/language", "sv_SE"); + break; + case Internationalisation::ltLT: + settings.setValue("locale/language", "lt_LT"); + break; + case Internationalisation::idID: + settings.setValue("locale/language", "id_ID"); + break; + case Internationalisation::auAU: + settings.setValue("locale/language", "au_AU"); + break; + case Internationalisation::nbNO: + settings.setValue("locale/language", "nb_NO"); + break; + case Internationalisation::arEG: + settings.setValue("locale/language", "ar_EG"); + break; + } + + QString localeName = settings.value("locale/language", "en_US").toString(); + qputenv("LANG", localeName.toUtf8()); + + QLocale defaultLocale(localeName); + QLocale::setDefault(defaultLocale); + + QApplication::setLayoutDirection(defaultLocale.textDirection()); + + qtTranslator->load("qt_" + defaultLocale.name(), QLibraryInfo::location(QLibraryInfo::TranslationsPath)); + QApplication::installTranslator(qtTranslator); + + if (defaultLocale.name() == "C") { + tsTranslator->load(localeName, QString(SHAREDIR) + "translations"); + } else { + tsTranslator->load(defaultLocale.name(), QString(SHAREDIR) + "translations"); + } + QApplication::installTranslator(tsTranslator); + + //Fill locale box + Internationalisation::fillLanguageBox(ui->localeList); + + //Process all events + QApplication::processEvents(); + + //Hide the splash screen since the language change is complete + emit dbusSignals->HideSplash(); +} + +void InfoPaneDropdown::on_StatusBarSwitch_toggled(bool checked) { + settings.setValue("bar/statusBar", checked); + updateStruts(); + + ui->AutoShowBarLabel->setEnabled(checked); + ui->AutoShowBarSwitch->setEnabled(checked); + ui->AutoShowBarExplanation->setEnabled(checked); +} + +void InfoPaneDropdown::on_TouchInputSwitch_toggled(bool checked) { + settings.setValue("input/touch", checked); +} + +void InfoPaneDropdown::on_quietModeSound_clicked() { + AudioMan->setQuietMode(AudioManager::none); + ui->quietModeSound->setChecked(true); +} + +void InfoPaneDropdown::on_quietModeNotification_clicked() { + AudioMan->setQuietMode(AudioManager::notifications); + ui->quietModeNotification->setChecked(true); +} + +void InfoPaneDropdown::on_quietModeMute_clicked() { + AudioMan->setQuietMode(AudioManager::mute); + ui->quietModeMute->setChecked(true); +} + +RemindersListModel::RemindersListModel(QObject* parent) : QAbstractListModel(parent) { + RemindersData = new QSettings("theSuite/theShell.reminders"); + RemindersData->beginGroup("reminders"); +} + +RemindersListModel::~RemindersListModel() { + RemindersData->endGroup(); + RemindersData->deleteLater(); +} + +int RemindersListModel::rowCount(const QModelIndex& parent) const { + Q_UNUSED(parent) + int count = RemindersData->beginReadArray("reminders"); + RemindersData->endArray(); + return count; +} + +QVariant RemindersListModel::data(const QModelIndex& index, int role) const { + QVariant returnValue; + + RemindersData->beginReadArray("reminders"); + RemindersData->setArrayIndex(index.row()); + if (role == Qt::DisplayRole) { + returnValue = RemindersData->value("title"); + } else if (role == Qt::UserRole) { + QDateTime activation = RemindersData->value("date").toDateTime(); + if (activation.daysTo(QDateTime::currentDateTime()) == 0) { + returnValue = activation.toString("hh:mm"); + } else if (activation.daysTo(QDateTime::currentDateTime()) < 7) { + returnValue = activation.toString("dddd"); + } else { + returnValue = activation.toString("ddd, dd MMM yyyy"); + } + } + + RemindersData->endArray(); + return returnValue; +} + +void RemindersListModel::updateData() { + emit dataChanged(index(0), index(rowCount())); +} + +RemindersDelegate::RemindersDelegate(QWidget* parent) : QStyledItemDelegate(parent) { + +} + +void RemindersDelegate::paint(QPainter* painter, const QStyleOptionViewItem& option, const QModelIndex& index) const { + painter->setFont(option.font); + + QRect textRect; + textRect.setLeft(6 * getDPIScaling()); + textRect.setTop(option.rect.top() + 6 * getDPIScaling()); + textRect.setBottom(option.rect.top() + option.fontMetrics.height() + 6 * getDPIScaling()); + textRect.setRight(option.rect.right()); + + QRect dateRect; + dateRect.setLeft(6 * getDPIScaling()); + dateRect.setTop(option.rect.top() + option.fontMetrics.height() + 8 * getDPIScaling()); + dateRect.setBottom(option.rect.top() + option.fontMetrics.height() * 2 + 6 * getDPIScaling()); + dateRect.setRight(option.rect.right()); + + if (option.state & QStyle::State_Selected) { + painter->setPen(Qt::transparent); + painter->setBrush(option.palette.color(QPalette::Highlight)); + painter->drawRect(option.rect); + painter->setBrush(Qt::transparent); + painter->setPen(option.palette.color(QPalette::HighlightedText)); + painter->drawText(textRect, index.data().toString()); + painter->drawText(dateRect, index.data(Qt::UserRole).toString()); + } else if (option.state & QStyle::State_MouseOver) { + QColor col = option.palette.color(QPalette::Highlight); + col.setAlpha(127); + painter->setBrush(col); + painter->setPen(Qt::transparent); + painter->drawRect(option.rect); + painter->setBrush(Qt::transparent); + painter->setPen(option.palette.color(QPalette::WindowText)); + painter->drawText(textRect, index.data().toString()); + painter->setPen(option.palette.color(QPalette::Disabled, QPalette::WindowText)); + painter->drawText(dateRect, index.data(Qt::UserRole).toString()); + } else { + painter->setPen(option.palette.color(QPalette::WindowText)); + painter->drawText(textRect, index.data().toString()); + painter->setPen(option.palette.color(QPalette::Disabled, QPalette::WindowText)); + painter->drawText(dateRect, index.data(Qt::UserRole).toString()); + } +} + +QSize RemindersDelegate::sizeHint(const QStyleOptionViewItem& option, const QModelIndex& index) const { + return QSize(option.fontMetrics.width(index.data().toString()), option.fontMetrics.height() * 2 + 14 * getDPIScaling()); +} + +void InfoPaneDropdown::on_ReminderCancel_clicked() { + ui->RemindersStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_ReminderNew_clicked() { + ui->ReminderTitle->setText(""); + ui->ReminderDate->setDateTime(QDateTime::currentDateTime().addSecs(3600)); //Current date + 1 hour + ui->RemindersStackedWidget->setCurrentIndex(1); +} + +void InfoPaneDropdown::on_ReminderCreate_clicked() { + if (ui->ReminderTitle->text() == "") { + return; + } + + QList> ReminderData; + + QSettings reminders("theSuite/theShell.reminders"); + reminders.beginGroup("reminders"); + int count = reminders.beginReadArray("reminders"); + + for (int i = 0; i < count; i++) { + reminders.setArrayIndex(i); + QPair data; + data.first = reminders.value("title").toString(); + data.second = reminders.value("date").toDateTime(); + ReminderData.append(data); + } + + QPair newData; + newData.first = ui->ReminderTitle->text(); + newData.second = ui->ReminderDate->dateTime().addSecs(-ui->ReminderDate->dateTime().time().second()); + ReminderData.append(newData); + + reminders.endArray(); + reminders.beginWriteArray("reminders"); + int i = 0; + for (QPair data : ReminderData) { + reminders.setArrayIndex(i); + reminders.setValue("title", data.first); + reminders.setValue("date", data.second); + i++; + } + reminders.endArray(); + reminders.endGroup(); + + ((RemindersListModel*) ui->RemindersList->model())->updateData(); + ui->RemindersStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_SuspendLockScreen_toggled(bool checked) { + settings.setValue("lockScreen/showOnSuspend", checked); +} + +void InfoPaneDropdown::on_BatteryChargeScrollBar_valueChanged(int value) { + if (!chartScrolling) { + chartScrolling = true; + batteryChart->scroll(value - startValue, 0); + startValue = value; + chartScrolling = false; + } +} + +void InfoPaneDropdown::on_chargeGraphButton_clicked() { + ui->chargeGraphButton->setChecked(true); + ui->rateGraphButton->setChecked(false); + ui->appsGraphButton->setChecked(false); + ui->batteryGraphStack->setCurrentIndex(0); + ui->batteryChartHeader->setText(tr("Charge History")); + ui->batteryChartShowProjected->setVisible(true); + updateBatteryChart(); +} + +void InfoPaneDropdown::on_rateGraphButton_clicked() { + ui->chargeGraphButton->setChecked(false); + ui->rateGraphButton->setChecked(true); + ui->appsGraphButton->setChecked(false); + ui->batteryGraphStack->setCurrentIndex(0); + ui->batteryChartHeader->setText(tr("Rate History")); + ui->batteryChartShowProjected->setVisible(false); + updateBatteryChart(); +} + +void InfoPaneDropdown::on_appsGraphButton_clicked() { + ui->chargeGraphButton->setChecked(false); + ui->rateGraphButton->setChecked(false); + ui->appsGraphButton->setChecked(true); + ui->batteryGraphStack->setCurrentIndex(1); + ui->batteryChartHeader->setText(tr("Application Power Usage")); + ui->batteryChartShowProjected->setVisible(false); + updateBatteryChart(); +} + +void InfoPaneDropdown::on_LargeTextSwitch_toggled(bool checked) { + themeSettings->setValue("accessibility/largeText", checked); +} + +void InfoPaneDropdown::on_HighContrastSwitch_toggled(bool checked) { + themeSettings->setValue("accessibility/highcontrast", checked); + setHeaderColour(QColor(0, 100, 255)); +} + +void InfoPaneDropdown::on_systemAnimationsAccessibilitySwitch_toggled(bool checked) { + themeSettings->setValue("accessibility/systemAnimations", checked); +} + +void InfoPaneDropdown::on_CapsNumLockBellSwitch_toggled(bool checked) { + themeSettings->setValue("accessibility/bellOnCapsNumLock", checked); +} + +void InfoPaneDropdown::on_FlightSwitch_toggled(bool checked) { + QDBusInterface i("org.freedesktop.NetworkManager", "/org/freedesktop/NetworkManager", "org.freedesktop.NetworkManager", QDBusConnection::systemBus(), this); + + //Set flags that persist between changes + settings.setValue("flightmode/on", checked); + if (checked) { + settings.setValue("flightmode/wifi", ui->WifiSwitch->isChecked()); + settings.setValue("flightmode/bt", ui->BluetoothSwitch->isChecked()); + + //Disable bluetooth and WiFi. + ui->WifiSwitch->setChecked(false); + ui->BluetoothSwitch->setChecked(false); + + //Disable WiMAX and mobile networking + i.setProperty("WwanEnabled", false); + i.setProperty("WimaxEnabled", false); + } else { + //Enable bluetooth and WiFi. + ui->WifiSwitch->setChecked(settings.value("flightmode/wifi", true).toBool()); + ui->BluetoothSwitch->setChecked(settings.value("flightmode/bt", true).toBool()); + + //Enable WiMAX and mobile networking + i.setProperty("WwanEnabled", true); + i.setProperty("WimaxEnabled", true); + } + + emit flightModeChanged(checked); + + //Don't disable the switch as they may be switched on during flight +} + +void InfoPaneDropdown::on_TwentyFourHourSwitch_toggled(bool checked) { + settings.setValue("time/use24hour", checked); +} + +void InfoPaneDropdown::on_systemIconTheme_currentIndexChanged(int index) { + themeSettings->setValue("icons/theme", ui->systemIconTheme->itemData(index).toString()); +} + +void InfoPaneDropdown::on_ReminderDelete_clicked() { + if (ui->RemindersList->selectionModel()->selectedRows().count() != 0) { + //Show delete screen + ui->RemindersStackedWidget->setCurrentIndex(2); + + ui->deleteReminderText->setText(ui->RemindersList->model()->data(ui->RemindersList->selectionModel()->selectedRows().first()).toString()); + ui->deleteReminderTime->setText(ui->RemindersList->model()->data(ui->RemindersList->selectionModel()->selectedRows().first(), Qt::UserRole).toString()); + } +} + +void InfoPaneDropdown::on_RemindersStackedWidget_currentChanged(int arg1) { + tVariantAnimation* height = new tVariantAnimation(); + height->setDuration(250); + height->setEasingCurve(QEasingCurve::InOutCubic); + height->setStartValue(ui->RemindersStackedWidget->height()); + if (arg1 == 0) { + height->setEndValue((int) (300 * getDPIScaling() - 10)); + //ui->ClockScrollArea->verticalScrollBar()->setEnabled(true); + ui->ClockScrollArea->setVerticalScrollBarPolicy(Qt::ScrollBarAsNeeded); + } else { + height->setEndValue(ui->ClockScrollArea->height() - 10); + //ui->ClockScrollArea->verticalScrollBar()->setEnabled(false); + ui->ClockScrollArea->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff); + } + connect(height, &tVariantAnimation::valueChanged, [ = ](QVariant value) { + ui->RemindersStackedWidget->setFixedHeight(value.toInt()); + ui->ClockScrollArea->verticalScrollBar()->setValue(ui->ClockScrollArea->verticalScrollBar()->maximum()); + }); + connect(height, &tVariantAnimation::finished, [ = ] { + ui->ClockScrollArea->verticalScrollBar()->setValue(ui->ClockScrollArea->verticalScrollBar()->maximum()); + }); + connect(height, SIGNAL(finished()), height, SLOT(deleteLater())); + height->start(); +} + +void InfoPaneDropdown::on_ReminderDeleteCancel_clicked() { + //Go back to normal screen + ui->RemindersStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_ReminderDeleteButton_clicked() { + QList> ReminderData; + + QSettings reminders("theSuite/theShell.reminders"); + reminders.beginGroup("reminders"); + int count = reminders.beginReadArray("reminders"); + + for (int i = 0; i < count; i++) { + reminders.setArrayIndex(i); + QPair data; + data.first = reminders.value("title").toString(); + data.second = reminders.value("date").toDateTime(); + ReminderData.append(data); + } + + reminders.endArray(); + + ReminderData.removeAt(ui->RemindersList->selectionModel()->selectedIndexes().at(0).row()); + + reminders.beginWriteArray("reminders"); + int i = 0; + for (QPair data : ReminderData) { + reminders.setArrayIndex(i); + reminders.setValue("title", data.first); + reminders.setValue("date", data.second); + i++; + } + reminders.endArray(); + reminders.endGroup(); + + ((RemindersListModel*) ui->RemindersList->model())->updateData(); + ui->RemindersStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_AttenuateSwitch_toggled(bool checked) { + settings.setValue("notifications/attenuate", checked); +} + +void InfoPaneDropdown::on_BarOnBottom_toggled(bool checked) { + settings.setValue("bar/onTop", !checked); + updateStruts(); +} + +void InfoPaneDropdown::updateStruts() { + emit updateStrutsSignal(); + + if (settings.value("bar/onTop", true).toBool()) { + ((QBoxLayout*) this->layout())->setDirection(QBoxLayout::TopToBottom); + ((QBoxLayout*) ui->partFrame->layout())->setDirection(QBoxLayout::TopToBottom); + ((QBoxLayout*) ui->settingsFrame->layout())->setDirection(QBoxLayout::TopToBottom); + ((QBoxLayout*) ui->kdeConnectFrame->layout())->setDirection(QBoxLayout::TopToBottom); + ui->upArrow->setPixmap(QIcon::fromTheme("go-up").pixmap(16 * getDPIScaling(), 16 * getDPIScaling())); + } else { + ((QBoxLayout*) this->layout())->setDirection(QBoxLayout::BottomToTop); + ((QBoxLayout*) ui->partFrame->layout())->setDirection(QBoxLayout::BottomToTop); + ((QBoxLayout*) ui->settingsFrame->layout())->setDirection(QBoxLayout::BottomToTop); + ((QBoxLayout*) ui->kdeConnectFrame->layout())->setDirection(QBoxLayout::BottomToTop); + ui->upArrow->setPixmap(QIcon::fromTheme("go-down").pixmap(16 * getDPIScaling(), 16 * getDPIScaling())); + } +} + +void InfoPaneDropdown::on_systemWidgetTheme_currentIndexChanged(int index) { + themeSettings->setValue("style/name", ui->systemWidgetTheme->itemData(index).toString()); + resetStyle(); +} + +void InfoPaneDropdown::resetStyle() { + emit dbusSignals->ThemeChanged(); +} + +void InfoPaneDropdown::on_decorativeColorThemeRadio_toggled(bool checked) { + if (checked) { + themeSettings->setValue("color/type", "decorative"); + updateAccentColourBox(); + resetStyle(); + } +} + +void InfoPaneDropdown::on_SoundFeedbackSoundSwitch_toggled(bool checked) { + settings.setValue("sound/feedbackSound", checked); +} + +void InfoPaneDropdown::on_VolumeOverdriveSwitch_toggled(bool checked) { + settings.setValue("sound/volumeOverdrive", checked); +} + +void InfoPaneDropdown::updateAccentColourBox() { + //Set up theme button combo box + int themeAccentColorIndex = themeSettings->value("color/accent", 0).toInt(); + + ui->themeButtonColor->clear(); + if (themeSettings->value("color/type", "dark") == "decorative") { + if (themeAccentColorIndex > 1) themeAccentColorIndex = 0; + ui->themeButtonColor->addItem(tr("Oxygen")); + ui->themeButtonColor->addItem(tr("Breeze")); + } else { + if (themeAccentColorIndex > 4) themeAccentColorIndex = 0; + ui->themeButtonColor->addItem(tr("Blue")); + ui->themeButtonColor->addItem(tr("Green")); + ui->themeButtonColor->addItem(tr("Orange")); + ui->themeButtonColor->addItem(tr("Pink")); + ui->themeButtonColor->addItem(tr("Turquoise")); + + ui->themeButtonColor->setCurrentIndex(themeAccentColorIndex); + } +} + +void InfoPaneDropdown::on_dpi100_toggled(bool checked) { + if (checked) { + sessionSettings->setValue("screen/dpi", 96); + } +} + +void InfoPaneDropdown::on_dpi150_toggled(bool checked) { + if (checked) { + sessionSettings->setValue("screen/dpi", 144); + } +} + +void InfoPaneDropdown::on_dpi200_toggled(bool checked) { + if (checked) { + sessionSettings->setValue("screen/dpi", 192); + } +} + +void InfoPaneDropdown::on_dpi300_toggled(bool checked) { + if (checked) { + sessionSettings->setValue("screen/dpi", 288); + } +} + +void InfoPaneDropdown::on_AutoShowBarSwitch_toggled(bool checked) { + settings.setValue("bar/autoshow", checked); +} + +void InfoPaneDropdown::on_userSettingsAdminAccount_toggled(bool checked) { + if (checked) { + ui->userSettingsStandardAccount->setChecked(false); + ui->userSettingsAdminAccount->setChecked(true); + } +} + +void InfoPaneDropdown::on_userSettingsStandardAccount_toggled(bool checked) { + if (checked) { + ui->userSettingsStandardAccount->setChecked(true); + ui->userSettingsAdminAccount->setChecked(false); + } +} + +void InfoPaneDropdown::notificationAction(uint id, QString action) { + if (id == timerNotificationId) { + //Preserve old timer in case user wants to restart it + QTime lastTimer = this->lastTimer; + + ringtone->stop(); + AudioMan->restoreStreams(); + timerNotificationId = 0; + + if (action == "+0.5") { + startTimer(QTime(0, 0, 30)); + } else if (action == "+1") { + startTimer(QTime(0, 1)); + } else if (action == "+2") { + startTimer(QTime(0, 2)); + } else if (action == "+5") { + startTimer(QTime(0, 5)); + } else if (action == "+10") { + startTimer(QTime(0, 10)); + } else if (action == "restart") { + startTimer(lastTimer); + } + this->lastTimer = lastTimer; + } +} + +void InfoPaneDropdown::updateAutostart() { + ui->autostartList->clear(); + + QDir autostartDir(QDir::homePath() + "/.config/autostart"); + for (QString fileName : autostartDir.entryList(QDir::NoDotAndDotDot | QDir::Files)) { + QString file = QDir::homePath() + "/.config/autostart/" + fileName; + QFile autostartFile(file); + autostartFile.open(QFile::ReadOnly); + QString data = autostartFile.readAll(); + autostartFile.close(); + + QString name = fileName; + QString icon = ""; + bool enabled = true; + bool validEntry = true; + + for (QString line : data.split("\n")) { + QString data = line.mid(line.indexOf("=") + 1); + if (line.startsWith("name=", Qt::CaseInsensitive)) { + name = data; + } else if (line.startsWith("onlyshowin=", Qt::CaseInsensitive)) { + if (!data.contains("theshell", Qt::CaseInsensitive)) { + validEntry = false; + } + } else if (line.startsWith("notshowin=", Qt::CaseInsensitive)) { + if (data.contains("theshell", Qt::CaseInsensitive)) { + validEntry = false; + } + } else if (line.startsWith("hidden=", Qt::CaseInsensitive)) { + if (data.toLower() == "true") { + enabled = false; + } + } else if (line.startsWith("icon=")) { + icon = data; + } + } + + if (validEntry) { + QListWidgetItem* item = new QListWidgetItem(); + item->setFlags(item->flags() | Qt::ItemIsUserCheckable); + if (enabled) { + item->setCheckState(Qt::Checked); + } else { + item->setCheckState(Qt::Unchecked); + } + if (icon != "") { + item->setIcon(QIcon::fromTheme(icon)); + } + item->setText(name); + item->setData(Qt::UserRole, file); + + ui->autostartList->addItem(item); + } + } +} +void InfoPaneDropdown::on_autostartList_itemChanged(QListWidgetItem* item) { + QFile file(item->data(Qt::UserRole).toString()); + + file.open(QFile::ReadOnly); + QString data = file.readAll(); + file.close(); + + QString rewriteData; + + for (QString line : data.split("\n")) { + if (!line.startsWith("hidden", Qt::CaseInsensitive)) { + rewriteData.append(line + "\n"); + } + } + + if (item->checkState() == Qt::Unchecked) { + rewriteData.append("Hidden=true\n"); + } + + file.open(QFile::WriteOnly); + file.write(rewriteData.toUtf8()); + file.close(); + + this->updateAutostart(); +} + +void InfoPaneDropdown::on_backAutoStartApps_clicked() { + ui->startupStack->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_pushButton_4_clicked() { + ui->startupStack->setCurrentIndex(1); + + AppsListModel* appsListModel = new AppsListModel(); + ui->autostartAppList->setModel(appsListModel); + ui->autostartAppList->setItemDelegate(new AppsDelegate(nullptr, false)); +} + +void InfoPaneDropdown::on_backAutoStartNewApp_clicked() { + ui->startupStack->setCurrentIndex(1); +} + +void InfoPaneDropdown::on_autostartAppList_clicked(const QModelIndex& index) { + App app = index.data(Qt::UserRole + 3).value(); + + ui->autostartAppName->setText(app.name()); + ui->autostartAppCommand->setText(app.command().trimmed()); + ui->autostartInTheshell->setChecked(false); + + ui->startupStack->setCurrentIndex(2); +} + +void InfoPaneDropdown::on_enterCommandAutoStartApps_clicked() { + ui->autostartAppName->setText(""); + ui->autostartAppCommand->setText(""); + ui->autostartInTheshell->setChecked(false); + ui->startupStack->setCurrentIndex(2); +} + +void InfoPaneDropdown::on_addAutostartApp_clicked() { + QString desktopEntryData; + desktopEntryData.append("[Desktop Entry]\n"); + desktopEntryData.append("Type=Application\n"); + desktopEntryData.append("Version=1.0\n"); + desktopEntryData.append("Name=" + ui->autostartAppName->text() + "\n"); + desktopEntryData.append("Exec=" + ui->autostartAppCommand->text() + "\n"); + desktopEntryData.append("Terminal=false\n"); + if (ui->autostartInTheshell->isChecked()) { + desktopEntryData.append("OnlyShowIn=theshell;"); + } + + QFile desktopEntry(QDir::homePath() + "/.config/autostart/" + ui->autostartAppName->text().toLower().replace(" ", "_").append(".desktop")); + + if (desktopEntry.exists()) { + if (QMessageBox::warning(this, "Autostart Definition", "There is already an autostart definition for this app. Do you want to overwrite it?", QMessageBox::Yes | QMessageBox::No, QMessageBox::No) == QMessageBox::No) { + return; + } + } + + desktopEntry.open(QFile::WriteOnly); + desktopEntry.write(desktopEntryData.toUtf8()); + desktopEntry.close(); + + updateAutostart(); + ui->startupStack->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_redshiftSwitch_toggled(bool checked) { + if (effectiveRedshiftOn) { + if (checked) { //Turn Redshift back on + overrideRedshift = 0; + } else { //Temporarily disable Redshift + overrideRedshift = 1; + } + } else { + if (checked) { //Temporarily enable Redshift + overrideRedshift = 2; + } else { //Turn Redshift back off + overrideRedshift = 0; + } + } +} + +void InfoPaneDropdown::on_grayColorThemeRadio_toggled(bool checked) { + if (checked) { + themeSettings->setValue("color/type", "gray"); + updateAccentColourBox(); + resetStyle(); + changeDropDown(Settings, false); + } +} + +void InfoPaneDropdown::on_AppNotifications_currentItemChanged(QListWidgetItem* current, QListWidgetItem* previous) { + if (current == NULL) { + ui->appNotificationsPane->setEnabled(false); + ui->appNotificationsConfigureLock->setVisible(false); + } else { + ui->appNotificationsTitle->setText(tr("Notifications for %1").arg(current->text())); + ui->appAllowNotifications->setChecked(notificationAppSettings->value(current->text() + "/allow", true).toBool()); + ui->appAllowSounds->setChecked(notificationAppSettings->value(current->text() + "/sounds", true).toBool()); + ui->appAllowPopup->setChecked(notificationAppSettings->value(current->text() + "/popup", true).toBool()); + ui->appBypassQuiet->setChecked(notificationAppSettings->value(current->text() + "/bypassQuiet", false).toBool()); + + if (current->text() == "theShell") { + ui->appNotificationsPane->setEnabled(false); + ui->appNotificationsConfigureLock->setText(tr("You can't configure notifications for %1").arg(current->text())); + ui->appNotificationsConfigureLock->setVisible(true); + } else { + ui->appNotificationsPane->setEnabled(true); + ui->appNotificationsConfigureLock->setVisible(false); + } + } +} + +void InfoPaneDropdown::on_appAllowNotifications_toggled(bool checked) { + if (ui->AppNotifications->currentItem() != NULL) { + notificationAppSettings->setValue(ui->AppNotifications->currentItem()->text() + "/allow", checked); + } +} + +void InfoPaneDropdown::on_appAllowSounds_toggled(bool checked) { + if (ui->AppNotifications->currentItem() != NULL) { + notificationAppSettings->setValue(ui->AppNotifications->currentItem()->text() + "/sounds", checked); + } +} + +void InfoPaneDropdown::on_appAllowPopup_toggled(bool checked) { + if (ui->AppNotifications->currentItem() != NULL) { + notificationAppSettings->setValue(ui->AppNotifications->currentItem()->text() + "/popup", checked); + } +} + +void InfoPaneDropdown::on_appBypassQuiet_toggled(bool checked) { + if (ui->AppNotifications->currentItem() != NULL) { + notificationAppSettings->setValue(ui->AppNotifications->currentItem()->text() + "/bypassQuiet", checked); + } +} + +void InfoPaneDropdown::on_SetSystemTimezoneButton_clicked() { + ui->TimezoneStackedWidget->setCurrentIndex(1); + + launchDateTimeService(); + QDBusInterface dateTimeInterface("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", QDBusConnection::systemBus()); + QString currentTimezone = dateTimeInterface.property("Timezone").toString(); + + timezoneData = QJsonObject(); + + ui->timezoneList->clear(); + QFile tzInfo("/usr/share/zoneinfo/zone.tab"); + tzInfo.open(QFile::ReadOnly); + while (!tzInfo.atEnd()) { + QString tzLine = tzInfo.readLine(); + if (!tzLine.startsWith("#")) { + QStringList parts = tzLine.trimmed().split("\t", QString::SkipEmptyParts); + if (parts.length() >= 3) { + QString region = parts.at(2).left(parts.at(2).indexOf("/")); + QString city = parts.at(2).mid(parts.at(2).indexOf("/") + 1); + + if (!timezoneData.contains(region)) { + QListWidgetItem* i = new QListWidgetItem(); + i->setText(region); + ui->timezoneList->addItem(i); + timezoneData.insert(region, QJsonArray()); + } + + QJsonObject cityData; + cityData.insert("name", city); + cityData.insert("country", parts.at(0).toLower()); + cityData.insert("descriptor", parts.at(2)); + if (parts.at(2) == currentTimezone) { + cityData.insert("selected", true); + } else { + cityData.insert("selected", false); + } + + QJsonArray a = timezoneData.value(region).toArray(); + a.append(cityData); + timezoneData.insert(region, a); + } + } + } + tzInfo.close(); + + ui->setTimezoneButton->setEnabled(false); + ui->timezoneCityList->clear(); +} + +void InfoPaneDropdown::on_backTimezone_clicked() { + ui->TimezoneStackedWidget->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_setTimezoneButton_clicked() { + ui->TimezoneStackedWidget->setCurrentIndex(0); + + //Set the timezone + LOWER_INFOPANE + launchDateTimeService(); + QDBusInterface dateTimeInterface("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", QDBusConnection::systemBus()); + QDBusPendingCallWatcher* w = new QDBusPendingCallWatcher(dateTimeInterface.asyncCall("SetTimezone", ui->timezoneCityList->currentItem()->data(Qt::UserRole), true)); + connect(w, SIGNAL(finished(QDBusPendingCallWatcher*)), w, SLOT(deleteLater())); + connect(w, SIGNAL(finished(QDBusPendingCallWatcher*)), this, SLOT(updateDSTNotification())); +} + +void InfoPaneDropdown::on_timezoneList_currentItemChanged(QListWidgetItem* current, QListWidgetItem* previous) { + ui->timezoneCityList->clear(); + if (current != NULL) { + QJsonArray a = timezoneData.value(current->text()).toArray(); + for (QJsonValue v : a) { + QListWidgetItem* i = new QListWidgetItem(); + QJsonObject cityData = v.toObject(); + i->setText(cityData.value("name").toString().replace("_", " ")); + i->setData(Qt::UserRole, cityData.value("descriptor").toString()); + i->setIcon(QIcon::fromTheme("flag-" + cityData.value("country").toString(), QIcon::fromTheme("flag"))); + ui->timezoneCityList->addItem(i); + if (cityData.value("selected").toBool()) { + i->setSelected(true); + } + } + } +} + +void InfoPaneDropdown::on_timezoneCityList_currentRowChanged(int currentRow) { + if (currentRow == -1) { + ui->setTimezoneButton->setEnabled(false); + } else { + ui->setTimezoneButton->setEnabled(true); + } +} + +void InfoPaneDropdown::on_batteryScreenOff_valueChanged(int value) { + settings.setValue("power/batteryScreenOff", value); + if (value == 121) { + ui->batteryScreenOffLabel->setText(tr("Never")); + } else { + ui->batteryScreenOffLabel->setText(tr("%n min(s)", NULL, value).arg(QString::number(value))); + } +} + +void InfoPaneDropdown::on_batterySuspend_valueChanged(int value) { + settings.setValue("power/batterySuspend", value); + if (value == 121) { + ui->batterySuspendLabel->setText(tr("Never")); + } else { + ui->batterySuspendLabel->setText(tr("%n min(s)", NULL, value).arg(QString::number(value))); + } +} + +void InfoPaneDropdown::on_powerScreenOff_valueChanged(int value) { + settings.setValue("power/powerScreenOff", value); + if (value == 121) { + ui->powerScreenOffLabel->setText(tr("Never")); + } else { + ui->powerScreenOffLabel->setText(tr("%n min(s)", NULL, value).arg(QString::number(value))); + } +} + +void InfoPaneDropdown::on_powerSuspend_valueChanged(int value) { + settings.setValue("power/powerSuspend", value); + if (value == 121) { + ui->powerSuspendLabel->setText(tr("Never")); + } else { + ui->powerSuspendLabel->setText(tr("%n min(s)", NULL, value).arg(QString::number(value))); + } +} + +void InfoPaneDropdown::on_quietModeExpandButton_clicked() { + tVariantAnimation* anim = new tVariantAnimation(); + anim->setStartValue(ui->quietModeExtras->height()); + if (ui->quietModeExtras->height() == 0) { + anim->setEndValue(ui->quietModeExtras->sizeHint().height()); + ui->quietModeExpandButton->setIcon(QIcon::fromTheme("go-up")); + } else { + anim->setEndValue(0); + ui->quietModeExpandButton->setIcon(QIcon::fromTheme("go-down")); + } + anim->setDuration(500); + anim->setEasingCurve(QEasingCurve::OutCubic); + connect(anim, SIGNAL(finished()), anim, SLOT(deleteLater())); + connect(anim, &tVariantAnimation::valueChanged, [ = ](QVariant value) { + ui->quietModeExtras->setFixedHeight(value.toInt()); + }); + anim->start(); +} + +void InfoPaneDropdown::on_quietModeForeverButton_toggled(bool checked) { + if (checked) { + ui->quietModeTurnOffAtTimer->setVisible(false); + ui->quietModeTurnOffInTimer->setVisible(false); + AudioMan->setQuietModeResetTime(QDateTime::fromString("")); + } +} + +void InfoPaneDropdown::on_quietModeTurnOffIn_toggled(bool checked) { + if (checked) { + ui->quietModeTurnOffAtTimer->setVisible(false); + ui->quietModeTurnOffInTimer->setVisible(true); + + QDateTime oneHour = QDateTime::currentDateTime().addSecs(3600); + AudioMan->setQuietModeResetTime(oneHour); + ui->quietModeTurnOffInTimer->setTime(QTime(1, 0)); + } +} + +void InfoPaneDropdown::on_quietModeTurnOffAt_toggled(bool checked) { + + if (checked) { + ui->quietModeTurnOffAtTimer->setVisible(true); + ui->quietModeTurnOffInTimer->setVisible(false); + + QDateTime oneHour = QDateTime::currentDateTime().addSecs(3600); + AudioMan->setQuietModeResetTime(oneHour); + ui->quietModeTurnOffAtTimer->setDateTime(oneHour); + } +} + +void InfoPaneDropdown::on_quietModeTurnOffAtTimer_editingFinished() { + AudioMan->setQuietModeResetTime(ui->quietModeTurnOffAtTimer->dateTime()); +} + +void InfoPaneDropdown::on_quietModeTurnOffInTimer_editingFinished() { + QDateTime timeout = QDateTime::currentDateTime().addMSecs(ui->quietModeTurnOffInTimer->time().msecsSinceStartOfDay()); + AudioMan->setQuietModeResetTime(timeout); +} + +void InfoPaneDropdown::on_removeAutostartButton_clicked() { + if (ui->autostartList->currentItem() != nullptr) { + tToast* toast = new tToast(); + toast->setText("Autostart item has been removed."); + toast->setTitle("Remove Autostart Item"); + + QMap actions; + actions.insert("undo", "Undo"); + toast->setActions(actions); + + QListWidgetItem* i = ui->autostartList->takeItem(ui->autostartList->currentIndex().row()); + bool* deleteItem = new bool(true); + + connect(toast, &tToast::dismissed, [ = ] { + if (*deleteItem) { + QFile(i->data(Qt::UserRole).toString()).remove(); + delete i; + } + delete deleteItem; + toast->deleteLater(); + }); + connect(toast, &tToast::actionClicked, [ = ](QString key) { + *deleteItem = false; + ui->autostartList->addItem(i); + }); + toast->show(this); + } +} + +void InfoPaneDropdown::on_resetDeviceButton_clicked() { + QProcess::startDetached("scallop --reset"); + this->close(); +} + +void InfoPaneDropdown::changeEvent(QEvent* event) { + if (event->type() == QEvent::LanguageChange) { + ui->retranslateUi(this); + } + QDialog::changeEvent(event); +} + +void InfoPaneDropdown::on_sunlightRedshift_toggled(bool checked) { + settings.setValue("display/redshiftSunlightCycle", checked); + updateRedshiftTime(); +} + +void InfoPaneDropdown::updateRedshiftTime() { + if (!settings.value("display/redshiftSunlightCycle", false).toBool()) { + //Don't grab location if user doesn't want + ui->startRedshift->setEnabled(true); + ui->endRedshift->setEnabled(true); + return; + } + ui->startRedshift->setEnabled(false); + ui->endRedshift->setEnabled(false); + + QDBusMessage getMessage = QDBusMessage::createMethodCall("org.freedesktop.DBus", "/", "org.freedesktop.DBus", "ListActivatableNames"); + QDBusReply reply = QDBusConnection::systemBus().call(getMessage); + if (!reply.value().contains("org.freedesktop.GeoClue2")) { + qDebug() << "Can't start GeoClue"; + return; + } + + QDBusMessage launchMessage = QDBusMessage::createMethodCall("org.freedesktop.DBus", "/", "org.freedesktop.DBus", "StartServiceByName"); + QVariantList args; + args.append("org.freedesktop.GeoClue2"); + args.append((uint) 0); + launchMessage.setArguments(args); + + QDBusConnection::systemBus().call(launchMessage); + + QDBusMessage clientMessage = QDBusMessage::createMethodCall("org.freedesktop.GeoClue2", "/org/freedesktop/GeoClue2/Manager", "org.freedesktop.GeoClue2.Manager", "GetClient"); + QDBusReply clientPathReply = QDBusConnection::systemBus().call(clientMessage); + geoclueClientPath = clientPathReply.value(); + + QDBusInterface clientInterface("org.freedesktop.GeoClue2", geoclueClientPath.path(), "org.freedesktop.GeoClue2.Client", QDBusConnection::systemBus()); + clientInterface.setProperty("DesktopId", "theshell"); + QDBusConnection::systemBus().connect(clientInterface.service(), geoclueClientPath.path(), clientInterface.interface(), "LocationUpdated", this, SLOT(updateGeoclueLocation())); + clientInterface.call("Start"); +} + +void InfoPaneDropdown::updateGeoclueLocation() { + QDBusInterface clientInterface("org.freedesktop.GeoClue2", geoclueClientPath.path(), "org.freedesktop.GeoClue2.Client", QDBusConnection::systemBus()); + QDBusObjectPath locationPath = clientInterface.property("Location").value(); + + QDBusInterface locationInterface("org.freedesktop.GeoClue2", locationPath.path(), "org.freedesktop.GeoClue2.Location", QDBusConnection::systemBus()); + double latitude = locationInterface.property("Latitude").toDouble(); + double longitude = locationInterface.property("Longitude").toDouble(); + + QNetworkAccessManager* manager = new QNetworkAccessManager(); + QNetworkRequest sunriseApi(QUrl(QString("https://api.sunrise-sunset.org/json?lat=%1&lng=%2&formatted=0").arg(latitude).arg(longitude))); + sunriseApi.setHeader(QNetworkRequest::UserAgentHeader, QString("theShell/%1").arg(TS_VERSION)); + + QNetworkReply* reply = manager->get(sunriseApi); + connect(reply, QOverload::of(&QNetworkReply::error), + [ = ](QNetworkReply::NetworkError code) { + qDebug() << "Error"; + }); + connect(reply, &QNetworkReply::finished, [ = ] { + QJsonDocument doc = QJsonDocument::fromJson(reply->readAll()); + QJsonObject root = doc.object(); + if (root.value("status").toString() != "OK") { + qDebug() << root.value("status").toString(); + return; + } + + //The time returned should be midway into the transition period, add/remove 30 minutes to compensate + QJsonObject results = root.value("results").toObject(); + QDateTime sunrise = QDateTime::fromString(results.value("sunrise").toString(), Qt::ISODate).toLocalTime().addSecs(-1800); + QDateTime sunset = QDateTime::fromString(results.value("sunset").toString(), Qt::ISODate).toLocalTime().addSecs(1800); + + ui->startRedshift->setDateTime(sunset); + ui->endRedshift->setDateTime(sunrise); + + reply->deleteLater(); + manager->deleteLater(); + }); + + clientInterface.call("Stop"); +} + +void InfoPaneDropdown::paintEvent(QPaintEvent* event) { + QPainter painter(this); + painter.setPen(this->palette().color(QPalette::WindowText)); + if (settings.value("bar/onTop", true).toBool()) { + painter.drawLine(0, this->height() - 1, this->width(), this->height() - 1); + } else { + painter.drawLine(0, 0, this->width(), 0); + } + event->accept(); +} + +void InfoPaneDropdown::on_systemGTK3Theme_currentIndexChanged(int index) { + gtk3Settings->setValue("Settings/gtk-theme-name", ui->systemGTK3Theme->itemText(index)); +} + +void InfoPaneDropdown::on_systemFontSize_valueChanged(int arg1) { + themeSettings->setValue("font/defaultSize", arg1); +} + +void InfoPaneDropdown::on_systemGTK3Font_currentFontChanged(const QFont& f) { + gtk3Settings->setValue("Settings/gtk-font-name", f.family() + " " + QString::number(ui->systemGTK3FontSize->value())); +} + +void InfoPaneDropdown::on_systemGTK3FontSize_valueChanged(int arg1) { + gtk3Settings->setValue("Settings/gtk-font-name", ui->systemGTK3Font->currentFont().family() + " " + QString::number(arg1)); +} + +void InfoPaneDropdown::on_useSystemFontForGTKButton_clicked() { + ui->systemGTK3Font->setCurrentFont(ui->systemFont->currentFont()); + ui->systemGTK3FontSize->setValue(ui->systemFontSize->value()); +} + +void InfoPaneDropdown::setHeaderColour(QColor col) { + if (ui->HighContrastSwitch->isChecked()) { + ui->partFrame->setPalette(QApplication::palette(ui->partFrame)); + } else { + QPalette pal = ui->partFrame->palette(); + + tVariantAnimation* anim = new tVariantAnimation(); + anim->setStartValue(pal.color(QPalette::Window)); + anim->setEndValue(col); + anim->setDuration(250); + anim->setEasingCurve(QEasingCurve::OutCubic); + connect(anim, &tVariantAnimation::valueChanged, [ = ](QVariant value) { + QPalette pal = ui->partFrame->palette(); + QColor col = value.value(); + + pal.setColor(QPalette::Window, col); + + //if ((col.red() + col.green() + col.blue()) / 3 < 127) { + pal.setColor(QPalette::WindowText, Qt::white); + pal.setColor(QPalette::Disabled, QPalette::WindowText, col.lighter(150)); + /*} else { + pal.setColor(QPalette::WindowText, Qt::black); + pal.setColor(QPalette::Disabled, QPalette::WindowText, col.darker(150)); + }*/ + + ui->partFrame->setPalette(pal); + + pal.setColor(QPalette::Window, col.lighter(120)); + ui->pushButton_7->setPalette(pal); + + ui->clockLabel->setShowDisabled(ui->clockLabel->showDisabled()); + ui->batteryLabel->setShowDisabled(ui->batteryLabel->showDisabled()); + ui->networkLabel->setShowDisabled(ui->networkLabel->showDisabled()); + ui->notificationsLabel->setShowDisabled(ui->notificationsLabel->showDisabled()); + ui->kdeconnectLabel->setShowDisabled(ui->kdeconnectLabel->showDisabled()); + }); + connect(anim, SIGNAL(finished()), anim, SLOT(deleteLater())); + anim->start(); + } +} + +bool InfoPaneDropdown::eventFilter(QObject* obj, QEvent* e) { + if (obj == ui->partFrame) { + if (e->type() == QEvent::Paint) { + QPainter p(ui->partFrame); + QPalette pal = ui->partFrame->palette(); + + p.setRenderHint(QPainter::Antialiasing); + p.setBrush(pal.color(QPalette::Window)); + p.setPen(Qt::transparent); + p.drawRect(0, 0, ui->partFrame->width(), ui->partFrame->height()); + + if (QApplication::layoutDirection() == Qt::RightToLeft) { + int width = ui->partFrame->width(); + QPolygonF firstPoly; + firstPoly.append(QPointF(width - slice1.currentValue().toFloat(), 0)); + firstPoly.append(QPointF(width - slice2.currentValue().toFloat(), ui->partFrame->height())); + firstPoly.append(QPointF(0, ui->partFrame->height())); + firstPoly.append(QPointF(0, 0)); + p.setBrush(pal.color(QPalette::Window).lighter(110)); + p.drawPolygon(firstPoly); + + QPolygonF secondPoly; + secondPoly.append(QPointF(width - ui->partFrame->width() * 0.85, 0)); + secondPoly.append(QPointF(width - ui->partFrame->width() * 0.825, ui->partFrame->height())); + secondPoly.append(QPointF(0, ui->partFrame->height())); + secondPoly.append(QPointF(0, 0)); + p.setBrush(pal.color(QPalette::Window).lighter(120)); + p.drawPolygon(secondPoly); + } else { + QPolygonF firstPoly; + firstPoly.append(QPointF(slice1.currentValue().toFloat(), 0)); + firstPoly.append(QPointF(slice2.currentValue().toFloat(), ui->partFrame->height())); + firstPoly.append(QPointF(ui->partFrame->width(), ui->partFrame->height())); + firstPoly.append(QPointF(ui->partFrame->width(), 0)); + p.setBrush(pal.color(QPalette::Window).lighter(110)); + p.drawPolygon(firstPoly); + + QPolygonF secondPoly; + secondPoly.append(QPointF(ui->partFrame->width() * 0.85, 0)); + secondPoly.append(QPointF(ui->partFrame->width() * 0.825, ui->partFrame->height())); + secondPoly.append(QPointF(ui->partFrame->width(), ui->partFrame->height())); + secondPoly.append(QPointF(ui->partFrame->width(), 0)); + p.setBrush(pal.color(QPalette::Window).lighter(120)); + p.drawPolygon(secondPoly); + } + return true; + } + } + return false; +} + +void InfoPaneDropdown::on_EmphasiseAppSwitch_toggled(bool checked) { + settings.setValue("notifications/emphasiseApp", checked); +} + +void InfoPaneDropdown::on_CompactBarSwitch_toggled(bool checked) { + if (settings.value("bar/compact") != checked) { + settings.setValue("bar/compact", checked); + + QMap actions; + actions.insert("logout", tr("Log Out Now")); + + tToast* t = new tToast(); + t->setTitle(tr("Logoff Required")); + + if (checked) { + t->setText(tr("In order to enable the Compact Bar, you'll need to log out and then log back on.")); + } else { + t->setText(tr("In order to disable the Compact Bar, you'll need to log out and then log back on.")); + } + t->setActions(actions); + t->setTimeout(10000); + connect(t, &tToast::actionClicked, [ = ](QString key) { + if (key == "logout") { + EndSession(EndSessionWait::logout); + } + }); + connect(t, SIGNAL(dismissed()), t, SLOT(deleteLater())); + t->show(this); + } +} + +void InfoPaneDropdown::keyPressEvent(QKeyEvent* event) { + +} + +void InfoPaneDropdown::updateDSTNotification() { + launchDateTimeService(); + + QDBusInterface dateTimeInterface("org.freedesktop.timedate1", "/org/freedesktop/timedate1", "org.freedesktop.timedate1", QDBusConnection::systemBus()); + QString currentTimezone = dateTimeInterface.property("Timezone").toString(); + + QString timezoneInfoPath = "/usr/share/zoneinfo/" + currentTimezone; + QProcess* timezoneProcess = new QProcess(); + connect(timezoneProcess, QOverload::of(&QProcess::finished), [ = ](int exitCode, QProcess::ExitStatus exitStatus) { + timezoneProcess->deleteLater(); + + struct Changeover { + QDateTime changeoverDate; + bool isDST; + int gmtOffset; + }; + + QList changeovers; + + while (!timezoneProcess->atEnd()) { + QStringList parts = QString(timezoneProcess->readLine()).split(" ", QString::SkipEmptyParts); + if (parts.length() == 16) { + QStringList dateText; + dateText.append(parts.at(4)); + //dateText.append(parts.at(2)); + + //I am so sorry :( + if (parts.at(2) == "Jan") { + dateText.append("01"); + } else if (parts.at(2) == "Feb") { + dateText.append("02"); + } else if (parts.at(2) == "Mar") { + dateText.append("03"); + } else if (parts.at(2) == "Apr") { + dateText.append("04"); + } else if (parts.at(2) == "May") { + dateText.append("05"); + } else if (parts.at(2) == "Jun") { + dateText.append("06"); + } else if (parts.at(2) == "Jul") { + dateText.append("07"); + } else if (parts.at(2) == "Aug") { + dateText.append("08"); + } else if (parts.at(2) == "Sep") { + dateText.append("09"); + } else if (parts.at(2) == "Oct") { + dateText.append("10"); + } else if (parts.at(2) == "Nov") { + dateText.append("11"); + } else if (parts.at(2) == "Dec") { + dateText.append("12"); + } + + dateText.append(parts.at(5)); + dateText.append(parts.at(3)); + + Changeover c; + QString dateConnectedText = dateText.join(" "); + c.changeoverDate = QDateTime::fromString(dateConnectedText, "hh:mm:ss MM yyyy d"); + c.changeoverDate.setTimeSpec(Qt::UTC); + c.isDST = parts.at(14).endsWith("1"); + c.gmtOffset = parts.at(15).mid(7).toInt(); + changeovers.append(c); + } + } + + bool showDaylightSavingsPanel = false; + Changeover changeover; + QDateTime current = QDateTime::currentDateTimeUtc(); + QDateTime currentLocal = QDateTime::currentDateTime(); + + for (int i = 0; i < changeovers.count(); i++) { + Changeover c = changeovers.at(i); + + int days = current.daysTo(c.changeoverDate); + if (days > 0 && days < 14) { + if ((currentLocal.isDaylightTime() && !c.isDST) || (!currentLocal.isDaylightTime() && c.isDST)) { + showDaylightSavingsPanel = true; + changeover = c; + } + } + } + + if (showDaylightSavingsPanel) { + ui->dstPanel->setVisible(true); + ui->dstLabel->setText(tr("On %1, Daylight Savings Time will %2. The clock will automatically adjust %3 by %n hour(s).", nullptr, 1) + .arg(QLocale().toString(changeover.changeoverDate.toLocalTime(), "ddd dd MMM yyyy")) + //: This is used during Daylight Savings notifications and will appear as "On [date], Daylight Savings Time will (begin|end)". + .arg(currentLocal.isDaylightTime() ? tr("end", "Context: \"Daylight Savings Time will end.\"") : tr("begin", "Context: \"Daylight Savings Time will begin.\"")) + //: This is used during Daylight Savings notifications and will appear as "The clock will automatically adjust (forwards|backwards) by [hours] hour(s).". + .arg(currentLocal.isDaylightTime() ? tr("backwards", "Context: \"The clock will automatically adjust backwards\"") : tr("forwards", "Context: \"The clock will automatically adjust forwards\""))); + } else { + ui->dstPanel->setVisible(false); + } + }); + timezoneProcess->start("zdump -v " + timezoneInfoPath); +} + +void InfoPaneDropdown::on_blackColorThemeRadio_toggled(bool checked) { + if (checked) { + themeSettings->setValue("color/type", "black"); + updateAccentColourBox(); + resetStyle(); + changeDropDown(Settings, false); + } +} + +void InfoPaneDropdown::changeSettingsPane(int pane) { + ui->settingsList->setCurrentRow(pane); +} + +void InfoPaneDropdown::on_allowGeoclueAgent_clicked() { + //Automatically edit the geoclue file + LOWER_INFOPANE + QProcess::execute("pkexec sed \"/whitelist=.*/ s/$/;theshell/\" -i /etc/geoclue/geoclue.conf"); + locationServices->reloadAuthorizationRequired(); + + QTimer::singleShot(500, [ = ] { + on_settingsList_currentRowChanged(6); + }); +} + +void InfoPaneDropdown::on_LocationMasterSwitch_toggled(bool checked) { + locationSettings->setValue("master/master", checked); +} + +void InfoPaneDropdown::setupLocationSettingsPane() { + if (locationServices->requiresAuthorization()) { + ui->locationStack->setCurrentIndex(0); + } else { + ui->locationStack->setCurrentIndex(1); + + ui->LocationAppsList->clear(); + QStringList availableApps = locationSettings->childGroups(); + availableApps.removeOne("master"); + + for (QString app : availableApps) { + locationSettings->beginGroup(app); + bool allow = locationSettings->value("allow").toBool(); + + App a = App::invalidApp(); + if (QFile("/usr/share/applications/" + app + ".desktop").exists()) { + a = AppsListModel::readAppFile("/usr/share/applications/" + app + ".desktop"); + } else if (QFile(QDir::homePath() + "/.local/share/applications" + app + ".desktop").exists()) { + a = AppsListModel::readAppFile(QDir::homePath() + "/.local/share/applications" + app + ".desktop"); + } + + QListWidgetItem* i = new QListWidgetItem(); + if (a.invalid()) { + i->setText(app); + } else { + i->setIcon(a.icon()); + i->setText(a.name()); + } + + i->setFlags(i->flags() | Qt::ItemIsUserCheckable); + if (allow) { + i->setCheckState(Qt::Checked); + } else { + i->setCheckState(Qt::Unchecked); + } + i->setData(Qt::UserRole, app); + ui->LocationAppsList->addItem(i); + + locationSettings->endGroup(); + } + } +} + +void InfoPaneDropdown::on_LocationAppsList_itemChanged(QListWidgetItem* item) { + if (item->checkState() == Qt::Checked) { + locationSettings->setValue(item->data(Qt::UserRole).toString() + "/allow", true); + } else { + locationSettings->setValue(item->data(Qt::UserRole).toString() + "/allow", false); + } +} + +void InfoPaneDropdown::on_backInput_clicked() { + ui->InputStack->setCurrentIndex(0); +} + +void InfoPaneDropdown::on_addLayout_clicked() { + ui->InputStack->setCurrentIndex(1); +} + +void InfoPaneDropdown::on_addKeyboardLayout_clicked() { + QListWidgetItem* item = ui->availableKeyboardLayouts->currentItem(); + QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); + currentLayouts.append(item->data(Qt::UserRole).toString()); + + QListWidgetItem* newItem = new QListWidgetItem(); + newItem->setText(item->text()); + newItem->setData(Qt::UserRole, item->data(Qt::UserRole)); + ui->selectedLayouts->addItem(newItem); + settings.setValue("input/layout", currentLayouts.join(",")); + + ui->InputStack->setCurrentIndex(0); + loadNewKeyboardLayoutMenu(); +} + +void InfoPaneDropdown::on_removeLayout_clicked() { + QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); + int item = ui->selectedLayouts->currentRow(); + currentLayouts.removeAt(item); + QListWidgetItem* i = ui->selectedLayouts->takeItem(item); + delete i; + settings.setValue("input/layout", currentLayouts.join(",")); + loadNewKeyboardLayoutMenu(); +} + +void InfoPaneDropdown::on_selectedLayouts_currentItemChanged(QListWidgetItem* current, QListWidgetItem* previous) { + if (current == nullptr) { + ui->removeLayout->setEnabled(false); + } else if (ui->selectedLayouts->count() == 1) { + ui->removeLayout->setEnabled(false); + } else { + ui->removeLayout->setEnabled(true); + } +} + +void InfoPaneDropdown::on_availableKeyboardLayouts_currentItemChanged(QListWidgetItem* current, QListWidgetItem* previous) { + if (current == nullptr) { + ui->addKeyboardLayout->setEnabled(false); + } else { + ui->addKeyboardLayout->setEnabled(true); + } +} + +void InfoPaneDropdown::KeyboardLayoutsMoved() { + //Completely recreate the selected layouts + QStringList currentLayouts; + for (int i = 0; i < ui->selectedLayouts->count(); i++) { + QListWidgetItem* item = ui->selectedLayouts->item(i); + currentLayouts.append(item->data(Qt::UserRole).toString()); + } + settings.setValue("input/layout", currentLayouts.join(",")); + loadNewKeyboardLayoutMenu(); +} + +void InfoPaneDropdown::on_moveLayoutDown_clicked() { + int row = ui->selectedLayouts->currentRow(); + if (row <= ui->selectedLayouts->count() - 1) { + ui->selectedLayouts->clearSelection(); + QListWidgetItem* item = ui->selectedLayouts->takeItem(row); + ui->selectedLayouts->insertItem(row + 1, item); + item->setSelected(true); + } + + QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); + QString layout = currentLayouts.takeAt(row); + currentLayouts.insert(row + 1, layout); + settings.setValue("input/layout", currentLayouts.join(",")); + loadNewKeyboardLayoutMenu(); +} + +void InfoPaneDropdown::on_moveLayoutUp_clicked() { + int row = ui->selectedLayouts->currentRow(); + if (row > 0) { + ui->selectedLayouts->clearSelection(); + QListWidgetItem* item = ui->selectedLayouts->takeItem(row); + ui->selectedLayouts->insertItem(row - 1, item); + item->setSelected(true); + } + + QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); + QString layout = currentLayouts.takeAt(row); + currentLayouts.insert(row - 1, layout); + settings.setValue("input/layout", currentLayouts.join(",")); + loadNewKeyboardLayoutMenu(); +} + +void InfoPaneDropdown::loadNewKeyboardLayoutMenu() { + //Check to see if current keyboard layout is included in list, and if not, select first + QString currentLayout = settings.value("input/currentLayout", "us(basic)").toString(); + QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); + if (!currentLayouts.contains(currentLayout)) { + setKeyboardLayout(currentLayouts.first()); + return; + } + + if (ui->selectedLayouts->count() == 1) { + emit newKeyboardLayoutMenuAvailable(nullptr); + } else { + QMenu* menu = new QMenu(); + menu->addSection(tr("Keyboard Layout")); + for (int i = 0; i < ui->selectedLayouts->count(); i++) { + QListWidgetItem* item = ui->selectedLayouts->item(i); + QAction* action = menu->addAction(item->text(), [ = ] { + setKeyboardLayout(item->data(Qt::UserRole).toString()); + }); + action->setCheckable(true); + if (item->data(Qt::UserRole) == currentLayout) { + action->setChecked(true); + } + } + emit newKeyboardLayoutMenuAvailable(menu); + } + QApplication::processEvents(); +} + +void InfoPaneDropdown::setKeyboardLayout(QString layout) { + settings.setValue("input/currentLayout", layout); + QProcess::startDetached("setxkbmap " + layout); + loadNewKeyboardLayoutMenu(); + emit keyboardLayoutChanged(layout.split("(").first().toUpper()); +} + +QString InfoPaneDropdown::setNextKeyboardLayout() { + QString currentLayout = settings.value("input/currentLayout", "us(basic)").toString(); + QStringList currentLayouts = settings.value("input/layout", "us(basic)").toString().split(","); + int currentIndex = currentLayouts.indexOf(currentLayout); + currentIndex++; + if (currentIndex == currentLayouts.count()) currentIndex = 0; + + QString layout = currentLayouts.at(currentIndex); + QTimer::singleShot(0, [ = ] { + setKeyboardLayout(layout); + }); + for (int i = 0; i < ui->selectedLayouts->count(); i++) { + if (ui->selectedLayouts->item(i)->data(Qt::UserRole) == layout) { + return ui->selectedLayouts->item(i)->text(); + } + } +} + +void InfoPaneDropdown::on_setupMousePassword_clicked() { + //Check Polkit authorization + PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.thesuite.theshell.configure-mouse-password", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::None); + + if (r == PolkitQt1::Authority::No) { + QMessageBox::warning(this, tr("Unauthorized"), tr("Polkit does not allow you to set up a mouse password."), QMessageBox::Ok, QMessageBox::Ok); + return; + } else if (r == PolkitQt1::Authority::Challenge) { + LOWER_INFOPANE + PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.thesuite.theshell.configure-mouse-password", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::AllowUserInteraction); + if (r != PolkitQt1::Authority::Yes) { + return; + } + } + + ui->lockScreenStack->setCurrentIndex(1); +} + +void InfoPaneDropdown::on_removeMousePassword_clicked() { + if (QMessageBox::question(this, tr("Remove Mouse Password?"), tr("Do you want to remove the Mouse Password for this account?"), QMessageBox::Yes | QMessageBox::No, QMessageBox::No) == QMessageBox::Yes) { + //Check Polkit authorization + PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.thesuite.theshell.configure-mouse-password", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::None); + + if (r == PolkitQt1::Authority::No) { + QMessageBox::warning(this, tr("Unauthorized"), tr("Polkit does not allow you to set up a mouse password."), QMessageBox::Ok, QMessageBox::Ok); + return; + } else if (r == PolkitQt1::Authority::Challenge) { + LOWER_INFOPANE + PolkitQt1::Authority::Result r = PolkitQt1::Authority::instance()->checkAuthorizationSync("org.thesuite.theshell.configure-mouse-password", PolkitQt1::UnixProcessSubject(QApplication::applicationPid()), PolkitQt1::Authority::AllowUserInteraction); + if (r != PolkitQt1::Authority::Yes) { + return; + } + } + + + //Remove the mouse password + QProcess* proc = new QProcess(); + QDir::home().mkdir(".theshell"); + + QString executable = "/usr/lib/ts-mousepass-change"; +#ifdef BLUEPRINT + executable += "b"; +#elif defined(CONSTRUCTION) + executable += "c"; +#endif + proc->start(executable + " --remove --passfile=" + QDir::homePath() + "/.theshell/mousepassword"); + proc->waitForFinished(); + + if (proc->exitCode() == 0) { + tToast* toast = new tToast(); + toast->setTitle(tr("Mouse Password")); + toast->setText(tr("Mouse Password was removed successfully")); + connect(toast, SIGNAL(dismissed()), toast, SLOT(deleteLater())); + toast->show(this); + } else { + tToast* toast = new tToast(); + toast->setTitle(tr("Mouse Password")); + toast->setText(tr("Mouse Password couldn't be removed")); + connect(toast, SIGNAL(dismissed()), toast, SLOT(deleteLater())); + toast->show(this); + } + + proc->deleteLater(); + } +} + +void InfoPaneDropdown::on_MousePasswordSetup_exit() { + ui->lockScreenStack->setCurrentIndex(0); + if (QFile(QDir::homePath() + "/.theshell/mousepassword").exists()) { + ui->removeMousePassword->setVisible(true); + } else { + ui->removeMousePassword->setVisible(false); + } +} + +void InfoPaneDropdown::on_websiteButton_clicked() { + QProcess::startDetached("xdg-open https://vicr123.github.io/theshell"); + this->close(); +} + +void InfoPaneDropdown::on_bugButton_clicked() { + QProcess::startDetached("xdg-open https://github.com/vicr123/theshell/issues"); + this->close(); +} + +void InfoPaneDropdown::on_distroWebpage_clicked() { + QProcess::startDetached("xdg-open " + ui->distroWebpage->text()); + this->close(); +} + +void InfoPaneDropdown::on_distroSupport_clicked() { + QProcess::startDetached("xdg-open " + ui->distroSupport->text()); + this->close(); +} + +void InfoPaneDropdown::on_sourcesButton_clicked() { + QProcess::startDetached("xdg-open https://github.com/vicr123/theshell"); + this->close(); +} + +void InfoPaneDropdown::on_quietModeCriticalOnly_clicked() { + AudioMan->setQuietMode(AudioManager::critical); + ui->quietModeCriticalOnly->setChecked(true); +} diff --git a/shell/infopanedropdown.ui b/shell/infopanedropdown.ui index 2192855..5f3321b 100644 --- a/shell/infopanedropdown.ui +++ b/shell/infopanedropdown.ui @@ -1 +1,6989 @@ - InfoPaneDropdown 0 0 1201 835 theShellStatusCenter :/icons/icon.svg:/icons/icon.svg 0 0 0 0 0 true QFrame::NoFrame QFrame::Raised 10 9 6 13 0 0 0 0 .. 16 16 false true .. 24 24 true true Clock System Status Network Notifications KDE Connect .. 24 24 true Qt::Horizontal 40 20 10 System Settings .. true true Flight Mode true FlightSwitch true false Qt::Vertical true Wi-Fi true WifiSwitch true true Qt::Vertical true Bluetooth true BluetoothSwitch Qt::Vertical Power Stretch PowerStretchSwitch Qt::Vertical Redshift RedshiftSwitch Qt::Horizontal 40 20 16777215 1 Qt::Horizontal 3 true 18 0 0 15 QFrame::NoFrame true 0 0 1169 1038 0 0 9 0 50 Qt::Vertical 20 40 40 16:20:00 15 Sunday, 1 Janurary 1111 QFrame::NoFrame QFrame::Raised 0 20 0 0 Icon Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop On Tableday, 1 April 2018, Daylight Savings Time will end. The clock will automatically adjust backwards by 1 hour. true Qt::Vertical 20 40 0 0 true QCalendarWidget::ISOWeekNumbers true true Qt::Vertical 20 40 Qt::Vertical 20 40 Qt::Horizontal 40 20 Qt::Horizontal 40 20 Qt::Horizontal 40 20 Today .. Qt::Horizontal 40 20 Qt::Horizontal 20 Timer 50 Qt::AlignCenter 0 15 0 1969 8 17 1969 8 17 HH:mm:ss Qt::UTC 50 00:00:00 Qt::AlignCenter 0 0 <html><head/><body><p>&quot;Happy Bee&quot;, &quot;Salty Ditty&quot; copyright (c) Kevin MacLeod. Licensed under the Creative Commons CC-BY license.</p></body></html> true Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter true Happy Bee Happy Bee Playing in the Dark Ice Cream Truck Party Complex Salty Ditty 0 Reset .. Start .. Qt::Horizontal 20 Stopwatch 50 00:00:00 Qt::AlignCenter 0 Qt::Horizontal 40 20 Reset .. Start .. Qt::Horizontal 0 true 0 0 0 0 20 Reminders QAbstractItemView::NoEditTriggers QAbstractItemView::SelectRows QAbstractItemView::ScrollPerPixel 0 0 Qt::Horizontal 40 20 Delete Reminder .. New Reminder .. true 20 New Reminder Date Title Qt::Vertical 20 40 0 Qt::Horizontal 40 20 Cancel .. Create Reminder .. true 20 Delete Reminder Delete this reminder? Qt::Horizontal 15 Reminder Reminder Text false 3:00 PM Qt::Horizontal Qt::Vertical 20 40 0 Qt::Horizontal 40 20 Cancel .. Delete .. Qt::Vertical 20 18 true 0 0 0 0 0 15 System Status 9 16777215 1 Qt::Horizontal 6 9 9 9 9 Current Battery Power: theShell Uptime: System Uptime: Qt::Horizontal 0 0 QFrame::NoFrame QFrame::Raised 0 0 15 Charge History Show projected charge true 0 0 Charge true true Rate true Apps true 0 0 Last updated 11:30:42 Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter .. 0 Qt::Horizontal true 0 0 0 0 0 0 true 0 0 0 0 0 15 Notifications 9 16777215 1 Qt::Horizontal 0 9 0 9 0 6 0 Quiet Mode 0 Sound .. true true Critical Only true No Notifications .. true Mute .. true 0 0 .. Qt::Horizontal 40 20 0 0 QFrame::NoFrame Qt::ScrollBarAlwaysOff Qt::ScrollBarAlwaysOff true 0 0 1183 132 0 9 0 9 Description of Quiet Mode true Fore&ver Turn off in 0 0 1 0 0 2000 1 1 HH:mm Turn off at 0 0 HH:mm:ss 16777215 1 Qt::Horizontal 0 0 true 0 0 0 0 0 Qt::Horizontal true 0 0 0 0 0 QFrame::NoFrame QFrame::Raised 0 0 0 0 0 0 0 0 0 0 0 15 System Settings 9 16777215 1 Qt::Horizontal 0 0 QFrame::NoFrame QAbstractItemView::NoEditTriggers false Qt::IgnoreAction Startup .. Gateway and Bar .. Networks .. Display .. Theme .. Sounds and Notifications .. Location .. Input .. Power .. Lock Screen .. Users .. Date and Time .. Language .. Accessibility .. Advanced .. About .. 1 16777215 Qt::Vertical 0 0 15 0 0 0 0 0 15 Startup 9 16777215 1 Qt::Horizontal true 0 true 9 9 9 9 0 0 Qt::Horizontal 40 20 Remove .. New App .. Autostart with Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop true 9 9 9 9 Which app do you want to automatically start with theShell? Back .. Qt::Horizontal 40 20 Command true 9 9 9 9 Command Back .. Qt::Horizontal 40 20 Add App .. Enter details of the app to autostart Application Name Qt::Vertical 20 40 Only autostart this app in theShell 0 0 0 0 0 15 Gateway and Bar 9 16777215 1 Qt::Horizontal 9 9 9 9 6 When this is checked, hovering over the Status Bar will automatically expand the bar. Otherwise, clicking on the Status Bar will expand the bar. true End Session Confirmation The Compact Bar is a smaller version of the traditional bar which arranges all the elements in one row to save vertical space. true barDesktopsSwitch Qt::Horizontal 40 20 AutoShowBarSwitch Automatically show bar StatusBarSwitch QFrame::NoFrame QFrame::Raised 0 0 0 0 Within &Gateway Fu&ll Screen Qt::Horizontal 40 20 Show Bar on bottom of screen CompactBarSwitch true Use Compact Bar TextSwitch The Status Bar is a shown when a window is maximised. true Use Status Bar Show text on window buttons BarOnBottomSwitch Show windows from other desktops Qt::Vertical 20 40 0 0 0 0 0 0 0 0 0 0 0 15 Display 9 16777215 1 Qt::Horizontal QFrame::NoFrame Qt::ScrollBarAlwaysOff true 0 0 381 547 0 0 0 0 0 9 9 9 9 6 Qt::Horizontal Screen Brightness QFrame::NoFrame QFrame::Raised 0 0 0 0 Qt::Horizontal 40 20 Adjust Screen Resolution .. 0 0 Screen Scaling Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop &100% (96 dpi) 1&50% (144 dpi) &200% (192 dpi) &300% (288 dpi) DPI settings will be applied at next login. 16777215 1 Qt::Horizontal 9 9 9 9 6 End Time If the start time is later than the end time, Redshift will be activated until the end time on the next day. true 15 Redshift 17 0 0 2000 1 1 HH:mm We'll send your current location to https://sunrise-sunset.org/ to determine sunlight times if you enable this option. true Start Time Uses Location true 0 0 Use Sunlight Cycle Pause Redshift Qt::Horizontal 40 20 6 0 0 2000 1 1 HH:mm Scheduled 1000 6500 5000 Qt::Horizontal false false Redshift Intensity Qt::Vertical 20 40 0 0 0 0 0 15 Theme 9 16777215 1 Qt::Horizontal 9 9 9 9 6 Accent Color Qt::Horizontal 40 20 QFrame::NoFrame QFrame::Raised 0 0 0 0 &Light Dar&k Black &Gray Decorati&ve Color Scheme 16777215 1 Qt::Horizontal 9 6 9 9 6 System Font 0 0 0 0 Icon Theme Use for GTK .. Widget Theme 0 0 16777215 1 Qt::Horizontal 9 9 9 9 6 0 0 GTK3 Font GTK3 Theme 0 0 Qt::Vertical 20 40 0 0 0 0 0 15 Notifications 9 16777215 1 Qt::Horizontal 9 9 9 9 6 QFrame::NoFrame QFrame::Raised 0 0 0 0 Show Contents Hide Contents Don't Show Qt::Horizontal 40 20 4 0 false 3 0 QFrame::StyledPanel QFrame::Raised 15 Notifications Allow notifications Allow sounds Allow popup Bypass Quiet Mode Allow this app's notifications to show when Quiet Mode is set to No Notifications true Qt::Vertical 20 40 You can't configure notifications for Show Notifications on lock screen 0 0 Applications Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop Emphasise sending app EmphasiseAppSwitch Qt::Horizontal 9 9 9 9 6 Volume change sound SoundFeedbackSoundSwitch Show options when connecting media Volume overdrive AttenuateSwitch VolumeOverdriveSwitch Attenuate audio Notification Sound MediaSwitch Qt::Horizontal 40 20 0 0 0 0 0 15 Location 9 16777215 1 Qt::Horizontal 0 Qt::Vertical 20 40 20 Permission Required Qt::AlignCenter To manage location settings in theShell, you'll need to give us permission to be a geoclue agent. Qt::AlignCenter Qt::Horizontal 40 20 Allow theShell to be a geoclue agent .. Qt::Horizontal 40 20 Have your administrator password ready Qt::AlignCenter Qt::Vertical QSizePolicy::Fixed 20 100 If you wish to manually configure theShell as a geoclue agent, you'll need to edit /etc/geoclue/geoclue.conf and append "theshell" to the end of the whitelist setting. Qt::AlignCenter true Qt::Vertical 20 40 0 0 0 0 0 6 9 9 9 9 Allow apps to access your physical location LocationMasterSwitch Qt::Horizontal 40 20 Qt::Horizontal QFrame::NoFrame 0 0 0 0 0 true 0 0 0 0 0 15 Input 9 16777215 1 Qt::Horizontal 9 9 9 9 6 QAbstractItemView::NoDragDrop Qt::MoveAction Keyboard Layout Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop 0 .. .. Qt::Horizontal 40 20 Remove .. Add .. Qt::Horizontal 9 9 9 9 6 Qt::Horizontal 40 20 Optimise for touch input Use Super Key to open Gateway TouchInputSwitch true <html><head/><body><p>If you'd like to use the Super Key for another key combination, turn this off so that theShell won't take control of it. <span style=" font-weight:600;">Changing t</span><span style=" font-weight:600;">his setting requires you to log out and then log back in.</span></p></body></html> true Audible Touch Feedback TouchFeedbackSwitch true true SuperkeyGatewaySwitch true 0 0 0 0 0 0 0 .. true 0 0 15 Select Keyboard Layout 9 16777215 1 Qt::Horizontal QFrame::NoFrame 16777215 1 Qt::Horizontal Qt::Horizontal 40 20 Add .. 0 0 0 0 0 15 Power 9 16777215 1 Qt::Horizontal 9 9 9 9 6 min 1 121 Qt::Horizontal QSlider::TicksBothSides When this device is running off battery power, Turn off screen after Suspend after 1 121 Qt::Horizontal QSlider::TicksBothSides min Qt::Horizontal 9 9 9 9 6 min Suspend after 1 121 Qt::Horizontal QSlider::TicksBothSides min 1 121 Qt::Horizontal QSlider::TicksBothSides Turn off screen after When this device is connected to power, Drag the slider to the right to turn off power management Qt::Horizontal 9 9 9 9 6 Power Button false Ask me what to do .. Power Off .. Reboot .. Log Out .. Suspend .. Lock .. Turn Off Screen .. When I press the Qt::Vertical 20 40 0 0 0 0 0 0 0 0 0 0 0 15 Lock Screen 9 16777215 1 Qt::Horizontal 9 9 9 9 6 SuspendLockScreenSwitch true true Browse... Qt::Horizontal 40 20 Background Lock screen after returning from suspend To change your password, go to User settings 16777215 1 Qt::Horizontal 9 9 9 9 6 0 Set Up .. Remove Mouse Password .. Qt::Horizontal 40 20 Mouse Password A mouse password trades security for convenience on the lock screen by substituting your password with a sequence of mouse buttons. <b>This can only be used on the lock screen, not while logging in.</b> true Qt::Vertical 20 284 0 0 0 0 true 0 true 0 0 0 0 0 0 15 Select a user 9 16777215 1 Qt::Horizontal QFrame::NoFrame 0 16777215 1 Qt::Horizontal 0 0 Qt::Horizontal 40 20 Next .. true 0 0 0 0 0 0 0 0 .. true 0 0 15 Edit User 9 16777215 1 Qt::Horizontal 6 9 9 9 9 Retype Password Full Name QLineEdit::Password (unchanged) Username QLineEdit::Password (unchanged) Password Password Hint Account Type 0 Standard true Administrator true Qt::Horizontal 40 20 Qt::Vertical 20 40 16777215 1 Qt::Horizontal 0 Qt::Horizontal 40 20 Delete User .. Apply Changes .. true 0 0 0 0 0 0 0 0 .. true 0 0 15 Delete User 9 16777215 1 Qt::Horizontal 6 9 9 9 9 Do you also want to keep files from this user? Items that will be kept if you choose to keep files: - Home directory - Mail Spool - Temporary Files 75 true This is the final step. The user will be deleted once you choose whether to keep or remove files. Qt::Vertical 20 40 16777215 1 Qt::Horizontal 0 Qt::Horizontal 40 20 Delete user only .. Delete user and all files .. 0 0 0 0 0 15 Date and Time 9 16777215 1 Qt::Horizontal 0 true 9 9 9 9 Qt::Vertical 20 40 Qt::Horizontal 40 20 Set .. Qt::Horizontal 40 20 400 200 Use network to sync date and time DateTimeNTPSwitch Qt::Horizontal 40 20 Use 24 hour time TwentyFourHourSwitch true true Qt::Horizontal 40 20 Qt::Horizontal 40 20 Set System Timezone .. true 9 9 9 9 Where are you located? 1 0 32 32 3 0 Back .. Qt::Horizontal 40 20 Set Timezone .. 0 0 0 0 0 15 Language 9 Qt::Horizontal QFrame::NoFrame Changing this setting requires you to log in and then log out. 9 0 0 0 0 0 15 Accessibility 9 16777215 1 Qt::Horizontal 9 9 9 9 6 Large Text High Contrast System Animations Qt::Horizontal 40 20 LargeTextSwitch true Tone on Caps Lock and Num Lock HighContrastSwitch true SystemAnimationsAccessibilitySwitch true true CapsNumLockBellSwitch Qt::Vertical 20 40 0 0 0 0 0 15 Advanced 9 16777215 1 Qt::Horizontal 9 9 9 9 6 Window Manager Command false Reset Device .. Reset theShell .. The items under here can do some bad things. Make sure you know what you're doing. Qt::Vertical 20 224 0 0 0 0 0 QFrame::NoFrame QFrame::Raised 0 0 0 0 0 15 System Information 9 16777215 1 Qt::Horizontal 9 9 9 9 6 You're using 0 0 15 75 true Distribution Name PointingHandCursor http://www.distro.org/ PointingHandCursor http://www.distro.org/ Support Qt::Horizontal 9 9 9 9 6 Available Swap Available Memory 0 0 8 GiB Kernel Version 8 GiB 4.11 Qt Version 5.9.0 Processor Intel 0 0 Qt::Horizontal 6 9 9 9 9 15 theShell %1 Desktop Environment You compiled theShell on %1 0 Website File Bug Sources Qt::Horizontal 40 20 Qt::Vertical 20 40 16777215 1 Qt::Horizontal theShell is Copyright (c) Victor Tran %1. Licensed under the terms of the GNU General Public License, version 3 or later. false 9 Qt::Horizontal Qt::Vertical QSizePolicy::Fixed 20 9 UpArrow Qt::AlignCenter Qt::Vertical QSizePolicy::Fixed 20 9 ClickableLabel QLabel
clickablelabel.h
clicked()
AnimatedStackedWidget QStackedWidget
animatedstackedwidget.h
1
NetworkWidget QWidget
networkmanager/networkwidget.h
1 networkAvailable(bool)
Switch QPushButton
switch.h
NotificationsWidget QWidget
notificationsWidget/notificationswidget.h
1
KdeConnectWidget QWidget
kdeconnect/kdeconnectwidget.h
1
MousePassword QWidget
locktypes/mousepassword.h
1 exit()
\ No newline at end of file + + + InfoPaneDropdown + + + + 0 + 0 + 1201 + 835 + + + + theShellStatusCenter + + + + :/icons/icon.svg:/icons/icon.svg + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + true + + + QFrame::NoFrame + + + QFrame::Raised + + + + 10 + + + 9 + + + 6 + + + + + + 13 + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + + + + .. + + + + 16 + 16 + + + + false + + + true + + + + + + + + + + + .. + + + + 24 + 24 + + + + true + + + + + + + true + + + Clock + + + + + + + System Status + + + + + + + Network + + + + + + + Notifications + + + + + + + KDE Connect + + + + + + + + + + + .. + + + + 24 + 24 + + + + true + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + 10 + + + + System Settings + + + + .. + + + true + + + + + + + + + + + + true + + + Flight Mode + + + + + + + true + + + FlightSwitch + + + true + + + false + + + + + + + Qt::Vertical + + + + + + + true + + + Wi-Fi + + + + + + + true + + + WifiSwitch + + + true + + + true + + + + + + + Qt::Vertical + + + + + + + true + + + Bluetooth + + + + + + + true + + + BluetoothSwitch + + + + + + + Qt::Vertical + + + + + + + Power Stretch + + + + + + + PowerStretchSwitch + + + + + + + Qt::Vertical + + + + + + + Redshift + + + + + + + RedshiftSwitch + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 5 + + + + true + + + + 18 + + + 0 + + + 0 + + + 15 + + + + + QFrame::NoFrame + + + true + + + + + 0 + 0 + 592 + 1058 + + + + + 0 + + + 0 + + + 9 + + + 0 + + + + + + + 50 + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + 40 + + + + 16:20:00 + + + + + + + + 15 + + + + Sunday, 1 Janurary 1111 + + + + + + + QFrame::NoFrame + + + QFrame::Raised + + + + 0 + + + 20 + + + 0 + + + 0 + + + + + + + Icon + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop + + + + + + + On Tableday, 1 April 2018, Daylight Savings Time will end. The clock will automatically adjust backwards by 1 hour. + + + true + + + + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + + + + 0 + 0 + + + + true + + + QCalendarWidget::ISOWeekNumbers + + + true + + + true + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Today + + + + .. + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + + + + Qt::Horizontal + + + + + + + + + + 20 + + + + Timer + + + + + + + + 50 + + + + Qt::AlignCenter + + + + 0 + 15 + 0 + 1969 + 8 + 16 + + + + + 1969 + 8 + 16 + + + + HH:mm:ss + + + Qt::UTC + + + + + + + + + + + 50 + + + + 00:00:00 + + + Qt::AlignCenter + + + + + + + + + + 0 + 0 + + + + <html><head/><body><p>&quot;Happy Bee&quot;, &quot;Salty Ditty&quot; copyright (c) Kevin MacLeod. Licensed under the Creative Commons CC-BY license.</p></body></html> + + + true + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + true + + + + + + + Happy Bee + + + + Happy Bee + + + + + Playing in the Dark + + + + + Ice Cream Truck + + + + + Party Complex + + + + + Salty Ditty + + + + + + + + 0 + + + + + Reset + + + + .. + + + + + + + Start + + + + .. + + + + + + + + + + + + + Qt::Horizontal + + + + + + + + + + 20 + + + + Stopwatch + + + + + + + + 50 + + + + 00:00:00 + + + Qt::AlignCenter + + + + + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Reset + + + + .. + + + + + + + Start + + + + .. + + + + + + + + + + + Qt::Horizontal + + + + + + + 0 + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 20 + + + + Reminders + + + + + + + QAbstractItemView::NoEditTriggers + + + QAbstractItemView::SelectRows + + + QAbstractItemView::ScrollPerPixel + + + + + + + 0 + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Delete Reminder + + + + .. + + + + + + + New Reminder + + + + .. + + + + + + + + + + true + + + + + + + 20 + + + + New Reminder + + + + + + + + + Date + + + + + + + Title + + + + + + + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Cancel + + + + .. + + + + + + + Create Reminder + + + + .. + + + + + + + + + + true + + + + + + + 20 + + + + Delete Reminder + + + + + + + Delete this reminder? + + + + + + + Qt::Horizontal + + + + + + + + 15 + + + + Reminder + + + + + + + Reminder Text + + + + + + + false + + + 3:00 PM + + + + + + + Qt::Horizontal + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Cancel + + + + .. + + + + + + + Delete + + + + .. + + + + + + + + + + + + + Qt::Vertical + + + + 20 + 18 + + + + + + + + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + System Status + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 6 + + + 9 + + + 9 + + + 9 + + + 9 + + + + + Current Battery Power: + + + + + + + theShell Uptime: + + + + + + + System Uptime: + + + + + + + + + Qt::Horizontal + + + + + + + + 0 + 0 + + + + QFrame::NoFrame + + + QFrame::Raised + + + + + + + + + 0 + 0 + + + + + 15 + + + + Charge History + + + + + + + Show projected charge + + + true + + + + + + + 0 + + + 0 + + + + + Charge + + + true + + + true + + + + + + + Rate + + + true + + + + + + + Apps + + + true + + + + + + + + + + 0 + 0 + + + + Last updated 11:30:42 + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + + + + + .. + + + + + + + + + 0 + + + + + + + Qt::Horizontal + + + + + + + + + + + + + + + + + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 0 + + + + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Notifications + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 0 + + + 9 + + + 0 + + + 9 + + + 0 + + + + + 6 + + + 0 + + + + + Quiet Mode + + + + + + + 0 + + + + + Sound + + + + .. + + + true + + + true + + + + + + + Critical Only + + + + .. + + + true + + + + + + + No Notifications + + + + .. + + + true + + + + + + + Mute + + + + .. + + + true + + + + + + + + 0 + 0 + + + + + + + + .. + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + 0 + 0 + + + + QFrame::NoFrame + + + Qt::ScrollBarAlwaysOff + + + Qt::ScrollBarAlwaysOff + + + true + + + + + 0 + 0 + 1183 + 132 + + + + + 0 + + + 9 + + + 0 + + + 9 + + + + + Description of Quiet Mode + + + true + + + + + + + Fore&ver + + + + + + + + + Turn off in + + + + + + + + 0 + 0 + + + + + 1 + 0 + 0 + 2000 + 1 + 1 + + + + HH:mm + + + + + + + + + + + Turn off at + + + + + + + + 0 + 0 + + + + HH:mm:ss + + + + + + + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + + 0 + 0 + + + + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + + + Qt::Horizontal + + + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + QFrame::NoFrame + + + QFrame::Raised + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 0 + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + System Settings + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + + 0 + 0 + + + + QFrame::NoFrame + + + QAbstractItemView::NoEditTriggers + + + false + + + Qt::IgnoreAction + + + + Startup + + + + .. + + + + + Gateway and Bar + + + + .. + + + + + Networks + + + + .. + + + + + Display + + + + .. + + + + + Theme + + + + .. + + + + + Sounds and Notifications + + + + .. + + + + + Location + + + + .. + + + + + Input + + + + .. + + + + + Power + + + + .. + + + + + Lock Screen + + + + .. + + + + + Users + + + + .. + + + + + Date and Time + + + + .. + + + + + Language + + + + .. + + + + + Accessibility + + + + .. + + + + + Advanced + + + + .. + + + + + About + + + + .. + + + + + + + + + + + + + + 1 + 16777215 + + + + Qt::Vertical + + + + + + + + 0 + 0 + + + + 15 + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Startup + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + true + + + 0 + + + + true + + + + 9 + + + 9 + + + 9 + + + 9 + + + + + 0 + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Remove + + + + .. + + + + + + + New App + + + + .. + + + + + + + + + + + + Autostart with + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop + + + + + + + + true + + + + 9 + + + 9 + + + 9 + + + 9 + + + + + Which app do you want to automatically start with theShell? + + + + + + + + + + + + Back + + + + .. + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Command + + + + + + + + + + true + + + + 9 + + + 9 + + + 9 + + + 9 + + + + + Command + + + + + + + + + + + + Back + + + + .. + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Add App + + + + .. + + + + + + + + + Enter details of the app to autostart + + + + + + + + + + Application Name + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + Only autostart this app in theShell + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Gateway and Bar + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + When this is checked, hovering over the Status Bar will automatically expand the bar. Otherwise, clicking on the Status Bar will expand the bar. + + + true + + + + + + + End Session Confirmation + + + + + + + The Compact Bar is a smaller version of the traditional bar which arranges all the elements in one row to save vertical space. + + + true + + + + + + + barDesktopsSwitch + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + AutoShowBarSwitch + + + + + + + Automatically show bar + + + + + + + StatusBarSwitch + + + + + + + QFrame::NoFrame + + + QFrame::Raised + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + Within &Gateway + + + + + + + Fu&ll Screen + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + Show Bar on bottom of screen + + + + + + + CompactBarSwitch + + + true + + + + + + + Use Compact Bar + + + + + + + TextSwitch + + + + + + + The Status Bar is a shown when a window is maximised. + + + true + + + + + + + Use Status Bar + + + + + + + Show text on window buttons + + + + + + + BarOnBottomSwitch + + + + + + + Show windows from other desktops + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 0 + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Display + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + QFrame::NoFrame + + + Qt::ScrollBarAlwaysOff + + + true + + + + + 0 + 0 + 381 + 547 + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + Qt::Horizontal + + + + + + + Screen Brightness + + + + + + + QFrame::NoFrame + + + QFrame::Raised + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Adjust Screen Resolution + + + + .. + + + + + + + + + + + 0 + 0 + + + + Screen Scaling + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop + + + + + + + + + &100% (96 dpi) + + + + + + + 1&50% (144 dpi) + + + + + + + &200% (192 dpi) + + + + + + + &300% (288 dpi) + + + + + + + DPI settings will be applied at next login. + + + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + End Time + + + + + + + If the start time is later than the end time, Redshift will be activated until the end time on the next day. + + + true + + + + + + + + 15 + + + + Redshift + + + + + + + + 17 + 0 + 0 + 2000 + 1 + 1 + + + + HH:mm + + + + + + + We'll send your current location to https://sunrise-sunset.org/ to determine sunlight times if you enable this option. + + + true + + + + + + + Start Time + + + + + + + + + Uses Location + + + + + + + true + + + + 0 + 0 + + + + Use Sunlight Cycle + + + + + + + + + + + Pause Redshift + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + 6 + 0 + 0 + 2000 + 1 + 1 + + + + HH:mm + + + + + + + Scheduled + + + + + + + 1000 + + + 6500 + + + 5000 + + + Qt::Horizontal + + + false + + + false + + + + + + + Redshift Intensity + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Theme + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + Accent Color + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + QFrame::NoFrame + + + QFrame::Raised + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + &Light + + + + + + + Dar&k + + + + + + + Black + + + + + + + &Gray + + + + + + + Decorati&ve + + + + + + + + + + + + + Color Scheme + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 6 + + + 9 + + + 9 + + + 6 + + + + + System Font + + + + + + + + 0 + 0 + + + + + + + + + + + + 0 + 0 + + + + + + + + Icon Theme + + + + + + + Use for GTK + + + + .. + + + + + + + Widget Theme + + + + + + + + 0 + 0 + + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + + 0 + 0 + + + + + + + + GTK3 Font + + + + + + + GTK3 Theme + + + + + + + + + + + 0 + 0 + + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Notifications + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + QFrame::NoFrame + + + QFrame::Raised + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + Show Contents + + + + + + + Hide Contents + + + + + + + Don't Show + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + + 4 + 0 + + + + + + + + false + + + + 3 + 0 + + + + QFrame::StyledPanel + + + QFrame::Raised + + + + + + + 15 + + + + Notifications + + + + + + + Allow notifications + + + + + + + Allow sounds + + + + + + + Allow popup + + + + + + + Bypass Quiet Mode + + + + + + + Allow this app's notifications to show when Quiet Mode is set to No Notifications + + + true + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + You can't configure notifications for + + + + + + + + + + Show Notifications on lock screen + + + + + + + + 0 + 0 + + + + Applications + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop + + + + + + + Emphasise sending app + + + + + + + EmphasiseAppSwitch + + + + + + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + Volume change sound + + + + + + + SoundFeedbackSoundSwitch + + + + + + + Show options when connecting media + + + + + + + Volume overdrive + + + + + + + AttenuateSwitch + + + + + + + VolumeOverdriveSwitch + + + + + + + Attenuate audio + + + + + + + Notification Sound + + + + + + + MediaSwitch + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Location + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 0 + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + 20 + + + + Permission Required + + + Qt::AlignCenter + + + + + + + To manage location settings in theShell, you'll need to give us permission to be a geoclue agent. + + + Qt::AlignCenter + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Allow theShell to be a geoclue agent + + + + .. + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + Have your administrator password ready + + + Qt::AlignCenter + + + + + + + Qt::Vertical + + + QSizePolicy::Fixed + + + + 20 + 100 + + + + + + + + If you wish to manually configure theShell as a geoclue agent, you'll need to edit /etc/geoclue/geoclue.conf and append "theshell" to the end of the whitelist setting. + + + Qt::AlignCenter + + + true + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 6 + + + 9 + + + 9 + + + 9 + + + 9 + + + + + Allow apps to access your physical location + + + + + + + LocationMasterSwitch + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + Qt::Horizontal + + + + + + + QFrame::NoFrame + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Input + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + QAbstractItemView::NoDragDrop + + + Qt::MoveAction + + + + + + + Keyboard Layout + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop + + + + + + + 0 + + + + + + + + + .. + + + + + + + + + + + .. + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Remove + + + + .. + + + + + + + Add + + + + .. + + + + + + + + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Optimise for touch input + + + + + + + Use Super Key to open Gateway + + + + + + + TouchInputSwitch + + + true + + + + + + + <html><head/><body><p>If you'd like to use the Super Key for another key combination, turn this off so that theShell won't take control of it. <span style=" font-weight:600;">Changing t</span><span style=" font-weight:600;">his setting requires you to log out and then log back in.</span></p></body></html> + + + true + + + + + + + Audible Touch Feedback + + + + + + + TouchFeedbackSwitch + + + true + + + true + + + + + + + SuperkeyGatewaySwitch + + + + + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + + + 0 + 0 + + + + + + + + .. + + + true + + + + + + + + 0 + 0 + + + + + 15 + + + + Select Keyboard Layout + + + 9 + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + QFrame::NoFrame + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Add + + + + .. + + + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Power + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + min + + + + + + + 1 + + + 121 + + + Qt::Horizontal + + + QSlider::TicksBothSides + + + + + + + When this device is running off battery power, + + + + + + + Turn off screen after + + + + + + + Suspend after + + + + + + + 1 + + + 121 + + + Qt::Horizontal + + + QSlider::TicksBothSides + + + + + + + min + + + + + + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + min + + + + + + + Suspend after + + + + + + + 1 + + + 121 + + + Qt::Horizontal + + + QSlider::TicksBothSides + + + + + + + min + + + + + + + 1 + + + 121 + + + Qt::Horizontal + + + QSlider::TicksBothSides + + + + + + + Turn off screen after + + + + + + + When this device is connected to power, + + + + + + + Drag the slider to the right to turn off power management + + + + + + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + Power Button + + + + + + + false + + + + Ask me what to do + + + + .. + + + + + Power Off + + + + .. + + + + + Reboot + + + + .. + + + + + Log Out + + + + .. + + + + + Suspend + + + + .. + + + + + Lock + + + + .. + + + + + Turn Off Screen + + + + .. + + + + + + + + When I press the + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 0 + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Lock Screen + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + SuspendLockScreenSwitch + + + true + + + true + + + + + + + + + + + + Browse... + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Background + + + + + + + Lock screen after returning from suspend + + + + + + + To change your password, go to User settings + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + 0 + + + + + Set Up + + + + .. + + + + + + + Remove Mouse Password + + + + .. + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + Mouse Password + + + + + + + A mouse password trades security for convenience on the lock screen by substituting your password with a sequence of mouse buttons. <b>This can only be used on the lock screen, not while logging in.</b> + + + true + + + + + + + + + Qt::Vertical + + + + 20 + 284 + + + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + true + + + 0 + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 0 + + + + + + 15 + + + + Select a user + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + QFrame::NoFrame + + + 0 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + + + 0 + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Next + + + + .. + + + + + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 0 + + + + + + 0 + 0 + + + + + + + + .. + + + true + + + + + + + + 0 + 0 + + + + + 15 + + + + Edit User + + + 9 + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 6 + + + 9 + + + 9 + + + 9 + + + 9 + + + + + + + Retype Password + + + + + + + Full Name + + + + + + + QLineEdit::Password + + + (unchanged) + + + + + + + Username + + + + + + + + + + + + + QLineEdit::Password + + + (unchanged) + + + + + + + + + + Password + + + + + + + Password Hint + + + + + + + Account Type + + + + + + + 0 + + + + + Standard + + + true + + + + + + + Administrator + + + true + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Delete User + + + + .. + + + + + + + Apply Changes + + + + .. + + + + + + + + + + true + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 0 + + + + + + 0 + 0 + + + + + + + + .. + + + true + + + + + + + + 0 + 0 + + + + + 15 + + + + Delete User + + + 9 + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 6 + + + 9 + + + 9 + + + 9 + + + 9 + + + + + Do you also want to keep files from this user? + +Items that will be kept if you choose to keep files: +- Home directory +- Mail Spool +- Temporary Files + + + + + + + + 75 + true + + + + This is the final step. The user will be deleted once you choose whether to keep or remove files. + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 0 + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Delete user only + + + + .. + + + + + + + Delete user and all files + + + + .. + + + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Date and Time + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 0 + + + + true + + + + 9 + + + 9 + + + 9 + + + 9 + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Set + + + + .. + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + 400 + 200 + + + + + + + + + + + + + Use network to sync date and time + + + + + + + DateTimeNTPSwitch + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + + Use 24 hour time + + + + + + + TwentyFourHourSwitch + + + true + + + true + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Set System Timezone + + + + .. + + + + + + + + + + + + true + + + + 9 + + + 9 + + + 9 + + + 9 + + + + + Where are you located? + + + + + + + + + + 1 + 0 + + + + + 32 + 32 + + + + + + + + + 3 + 0 + + + + + + + + + + + + Back + + + + .. + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + Set Timezone + + + + .. + + + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Language + + + 9 + + + + + + + Qt::Horizontal + + + + + + + QFrame::NoFrame + + + + + + + Changing this setting requires you to log in and then log out. + + + 9 + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Accessibility + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + Large Text + + + + + + + High Contrast + + + + + + + System Animations + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + LargeTextSwitch + + + true + + + + + + + Tone on Caps Lock and Num Lock + + + + + + + HighContrastSwitch + + + true + + + + + + + SystemAnimationsAccessibilitySwitch + + + true + + + true + + + + + + + CapsNumLockBellSwitch + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + Advanced + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + Window Manager Command + + + + + + + + + + false + + + Reset Device + + + + .. + + + + + + + Reset theShell + + + + .. + + + + + + + The items under here can do some bad things. Make sure you know what you're doing. + + + + + + + + + Qt::Vertical + + + + 20 + 224 + + + + + + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + QFrame::NoFrame + + + QFrame::Raised + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 15 + + + + System Information + + + 9 + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + You're using + + + + + + + + 0 + 0 + + + + + 15 + 75 + true + + + + Distribution Name + + + + + + + PointingHandCursor + + + http://www.distro.org/ + + + + + + + PointingHandCursor + + + http://www.distro.org/ + + + + + + + Support + + + + + + + + + Qt::Horizontal + + + + + + + 9 + + + 9 + + + 9 + + + 9 + + + 6 + + + + + Available Swap + + + + + + + Available Memory + + + + + + + + 0 + 0 + + + + 8 GiB + + + + + + + Kernel Version + + + + + + + 8 GiB + + + + + + + 4.11 + + + + + + + Qt Version + + + + + + + 5.9.0 + + + + + + + Processor + + + + + + + Intel + + + + + + + + + + 0 + 0 + + + + Qt::Horizontal + + + + + + + + + + 6 + + + 9 + + + 9 + + + 9 + + + 9 + + + + + + 15 + + + + theShell %1 + + + + + + + Desktop Environment + + + + + + + You compiled theShell on %1 + + + + + + + 0 + + + + + Website + + + + .. + + + + + + + File Bug + + + + .. + + + + + + + Sources + + + + .. + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + 16777215 + 1 + + + + Qt::Horizontal + + + + + + + theShell is Copyright (c) Victor Tran %1. Licensed under the terms of the GNU General Public License, version 3 or later. + + + false + + + 9 + + + + + + + + + + + + + + Qt::Horizontal + + + + + + + + + + + Qt::Vertical + + + QSizePolicy::Fixed + + + + 20 + 9 + + + + + + + + UpArrow + + + Qt::AlignCenter + + + + + + + Qt::Vertical + + + QSizePolicy::Fixed + + + + 20 + 9 + + + + + + + + + ClickableLabel + QLabel +
clickablelabel.h
+ + clicked() + +
+ + AnimatedStackedWidget + QStackedWidget +
animatedstackedwidget.h
+ 1 +
+ + NetworkWidget + QWidget +
networkmanager/networkwidget.h
+ 1 + + networkAvailable(bool) + +
+ + Switch + QPushButton +
switch.h
+
+ + NotificationsWidget + QWidget +
notificationsWidget/notificationswidget.h
+ 1 +
+ + KdeConnectWidget + QWidget +
kdeconnect/kdeconnectwidget.h
+ 1 +
+ + MousePassword + QWidget +
locktypes/mousepassword.h
+ 1 + + exit() + +
+
+ + + + +
diff --git a/shell/menu.cpp b/shell/menu.cpp index a2782b6..8a2b0d8 100644 --- a/shell/menu.cpp +++ b/shell/menu.cpp @@ -21,6 +21,9 @@ #include "menu.h" #include "ui_menu.h" +#define False 0 +#define True 1 + extern void EndSession(EndSessionWait::shutdownType type); extern float getDPIScaling(); extern MainWindow* MainWin; @@ -29,10 +32,9 @@ extern TutorialWindow* TutorialWin; extern NativeEventFilter* NativeFilter; extern ScreenRecorder* screenRecorder; -Menu::Menu(QWidget *parent) : +Menu::Menu(QWidget* parent) : QDialog(parent), - ui(new Ui::Menu) -{ + ui(new Ui::Menu) { ui->setupUi(this); QRect screenGeometry = QApplication::desktop()->screenGeometry(); @@ -125,15 +127,14 @@ Menu::Menu(QWidget *parent) : //this->bt = bt; } -Menu::~Menu() -{ +Menu::~Menu() { delete ui; } void Menu::show() { unsigned long desktop = 0xFFFFFFFF; XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_DESKTOP", False), - XA_CARDINAL, 32, PropModeReplace, (unsigned char*) &desktop, 1); //Set visible on all desktops + XA_CARDINAL, 32, PropModeReplace, (unsigned char*) &desktop, 1); //Set visible on all desktops QDialog::show(); doCheckForClose = true; @@ -163,7 +164,7 @@ void Menu::show() { TutorialWin->showScreen(TutorialWindow::GatewaySearch); } -void Menu::changeEvent(QEvent *event) { +void Menu::changeEvent(QEvent* event) { QDialog::changeEvent(event); if (event->type() == QEvent::ActivationChange) { if (!this->isActiveWindow()) { @@ -187,7 +188,7 @@ void Menu::close() { animation->setDuration(500); animation->setEasingCurve(QEasingCurve::OutCubic); connect(animation, SIGNAL(finished()), animation, SLOT(deleteLater())); - connect(animation, &tPropertyAnimation::finished, [=]() { + connect(animation, &tPropertyAnimation::finished, [ = ]() { emit menuClosing(); QDialog::hide(); }); @@ -206,7 +207,7 @@ void Menu::checkForclose() { } } -bool Menu::checkFocus(QLayout *layout) { +bool Menu::checkFocus(QLayout* layout) { bool hasFocus = this->isActiveWindow(); QLayoutItem* item; while ((item = layout->takeAt(0)) != NULL) { @@ -223,8 +224,7 @@ bool Menu::checkFocus(QLayout *layout) { return hasFocus; } -void Menu::on_pushButton_clicked() -{ +void Menu::on_pushButton_clicked() { if (settings.value("ui/useFullScreenEndSession", false).toBool()) { EndSessionWait* endSession = new EndSessionWait(EndSessionWait::ask); endSession->showFullScreen(); @@ -249,8 +249,7 @@ void Menu::on_pushButton_clicked() } } -void Menu::on_pushButton_2_clicked() -{ +void Menu::on_pushButton_2_clicked() { /*tPropertyAnimation* anim = new tPropertyAnimation(ui->offFrame, "geometry"); anim->setStartValue(QRect(10 * getDPIScaling(), 10 * getDPIScaling(), this->width() - 20 * getDPIScaling(), this->height() - 20 * getDPIScaling())); //anim->setEndValue(QRect(10, this->height(), this->width() - 20, this->height() - 20)); @@ -267,8 +266,7 @@ void Menu::on_pushButton_2_clicked() ui->stackedWidget->setCurrentIndex(0); } -void Menu::on_commandLinkButton_clicked() -{ +void Menu::on_commandLinkButton_clicked() { if (ui->endSessionWarnings->count() > 0) { pendingEndSessionType = EndSessionWait::powerOff; ui->endSessionAnywayButton->setText(tr("Power Off Anyway")); @@ -279,8 +277,7 @@ void Menu::on_commandLinkButton_clicked() } } -void Menu::on_commandLinkButton_2_clicked() -{ +void Menu::on_commandLinkButton_2_clicked() { if (ui->endSessionWarnings->count() > 0) { pendingEndSessionType = EndSessionWait::reboot; ui->endSessionAnywayButton->setText(tr("Reboot Anyway")); @@ -291,8 +288,7 @@ void Menu::on_commandLinkButton_2_clicked() } } -void Menu::on_commandLinkButton_3_clicked() -{ +void Menu::on_commandLinkButton_3_clicked() { if (ui->endSessionWarnings->count() > 0) { pendingEndSessionType = EndSessionWait::logout; ui->endSessionAnywayButton->setText(tr("Log Out Anyway")); @@ -303,20 +299,19 @@ void Menu::on_commandLinkButton_3_clicked() } } -void Menu::on_lineEdit_textEdited(const QString &arg1) -{ +void Menu::on_lineEdit_textEdited(const QString& arg1) { ((AppsListModel*) ui->appsListView->model())->search(arg1); ui->appsListView->selectionModel()->select(ui->appsListView->model()->index(0, 0), QItemSelectionModel::ClearAndSelect); } -bool Menu::eventFilter(QObject *object, QEvent *event) { +bool Menu::eventFilter(QObject* object, QEvent* event) { if (event->type() == QEvent::KeyPress && ((QKeyEvent*) event)->key() == Qt::Key_Escape) { this->close(); return true; } if (event->type() == QEvent::KeyPress) { - QKeyEvent *e = (QKeyEvent*) event; + QKeyEvent* e = (QKeyEvent*) event; int currentRow; if (ui->appsListView->selectionModel()->selectedRows().count() == 0) { @@ -334,8 +329,8 @@ bool Menu::eventFilter(QObject *object, QEvent *event) { } } } else if ((QApplication::layoutDirection() == Qt::RightToLeft - ? e->key() == Qt::Key_Left - : e->key() == Qt::Key_Right) && ui->appsListView->model()->index(currentRow, 0).data(Qt::UserRole + 3).value().actions().count() > 0) { + ? e->key() == Qt::Key_Left + : e->key() == Qt::Key_Right) && ui->appsListView->model()->index(currentRow, 0).data(Qt::UserRole + 3).value().actions().count() > 0) { showActionMenuByIndex(ui->appsListView->model()->index(currentRow, 0)); return true; } else if (e->key() == Qt::Key_Down) { @@ -367,15 +362,15 @@ bool Menu::eventFilter(QObject *object, QEvent *event) { ui->appsListView->scrollTo(indexToSelect); return true; } else { - if (object != ui->lineEdit) { - ui->lineEdit->event(event); - return true; - } + if (object != ui->lineEdit) { + ui->lineEdit->event(event); + return true; + } } e->ignore(); return false; } else if (event->type() == QEvent::MouseButtonRelease && object == ui->appsListView->viewport()) { - QMouseEvent *e = (QMouseEvent*) event; + QMouseEvent* e = (QMouseEvent*) event; QModelIndex index = ui->appsListView->indexAt(e->pos()); if (!index.isValid()) { return false; @@ -383,9 +378,9 @@ bool Menu::eventFilter(QObject *object, QEvent *event) { QList acts = index.data(Qt::UserRole + 3).value().actions(); if (acts.count() > 0 && - QApplication::layoutDirection() == Qt::RightToLeft - ?(e->pos().x() < 34 * getDPIScaling()) - :(e->pos().x() > ui->appsListView->viewport()->width() - 34 * getDPIScaling())) { + QApplication::layoutDirection() == Qt::RightToLeft + ? (e->pos().x() < 34 * getDPIScaling()) + : (e->pos().x() > ui->appsListView->viewport()->width() - 34 * getDPIScaling())) { showActionMenuByIndex(index); } else { launchAppByIndex(index); @@ -397,8 +392,7 @@ bool Menu::eventFilter(QObject *object, QEvent *event) { } } -void Menu::on_lineEdit_returnPressed() -{ +void Menu::on_lineEdit_returnPressed() { /*if (ui->listWidget->count() > 0) { if (ui->listWidget->selectedItems().count() == 1) { on_listWidget_itemClicked(ui->listWidget->selectedItems().first()); @@ -417,19 +411,17 @@ void Menu::on_lineEdit_returnPressed() } } -void Menu::on_pushButton_3_clicked() -{ +void Menu::on_pushButton_3_clicked() { QProcess::startDetached("scallop"); this->close(); } -void Menu::on_commandLinkButton_5_clicked() -{ +void Menu::on_commandLinkButton_5_clicked() { EndSession(EndSessionWait::suspend); this->close(); } -void Menu::paintEvent(QPaintEvent *event) { +void Menu::paintEvent(QPaintEvent* event) { QPainter painter(this); //painter.setRenderHint(QPainter::Antialiasing); painter.setPen(this->palette().color(QPalette::WindowText)); @@ -446,28 +438,25 @@ void Menu::paintEvent(QPaintEvent *event) { void Menu::setGeometry(int x, int y, int w, int h) { //Use wmctrl command because KWin has a problem with moving windows offscreen. QDialog::setGeometry(x, y, w, h); QProcess::execute("wmctrl -r " + this->windowTitle() + " -e 0," + - QString::number(x) + "," + QString::number(y) + "," + - QString::number(w) + "," + QString::number(h)); + QString::number(x) + "," + QString::number(y) + "," + + QString::number(w) + "," + QString::number(h)); } void Menu::setGeometry(QRect geometry) { this->setGeometry(geometry.x(), geometry.y(), geometry.width(), geometry.height()); } -void Menu::on_commandLinkButton_7_clicked() -{ +void Menu::on_commandLinkButton_7_clicked() { EndSession(EndSessionWait::hibernate); this->close(); } -void Menu::on_commandLinkButton_8_clicked() -{ +void Menu::on_commandLinkButton_8_clicked() { EndSession(EndSessionWait::screenOff); this->close(); } -void Menu::on_commandLinkButton_6_clicked() -{ +void Menu::on_commandLinkButton_6_clicked() { this->close(); DBusEvents->LockScreen(); } @@ -481,22 +470,21 @@ struct LoginSession { }; Q_DECLARE_METATYPE(LoginSession) -const QDBusArgument &operator<<(QDBusArgument &argument, const LoginSession &session) { +const QDBusArgument& operator<<(QDBusArgument& argument, const LoginSession& session) { argument.beginStructure(); argument << session.sessionId << session.userId << session.username << session.seat << session.path; argument.endStructure(); return argument; } -const QDBusArgument &operator>>(const QDBusArgument &argument, LoginSession &session) { +const QDBusArgument& operator>>(const QDBusArgument& argument, LoginSession& session) { argument.beginStructure(); argument >> session.sessionId >> session.userId >> session.username >> session.seat >> session.path; argument.endStructure(); return argument; } -void Menu::on_commandLinkButton_4_clicked() -{ +void Menu::on_commandLinkButton_4_clicked() { //Load available users QDBusInterface i("org.freedesktop.login1", "/org/freedesktop/login1/session/self", "org.freedesktop.login1.Session", QDBusConnection::systemBus()); QString thisId = i.property("Id").toString(); @@ -566,7 +554,7 @@ void Menu::on_commandLinkButton_4_clicked() } } -void Menu::mousePressEvent(QMouseEvent *event) { +void Menu::mousePressEvent(QMouseEvent* event) { if (QApplication::isRightToLeft()) { if (event->x() < 5) { resizing = true; @@ -578,7 +566,7 @@ void Menu::mousePressEvent(QMouseEvent *event) { } } -void Menu::mouseMoveEvent(QMouseEvent *event) { +void Menu::mouseMoveEvent(QMouseEvent* event) { QRect screenGeometry = QApplication::desktop()->screenGeometry(); if (resizing) { int width; @@ -614,14 +602,13 @@ void Menu::mouseMoveEvent(QMouseEvent *event) { } } -void Menu::mouseReleaseEvent(QMouseEvent *event) { +void Menu::mouseReleaseEvent(QMouseEvent* event) { resizing = false; this->setCursor(QCursor(Qt::ArrowCursor)); settings.setValue("gateway/width", this->width()); } -void Menu::on_exitButton_clicked() -{ +void Menu::on_exitButton_clicked() { QApplication::exit(0); } @@ -629,8 +616,7 @@ void Menu::reject() { this->close(); } -void Menu::on_fakeEndButton_clicked() -{ +void Menu::on_fakeEndButton_clicked() { if (ui->endSessionWarnings->count() > 0) { pendingEndSessionType = EndSessionWait::dummy; ui->endSessionAnywayButton->setText("Perform Fake Exit Anyway"); @@ -641,20 +627,17 @@ void Menu::on_fakeEndButton_clicked() } } -void Menu::on_helpButton_clicked() -{ +void Menu::on_helpButton_clicked() { QProcess::startDetached("xdg-open https://vicr123.github.io/theshell/help"); this->close(); } -void Menu::on_reportBugButton_clicked() -{ +void Menu::on_reportBugButton_clicked() { QProcess::startDetached("xdg-open https://github.com/vicr123/theshell/issues"); this->close(); } -void Menu::launchAppByIndex(const QModelIndex &index) -{ +void Menu::launchAppByIndex(const QModelIndex& index) { if (((AppsListModel*) ui->appsListView->model())->launchApp(index)) { this->close(); } @@ -666,7 +649,7 @@ void Menu::showActionMenuByIndex(QModelIndex index) { QList acts = index.data(Qt::UserRole + 3).value().actions(); for (App action : acts) { - menu->addAction(QIcon::fromTheme("arrow-right"), action.name(), [=] { + menu->addAction(QIcon::fromTheme("arrow-right"), action.name(), [ = ] { QString command = action.command(); command.remove("env "); QProcess* process = new QProcess(); @@ -688,12 +671,11 @@ void Menu::showActionMenuByIndex(QModelIndex index) { QRect rect = ui->appsListView->visualRect(index); menu->exec(ui->appsListView->mapToGlobal(QApplication::layoutDirection() == Qt::RightToLeft - ? rect.topLeft() - : rect.topRight())); + ? rect.topLeft() + : rect.topRight())); } -void Menu::on_appsListView_customContextMenuRequested(const QPoint &pos) -{ +void Menu::on_appsListView_customContextMenuRequested(const QPoint& pos) { QModelIndex index = ui->appsListView->indexAt(pos); if (index.isValid()) { QString desktopEntry = index.data(Qt::UserRole + 2).toString(); @@ -702,7 +684,7 @@ void Menu::on_appsListView_customContextMenuRequested(const QPoint &pos) menu->addSection(index.data(Qt::DecorationRole).value(), tr("For \"%1\"").arg(index.data(Qt::DisplayRole).toString())); if (index.data(Qt::UserRole + 1).toBool()) { - menu->addAction(QIcon::fromTheme("bookmark-remove"), "Undock", [=] { + menu->addAction(QIcon::fromTheme("bookmark-remove"), "Undock", [ = ] { settings.beginGroup("gateway"); QStringList oldEntries; @@ -728,7 +710,7 @@ void Menu::on_appsListView_customContextMenuRequested(const QPoint &pos) ((AppsListModel*) ui->appsListView->model())->loadData(); }); } else { - menu->addAction(QIcon::fromTheme("bookmark-new"), "Dock", [=] { + menu->addAction(QIcon::fromTheme("bookmark-new"), "Dock", [ = ] { settings.beginGroup("gateway"); QStringList oldEntries; @@ -759,23 +741,19 @@ void Menu::on_appsListView_customContextMenuRequested(const QPoint &pos) } } -void Menu::on_cancelEndSessionWarningButton_clicked() -{ +void Menu::on_cancelEndSessionWarningButton_clicked() { ui->stackedWidget->setCurrentIndex(1); } -void Menu::on_endSessionAnywayButton_clicked() -{ +void Menu::on_endSessionAnywayButton_clicked() { EndSession(pendingEndSessionType); } -void Menu::on_cancelSwitchUsersButton_clicked() -{ +void Menu::on_cancelSwitchUsersButton_clicked() { ui->stackedWidget->setCurrentIndex(1); } -void Menu::on_startNewSessionButton_clicked() -{ +void Menu::on_startNewSessionButton_clicked() { this->close(); DBusEvents->LockScreen(); @@ -783,8 +761,7 @@ void Menu::on_startNewSessionButton_clicked() QDBusConnection::systemBus().send(message); } -void Menu::on_availableUsersList_itemActivated(QListWidgetItem *item) -{ +void Menu::on_availableUsersList_itemActivated(QListWidgetItem* item) { this->close(); DBusEvents->LockScreen(); diff --git a/shell/menu.h b/shell/menu.h index 2d33db3..40f2395 100644 --- a/shell/menu.h +++ b/shell/menu.h @@ -32,7 +32,6 @@ #include #include #include -#include "endsessionwait.h" #include "mainwindow.h" #include "dbusevents.h" #include "tutorialwindow.h" @@ -41,20 +40,20 @@ #include "apps/appslistmodel.h" #include "networkmanager/availablenetworkslist.h" #include "screenrecorder.h" +#include "endsessionwait.h" #undef KeyPress namespace Ui { -class Menu; + class Menu; } -class Menu : public QDialog -{ - Q_OBJECT - Q_PROPERTY(QRect geometry READ geometry WRITE setGeometry) +class Menu : public QDialog { + Q_OBJECT + Q_PROPERTY(QRect geometry READ geometry WRITE setGeometry) public: - explicit Menu(QWidget *parent = 0); + explicit Menu(QWidget* parent = 0); ~Menu(); void setGeometry(int x, int y, int w, int h); void setGeometry(QRect geometry); @@ -80,9 +79,9 @@ class Menu : public QDialog void on_commandLinkButton_3_clicked(); - void on_lineEdit_textEdited(const QString &arg1); + void on_lineEdit_textEdited(const QString& arg1); - bool eventFilter(QObject *object, QEvent *event); + bool eventFilter(QObject* object, QEvent* event); void on_lineEdit_returnPressed(); @@ -106,11 +105,11 @@ class Menu : public QDialog void on_reportBugButton_clicked(); - void launchAppByIndex(const QModelIndex &index); + void launchAppByIndex(const QModelIndex& index); void showActionMenuByIndex(QModelIndex index); - void on_appsListView_customContextMenuRequested(const QPoint &pos); + void on_appsListView_customContextMenuRequested(const QPoint& pos); void on_cancelEndSessionWarningButton_clicked(); @@ -120,12 +119,12 @@ class Menu : public QDialog void on_startNewSessionButton_clicked(); - void on_availableUsersList_itemActivated(QListWidgetItem *item); + void on_availableUsersList_itemActivated(QListWidgetItem* item); private: - Ui::Menu *ui; + Ui::Menu* ui; - bool checkFocus(QLayout *layout); + bool checkFocus(QLayout* layout); QSettings settings; //QList apps; diff --git a/shell/newmedia.cpp b/shell/newmedia.cpp index f9d30e1..309ffbd 100644 --- a/shell/newmedia.cpp +++ b/shell/newmedia.cpp @@ -21,10 +21,12 @@ #include "newmedia.h" #include "ui_newmedia.h" -NewMedia::NewMedia(QString description, QWidget *parent) : +#define False 0 +#define True 1 + +NewMedia::NewMedia(QString description, QWidget* parent) : QDialog(parent), - ui(new Ui::NewMedia) -{ + ui(new Ui::NewMedia) { ui->setupUi(this); ui->description->setText(description); @@ -34,8 +36,7 @@ NewMedia::NewMedia(QString description, QWidget *parent) : ui->openFiles->setVisible(false); } -NewMedia::~NewMedia() -{ +NewMedia::~NewMedia() { delete ui; } @@ -43,8 +44,8 @@ NewMedia::~NewMedia() void NewMedia::setGeometry(int x, int y, int w, int h) { //Use wmctrl command because KWin has a problem with moving windows offscreen. QDialog::setGeometry(x, y, w, h); QProcess::execute("wmctrl -r " + this->windowTitle() + " -e 0," + - QString::number(x) + "," + QString::number(y) + "," + - QString::number(w) + "," + QString::number(h)); + QString::number(x) + "," + QString::number(y) + "," + + QString::number(w) + "," + QString::number(h)); } void NewMedia::setGeometry(QRect geometry) { @@ -55,23 +56,23 @@ void NewMedia::show() { Atom DesktopWindowTypeAtom; DesktopWindowTypeAtom = XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE_NOTIFICATION", False); int retval = XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_WINDOW_TYPE", False), - XA_ATOM, 32, PropModeReplace, (unsigned char*) &DesktopWindowTypeAtom, 1); //Change Window Type + XA_ATOM, 32, PropModeReplace, (unsigned char*) &DesktopWindowTypeAtom, 1); //Change Window Type unsigned long desktop = 0xFFFFFFFF; retval = XChangeProperty(QX11Info::display(), this->winId(), XInternAtom(QX11Info::display(), "_NET_WM_DESKTOP", False), - XA_CARDINAL, 32, PropModeReplace, (unsigned char*) &desktop, 1); //Set visible on all desktops + XA_CARDINAL, 32, PropModeReplace, (unsigned char*) &desktop, 1); //Set visible on all desktops QDialog::show(); QRect screenGeometry = QApplication::desktop()->screenGeometry(); this->setGeometry(screenGeometry.x(), screenGeometry.y() - this->height(), screenGeometry.width(), this->height()); - tPropertyAnimation *anim = new tPropertyAnimation(this, "geometry"); + tPropertyAnimation* anim = new tPropertyAnimation(this, "geometry"); anim->setStartValue(this->geometry()); anim->setEndValue(QRect(screenGeometry.x(), screenGeometry.y(), screenGeometry.width(), this->height())); anim->setDuration(100); anim->setEasingCurve(QEasingCurve::OutCubic); - connect(anim, &tPropertyAnimation::finished, [=](){ + connect(anim, &tPropertyAnimation::finished, [ = ]() { this->repaint(); }); anim->start(); @@ -92,12 +93,12 @@ void NewMedia::show() { void NewMedia::close() { QRect screenGeometry = QApplication::desktop()->screenGeometry(); - tPropertyAnimation *anim = new tPropertyAnimation(this, "geometry"); + tPropertyAnimation* anim = new tPropertyAnimation(this, "geometry"); anim->setStartValue(this->geometry()); anim->setEndValue(QRect(screenGeometry.x(), screenGeometry.y() - this->height(), screenGeometry.width(), this->height())); anim->setDuration(500); anim->setEasingCurve(QEasingCurve::InCubic); - connect(anim, &tPropertyAnimation::finished, [=]() { + connect(anim, &tPropertyAnimation::finished, [ = ]() { QDialog::close(); }); anim->start(); @@ -107,19 +108,17 @@ void NewMedia::reject() { this->close(); } -void NewMedia::paintEvent(QPaintEvent *event) { +void NewMedia::paintEvent(QPaintEvent* event) { QPainter painter(this); painter.setPen(this->palette().color(QPalette::WindowText)); painter.drawLine(0, this->height() - 1, this->width(), this->height() - 1); event->accept(); } -void NewMedia::on_closeButton_clicked() -{ +void NewMedia::on_closeButton_clicked() { this->close(); } -void NewMedia::on_doNothingOptionToolButton_clicked() -{ +void NewMedia::on_doNothingOptionToolButton_clicked() { this->close(); } diff --git a/shell/newmedia.h b/shell/newmedia.h index 228b44f..337db5c 100644 --- a/shell/newmedia.h +++ b/shell/newmedia.h @@ -46,34 +46,35 @@ #undef FocusOut #undef CursorShape #undef Unsorted +#undef False +#undef True namespace Ui { -class NewMedia; + class NewMedia; } -class NewMedia : public QDialog -{ - Q_OBJECT +class NewMedia : public QDialog { + Q_OBJECT -public: - explicit NewMedia(QString description, QWidget *parent = 0); - ~NewMedia(); + public: + explicit NewMedia(QString description, QWidget* parent = 0); + ~NewMedia(); - void show(); - void close(); - void reject(); + void show(); + void close(); + void reject(); - void setGeometry(int x, int y, int w, int h); - void setGeometry(QRect geometry); -private slots: - void on_closeButton_clicked(); + void setGeometry(int x, int y, int w, int h); + void setGeometry(QRect geometry); + private slots: + void on_closeButton_clicked(); - void on_doNothingOptionToolButton_clicked(); + void on_doNothingOptionToolButton_clicked(); -private: - Ui::NewMedia *ui; + private: + Ui::NewMedia* ui; - void paintEvent(QPaintEvent* event); + void paintEvent(QPaintEvent* event); }; #endif // NEWMEDIA_H diff --git a/shell/shell.pro b/shell/shell.pro index cb735ff..82d6fd7 100644 --- a/shell/shell.pro +++ b/shell/shell.pro @@ -15,7 +15,7 @@ unix { greaterThan(QT_MAJOR_VERSION, 4): QT += widgets -DEFINES += TS_VERSION='\\"8.0.1\\"' +DEFINES += TS_VERSION='\\"8.0.2\\"' unix { QT += thelib x11extras diff --git a/shell/systrayicons.cpp b/shell/systrayicons.cpp index 4962466..6d07517 100644 --- a/shell/systrayicons.cpp +++ b/shell/systrayicons.cpp @@ -21,18 +21,19 @@ #include "systrayicons.h" #define None 0L +#define False 0 +#define True 1 extern NativeEventFilter* NativeFilter; -SysTrayIcons::SysTrayIcons(QWidget *parent) : QFrame(parent) -{ +SysTrayIcons::SysTrayIcons(QWidget* parent) : QFrame(parent) { //Prepare a layout for the system tray QBoxLayout* layout = new QBoxLayout(QBoxLayout::LeftToRight); layout->setSpacing(6); this->setLayout(layout); //Connect the signal to dock a system tray - connect(NativeFilter, SIGNAL(SysTrayEvent(long,long,long,long)), this, SLOT(SysTrayEvent(long,long,long,long))); + connect(NativeFilter, SIGNAL(SysTrayEvent(long, long, long, long)), this, SLOT(SysTrayEvent(long, long, long, long))); //Get the correct manager selection unsigned long selection = 0; @@ -104,11 +105,11 @@ void SysTrayIcons::SysTrayEvent(long opcode, long data2, long data3, long data4) widget->setFixedSize(16, 16); this->layout()->addWidget(widget); - connect(window, &QWindow::destroyed, [=]() { + connect(window, &QWindow::destroyed, [ = ]() { widget->deleteLater(); }); - connect(window, &QWindow::visibleChanged, [=](bool visible) { - widget->setVisible(visible); + connect(window, &QWindow::visibleChanged, [ = ](bool visible) { + widget->setVisible(visible); }); } } @@ -128,7 +129,7 @@ void SysTrayIcons::SniItemUnregistered(QString service) { } } -SniIcon::SniIcon(QString service, QWidget *parent) : QLabel(parent) { +SniIcon::SniIcon(QString service, QWidget* parent) : QLabel(parent) { this->service = service; QStringList pathParts = service.split("/"); service = pathParts.first(); @@ -213,7 +214,7 @@ void SniIcon::ReloadIcon() { } } -void SniIcon::mouseReleaseEvent(QMouseEvent *event) { +void SniIcon::mouseReleaseEvent(QMouseEvent* event) { QPoint pos = this->mapToGlobal(event->pos()); if (event->button() == Qt::LeftButton) { interface->call("Activate", pos.x(), pos.y()); @@ -224,7 +225,7 @@ void SniIcon::mouseReleaseEvent(QMouseEvent *event) { } } -void SniIcon::wheelEvent(QWheelEvent *event) { +void SniIcon::wheelEvent(QWheelEvent* event) { if (event->orientation() == Qt::Vertical) { interface->call("Scroll", event->delta(), "vertical"); } else { diff --git a/theShell.pro.user b/theShell.pro.user index c059eb7..d533110 100644 --- a/theShell.pro.user +++ b/theShell.pro.user @@ -1,10 +1,10 @@ - + EnvironmentId - {764bc000-0a42-4188-b804-04ae5db917cd} + {f2fc4ec7-edcf-4ab7-9629-49d8f336bec9} ProjectExplorer.Project.ActiveTarget @@ -49,218 +49,237 @@ true true true + *.md, *.MD, Makefile false + true ProjectExplorer.Project.PluginSettings - + + + true + true + true + true + true + + + 0 + true + + true + Builtin.Questionable + + true + Builtin.DefaultTidyAndClazy + 8 + + + + true + + ProjectExplorer.Project.Target.0 - Desktop - Desktop - {0165bd08-f8f7-40a8-9b5a-0fb153c311ea} + Desktop + Chroot + Chroot + {349428f3-052e-4ff1-9317-285f3968ad62} 0 0 - 3 + 0 - /home/victor/Documents/Apps/build-theShell-Desktop-Debug + true + 0 + /home/victor/Documents/Apps/build-theShell-Chroot-Debug + /home/victor/Documents/Apps/build-theShell-Chroot-Debug true - qmake - QtProjectManager.QMakeBuildStep - false - CONFIG+=construction + false - false - false + true - Make - Qt4ProjectManager.MakeStep - - -w - -r - + false + false 2 Build - + Build ProjectExplorer.BuildSteps.Build true - Make - Qt4ProjectManager.MakeStep - - -w - -r - + true clean + false 1 Clean - + Clean ProjectExplorer.BuildSteps.Clean 2 false + - Debug - + Debug Qt4ProjectManager.Qt4BuildConfiguration 2 - true + 2 + 2 - /home/victor/Documents/Apps/build-theShell-Desktop-Release + true + 2 + /home/victor/Documents/Apps/build-theShell-Chroot-Release + /home/victor/Documents/Apps/build-theShell-Chroot-Release true - qmake - QtProjectManager.QMakeBuildStep - false false - false - false + true - Make - Qt4ProjectManager.MakeStep - - -w - -r - + false + false 2 Build - + Build ProjectExplorer.BuildSteps.Build true - Make - Qt4ProjectManager.MakeStep - - -w - -r - + true clean + false 1 Clean - + Clean ProjectExplorer.BuildSteps.Clean 2 false + - Release - + Release Qt4ProjectManager.Qt4BuildConfiguration 0 - true + 0 + 2 - /home/victor/Documents/Apps/build-theShell-Desktop-Profile + true + 0 + /home/victor/Documents/Apps/build-theShell-Chroot-Profile + /home/victor/Documents/Apps/build-theShell-Chroot-Profile true - qmake - QtProjectManager.QMakeBuildStep - true false - true - false + true - Make - Qt4ProjectManager.MakeStep - - -w - -r - + false + false 2 Build - + Build ProjectExplorer.BuildSteps.Build true - Make - Qt4ProjectManager.MakeStep - - -w - -r - + true clean + false 1 Clean - + Clean ProjectExplorer.BuildSteps.Clean 2 false + - Profile - + Profile Qt4ProjectManager.Qt4BuildConfiguration 0 - true + 0 + 0 3 0 Deploy - + Deploy ProjectExplorer.BuildSteps.Deploy 1 - Deploy locally - + + false ProjectExplorer.DefaultDeployConfiguration 1 + dwarf + + cpu-cycles + + + 250 + + -e + cpu-cycles + --call-graph + dwarf,4096 + -F + 250 + + -F + true + 4096 false false 1000 @@ -275,6 +294,7 @@ 0.01 10 true + kcachegrind 1 25 @@ -300,24 +320,41 @@ 13 14 + 2 - startsession - - Qt4ProjectManager.Qt4RunConfiguration:/home/victor/Documents/Apps/theShell/startsession/startsession.pro - true - --no-autostart - startsession/startsession.pro - - /home/victor/Documents/Apps/build-theShell-Desktop-Debug/startsession - 3768 + Qt4ProjectManager.Qt4RunConfiguration:/home/victor/Documents/Apps/theshell/mousepass/mousepass.pro + /home/victor/Documents/Apps/theshell/mousepass/mousepass.pro + + false + false true + true false false true + + /home/victor/Documents/Apps/build-theShell-Chroot-Debug/mousepass + dwarf + + cpu-cycles + + + 250 + + -e + cpu-cycles + --call-graph + dwarf,4096 + -F + 250 + + -F + true + 4096 false false 1000 @@ -332,12 +369,13 @@ 0.01 10 true - 2 + kcachegrind + 1 25 1 true - true + false true valgrind @@ -357,24 +395,41 @@ 13 14 + 2 - polkitagent - - Qt4ProjectManager.Qt4RunConfiguration:/home/victor/Documents/Apps/theShell/polkitagent/polkitagent.pro - true - - polkitagent/polkitagent.pro - - /home/victor/Documents/Apps/build-theShell-Desktop-Debug/polkitagent - 3768 + Qt4ProjectManager.Qt4RunConfiguration:/home/victor/Documents/Apps/theshell/polkitagent/polkitagent.pro + /home/victor/Documents/Apps/theshell/polkitagent/polkitagent.pro + + false + false true + true false false true + + /home/victor/Documents/Apps/build-theShell-Chroot-Debug/polkitagent + dwarf + + cpu-cycles + + + 250 + + -e + cpu-cycles + --call-graph + dwarf,4096 + -F + 250 + + -F + true + 4096 false false 1000 @@ -389,12 +444,13 @@ 0.01 10 true - 2 + kcachegrind + 1 25 1 true - true + false true valgrind @@ -414,24 +470,41 @@ 13 14 + 2 - mousepass - - Qt4ProjectManager.Qt4RunConfiguration:/home/victor/Documents/Apps/theShell/mousepass/mousepass.pro - true - - mousepass/mousepass.pro - - /home/victor/Documents/Apps/build-theShell-Desktop-Debug/mousepass - 3768 + Qt4ProjectManager.Qt4RunConfiguration:/home/victor/Documents/Apps/theshell/startsession/startsession.pro + /home/victor/Documents/Apps/theshell/startsession/startsession.pro + + false + false true + true false false true + + /home/victor/Documents/Apps/build-theShell-Chroot-Debug/startsession + dwarf + + cpu-cycles + + + 250 + + -e + cpu-cycles + --call-graph + dwarf,4096 + -F + 250 + + -F + true + 4096 false false 1000 @@ -446,12 +519,13 @@ 0.01 10 true - 2 + kcachegrind + 1 25 1 true - true + false true valgrind @@ -471,22 +545,22 @@ 13 14 + 2 - shell - - Qt4ProjectManager.Qt4RunConfiguration:/home/victor/Documents/Apps/theShell/shell/shell.pro - true - - shell/shell.pro - - /home/victor/Documents/Apps/build-theShell-Desktop-Debug/shell - 3768 + Qt4ProjectManager.Qt4RunConfiguration:/home/victor/Documents/Apps/theshell/shell/shell.pro + /home/victor/Documents/Apps/theshell/shell/shell.pro + + false + false true + true false false true + + /home/victor/Documents/Apps/build-theShell-Chroot-Debug/shell 4 @@ -497,10 +571,10 @@ ProjectExplorer.Project.Updater.FileVersion - 18 + 22 Version - 18 + 22