From 71c2fda95224f0a04316c5f1059628d33564ca43 Mon Sep 17 00:00:00 2001 From: Ken Moore Date: Thu, 18 Dec 2014 07:47:48 -0500 Subject: [PATCH] Commit a checkpoint on the conversion of Lumina to Qt5. It is functional at the moment, but still has a few rough edges with regards to the X11 background interface (due to the move from XLib to XCB in Qt5). This reulst in some of the window manager interactions not behaving properly (such as sticky status on panels). --- DEPENDENCIES | 22 +- libLumina/LuminaOS.h | 1 + libLumina/LuminaSingleApplication.cpp | 107 +++++++++ libLumina/LuminaSingleApplication.h | 54 +++++ libLumina/LuminaThemes.cpp | 2 +- libLumina/LuminaUtils.cpp | 4 + libLumina/LuminaUtils.h | 1 + libLumina/LuminaX11.cpp | 208 +++++++++++++++++- libLumina/LuminaX11.h | 35 +++ libLumina/LuminaXDG.cpp | 19 +- libLumina/LuminaXDG.h | 2 + libLumina/libLumina.pro | 12 +- libLumina/make-linux-distro.sh | 0 lumina-config/lumina-config.pro | 15 +- lumina-config/main.cpp | 18 +- lumina-desktop/LDesktop.cpp | 24 +- lumina-desktop/LPanel.cpp | 14 +- lumina-desktop/LSession.cpp | 95 ++++++-- lumina-desktop/LSession.h | 24 +- lumina-desktop/LWinInfo.h | 1 + .../desktop-plugins/notepad/NotepadPlugin.cpp | 2 +- lumina-desktop/lumina-desktop.pro | 8 +- lumina-desktop/main.cpp | 6 +- lumina-desktop/panel-plugins/LPPlugin.h | 1 + lumina-desktop/panel-plugins/LTBWidget.h | 17 +- .../panel-plugins/systemtray/LSysTray.cpp | 14 +- .../panel-plugins/systemtray/LSysTray.h | 2 +- .../panel-plugins/systemtray/TrayIcon.cpp | 22 +- .../panel-plugins/taskmanager/LTaskButton.cpp | 27 +-- .../taskmanager/LTaskManagerPlugin.cpp | 2 +- .../userbutton/UserItemWidget.cpp | 14 +- lumina-fm/BackgroundWorker.cpp | 11 +- lumina-fm/MainUI.cpp | 120 +++++----- lumina-fm/MainUI.h | 26 ++- lumina-fm/lumina-fm.pro | 9 +- lumina-fm/main.cpp | 23 +- lumina-open/LFileDialog.h | 1 + lumina-open/lumina-open.pro | 1 + lumina-open/main.cpp | 4 +- lumina-screenshot/MainUI.cpp | 7 +- lumina-screenshot/MainUI.h | 2 + lumina-screenshot/MainUI.ui | 2 +- lumina-screenshot/lumina-screenshot.pro | 13 +- lumina-screenshot/main.cpp | 2 +- lumina-search/lumina-search.pro | 13 +- lumina-search/main.cpp | 5 +- port-files/Makefile | 12 +- port-files/pkg-plist | 1 + 48 files changed, 783 insertions(+), 242 deletions(-) create mode 100644 libLumina/LuminaSingleApplication.cpp create mode 100644 libLumina/LuminaSingleApplication.h mode change 100644 => 100755 libLumina/make-linux-distro.sh diff --git a/DEPENDENCIES b/DEPENDENCIES index dafae1e01..8e9e8c5ff 100644 --- a/DEPENDENCIES +++ b/DEPENDENCIES @@ -20,6 +20,7 @@ xbrightness (x11/xbrightness) (Screen Brightness Control) Build time dependencies: +== (Version 0.7.2) == Qt 4.8+ qt4-core (devel/qt4-corelib)) qt4-gui (x11-toolkits/qt4-gui) @@ -31,11 +32,30 @@ Qt 4.8+ qt4-moc (devel/qt4-moc) qt4-rcc (devel/qt4-rcc) devel/qt4-qtsolutions-singleapplication - + X.org and XLib with extensions: Xrender (x11/libXrender) Xcomposite (x11/libXcomposite) Xdamage (x11/libXdamage) + +== (Version 0.8.0+) == +Qt 5.2+ + qt5-core + qt5-buildtools + qt5-gui + qt5-widgets + qt5-multimedia + qt5-network + qt5-qmake + qt5-svg + qt5-x11extras + +X.org and XCB extensions (possibly the XLib libraries above during the transition phase): + libxcb + xcb-util-wm (window manager framework) + xcb-damage (included in base XCB lib?) + xcb-composite (included in base XCB lib?) + xcb-render (included in base XCB lib?) diff --git a/libLumina/LuminaOS.h b/libLumina/LuminaOS.h index 90f68691e..7bf0e9230 100644 --- a/libLumina/LuminaOS.h +++ b/libLumina/LuminaOS.h @@ -16,6 +16,7 @@ #include #include #include +#include #include "LuminaUtils.h" diff --git a/libLumina/LuminaSingleApplication.cpp b/libLumina/LuminaSingleApplication.cpp new file mode 100644 index 000000000..ce9830354 --- /dev/null +++ b/libLumina/LuminaSingleApplication.cpp @@ -0,0 +1,107 @@ +//=========================================== +// Lumina-DE source code +// Copyright (c) 2014, Ken Moore +// Available under the 3-clause BSD license +// See the LICENSE file for full details +//=========================================== +#include "LuminaSingleApplication.h" +#include +#include +#include +#include + +#include //for getlogin() + +LSingleApplication::LSingleApplication(int &argc, char **argv) : QApplication(argc, argv){ + //Initialize a couple convenience internal variables + cfile = QDir::tempPath()+"/.LSingleApp-%1-%2"; + QString username = QString(getlogin()); + QString appname = this->applicationName(); + //Obscure the user/app in the filename (TO DO) + //qDebug() << username << appname; + //bool junk; + //qDebug() << QString::number( username.toInt(&junk,16) ); + cfile = cfile.arg( username, appname ); + lockfile = new QLockFile(cfile+"-lock"); + lockfile->setStaleLockTime(0); //long-lived processes + for(int i=1; iisLocked() ){ + //currently locked instance: remove the lock now + lserver->close(); + QLocalServer::removeServer(cfile); + lockfile->unlock(); + } +} + +bool LSingleApplication::isPrimaryProcess(){ + return isActive; +} + +void LSingleApplication::PerformLockChecks(){ + bool primary = lockfile->tryLock(); + //qDebug() << "Try Lock: " << primary; + if(!primary){ + //Pre-existing lock - check it for validity + QString appname, hostname; + qint64 pid; + lockfile->getLockInfo(&pid, &hostname, &appname); //PID already exists if it gets this far, ignore hostname + //qDebug() << " - Lock Info:" << pid << hostname << appname; + if( appname!=this->applicationName() || !QFile::exists(cfile) ){ + //Some other process has the same PID or the server does not exist - stale lock + //qDebug() << " - Stale Lock"; + lockfile->removeStaleLockFile(); + //Now re-try to create the lock + primary = lockfile->tryLock(); + //qDebug() << " - Try Lock Again:" << primary; + } + } + if(primary){ + //Create the server socket + //qDebug() << "Create Local Server"; + if(QFile::exists(cfile)){ QLocalServer::removeServer(cfile); } //stale socket/server file + lserver = new QLocalServer(this); + connect(lserver, SIGNAL(newConnection()), this, SLOT(newInputsAvailable()) ); + if( lserver->listen(cfile) ){ + lserver->setSocketOptions(QLocalServer::UserAccessOption); + //qDebug() << " - Success"; + isActive = true; + }else{ + //qDebug() << " - Failure:" << lserver->errorString(); + lockfile->unlock(); + } + + }else{ + //forward the current inputs to the locked process for processing and exit + //qDebug() << "Forward inputs to locking process:" << inputlist; + QLocalSocket socket(this); + socket.connectToServer(cfile); + socket.waitForConnected(); + if(!socket.isValid()){ exit(1); } //error - could not forward info + socket.write( inputlist.join("::::").toLocal8Bit() ); + socket.waitForDisconnected(500); //max out at 1/2 second (only hits this if no inputs) + } + +} + +//New messages detected +void LSingleApplication::newInputsAvailable(){ + while(lserver->hasPendingConnections()){ + QLocalSocket *sock = lserver->nextPendingConnection(); + QByteArray bytes; + sock->waitForReadyRead(); + while(sock->bytesAvailable() > 0){ //if(sock->waitForReadyRead()){ + //qDebug() << "Info Available"; + bytes.append( sock->readAll() ); + } + sock->disconnectFromServer(); + QStringList inputs = QString::fromLocal8Bit(bytes).split("::::"); + //qDebug() << " - New Inputs Detected:" << inputs; + emit InputsAvailable(inputs); + } +} \ No newline at end of file diff --git a/libLumina/LuminaSingleApplication.h b/libLumina/LuminaSingleApplication.h new file mode 100644 index 000000000..f61a90c02 --- /dev/null +++ b/libLumina/LuminaSingleApplication.h @@ -0,0 +1,54 @@ +//=========================================== +// Lumina-DE source code +// Copyright (c) 2014, Ken Moore +// Available under the 3-clause BSD license +// See the LICENSE file for full details +//=========================================== +// This is the general class for a single-instance application +//=========================================== +//EXAMPLE USAGE in main.cpp: +// +// LSingleApplication app(argc, argv); +// if( !app.isPrimaryProcess() ){ +// return 0; +// } +// QMainWindow w; //or whatever the main window class is +// connect(app, SIGNAL(InputsAvailable(QStringList)), w, SLOT()); //for interactive apps - optional +// app.exec(); +//=========================================== +#ifndef _LUMINA_LIBRARY_SINGLE_APPLICATION_H +#define _LUMINA_LIBRARY_SINGLE_APPLICATION_H + +#include +#include +#include +#include +#include + + +class LSingleApplication : public QApplication{ + Q_OBJECT +public: + LSingleApplication(int &argc, char **argv); + ~LSingleApplication(); + + bool isPrimaryProcess(); + +private: + bool isActive; + QLockFile *lockfile; + QLocalServer *lserver; + QString cfile; + QStringList inputlist; + + void PerformLockChecks(); + +private slots: + void newInputsAvailable(); //internally used to detect a message from an alternate instance + +signals: + void InputsAvailable(QStringList); + +}; + +#endif diff --git a/libLumina/LuminaThemes.cpp b/libLumina/LuminaThemes.cpp index feacc81d2..fd740e20e 100644 --- a/libLumina/LuminaThemes.cpp +++ b/libLumina/LuminaThemes.cpp @@ -11,7 +11,7 @@ #include #include #include - +#include QStringList LTHEME::availableSystemThemes(){ //returns: [name::::path] for each item diff --git a/libLumina/LuminaUtils.cpp b/libLumina/LuminaUtils.cpp index 830cfc976..ed08857fc 100644 --- a/libLumina/LuminaUtils.cpp +++ b/libLumina/LuminaUtils.cpp @@ -5,6 +5,10 @@ // See the LICENSE file for full details //=========================================== #include "LuminaUtils.h" +#include +#include +#include +#include int LUtils::runCmd(QString cmd, QStringList args){ QProcess *proc = new QProcess; diff --git a/libLumina/LuminaUtils.h b/libLumina/LuminaUtils.h index 44bec991f..3a75fc3bf 100644 --- a/libLumina/LuminaUtils.h +++ b/libLumina/LuminaUtils.h @@ -16,6 +16,7 @@ #include #include #include +#include class LUtils{ public: diff --git a/libLumina/LuminaX11.cpp b/libLumina/LuminaX11.cpp index 68d54c6df..699d7b997 100644 --- a/libLumina/LuminaX11.cpp +++ b/libLumina/LuminaX11.cpp @@ -6,6 +6,12 @@ //=========================================== #include "LuminaX11.h" +#include +#include +#include +#include +#include + //X includes (these need to be last due to Qt compile issues) #include #include @@ -13,6 +19,27 @@ #include #include +//XCB Library includes +#include +#include +#include +#include +#include + +//xcb_ewmh_connection_t ewmh_handle; + +//===== Get EWMH connection handle ===== +/*xcb_ewmh_connection_t* LX11::EWMH_C(){ + static bool firstrun = true; + if(firstrun){ + qDebug() << "Init EWMH structure"; + xcb_ewmh_init_atoms(QX11Info::connection(), &ewmh_handle); + firstrun = false; + } + qDebug() << "Return EWMH structure pointer:" << &ewmh_handle; + return &ewmh_handle; +}*/ + //===== WindowList() ======== QList LX11::WindowList(){ QList output; @@ -26,7 +53,7 @@ QList LX11::WindowList(){ QString name = LX11::WindowClass(output[i]); if(output[i] == 0){ remove=true; } else if( desk >= 0 && LX11::WindowDesktop(output[i]) != desk){ remove = true; } - else if( name=="Lumina-DE" ){ remove = true; } + else if( name=="Lumina Desktop Environment" ){ remove = true; } else if(name.startsWith("Lumina-")){ //qDebug() << "Lumina Window:" << name << LX11::WindowName(output[i]); if(LX11::WindowName(output[i]).toLower()==name.toLower() ){ remove=true; } @@ -52,6 +79,17 @@ QList LX11::WindowList(){ // ===== GetClientList() ===== QList LX11::GetClientList(){ QList output; + //XCB Library + /*qDebug() << "Get Client list cookie"; + xcb_get_property_cookie_t cookie = xcb_ewmh_get_client_list_unchecked( LX11::EWMH_C(), 0); + xcb_ewmh_get_windows_reply_t winlist; + qDebug() << "Get client list"; + if( xcb_ewmh_get_client_list_reply( LX11::EWMH_C(), cookie, &winlist, NULL) ){ + qDebug() << " - Loop over items"; + for(unsigned int i=0; i LX11::GetClientStackingList(){ } // ===== findChildren() ===== -QList LX11::findChildren(Window parent, int levels){ +QList LX11::findChildren(WId parent, int levels){ Window rootR, parentR; Window *childrenR; unsigned int num; @@ -129,6 +167,9 @@ WId LX11::ActiveWindow(){ // ===== SetNumberOfDesktops() ===== void LX11::SetNumberOfDesktops(int number){ + //XCB Library + + //XLib Display *display = QX11Info::display(); Window rootWindow = QX11Info::appRootWindow(); @@ -253,8 +294,13 @@ void LX11::IconifyWindow(WId win){ // ===== RestoreWindow() ===== void LX11::RestoreWindow(WId win){ - Display *disp = QX11Info::display(); - XMapRaised(disp, win); //make it visible again and raise it to the top + //XCB Library + uint32_t val = XCB_STACK_MODE_ABOVE; + xcb_configure_window(QX11Info::connection(), win, XCB_CONFIG_WINDOW_STACK_MODE, &val); //raise it + xcb_map_window(QX11Info::connection(), win); //map it + //XLib + //Display *disp = QX11Info::display(); + //XMapRaised(disp, win); //make it visible again and raise it to the top } // ===== ActivateWindow() ===== @@ -315,12 +361,16 @@ void LX11::ReservePanelLocation(WId win, int xstart, int ystart, int width, int // ===== SetAsSticky() ===== void LX11::SetAsSticky(WId win){ //make this window "stick" to all virtual desktops + + //XCB Library + // xcb_change_property(QX11Info::connection(), XCB_PROP_MODE_APPEND, win, _NET_WM_STATE, XCB_ATOM, 32, 1, _NET_WM_STATE_STICKY); + + //XLib Display *disp = QX11Info::display(); Atom stick = XInternAtom(disp, "_NET_WM_STATE_STICKY",false); Atom state = XInternAtom(disp, "_NET_WM_STATE", false); - XChangeProperty(disp, win, state, XA_ATOM, 32, PropModeAppend, (unsigned char*) &stick, 1); - + XChangeProperty(disp, win, state, XA_ATOM, 32, PropModeAppend, (unsigned char*) &stick, 1L); } // ===== SetAsPanel() ===== @@ -549,7 +599,12 @@ int LX11::WindowDesktop(WId win){ // ===== GetWindowState() ===== LX11::WINDOWSTATE LX11::GetWindowState(WId win){ + LX11::WINDOWSTATE state = LX11::VISIBLE; + + //XCB Library (TO DO) + + //XLib Display *disp = QX11Info::display(); Atom SA = XInternAtom(disp, "_NET_WM_STATE", true); Atom ATTENTION = XInternAtom(disp, "_NET_WM_STATE_DEMANDS_ATTENTION", false); @@ -564,8 +619,7 @@ LX11::WINDOWSTATE LX11::GetWindowState(WId win){ int status = XGetWindowProperty( disp, win, SA, 0, ~(0L), false, AnyPropertyType, &type, &format, &num, &bytes, (unsigned char**) &data); - - LX11::WINDOWSTATE state = LX11::VISIBLE; + if(status >= Success && data){ for(unsigned int i=0; i LXCB::WindowList(bool rawlist){ + QList output; + qDebug() << "Get Client list cookie"; + xcb_get_property_cookie_t cookie = xcb_ewmh_get_client_list_unchecked( &EWMH, 0); + xcb_ewmh_get_windows_reply_t winlist; + qDebug() << "Get client list"; + if( 1 == xcb_ewmh_get_client_list_reply( &EWMH, cookie, &winlist, NULL) ){ + qDebug() << " - Loop over items"; + unsigned int wkspace = CurrentWorkspace(); + for(unsigned int i=0; imap_state==XCB_MAP_STATE_VIEWABLE){ cstate = VISIBLE; } + else{ cstate = INVISIBLE; } + free(attr); + } + } + return cstate; +} + +// === SetAsSticky() === +void LXCB::SetAsSticky(WId win){ + xcb_change_property( QX11Info::connection(), XCB_PROP_MODE_APPEND, win, EWMH._NET_WM_STATE, XCB_ATOM_ATOM, 32, 1, &(EWMH._NET_WM_STATE_STICKY) ); + xcb_flush(QX11Info::connection()); //apply it right away +} + +// === SetScreenWorkArea() === +/*void LXCB::SetScreenWorkArea(unsigned int screen, QRect rect){ + //This is only useful because Fluxbox does not set the _NET_WORKAREA root atom + // This needs to be better incorporated into the new window manager later + + //First get the current workarea array (for all monitors/screens) + xcb_get_property_cookie_t cookie = xcb_ewmh_get_workarea_unchecked(&EWMH, 0); + xcb_ewmh_get_workarea_reply_t work; + if(0==xcb_ewmh_get_workarea_reply(&EWMH, cookie, &work, NULL)){ return; } //Error: Could not retrieve current work areas + //Save what we need only from the reply + unsigned int desks = work.workarea_len; + if(desks <= screen){ return; } //invalid screen to modify + qDebug() << "Number of desktops/screens:" << desks; + xcb_ewmh_geometry_t *dareas = work.workarea; + //Adjust the work area for the input monitor/screen + dareas[screen].x = rect.x(); + dareas[screen].y = rect.y(); + dareas[screen].width = rect.width(); + dareas[screen].height = rect.height(); + //Now save the array again + xcb_ewmh_set_workarea(&EWMH, 0, desks, dareas); //_NET_WORKAREA + //Make sure to clear that reply + xcb_ewmh_get_workarea_reply_wipe(&work); +}*/ \ No newline at end of file diff --git a/libLumina/LuminaX11.h b/libLumina/LuminaX11.h index e7cded496..ac232de16 100644 --- a/libLumina/LuminaX11.h +++ b/libLumina/LuminaX11.h @@ -20,6 +20,7 @@ #include #include #include +#include // Addition includes for compilations (cause issues with X11 libs later) #include #include @@ -33,6 +34,8 @@ //#include //#include +#include + //SYSTEM TRAY STANDARD DEFINITIONS #define _NET_SYSTEM_TRAY_ORIENTATION_HORZ 0 #define _NET_SYSTEM_TRAY_ORIENTATION_VERT 1 @@ -46,6 +49,9 @@ class LX11{ public: enum WINDOWSTATE {VISIBLE, INVISIBLE, ACTIVE, ATTENTION, IGNORE}; + //Internal Use Functions + //static xcb_ewmh_connection_t* EWMH_C(); //Get the XCB_ewmh handle; + //General Info Functions static QList WindowList(); //List all current windows static QList GetClientList(); // _NET_WM_CLIENT list @@ -102,4 +108,33 @@ class LX11{ static QString getNetWMProp(WId win, QString prop); //Returns a _NET_WM_* string value }; +//XCB Library replacement for LX11 (Qt5 uses XCB instead of XLib) +class LXCB{ + +private: + xcb_ewmh_connection_t EWMH; + +public: + enum WINDOWSTATE {VISIBLE, INVISIBLE, ACTIVE, ATTENTION, IGNORE}; + + LXCB(); + ~LXCB(); + + //== Main Interface functions == + // General Information + QList WindowList(bool rawlist = false); //list all non-Lumina windows (rawlist -> all workspaces) + unsigned int CurrentWorkspace(); + + //Session Modification + + + //Window Information + QString WindowClass(WId); + unsigned int WindowWorkspace(WId); + WINDOWSTATE WindowState(WId win); //Visible state of window + + //Window Modification + void SetAsSticky(WId); +}; + #endif \ No newline at end of file diff --git a/libLumina/LuminaXDG.cpp b/libLumina/LuminaXDG.cpp index 057954dd7..84a6f6653 100644 --- a/libLumina/LuminaXDG.cpp +++ b/libLumina/LuminaXDG.cpp @@ -6,6 +6,8 @@ //=========================================== #include "LuminaXDG.h" #include "LuminaOS.h" +#include +#include static QStringList mimeglobs; static qint64 mimechecktime; @@ -44,7 +46,7 @@ XDGDesktop LXDG::loadDesktopFile(QString filePath, bool& ok){ QString var = line.section("=",0,0).simplified(); QString loc = var.section("[",1,1).section("]",0,0).simplified(); // localization var = var.section("[",0,0).simplified(); //remove the localization - QString val = line.section("=",1,1).simplified(); + QString val = line.section("=",1,50).simplified(); //------------------- if(var=="Name"){ if(DF.name.isEmpty() && loc.isEmpty()){ DF.name = val; } @@ -558,6 +560,21 @@ void LXDG::setDefaultAppForMime(QString mime, QString app){ return; } +QStringList LXDG::findAVFileExtensions(){ + //output format: QDir name filter for valid A/V file extensions + QStringList globs = LXDG::loadMimeFileGlobs2(); + QStringList av = globs.filter(":audio/"); + av << globs.filter(":video/"); + for(int i=0; i:: if(mimeglobs.isEmpty() || (mimechecktime < (QDateTime::currentMSecsSinceEpoch()-30000)) ){ diff --git a/libLumina/LuminaXDG.h b/libLumina/LuminaXDG.h index ec9948207..ad09d490d 100644 --- a/libLumina/LuminaXDG.h +++ b/libLumina/LuminaXDG.h @@ -93,6 +93,8 @@ class LXDG{ static QString findDefaultAppForMime(QString mime); //Set the default application for a mime-type static void setDefaultAppForMime(QString mime, QString app); + //List all the registered audio/video file extensions + static QStringList findAVFileExtensions(); //Load all the "globs2" mime database files static QStringList loadMimeFileGlobs2(); }; diff --git a/libLumina/libLumina.pro b/libLumina/libLumina.pro index d37c2c0d3..5b9cfe6c5 100644 --- a/libLumina/libLumina.pro +++ b/libLumina/libLumina.pro @@ -1,5 +1,6 @@ -QT += core +QT += core network +greaterThan(QT_MAJOR_VERSION, 4): QT += widgets x11extras multimedia TARGET=LuminaUtils @@ -24,12 +25,14 @@ HEADERS += LuminaXDG.h \ LuminaUtils.h \ LuminaX11.h \ LuminaThemes.h \ - LuminaOS.h + LuminaOS.h \ + LuminaSingleApplication.h SOURCES += LuminaXDG.cpp \ LuminaUtils.cpp \ LuminaX11.cpp \ LuminaThemes.cpp \ + LuminaSingleApplication.cpp \ LuminaOS-FreeBSD.cpp \ LuminaOS-DragonFly.cpp \ LuminaOS-OpenBSD.cpp \ @@ -39,14 +42,15 @@ SOURCES += LuminaXDG.cpp \ INCLUDEPATH += $$PREFIX/include -LIBS += -lX11 -lXrender -lXcomposite +LIBS += -lX11 -lXrender -lXcomposite -lxcb -lxcb-ewmh -lxcb-icccm include.path=$$PREFIX/include/ include.files=LuminaXDG.h \ LuminaUtils.h \ LuminaX11.h \ LuminaThemes.h \ - LuminaOS.h + LuminaOS.h \ + LuminaSingleApplication.h colors.path=$$PREFIX/share/Lumina-DE/colors/ colors.files=colors/Lumina-Red.qss.colors \ diff --git a/libLumina/make-linux-distro.sh b/libLumina/make-linux-distro.sh old mode 100644 new mode 100755 diff --git a/lumina-config/lumina-config.pro b/lumina-config/lumina-config.pro index ff8211b30..ec6d09e3a 100644 --- a/lumina-config/lumina-config.pro +++ b/lumina-config/lumina-config.pro @@ -1,5 +1,6 @@ QT += core gui +greaterThan(QT_MAJOR_VERSION, 4): QT += widgets x11extras network TARGET = lumina-config isEmpty(PREFIX) { @@ -34,17 +35,17 @@ FORMS += mainUI.ui \ INCLUDEPATH += ../libLumina $$PREFIX/include LIBS += -L../libLumina -lLuminaUtils -freebsd-* { - LIBS += -lQtSolutions_SingleApplication-head -} -openbsd-g++4 { - LIBS += -lQtSolutions_SingleApplication-head -} +#freebsd-* { +# LIBS += -lQtSolutions_SingleApplication-head +#} +#openbsd-g++4 { +# LIBS += -lQtSolutions_SingleApplication-head +#} openbsd-g++4 { LRELEASE = lrelease4 } else { - LRELEASE = lrelease-qt4 + LRELEASE = $$PREFIX/lib/qt5/bin/lrelease } QMAKE_LIBDIR = ../libLumina diff --git a/lumina-config/main.cpp b/lumina-config/main.cpp index 27af600dd..af5c0ab95 100644 --- a/lumina-config/main.cpp +++ b/lumina-config/main.cpp @@ -1,25 +1,19 @@ #include -#ifdef __FreeBSD__ - #include -#endif -#include +#include #include #include #include "mainUI.h" #include #include +#include int main(int argc, char ** argv) { - #ifndef __FreeBSD__ - QApplication a(argc, argv); - #else - QtSingleApplication a(argc, argv); - if( a.isRunning() ) - return !(a.sendMessage("show")); - #endif + LSingleApplication a(argc, argv); + if(!a.isPrimaryProcess()){ return 0; } + LuminaThemeEngine theme(&a); QTranslator translator; QLocale mylocale; @@ -32,7 +26,7 @@ int main(int argc, char ** argv) MainUI w; - QObject::connect(&a, SIGNAL(messageReceived(const QString&)), &w, SLOT(slotSingleInstance()) ); + QObject::connect(&a, SIGNAL(InputsAvailable(QStringList)), &w, SLOT(slotSingleInstance()) ); QObject::connect(&theme, SIGNAL(updateIcons()), &w, SLOT(setupIcons()) ); w.show(); diff --git a/lumina-desktop/LDesktop.cpp b/lumina-desktop/LDesktop.cpp index 9db4eac73..07225fad7 100644 --- a/lumina-desktop/LDesktop.cpp +++ b/lumina-desktop/LDesktop.cpp @@ -11,6 +11,8 @@ #include #include "LWinInfo.h" +#define DEBUG 1 + LDesktop::LDesktop(int deskNum) : QObject(){ DPREFIX = "desktop-"+QString::number(deskNum)+"/"; @@ -103,9 +105,9 @@ void LDesktop::CreateDesktopPluginContainer(LDPlugin *plug){ // ===================== void LDesktop::InitDesktop(){ //This is called *once* during the main initialization routines - qDebug() << "Init Desktop:" << desktopnumber; + if(DEBUG){ qDebug() << "Init Desktop:" << desktopnumber; } connect(desktop, SIGNAL(resized(int)), this, SLOT(UpdateGeometry(int))); - qDebug() << "Desktop #"< "<< desktop->screenGeometry(desktopnumber).x() << desktop->screenGeometry(desktopnumber).y() << desktop->screenGeometry(desktopnumber).width() << desktop->screenGeometry(desktopnumber).height(); + if(DEBUG){ qDebug() << "Desktop #"< "<< desktop->screenGeometry(desktopnumber).x() << desktop->screenGeometry(desktopnumber).y() << desktop->screenGeometry(desktopnumber).width() << desktop->screenGeometry(desktopnumber).height(); } deskMenu = new QMenu(0); connect(deskMenu, SIGNAL(triggered(QAction*)), this, SLOT(SystemApplication(QAction*)) ); winMenu = new QMenu(0); @@ -124,17 +126,20 @@ void LDesktop::InitDesktop(){ watcher->addPath(settings->fileName()); connect(watcher, SIGNAL(fileChanged(QString)), this, SLOT(SettingsChanged()) ); + if(DEBUG){ qDebug() << "Create bgWindow"; } bgWindow = new QWidget(); bgWindow->setObjectName("bgWindow"); bgWindow->setContextMenuPolicy(Qt::CustomContextMenu); + bgWindow->setWindowFlags(Qt::FramelessWindowHint); LX11::SetAsDesktop(bgWindow->winId()); bgWindow->setGeometry(desktop->screenGeometry(desktopnumber)); connect(bgWindow, SIGNAL(customContextMenuRequested(const QPoint&)), this, SLOT(ShowMenu()) ); + if(DEBUG){ qDebug() << "Create bgDesktop"; } bgDesktop = new QMdiArea(bgWindow); //Make sure the desktop area is transparent to show the background bgDesktop->setBackground( QBrush(Qt::NoBrush) ); bgDesktop->setStyleSheet( "QMdiArea{ border: none; background: transparent;}" ); - qDebug() << " - Desktop Init Done:" << desktopnumber; + if(DEBUG){ qDebug() << " - Desktop Init Done:" << desktopnumber; } //Start the update processes QTimer::singleShot(10,this, SLOT(UpdateMenu()) ); QTimer::singleShot(0,this, SLOT(UpdateBackground()) ); @@ -155,10 +160,10 @@ void LDesktop::SettingsChanged(){ } void LDesktop::UpdateMenu(bool fast){ - //qDebug() << " - Update Menu:" << desktopnumber; + if(DEBUG){ qDebug() << " - Update Menu:" << desktopnumber; } //Put a label at the top int num = LX11::GetCurrentDesktop(); - //qDebug() << "Found desktop number:" << num; + if(DEBUG){ qDebug() << "Found workspace number:" << num; } if(num < 0){ workspacelabel->setText( ""+tr("Lumina Desktop")+""); } else{ workspacelabel->setText( ""+QString(tr("Workspace %1")).arg(QString::number(num+1))+""); } if(fast && usewinmenu){ UpdateWinMenu(); } @@ -216,7 +221,7 @@ void LDesktop::winClicked(QAction* act){ } void LDesktop::UpdateDesktop(){ - qDebug() << " - Update Desktop Plugins for screen:" << desktopnumber; + if(DEBUG){ qDebug() << " - Update Desktop Plugins for screen:" << desktopnumber; } if(deskupdating){ return; } //make sure to only run this once deskupdating = true; QStringList plugins = settings->value(DPREFIX+"pluginlist", QStringList()).toStringList(); @@ -372,7 +377,7 @@ void LDesktop::DesktopPluginRemoved(QString ID){ } void LDesktop::UpdatePanels(){ - qDebug() << " - Update Panels For Screen:" << desktopnumber; + if(DEBUG){ qDebug() << " - Update Panels For Screen:" << desktopnumber; } int panels = settings->value(DPREFIX+"panels", -1).toInt(); if(panels==-1 && defaultdesktop){ panels=1; } //need at least 1 panel on the primary desktop //Remove all extra panels @@ -394,7 +399,7 @@ void LDesktop::UpdatePanels(){ } } if(!found){ - qDebug() << " -- Create panel "<< i; + if(DEBUG){ qDebug() << " -- Create panel "<< i; } //New panel LPanel *pan = new LPanel(settings, desktopnumber, i, bgWindow); PANELS << pan; @@ -412,6 +417,7 @@ void LDesktop::UpdateDesktopPluginArea(){ } //Now make sure the desktop plugin area is only the visible area QRect rec = visReg.boundingRect(); + //LSession::handle()->XCB->SetScreenWorkArea((unsigned int) desktopnumber, rec); //Now remove the X offset to place it on the current screen (needs widget-coords, not global) rec.moveTopLeft( QPoint( rec.x()-desktop->screenGeometry(desktopnumber).x() , rec.y() ) ); //qDebug() << "DPlug Area:" << rec.x() << rec.y() << rec.width() << rec.height(); @@ -426,7 +432,7 @@ void LDesktop::UpdateBackground(){ //Get the current Background if(bgupdating || bgWindow==0){ return; } //prevent multiple calls to this at the same time bgupdating = true; - qDebug() << " - Update Desktop Background for screen:" << desktopnumber; + if(DEBUG){ qDebug() << " - Update Desktop Background for screen:" << desktopnumber; } //Get the list of background(s) to show QStringList bgL = settings->value(DPREFIX+"background/filelist", QStringList()).toStringList(); //qDebug() << " - List:" << bgL << CBG; diff --git a/lumina-desktop/LPanel.cpp b/lumina-desktop/LPanel.cpp index 138a8d77d..afef1e131 100644 --- a/lumina-desktop/LPanel.cpp +++ b/lumina-desktop/LPanel.cpp @@ -34,12 +34,13 @@ LPanel::LPanel(QSettings *file, int scr, int num, QWidget *parent) : QWidget(){ this->setWindowFlags(Qt::Tool | Qt::WindowStaysOnTopHint | Qt::FramelessWindowHint ); this->setFocusPolicy(Qt::NoFocus); this->setWindowTitle(""); - this->setAttribute(Qt::WA_X11NetWmWindowTypeDock); //Reserve as panel/dock + //this->setAttribute(Qt::WA_X11NetWmWindowTypeDock); //Reserve as panel/dock this->setAttribute(Qt::WA_AlwaysShowToolTips); this->setObjectName("LuminaPanelWidget"); panelArea->setObjectName("LuminaPanelPluginWidget"); - //LX11::SetAsPanel(this->winId()); //set proper type of window for a panel since Qt can't do it - LX11::SetAsSticky(this->winId()); + LX11::SetAsPanel(this->winId()); //set proper type of window for a panel since Qt can't do it + LSession::handle()->XCB->SetAsSticky(this->winId()); + //LX11::SetAsSticky(this->winId()); layout = new QBoxLayout(QBoxLayout::LeftToRight); layout->setContentsMargins(0,0,0,0); layout->setSpacing(1); @@ -86,7 +87,7 @@ void LPanel::UpdatePanel(){ this->setGeometry(xloc,0,xwid, ht ); if(!hidden){ LX11::ReservePanelLocation(this->winId(), xloc, 0, this->width(), ht, "top"); } else{ - LX11::ReservePanelLocation(this->winId(), xloc, 0, this->width(), 2, "top"); + LX11::ReservePanelLocation(this->winId(), xloc, 0, this->width(), 2, "top"); hidepoint = QPoint(xloc, 2-ht); showpoint = QPoint(xloc, 0); this->move(hidepoint); //Could bleed over onto the screen above @@ -128,6 +129,9 @@ void LPanel::UpdatePanel(){ this->move(hidepoint); //Could bleed over onto the screen right } } + //With QT5, we need to make sure to reset window properties on occasion + LSession::handle()->XCB->SetAsSticky(this->winId()); + LX11::SetAsPanel(this->winId()); //Now update the appearance of the toolbar QString color = settings->value(PPREFIX+"color", "rgba(255,255,255,160)").toString(); QString style = "QWidget#LuminaPanelPluginWidget{ background: %1; border-radius: 3px; border: 1px solid %1; }"; @@ -233,7 +237,7 @@ void LPanel::paintEvent(QPaintEvent *event){ //qDebug() << "Global Rec:" << rec.x() << rec.y() << screennum; rec.moveTo( rec.x()-screen->screenGeometry(screennum).x(), rec.y() ); //qDebug() << "Adjusted Global Rec:" << rec.x() << rec.y(); - painter->drawPixmap(event->rect(), QPixmap::grabWidget(bgWindow, rec) ); + painter->drawPixmap(event->rect(), bgWindow->grab(rec) ); QWidget::paintEvent(event); //now pass the event along to the normal painting event } diff --git a/lumina-desktop/LSession.cpp b/lumina-desktop/LSession.cpp index de3d93079..c8b98b22c 100644 --- a/lumina-desktop/LSession.cpp +++ b/lumina-desktop/LSession.cpp @@ -8,6 +8,10 @@ #include #include +#include "LXcbEventFilter.h" + +//LibLumina X11 class +#include //X includes (these need to be last due to Qt compile issues) #include @@ -17,9 +21,11 @@ #include #ifndef DEBUG -#define DEBUG 0 +#define DEBUG 1 #endif +XCBEventFilter *evFilter = 0; + LSession::LSession(int &argc, char ** argv) : QApplication(argc, argv){ this->setApplicationName("Lumina Desktop Environment"); this->setApplicationVersion("0.7.2"); @@ -33,14 +39,18 @@ LSession::LSession(int &argc, char ** argv) : QApplication(argc, argv){ SystemTrayID = 0; VisualTrayID = 0; TrayDmgEvent = 0; TrayDmgError = 0; + XCB = 0; //initialize the empty internal pointers to 0 appmenu = 0; settingsmenu = 0; currTranslator=0; mediaObj=0; - audioOut=0; + //audioOut=0; audioThread=0; sessionsettings=0; + //Setup the event filter for Qt5 + evFilter = new XCBEventFilter(this); + this->installNativeEventFilter( evFilter ); } LSession::~LSession(){ @@ -53,13 +63,15 @@ LSession::~LSession(){ delete appmenu; delete currTranslator; if(mediaObj!=0){delete mediaObj;} - if(audioOut!=0){delete audioOut; } + //if(audioOut!=0){delete audioOut; } } void LSession::setupSession(){ qDebug() << "Initializing Session"; QTime* timer = 0; if(DEBUG){ timer = new QTime(); timer->start(); qDebug() << " - Init srand:" << timer->elapsed();} + //Initialize the XCB interface backend + XCB = new LXCB(); //Seed random number generator (if needed) qsrand( QTime::currentTime().msec() ); //Setup the QSettings default paths @@ -260,7 +272,7 @@ void LSession::SessionEnding(){ stopSystemTray(); } -bool LSession::x11EventFilter(XEvent *event){ +/*bool LSession::x11EventFilter(XEvent *event){ //Detect X Event types and send the appropriate signal(s) switch(event->type){ // ------------------------- @@ -335,7 +347,7 @@ bool LSession::x11EventFilter(XEvent *event){ // ----------------------- //Now continue on with the event handling (don't change it) return false; -} +}*/ //=============== // SYSTEM ACCESS @@ -368,23 +380,73 @@ void LSession::playAudioFile(QString filepath){ //Setup the audio output systems for the desktop //return; //Disable this for now: too many issues with Phonon at the moment (hangs the session) bool init = false; + if(DEBUG){ qDebug() << "Play Audio File"; } if(audioThread==0){ qDebug() << " - Initialize audio systems"; audioThread = new QThread(); init = true; } - if(mediaObj==0){ qDebug() << " - Initialize Phonon media Object"; mediaObj = new Phonon::MediaObject(); init = true;} - if(audioOut==0){ qDebug() << " - Initialize Phonon audio output"; audioOut = new Phonon::AudioOutput(); init=true;} - if(mediaObj && audioOut && init){ //in case Phonon errors for some reason - qDebug() << " -- Create path between audio objects"; - Phonon::createPath(mediaObj, audioOut); + //if(mediaObj==0){ qDebug() << " - Initialize Phonon media Object"; mediaObj = new Phonon::MediaObject(); init = true;} + if(mediaObj==0){ qDebug() << " - Initialize media player"; mediaObj = new QMediaPlayer(); init = true;} + //if(audioOut==0){ qDebug() << " - Initialize Phonon audio output"; audioOut = new Phonon::AudioOutput(); init=true;} + if(mediaObj && init){ //in case it errors for some reason + //qDebug() << " -- Create path between audio objects"; + //Phonon::createPath(mediaObj, audioOut); qDebug() << " -- Move audio objects to separate thread"; mediaObj->moveToThread(audioThread); - audioOut->moveToThread(audioThread); + //audioOut->moveToThread(audioThread); + audioThread->start(); } - if(mediaObj !=0 && audioOut!=0){ - mediaObj->setCurrentSource(QUrl(filepath)); + if(mediaObj !=0 ){//&& audioOut!=0){ + //mediaObj->setCurrentSource(QUrl(filepath)); + mediaObj->setMedia(QUrl::fromLocalFile(filepath)); + mediaObj->setVolume(100); mediaObj->play(); - audioThread->start(); + //audioThread->start(); } + if(DEBUG){ qDebug() << " - Done with Audio File"; } +} +// ======================= +// XCB EVENT FILTER FUNCTIONS +// ======================= +void LSession::WindowPropertyEvent(){ + if(DEBUG){ qDebug() << "Window Property Event"; } + LSession::restoreOverrideCursor(); //restore the mouse cursor back to normal (new window opened?) + emit WindowListEvent(); } +void LSession::SysTrayDockRequest(WId win){ + attachTrayWindow(win); //Check to see if the window is already registered +} + +void LSession::WindowClosedEvent(WId win){ + removeTrayWindow(win); //Check to see if the window is a tray app +} + +void LSession::WindowConfigureEvent(WId win){ + for(int i=0; isetTrayDamageFlag(TrayDmgEvent); qDebug() << "System Tray Started Successfully"; + if(DEBUG){ qDebug() << " - System Tray Flags:" << TrayDmgEvent << TrayDmgError; } } } @@ -445,6 +509,7 @@ void LSession::attachTrayWindow(WId win){ if(TrayStopping){ return; } if(RunningTrayApps.contains(win)){ return; } //already managed RunningTrayApps << win; + if(DEBUG){ qDebug() << "Tray List Changed"; } emit TrayListChanged(); /*//Now try to embed the window into the tray //(NOT USED - Breaks visuals due to X11 graphics constraints - need to do embed in a single visual tray instead) @@ -476,4 +541,4 @@ void LSession::removeTrayWindow(WId win){ break; } } -} \ No newline at end of file +} diff --git a/lumina-desktop/LSession.h b/lumina-desktop/LSession.h index 1e773f748..68916a77d 100644 --- a/lumina-desktop/LSession.h +++ b/lumina-desktop/LSession.h @@ -18,8 +18,7 @@ #include #include #include -#include -#include +#include #include #include @@ -29,8 +28,8 @@ #include "SystemWindow.h" #include "LDesktop.h" #include "WMProcess.h" +//#include "LXcbEventFilter.h" -//LibLumina X11 class #include //SYSTEM TRAY STANDARD DEFINITIONS @@ -54,7 +53,7 @@ class LSession : public QApplication{ //Functions to be called during startup void setupSession(); - virtual bool x11EventFilter(XEvent *event); + //virtual bool x11EventFilter(XEvent *event); bool LoadLocale(QString); @@ -63,6 +62,15 @@ class LSession : public QApplication{ bool registerVisualTray(WId); void unregisterVisualTray(WId); + //Special functions for XCB event filter parsing only + // (DO NOT USE MANUALLY) + void WindowPropertyEvent(); + void SysTrayDockRequest(WId); + void WindowClosedEvent(WId); + void WindowConfigureEvent(WId); + void WindowDamageEvent(WId); + void WindowSelectionClearEvent(WId); + //System Access //Return a pointer to the current session static LSession* handle(){ @@ -74,7 +82,8 @@ class LSession : public QApplication{ AppMenu* applicationMenu(); void systemWindow(); SettingsMenu* settingsMenu(); - + LXCB *XCB; //class for XCB usage + QSettings* sessionSettings(); //Play System Audio @@ -84,13 +93,12 @@ class LSession : public QApplication{ WMProcess *WM; QList DESKTOPS; QFileSystemWatcher *watcher; - + //XCBEventFilter *evFilter; //Internal variable for global usage AppMenu *appmenu; SettingsMenu *settingsmenu; QTranslator *currTranslator; - Phonon::MediaObject *mediaObj; - Phonon::AudioOutput *audioOut; + QMediaPlayer *mediaObj; QThread *audioThread; QSettings *sessionsettings; diff --git a/lumina-desktop/LWinInfo.h b/lumina-desktop/LWinInfo.h index 750ab508d..ae67499b2 100644 --- a/lumina-desktop/LWinInfo.h +++ b/lumina-desktop/LWinInfo.h @@ -19,6 +19,7 @@ // Local includes #include "Globals.h" //For the STATES enumeration definition +//#include "LSession.h" class LWinInfo{ diff --git a/lumina-desktop/desktop-plugins/notepad/NotepadPlugin.cpp b/lumina-desktop/desktop-plugins/notepad/NotepadPlugin.cpp index ae52378fc..d3e1e10d7 100644 --- a/lumina-desktop/desktop-plugins/notepad/NotepadPlugin.cpp +++ b/lumina-desktop/desktop-plugins/notepad/NotepadPlugin.cpp @@ -11,7 +11,7 @@ NotePadPlugin::NotePadPlugin(QWidget* parent, QString ID) : LDPlugin(parent, ID) vlay->setContentsMargins(3,3,3,3); frame = new QFrame(this); frame->setObjectName("notepadbase"); - frame->setStyleSheet("QFrame#notepadbase{border-size: 1px; background: rgba(255,255,255,50); color: black;} QFrame{ border: none; border-radius: 3px; background: rgba(255,255,255,100); color: black;}"); + frame->setStyleSheet("QFrame#notepadbase{border-width: 1px; background: rgba(255,255,255,50); color: black;} QFrame{ border: none; border-radius: 3px; background: rgba(255,255,255,100); color: black;}"); this->layout()->addWidget(frame); frame->setLayout(vlay); diff --git a/lumina-desktop/lumina-desktop.pro b/lumina-desktop/lumina-desktop.pro index 8772b6619..02581bdc1 100644 --- a/lumina-desktop/lumina-desktop.pro +++ b/lumina-desktop/lumina-desktop.pro @@ -1,5 +1,6 @@ -QT += core gui network phonon +QT += core gui network +greaterThan(QT_MAJOR_VERSION, 4): QT += widgets x11extras multimedia TARGET = Lumina-DE isEmpty(PREFIX) { @@ -7,7 +8,7 @@ isEmpty(PREFIX) { } target.path = $$PREFIX/bin -LIBS += -L../libLumina -lLuminaUtils -lXdamage -lX11 +LIBS += -L../libLumina -lLuminaUtils -lXdamage -lX11 -lxcb -lxcb-damage QMAKE_LIBDIR = ../libLumina DEPENDPATH += ../libLumina @@ -16,7 +17,7 @@ TEMPLATE = app openbsd-g++4 { LRELEASE = lrelease4 } else { - LRELEASE = lrelease-qt4 + LRELEASE = /usr/local/lib/qt5/bin/lrelease } SOURCES += main.cpp \ @@ -47,6 +48,7 @@ SOURCES += main.cpp \ HEADERS += Globals.h \ WMProcess.h \ + LXcbEventFilter.h \ LSession.h \ LDesktop.h \ LPanel.h \ diff --git a/lumina-desktop/main.cpp b/lumina-desktop/main.cpp index 884e94412..8305be603 100644 --- a/lumina-desktop/main.cpp +++ b/lumina-desktop/main.cpp @@ -23,10 +23,10 @@ #include #include -#define DEBUG 0 +#define DEBUG 1 QFile logfile(QDir::homePath()+"/.lumina/logs/runtime.log"); -void MessageOutput(QtMsgType type, const char *msg){ +void MessageOutput(QtMsgType type, const QMessageLogContext &context, const QString &msg){ QString txt; switch(type){ case QtDebugMsg: @@ -76,7 +76,7 @@ int main(int argc, char ** argv) if(DEBUG){ qDebug() << "Theme Init:" << timer->elapsed(); } LuminaThemeEngine theme(&a); //Setup Log File - qInstallMsgHandler(MessageOutput); + qInstallMessageHandler(MessageOutput); if(DEBUG){ qDebug() << "Session Setup:" << timer->elapsed(); } a.setupSession(); if(DEBUG){ qDebug() << "Load Locale:" << timer->elapsed(); } diff --git a/lumina-desktop/panel-plugins/LPPlugin.h b/lumina-desktop/panel-plugins/LPPlugin.h index ae4e7fbc7..c8347a8e1 100644 --- a/lumina-desktop/panel-plugins/LPPlugin.h +++ b/lumina-desktop/panel-plugins/LPPlugin.h @@ -28,6 +28,7 @@ class LPPlugin : public QWidget{ plugintype=ptype; this->setContentsMargins(0,0,0,0); this->setSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred); + this->setFocusPolicy(Qt::NoFocus); //no keyboard focus on the panel/plugins if(horizontal){LY = new QBoxLayout(QBoxLayout::LeftToRight, this); } else{ LY = new QBoxLayout(QBoxLayout::TopToBottom, this); } LY->setContentsMargins(0,0,0,0); diff --git a/lumina-desktop/panel-plugins/LTBWidget.h b/lumina-desktop/panel-plugins/LTBWidget.h index 5252c619e..7ca46d0dc 100644 --- a/lumina-desktop/panel-plugins/LTBWidget.h +++ b/lumina-desktop/panel-plugins/LTBWidget.h @@ -12,20 +12,21 @@ #include #include "Globals.h" +#include class LTBWidget : public QToolButton{ Q_OBJECT private: - Lumina::STATES cstate; + LXCB::WINDOWSTATE cstate; QString rawstyle; void updateBackground(){ QString background = "background: transparent; "; //default value QString border = "border: 1px solid transparent;"; - if(cstate == Lumina::NONE){ } //just use the defaults - else if(cstate == Lumina::VISIBLE){ background = "background: qlineargradient(spread:pad, x1:0, y1:0, x2:1, y2:1, stop:0 rgba(255, 255, 255, 240), stop:0.505682 rgba(240, 240, 240, 150), stop:1 rgba(210, 210, 210, 55));"; border="border: 1px solid transparent;"; } - else if(cstate == Lumina::INVISIBLE){background = "background: qlineargradient(spread:pad, x1:0, y1:0, x2:1, y2:1, stop:0 rgba(215, 215, 215, 240), stop:0.505682 rgba(184, 185, 186, 150), stop:1 rgba(221, 246, 255, 55));"; border="border: 1px solid transparent;"; } - else if(cstate == Lumina::ACTIVE){ background= "background: qlineargradient(spread:pad, x1:0, y1:0, x2:1, y2:1, stop:0 rgba(241, 233, 156, 240), stop:0.355682 rgba(255, 243, 127, 150), stop:1 rgba(221, 246, 255, 55));"; border ="border: 1px solid transparent;"; } - else if(cstate == Lumina::NOTIFICATION){ background= "background: qlineargradient(spread:pad, x1:0, y1:0, x2:1, y2:1, stop:0 rgba(252, 187, 127, 240), stop:0.505682 rgba(255, 222, 197, 150), stop:1 rgba(221, 246, 255, 55));"; border="border: 1px solid transparent;"; } + if(cstate == LXCB::IGNORE){ } //just use the defaults + else if(cstate == LXCB::VISIBLE){ background = "background: qlineargradient(spread:pad, x1:0, y1:0, x2:1, y2:1, stop:0 rgba(255, 255, 255, 240), stop:0.505682 rgba(240, 240, 240, 150), stop:1 rgba(210, 210, 210, 55));"; border="border: 1px solid transparent;"; } + else if(cstate == LXCB::INVISIBLE){background = "background: qlineargradient(spread:pad, x1:0, y1:0, x2:1, y2:1, stop:0 rgba(215, 215, 215, 240), stop:0.505682 rgba(184, 185, 186, 150), stop:1 rgba(221, 246, 255, 55));"; border="border: 1px solid transparent;"; } + else if(cstate == LXCB::ACTIVE){ background= "background: qlineargradient(spread:pad, x1:0, y1:0, x2:1, y2:1, stop:0 rgba(241, 233, 156, 240), stop:0.355682 rgba(255, 243, 127, 150), stop:1 rgba(221, 246, 255, 55));"; border ="border: 1px solid transparent;"; } + else if(cstate == LXCB::ATTENTION){ background= "background: qlineargradient(spread:pad, x1:0, y1:0, x2:1, y2:1, stop:0 rgba(252, 187, 127, 240), stop:0.505682 rgba(255, 222, 197, 150), stop:1 rgba(221, 246, 255, 55));"; border="border: 1px solid transparent;"; } QString raw = rawstyle; this->setStyleSheet( raw.replace("%1",background).replace("%2", border) ); } @@ -37,7 +38,7 @@ class LTBWidget : public QToolButton{ public: LTBWidget(QWidget* parent) : QToolButton(parent){ //this->setStyleSheet( this->styleSheet()+" LTBWidget::menu-indicator{image: none;}"); - cstate = Lumina::NONE; + cstate = LXCB::IGNORE; this->setPopupMode(QToolButton::InstantPopup); this->setAutoRaise(true); @@ -48,7 +49,7 @@ class LTBWidget : public QToolButton{ ~LTBWidget(){ } - void setState(Lumina::STATES newstate){ + void setState(LXCB::WINDOWSTATE newstate){ cstate = newstate; updateBackground(); } diff --git a/lumina-desktop/panel-plugins/systemtray/LSysTray.cpp b/lumina-desktop/panel-plugins/systemtray/LSysTray.cpp index dacb7b55a..1eafffee6 100644 --- a/lumina-desktop/panel-plugins/systemtray/LSysTray.cpp +++ b/lumina-desktop/panel-plugins/systemtray/LSysTray.cpp @@ -53,7 +53,7 @@ void LSysTray::start(){ isRunning = LSession::handle()->registerVisualTray(this->winId()); qDebug() << "Visual Tray Started:" << this->type() << isRunning; if(isRunning){ - upTimer->start(); + //upTimer->start(); QTimer::singleShot(0,this, SLOT(checkAll()) ); } //Make sure we catch all events right away @@ -169,6 +169,7 @@ void LSysTray::checkAll(){ if(!isRunning || stopping || checking){ return; } //Don't check if not running at the moment checking = true; //qDebug() << "System Tray: Check tray apps"; + bool listChanged = false; QList wins = LSession::handle()->currentTrayApps(this->winId()); for(int i=0; iappID()); @@ -179,6 +180,7 @@ void LSysTray::checkAll(){ LI->removeWidget(cont); delete cont; i--; //List size changed + listChanged = true; //Re-adjust the maximum widget size to account for what is left if(this->layout()->direction()==QBoxLayout::LeftToRight){ this->setMaximumSize( trayIcons.length()*this->height(), 10000); @@ -217,9 +219,17 @@ void LSysTray::checkAll(){ LI->removeWidget(cont); delete cont; continue; - } + }else{ + listChanged = true; + } LI->update(); //make sure there is no blank space in the layout } + /*if(listChanged){ + //Icons got moved around: be sure to re-draw all of them to fix visuals + for(int i=0; iupdate(); + } + }*/ //qDebug() << " - System Tray: check done"; checking = false; } diff --git a/lumina-desktop/panel-plugins/systemtray/LSysTray.h b/lumina-desktop/panel-plugins/systemtray/LSysTray.h index f45a52ad1..1b482ef78 100644 --- a/lumina-desktop/panel-plugins/systemtray/LSysTray.h +++ b/lumina-desktop/panel-plugins/systemtray/LSysTray.h @@ -12,7 +12,7 @@ #include #include #include -#include +//#include #include //Local includes diff --git a/lumina-desktop/panel-plugins/systemtray/TrayIcon.cpp b/lumina-desktop/panel-plugins/systemtray/TrayIcon.cpp index 64c7c77d0..716a49ed1 100644 --- a/lumina-desktop/panel-plugins/systemtray/TrayIcon.cpp +++ b/lumina-desktop/panel-plugins/systemtray/TrayIcon.cpp @@ -6,11 +6,13 @@ //=========================================== #include "TrayIcon.h" -#include -#include +//#include +//#include #include -static Damage dmgID = 0; +//#include +//static xcb_damage_damage_t dmgID; +static int dmgID = 0; TrayIcon::TrayIcon(QWidget *parent) : QWidget(parent){ AID = 0; //nothing yet @@ -36,10 +38,10 @@ void TrayIcon::attachApp(WId id){ if( LX11::EmbedWindow(AID, IID) ){ LX11::RestoreWindow(AID); //make it visible //XSelectInput(QX11Info::display(), AID, StructureNotifyMask); + //xcb_damage_create(QX11Info::connection(), dmgID, AID, XCB_DAMAGE_REPORT_LEVEL_RAW_RECTANGLES); dmgID = XDamageCreate( QX11Info::display(), AID, XDamageReportRawRectangles ); - updateIcon(); qDebug() << "New System Tray App:" << AID; - QTimer::singleShot(500, this, SLOT(updateIcon()) ); + QTimer::singleShot(1000, this, SLOT(updateIcon()) ); }else{ qWarning() << "Could not Embed Tray Application:" << AID; //LX11::DestroyWindow(IID); @@ -64,9 +66,9 @@ void TrayIcon::detachApp(){ //Now detach the application window and clean up qDebug() << " - Unembed"; LX11::UnembedWindow(tmp); - if(dmgID!=0){ - XDamageDestroy(QX11Info::display(), dmgID); - } + //if(dmgID!=0){ + //XDamageDestroy(QX11Info::display(), dmgID); + //} qDebug() << " - finished app:" << tmp; //if(IID!=this->winId()){ LX11::DestroyWindow(IID); } IID = 0; @@ -98,6 +100,7 @@ void TrayIcon::updateIcon(){ //Make sure the icon is square QSize icosize = this->size(); LX11::ResizeWindow(AID, icosize.width(), icosize.height()); + QTimer::singleShot(500, this, SLOT(update()) ); //make sure to re-draw the window in a moment } // ============= @@ -115,7 +118,7 @@ void TrayIcon::paintEvent(QPaintEvent *event){ QPixmap pix = LX11::WindowImage(AID, false); if(pix.isNull()){ //Try to grab the window directly with Qt - //qDebug() << " - - Grab window directly"; + qDebug() << " - - Grab window directly"; pix = QPixmap::grabWindow(AID); } //qDebug() << " - Pix size:" << pix.size().width() << pix.size().height(); @@ -138,6 +141,7 @@ void TrayIcon::resizeEvent(QResizeEvent *event){ //qDebug() << "Resize Event:" << event->size().width() << event->size().height(); if(AID!=0){ LX11::ResizeWindow(AID, event->size().width(), event->size().height()); + QTimer::singleShot(500, this, SLOT(update()) ); //make sure to re-draw the window in a moment } } diff --git a/lumina-desktop/panel-plugins/taskmanager/LTaskButton.cpp b/lumina-desktop/panel-plugins/taskmanager/LTaskButton.cpp index 6ea7854e5..9dfc09796 100644 --- a/lumina-desktop/panel-plugins/taskmanager/LTaskButton.cpp +++ b/lumina-desktop/panel-plugins/taskmanager/LTaskButton.cpp @@ -5,6 +5,7 @@ // See the LICENSE file for full details //=========================================== #include "LTaskButton.h" +#include "LSession.h" LTaskButton::LTaskButton(QWidget *parent) : LTBWidget(parent){ actMenu = new QMenu(this); @@ -71,7 +72,7 @@ void LTaskButton::UpdateButton(){ LWINLIST = WINLIST; winMenu->clear(); - Lumina::STATES showstate = Lumina::NOSHOW; + LXCB::WINDOWSTATE showstate = LXCB::IGNORE; for(int i=0; isetToolTip(cname); - /* - if(this->icon().isNull()){ - this->setIcon( LXDG::findIcon(cname.toLower(),"") ); - if(this->icon().isNull()){ - this->setIcon( LXDG::findIcon("preferences-system-windows","") ); - noicon=true; - }else{ - noicon = false; - } - }else{ - noicon = false; - }*/ } bool junk; QAction *tmp = winMenu->addAction( WINLIST[i].icon(junk), WINLIST[i].text() ); tmp->setData(i); //save which number in the WINLIST this entry is for - Lumina::STATES stat = WINLIST[i].status(); - if(stat==Lumina::NOTIFICATION){ showstate = stat; } //highest priority - else if( stat==Lumina::ACTIVE && showstate != Lumina::NOTIFICATION){ showstate = stat; } //next priority - else if( stat==Lumina::Lumina::VISIBLE && showstate != Lumina::NOTIFICATION && showstate != Lumina::ACTIVE){ showstate = stat; } - else if(showstate == Lumina::INVISIBLE || showstate == Lumina::NOSHOW){ showstate = stat; } //anything is the same/better + LXCB::WINDOWSTATE stat = LSession::handle()->XCB->WindowState(WINLIST[i].windowID()); + if(stat==LXCB::ATTENTION){ showstate = stat; } //highest priority + else if( stat==LXCB::ACTIVE && showstate != LXCB::ATTENTION){ showstate = stat; } //next priority + else if( stat==LXCB::VISIBLE && showstate != LXCB::ATTENTION && showstate != LXCB::ACTIVE){ showstate = stat; } + else if(showstate == LXCB::INVISIBLE || showstate == LXCB::IGNORE){ showstate = stat; } //anything is the same/better } //Now setup the button appropriately // - visibility - if(showstate == Lumina::NOSHOW || WINLIST.length() < 1){ this->setVisible(false); } + if(showstate == LXCB::IGNORE || WINLIST.length() < 1){ this->setVisible(false); } else{ this->setVisible(true); } // - functionality if(WINLIST.length() == 1){ diff --git a/lumina-desktop/panel-plugins/taskmanager/LTaskManagerPlugin.cpp b/lumina-desktop/panel-plugins/taskmanager/LTaskManagerPlugin.cpp index 674c90886..8f131c9e6 100644 --- a/lumina-desktop/panel-plugins/taskmanager/LTaskManagerPlugin.cpp +++ b/lumina-desktop/panel-plugins/taskmanager/LTaskManagerPlugin.cpp @@ -31,7 +31,7 @@ void LTaskManagerPlugin::UpdateButtons(){ //Make sure this only runs one at a time updating=true; //Get the current window list - QList winlist = LX11::WindowList(); + QList winlist = LSession::handle()->XCB->WindowList(); //qDebug() << "Update Buttons:" << winlist; //Now go through all the current buttons first for(int i=0; isetPixmap( LXDG::findIcon(item.icon, "preferences-system-windows-actions").pixmap(30,30) ); + icon->setPixmap( LXDG::findIcon(item.icon, "preferences-system-windows-actions").pixmap(32,32) ); name->setText( this->fontMetrics().elidedText(item.name, Qt::ElideRight, 180) ); }else{ - icon->setPixmap( LXDG::findIcon("unknown","").pixmap(30,30) ); + icon->setPixmap( LXDG::findIcon("unknown","").pixmap(32,32) ); name->setText( this->fontMetrics().elidedText(itemPath.section("/",-1), Qt::ElideRight, 180) ); } }else if(isDir){ if(itemPath.endsWith("/")){ itemPath.chop(1); } if(goback){ - icon->setPixmap( LXDG::findIcon("go-previous","").pixmap(30,30) ); + icon->setPixmap( LXDG::findIcon("go-previous","").pixmap(32,32) ); name->setText( tr("Go Back") ); }else{ - icon->setPixmap( LXDG::findIcon("folder","").pixmap(30,30) ); + icon->setPixmap( LXDG::findIcon("folder","").pixmap(32,32) ); name->setText( this->fontMetrics().elidedText(itemPath.section("/",-1), Qt::ElideRight, 180) ); } }else{ if(itemPath.endsWith("/")){ itemPath.chop(1); } - icon->setPixmap( LXDG::findMimeIcon(itemPath.section("/",-1).section(".",-1)).pixmap(30,30) ); + icon->setPixmap( LXDG::findMimeIcon(itemPath.section("/",-1).section(".",-1)).pixmap(32,32) ); name->setText( this->fontMetrics().elidedText(itemPath.section("/",-1), Qt::ElideRight, 180) ); } linkPath = QFile::symLinkTarget(itemPath); @@ -48,7 +48,7 @@ UserItemWidget::UserItemWidget(QWidget *parent, XDGDesktop item) : QFrame(parent linkPath = QFile::symLinkTarget(item.filePath); isShortcut = item.filePath.contains("/home/") && (item.filePath.contains("/Desktop/") || item.filePath.contains("/.lumina/favorites/") ); //Now fill it appropriately - icon->setPixmap( LXDG::findIcon(item.icon,"preferences-system-windows-actions").pixmap(30,30) ); + icon->setPixmap( LXDG::findIcon(item.icon,"preferences-system-windows-actions").pixmap(32,32) ); name->setText( this->fontMetrics().elidedText(item.name, Qt::ElideRight, 180) ); icon->setWhatsThis(item.filePath); //Now setup the button appropriately @@ -70,7 +70,7 @@ void UserItemWidget::createWidget(){ button->setIconSize( QSize(14,14) ); button->setAutoRaise(true); icon = new QLabel(this); - icon->setFixedSize( QSize(30,30) ); + icon->setFixedSize( QSize(34,34) ); name = new QLabel(this); //Add them to the layout this->setLayout(new QHBoxLayout()); diff --git a/lumina-fm/BackgroundWorker.cpp b/lumina-fm/BackgroundWorker.cpp index 1e6ef28d3..9b3804d5f 100644 --- a/lumina-fm/BackgroundWorker.cpp +++ b/lumina-fm/BackgroundWorker.cpp @@ -1,7 +1,7 @@ #include "BackgroundWorker.h" #include -#include +#include #include BackgroundWorker::BackgroundWorker() : QObject(){ @@ -26,12 +26,9 @@ void BackgroundWorker::startDirChecks(QString path){ //Now check for multimedia files if(multiFilter.isEmpty()){ - //Initial Run - load supported multimedia extensions - QStringList mimes = Phonon::BackendCapabilities::availableMimeTypes(); - mimes = mimes.filter("audio/") + mimes.filter("video/"); - for(int i=0; imenuView->addAction(listWA); ui->menuView->addAction(icoWA); //Setup the special Phonon widgets - mediaObj = new Phonon::MediaObject(this); - mediaObj->setTickInterval(200); //1/5 second ticks for updates - videoDisplay = new Phonon::VideoWidget(this); + mediaObj = new QMediaPlayer(this); + mediaObj->setVolume(100); + mediaObj->setNotifyInterval(500); //only every 1/2 second update + videoDisplay = new QVideoWidget(this); videoDisplay->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); ui->videoLayout->addWidget(videoDisplay); - Phonon::createPath(mediaObj, videoDisplay); + mediaObj->setVideoOutput(videoDisplay); videoDisplay->setVisible(false); - audioOut = new Phonon::AudioOutput(Phonon::VideoCategory, this); - Phonon::createPath(mediaObj, audioOut); - playerSlider = new Phonon::SeekSlider(this); - playerSlider->setMediaObject(mediaObj); + playerSlider = new QSlider(this); + playerSlider->setOrientation(Qt::Horizontal); ui->videoControlLayout->insertWidget(4, playerSlider); ui->tool_player_stop->setEnabled(false); //nothing to stop yet ui->tool_player_pause->setVisible(false); //nothing to pause yet + playerSlider->setEnabled(false); //nothing to seek yet //Setup any specialty keyboard shortcuts nextTabLShort = new QShortcut( QKeySequence(tr("Shift+Left")), this); nextTabRShort = new QShortcut( QKeySequence(tr("Shift+Right")), this); @@ -232,10 +232,16 @@ void MainUI::setupConnections(){ connect(ui->tool_player_play, SIGNAL(clicked()), this, SLOT(playerStart())); connect(ui->tool_player_stop, SIGNAL(clicked()), this, SLOT(playerStop())); connect(ui->combo_player_list, SIGNAL(currentIndexChanged(int)), this, SLOT(playerFileChanged()) ); - connect(mediaObj, SIGNAL(finished()), this, SLOT(playerFinished()) ); - connect(mediaObj, SIGNAL(tick(qint64)), this, SLOT(playerTimeChanged(qint64)) ); - connect(mediaObj, SIGNAL(stateChanged(Phonon::State, Phonon::State)), this, SLOT(playerStateChanged(Phonon::State, Phonon::State)) ); - connect(mediaObj, SIGNAL(hasVideoChanged(bool)), this, SLOT(playerVideoAvailable(bool)) ); + connect(playerSlider, SIGNAL(sliderPressed()), this, SLOT(playerSliderHeld()) ); + connect(playerSlider, SIGNAL(sliderReleased()), this, SLOT(playerSliderChanged()) ); + connect(playerSlider, SIGNAL(valueChanged(int)), this, SLOT(playerSliderMoved(int)) ); + connect(mediaObj, SIGNAL(durationChanged(qint64)), this, SLOT(playerDurationChanged(qint64)) ); + connect(mediaObj, SIGNAL(seekableChanged(bool)), playerSlider, SLOT(setEnabled(bool)) ); + connect(mediaObj, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)), this, SLOT(playerStatusChanged(QMediaPlayer::MediaStatus)) ); + connect(mediaObj, SIGNAL(positionChanged(qint64)), this, SLOT(playerTimeChanged(qint64)) ); + connect(mediaObj, SIGNAL(stateChanged(QMediaPlayer::State)), this, SLOT(playerStateChanged(QMediaPlayer::State)) ); + connect(mediaObj, SIGNAL(videoAvailableChanged(bool)), this, SLOT(playerVideoAvailable(bool)) ); + connect(mediaObj, SIGNAL(error(QMediaPlayer::Error)), this, SLOT(playerError()) ); //Special Keyboard Shortcuts connect(nextTabLShort, SIGNAL(activated()), this, SLOT( prevTab() ) ); connect(nextTabRShort, SIGNAL(activated()), this, SLOT( nextTab() ) ); @@ -391,7 +397,7 @@ void MainUI::setCurrentDir(QString dir){ ui->tool_goToPlayer->setVisible(false); ui->tool_goToRestore->setVisible(false); ui->tool_goToImages->setVisible(false); - if(olddir==rawdir){ + if(olddir!=rawdir){ emit DirChanged(rawdir); //This will be automatically run when a new dir is loaded } if(isUserWritable){ ui->label_dir_stats->setText(""); } @@ -937,24 +943,29 @@ void MainUI::restoreItems(){ void MainUI::playerStart(){ if(ui->stackedWidget->currentWidget()!=ui->page_audioPlayer){ return; } //don't play if not in the player - if(mediaObj->state()==Phonon::PausedState){ + if(mediaObj->state()==QMediaPlayer::PausedState \ + && mediaObj->currentMedia().canonicalUrl().fileName()==ui->combo_player_list->currentText() ){ mediaObj->play(); - }else{ // if(mediaObj->state()==Phonon::StoppedState || mediaObj->state()==Phonon::ErrorState || (playerFile->fileName().section("/",-1) != ui->combo_player_list->currentText()) || playerFile->isOpen() ){ + }else{ mediaObj->stop(); //Get the selected file path QString filePath = getCurrentDir(); if(!filePath.endsWith("/")){ filePath.append("/"); } filePath.append( ui->combo_player_list->currentText() ); - //if(playerFile->isOpen()){ playerFile->close(); } - //playerFile->setFileName(filePath); - //if(playerFile->open(QIODevice::ReadOnly)){ - mediaObj->setCurrentSource( QUrl(filePath) ); - playerSlider->setMediaObject(mediaObj); + mediaObj->setMedia( QUrl::fromLocalFile(filePath) ); + playerTTime.clear(); + playerSlider->setEnabled(mediaObj->isSeekable()); mediaObj->play(); - //} } } +void MainUI::playerError(){ + QString msg = QString(tr("Error Playing File: %1")); + msg = msg.arg( mediaObj->currentMedia().canonicalUrl().fileName() ); + msg.append("\n"+mediaObj->errorString()); + ui->label_player_novideo->setText(msg); +} + void MainUI::playerStop(){ mediaObj->stop(); } @@ -965,51 +976,48 @@ void MainUI::playerPause(){ void MainUI::playerNext(){ ui->combo_player_list->setCurrentIndex( ui->combo_player_list->currentIndex()+1); + if(mediaObj->state()!=QMediaPlayer::StoppedState){ playerStart(); } } void MainUI::playerPrevious(){ ui->combo_player_list->setCurrentIndex( ui->combo_player_list->currentIndex()-1); + if(mediaObj->state()!=QMediaPlayer::StoppedState){ playerStart(); } } void MainUI::playerFinished(){ - //playerFile->close(); if(ui->combo_player_list->currentIndex()<(ui->combo_player_list->count()-1) && ui->check_player_gotonext->isChecked()){ ui->combo_player_list->setCurrentIndex( ui->combo_player_list->currentIndex()+1 ); + QTimer::singleShot(0,this,SLOT(playerStart())); }else{ ui->label_player_novideo->setText(tr("Finished")); } } -void MainUI::playerStateChanged(Phonon::State newstate, Phonon::State oldstate){ +void MainUI::playerStatusChanged(QMediaPlayer::MediaStatus stat){ + //Only use this for end-of-file detection - use the state detection otherwise + if(stat == QMediaPlayer::EndOfMedia){ + if(!mediaObj->isMuted()){ playerFinished(); } //make sure it is not being seeked right now + } +} + +void MainUI::playerStateChanged(QMediaPlayer::State newstate){ //This function keeps track of updating the visuals of the player bool running = false; bool showVideo = false; QString msg; switch(newstate){ - case Phonon::LoadingState: + case QMediaPlayer::PlayingState: running=true; - ui->label_player_novideo->setText(tr("Loading File...")); - break; - case Phonon::PlayingState: - running=true; - showVideo = mediaObj->hasVideo(); - msg = mediaObj->metaData(Phonon::TitleMetaData).join(" "); + showVideo = mediaObj->isVideoAvailable(); + msg = "";//mediaObj->metaData(Phonon::TitleMetaData).join(" "); if(msg.simplified().isEmpty()){ msg = ui->combo_player_list->currentText(); } ui->label_player_novideo->setText(tr("Playing:")+"\n"+msg); break; - case Phonon::BufferingState: - running=true; - showVideo=true; //don't blank the screen - break; - case Phonon::PausedState: + case QMediaPlayer::PausedState: showVideo=videoDisplay->isVisible(); //don't change the screen break; - case Phonon::StoppedState: - if(oldstate==Phonon::LoadingState){ mediaObj->play(); } - else{ ui->label_player_novideo->setText(tr("Stopped")); } - break; - case Phonon::ErrorState: - ui->label_player_novideo->setText(tr("Error Playing File")+"\n("+mediaObj->errorString()+")"); + case QMediaPlayer::StoppedState: + ui->label_player_novideo->setText(tr("Stopped")); break; } ui->tool_player_play->setVisible(!running); @@ -1024,20 +1032,34 @@ void MainUI::playerVideoAvailable(bool showVideo){ videoDisplay->setVisible(showVideo); } +void MainUI::playerDurationChanged(qint64 dur){ + if(dur < 0){ return; } //not ready yet + playerSlider->setMaximum(mediaObj->duration()); + playerTTime = msToText(dur); +} + void MainUI::playerTimeChanged(qint64 ctime){ - if(playerTTime=="0:00" || playerTTime.isEmpty()){ playerTTime = msToText(mediaObj->totalTime()); } //only calculate as necessary - //qDebug() << "Time:" << msToText(ctime) << playerTTime << mediaObj->isSeekable() << mediaObj->hasVideo(); - ui->label_player_runstats->setText( msToText(ctime)+"/"+playerTTime ); + if(mediaObj->isMuted() || playerTTime.isEmpty() ){ return; } //currently being moved + playerSlider->setSliderPosition(ctime); +} + +void MainUI::playerSliderMoved(int val){ + ui->label_player_runstats->setText( msToText(val)+"/"+playerTTime ); + if(mediaObj->isMuted()){ mediaObj->setPosition(playerSlider->value()); } //currently seeking +} + +void MainUI::playerSliderHeld(){ + mediaObj->setMuted(true); + mediaObj->pause(); +} +void MainUI::playerSliderChanged(){ + if(mediaObj->state()==QMediaPlayer::PausedState){ mediaObj->play(); } + mediaObj->setMuted(false); } void MainUI::playerFileChanged(){ ui->tool_player_next->setEnabled( ui->combo_player_list->count() > (ui->combo_player_list->currentIndex()+1) ); ui->tool_player_prev->setEnabled( (ui->combo_player_list->currentIndex()-1) >= 0 ); - if(ui->stackedWidget->currentWidget()!=ui->page_audioPlayer){ return; } //don't play if not in the player - //If one is playing, so ahead and start playing the new selection - if(ui->check_player_gotonext->isChecked() ){ - QTimer::singleShot(0,this,SLOT(playerStart())); - } } //---------------------------------- diff --git a/lumina-fm/MainUI.h b/lumina-fm/MainUI.h index 87a526686..1cc268307 100644 --- a/lumina-fm/MainUI.h +++ b/lumina-fm/MainUI.h @@ -40,13 +40,9 @@ #include #include -//Phonon widgets -//#include -#include -#include -#include -#include -#include +//Multimedia Widgets +#include +#include // libLumina includes #include @@ -89,10 +85,10 @@ public slots: QString favdir; //Phonon Widgets for the multimedia player - Phonon::MediaObject *mediaObj; - Phonon::VideoWidget *videoDisplay; - Phonon::AudioOutput *audioOut; - Phonon::SeekSlider *playerSlider; + QMediaPlayer *mediaObj; + QVideoWidget *videoDisplay; + //Phonon::AudioOutput *audioOut; + QSlider *playerSlider; QString playerTTime; //total time - to prevent recalculation every tick //Internal variables @@ -184,14 +180,20 @@ private slots: //Multimedia Player Functions void playerStart(); + void playerError(); void playerStop(); void playerPause(); void playerNext(); void playerPrevious(); void playerFinished(); //automatically called by the media object - void playerStateChanged(Phonon::State newstate, Phonon::State oldstate); //automatically called by the media object + void playerStatusChanged(QMediaPlayer::MediaStatus stat); //automatically called + void playerStateChanged(QMediaPlayer::State newstate); //automatically called by the media object void playerVideoAvailable(bool showVideo); //automatically called by the media object + void playerDurationChanged(qint64); void playerTimeChanged(qint64 ctime); //automatically called by the media object + void playerSliderMoved(int); + void playerSliderHeld(); + void playerSliderChanged(); void playerFileChanged(); //Context Menu Actions diff --git a/lumina-fm/lumina-fm.pro b/lumina-fm/lumina-fm.pro index cc9ad275c..d0fb713b5 100644 --- a/lumina-fm/lumina-fm.pro +++ b/lumina-fm/lumina-fm.pro @@ -1,5 +1,6 @@ -QT += core gui phonon +QT += core gui +greaterThan(QT_MAJOR_VERSION, 4): QT += widgets multimedia multimediawidgets TARGET = lumina-fm isEmpty(PREFIX) { @@ -30,14 +31,14 @@ FORMS += MainUI.ui \ INCLUDEPATH += ../libLumina $$PREFIX/include LIBS += -L../libLumina -lLuminaUtils -freebsd-* { +/*freebsd-* { LIBS += -lQtSolutions_SingleApplication-head -} +}*/ openbsd-g++4 { LRELEASE = lrelease4 } else { - LRELEASE = lrelease-qt4 + LRELEASE = $$PREFIX/lib/qt5/bin/lrelease } QMAKE_LIBDIR = ../libLumina diff --git a/lumina-fm/main.cpp b/lumina-fm/main.cpp index e2f70bc15..760ca7ad3 100644 --- a/lumina-fm/main.cpp +++ b/lumina-fm/main.cpp @@ -1,11 +1,12 @@ #include -#ifdef __FreeBSD__ +/*#ifdef __FreeBSD__ #include -#endif -#include +#endif*/ +#include #include #include -#include +#include +//#include #include "MainUI.h" #include @@ -25,32 +26,32 @@ int main(int argc, char ** argv) } } if(in.isEmpty()){ in << QDir::homePath(); } - #ifdef __FreeBSD__ + /*#ifdef __FreeBSD__ QtSingleApplication a(argc, argv); if( a.isRunning() ){ return !(a.sendMessage(in.join("\n"))); } - #else + #else*/ QApplication a(argc, argv); - #endif + qDebug() << "Loaded QApplication"; + //#endif a.setApplicationName("Insight File Manager"); LuminaThemeEngine themes(&a); //Load current Locale QTranslator translator; QLocale mylocale; QString langCode = mylocale.name(); - if ( ! QFile::exists(LOS::LuminaShare()+"i18n/lumina-fm_" + langCode + ".qm" ) ) langCode.truncate(langCode.indexOf("_")); translator.load( QString("lumina-fm_") + langCode, LOS::LuminaShare()+"i18n/" ); a.installTranslator( &translator ); qDebug() << "Locale:" << langCode; //Load current encoding for this locale - QTextCodec::setCodecForTr( QTextCodec::codecForLocale() ); //make sure to use the same codec - qDebug() << "Locale Encoding:" << QTextCodec::codecForLocale()->name(); + //QTextCodec::setCodecForTr( QTextCodec::codecForLocale() ); //make sure to use the same codec + //qDebug() << "Locale Encoding:" << QTextCodec::codecForLocale()->name(); MainUI w; - QObject::connect(&a, SIGNAL(messageReceived(const QString&)), &w, SLOT(slotSingleInstance(const QString&)) ); + //QObject::connect(&a, SIGNAL(messageReceived(const QString&)), &w, SLOT(slotSingleInstance(const QString&)) ); QObject::connect(&themes, SIGNAL(updateIcons()), &w, SLOT(setupIcons()) ); w.OpenDirs(in); w.show(); diff --git a/lumina-open/LFileDialog.h b/lumina-open/LFileDialog.h index 27f038d60..eaed3625d 100644 --- a/lumina-open/LFileDialog.h +++ b/lumina-open/LFileDialog.h @@ -19,6 +19,7 @@ #include #include #include +#include #include //From libLuminaUtils #include diff --git a/lumina-open/lumina-open.pro b/lumina-open/lumina-open.pro index b70d6b27c..ce0e231dd 100644 --- a/lumina-open/lumina-open.pro +++ b/lumina-open/lumina-open.pro @@ -1,5 +1,6 @@ QT += core gui +greaterThan(QT_MAJOR_VERSION, 4): QT += widgets x11extras TARGET = lumina-open isEmpty(PREFIX) { diff --git a/lumina-open/main.cpp b/lumina-open/main.cpp index 4fcf70b7b..a92a585f1 100644 --- a/lumina-open/main.cpp +++ b/lumina-open/main.cpp @@ -125,8 +125,8 @@ QString cmdFromUser(int argc, char **argv, QString inFile, QString extension, QS qDebug() << "Locale:" << langCode; //Load current encoding for this locale - QTextCodec::setCodecForTr( QTextCodec::codecForLocale() ); //make sure to use the same codec - qDebug() << "Locale Encoding:" << QTextCodec::codecForLocale()->name(); + //QTextCodec::setCodecForTr( QTextCodec::codecForLocale() ); //make sure to use the same codec + //qDebug() << "Locale Encoding:" << QTextCodec::codecForLocale()->name(); LFileDialog w; if(inFile.startsWith(extension)){ diff --git a/lumina-screenshot/MainUI.cpp b/lumina-screenshot/MainUI.cpp index 5ff698bdb..9abe93a2d 100644 --- a/lumina-screenshot/MainUI.cpp +++ b/lumina-screenshot/MainUI.cpp @@ -11,7 +11,7 @@ MainUI::MainUI() : QMainWindow(), ui(new Ui::MainUI){ ui->setupUi(this); //load the designer file - cpic = QPixmap::grabWindow(QApplication::desktop()->winId()); //initial screenshot + cpic = QApplication::screens().at(0)->grabWindow(QApplication::desktop()->winId()); //initial screenshot ppath = QDir::homePath(); QWidget *spacer = new QWidget(); spacer->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); @@ -90,12 +90,13 @@ bool MainUI::getWindow(){ } void MainUI::getPixmap(){ + QScreen *scrn = QApplication::screens().at(0); if(cwin==0){ //Grab the whole screen - cpic = QPixmap::grabWindow(QApplication::desktop()->winId()); + cpic = scrn->grabWindow(QApplication::desktop()->winId()); }else{ //Grab just the designated window - cpic = QPixmap::grabWindow(cwin); + cpic = scrn->grabWindow(cwin); } this->show(); //Now display the pixmap on the label as well diff --git a/lumina-screenshot/MainUI.h b/lumina-screenshot/MainUI.h index c350f366f..8c4081313 100644 --- a/lumina-screenshot/MainUI.h +++ b/lumina-screenshot/MainUI.h @@ -16,6 +16,8 @@ #include #include #include +#include +#include #include #include diff --git a/lumina-screenshot/MainUI.ui b/lumina-screenshot/MainUI.ui index 2d35b68ce..a9ee7aaa8 100644 --- a/lumina-screenshot/MainUI.ui +++ b/lumina-screenshot/MainUI.ui @@ -118,7 +118,7 @@ TopToolBarArea - true + false diff --git a/lumina-screenshot/lumina-screenshot.pro b/lumina-screenshot/lumina-screenshot.pro index 1681a12b1..b43d582cb 100644 --- a/lumina-screenshot/lumina-screenshot.pro +++ b/lumina-screenshot/lumina-screenshot.pro @@ -1,5 +1,6 @@ QT += core gui +greaterThan(QT_MAJOR_VERSION, 4): QT += widgets x11extras TARGET = lumina-screenshot isEmpty(PREFIX) { @@ -18,16 +19,10 @@ FORMS += MainUI.ui INCLUDEPATH += ../libLumina $$PREFIX/include - LIBS += -L../libLumina -lLuminaUtils -freebsd-* { - LIBS += -lQtSolutions_SingleApplication-head -} +LIBS += -L../libLumina -lLuminaUtils + +LRELEASE = $$PREFIX/lib/qt5/bin/lrelease -openbsd-g++4 { - LRELEASE = lrelease4 -} else { - LRELEASE = lrelease-qt4 -} QMAKE_LIBDIR = ../libLumina DEPENDPATH += ../libLumina diff --git a/lumina-screenshot/main.cpp b/lumina-screenshot/main.cpp index b7112a4d0..9561430d9 100644 --- a/lumina-screenshot/main.cpp +++ b/lumina-screenshot/main.cpp @@ -1,5 +1,5 @@ #include -#include +#include #include #include diff --git a/lumina-search/lumina-search.pro b/lumina-search/lumina-search.pro index 3f428c6a4..fcc6ae0fb 100644 --- a/lumina-search/lumina-search.pro +++ b/lumina-search/lumina-search.pro @@ -1,5 +1,6 @@ QT += core gui +greaterThan(QT_MAJOR_VERSION, 4): QT += widgets TARGET = lumina-search isEmpty(PREFIX) { @@ -20,16 +21,10 @@ FORMS += MainUI.ui INCLUDEPATH += ../libLumina $$PREFIX/include - LIBS += -L../libLumina -lLuminaUtils -freebsd-* { - LIBS += -lQtSolutions_SingleApplication-head -} +LIBS += -L../libLumina -lLuminaUtils + +LRELEASE = $$PREFIX/lib/qt5/bin/lrelease -openbsd-g++4 { - LRELEASE = lrelease4 -} else { - LRELEASE = lrelease-qt4 -} QMAKE_LIBDIR = ../libLumina DEPENDPATH += ../libLumina diff --git a/lumina-search/main.cpp b/lumina-search/main.cpp index 886884d50..a4d04d4b4 100644 --- a/lumina-search/main.cpp +++ b/lumina-search/main.cpp @@ -1,5 +1,5 @@ #include -#include +#include #include #include @@ -9,8 +9,11 @@ int main(int argc, char ** argv) { + //qDebug() << "Init App..."; QApplication a(argc, argv); + //qDebug() << "Init Theme Engine..."; LuminaThemeEngine theme(&a); + //qDebug() << "Load Translations..."; a.setApplicationName("Search for..."); QTranslator translator; QLocale mylocale; diff --git a/port-files/Makefile b/port-files/Makefile index e625c4b4d..483c49e34 100644 --- a/port-files/Makefile +++ b/port-files/Makefile @@ -3,7 +3,7 @@ PORTNAME= lumina GITVERSION= CHGVERSION -PORTVERSION= 0.7.2.${GITVERSION} +PORTVERSION= 0.8.0.${GITVERSION} PORTEPOCH= 1 CATEGORIES= x11 DISTNAME= ${PORTNAME}-${GITVERSION} @@ -23,16 +23,14 @@ RUN_DEPENDS= xorg>=0:${PORTSDIR}/x11/xorg \ xscreensaver-demo:${PORTSDIR}/x11/xscreensaver \ xbrightness:${PORTSDIR}/x11/xbrightness \ numlockx:${PORTSDIR}/x11/numlockx \ - phonon-gstreamer>=0:${PORTSDIR}/multimedia/phonon-gstreamer \ - gstreamer-plugins-ogg>=0:${PORTSDIR}/audio/gstreamer-plugins-ogg -LIB_DEPENDS= libQtSolutions_SingleApplication-head.so:${PORTSDIR}/devel/qt4-qtsolutions-singleapplication \ - libjpeg.so:${PORTSDIR}/graphics/jpeg +#LIB_DEPENDS= MAKE_JOBS_UNSAFE=yes USE_XORG= x11 xcomposite xdamage xrender +USE_XCB= x11extras wm USE_LDCONFIG= yes -USE_QT4= corelib gui network svg linguist phonon imageformats \ - moc_build rcc_build uic_build +USE_QT5= corelib gui network svg linguist multimedia imageformats \ + buildtools x11extras USES= qmake tar:bzip2 WRKSRC= ${WRKDIR}/lumina diff --git a/port-files/pkg-plist b/port-files/pkg-plist index b07c02aa1..a0c7dd823 100644 --- a/port-files/pkg-plist +++ b/port-files/pkg-plist @@ -13,6 +13,7 @@ include/LuminaUtils.h include/LuminaX11.h include/LuminaThemes.h include/LuminaOS.h +include/LuminaSingleApplication.h share/applications/lumina-fm.desktop share/applications/lumina-screenshot.desktop share/applications/lumina-search.desktop