//=========================================== // Lumina-DE source code // Copyright (c) 2012-2016, Ken Moore // Available under the 3-clause BSD license // See the LICENSE file for full details //=========================================== #include "LDesktopUtils.h" #include #include #include #include #include "LuminaThemes.h" static QStringList fav; QString LDesktopUtils::LuminaDesktopVersion(){ QString ver = "1.4.0"; #ifdef GIT_VERSION ver.append( QString(" (Git Revision: %1)").arg(GIT_VERSION) ); #endif return ver; } QString LDesktopUtils::LuminaDesktopBuildDate(){ #ifdef BUILD_DATE return BUILD_DATE; #endif return ""; } //Various function for finding valid QtQuick plugins on the system bool LDesktopUtils::validQuickPlugin(QString ID){ return ( !LDesktopUtils::findQuickPluginFile(ID).isEmpty() ); } QString LDesktopUtils::findQuickPluginFile(QString ID){ if(ID.startsWith("quick-")){ ID = ID.section("-",1,50); } //just in case //Give preference to any user-supplied plugins (overwrites for system plugins) QString path = QString(getenv("XDG_CONFIG_HOME"))+"/lumina-desktop/quickplugins/quick-"+ID+".qml"; if( QFile::exists(path) ){return path; } path = LOS::LuminaShare()+"quickplugins/quick-"+ID+".qml"; if( QFile::exists(path) ){return path; } return ""; //could not be found } QStringList LDesktopUtils::listQuickPlugins(){ QDir dir(QString(getenv("XDG_CONFIG_HOME"))+"/lumina-desktop/quickplugins"); QStringList files = dir.entryList(QStringList() << "quick-*.qml", QDir::Files | QDir::NoDotAndDotDot, QDir::Name); dir.cd(LOS::LuminaShare()+"quickplugins"); files << dir.entryList(QStringList() << "quick-*.qml", QDir::Files | QDir::NoDotAndDotDot, QDir::Name); for(int i=0; i*1000000 + *1000 + // Example: 1.2.3 -> 1002003 } void LDesktopUtils::LoadSystemDefaults(bool skipOS){ //Will create the Lumina configuration files based on the current system template (if any) qDebug() << "Loading System Defaults"; bool skipmime = QFile::exists( QString(getenv("XDG_CONFIG_HOME"))+"/lumina-mimapps.list" ); qDebug() << " - Skipping mimetype default apps" << skipmime; QStringList sysDefaults; if(!skipOS){ sysDefaults = LUtils::readFile(LOS::AppPrefix()+"etc/luminaDesktop.conf"); } if(sysDefaults.isEmpty() && !skipOS){ sysDefaults = LUtils::readFile(LOS::AppPrefix()+"etc/luminaDesktop.conf.dist"); } if(sysDefaults.isEmpty() && !skipOS) { sysDefaults = LUtils::readFile(LOS::SysPrefix()+"etc/luminaDesktop.conf"); } if(sysDefaults.isEmpty() && !skipOS){ sysDefaults = LUtils::readFile(LOS::SysPrefix()+"etc/luminaDesktop.conf.dist"); } if(sysDefaults.isEmpty() && !skipOS) { sysDefaults = LUtils::readFile(L_ETCDIR+"/luminaDesktop.conf"); } if(sysDefaults.isEmpty() && !skipOS){ sysDefaults = LUtils::readFile(L_ETCDIR+"/luminaDesktop.conf.dist"); } if(sysDefaults.isEmpty()){ sysDefaults = LUtils::readFile(LOS::LuminaShare()+"luminaDesktop.conf"); } //Find the number of the left-most desktop screen QString screen = "0"; QRect screenGeom; QDesktopWidget *desk =QApplication::desktop(); for(int i=0; iscreenCount(); i++){ if(desk->screenGeometry(i).x()==0){ screen = QString::number(i); screenGeom = desk->screenGeometry(i); break; } } //Now setup the default "desktopsettings.conf" and "sessionsettings.conf" files QStringList deskset, sesset;//, lopenset; // -- SESSION SETTINGS -- QStringList tmp = sysDefaults.filter("session_"); if(tmp.isEmpty()){ tmp = sysDefaults.filter("session."); }//for backwards compat sesset << "[General]"; //everything is in this section sesset << "DesktopVersion="+LDesktopUtils::LuminaDesktopVersion(); for(int i=0; iname(); //(only works for the primary desktop at the moment) tmp = sysDefaults.filter("desktop_"); if(tmp.isEmpty()){ tmp = sysDefaults.filter("desktop."); }//for backwards compat if(!tmp.isEmpty()){deskset << "[desktop-"+deskID+"]"; } for(int i=0; i 1000000], [1.2.3 -> 1002003], [0.6.1 -> 6001] //returns true if something changed int oldversion = LDesktopUtils::VersionStringToNumber(lastversion); int nversion = LDesktopUtils::VersionStringToNumber(currentversion); bool newversion = ( oldversion < nversion ); //increasing version number bool newrelease = ( lastversion.contains("-devel", Qt::CaseInsensitive) && QApplication::applicationVersion().contains("-release", Qt::CaseInsensitive) ); //Moving from devel to release QString confdir = QString(getenv("XDG_CONFIG_HOME"))+"/lumina-desktop/"; //Check for the desktop settings file QString dset = confdir+"desktopsettings.conf"; bool firstrun = false; if(!QFile::exists(dset) || oldversion < 5000){ if( oldversion < 100000 && nversion>=100000 ){ system("rm -rf ~/.lumina"); qDebug() << "Current desktop settings obsolete: Re-implementing defaults"; } else{ firstrun = true; } LDesktopUtils::LoadSystemDefaults(); } //Convert the favorites framework as necessary (change occured with 0.8.4) if(newversion || newrelease){ LDesktopUtils::upgradeFavorites(oldversion); } //Convert from the old desktop numbering system to the new one (change occured with 1.0.1) if(oldversion<=1000001){ QStringList DS = LUtils::readFile(dset); QList screens = QApplication::screens(); for(int i=0; i=0 && ok && num< screens.length()){ //This one needs to be converted DS[i] = "[desktop-"+screens[num]->name()+"]"; } }else if(DS[i].startsWith("[panel")){ bool ok = false; int num = DS[i].section("panel",-1).section(".",0,0).toInt(&ok); if(num>=0 && ok && num< screens.length()){ //This one needs to be converted QString rest = DS[i].section(".",1,-1); //everything after the desktop number in the current setting DS[i] = "[panel_"+screens[num]->name()+"."+rest; } } } LUtils::writeFile(dset, DS, true); } if(oldversion<1003004){ //Lumina 1.3.4 - Migrate theme settings from old format to the new theme engine format QString themefile = QString(getenv("XDG_CONFIG_HOME"))+"/lthemeengine/lthemeengine.conf"; if(!QFile::exists(themefile)){ QDir dir; dir.mkpath(themefile.section("/",0,-2)); //make sure the main directory exists first //Need to migrate theme settings from the old location to the new one QSettings newtheme(themefile, QSettings::NativeFormat); qDebug() << "Migrating Theme settings:" << newtheme.fileName(); QStringList oldtheme = LUtils::readFile( QString(getenv("XDG_CONFIG_HOME"))+"/lumina-desktop/themesettings.cfg" ); //Find the system install location for the theme engine for use later QString enginedir = LOS::LuminaShare()+"/../lthemeengine/"; //Find/match the icon theme QString tmp = oldtheme.filter("ICONTHEME=").join("\n").section("=",1,-1).section("\n",0,0).simplified(); if(tmp.isEmpty()){ tmp = "material-design-light"; } //unknown Icon theme - use the default "light" version newtheme.setValue("Appearance/icon_theme",tmp); //Quick detect/adjust of the tone of the color theme based on the icons/colors (no 1-to-1 color theme matching between systems) bool isdarktheme = tmp.contains("dark"); isdarktheme = isdarktheme || oldtheme.filter("COLORFILE=").join("\n").section("=",1,-1).section("\n",0,0).contains("DarkGlass"); //Quick adjust for the material-design icon theme to make it match the current dark/light theme if(tmp.contains("material-design")){ newtheme.setValue("Appearance/icon_theme", QString("material-design-")+ (isdarktheme ? "dark" : "light") ); } if(isdarktheme){ newtheme.setValue("Appearance/custom_palette", true); newtheme.setValue("Appearance/color_scheme_path", enginedir+"colors/darker.conf"); newtheme.setValue("Interface/desktop_stylesheets", QStringList() << enginedir+"desktop_qss/DarkGlass.qss"); }else{ newtheme.setValue("Appearance/custom_palette", true); newtheme.setValue("Appearance/color_scheme_path", enginedir+"colors/airy.conf"); newtheme.setValue("Interface/desktop_stylesheets", QStringList() << enginedir+"desktop_qss/Glass.qss"); } newtheme.setValue("Appearance/style", "Fusion"); newtheme.setValue("Interface/stylesheets", QStringList() << enginedir+"qss/tooltip-simple.qss" << enginedir+"qss/scrollbar-simple.qss" << enginedir+"qss/sliders-simple.qss"); newtheme.sync(); //flush this to file right now } //end check for theme file existance } //Check the fluxbox configuration files dset = QString(getenv("XDG_CONFIG_HOME"))+"/lumina-desktop/"; if(!QFile::exists(dset+"fluxbox-init")){ firstrun = true; } bool fluxcopy = false; if(!QFile::exists(dset+"fluxbox-init")){ fluxcopy=true; } else if(!QFile::exists(dset+"fluxbox-keys")){fluxcopy=true; } else if(oldversion < 60){ fluxcopy=true; qDebug() << "Current fluxbox settings obsolete: Re-implementing defaults"; } if(fluxcopy){ qDebug() << "Copying default fluxbox configuration files"; if(QFile::exists(dset+"fluxbox-init")){ QFile::remove(dset+"fluxbox-init"); } if(QFile::exists(dset+"fluxbox-keys")){ QFile::remove(dset+"fluxbox-keys"); } QString finit = LUtils::readFile(LOS::LuminaShare()+"fluxbox-init-rc").join("\n"); finit.replace("${XDG_CONFIG_HOME}", QString(getenv("XDG_CONFIG_HOME"))); LUtils::writeFile(dset+"fluxbox-init", finit.split("\n")); QFile::copy(LOS::LuminaShare()+"fluxbox-keys", dset+"fluxbox-keys"); QFile::setPermissions(dset+"fluxbox-init", QFile::ReadOwner | QFile::WriteOwner | QFile::ReadUser | QFile::ReadOther | QFile::ReadGroup); QFile::setPermissions(dset+"fluxbox-keys", QFile::ReadOwner | QFile::WriteOwner | QFile::ReadUser | QFile::ReadOther | QFile::ReadGroup); } if(firstrun){ qDebug() << "First time using Lumina!!"; } return (firstrun || newversion || newrelease); } int LDesktopUtils::VersionStringToNumber(QString version){ version = version.section("-",0,0); //trim any extra labels off the end int maj, mid, min; //major/middle/minor version numbers (..) maj = mid = min = 0; bool ok = true; maj = version.section(".",0,0).toInt(&ok); if(ok){ mid = version.section(".",1,1).toInt(&ok); }else{ maj = 0; } if(ok){ min = version.section(".",2,2).toInt(&ok); }else{ mid = 0; } if(!ok){ min = 0; } //Now assemble the number //NOTE: This format allows numbers to be anywhere from 0->999 without conflict return (maj*1000000 + mid*1000 + min); } void LDesktopUtils::MigrateDesktopSettings(QSettings *settings, QString fromID, QString toID){ //desktop-ID QStringList keys = settings->allKeys(); QStringList filter = keys.filter("desktop-"+fromID+"/"); for(int i=0; isetValue("desktop-"+toID+"/"+filter[i].section("/",1,-1), settings->value(filter[i])); settings->remove(filter[i]); } //panel_ID.[number] filter = keys.filter("panel_"+fromID+"."); for(int i=0; isetValue("panel_"+toID+"."+ filter[i].section("/",0,0).section(".",-1)+"/"+filter[i].section("/",1,-1), settings->value(filter[i])); settings->remove(filter[i]); } }