remove the shell from plasma-framework
This commit is contained in:
parent
dc17c39a95
commit
e6f71eebd1
@ -5,4 +5,3 @@ add_subdirectory(plasmapkg)
|
||||
add_subdirectory(platformstatus)
|
||||
add_subdirectory(scriptengines)
|
||||
add_subdirectory(plasmaquick)
|
||||
add_subdirectory(shell)
|
||||
|
@ -1,102 +0,0 @@
|
||||
project(plasma-shell)
|
||||
|
||||
|
||||
# Tell CMake to run moc when necessary:
|
||||
set(CMAKE_AUTOMOC ON)
|
||||
# As moc files are generated in the binary dir, tell CMake
|
||||
# to always look for includes there:
|
||||
set(CMAKE_INCLUDE_CURRENT_DIR ON)
|
||||
|
||||
set(CMAKE_MODULE_PATH ${ECM_MODULE_PATH})
|
||||
|
||||
find_package(Qt5Qml REQUIRED)
|
||||
find_package(Qt5Quick REQUIRED)
|
||||
find_package(Qt5DBus REQUIRED)
|
||||
find_package(Qt5Script REQUIRED)
|
||||
find_package(KF5CoreAddons REQUIRED)
|
||||
find_package(KF5Crash REQUIRED)
|
||||
find_package(KF5Solid REQUIRED)
|
||||
find_package(KF5Activities REQUIRED)
|
||||
find_package(KF5TextEditor) # not part of KF5.0
|
||||
find_package(KF5DBusAddons ${KF5_VERSION} REQUIRED)
|
||||
|
||||
set(HAVE_KTEXTEDITOR ${KF5TextEditor_FOUND})
|
||||
|
||||
configure_file(config-ktexteditor.h.cmake ${CMAKE_CURRENT_BINARY_DIR}/config-ktexteditor.h )
|
||||
|
||||
|
||||
set(scripting_SRC
|
||||
scripting/appinterface.cpp
|
||||
scripting/applet.cpp
|
||||
scripting/containment.cpp
|
||||
scripting/configgroup.cpp
|
||||
scripting/desktopscriptengine.cpp
|
||||
scripting/i18n.cpp
|
||||
scripting/panel.cpp
|
||||
scripting/rect.cpp
|
||||
scripting/scriptengine.cpp
|
||||
scripting/widget.cpp
|
||||
)
|
||||
|
||||
set(plasmashell_dbusXML dbus/org.kde.PlasmaShell.xml)
|
||||
qt5_add_dbus_adaptor(scripting_SRC ${plasmashell_dbusXML} shellcorona.h ShellCorona plasmashelladaptor)
|
||||
|
||||
set (plasma_shell_SRCS
|
||||
activity.cpp
|
||||
main.cpp
|
||||
containmentconfigview.cpp
|
||||
currentcontainmentactionsmodel.cpp
|
||||
desktopview.cpp
|
||||
kidenticongenerator.cpp
|
||||
panelview.cpp
|
||||
panelconfigview.cpp
|
||||
panelshadows.cpp
|
||||
shellcorona.cpp
|
||||
shellmanager.cpp
|
||||
osd.cpp
|
||||
${scripting_SRC}
|
||||
)
|
||||
if (KF5TextEditor_FOUND)
|
||||
set (plasma_shell_SRCS ${plasma_shell_SRCS}
|
||||
interactiveconsole.cpp
|
||||
)
|
||||
endif()
|
||||
add_executable(plasma-shell
|
||||
${plasma_shell_SRCS}
|
||||
)
|
||||
|
||||
target_link_libraries(plasma-shell
|
||||
Qt5::Quick
|
||||
Qt5::Qml
|
||||
Qt5::DBus
|
||||
KF5::KIOCore
|
||||
KF5::WindowSystem
|
||||
KF5::CoreAddons
|
||||
KF5::Crash
|
||||
KF5::Plasma
|
||||
KF5::PlasmaQuick
|
||||
Qt5::Script
|
||||
KF5::Solid
|
||||
KF5::Declarative
|
||||
KF5::I18n
|
||||
KF5::XmlGui
|
||||
KF5::IconThemes
|
||||
KF5::Activities
|
||||
KF5::GlobalAccel
|
||||
KF5::DBusAddons
|
||||
)
|
||||
if (TARGET KF5::TextEditor)
|
||||
target_link_libraries(plasma-shell KF5::TextEditor)
|
||||
endif()
|
||||
target_include_directories(plasma-shell PRIVATE "${CMAKE_BINARY_DIR}")
|
||||
|
||||
if(HAVE_X11)
|
||||
target_link_libraries(plasma-shell ${X11_LIBRARIES} ${XCB_XCB_LIBRARY} )
|
||||
target_link_libraries(plasma-shell Qt5::X11Extras)
|
||||
endif()
|
||||
|
||||
install(TARGETS plasma-shell ${INSTALL_TARGETS_DEFAULT_ARGS})
|
||||
install(FILES plasma-shell.desktop DESTINATION ${AUTOSTART_INSTALL_DIR})
|
||||
install( FILES dbus/org.kde.PlasmaShell.xml DESTINATION ${DBUS_INTERFACES_INSTALL_DIR} )
|
||||
|
||||
add_subdirectory(widgetexplorer)
|
@ -1,176 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010 Chani Armitage <chani@kde.org>
|
||||
*
|
||||
* 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 2,
|
||||
* 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "shellcorona.h"
|
||||
#include "kidenticongenerator.h"
|
||||
|
||||
#include <QAction>
|
||||
#include <QDebug>
|
||||
#include <QPixmap>
|
||||
#include <QString>
|
||||
#include <QSize>
|
||||
#include <QFile>
|
||||
|
||||
#include <kactioncollection.h>
|
||||
#include <kconfig.h>
|
||||
#include <kwindowsystem.h>
|
||||
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/Corona>
|
||||
|
||||
#include <kactivities/controller.h>
|
||||
#include <kactivities/consumer.h>
|
||||
|
||||
#include "activity.h"
|
||||
|
||||
Activity::Activity(const QString &id, Plasma::Corona *parent)
|
||||
: QObject(parent),
|
||||
m_id(id),
|
||||
m_plugin("org.kde.desktopcontainment"),//FIXME ask the corona
|
||||
m_info(new KActivities::Info(id, this)),
|
||||
m_activityConsumer(new KActivities::Consumer(this)),
|
||||
m_current(false)
|
||||
{
|
||||
m_name = m_info->name();
|
||||
m_icon = m_info->icon();
|
||||
|
||||
connect(m_info, SIGNAL(infoChanged()), this, SLOT(activityChanged()));
|
||||
connect(m_info, SIGNAL(stateChanged(KActivities::Info::State)), this, SIGNAL(stateChanged()));
|
||||
connect(m_info, SIGNAL(started()), this, SIGNAL(opened()));
|
||||
connect(m_info, SIGNAL(stopped()), this, SIGNAL(closed()));
|
||||
connect(m_info, SIGNAL(removed()), this, SIGNAL(removed()));
|
||||
connect(m_info, SIGNAL(removed()), this, SLOT(cleanupActivity()));
|
||||
|
||||
connect(m_activityConsumer, SIGNAL(currentActivityChanged(QString)), this, SLOT(checkIfCurrent()));
|
||||
checkIfCurrent();
|
||||
}
|
||||
|
||||
Activity::~Activity()
|
||||
{
|
||||
}
|
||||
|
||||
void Activity::activityChanged()
|
||||
{
|
||||
setName(m_info->name());
|
||||
setIcon(m_info->icon());
|
||||
}
|
||||
|
||||
QString Activity::id()
|
||||
{
|
||||
return m_id;
|
||||
}
|
||||
|
||||
QString Activity::name()
|
||||
{
|
||||
return m_name;
|
||||
}
|
||||
|
||||
QPixmap Activity::pixmap(const QSize &size)
|
||||
{
|
||||
if (m_info->isValid() && !m_info->icon().isEmpty()) {
|
||||
return QIcon::fromTheme(m_info->icon()).pixmap(size);
|
||||
} else {
|
||||
return KIdenticonGenerator::self()->generatePixmap(size.width(), m_id);
|
||||
}
|
||||
}
|
||||
|
||||
bool Activity::isCurrent()
|
||||
{
|
||||
return m_current;
|
||||
//TODO maybe plasmaapp should cache the current activity to reduce dbus calls?
|
||||
}
|
||||
|
||||
void Activity::checkIfCurrent()
|
||||
{
|
||||
const bool current = m_id == m_activityConsumer->currentActivity();
|
||||
if (current != m_current) {
|
||||
m_current = current;
|
||||
emit currentStatusChanged();
|
||||
}
|
||||
}
|
||||
|
||||
KActivities::Info::State Activity::state()
|
||||
{
|
||||
return m_info->state();
|
||||
}
|
||||
|
||||
void Activity::remove()
|
||||
{
|
||||
KActivities::Controller().removeActivity(m_id);
|
||||
}
|
||||
|
||||
void Activity::cleanupActivity()
|
||||
{
|
||||
const QString name = "activities/" + m_id;
|
||||
QFile::remove(QStandardPaths::writableLocation(QStandardPaths::DataLocation)+QChar('/')+name);
|
||||
}
|
||||
|
||||
void Activity::activate()
|
||||
{
|
||||
KActivities::Controller().setCurrentActivity(m_id);
|
||||
}
|
||||
|
||||
void Activity::setName(const QString &name)
|
||||
{
|
||||
m_name = name;
|
||||
}
|
||||
|
||||
void Activity::setIcon(const QString &icon)
|
||||
{
|
||||
m_icon = icon;
|
||||
}
|
||||
|
||||
void Activity::close()
|
||||
{
|
||||
KActivities::Controller().stopActivity(m_id);
|
||||
}
|
||||
|
||||
KConfigGroup Activity::config() const
|
||||
{
|
||||
const QString name = "activities/" + m_id;
|
||||
KConfig external(name, KConfig::SimpleConfig, QStandardPaths::GenericDataLocation);
|
||||
|
||||
//passing an empty string for the group name turns a kconfig into a kconfiggroup
|
||||
return external.group(QString());
|
||||
}
|
||||
|
||||
void Activity::open()
|
||||
{
|
||||
KActivities::Controller().startActivity(m_id);
|
||||
}
|
||||
|
||||
void Activity::setDefaultPlugin(const QString &plugin)
|
||||
{
|
||||
m_plugin = plugin;
|
||||
//FIXME save&restore this setting
|
||||
}
|
||||
|
||||
QString Activity::defaultPlugin() const
|
||||
{
|
||||
return m_plugin;
|
||||
}
|
||||
|
||||
const KActivities::Info * Activity::info() const
|
||||
{
|
||||
return m_info;
|
||||
}
|
||||
|
||||
#include "activity.moc"
|
||||
|
||||
// vim: sw=4 sts=4 et tw=100
|
@ -1,150 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010 Chani Armitage <chani@kde.org>
|
||||
*
|
||||
* 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 2,
|
||||
* 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef ACTIVITY_H
|
||||
#define ACTIVITY_H
|
||||
|
||||
#include <QObject>
|
||||
#include <QHash>
|
||||
|
||||
#include <kactivities/info.h>
|
||||
#include <kconfiggroup.h>
|
||||
|
||||
class QSize;
|
||||
class QString;
|
||||
class QPixmap;
|
||||
class KConfig;
|
||||
|
||||
namespace KActivities
|
||||
{
|
||||
class Consumer;
|
||||
} // namespace KActivities
|
||||
|
||||
|
||||
namespace Plasma
|
||||
{
|
||||
class Containment;
|
||||
class Corona;
|
||||
} // namespace Plasma
|
||||
|
||||
class DesktopCorona;
|
||||
|
||||
/**
|
||||
* This class represents one activity.
|
||||
* an activity has an ID and a name, from nepomuk.
|
||||
* it also is associated with one or more containments.
|
||||
*
|
||||
* do NOT construct these yourself; use DesktopCorona::activity()
|
||||
*/
|
||||
class Activity : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
Activity(const QString &id, Plasma::Corona *parent = 0);
|
||||
~Activity();
|
||||
|
||||
QString id();
|
||||
QString name();
|
||||
QPixmap pixmap(const QSize &size); //FIXME do we want diff. sizes? updates?
|
||||
|
||||
enum State {
|
||||
Invalid = KActivities::Info::Invalid,
|
||||
Running = KActivities::Info::Running,
|
||||
Starting = KActivities::Info::Starting,
|
||||
Stopped = KActivities::Info::Stopped,
|
||||
Stopping = KActivities::Info::Stopping,
|
||||
PreCreation = 32
|
||||
};
|
||||
|
||||
/**
|
||||
* whether this is the currently active activity
|
||||
*/
|
||||
bool isCurrent();
|
||||
|
||||
/**
|
||||
* state of the activity
|
||||
*/
|
||||
KActivities::Info::State state();
|
||||
|
||||
/**
|
||||
* set the plugin to use when creating new containments
|
||||
*/
|
||||
void setDefaultPlugin(const QString &plugin);
|
||||
|
||||
/**
|
||||
* The plugin to use when creating new containments
|
||||
*/
|
||||
QString defaultPlugin() const;
|
||||
|
||||
/**
|
||||
* @returns the info object for this activity
|
||||
*/
|
||||
const KActivities::Info * info() const;
|
||||
|
||||
KConfigGroup config() const;
|
||||
|
||||
Q_SIGNALS:
|
||||
void infoChanged();
|
||||
void stateChanged();
|
||||
void currentStatusChanged();
|
||||
|
||||
void removed();
|
||||
void opened();
|
||||
void closed();
|
||||
|
||||
public Q_SLOTS:
|
||||
void setName(const QString &name);
|
||||
void setIcon(const QString &icon);
|
||||
|
||||
/**
|
||||
* delete the activity forever
|
||||
*/
|
||||
void remove();
|
||||
|
||||
/**
|
||||
* make this activity the current activity
|
||||
*/
|
||||
void activate();
|
||||
|
||||
/**
|
||||
* save and remove all our containments
|
||||
*/
|
||||
void close();
|
||||
|
||||
/**
|
||||
* load the saved containment(s) for this activity
|
||||
*/
|
||||
void open();
|
||||
|
||||
private Q_SLOTS:
|
||||
void activityChanged();
|
||||
void checkIfCurrent();
|
||||
void cleanupActivity();
|
||||
|
||||
private:
|
||||
QString m_id;
|
||||
QString m_name;
|
||||
QString m_icon;
|
||||
QString m_plugin;
|
||||
KActivities::Info *m_info;
|
||||
KActivities::Consumer *m_activityConsumer;
|
||||
bool m_current;
|
||||
};
|
||||
|
||||
#endif
|
@ -1,2 +0,0 @@
|
||||
#cmakedefine01 HAVE_KTEXTEDITOR
|
||||
|
@ -1,185 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "currentcontainmentactionsmodel.h"
|
||||
#include "containmentconfigview.h"
|
||||
#include "configmodel.h"
|
||||
|
||||
#include <kdeclarative/configpropertymap.h>
|
||||
|
||||
#include <QDebug>
|
||||
#include <QDir>
|
||||
#include <QQmlContext>
|
||||
#include <QQmlEngine>
|
||||
#include <QQmlComponent>
|
||||
|
||||
#include <klocalizedstring.h>
|
||||
|
||||
#include <Plasma/Corona>
|
||||
#include <Plasma/ContainmentActions>
|
||||
#include <Plasma/PluginLoader>
|
||||
#include <qstandardpaths.h>
|
||||
|
||||
//////////////////////////////ContainmentConfigView
|
||||
ContainmentConfigView::ContainmentConfigView(Plasma::Containment *cont, QWindow *parent)
|
||||
: ConfigView(cont, parent),
|
||||
m_containment(cont),
|
||||
m_wallpaperConfigModel(0),
|
||||
m_containmentActionConfigModel(0),
|
||||
m_currentContainmentActionsModel(0),
|
||||
m_currentWallpaperConfig(0),
|
||||
m_ownWallpaperConfig(0)
|
||||
{
|
||||
qmlRegisterType<QAbstractItemModel>();
|
||||
engine()->rootContext()->setContextProperty("configDialog", this);
|
||||
setCurrentWallpaper(cont->containment()->wallpaper());
|
||||
|
||||
Plasma::Package pkg = Plasma::PluginLoader::self()->loadPackage("Plasma/Wallpaper");
|
||||
pkg.setPath(m_containment->wallpaper());
|
||||
QFile file(pkg.filePath("config", "main.xml"));
|
||||
KConfigGroup cfg = m_containment->config();
|
||||
cfg = KConfigGroup(&cfg, "Wallpaper");
|
||||
|
||||
syncWallpaperObjects();
|
||||
}
|
||||
|
||||
ContainmentConfigView::~ContainmentConfigView()
|
||||
{
|
||||
}
|
||||
|
||||
void ContainmentConfigView::init()
|
||||
{
|
||||
setSource(QUrl::fromLocalFile(m_containment->corona()->package().filePath("containmentconfigurationui")));
|
||||
}
|
||||
|
||||
PlasmaQuick::ConfigModel *ContainmentConfigView::containmentActionConfigModel()
|
||||
{
|
||||
if (!m_containmentActionConfigModel) {
|
||||
m_containmentActionConfigModel = new PlasmaQuick::ConfigModel(this);
|
||||
|
||||
KPluginInfo::List actions = Plasma::PluginLoader::self()->listContainmentActionsInfo(QString());
|
||||
|
||||
Plasma::Package pkg = Plasma::PluginLoader::self()->loadPackage("Plasma/Generic");
|
||||
|
||||
foreach (const KPluginInfo &info, actions) {
|
||||
pkg.setDefaultPackageRoot(QStandardPaths::locate(QStandardPaths::GenericDataLocation, "plasma/containmentactions", QStandardPaths::LocateDirectory));
|
||||
m_containmentActionConfigModel->appendCategory(info.icon(), info.name(), pkg.filePath("ui", "config.qml"), info.pluginName());
|
||||
}
|
||||
|
||||
}
|
||||
return m_containmentActionConfigModel;
|
||||
}
|
||||
|
||||
QAbstractItemModel *ContainmentConfigView::currentContainmentActionsModel()
|
||||
{
|
||||
if (!m_currentContainmentActionsModel) {
|
||||
m_currentContainmentActionsModel = new CurrentContainmentActionsModel(m_containment, this);
|
||||
}
|
||||
return m_currentContainmentActionsModel;
|
||||
}
|
||||
|
||||
PlasmaQuick::ConfigModel *ContainmentConfigView::wallpaperConfigModel()
|
||||
{
|
||||
if (!m_wallpaperConfigModel) {
|
||||
m_wallpaperConfigModel = new PlasmaQuick::ConfigModel(this);
|
||||
QStringList dirs(QStandardPaths::locateAll(QStandardPaths::GenericDataLocation, "plasma/wallpapers", QStandardPaths::LocateDirectory));
|
||||
Plasma::Package pkg = Plasma::PluginLoader::self()->loadPackage("Plasma/Generic");
|
||||
foreach (const QString &dirPath, dirs) {
|
||||
QDir dir(dirPath);
|
||||
pkg.setDefaultPackageRoot(dirPath);
|
||||
QStringList packages;
|
||||
|
||||
foreach (const QString &sdir, dir.entryList(QDir::AllDirs | QDir::Readable)) {
|
||||
QString metadata = dirPath + '/' + sdir + "/metadata.desktop";
|
||||
if (QFile::exists(metadata)) {
|
||||
packages << sdir;
|
||||
}
|
||||
}
|
||||
|
||||
foreach (const QString &package, packages) {
|
||||
pkg.setPath(package);
|
||||
if (!pkg.isValid()) {
|
||||
continue;
|
||||
}
|
||||
m_wallpaperConfigModel->appendCategory(pkg.metadata().icon(), pkg.metadata().name(), pkg.filePath("ui", "config.qml"), package);
|
||||
}
|
||||
}
|
||||
}
|
||||
return m_wallpaperConfigModel;
|
||||
}
|
||||
|
||||
KDeclarative::ConfigPropertyMap *ContainmentConfigView::wallpaperConfiguration() const
|
||||
{
|
||||
return m_currentWallpaperConfig;
|
||||
}
|
||||
|
||||
QString ContainmentConfigView::currentWallpaper() const
|
||||
{
|
||||
return m_currentWallpaper;
|
||||
}
|
||||
|
||||
void ContainmentConfigView::setCurrentWallpaper(const QString &wallpaper)
|
||||
{
|
||||
if (m_currentWallpaper == wallpaper) {
|
||||
return;
|
||||
}
|
||||
|
||||
delete m_ownWallpaperConfig;
|
||||
m_ownWallpaperConfig = 0;
|
||||
|
||||
if (m_containment->wallpaper() == wallpaper) {
|
||||
syncWallpaperObjects();
|
||||
} else {
|
||||
|
||||
//we have to construct an independent ConfigPropertyMap when we want to configure wallpapers that are not the current one
|
||||
Plasma::Package pkg = Plasma::PluginLoader::self()->loadPackage("Plasma/Generic");
|
||||
pkg.setDefaultPackageRoot("plasma/wallpapers");
|
||||
pkg.setPath(wallpaper);
|
||||
QFile file(pkg.filePath("config", "main.xml"));
|
||||
KConfigGroup cfg = m_containment->config();
|
||||
cfg = KConfigGroup(&cfg, "Wallpaper");
|
||||
m_currentWallpaperConfig = m_ownWallpaperConfig = new KDeclarative::ConfigPropertyMap(new Plasma::ConfigLoader(&cfg, &file), this);
|
||||
}
|
||||
|
||||
m_currentWallpaper = wallpaper;
|
||||
emit currentWallpaperChanged();
|
||||
emit wallpaperConfigurationChanged();
|
||||
}
|
||||
|
||||
void ContainmentConfigView::applyWallpaper()
|
||||
{
|
||||
m_containment->setWallpaper(m_currentWallpaper);
|
||||
|
||||
delete m_ownWallpaperConfig;
|
||||
m_ownWallpaperConfig = 0;
|
||||
|
||||
syncWallpaperObjects();
|
||||
emit wallpaperConfigurationChanged();
|
||||
}
|
||||
|
||||
void ContainmentConfigView::syncWallpaperObjects()
|
||||
{
|
||||
QObject *wallpaperGraphicsObject = m_containment->property("wallpaperGraphicsObject").value<QObject *>();
|
||||
engine()->rootContext()->setContextProperty("wallpaper", wallpaperGraphicsObject);
|
||||
|
||||
//FIXME: why m_wallpaperGraphicsObject->property("configuration").value<ConfigPropertyMap *>() doesn't work?
|
||||
m_currentWallpaperConfig = static_cast<KDeclarative::ConfigPropertyMap *>(wallpaperGraphicsObject->property("configuration").value<QObject *>());
|
||||
}
|
||||
|
||||
#include "private/moc_containmentconfigview.cpp"
|
@ -1,80 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef CONTAINMENTCONFIGVIEW_H
|
||||
#define CONTAINMENTCONFIGVIEW_H
|
||||
|
||||
|
||||
#include "configview.h"
|
||||
|
||||
|
||||
namespace Plasma {
|
||||
class Containment;
|
||||
}
|
||||
|
||||
class QAbstractItemModel;
|
||||
class CurrentContainmentActionsModel;
|
||||
|
||||
namespace KDeclarative {
|
||||
class ConfigPropertyMap;
|
||||
}
|
||||
|
||||
//TODO: out of the library?
|
||||
class ContainmentConfigView : public PlasmaQuick::ConfigView
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(PlasmaQuick::ConfigModel *containmentActionConfigModel READ containmentActionConfigModel CONSTANT)
|
||||
Q_PROPERTY(QAbstractItemModel *currentContainmentActionsModel READ currentContainmentActionsModel CONSTANT)
|
||||
Q_PROPERTY(PlasmaQuick::ConfigModel *wallpaperConfigModel READ wallpaperConfigModel CONSTANT)
|
||||
Q_PROPERTY(KDeclarative::ConfigPropertyMap *wallpaperConfiguration READ wallpaperConfiguration NOTIFY wallpaperConfigurationChanged)
|
||||
Q_PROPERTY(QString currentWallpaper READ currentWallpaper WRITE setCurrentWallpaper NOTIFY currentWallpaperChanged)
|
||||
|
||||
public:
|
||||
ContainmentConfigView(Plasma::Containment *interface, QWindow *parent = 0);
|
||||
virtual ~ContainmentConfigView();
|
||||
|
||||
virtual void init();
|
||||
|
||||
PlasmaQuick::ConfigModel *containmentActionConfigModel();
|
||||
QAbstractItemModel *currentContainmentActionsModel();
|
||||
PlasmaQuick::ConfigModel *wallpaperConfigModel();
|
||||
QString currentWallpaper() const;
|
||||
void setCurrentWallpaper(const QString &wallpaper);
|
||||
KDeclarative::ConfigPropertyMap *wallpaperConfiguration() const;
|
||||
|
||||
Q_INVOKABLE void applyWallpaper();
|
||||
|
||||
Q_SIGNALS:
|
||||
void currentWallpaperChanged();
|
||||
void wallpaperConfigurationChanged();
|
||||
|
||||
protected:
|
||||
void syncWallpaperObjects();
|
||||
|
||||
private:
|
||||
Plasma::Containment *m_containment;
|
||||
PlasmaQuick::ConfigModel *m_wallpaperConfigModel;
|
||||
PlasmaQuick::ConfigModel *m_containmentActionConfigModel;
|
||||
CurrentContainmentActionsModel *m_currentContainmentActionsModel;
|
||||
QString m_currentWallpaper;
|
||||
KDeclarative::ConfigPropertyMap *m_currentWallpaperConfig;
|
||||
KDeclarative::ConfigPropertyMap *m_ownWallpaperConfig;
|
||||
};
|
||||
|
||||
#endif // multiple inclusion guard
|
@ -1,262 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "currentcontainmentactionsmodel.h"
|
||||
|
||||
#include <QMouseEvent>
|
||||
|
||||
#include <QDebug>
|
||||
#include <QDialog>
|
||||
#include <QVBoxLayout>
|
||||
#include <QDialogButtonBox>
|
||||
|
||||
#include <kaboutdata.h>
|
||||
#include <kaboutapplicationdialog.h>
|
||||
#include <klocalizedstring.h>
|
||||
|
||||
#include <Plasma/Corona>
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/ContainmentActions>
|
||||
#include <Plasma/PluginLoader>
|
||||
|
||||
|
||||
CurrentContainmentActionsModel::CurrentContainmentActionsModel(Plasma::Containment *cotainment, QObject *parent)
|
||||
: QStandardItemModel(parent),
|
||||
m_containment(cotainment),
|
||||
m_tempConfigParent(QString(), KConfig::SimpleConfig)
|
||||
{
|
||||
QHash<int, QByteArray> roleNames;
|
||||
roleNames[ActionRole] = "action";
|
||||
roleNames[PluginNameRole] = "pluginName";
|
||||
roleNames[HasConfigurationInterfaceRole] = "hasConfigurationInterface";
|
||||
|
||||
setRoleNames(roleNames);
|
||||
|
||||
m_baseCfg = KConfigGroup(m_containment->corona()->config(), "ActionPlugins");
|
||||
m_baseCfg = KConfigGroup(&m_baseCfg, QString::number(m_containment->containmentType()));
|
||||
|
||||
QHash<QString, Plasma::ContainmentActions*> actions = cotainment->containmentActions();
|
||||
|
||||
|
||||
QHashIterator<QString, Plasma::ContainmentActions*> i(actions);
|
||||
while (i.hasNext()) {
|
||||
i.next();
|
||||
|
||||
QStandardItem *item = new QStandardItem();
|
||||
item->setData(i.key(), ActionRole);
|
||||
item->setData(i.value()->pluginInfo().pluginName(), PluginNameRole);
|
||||
|
||||
m_plugins[i.key()] = Plasma::PluginLoader::self()->loadContainmentActions(m_containment, i.value()->pluginInfo().pluginName());
|
||||
m_plugins[i.key()]->setContainment(m_containment);
|
||||
KConfigGroup cfg(&m_baseCfg, i.key());
|
||||
m_plugins[i.key()]->restore(cfg);
|
||||
item->setData(m_plugins[i.key()]->pluginInfo().property("X-Plasma-HasConfigurationInterface").toBool(), HasConfigurationInterfaceRole);
|
||||
|
||||
appendRow(item);
|
||||
}
|
||||
}
|
||||
|
||||
CurrentContainmentActionsModel::~CurrentContainmentActionsModel()
|
||||
{
|
||||
}
|
||||
|
||||
QString CurrentContainmentActionsModel::mouseEventString(int mouseButton, int modifiers)
|
||||
{
|
||||
QMouseEvent *mouse = new QMouseEvent(QEvent::MouseButtonRelease, QPoint(), (Qt::MouseButton)mouseButton, (Qt::MouseButton)mouseButton, (Qt::KeyboardModifiers) modifiers);
|
||||
|
||||
QString string = Plasma::ContainmentActions::eventToString(mouse);
|
||||
|
||||
delete mouse;
|
||||
|
||||
return string;
|
||||
}
|
||||
|
||||
QString CurrentContainmentActionsModel::wheelEventString(const QPointF &delta, int mouseButtons, int modifiers)
|
||||
{
|
||||
QWheelEvent *wheel = new QWheelEvent(QPointF(), QPointF(), delta.toPoint(), QPoint(), 0, Qt::Vertical, (Qt::MouseButtons)mouseButtons, (Qt::KeyboardModifiers) modifiers);
|
||||
|
||||
QString string = Plasma::ContainmentActions::eventToString(wheel);
|
||||
|
||||
delete wheel;
|
||||
|
||||
return string;
|
||||
}
|
||||
|
||||
bool CurrentContainmentActionsModel::isTriggerUsed(const QString &trigger)
|
||||
{
|
||||
return m_plugins.contains(trigger);
|
||||
}
|
||||
|
||||
bool CurrentContainmentActionsModel::append(const QString &action, const QString &plugin)
|
||||
{
|
||||
if (m_plugins.contains(action)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
QStandardItem *item = new QStandardItem();
|
||||
item->setData(action, ActionRole);
|
||||
item->setData(plugin, PluginNameRole);
|
||||
|
||||
m_plugins[action] = Plasma::PluginLoader::self()->loadContainmentActions(m_containment, plugin);
|
||||
m_plugins[action]->setContainment(m_containment);
|
||||
//empty config: the new one will ne in default state
|
||||
KConfigGroup tempConfig(&m_tempConfigParent, "test");
|
||||
m_plugins[action]->restore(tempConfig);
|
||||
item->setData(m_plugins[action]->pluginInfo().property("X-Plasma-HasConfigurationInterface").toBool(), HasConfigurationInterfaceRole);
|
||||
m_removedTriggers.removeAll(action);
|
||||
|
||||
appendRow(item);
|
||||
return true;
|
||||
}
|
||||
|
||||
void CurrentContainmentActionsModel::update(int row, const QString &action, const QString &plugin)
|
||||
{
|
||||
const QString oldPlugin = itemData(index(row, 0)).value(PluginNameRole).toString();
|
||||
const QString oldTrigger = itemData(index(row, 0)).value(ActionRole).toString();
|
||||
|
||||
if (oldTrigger == action && oldPlugin == plugin) {
|
||||
return;
|
||||
}
|
||||
|
||||
QModelIndex idx = index(row, 0);
|
||||
|
||||
if (idx.isValid()) {
|
||||
setData(idx, action, ActionRole);
|
||||
setData(idx, plugin, PluginNameRole);
|
||||
|
||||
delete m_plugins[oldTrigger];
|
||||
m_plugins.remove(oldTrigger);
|
||||
|
||||
if (oldPlugin != plugin) {
|
||||
m_removedTriggers << oldTrigger;
|
||||
}
|
||||
|
||||
if (!m_plugins.contains(action) || oldPlugin != plugin) {
|
||||
delete m_plugins[action];
|
||||
m_plugins[action] = Plasma::PluginLoader::self()->loadContainmentActions(m_containment, plugin);
|
||||
m_plugins[action]->setContainment(m_containment);
|
||||
//empty config: the new one will ne in default state
|
||||
KConfigGroup tempConfig(&m_tempConfigParent, "test");
|
||||
m_plugins[action]->restore(tempConfig);
|
||||
setData(idx, m_plugins[action]->pluginInfo().property("X-Plasma-HasConfigurationInterface").toBool(), HasConfigurationInterfaceRole);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CurrentContainmentActionsModel::remove(int row)
|
||||
{
|
||||
const QString action = itemData(index(row, 0)).value(ActionRole).toString();
|
||||
removeRows(row, 1);
|
||||
|
||||
if (m_plugins.contains(action)) {
|
||||
delete m_plugins[action];
|
||||
m_plugins.remove(action);
|
||||
m_removedTriggers << action;
|
||||
}
|
||||
}
|
||||
|
||||
void CurrentContainmentActionsModel::showConfiguration(int row)
|
||||
{
|
||||
const QString action = itemData(index(row, 0)).value(ActionRole).toString();
|
||||
|
||||
if (!m_plugins.contains(action)) {
|
||||
return;
|
||||
}
|
||||
|
||||
QDialog *configDlg = new QDialog();
|
||||
configDlg->setAttribute(Qt::WA_DeleteOnClose);
|
||||
QLayout *lay = new QVBoxLayout(configDlg);
|
||||
configDlg->setLayout(lay);
|
||||
configDlg->setWindowModality(Qt::WindowModal);
|
||||
|
||||
Plasma::ContainmentActions *pluginInstance = m_plugins[action];
|
||||
//put the config in the dialog
|
||||
QWidget *w = pluginInstance->createConfigurationInterface(configDlg);
|
||||
QString title;
|
||||
if (w) {
|
||||
lay->addWidget(w);
|
||||
title = w->windowTitle();
|
||||
}
|
||||
|
||||
configDlg->setWindowTitle(title.isEmpty() ? i18n("Configure Plugin") :title);
|
||||
//put buttons below
|
||||
QDialogButtonBox *buttons = new QDialogButtonBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel,
|
||||
Qt::Horizontal, configDlg);
|
||||
lay->addWidget(buttons);
|
||||
|
||||
QObject::connect(buttons, &QDialogButtonBox::accepted,
|
||||
[configDlg, pluginInstance] () {
|
||||
pluginInstance->configurationAccepted();
|
||||
configDlg->deleteLater();
|
||||
});
|
||||
|
||||
QObject::connect(buttons, &QDialogButtonBox::rejected,
|
||||
[configDlg] () {
|
||||
configDlg->deleteLater();
|
||||
});
|
||||
|
||||
|
||||
configDlg->show();
|
||||
}
|
||||
|
||||
void CurrentContainmentActionsModel::showAbout(int row)
|
||||
{
|
||||
const QString action = itemData(index(row, 0)).value(ActionRole).toString();
|
||||
|
||||
if (!m_plugins.contains(action)) {
|
||||
return;
|
||||
}
|
||||
|
||||
KPluginInfo info = m_plugins[action]->pluginInfo();
|
||||
|
||||
KAboutData aboutData(info.name().toUtf8(),
|
||||
info.name().toUtf8(),
|
||||
ki18n(info.name().toUtf8()).toString(),
|
||||
info.version().toUtf8(), ki18n(info.comment().toUtf8()).toString(),
|
||||
KAboutLicense::byKeyword(info.license()).key(), ki18n(QByteArray()).toString(), ki18n(QByteArray()).toString(), info.website().toLatin1(),
|
||||
info.email().toLatin1());
|
||||
|
||||
aboutData.setProgramIconName(info.icon());
|
||||
|
||||
aboutData.addAuthor(ki18n(info.author().toUtf8()).toString(), ki18n(QByteArray()).toString(), info.email().toLatin1());
|
||||
|
||||
KAboutApplicationDialog *aboutDialog = new KAboutApplicationDialog(aboutData, qobject_cast<QWidget*>(parent()));
|
||||
aboutDialog->show();
|
||||
}
|
||||
|
||||
void CurrentContainmentActionsModel::save()
|
||||
{
|
||||
|
||||
foreach (const QString &removedTrigger, m_removedTriggers) {
|
||||
m_containment->setContainmentActions(removedTrigger, QString());
|
||||
}
|
||||
m_removedTriggers.clear();
|
||||
|
||||
QHashIterator<QString, Plasma::ContainmentActions*> i(m_plugins);
|
||||
while (i.hasNext()) {
|
||||
i.next();
|
||||
|
||||
KConfigGroup cfg(&m_baseCfg, i.key());
|
||||
i.value()->save(cfg);
|
||||
|
||||
m_containment->setContainmentActions(i.key(), i.value()->pluginInfo().pluginName());
|
||||
}
|
||||
}
|
||||
|
||||
#include "private/moc_currentcontainmentactionsmodel.cpp"
|
@ -1,68 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef CURRENTCONTAINMENTACTIONSMODEL_H
|
||||
#define CURRENTCONTAINMENTACTIONSMODEL_H
|
||||
|
||||
#include <QStandardItemModel>
|
||||
|
||||
#include <kconfig.h>
|
||||
#include <kconfiggroup.h>
|
||||
|
||||
namespace Plasma {
|
||||
class Containment;
|
||||
class ContainmentActions;
|
||||
}
|
||||
|
||||
//This model load the data about available containment actions plugins, such as context menus that can be loaded on mouse click
|
||||
//TODO: out of the library?
|
||||
class CurrentContainmentActionsModel : public QStandardItemModel
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
enum Roles {
|
||||
ActionRole = Qt::UserRole+1,
|
||||
PluginNameRole,
|
||||
HasConfigurationInterfaceRole
|
||||
};
|
||||
|
||||
CurrentContainmentActionsModel(Plasma::Containment *cotainment, QObject *parent = 0);
|
||||
~CurrentContainmentActionsModel();
|
||||
|
||||
Q_INVOKABLE bool isTriggerUsed(const QString &trigger);
|
||||
Q_INVOKABLE QString mouseEventString(int mouseButtons, int modifiers);
|
||||
Q_INVOKABLE QString wheelEventString(const QPointF &delta, int mouseButtons, int modifiers);
|
||||
Q_INVOKABLE bool append(const QString &action, const QString &plugin);
|
||||
Q_INVOKABLE void update(int row, const QString &action, const QString &plugin);
|
||||
Q_INVOKABLE void remove(int row);
|
||||
Q_INVOKABLE void showConfiguration(int row);
|
||||
Q_INVOKABLE void showAbout(int row);
|
||||
Q_INVOKABLE void save();
|
||||
|
||||
private:
|
||||
Plasma::Containment *m_containment;
|
||||
QHash<QString, Plasma::ContainmentActions *> m_plugins;
|
||||
KConfigGroup m_baseCfg;
|
||||
KConfigGroup m_tempConfig;
|
||||
KConfig m_tempConfigParent;
|
||||
QStringList m_removedTriggers;
|
||||
};
|
||||
|
||||
#endif
|
@ -1,15 +0,0 @@
|
||||
<!DOCTYPE node PUBLIC "-//freedesktop//DTD D-BUS Object Introspection 1.0//EN" "http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd">
|
||||
<node>
|
||||
<interface name="org.kde.PlasmaShell">
|
||||
<method name="toggleDashboard">
|
||||
</method>
|
||||
<method name="setDashboardShown">
|
||||
<arg name="show" type="b" direction="in"/>
|
||||
</method>
|
||||
<method name="showInteractiveConsole">
|
||||
</method>
|
||||
<method name="loadScriptInInteractiveConsole">
|
||||
<arg name="script" type="s" direction="in"/>
|
||||
</method>
|
||||
</interface>
|
||||
</node>
|
@ -1,180 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* 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 2 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, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "desktopview.h"
|
||||
#include "containmentconfigview.h"
|
||||
#include "shellcorona.h"
|
||||
#include "shellmanager.h"
|
||||
|
||||
#include <QQmlEngine>
|
||||
#include <QQmlContext>
|
||||
#include <QScreen>
|
||||
|
||||
#include <kwindowsystem.h>
|
||||
#include <klocalizedstring.h>
|
||||
|
||||
#include <Plasma/Package>
|
||||
|
||||
DesktopView::DesktopView(ShellCorona *corona, QScreen *screen)
|
||||
: PlasmaQuick::View(corona, 0),
|
||||
m_stayBehind(false),
|
||||
m_fillScreen(false),
|
||||
m_dashboardShown(false)
|
||||
{
|
||||
setTitle(i18n("Desktop"));
|
||||
setIcon(QIcon::fromTheme("user-desktop"));
|
||||
setScreen(screen);
|
||||
engine()->rootContext()->setContextProperty("desktop", this);
|
||||
setSource(QUrl::fromLocalFile(corona->package().filePath("views", "Desktop.qml")));
|
||||
|
||||
connect(this, &QWindow::xChanged, [=]() {
|
||||
if (m_fillScreen) {
|
||||
setGeometry(this->screen()->geometry());
|
||||
}
|
||||
});
|
||||
connect(this, &QWindow::yChanged, [=]() {
|
||||
if (m_fillScreen) {
|
||||
setGeometry(this->screen()->geometry());
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
DesktopView::~DesktopView()
|
||||
{
|
||||
}
|
||||
|
||||
bool DesktopView::stayBehind() const
|
||||
{
|
||||
return m_stayBehind;
|
||||
}
|
||||
|
||||
void DesktopView::setStayBehind(bool stayBehind)
|
||||
{
|
||||
if (ShellManager::s_forceWindowed || stayBehind == m_stayBehind) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (stayBehind) {
|
||||
KWindowSystem::setType(winId(), NET::Desktop);
|
||||
} else {
|
||||
KWindowSystem::setType(winId(), NET::Normal);
|
||||
}
|
||||
|
||||
m_stayBehind = stayBehind;
|
||||
emit stayBehindChanged();
|
||||
}
|
||||
|
||||
bool DesktopView::fillScreen() const
|
||||
{
|
||||
return m_fillScreen;
|
||||
}
|
||||
|
||||
void DesktopView::setFillScreen(bool fillScreen)
|
||||
{
|
||||
if (ShellManager::s_forceWindowed || fillScreen == m_fillScreen) {
|
||||
return;
|
||||
}
|
||||
|
||||
m_fillScreen = fillScreen;
|
||||
|
||||
if (m_fillScreen) {
|
||||
setGeometry(screen()->geometry());
|
||||
setMinimumSize(screen()->geometry().size());
|
||||
setMaximumSize(screen()->geometry().size());
|
||||
connect(screen(), &QScreen::geometryChanged, this, static_cast<void (QWindow::*)(const QRect&)>(&QWindow::setGeometry));
|
||||
} else {
|
||||
disconnect(screen(), &QScreen::geometryChanged, this, static_cast<void (QWindow::*)(const QRect&)>(&QWindow::setGeometry));
|
||||
}
|
||||
|
||||
emit fillScreenChanged();
|
||||
}
|
||||
|
||||
void DesktopView::setDashboardShown(bool shown)
|
||||
{
|
||||
if (shown) {
|
||||
if (m_stayBehind) {
|
||||
KWindowSystem::setType(winId(), NET::Normal);
|
||||
KWindowSystem::clearState(winId(), NET::SkipTaskbar|NET::KeepBelow);
|
||||
}
|
||||
setFlags(Qt::FramelessWindowHint | Qt::CustomizeWindowHint);
|
||||
|
||||
raise();
|
||||
KWindowSystem::raiseWindow(winId());
|
||||
KWindowSystem::forceActiveWindow(winId());
|
||||
|
||||
QObject *wpGraphicObject = containment()->property("wallpaperGraphicsObject").value<QObject *>();
|
||||
if (wpGraphicObject) {
|
||||
wpGraphicObject->setProperty("opacity", 0.3);
|
||||
}
|
||||
} else {
|
||||
if (m_stayBehind) {
|
||||
KWindowSystem::setType(winId(), NET::Desktop);
|
||||
KWindowSystem::setState(winId(), NET::SkipTaskbar|NET::SkipPager|NET::KeepBelow);
|
||||
}
|
||||
lower();
|
||||
KWindowSystem::lowerWindow(winId());
|
||||
|
||||
QObject *wpGraphicObject = containment()->property("wallpaperGraphicsObject").value<QObject *>();
|
||||
if (wpGraphicObject) {
|
||||
wpGraphicObject->setProperty("opacity", 1);
|
||||
}
|
||||
}
|
||||
|
||||
m_dashboardShown = shown;
|
||||
}
|
||||
|
||||
bool DesktopView::event(QEvent *e)
|
||||
{
|
||||
if (e->type() == QEvent::Close) {
|
||||
//prevent ALT+F4 from killing the shell
|
||||
e->ignore();
|
||||
return true;
|
||||
}
|
||||
|
||||
return PlasmaQuick::View::event(e);
|
||||
}
|
||||
|
||||
bool DesktopView::isDashboardShown() const
|
||||
{
|
||||
return m_dashboardShown;
|
||||
}
|
||||
|
||||
|
||||
void DesktopView::showConfigurationInterface(Plasma::Applet *applet)
|
||||
{
|
||||
if (m_configView) {
|
||||
m_configView.data()->hide();
|
||||
m_configView.data()->deleteLater();
|
||||
}
|
||||
|
||||
if (!applet || !applet->containment()) {
|
||||
return;
|
||||
}
|
||||
|
||||
Plasma::Containment *cont = qobject_cast<Plasma::Containment *>(applet);
|
||||
|
||||
if (cont) {
|
||||
m_configView = new ContainmentConfigView(cont);
|
||||
} else {
|
||||
m_configView = new PlasmaQuick::ConfigView(applet);
|
||||
}
|
||||
m_configView.data()->init();
|
||||
m_configView.data()->show();
|
||||
}
|
||||
|
||||
#include "moc_desktopview.cpp"
|
@ -1,68 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* 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 2 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, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef DESKTOVIEW_H
|
||||
#define DESKTOVIEW_H
|
||||
|
||||
|
||||
#include <view.h>
|
||||
#include "panelconfigview.h"
|
||||
#include <QtCore/qpointer.h>
|
||||
|
||||
class ShellCorona;
|
||||
|
||||
class DesktopView : public PlasmaQuick::View
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(bool stayBehind READ stayBehind WRITE setStayBehind NOTIFY stayBehindChanged)
|
||||
Q_PROPERTY(bool fillScreen READ fillScreen WRITE setFillScreen NOTIFY fillScreenChanged)
|
||||
|
||||
public:
|
||||
explicit DesktopView(ShellCorona *corona, QScreen *screen);
|
||||
virtual ~DesktopView();
|
||||
|
||||
bool stayBehind() const;
|
||||
void setStayBehind(bool stayBehind);
|
||||
|
||||
bool fillScreen() const;
|
||||
void setFillScreen(bool fillScreen);
|
||||
|
||||
void setDashboardShown(bool shown);
|
||||
bool isDashboardShown() const;
|
||||
|
||||
protected:
|
||||
bool event(QEvent *e);
|
||||
|
||||
protected Q_SLOTS:
|
||||
/**
|
||||
* It will be called when the configuration is requested
|
||||
*/
|
||||
virtual void showConfigurationInterface(Plasma::Applet *applet);
|
||||
|
||||
Q_SIGNALS:
|
||||
void stayBehindChanged();
|
||||
void fillScreenChanged();
|
||||
|
||||
private:
|
||||
QPointer<PlasmaQuick::ConfigView> m_configView;
|
||||
bool m_stayBehind : 1;
|
||||
bool m_fillScreen : 1;
|
||||
bool m_dashboardShown : 1;
|
||||
};
|
||||
|
||||
#endif // DESKTOVIEW_H
|
@ -1,576 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
* Copyright 2014 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "interactiveconsole.h"
|
||||
|
||||
#include <QDateTime>
|
||||
#include <QDBusConnection>
|
||||
#include <QDBusMessage>
|
||||
#include <QFile>
|
||||
#include <QHBoxLayout>
|
||||
#include <QLabel>
|
||||
#include <QSplitter>
|
||||
#include <QToolButton>
|
||||
#include <QVBoxLayout>
|
||||
#include <QStandardPaths>
|
||||
#include <QIcon>
|
||||
|
||||
#include <QFileDialog>
|
||||
#include <QAction>
|
||||
#include <KShell>
|
||||
#include <KMessageBox>
|
||||
#include <klocalizedstring.h>
|
||||
#include <QMenu>
|
||||
#include <KServiceTypeTrader>
|
||||
#include <KStandardAction>
|
||||
#include <QTextBrowser>
|
||||
#include <KTextEdit>
|
||||
#include <KTextEditor/ConfigInterface>
|
||||
#include <KTextEditor/Document>
|
||||
#include <KTextEditor/View>
|
||||
#include <KToolBar>
|
||||
|
||||
#include <Plasma/Package>
|
||||
|
||||
#include "scripting/desktopscriptengine.h"
|
||||
#include "shellpluginloader.h"
|
||||
#include "shellcorona.h"
|
||||
|
||||
//TODO:
|
||||
// interative help?
|
||||
static const QString s_autosaveFileName("interactiveconsoleautosave.js");
|
||||
static const QString s_kwinService = "org.kde.kwin.Scripting";
|
||||
|
||||
InteractiveConsole::InteractiveConsole(ShellCorona *corona, QWidget *parent)
|
||||
: QDialog(parent),
|
||||
m_corona(corona),
|
||||
m_splitter(new QSplitter(Qt::Vertical, this)),
|
||||
m_editorPart(0),
|
||||
m_editor(0),
|
||||
m_output(0),
|
||||
m_loadAction(KStandardAction::open(this, SLOT(openScriptFile()), this)),
|
||||
m_saveAction(KStandardAction::saveAs(this, SLOT(saveScript()), this)),
|
||||
m_clearAction(KStandardAction::clear(this, SLOT(clearEditor()), this)),
|
||||
m_executeAction(new QAction(QIcon::fromTheme("system-run"), i18n("&Execute"), this)),
|
||||
m_plasmaAction(new QAction(QIcon::fromTheme("plasma"), i18nc("Toolbar Button to switch to Plasma Scripting Mode", "Plasma"), this)),
|
||||
m_kwinAction(new QAction(QIcon::fromTheme("kwin"), i18nc("Toolbar Button to switch to KWin Scripting Mode", "KWin"), this)),
|
||||
m_snippetsMenu(new QMenu(i18n("Templates"), this)),
|
||||
m_fileDialog(0),
|
||||
m_closeWhenCompleted(false),
|
||||
m_mode(PlasmaConsole)
|
||||
{
|
||||
addAction(KStandardAction::close(this, SLOT(close()), this));
|
||||
addAction(m_saveAction);
|
||||
addAction(m_clearAction);
|
||||
|
||||
setWindowTitle(i18n("Desktop Shell Scripting Console"));
|
||||
setAttribute(Qt::WA_DeleteOnClose);
|
||||
//setButtons(QDialog::None);
|
||||
|
||||
QWidget *widget = new QWidget(m_splitter);
|
||||
QVBoxLayout *editorLayout = new QVBoxLayout(widget);
|
||||
|
||||
QLabel *label = new QLabel(i18n("Editor"), widget);
|
||||
QFont f = label->font();
|
||||
f.setBold(true);
|
||||
label->setFont(f);
|
||||
editorLayout->addWidget(label);
|
||||
|
||||
connect(m_snippetsMenu, SIGNAL(aboutToShow()), this, SLOT(populateTemplatesMenu()));
|
||||
|
||||
QToolButton *loadTemplateButton = new QToolButton(this);
|
||||
loadTemplateButton->setPopupMode(QToolButton::InstantPopup);
|
||||
loadTemplateButton->setMenu(m_snippetsMenu);
|
||||
loadTemplateButton->setText(i18n("Load"));
|
||||
connect(loadTemplateButton, SIGNAL(triggered(QAction*)), this, SLOT(loadTemplate(QAction*)));
|
||||
|
||||
QToolButton *useTemplateButton = new QToolButton(this);
|
||||
useTemplateButton->setPopupMode(QToolButton::InstantPopup);
|
||||
useTemplateButton->setMenu(m_snippetsMenu);
|
||||
useTemplateButton->setText(i18n("Use"));
|
||||
connect(useTemplateButton, SIGNAL(triggered(QAction*)), this, SLOT(useTemplate(QAction*)));
|
||||
|
||||
QActionGroup *modeGroup = new QActionGroup(this);
|
||||
modeGroup->addAction(m_plasmaAction);
|
||||
modeGroup->addAction(m_kwinAction);
|
||||
m_plasmaAction->setCheckable(true);
|
||||
m_kwinAction->setCheckable(true);
|
||||
m_plasmaAction->setChecked(true);
|
||||
connect(modeGroup, SIGNAL(triggered(QAction*)), this, SLOT(modeChanged()));
|
||||
|
||||
KToolBar *toolBar = new KToolBar(this, true, false);
|
||||
toolBar->setToolButtonStyle(Qt::ToolButtonTextBesideIcon);
|
||||
toolBar->addAction(m_loadAction);
|
||||
toolBar->addAction(m_saveAction);
|
||||
toolBar->addAction(m_clearAction);
|
||||
toolBar->addAction(m_executeAction);
|
||||
toolBar->addAction(m_plasmaAction);
|
||||
toolBar->addAction(m_kwinAction);
|
||||
toolBar->addWidget(loadTemplateButton);
|
||||
toolBar->addWidget(useTemplateButton);
|
||||
|
||||
editorLayout->addWidget(toolBar);
|
||||
|
||||
KService::List offers = KServiceTypeTrader::self()->query("KTextEditor/Document");
|
||||
foreach (const KService::Ptr service, offers) {
|
||||
m_editorPart = service->createInstance<KTextEditor::Document>(widget);
|
||||
if (m_editorPart) {
|
||||
m_editorPart->setHighlightingMode("JavaScript/PlasmaDesktop");
|
||||
|
||||
KTextEditor::View * view = m_editorPart->createView(widget);
|
||||
view->setContextMenu(view->defaultContextMenu());
|
||||
|
||||
KTextEditor::ConfigInterface *config = qobject_cast<KTextEditor::ConfigInterface*>(view);
|
||||
if (config) {
|
||||
config->setConfigValue("line-numbers", true);
|
||||
config->setConfigValue("dynamic-word-wrap", true);
|
||||
}
|
||||
|
||||
editorLayout->addWidget(view);
|
||||
connect(m_editorPart, SIGNAL(textChanged(KTextEditor::Document*)),
|
||||
this, SLOT(scriptTextChanged()));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!m_editorPart) {
|
||||
m_editor = new KTextEdit(widget);
|
||||
editorLayout->addWidget(m_editor);
|
||||
connect(m_editor, SIGNAL(textChanged()), this, SLOT(scriptTextChanged()));
|
||||
}
|
||||
|
||||
m_splitter->addWidget(widget);
|
||||
|
||||
widget = new QWidget(m_splitter);
|
||||
QVBoxLayout *outputLayout = new QVBoxLayout(widget);
|
||||
|
||||
label = new QLabel(i18n("Output"), widget);
|
||||
f = label->font();
|
||||
f.setBold(true);
|
||||
label->setFont(f);
|
||||
outputLayout->addWidget(label);
|
||||
|
||||
KToolBar *outputToolBar = new KToolBar(widget, true, false);
|
||||
outputToolBar->setToolButtonStyle(Qt::ToolButtonTextBesideIcon);
|
||||
QAction *clearOutputAction = KStandardAction::clear(this, SLOT(clearOutput()), this);
|
||||
outputToolBar->addAction(clearOutputAction);
|
||||
outputLayout->addWidget(outputToolBar);
|
||||
|
||||
m_output = new QTextBrowser(widget);
|
||||
outputLayout->addWidget(m_output);
|
||||
m_splitter->addWidget(widget);
|
||||
|
||||
QVBoxLayout *l = new QVBoxLayout(this);
|
||||
l->addWidget(m_splitter);
|
||||
|
||||
KConfigGroup cg(KSharedConfig::openConfig(), "InteractiveConsole");
|
||||
restoreGeometry(cg.readEntry<QByteArray>("Geometry", QByteArray()));
|
||||
|
||||
m_splitter->setStretchFactor(0, 10);
|
||||
m_splitter->restoreState(cg.readEntry("SplitterState", QByteArray()));
|
||||
|
||||
scriptTextChanged();
|
||||
|
||||
connect(m_executeAction, SIGNAL(triggered()), this, SLOT(evaluateScript()));
|
||||
m_executeAction->setShortcut(Qt::CTRL + Qt::Key_E);
|
||||
|
||||
const QString autosave = QStandardPaths::writableLocation(QStandardPaths::DataLocation) + "/" + s_autosaveFileName;
|
||||
if (QFile::exists(autosave)) {
|
||||
loadScript(autosave);
|
||||
}
|
||||
}
|
||||
|
||||
InteractiveConsole::~InteractiveConsole()
|
||||
{
|
||||
KConfigGroup cg(KSharedConfig::openConfig(), "InteractiveConsole");
|
||||
cg.writeEntry("Geometry", saveGeometry());
|
||||
cg.writeEntry("SplitterState", m_splitter->saveState());
|
||||
}
|
||||
|
||||
void InteractiveConsole::setMode(ConsoleMode mode)
|
||||
{
|
||||
m_mode = mode;
|
||||
switch (mode) {
|
||||
case PlasmaConsole:
|
||||
m_plasmaAction->setChecked(true);
|
||||
break;
|
||||
case KWinConsole:
|
||||
m_kwinAction->setChecked(true);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::modeChanged()
|
||||
{
|
||||
if (m_plasmaAction->isChecked()) {
|
||||
m_mode = PlasmaConsole;
|
||||
} else if (m_kwinAction->isChecked()) {
|
||||
m_mode = KWinConsole;
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::loadScript(const QString &script)
|
||||
{
|
||||
if (m_editorPart) {
|
||||
m_editorPart->closeUrl(false);
|
||||
if (m_editorPart->openUrl(QUrl::fromLocalFile(script))) {
|
||||
m_editorPart->setHighlightingMode("JavaScript/PlasmaDesktop");
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
QFile file(KShell::tildeExpand(script));
|
||||
if (file.open(QIODevice::ReadOnly | QIODevice::Text) ) {
|
||||
m_editor->setText(file.readAll());
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
m_output->append(i18n("Unable to load script file <b>%1</b>", script));
|
||||
}
|
||||
|
||||
void InteractiveConsole::showEvent(QShowEvent *)
|
||||
{
|
||||
if (m_editorPart) {
|
||||
m_editorPart->views().first()->setFocus();
|
||||
} else {
|
||||
m_editor->setFocus();
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::closeEvent(QCloseEvent *event)
|
||||
{
|
||||
onClose();
|
||||
QDialog::closeEvent(event);
|
||||
}
|
||||
|
||||
void InteractiveConsole::reject()
|
||||
{
|
||||
onClose();
|
||||
QDialog::reject();
|
||||
}
|
||||
|
||||
void InteractiveConsole::onClose()
|
||||
{
|
||||
// need to save first!
|
||||
const QString path = QStandardPaths::writableLocation(QStandardPaths::DataLocation) + "/" + s_autosaveFileName;
|
||||
m_closeWhenCompleted = true;
|
||||
saveScript(QUrl::fromLocalFile(path));
|
||||
}
|
||||
|
||||
void InteractiveConsole::print(const QString &string)
|
||||
{
|
||||
m_output->append(string);
|
||||
}
|
||||
|
||||
void InteractiveConsole::scriptTextChanged()
|
||||
{
|
||||
const bool enable = m_editorPart ? !m_editorPart->isEmpty() : !m_editor->document()->isEmpty();
|
||||
m_saveAction->setEnabled(enable);
|
||||
m_clearAction->setEnabled(enable);
|
||||
m_executeAction->setEnabled(enable);
|
||||
}
|
||||
|
||||
void InteractiveConsole::openScriptFile()
|
||||
{
|
||||
delete m_fileDialog;
|
||||
|
||||
m_fileDialog = new QFileDialog();
|
||||
m_fileDialog->setAcceptMode(QFileDialog::AcceptOpen);
|
||||
m_fileDialog->setWindowTitle(i18n("Open Script File"));
|
||||
|
||||
QStringList mimetypes;
|
||||
mimetypes << "application/javascript";
|
||||
m_fileDialog->setMimeTypeFilters(mimetypes);
|
||||
|
||||
connect(m_fileDialog, SIGNAL(finished(int)), this, SLOT(openScriptUrlSelected(int)));
|
||||
m_fileDialog->show();
|
||||
}
|
||||
|
||||
void InteractiveConsole::openScriptUrlSelected(int result)
|
||||
{
|
||||
if (!m_fileDialog) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (result == QDialog::Accepted) {
|
||||
const QUrl url = m_fileDialog->selectedUrls().first();
|
||||
if (!url.isEmpty()) {
|
||||
loadScriptFromUrl(url);
|
||||
}
|
||||
}
|
||||
|
||||
m_fileDialog->deleteLater();
|
||||
m_fileDialog = 0;
|
||||
}
|
||||
|
||||
void InteractiveConsole::loadScriptFromUrl(const QUrl &url)
|
||||
{
|
||||
if (m_editorPart) {
|
||||
m_editorPart->closeUrl(false);
|
||||
m_editorPart->openUrl(url);
|
||||
m_editorPart->setHighlightingMode("JavaScript/PlasmaDesktop");
|
||||
} else {
|
||||
m_editor->clear();
|
||||
m_editor->setEnabled(false);
|
||||
|
||||
if (m_job) {
|
||||
m_job.data()->kill();
|
||||
}
|
||||
|
||||
m_job = KIO::get(url, KIO::Reload, KIO::HideProgressInfo);
|
||||
connect(m_job.data(), SIGNAL(data(KIO::Job*,QByteArray)), this, SLOT(scriptFileDataRecvd(KIO::Job*,QByteArray)));
|
||||
connect(m_job.data(), SIGNAL(result(KJob*)), this, SLOT(reenableEditor(KJob*)));
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::populateTemplatesMenu()
|
||||
{
|
||||
m_snippetsMenu->clear();
|
||||
|
||||
QMap<QString, KService::Ptr> sorted;
|
||||
const QString constraint = QString("[X-Plasma-Shell] == '%1'")
|
||||
.arg(qApp->applicationName());
|
||||
KService::List templates = KServiceTypeTrader::self()->query("Plasma/LayoutTemplate", constraint);
|
||||
foreach (const KService::Ptr &service, templates) {
|
||||
sorted.insert(service->name(), service);
|
||||
}
|
||||
|
||||
QMapIterator<QString, KService::Ptr> it(sorted);
|
||||
|
||||
Plasma::Package package = ShellPluginLoader::self()->loadPackage("Plasma/LayoutTemplate");
|
||||
|
||||
while (it.hasNext()) {
|
||||
it.next();
|
||||
KPluginInfo info(it.value());
|
||||
const QString path = QStandardPaths::locate(QStandardPaths::GenericDataLocation
|
||||
, package.defaultPackageRoot() + '/' + info.pluginName() + '/');
|
||||
if (!path.isEmpty()) {
|
||||
package.setPath(info.pluginName());
|
||||
const QString scriptFile = package.filePath("mainscript");
|
||||
if (!scriptFile.isEmpty()) {
|
||||
QAction *action = m_snippetsMenu->addAction(info.name());
|
||||
action->setData(info.pluginName());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::loadTemplate(QAction *action)
|
||||
{
|
||||
Plasma::Package package = ShellPluginLoader::self()->loadPackage("Plasma/LayoutTemplate");
|
||||
|
||||
const QString pluginName = action->data().toString();
|
||||
const QString path = QStandardPaths::locate(QStandardPaths::GenericDataLocation
|
||||
, package.defaultPackageRoot() + '/' + pluginName + '/');
|
||||
if (!path.isEmpty()) {
|
||||
package.setPath(pluginName);
|
||||
const QString scriptFile = package.filePath("mainscript");
|
||||
if (!scriptFile.isEmpty()) {
|
||||
loadScriptFromUrl(QUrl::fromLocalFile(scriptFile));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::useTemplate(QAction *action)
|
||||
{
|
||||
QString code("var template = loadTemplate('" + action->data().toString() + "')");
|
||||
if (m_editorPart) {
|
||||
const QList<KTextEditor::View *> views = m_editorPart->views();
|
||||
if (views.isEmpty()) {
|
||||
m_editorPart->insertLines(m_editorPart->lines(), QStringList() << code);
|
||||
} else {
|
||||
KTextEditor::Cursor cursor = views.at(0)->cursorPosition();
|
||||
m_editorPart->insertLines(cursor.line(), QStringList() << code);
|
||||
cursor.setLine(cursor.line() + 1);
|
||||
views.at(0)->setCursorPosition(cursor);
|
||||
}
|
||||
} else {
|
||||
m_editor->insertPlainText(code);
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::scriptFileDataRecvd(KIO::Job *job, const QByteArray &data)
|
||||
{
|
||||
Q_ASSERT(m_editor);
|
||||
|
||||
if (job == m_job.data()) {
|
||||
m_editor->insertPlainText(data);
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::saveScript()
|
||||
{
|
||||
if (m_editorPart) {
|
||||
m_editorPart->documentSaveAs();
|
||||
return;
|
||||
}
|
||||
|
||||
delete m_fileDialog;
|
||||
|
||||
m_fileDialog = new QFileDialog();
|
||||
m_fileDialog->setAcceptMode(QFileDialog::AcceptSave);
|
||||
m_fileDialog->setWindowTitle(i18n("Save Script File"));
|
||||
|
||||
QStringList mimetypes;
|
||||
mimetypes << "application/javascript";
|
||||
m_fileDialog->setMimeTypeFilters(mimetypes);
|
||||
|
||||
connect(m_fileDialog, SIGNAL(finished(int)), this, SLOT(saveScriptUrlSelected(int)));
|
||||
m_fileDialog->show();
|
||||
}
|
||||
|
||||
void InteractiveConsole::saveScriptUrlSelected(int result)
|
||||
{
|
||||
if (!m_fileDialog) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (result == QDialog::Accepted) {
|
||||
const QUrl url = m_fileDialog->selectedUrls().first();
|
||||
if (!url.isEmpty()) {
|
||||
saveScript(url);
|
||||
}
|
||||
}
|
||||
|
||||
m_fileDialog->deleteLater();
|
||||
m_fileDialog = 0;
|
||||
}
|
||||
|
||||
void InteractiveConsole::saveScript(const QUrl &url)
|
||||
{
|
||||
if (m_editorPart) {
|
||||
m_editorPart->saveAs(url);
|
||||
} else {
|
||||
m_editor->setEnabled(false);
|
||||
|
||||
if (m_job) {
|
||||
m_job.data()->kill();
|
||||
}
|
||||
|
||||
m_job = KIO::put(url, -1, KIO::HideProgressInfo);
|
||||
connect(m_job.data(), SIGNAL(dataReq(KIO::Job*,QByteArray&)), this, SLOT(scriptFileDataReq(KIO::Job*,QByteArray&)));
|
||||
connect(m_job.data(), SIGNAL(result(KJob*)), this, SLOT(reenableEditor(KJob*)));
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::scriptFileDataReq(KIO::Job *job, QByteArray &data)
|
||||
{
|
||||
Q_ASSERT(m_editor);
|
||||
|
||||
if (!m_job || m_job.data() != job) {
|
||||
return;
|
||||
}
|
||||
|
||||
data.append(m_editor->toPlainText().toLocal8Bit());
|
||||
m_job.clear();
|
||||
}
|
||||
|
||||
void InteractiveConsole::reenableEditor(KJob* job)
|
||||
{
|
||||
Q_ASSERT(m_editor);
|
||||
if (m_closeWhenCompleted && job->error() != 0) {
|
||||
close();
|
||||
}
|
||||
|
||||
m_closeWhenCompleted = false;
|
||||
m_editor->setEnabled(true);
|
||||
}
|
||||
|
||||
void InteractiveConsole::evaluateScript()
|
||||
{
|
||||
//qDebug() << "evaluating" << m_editor->toPlainText();
|
||||
const QString path = QStandardPaths::writableLocation(QStandardPaths::DataLocation) + "/" + s_autosaveFileName;
|
||||
saveScript(QUrl::fromLocalFile(path));
|
||||
|
||||
m_output->moveCursor(QTextCursor::End);
|
||||
QTextCursor cursor = m_output->textCursor();
|
||||
m_output->setTextCursor(cursor);
|
||||
|
||||
QTextCharFormat format;
|
||||
format.setFontWeight(QFont::Bold);
|
||||
format.setFontUnderline(true);
|
||||
|
||||
if (cursor.position() > 0) {
|
||||
cursor.insertText("\n\n");
|
||||
}
|
||||
|
||||
QDateTime dt = QDateTime::currentDateTime();
|
||||
cursor.insertText(i18n("Executing script at %1", QLocale().toString(dt)));
|
||||
|
||||
format.setFontWeight(QFont::Normal);
|
||||
format.setFontUnderline(false);
|
||||
QTextBlockFormat block = cursor.blockFormat();
|
||||
block.setLeftMargin(10);
|
||||
cursor.insertBlock(block, format);
|
||||
QTime t;
|
||||
t.start();
|
||||
|
||||
if (m_mode == PlasmaConsole) {
|
||||
WorkspaceScripting::DesktopScriptEngine scriptEngine(m_corona, false, this);
|
||||
connect(&scriptEngine, SIGNAL(print(QString)), this, SLOT(print(QString)));
|
||||
connect(&scriptEngine, SIGNAL(printError(QString)), this, SLOT(print(QString)));
|
||||
connect(&scriptEngine, SIGNAL(createPendingPanelViews()), m_corona, SLOT(createWaitingPanels()));
|
||||
scriptEngine.evaluateScript(m_editorPart ? m_editorPart->text() : m_editor->toPlainText());
|
||||
} else if (m_mode == KWinConsole) {
|
||||
QDBusMessage message = QDBusMessage::createMethodCall(s_kwinService, "/Scripting", QString(), "loadScript");
|
||||
QList<QVariant> arguments;
|
||||
arguments << QVariant(path);
|
||||
message.setArguments(arguments);
|
||||
QDBusMessage reply = QDBusConnection::sessionBus().call(message);
|
||||
if (reply.type() == QDBusMessage::ErrorMessage) {
|
||||
print(reply.errorMessage());
|
||||
} else {
|
||||
const int id = reply.arguments().first().toInt();
|
||||
QDBusConnection::sessionBus().connect(s_kwinService, "/" + QString::number(id), QString(), "print", this, SLOT(print(QString)));
|
||||
QDBusConnection::sessionBus().connect(s_kwinService, "/" + QString::number(id), QString(), "printError", this, SLOT(print(QString)));
|
||||
message = QDBusMessage::createMethodCall(s_kwinService, "/" + QString::number(id), QString(), "run");
|
||||
reply = QDBusConnection::sessionBus().call(message);
|
||||
if (reply.type() == QDBusMessage::ErrorMessage) {
|
||||
print(reply.errorMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
cursor.insertText("\n\n");
|
||||
format.setFontWeight(QFont::Bold);
|
||||
// xgettext:no-c-format
|
||||
cursor.insertText(i18n("Runtime: %1ms", QString::number(t.elapsed())), format);
|
||||
block.setLeftMargin(0);
|
||||
cursor.insertBlock(block);
|
||||
m_output->ensureCursorVisible();
|
||||
}
|
||||
|
||||
void InteractiveConsole::clearEditor()
|
||||
{
|
||||
if (m_editorPart) {
|
||||
m_editorPart->clear();
|
||||
} else {
|
||||
m_editor->clear();
|
||||
}
|
||||
}
|
||||
|
||||
void InteractiveConsole::clearOutput()
|
||||
{
|
||||
m_output->clear();
|
||||
}
|
||||
|
||||
#include "interactiveconsole.moc"
|
||||
|
@ -1,118 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
* Copyright 2014 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef INTERACTIVECONSOLE
|
||||
#define INTERACTIVECONSOLE
|
||||
|
||||
#include <QWeakPointer>
|
||||
#include <QScriptValue>
|
||||
|
||||
#include <QDialog>
|
||||
|
||||
#include <KIO/Job>
|
||||
|
||||
class QSplitter;
|
||||
|
||||
class QAction;
|
||||
class QFileDialog;
|
||||
class QMenu;
|
||||
class KTextEdit;
|
||||
class QTextBrowser;
|
||||
|
||||
class ShellCorona;
|
||||
|
||||
namespace KTextEditor
|
||||
{
|
||||
class Document;
|
||||
} // namespace KParts
|
||||
|
||||
namespace Plasma
|
||||
{
|
||||
class Corona;
|
||||
} // namespace Plasma
|
||||
|
||||
class ScriptEngine;
|
||||
|
||||
class InteractiveConsole : public QDialog
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
InteractiveConsole(ShellCorona *corona, QWidget *parent = 0);
|
||||
~InteractiveConsole();
|
||||
|
||||
void loadScript(const QString &path);
|
||||
enum ConsoleMode {
|
||||
PlasmaConsole,
|
||||
KWinConsole
|
||||
};
|
||||
void setMode(ConsoleMode mode);
|
||||
|
||||
protected:
|
||||
void showEvent(QShowEvent *);
|
||||
void closeEvent(QCloseEvent *event);
|
||||
|
||||
protected Q_SLOTS:
|
||||
void print(const QString &string);
|
||||
void reject();
|
||||
|
||||
private Q_SLOTS:
|
||||
void openScriptFile();
|
||||
void saveScript();
|
||||
void scriptTextChanged();
|
||||
void evaluateScript();
|
||||
void clearEditor();
|
||||
void clearOutput();
|
||||
void scriptFileDataRecvd(KIO::Job *job, const QByteArray &data);
|
||||
void scriptFileDataReq(KIO::Job *job, QByteArray &data);
|
||||
void reenableEditor(KJob *job);
|
||||
void saveScriptUrlSelected(int result);
|
||||
void openScriptUrlSelected(int result);
|
||||
void loadScriptFromUrl(const QUrl &url);
|
||||
void populateTemplatesMenu();
|
||||
void loadTemplate(QAction *);
|
||||
void useTemplate(QAction *);
|
||||
void modeChanged();
|
||||
|
||||
private:
|
||||
void onClose();
|
||||
void saveScript(const QUrl &url);
|
||||
|
||||
ShellCorona *m_corona;
|
||||
QSplitter *m_splitter;
|
||||
KTextEditor::Document *m_editorPart;
|
||||
KTextEdit *m_editor;
|
||||
QTextBrowser *m_output;
|
||||
QAction *m_loadAction;
|
||||
QAction *m_saveAction;
|
||||
QAction *m_clearAction;
|
||||
QAction *m_executeAction;
|
||||
QAction *m_plasmaAction;
|
||||
QAction *m_kwinAction;
|
||||
QMenu *m_snippetsMenu;
|
||||
|
||||
QFileDialog *m_fileDialog;
|
||||
QWeakPointer<KIO::Job> m_job;
|
||||
bool m_closeWhenCompleted;
|
||||
ConsoleMode m_mode;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -1,302 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010 Ivan Cukic <ivan.cukic(at)kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library/Lesser General Public License
|
||||
* version 2, or (at your option) any later version, as published by the
|
||||
* Free Software Foundation
|
||||
*
|
||||
* 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 Library/Lesser General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "kidenticongenerator.h"
|
||||
|
||||
#include <QHash>
|
||||
#include <QPainter>
|
||||
#include <QDebug>
|
||||
#include <QCryptographicHash>
|
||||
|
||||
#include <kiconeffect.h>
|
||||
|
||||
#include <Plasma/Svg>
|
||||
#include <Plasma/Theme>
|
||||
|
||||
#define VALUE_LIMIT_UP 192
|
||||
#define VALUE_LIMIT_DOWN 64
|
||||
|
||||
class KIdenticonGenerator::Private {
|
||||
public:
|
||||
QPixmap generatePattern(int size, quint32 hash, QIcon::Mode mode);
|
||||
|
||||
QString elementName(const QString & element, QIcon::Mode mode);
|
||||
QColor colorForHash(quint32 hash) const;
|
||||
quint32 hash(const QString & data);
|
||||
|
||||
static KIdenticonGenerator * instance;
|
||||
|
||||
Plasma::Theme *theme;
|
||||
Plasma::Svg shapes;
|
||||
Plasma::Svg svg;
|
||||
};
|
||||
|
||||
QPixmap KIdenticonGenerator::Private::generatePattern(int size, quint32 hash, QIcon::Mode mode)
|
||||
{
|
||||
// We are dividing the pixmap into 9 blocks - 3 x 3
|
||||
int blockSize = size / 3;
|
||||
|
||||
// pulling parts of the hash
|
||||
quint32 tmp = hash;
|
||||
|
||||
quint8 block[4];
|
||||
block[0] = tmp & 31; tmp >>= 5;
|
||||
block[1] = tmp & 31; tmp >>= 5;
|
||||
block[2] = tmp & 31; tmp >>= 5;
|
||||
|
||||
// Painting alpha channel
|
||||
QPixmap pixmapAlpha(size, size);
|
||||
pixmapAlpha.fill(Qt::black);
|
||||
|
||||
QPainter painterAlpha(& pixmapAlpha);
|
||||
|
||||
QRectF rect(0, 0, blockSize + 0.5, blockSize + 0.5);
|
||||
|
||||
for (int i = 0; i < 4; i++) {
|
||||
// Painting the corner item
|
||||
rect.moveTopLeft(QPoint(0, 0));
|
||||
shapes.paint(& painterAlpha, rect, "shape" + QString::number(block[0] + 1));
|
||||
|
||||
// Painting side item
|
||||
rect.moveTopLeft(QPoint(blockSize, 0));
|
||||
shapes.paint(& painterAlpha, rect, "shape" + QString::number(block[1] + 1));
|
||||
|
||||
// Rotating the canvas to paint other edges
|
||||
painterAlpha.translate(size, 0);
|
||||
painterAlpha.rotate(90);
|
||||
}
|
||||
|
||||
// Painting center item
|
||||
rect.moveTopLeft(QPoint(blockSize, blockSize));
|
||||
shapes.paint(& painterAlpha, rect, "shape" + QString::number(block[2] + 1));
|
||||
|
||||
painterAlpha.end();
|
||||
|
||||
// Painting final pixmap
|
||||
QPixmap pixmapResult(size, size);
|
||||
|
||||
|
||||
pixmapResult.fill(Qt::transparent);
|
||||
|
||||
// QRadialGradient gradient(50, 50, 100);
|
||||
// gradient.setColorAt(0, color.lighter());
|
||||
// gradient.setColorAt(1, color.darker());
|
||||
|
||||
QPainter resultPainter(& pixmapResult);
|
||||
// resultPainter.fillRect(0, 0, size, size, gradient);
|
||||
svg.paint(& resultPainter, QRect(0, 0, size, size), elementName("content", mode));
|
||||
|
||||
resultPainter.end();
|
||||
|
||||
pixmapResult.setAlphaChannel(pixmapAlpha);
|
||||
|
||||
// QImage itmp = pixmapResult.toImage();
|
||||
// KIconEffect::colorize(itmp, colorForHash(hash), 1.0);
|
||||
// pixmapResult = pixmapResult.fromImage(itmp);
|
||||
|
||||
return pixmapResult;
|
||||
}
|
||||
|
||||
QColor KIdenticonGenerator::Private::colorForHash(quint32 hash) const
|
||||
{
|
||||
// Color is chosen according to hash
|
||||
QColor color;
|
||||
|
||||
// Getting the value from color svg, but we must restrain it to
|
||||
// values in range from VALUE_LIMIT_DOWN to VALUE_LIMIT_UP
|
||||
|
||||
int value = theme->color(Plasma::Theme::TextColor).value();
|
||||
if (value < VALUE_LIMIT_DOWN) {
|
||||
value = VALUE_LIMIT_DOWN;
|
||||
} else if (value > VALUE_LIMIT_UP) {
|
||||
value = VALUE_LIMIT_UP;
|
||||
}
|
||||
|
||||
color.setHsv(
|
||||
hash % 359 + 1, // hue depending on hash
|
||||
250, // high saturation level
|
||||
value
|
||||
);
|
||||
|
||||
return color;
|
||||
|
||||
}
|
||||
|
||||
QString KIdenticonGenerator::Private::elementName(const QString & element, QIcon::Mode mode)
|
||||
{
|
||||
QString prefix;
|
||||
|
||||
switch (mode) {
|
||||
case QIcon::Normal:
|
||||
prefix = "normal-";
|
||||
break;
|
||||
|
||||
case QIcon::Disabled:
|
||||
prefix = "disabled-";
|
||||
break;
|
||||
|
||||
case QIcon::Selected:
|
||||
prefix = "selected-";
|
||||
break;
|
||||
|
||||
case QIcon::Active:
|
||||
prefix = "active-";
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
|
||||
}
|
||||
|
||||
if (svg.hasElement(prefix + element)) {
|
||||
return prefix + element;
|
||||
} else {
|
||||
return element;
|
||||
}
|
||||
}
|
||||
|
||||
quint32 KIdenticonGenerator::Private::hash(const QString & data)
|
||||
{
|
||||
// qHash function doesn't give random enough results
|
||||
// and gives similar hashes for similar strings.
|
||||
|
||||
QByteArray bytes = QCryptographicHash::hash(data.toUtf8(), QCryptographicHash::Md5);
|
||||
|
||||
// Generating hash
|
||||
quint32 hash = 0;
|
||||
|
||||
char * hashBytes = (char *) & hash;
|
||||
for (int i = 0; i < bytes.size(); i++) {
|
||||
// Using XOR for mixing the bytes because
|
||||
// it is fast and cryptographically safe
|
||||
// (more than enough for our use-case)
|
||||
hashBytes[i % 4] ^= bytes.at(i);
|
||||
}
|
||||
|
||||
return hash;
|
||||
}
|
||||
|
||||
KIdenticonGenerator * KIdenticonGenerator::Private::instance = NULL;
|
||||
|
||||
KIdenticonGenerator * KIdenticonGenerator::self()
|
||||
{
|
||||
if (!Private::instance) {
|
||||
Private::instance = new KIdenticonGenerator();
|
||||
}
|
||||
|
||||
return Private::instance;
|
||||
}
|
||||
|
||||
KIdenticonGenerator::KIdenticonGenerator()
|
||||
: d(new Private())
|
||||
{
|
||||
d->theme = new Plasma::Theme(0);
|
||||
// loading SVGs
|
||||
d->shapes.setImagePath("widgets/identiconshapes");
|
||||
d->shapes.setContainsMultipleImages(true);
|
||||
|
||||
d->svg.setImagePath("widgets/identiconsvg");
|
||||
d->svg.setContainsMultipleImages(true);
|
||||
}
|
||||
|
||||
KIdenticonGenerator::~KIdenticonGenerator()
|
||||
{
|
||||
delete d->theme;
|
||||
}
|
||||
|
||||
#define generateIconModes( PARAM ) \
|
||||
for (int omode = QIcon::Normal; omode <= QIcon::Selected; omode++) { \
|
||||
QIcon::Mode mode = (QIcon::Mode)omode; \
|
||||
result.addPixmap(generatePixmap(size, PARAM, mode), mode); \
|
||||
}
|
||||
|
||||
QIcon KIdenticonGenerator::generate(int size, quint32 hash)
|
||||
{
|
||||
QIcon result;
|
||||
generateIconModes(hash);
|
||||
return result;
|
||||
}
|
||||
|
||||
QIcon KIdenticonGenerator::generate(int size, const QString & data)
|
||||
{
|
||||
QIcon result;
|
||||
generateIconModes(data);
|
||||
return result;
|
||||
}
|
||||
|
||||
QIcon KIdenticonGenerator::generate(int size, const QIcon & icon)
|
||||
{
|
||||
QIcon result;
|
||||
generateIconModes(icon);
|
||||
return result;
|
||||
}
|
||||
|
||||
QPixmap KIdenticonGenerator::generatePixmap(int size, QString id, QIcon::Mode mode)
|
||||
{
|
||||
return generatePixmap(size, d->hash(id), mode);
|
||||
}
|
||||
|
||||
QPixmap KIdenticonGenerator::generatePixmap(int size, quint32 hash, QIcon::Mode mode)
|
||||
{
|
||||
QPixmap pixmap(size, size);
|
||||
pixmap.fill(Qt::transparent);
|
||||
|
||||
// Painting background and the pattern
|
||||
{
|
||||
QPainter painter(& pixmap);
|
||||
d->svg.paint(& painter, QRect(0, 0, size, size), d->elementName("background", mode));
|
||||
painter.drawPixmap(0, 0, d->generatePattern(size, hash, mode));
|
||||
painter.end();
|
||||
}
|
||||
|
||||
// coloring the painted image
|
||||
QImage itmp = pixmap.toImage();
|
||||
KIconEffect::colorize(itmp, d->colorForHash(hash), 1.0);
|
||||
if (mode == QIcon::Disabled) {
|
||||
KIconEffect::toGray(itmp, 0.7);
|
||||
}
|
||||
pixmap = pixmap.fromImage(itmp);
|
||||
|
||||
// Drawing the overlay
|
||||
{
|
||||
QPainter painter(& pixmap);
|
||||
d->svg.paint(& painter, QRect(0, 0, size, size), d->elementName("overlay", mode));
|
||||
}
|
||||
|
||||
return pixmap;
|
||||
}
|
||||
|
||||
QPixmap KIdenticonGenerator::generatePixmap(int size, const QIcon & icon, QIcon::Mode mode)
|
||||
{
|
||||
QPixmap pixmap(size, size);
|
||||
pixmap.fill(Qt::transparent);
|
||||
|
||||
QRect paintRect(0, 0, size, size);
|
||||
|
||||
// Painting background and the pattern
|
||||
QPainter painter(& pixmap);
|
||||
d->svg.paint(& painter, QRect(0, 0, size, size), d->elementName("background", mode));
|
||||
|
||||
icon.paint(& painter, paintRect, Qt::AlignCenter, mode);
|
||||
|
||||
painter.end();
|
||||
|
||||
return pixmap;
|
||||
}
|
||||
|
@ -1,48 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010 Ivan Cukic <ivan.cukic(at)kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library/Lesser General Public License
|
||||
* version 2, or (at your option) any later version, as published by the
|
||||
* Free Software Foundation
|
||||
*
|
||||
* 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 Library/Lesser General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef KIDENTICONGENERATOR_H
|
||||
#define KIDENTICONGENERATOR_H
|
||||
|
||||
#include <QPixmap>
|
||||
#include <QIcon>
|
||||
|
||||
#include <Plasma/Svg>
|
||||
|
||||
class KIdenticonGenerator {
|
||||
public:
|
||||
static KIdenticonGenerator * self();
|
||||
~KIdenticonGenerator();
|
||||
|
||||
QPixmap generatePixmap(int size, QString id, QIcon::Mode mode = QIcon::Normal);
|
||||
QPixmap generatePixmap(int size, quint32 hash, QIcon::Mode mode = QIcon::Normal);
|
||||
QPixmap generatePixmap(int size, const QIcon & icon, QIcon::Mode mode = QIcon::Normal);
|
||||
|
||||
QIcon generate(int size, const QString & data);
|
||||
QIcon generate(int size, quint32 hash);
|
||||
QIcon generate(int size, const QIcon & icon);
|
||||
|
||||
private:
|
||||
KIdenticonGenerator();
|
||||
|
||||
class Private;
|
||||
Private * const d;
|
||||
};
|
||||
|
||||
#endif // KIDENTICONGENERATOR_H
|
@ -1,92 +0,0 @@
|
||||
/*
|
||||
* Copyright 2012 Marco Martin <mart@kde.org>
|
||||
* Copyright 2013 Sebastian Kügler <sebas@kde.org>
|
||||
*
|
||||
* 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 2 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, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include <QApplication>
|
||||
#include <qcommandlineparser.h>
|
||||
#include <QtQml/QQmlDebuggingEnabler>
|
||||
#include <QDebug>
|
||||
|
||||
#include <kdbusservice.h>
|
||||
#include <klocalizedstring.h>
|
||||
|
||||
#include "shellpluginloader.h"
|
||||
#include "shellmanager.h"
|
||||
|
||||
static const char description[] = "Plasma Shell";
|
||||
static const char version[] = "2.0";
|
||||
static QCommandLineParser parser;
|
||||
|
||||
void noMessageOutput(QtMsgType type, const char *msg)
|
||||
{
|
||||
Q_UNUSED(type);
|
||||
Q_UNUSED(msg);
|
||||
}
|
||||
int main(int argc, char** argv)
|
||||
{
|
||||
QQmlDebuggingEnabler debugEnabler;
|
||||
|
||||
QApplication app(argc, argv);
|
||||
app.setApplicationName("plasma_shell");
|
||||
app.setOrganizationDomain("kde.org");
|
||||
app.setApplicationVersion(version);
|
||||
app.setQuitOnLastWindowClosed(false);
|
||||
parser.setApplicationDescription(description);
|
||||
KDBusService service(KDBusService::Unique);
|
||||
|
||||
QCommandLineOption dbg(QStringList() << QStringLiteral("d") <<
|
||||
QStringLiteral("qmljsdebugger"),
|
||||
QStringLiteral("Enable QML Javascript debugger"));
|
||||
|
||||
QCommandLineOption win(QStringList() << QStringLiteral("w") <<
|
||||
QStringLiteral("windowed"),
|
||||
QStringLiteral("Force a windowed view for testing purposes"));
|
||||
|
||||
QCommandLineOption respawn(QStringList() << QStringLiteral("n") <<
|
||||
QStringLiteral("no-respawn"),
|
||||
QStringLiteral("Do not restart plasma-shell automatically after a crash"));
|
||||
|
||||
QCommandLineOption crash(QStringList() << QStringLiteral("c") << QStringLiteral("crashes"),
|
||||
QStringLiteral("Recent number of crashes"),
|
||||
QStringLiteral("n"));
|
||||
|
||||
QCommandLineOption shutup(QStringList() << QStringLiteral("s") << QStringLiteral("shut-up"),
|
||||
QStringLiteral("Shuts up the output"));
|
||||
|
||||
parser.addVersionOption();
|
||||
parser.addHelpOption();
|
||||
parser.addOption(dbg);
|
||||
parser.addOption(win);
|
||||
parser.addOption(respawn);
|
||||
parser.addOption(crash);
|
||||
parser.addOption(shutup);
|
||||
|
||||
parser.process(app);
|
||||
|
||||
if (parser.isSet(shutup)) {
|
||||
qInstallMsgHandler(noMessageOutput);
|
||||
}
|
||||
Plasma::PluginLoader::setPluginLoader(new ShellPluginLoader);
|
||||
|
||||
ShellManager::setCrashCount(parser.value(crash).toInt());
|
||||
ShellManager::s_forceWindowed = parser.isSet(win);
|
||||
ShellManager::s_noRespawn = parser.isSet(respawn);
|
||||
ShellManager::instance();
|
||||
|
||||
return app.exec();
|
||||
}
|
@ -1,324 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 2009 Chani Armitage <chani@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "mousepluginwidget.h"
|
||||
|
||||
#include <Plasma/Containment>
|
||||
|
||||
#include <kaboutdata.h>
|
||||
#include <kaboutapplicationdialog.h>
|
||||
#include <KDebug>
|
||||
|
||||
#include <QApplication>
|
||||
#include <QComboBox>
|
||||
#include <QDialog>
|
||||
#include <QDialogButtonBox>
|
||||
#include <QGridLayout>
|
||||
|
||||
Q_DECLARE_METATYPE(KPluginInfo)
|
||||
|
||||
MousePluginWidget::MousePluginWidget(const QString &pluginName, const QString &trigger, QGridLayout *layoutHack, QWidget *parent)
|
||||
: QObject(parent),
|
||||
m_configDlg(0),
|
||||
m_containment(0),
|
||||
m_lastConfigLocation(trigger),
|
||||
m_tempConfigParent(QString(), KConfig::SimpleConfig)
|
||||
{
|
||||
KPluginInfo::List plugins = Plasma::ContainmentActions::listContainmentActionsInfo();
|
||||
if (plugins.isEmpty()) {
|
||||
//panic!!
|
||||
QLabel *fail = new QLabel(i18n("No plugins found, check your installation."), parent);
|
||||
layoutHack->addWidget(fail, 0, 0);
|
||||
return;
|
||||
}
|
||||
|
||||
//make us some widgets
|
||||
m_pluginList = new QComboBox(parent);
|
||||
m_aboutButton = new QToolButton(parent);
|
||||
m_clearButton = new QToolButton(parent);
|
||||
m_triggerButton = new MouseInputButton(parent);
|
||||
m_configButton = new QToolButton(parent);
|
||||
//m_ui.description->setText(plugin.comment());
|
||||
|
||||
//plugin list
|
||||
//FIXME is there some way to share this across all the entries?
|
||||
foreach (const KPluginInfo& plugin, plugins) {
|
||||
if (plugin.property("NoDisplay").toBool()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
m_pluginList->addItem(KIcon(plugin.icon()), plugin.name(), QVariant::fromValue(plugin));
|
||||
if (plugin.pluginName() == pluginName) {
|
||||
m_pluginList->setCurrentIndex(m_pluginList->count() - 1);
|
||||
m_plugin = plugin;
|
||||
}
|
||||
}
|
||||
|
||||
if (! m_plugin.isValid()) {
|
||||
//probably an empty string; pick the first one
|
||||
m_pluginList->setCurrentIndex(0);
|
||||
m_plugin = plugins.first();
|
||||
}
|
||||
|
||||
//I can haz config?
|
||||
m_tempConfig = KConfigGroup(&m_tempConfigParent, "test");
|
||||
if (!m_plugin.property("X-Plasma-HasConfigurationInterface").toBool()) {
|
||||
m_configButton->setVisible(false);
|
||||
}
|
||||
|
||||
setTrigger(trigger);
|
||||
|
||||
//pretty icons for the buttons
|
||||
m_aboutButton->setIcon(KIcon("dialog-information"));
|
||||
m_aboutButton->setToolTip(i18nc("About mouse action", "About"));
|
||||
m_triggerButton->setIcon(KIcon("input-mouse"));
|
||||
m_configButton->setIcon(KIcon("configure"));
|
||||
m_configButton->setToolTip(i18nc("Configure mouse action", "Configure"));
|
||||
m_clearButton->setIcon(KIcon("list-remove"));
|
||||
m_clearButton->setToolTip(i18nc("Remove mouse action", "Remove"));
|
||||
|
||||
//HACK
|
||||
//FIXME what's the Right Way to do this?
|
||||
int row = layoutHack->rowCount();
|
||||
layoutHack->addWidget(m_triggerButton, row, 0);
|
||||
layoutHack->addWidget(m_pluginList, row, 1);
|
||||
layoutHack->addWidget(m_configButton, row, 2);
|
||||
layoutHack->addWidget(m_aboutButton, row, 3);
|
||||
layoutHack->addWidget(m_clearButton, row, 4);
|
||||
|
||||
//connect
|
||||
connect(m_pluginList, SIGNAL(currentIndexChanged(int)), this, SLOT(setPlugin(int)));
|
||||
connect(m_triggerButton, SIGNAL(triggerChanged(QString,QString)), this, SLOT(changeTrigger(QString,QString)));
|
||||
connect(m_configButton, SIGNAL(clicked()), this, SLOT(configure()));
|
||||
connect(m_clearButton, SIGNAL(clicked()), this, SLOT(clearTrigger()));
|
||||
connect(m_aboutButton, SIGNAL(clicked()), this, SLOT(showAbout()));
|
||||
}
|
||||
|
||||
MousePluginWidget::~MousePluginWidget()
|
||||
{
|
||||
delete m_pluginInstance.data();
|
||||
}
|
||||
|
||||
void MousePluginWidget::setPlugin(int index)
|
||||
{
|
||||
m_plugin = m_pluginList->itemData(index).value<KPluginInfo>();
|
||||
//clear all the old plugin's stuff
|
||||
if (m_configDlg) {
|
||||
kDebug() << "can't happen";
|
||||
m_configDlg->deleteLater();
|
||||
m_configDlg = 0;
|
||||
}
|
||||
if (m_pluginInstance) {
|
||||
delete m_pluginInstance.data();
|
||||
kDebug() << "tried to delete instance";
|
||||
}
|
||||
//reset config button
|
||||
bool hasConfig = m_plugin.property("X-Plasma-HasConfigurationInterface").toBool();
|
||||
m_configButton->setVisible(hasConfig);
|
||||
m_tempConfig.deleteGroup();
|
||||
m_lastConfigLocation.clear();
|
||||
//FIXME a stray mousewheel deleting your config would be no fun.
|
||||
//perhaps we could mark it for deletion, and then... um.. not delete it if the user goes back to
|
||||
//that plugin? but then we'd have to record which plugin the config is *for*...
|
||||
emit configChanged(m_triggerButton->trigger());
|
||||
}
|
||||
|
||||
void MousePluginWidget::setContainment(Plasma::Containment *ctmt)
|
||||
{
|
||||
//note: since the old plugin's parent is the old containment,
|
||||
//we let that containment take care of deleting it
|
||||
m_containment = ctmt;
|
||||
}
|
||||
|
||||
void MousePluginWidget::setTrigger(const QString &trigger)
|
||||
{
|
||||
m_triggerButton->setTrigger(trigger);
|
||||
updateConfig(trigger);
|
||||
}
|
||||
|
||||
void MousePluginWidget::clearTrigger()
|
||||
{
|
||||
QString oldTrigger = m_triggerButton->trigger();
|
||||
setTrigger(QString());
|
||||
emit triggerChanged(oldTrigger, QString());
|
||||
|
||||
//byebye!
|
||||
m_pluginList->deleteLater();
|
||||
m_aboutButton->deleteLater();
|
||||
m_clearButton->deleteLater();
|
||||
m_triggerButton->deleteLater();
|
||||
m_configButton->deleteLater();
|
||||
|
||||
deleteLater();
|
||||
}
|
||||
|
||||
void MousePluginWidget::changeTrigger(const QString &oldTrigger, const QString& newTrigger)
|
||||
{
|
||||
updateConfig(newTrigger);
|
||||
emit triggerChanged(oldTrigger, newTrigger);
|
||||
}
|
||||
|
||||
void MousePluginWidget::updateConfig(const QString &trigger)
|
||||
{
|
||||
m_configButton->setEnabled(!trigger.isEmpty());
|
||||
m_pluginList->setEnabled(!trigger.isEmpty());
|
||||
}
|
||||
|
||||
void MousePluginWidget::configure()
|
||||
{
|
||||
if (!m_pluginInstance) {
|
||||
Plasma::ContainmentActions *pluginInstance = Plasma::ContainmentActions::load(m_containment, m_plugin.pluginName());
|
||||
if (!pluginInstance) {
|
||||
//FIXME tell user
|
||||
kDebug() << "failed to load plugin!";
|
||||
return;
|
||||
}
|
||||
|
||||
m_pluginInstance = pluginInstance;
|
||||
|
||||
if (m_lastConfigLocation.isEmpty()) {
|
||||
pluginInstance->restore(m_tempConfig);
|
||||
} else {
|
||||
KConfigGroup cfg = m_containment->containmentActionsConfig();
|
||||
cfg = KConfigGroup(&cfg, m_lastConfigLocation);
|
||||
pluginInstance->restore(cfg);
|
||||
}
|
||||
}
|
||||
|
||||
if (!m_configDlg) {
|
||||
m_configDlg = new QDialog(qobject_cast<QWidget*>(parent()));
|
||||
QLayout *lay = new QVBoxLayout(m_configDlg);
|
||||
m_configDlg->setLayout(lay);
|
||||
m_configDlg->setWindowModality(Qt::WindowModal);
|
||||
|
||||
//put the config in the dialog
|
||||
QWidget *w = m_pluginInstance.data()->createConfigurationInterface(m_configDlg);
|
||||
if (w) {
|
||||
lay->addWidget(w);
|
||||
}
|
||||
const QString title = w->windowTitle();
|
||||
|
||||
m_configDlg->setWindowTitle(title.isEmpty() ? i18n("Configure Plugin") :title);
|
||||
//put buttons below
|
||||
QDialogButtonBox *buttons = new QDialogButtonBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel,
|
||||
Qt::Horizontal, m_configDlg);
|
||||
lay->addWidget(buttons);
|
||||
|
||||
//TODO other signals?
|
||||
connect(buttons, SIGNAL(accepted()), this, SLOT(acceptConfig()));
|
||||
connect(buttons, SIGNAL(rejected()), this, SLOT(rejectConfig()));
|
||||
}
|
||||
|
||||
m_configDlg->show();
|
||||
}
|
||||
|
||||
void MousePluginWidget::acceptConfig()
|
||||
{
|
||||
kDebug() << "accept";
|
||||
if (m_pluginInstance) {
|
||||
m_pluginInstance.data()->configurationAccepted();
|
||||
}
|
||||
|
||||
m_configDlg->deleteLater();
|
||||
m_configDlg = 0;
|
||||
emit configChanged(m_triggerButton->trigger());
|
||||
}
|
||||
|
||||
void MousePluginWidget::rejectConfig()
|
||||
{
|
||||
kDebug() << "reject";
|
||||
m_configDlg->deleteLater();
|
||||
m_configDlg = 0;
|
||||
}
|
||||
|
||||
void MousePluginWidget::prepareForSave()
|
||||
{
|
||||
if (!m_configButton->isVisible() || m_pluginInstance || m_lastConfigLocation.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
//back up our config because it'll be erased for saving
|
||||
KConfigGroup cfg = m_containment->containmentActionsConfig();
|
||||
cfg = KConfigGroup(&cfg, m_lastConfigLocation);
|
||||
cfg.copyTo(&m_tempConfig);
|
||||
//kDebug() << "copied to temp";
|
||||
}
|
||||
|
||||
void MousePluginWidget::save()
|
||||
{
|
||||
const QString trigger = m_triggerButton->trigger();
|
||||
if (trigger.isEmpty()) {
|
||||
m_lastConfigLocation.clear();
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_pluginInstance || !m_lastConfigLocation.isEmpty()) {
|
||||
KConfigGroup cfg = m_containment->containmentActionsConfig();
|
||||
cfg = KConfigGroup(&cfg, trigger);
|
||||
if (m_pluginInstance) {
|
||||
m_pluginInstance.data()->save(cfg);
|
||||
} else {
|
||||
m_tempConfig.copyTo(&cfg);
|
||||
}
|
||||
m_lastConfigLocation = trigger;
|
||||
}
|
||||
m_containment->setContainmentActions(trigger, m_plugin.pluginName());
|
||||
}
|
||||
|
||||
//copied from appletbrowser.cpp
|
||||
//FIXME add a feature to KAboutApplicationDialog to delete the object
|
||||
/* This is just a wrapper around KAboutApplicationDialog that deletes
|
||||
the KAboutData object that it is associated with, when it is deleted.
|
||||
This is required to free memory correctly when KAboutApplicationDialog
|
||||
is called with a temporary KAboutData that is allocated on the heap.
|
||||
(see the code below, in AppletBrowserWidget::infoAboutApplet())
|
||||
*/
|
||||
class KAboutApplicationDialog2 : public KAboutApplicationDialog
|
||||
{
|
||||
public:
|
||||
KAboutApplicationDialog2(KAboutData *ab, QWidget *parent = 0)
|
||||
: KAboutApplicationDialog(ab, parent), m_ab(ab) {}
|
||||
|
||||
~KAboutApplicationDialog2()
|
||||
{
|
||||
delete m_ab;
|
||||
}
|
||||
|
||||
private:
|
||||
KAboutData *m_ab;
|
||||
};
|
||||
|
||||
void MousePluginWidget::showAbout()
|
||||
{
|
||||
KAboutData *aboutData = new KAboutData(m_plugin.name().toUtf8(),
|
||||
m_plugin.name().toUtf8(),
|
||||
ki18n(m_plugin.name().toUtf8()),
|
||||
m_plugin.version().toUtf8(), ki18n(m_plugin.comment().toUtf8()),
|
||||
m_plugin.fullLicense().key(), ki18n(QByteArray()), ki18n(QByteArray()), m_plugin.website().toLatin1(),
|
||||
m_plugin.email().toLatin1());
|
||||
|
||||
aboutData->setProgramIconName(m_plugin.icon());
|
||||
|
||||
aboutData->addAuthor(ki18n(m_plugin.author().toUtf8()), ki18n(QByteArray()), m_plugin.email().toLatin1());
|
||||
|
||||
KAboutApplicationDialog *aboutDialog = new KAboutApplicationDialog2(aboutData, qobject_cast<QWidget*>(parent()));
|
||||
aboutDialog->show();
|
||||
}
|
||||
|
||||
// vim: sw=4 sts=4 et tw=100
|
@ -1,75 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 2009 Chani Armitage <chani@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef MOUSEPLUGINWIDGET_H
|
||||
#define MOUSEPLUGINWIDGET_H
|
||||
|
||||
#include <QDialog>
|
||||
#include <QLabel>
|
||||
#include <QToolButton>
|
||||
|
||||
#include <kconfiggroup.h>
|
||||
|
||||
#include <plasma/containmentactions.h>
|
||||
#include "mouseinputbutton.h"
|
||||
|
||||
class QComboBox;
|
||||
class QGridLayout;
|
||||
|
||||
class MousePluginWidget : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
MousePluginWidget(const QString &plugin, const QString &trigger, QGridLayout *layoutHack, QWidget *parent = 0);
|
||||
~MousePluginWidget();
|
||||
|
||||
void setTrigger(const QString &trigger);
|
||||
void prepareForSave();
|
||||
void save();
|
||||
|
||||
signals:
|
||||
void triggerChanged(const QString &oldTrigger, const QString &newTrigger);
|
||||
void configChanged(const QString &trigger);
|
||||
|
||||
|
||||
private slots:
|
||||
void changeTrigger(const QString &oldTrigger, const QString& newTrigger);
|
||||
|
||||
|
||||
void configure();
|
||||
void acceptConfig();
|
||||
void rejectConfig();
|
||||
void showAbout();
|
||||
|
||||
private:
|
||||
void updateConfig(const QString &trigger);
|
||||
|
||||
QComboBox *m_pluginList;
|
||||
QDialog *m_configDlg;
|
||||
|
||||
KPluginInfo m_plugin;
|
||||
QWeakPointer<Plasma::ContainmentActions> m_pluginInstance;
|
||||
Plasma::Containment *m_containment;
|
||||
QString m_lastConfigLocation;
|
||||
KConfigGroup m_tempConfig;
|
||||
KConfig m_tempConfigParent;
|
||||
|
||||
};
|
||||
#endif
|
||||
|
@ -1,133 +0,0 @@
|
||||
/*
|
||||
* Copyright 2014 (c) Martin Klapetek <mklapetek@kde.org>
|
||||
*
|
||||
* 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 2 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, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "osd.h"
|
||||
#include "shellpluginloader.h"
|
||||
#include "shellcorona.h"
|
||||
|
||||
#include <QDBusConnection>
|
||||
#include <QTimer>
|
||||
#include <QWindow>
|
||||
#include <QDebug>
|
||||
#include <QUrl>
|
||||
|
||||
#include <Plasma/Package>
|
||||
#include <KDeclarative/QmlObject>
|
||||
#include <klocalizedstring.h>
|
||||
|
||||
|
||||
Osd::Osd(ShellCorona *corona)
|
||||
: QObject(corona)
|
||||
{
|
||||
const QString osdPath = corona->lookAndFeelPackage().filePath("osdmainscript");
|
||||
if (osdPath.isEmpty()) {
|
||||
qWarning() << "Failed to load the OSD script file from" << osdPath;
|
||||
return;
|
||||
}
|
||||
|
||||
m_osdObject = new KDeclarative::QmlObject(this);
|
||||
m_osdObject->setSource(QUrl::fromLocalFile(osdPath));
|
||||
m_timeout = m_osdObject->rootObject()->property("timeout").toInt();
|
||||
|
||||
QDBusConnection::sessionBus().registerObject("/org/kde/osdService", this, QDBusConnection::ExportAllSlots);
|
||||
|
||||
m_osdTimer = new QTimer(this);
|
||||
m_osdTimer->setSingleShot(true);
|
||||
connect(m_osdTimer, SIGNAL(timeout()),
|
||||
this, SLOT(hideOsd()));
|
||||
}
|
||||
|
||||
Osd::~Osd()
|
||||
{
|
||||
}
|
||||
|
||||
void Osd::brightnessChanged(int percent)
|
||||
{
|
||||
// FIXME: need brightness icon
|
||||
showProgress(QString(), percent);
|
||||
}
|
||||
|
||||
void Osd::volumeChanged(int percent)
|
||||
{
|
||||
QString icon;
|
||||
if (percent >= 75) {
|
||||
icon = QStringLiteral("audio-volume-high");
|
||||
} else if (percent < 75 && percent >= 25) {
|
||||
icon = QStringLiteral("audio-volume-medium");
|
||||
} else if (percent < 25 && percent > 0) {
|
||||
icon = QStringLiteral("audio-volume-low");
|
||||
} else if (percent == 0) {
|
||||
icon = QStringLiteral("audio-volume-muted");
|
||||
showText(icon, i18n("Audio Muted"));
|
||||
return;
|
||||
}
|
||||
|
||||
showProgress(icon, percent);
|
||||
}
|
||||
|
||||
void Osd::mediaPlayerVolumeChanged(int percent, const QString &playerName, const QString &playerIconName)
|
||||
{
|
||||
if (percent == 0) {
|
||||
showText(playerIconName, i18nc("OSD informing that some media app is muted, eg. Amarok Muted", "%1 Muted", playerName));
|
||||
} else {
|
||||
showProgress(playerIconName, percent, playerName);
|
||||
}
|
||||
}
|
||||
|
||||
void Osd::kbdLayoutChanged(const QString &layoutName)
|
||||
{
|
||||
//FIXME: need a kbd icon
|
||||
showText(QString(), layoutName);
|
||||
}
|
||||
|
||||
void Osd::virtualDesktopChanged(const QString ¤tVirtualDesktopName)
|
||||
{
|
||||
//FIXME: need a VD icon
|
||||
showText(QString(), currentVirtualDesktopName);
|
||||
}
|
||||
|
||||
void Osd::showProgress(const QString &icon, const int percent, const QString &additionalText)
|
||||
{
|
||||
int value = qBound(0, percent, 100);
|
||||
m_osdObject->rootObject()->setProperty("osdValue", value);
|
||||
m_osdObject->rootObject()->setProperty("osdAdditionalText", additionalText);
|
||||
m_osdObject->rootObject()->setProperty("showingProgress", true);
|
||||
m_osdObject->rootObject()->setProperty("icon", icon);
|
||||
|
||||
showOsd();
|
||||
}
|
||||
|
||||
void Osd::showText(const QString &icon, const QString &text)
|
||||
{
|
||||
m_osdObject->rootObject()->setProperty("osdValue", text);
|
||||
m_osdObject->rootObject()->setProperty("showingProgress", false);
|
||||
m_osdObject->rootObject()->setProperty("icon", icon);
|
||||
|
||||
showOsd();
|
||||
}
|
||||
|
||||
void Osd::showOsd()
|
||||
{
|
||||
m_osdObject->rootObject()->setProperty("visible", true);
|
||||
m_osdTimer->start(m_timeout);
|
||||
}
|
||||
|
||||
void Osd::hideOsd()
|
||||
{
|
||||
m_osdObject->rootObject()->setProperty("visible", false);
|
||||
}
|
@ -1,62 +0,0 @@
|
||||
/*
|
||||
* Copyright 2014 (c) Martin Klapetek <mklapetek@kde.org>
|
||||
*
|
||||
* 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 2 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, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef OSD_H
|
||||
#define OSD_H
|
||||
|
||||
#include <QObject>
|
||||
#include <QString>
|
||||
|
||||
namespace KDeclarative {
|
||||
class QmlObject;
|
||||
}
|
||||
namespace Plasma {
|
||||
class Package;
|
||||
}
|
||||
|
||||
class QTimer;
|
||||
class ShellCorona;
|
||||
|
||||
class Osd : public QObject {
|
||||
Q_OBJECT
|
||||
Q_CLASSINFO("D-Bus Interface", "org.kde.osdService")
|
||||
public:
|
||||
Osd(ShellCorona *corona);
|
||||
~Osd();
|
||||
|
||||
public Q_SLOTS:
|
||||
void brightnessChanged(int percent);
|
||||
void volumeChanged(int percent);
|
||||
void mediaPlayerVolumeChanged(int percent, const QString &playerName, const QString &playerIconName);
|
||||
void kbdLayoutChanged(const QString &layoutName);
|
||||
void virtualDesktopChanged(const QString ¤tVirtualDesktopName);
|
||||
|
||||
private Q_SLOTS:
|
||||
void hideOsd();
|
||||
|
||||
private:
|
||||
void showProgress(const QString &icon, const int percent, const QString &additionalText = QString());
|
||||
void showText(const QString &icon, const QString &text);
|
||||
void showOsd();
|
||||
|
||||
KDeclarative::QmlObject *m_osdObject;
|
||||
QTimer *m_osdTimer;
|
||||
int m_timeout;
|
||||
};
|
||||
|
||||
#endif // OSD_H
|
@ -1,145 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "panelconfigview.h"
|
||||
#include "panelview.h"
|
||||
#include "panelshadows_p.h"
|
||||
|
||||
#include <QDebug>
|
||||
#include <QDir>
|
||||
#include <QQmlComponent>
|
||||
#include <QQmlEngine>
|
||||
#include <QQmlContext>
|
||||
#include <QScreen>
|
||||
#include <QAction>
|
||||
|
||||
#include <klocalizedstring.h>
|
||||
#include <kwindoweffects.h>
|
||||
#include <KActionCollection>
|
||||
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/Corona>
|
||||
#include <Plasma/PluginLoader>
|
||||
|
||||
//////////////////////////////PanelConfigView
|
||||
PanelConfigView::PanelConfigView(Plasma::Containment *containment, PanelView *panelView, QWindow *parent)
|
||||
: ConfigView(containment, parent),
|
||||
m_containment(containment),
|
||||
m_panelView(panelView)
|
||||
{
|
||||
m_visibilityMode = panelView->visibilityMode();
|
||||
panelView->setVisibilityMode(PanelView::WindowsGoBelow);
|
||||
setScreen(panelView->screen());
|
||||
connect(panelView, &QWindow::screenChanged, [=](QScreen *screen){setScreen(screen); syncGeometry();});
|
||||
|
||||
setFlags(Qt::BypassWindowManagerHint);
|
||||
|
||||
KWindowEffects::enableBlurBehind(winId(), true);
|
||||
updateContrast();
|
||||
connect(&m_theme, &Plasma::Theme::themeChanged, this, &PanelConfigView::updateContrast);
|
||||
|
||||
engine()->rootContext()->setContextProperty("panel", panelView);
|
||||
engine()->rootContext()->setContextProperty("configDialog", this);
|
||||
connect(containment, &Plasma::Containment::formFactorChanged,
|
||||
this, &PanelConfigView::syncGeometry);
|
||||
|
||||
PanelShadows::self()->addWindow(this);
|
||||
}
|
||||
|
||||
PanelConfigView::~PanelConfigView()
|
||||
{
|
||||
m_panelView->setVisibilityMode(m_visibilityMode);
|
||||
PanelShadows::self()->removeWindow(this);
|
||||
}
|
||||
|
||||
void PanelConfigView::init()
|
||||
{
|
||||
setSource(QUrl::fromLocalFile(m_containment->corona()->package().filePath("panelconfigurationui")));
|
||||
syncGeometry();
|
||||
}
|
||||
|
||||
void PanelConfigView::updateContrast()
|
||||
{
|
||||
KWindowEffects::enableBackgroundContrast(winId(), m_theme.backgroundContrastEnabled(),
|
||||
m_theme.backgroundContrast(),
|
||||
m_theme.backgroundIntensity(),
|
||||
m_theme.backgroundSaturation());
|
||||
}
|
||||
|
||||
void PanelConfigView::showAddWidgetDialog()
|
||||
{
|
||||
QAction *addWidgetAction = m_containment->actions()->action("add widgets");
|
||||
if (addWidgetAction) {
|
||||
addWidgetAction->trigger();
|
||||
}
|
||||
}
|
||||
|
||||
void PanelConfigView::addPanelSpacer()
|
||||
{
|
||||
m_containment->createApplet("org.kde.plasma.panelspacer");
|
||||
}
|
||||
|
||||
void PanelConfigView::syncGeometry()
|
||||
{
|
||||
if (!m_containment || !rootObject()) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_containment->formFactor() == Plasma::Types::Vertical) {
|
||||
resize(rootObject()->implicitWidth(), screen()->size().height());
|
||||
|
||||
if (m_containment->location() == Plasma::Types::LeftEdge) {
|
||||
setPosition(m_panelView->geometry().right(), screen()->geometry().top());
|
||||
} else if (m_containment->location() == Plasma::Types::RightEdge) {
|
||||
setPosition(m_panelView->geometry().left() - width(), screen()->geometry().top());
|
||||
}
|
||||
|
||||
} else {
|
||||
resize(screen()->size().width(), rootObject()->implicitHeight());
|
||||
|
||||
if (m_containment->location() == Plasma::Types::TopEdge) {
|
||||
setPosition(screen()->geometry().left(), m_panelView->geometry().bottom());
|
||||
} else if (m_containment->location() == Plasma::Types::BottomEdge) {
|
||||
setPosition(screen()->geometry().left(), m_panelView->geometry().top() - height());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void PanelConfigView::focusOutEvent(QFocusEvent *ev)
|
||||
{
|
||||
Q_UNUSED(ev)
|
||||
close();
|
||||
}
|
||||
|
||||
void PanelConfigView::setVisibilityMode(PanelView::VisibilityMode mode)
|
||||
{
|
||||
if (m_visibilityMode == mode) {
|
||||
return;
|
||||
}
|
||||
|
||||
m_visibilityMode = mode;
|
||||
emit visibilityModeChanged();
|
||||
}
|
||||
|
||||
PanelView::VisibilityMode PanelConfigView::visibilityMode() const
|
||||
{
|
||||
return m_visibilityMode;
|
||||
}
|
||||
|
||||
#include "moc_panelconfigview.cpp"
|
@ -1,78 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef PANELCONFIGVIEW_H
|
||||
#define PANELCONFIGVIEW_H
|
||||
|
||||
#include "configview.h"
|
||||
#include "panelview.h"
|
||||
|
||||
#include <QQuickItem>
|
||||
#include <QQuickView>
|
||||
#include <QJSValue>
|
||||
#include <QQmlListProperty>
|
||||
#include <QStandardItemModel>
|
||||
#include <Plasma/Theme>
|
||||
|
||||
class AppletInterface;
|
||||
class ConfigPropertyMap;
|
||||
class PanelView;
|
||||
|
||||
namespace Plasma {
|
||||
class Containment;
|
||||
}
|
||||
|
||||
class PanelConfigView : public PlasmaQuick::ConfigView
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(PanelView::VisibilityMode visibilityMode READ visibilityMode WRITE setVisibilityMode NOTIFY visibilityModeChanged)
|
||||
|
||||
public:
|
||||
PanelConfigView(Plasma::Containment *interface, PanelView *panelView, QWindow *parent = 0);
|
||||
virtual ~PanelConfigView();
|
||||
|
||||
void init();
|
||||
|
||||
PanelView::VisibilityMode visibilityMode() const;
|
||||
void setVisibilityMode(PanelView::VisibilityMode mode);
|
||||
|
||||
public Q_SLOTS:
|
||||
void showAddWidgetDialog();
|
||||
void addPanelSpacer();
|
||||
|
||||
protected:
|
||||
void focusOutEvent(QFocusEvent *ev);
|
||||
|
||||
protected Q_SLOTS:
|
||||
void syncGeometry();
|
||||
|
||||
private Q_SLOTS:
|
||||
void updateContrast();
|
||||
|
||||
Q_SIGNALS:
|
||||
void visibilityModeChanged();
|
||||
|
||||
private:
|
||||
Plasma::Containment *m_containment;
|
||||
PanelView *m_panelView;
|
||||
PanelView::VisibilityMode m_visibilityMode;
|
||||
Plasma::Theme m_theme;
|
||||
};
|
||||
|
||||
#endif // multiple inclusion guard
|
@ -1,506 +0,0 @@
|
||||
/*
|
||||
* Copyright 2011 by Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License version 2,
|
||||
* 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "panelshadows_p.h"
|
||||
|
||||
#include <QWindow>
|
||||
#include <QPainter>
|
||||
|
||||
#include <config-plasma.h>
|
||||
#if HAVE_X11
|
||||
#include <QX11Info>
|
||||
#include <X11/Xatom.h>
|
||||
#include <X11/Xlib.h>
|
||||
#include <X11/Xlib-xcb.h>
|
||||
#include <fixx11h.h>
|
||||
#endif
|
||||
|
||||
#include <qdebug.h>
|
||||
|
||||
class PanelShadows::Private
|
||||
{
|
||||
public:
|
||||
Private(PanelShadows *shadows)
|
||||
: q(shadows)
|
||||
#if HAVE_X11
|
||||
,_connection( 0x0 ),
|
||||
_gc( 0x0 )
|
||||
, m_isX11(QX11Info::isPlatformX11())
|
||||
#endif
|
||||
{
|
||||
}
|
||||
|
||||
~Private()
|
||||
{
|
||||
// Do not call clearPixmaps() from here: it creates new QPixmap(),
|
||||
// which causes a crash when application is stopping.
|
||||
freeX11Pixmaps();
|
||||
}
|
||||
|
||||
void freeX11Pixmaps();
|
||||
void clearPixmaps();
|
||||
void setupPixmaps();
|
||||
Qt::HANDLE createPixmap(const QPixmap& source);
|
||||
void initPixmap(const QString &element);
|
||||
QPixmap initEmptyPixmap(const QSize &size);
|
||||
void updateShadow(const QWindow *window, Plasma::FrameSvg::EnabledBorders);
|
||||
void clearShadow(const QWindow *window);
|
||||
void updateShadows();
|
||||
void windowDestroyed(QObject *deletedObject);
|
||||
void setupData(Plasma::FrameSvg::EnabledBorders enabledBorders);
|
||||
|
||||
PanelShadows *q;
|
||||
QList<QPixmap> m_shadowPixmaps;
|
||||
|
||||
QPixmap m_emptyCornerPix;
|
||||
QPixmap m_emptyCornerLeftPix;
|
||||
QPixmap m_emptyCornerTopPix;
|
||||
QPixmap m_emptyCornerRightPix;
|
||||
QPixmap m_emptyCornerBottomPix;
|
||||
QPixmap m_emptyVerticalPix;
|
||||
QPixmap m_emptyHorizontalPix;
|
||||
|
||||
#if HAVE_X11
|
||||
//! xcb connection
|
||||
xcb_connection_t* _connection;
|
||||
|
||||
//! graphical context
|
||||
xcb_gcontext_t _gc;
|
||||
bool m_isX11;
|
||||
#endif
|
||||
|
||||
QHash<Plasma::FrameSvg::EnabledBorders, QVector<unsigned long> > data;
|
||||
QHash<const QWindow *, Plasma::FrameSvg::EnabledBorders> m_windows;
|
||||
};
|
||||
|
||||
class DialogShadowsSingleton
|
||||
{
|
||||
public:
|
||||
DialogShadowsSingleton()
|
||||
{
|
||||
}
|
||||
|
||||
PanelShadows self;
|
||||
};
|
||||
|
||||
Q_GLOBAL_STATIC(DialogShadowsSingleton, privateDialogShadowsSelf)
|
||||
|
||||
PanelShadows::PanelShadows(QObject *parent, const QString &prefix)
|
||||
: Plasma::Svg(parent),
|
||||
d(new Private(this))
|
||||
{
|
||||
setImagePath(prefix);
|
||||
connect(this, SIGNAL(repaintNeeded()), this, SLOT(updateShadows()));
|
||||
}
|
||||
|
||||
PanelShadows::~PanelShadows()
|
||||
{
|
||||
delete d;
|
||||
}
|
||||
|
||||
PanelShadows *PanelShadows::self()
|
||||
{
|
||||
return &privateDialogShadowsSelf->self;
|
||||
}
|
||||
|
||||
void PanelShadows::addWindow(const QWindow *window, Plasma::FrameSvg::EnabledBorders enabledBorders)
|
||||
{
|
||||
if (!window) {
|
||||
return;
|
||||
}
|
||||
|
||||
d->m_windows[window] = enabledBorders;
|
||||
d->updateShadow(window, enabledBorders);
|
||||
connect(window, SIGNAL(destroyed(QObject*)),
|
||||
this, SLOT(windowDestroyed(QObject*)), Qt::UniqueConnection);
|
||||
}
|
||||
|
||||
void PanelShadows::removeWindow(const QWindow *window)
|
||||
{
|
||||
if (!d->m_windows.contains(window)) {
|
||||
return;
|
||||
}
|
||||
|
||||
d->m_windows.remove(window);
|
||||
disconnect(window, 0, this, 0);
|
||||
d->clearShadow(window);
|
||||
|
||||
if (d->m_windows.isEmpty()) {
|
||||
d->clearPixmaps();
|
||||
}
|
||||
}
|
||||
|
||||
void PanelShadows::Private::windowDestroyed(QObject *deletedObject)
|
||||
{
|
||||
m_windows.remove(static_cast<QWindow *>(deletedObject));
|
||||
|
||||
if (m_windows.isEmpty()) {
|
||||
clearPixmaps();
|
||||
}
|
||||
}
|
||||
|
||||
void PanelShadows::Private::updateShadows()
|
||||
{
|
||||
setupPixmaps();
|
||||
QHash<const QWindow *, Plasma::FrameSvg::EnabledBorders>::const_iterator i;
|
||||
for (i = m_windows.constBegin(); i != m_windows.constEnd(); ++i) {
|
||||
updateShadow(i.key(), i.value());
|
||||
}
|
||||
}
|
||||
|
||||
Qt::HANDLE PanelShadows::Private::createPixmap(const QPixmap& source)
|
||||
{
|
||||
|
||||
// do nothing for invalid pixmaps
|
||||
if( source.isNull() ) return 0;
|
||||
|
||||
/*
|
||||
in some cases, pixmap handle is invalid. This is the case notably
|
||||
when Qt uses to RasterEngine. In this case, we create an X11 Pixmap
|
||||
explicitly and draw the source pixmap on it.
|
||||
*/
|
||||
|
||||
#if HAVE_X11
|
||||
if (!m_isX11) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
// check connection
|
||||
if( !_connection ) _connection = QX11Info::connection();
|
||||
|
||||
const int width( source.width() );
|
||||
const int height( source.height() );
|
||||
|
||||
// create X11 pixmap
|
||||
Pixmap pixmap = XCreatePixmap( QX11Info::display(), QX11Info::appRootWindow(), width, height, 32 );
|
||||
|
||||
// check gc
|
||||
if( !_gc )
|
||||
{
|
||||
_gc = xcb_generate_id( _connection );
|
||||
xcb_create_gc( _connection, _gc, pixmap, 0, 0x0 );
|
||||
}
|
||||
|
||||
// // create explicitly shared QPixmap from it
|
||||
// QPixmap dest( QPixmap::fromX11Pixmap( pixmap, QPixmap::ExplicitlyShared ) );
|
||||
//
|
||||
// // create surface for pixmap
|
||||
// {
|
||||
// QPainter painter( &dest );
|
||||
// painter.setCompositionMode( QPainter::CompositionMode_Source );
|
||||
// painter.drawPixmap( 0, 0, source );
|
||||
// }
|
||||
//
|
||||
//
|
||||
// return pixmap;
|
||||
QImage image( source.toImage() );
|
||||
xcb_put_image(
|
||||
_connection, XCB_IMAGE_FORMAT_Z_PIXMAP, pixmap, _gc,
|
||||
image.width(), image.height(), 0, 0,
|
||||
0, 32,
|
||||
image.byteCount(), image.constBits());
|
||||
|
||||
return (Qt::HANDLE)pixmap;
|
||||
|
||||
#else
|
||||
return 0;
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
void PanelShadows::Private::initPixmap(const QString &element)
|
||||
{
|
||||
m_shadowPixmaps << q->pixmap(element);
|
||||
}
|
||||
|
||||
QPixmap PanelShadows::Private::initEmptyPixmap(const QSize &size)
|
||||
{
|
||||
#if HAVE_X11
|
||||
if (!m_isX11) {
|
||||
return QPixmap();
|
||||
}
|
||||
QPixmap tempEmptyPix(size);
|
||||
if (!size.isEmpty()) {
|
||||
tempEmptyPix.fill(Qt::transparent);
|
||||
}
|
||||
return tempEmptyPix;
|
||||
#else
|
||||
Q_UNUSED(size)
|
||||
return QPixmap();
|
||||
#endif
|
||||
}
|
||||
|
||||
void PanelShadows::Private::setupPixmaps()
|
||||
{
|
||||
clearPixmaps();
|
||||
initPixmap("shadow-top");
|
||||
initPixmap("shadow-topright");
|
||||
initPixmap("shadow-right");
|
||||
initPixmap("shadow-bottomright");
|
||||
initPixmap("shadow-bottom");
|
||||
initPixmap("shadow-bottomleft");
|
||||
initPixmap("shadow-left");
|
||||
initPixmap("shadow-topleft");
|
||||
|
||||
m_emptyCornerPix = initEmptyPixmap(QSize(1,1));
|
||||
m_emptyCornerLeftPix = initEmptyPixmap(QSize(q->elementSize("shadow-topleft").width(), 1));
|
||||
m_emptyCornerTopPix = initEmptyPixmap(QSize(1, q->elementSize("shadow-topleft").height()));
|
||||
m_emptyCornerRightPix = initEmptyPixmap(QSize(q->elementSize("shadow-bottomright").width(), 1));
|
||||
m_emptyCornerBottomPix = initEmptyPixmap(QSize(1, q->elementSize("shadow-bottomright").height()));
|
||||
m_emptyVerticalPix = initEmptyPixmap(QSize(1, q->elementSize("shadow-left").height()));
|
||||
m_emptyHorizontalPix = initEmptyPixmap(QSize(q->elementSize("shadow-top").width(), 1));
|
||||
|
||||
}
|
||||
|
||||
|
||||
void PanelShadows::Private::setupData(Plasma::FrameSvg::EnabledBorders enabledBorders)
|
||||
{
|
||||
#if HAVE_X11
|
||||
if (!m_isX11) {
|
||||
return;
|
||||
}
|
||||
//shadow-top
|
||||
if (enabledBorders & Plasma::FrameSvg::TopBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_shadowPixmaps[0]));
|
||||
} else {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyHorizontalPix));
|
||||
}
|
||||
|
||||
//shadow-topright
|
||||
if (enabledBorders & Plasma::FrameSvg::TopBorder &&
|
||||
enabledBorders & Plasma::FrameSvg::RightBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_shadowPixmaps[1]));
|
||||
} else if (enabledBorders & Plasma::FrameSvg::TopBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerTopPix));
|
||||
} else if (enabledBorders & Plasma::FrameSvg::RightBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerRightPix));
|
||||
} else {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerPix));
|
||||
}
|
||||
|
||||
//shadow-right
|
||||
if (enabledBorders & Plasma::FrameSvg::RightBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_shadowPixmaps[2]));
|
||||
} else {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyVerticalPix));
|
||||
}
|
||||
|
||||
//shadow-bottomright
|
||||
if (enabledBorders & Plasma::FrameSvg::BottomBorder &&
|
||||
enabledBorders & Plasma::FrameSvg::RightBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_shadowPixmaps[3]));
|
||||
} else if (enabledBorders & Plasma::FrameSvg::BottomBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerBottomPix));
|
||||
} else if (enabledBorders & Plasma::FrameSvg::RightBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerRightPix));
|
||||
} else {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerPix));
|
||||
}
|
||||
|
||||
//shadow-bottom
|
||||
if (enabledBorders & Plasma::FrameSvg::BottomBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_shadowPixmaps[4]));
|
||||
} else {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyHorizontalPix));
|
||||
}
|
||||
|
||||
//shadow-bottomleft
|
||||
if (enabledBorders & Plasma::FrameSvg::BottomBorder &&
|
||||
enabledBorders & Plasma::FrameSvg::LeftBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_shadowPixmaps[5]));
|
||||
} else if (enabledBorders & Plasma::FrameSvg::BottomBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerBottomPix));
|
||||
} else if (enabledBorders & Plasma::FrameSvg::LeftBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerLeftPix));
|
||||
} else {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerPix));
|
||||
}
|
||||
|
||||
//shadow-left
|
||||
if (enabledBorders & Plasma::FrameSvg::LeftBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_shadowPixmaps[6]));
|
||||
} else {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyVerticalPix));
|
||||
}
|
||||
|
||||
//shadow-topleft
|
||||
if (enabledBorders & Plasma::FrameSvg::TopBorder &&
|
||||
enabledBorders & Plasma::FrameSvg::LeftBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_shadowPixmaps[7]));
|
||||
} else if (enabledBorders & Plasma::FrameSvg::TopBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerTopPix));
|
||||
} else if (enabledBorders & Plasma::FrameSvg::LeftBorder) {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerLeftPix));
|
||||
} else {
|
||||
data[enabledBorders] << reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerPix));
|
||||
}
|
||||
#endif
|
||||
|
||||
int left, top, right, bottom = 0;
|
||||
|
||||
QSize marginHint;
|
||||
if (enabledBorders & Plasma::FrameSvg::TopBorder) {
|
||||
marginHint = q->elementSize("shadow-hint-top-margin");
|
||||
if (marginHint.isValid()) {
|
||||
top = marginHint.height();
|
||||
} else {
|
||||
top = m_shadowPixmaps[0].height(); // top
|
||||
}
|
||||
} else {
|
||||
top = 1;
|
||||
}
|
||||
|
||||
if (enabledBorders & Plasma::FrameSvg::RightBorder) {
|
||||
marginHint = q->elementSize("shadow-hint-right-margin");
|
||||
if (marginHint.isValid()) {
|
||||
right = marginHint.width();
|
||||
} else {
|
||||
right = m_shadowPixmaps[2].width(); // right
|
||||
}
|
||||
} else {
|
||||
right = 1;
|
||||
}
|
||||
|
||||
if (enabledBorders & Plasma::FrameSvg::BottomBorder) {
|
||||
marginHint = q->elementSize("shadow-hint-bottom-margin");
|
||||
if (marginHint.isValid()) {
|
||||
bottom = marginHint.height();
|
||||
} else {
|
||||
bottom = m_shadowPixmaps[4].height(); // bottom
|
||||
}
|
||||
} else {
|
||||
bottom = 1;
|
||||
}
|
||||
|
||||
if (enabledBorders & Plasma::FrameSvg::LeftBorder) {
|
||||
marginHint = q->elementSize("shadow-hint-left-margin");
|
||||
if (marginHint.isValid()) {
|
||||
left = marginHint.width();
|
||||
} else {
|
||||
left = m_shadowPixmaps[6].width(); // left
|
||||
}
|
||||
} else {
|
||||
left = 1;
|
||||
}
|
||||
|
||||
data[enabledBorders] << top << right << bottom << left;
|
||||
}
|
||||
|
||||
void PanelShadows::Private::freeX11Pixmaps()
|
||||
{
|
||||
#if HAVE_X11
|
||||
if (!m_isX11) {
|
||||
return;
|
||||
}
|
||||
foreach (const QPixmap &pixmap, m_shadowPixmaps) {
|
||||
if (!QX11Info::display()) {
|
||||
return;
|
||||
}
|
||||
if (!pixmap.isNull()) {
|
||||
XFreePixmap(QX11Info::display(), reinterpret_cast<unsigned long>(createPixmap(pixmap)));
|
||||
}
|
||||
}
|
||||
|
||||
if (!m_emptyCornerPix.isNull()) {
|
||||
XFreePixmap(QX11Info::display(), reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerPix)));
|
||||
}
|
||||
if (!m_emptyCornerBottomPix.isNull()) {
|
||||
XFreePixmap(QX11Info::display(), reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerBottomPix)));
|
||||
}
|
||||
if (!m_emptyCornerLeftPix.isNull()) {
|
||||
XFreePixmap(QX11Info::display(), reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerLeftPix)));
|
||||
}
|
||||
if (!m_emptyCornerRightPix.isNull()) {
|
||||
XFreePixmap(QX11Info::display(), reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerRightPix)));
|
||||
}
|
||||
if (!m_emptyCornerTopPix.isNull()) {
|
||||
XFreePixmap(QX11Info::display(), reinterpret_cast<unsigned long>(createPixmap(m_emptyCornerTopPix)));
|
||||
}
|
||||
if (!m_emptyVerticalPix.isNull()) {
|
||||
XFreePixmap(QX11Info::display(), reinterpret_cast<unsigned long>(createPixmap(m_emptyVerticalPix)));
|
||||
}
|
||||
if (!m_emptyHorizontalPix.isNull()) {
|
||||
XFreePixmap(QX11Info::display(), reinterpret_cast<unsigned long>(createPixmap(m_emptyHorizontalPix)));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void PanelShadows::Private::clearPixmaps()
|
||||
{
|
||||
#if HAVE_X11
|
||||
freeX11Pixmaps();
|
||||
|
||||
m_emptyCornerPix = QPixmap();
|
||||
m_emptyCornerBottomPix = QPixmap();
|
||||
m_emptyCornerLeftPix = QPixmap();
|
||||
m_emptyCornerRightPix = QPixmap();
|
||||
m_emptyCornerTopPix = QPixmap();
|
||||
m_emptyVerticalPix = QPixmap();
|
||||
m_emptyHorizontalPix = QPixmap();
|
||||
#endif
|
||||
m_shadowPixmaps.clear();
|
||||
data.clear();
|
||||
}
|
||||
|
||||
void PanelShadows::Private::updateShadow(const QWindow *window, Plasma::FrameSvg::EnabledBorders enabledBorders)
|
||||
{
|
||||
#if HAVE_X11
|
||||
if (!m_isX11) {
|
||||
return;
|
||||
}
|
||||
if (m_shadowPixmaps.isEmpty()) {
|
||||
setupPixmaps();
|
||||
}
|
||||
|
||||
if (!data.contains(enabledBorders)) {
|
||||
setupData(enabledBorders);
|
||||
}
|
||||
|
||||
Display *dpy = QX11Info::display();
|
||||
Atom atom = XInternAtom(dpy, "_KDE_NET_WM_SHADOW", False);
|
||||
|
||||
qDebug() << "going to set the shadow of" << window->winId() << "to" << data;
|
||||
XChangeProperty(dpy, window->winId(), atom, XA_CARDINAL, 32, PropModeReplace,
|
||||
reinterpret_cast<const unsigned char *>(data[enabledBorders].constData()), data[enabledBorders].size());
|
||||
#else
|
||||
Q_UNUSED(window)
|
||||
Q_UNUSED(enabledBorders)
|
||||
#endif
|
||||
}
|
||||
|
||||
void PanelShadows::Private::clearShadow(const QWindow *window)
|
||||
{
|
||||
#if HAVE_X11
|
||||
if (!m_isX11) {
|
||||
return;
|
||||
}
|
||||
Display *dpy = QX11Info::display();
|
||||
Atom atom = XInternAtom(dpy, "_KDE_NET_WM_SHADOW", False);
|
||||
XDeleteProperty(dpy, window->winId(), atom);
|
||||
#else
|
||||
Q_UNUSED(window)
|
||||
#endif
|
||||
}
|
||||
|
||||
bool PanelShadows::enabled() const
|
||||
{
|
||||
return hasElement("shadow-left");
|
||||
}
|
||||
|
||||
#include "moc_panelshadows_p.cpp"
|
||||
|
@ -1,52 +0,0 @@
|
||||
/*
|
||||
* Copyright 2011 by Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License version 2,
|
||||
* 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef PLASMA_PANELSHADOWS_H
|
||||
#define PLASMA_PANELSHADOWS_H
|
||||
|
||||
#include <QSet>
|
||||
|
||||
#include "plasma/framesvg.h"
|
||||
#include "plasma/svg.h"
|
||||
|
||||
|
||||
class PanelShadows : public Plasma::Svg
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit PanelShadows(QObject *parent = 0, const QString &prefix = "widgets/panel-background");
|
||||
~PanelShadows();
|
||||
|
||||
static PanelShadows *self();
|
||||
|
||||
void addWindow(const QWindow *window, Plasma::FrameSvg::EnabledBorders enabledBorders = Plasma::FrameSvg::AllBorders);
|
||||
void removeWindow(const QWindow *window);
|
||||
|
||||
bool enabled() const;
|
||||
|
||||
private:
|
||||
class Private;
|
||||
Private * const d;
|
||||
|
||||
Q_PRIVATE_SLOT(d, void updateShadows())
|
||||
Q_PRIVATE_SLOT(d, void windowDestroyed(QObject *deletedObject))
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -1,757 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* 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 2 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, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include <config-plasma.h>
|
||||
|
||||
#include "panelview.h"
|
||||
#include "shellcorona.h"
|
||||
#include "panelshadows_p.h"
|
||||
#include "panelconfigview.h"
|
||||
|
||||
#include <QAction>
|
||||
#include <QApplication>
|
||||
#include <QDebug>
|
||||
#include <QDesktopWidget>
|
||||
#include <QScreen>
|
||||
#include <QQmlEngine>
|
||||
#include <QQmlContext>
|
||||
#include <QTimer>
|
||||
|
||||
#include <kactioncollection.h>
|
||||
#include <kwindowsystem.h>
|
||||
#include <kwindoweffects.h>
|
||||
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/Package>
|
||||
|
||||
#if HAVE_X11
|
||||
#include <xcb/xcb.h>
|
||||
#include <QX11Info>
|
||||
#endif
|
||||
|
||||
PanelView::PanelView(ShellCorona *corona, QWindow *parent)
|
||||
: PlasmaQuick::View(corona, parent),
|
||||
m_offset(0),
|
||||
m_maxLength(0),
|
||||
m_minLength(0),
|
||||
m_distance(0),
|
||||
m_alignment(Qt::AlignLeft),
|
||||
m_corona(corona),
|
||||
m_strutsTimer(new QTimer(this)),
|
||||
m_visibilityMode(NormalPanel)
|
||||
{
|
||||
QSurfaceFormat format;
|
||||
format.setAlphaBufferSize(8);
|
||||
setFormat(format);
|
||||
setClearBeforeRendering(true);
|
||||
setColor(QColor(Qt::transparent));
|
||||
setFlags(Qt::FramelessWindowHint|Qt::WindowDoesNotAcceptFocus);
|
||||
KWindowSystem::setType(winId(), NET::Dock);
|
||||
setVisible(true);
|
||||
|
||||
themeChanged();
|
||||
connect(&m_theme, &Plasma::Theme::themeChanged, this, &PanelView::themeChanged);
|
||||
|
||||
m_positionPaneltimer.setSingleShot(true);
|
||||
m_positionPaneltimer.setInterval(150);
|
||||
connect(&m_positionPaneltimer, &QTimer::timeout,
|
||||
this, [=] () {
|
||||
restore();
|
||||
positionPanel();
|
||||
});
|
||||
|
||||
m_unhideTimer.setSingleShot(true);
|
||||
m_unhideTimer.setInterval(500);
|
||||
connect(&m_unhideTimer, &QTimer::timeout,
|
||||
this, &PanelView::updateUnhideTrigger);
|
||||
|
||||
//Screen management
|
||||
connect(this, &QWindow::screenChanged,
|
||||
this, &PanelView::screenChangedProxy);
|
||||
connect(this, &QWindow::screenChanged,
|
||||
this, &PanelView::positionPanel);
|
||||
connect(screen(), &QScreen::geometryChanged,
|
||||
this, &PanelView::positionPanel);
|
||||
connect(this, &PlasmaQuick::View::locationChanged,
|
||||
&m_positionPaneltimer, [=] () {
|
||||
m_positionPaneltimer.start();
|
||||
});
|
||||
connect(this, &PlasmaQuick::View::containmentChanged,
|
||||
this, &PanelView::positionPanel);
|
||||
connect(this, &PlasmaQuick::View::containmentChanged,
|
||||
this, [=] () {
|
||||
m_positionPaneltimer.start();
|
||||
});
|
||||
|
||||
|
||||
|
||||
if (!m_corona->package().isValid()) {
|
||||
qWarning() << "Invalid home screen package";
|
||||
}
|
||||
|
||||
m_strutsTimer->setSingleShot(true);
|
||||
connect(m_strutsTimer, &QTimer::timeout,
|
||||
this, &PanelView::updateStruts);
|
||||
connect(QApplication::desktop(), &QDesktopWidget::screenCountChanged,
|
||||
this, &PanelView::updateStruts);
|
||||
|
||||
setResizeMode(PlasmaQuick::View::SizeRootObjectToView);
|
||||
qmlRegisterType<QScreen>();
|
||||
engine()->rootContext()->setContextProperty("panel", this);
|
||||
setSource(QUrl::fromLocalFile(m_corona->package().filePath("views", "Panel.qml")));
|
||||
PanelShadows::self()->addWindow(this);
|
||||
}
|
||||
|
||||
PanelView::~PanelView()
|
||||
{
|
||||
if (containment()) {
|
||||
config().writeEntry("offset", m_offset);
|
||||
config().writeEntry("max", m_maxLength);
|
||||
config().writeEntry("min", m_minLength);
|
||||
if (formFactor() == Plasma::Types::Vertical) {
|
||||
config().writeEntry("length", size().height());
|
||||
config().writeEntry("thickness", size().width());
|
||||
} else {
|
||||
config().writeEntry("length", size().width());
|
||||
config().writeEntry("thickness", size().height());
|
||||
}
|
||||
config().writeEntry("alignment", (int)m_alignment);
|
||||
m_corona->requestApplicationConfigSync();
|
||||
m_corona->requestApplicationConfigSync();
|
||||
}
|
||||
PanelShadows::self()->removeWindow(this);
|
||||
}
|
||||
|
||||
KConfigGroup PanelView::config() const
|
||||
{
|
||||
if (!containment()) {
|
||||
return KConfigGroup();
|
||||
}
|
||||
KConfigGroup views(m_corona->applicationConfig(), "PlasmaViews");
|
||||
views = KConfigGroup(&views, QString("Panel %1").arg(containment()->id()));
|
||||
|
||||
if (containment()->formFactor() == Plasma::Types::Vertical) {
|
||||
return KConfigGroup(&views, "Types::Vertical" + QString::number(screen()->size().height()));
|
||||
//treat everything else as horizontal
|
||||
} else {
|
||||
return KConfigGroup(&views, "Horizontal" + QString::number(screen()->size().width()));
|
||||
}
|
||||
}
|
||||
|
||||
void PanelView::maximize()
|
||||
{
|
||||
int length;
|
||||
if (containment()->formFactor() == Plasma::Types::Vertical) {
|
||||
length = screen()->size().height();
|
||||
} else {
|
||||
length = screen()->size().width();
|
||||
}
|
||||
setOffset(0);
|
||||
setMinimumLength(length);
|
||||
setMaximumLength(length);
|
||||
}
|
||||
|
||||
Qt::Alignment PanelView::alignment() const
|
||||
{
|
||||
return m_alignment;
|
||||
}
|
||||
|
||||
void PanelView::setAlignment(Qt::Alignment alignment)
|
||||
{
|
||||
if (m_alignment == alignment) {
|
||||
return;
|
||||
}
|
||||
|
||||
m_alignment = alignment;
|
||||
config().writeEntry("alignment", (int)m_alignment);
|
||||
emit alignmentChanged();
|
||||
positionPanel();
|
||||
}
|
||||
|
||||
int PanelView::offset() const
|
||||
{
|
||||
return m_offset;
|
||||
}
|
||||
|
||||
void PanelView::setOffset(int offset)
|
||||
{
|
||||
if (m_offset == offset) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (formFactor() == Plasma::Types::Vertical) {
|
||||
if (offset + m_maxLength > screen()->size().height()) {
|
||||
setMaximumLength( -m_offset + screen()->size().height() );
|
||||
}
|
||||
} else {
|
||||
if (offset + m_maxLength > screen()->size().width()) {
|
||||
setMaximumLength( -m_offset + screen()->size().width() );
|
||||
}
|
||||
}
|
||||
|
||||
m_offset = offset;
|
||||
config().writeEntry("offset", m_offset);
|
||||
positionPanel();
|
||||
emit offsetChanged();
|
||||
m_corona->requestApplicationConfigSync();
|
||||
m_strutsTimer->start(STRUTSTIMERDELAY);
|
||||
}
|
||||
|
||||
int PanelView::thickness() const
|
||||
{
|
||||
return config().readEntry<int>("thickness", 30);
|
||||
}
|
||||
|
||||
void PanelView::setThickness(int value)
|
||||
{
|
||||
if (value == thickness()) {
|
||||
return;
|
||||
}
|
||||
|
||||
config().writeEntry("thickness", value);
|
||||
m_corona->requestApplicationConfigSync();
|
||||
positionPanel();
|
||||
}
|
||||
|
||||
int PanelView::length() const
|
||||
{
|
||||
return config().readEntry<int>("length",
|
||||
formFactor() == Plasma::Types::Vertical ?
|
||||
screen()->size().height() :
|
||||
screen()->size().width()
|
||||
);
|
||||
}
|
||||
|
||||
void PanelView::setLength(int value)
|
||||
{
|
||||
if (value == length()) {
|
||||
return;
|
||||
}
|
||||
|
||||
config().writeEntry("length", value);
|
||||
m_corona->requestApplicationConfigSync();
|
||||
positionPanel();
|
||||
}
|
||||
|
||||
int PanelView::maximumLength() const
|
||||
{
|
||||
return m_maxLength;
|
||||
}
|
||||
|
||||
void PanelView::setMaximumLength(int length)
|
||||
{
|
||||
if (length == m_maxLength) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_minLength > length) {
|
||||
setMinimumLength(length);
|
||||
}
|
||||
|
||||
if (formFactor() == Plasma::Types::Vertical) {
|
||||
setMaximumHeight(length);
|
||||
} else {
|
||||
setMaximumWidth(length);
|
||||
}
|
||||
config().writeEntry("maxLength", length);
|
||||
m_maxLength = length;
|
||||
emit maximumLengthChanged();
|
||||
positionPanel();
|
||||
m_corona->requestApplicationConfigSync();
|
||||
}
|
||||
|
||||
int PanelView::minimumLength() const
|
||||
{
|
||||
return m_minLength;
|
||||
}
|
||||
|
||||
void PanelView::setMinimumLength(int length)
|
||||
{
|
||||
if (length == m_minLength) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_maxLength < length) {
|
||||
setMaximumLength(length);
|
||||
}
|
||||
|
||||
if (formFactor() == Plasma::Types::Vertical) {
|
||||
setMinimumHeight(length);
|
||||
} else {
|
||||
setMinimumWidth(length);
|
||||
}
|
||||
config().writeEntry("minLength", length);
|
||||
m_minLength = length;
|
||||
positionPanel();
|
||||
emit minimumLengthChanged();
|
||||
m_corona->requestApplicationConfigSync();
|
||||
}
|
||||
|
||||
int PanelView::distance() const
|
||||
{
|
||||
return m_distance;
|
||||
}
|
||||
|
||||
void PanelView::setDistance(int dist)
|
||||
{
|
||||
if (m_distance == dist) {
|
||||
return;
|
||||
}
|
||||
|
||||
m_distance = dist;
|
||||
emit distanceChanged();
|
||||
positionPanel();
|
||||
}
|
||||
|
||||
void PanelView::setVisibilityMode(PanelView::VisibilityMode mode)
|
||||
{
|
||||
m_visibilityMode = mode;
|
||||
|
||||
if (mode == LetWindowsCover) {
|
||||
KWindowSystem::setState(winId(), NET::KeepBelow);
|
||||
} else {
|
||||
KWindowSystem::clearState(winId(), NET::KeepBelow);
|
||||
}
|
||||
//life is vastly simpler if we ensure we're visible now
|
||||
show();
|
||||
|
||||
disconnect(containment(), &Plasma::Applet::activated, this, &PanelView::unhide);
|
||||
if (!(mode == NormalPanel || mode == WindowsGoBelow)) {
|
||||
connect(containment(), &Plasma::Applet::activated, this, &PanelView::unhide);
|
||||
}
|
||||
|
||||
config().writeEntry("panelVisibility", (int)mode);
|
||||
|
||||
|
||||
updateStruts();
|
||||
|
||||
KWindowSystem::setOnAllDesktops(winId(), true);
|
||||
emit visibilityModeChanged();
|
||||
updateUnhideTrigger();
|
||||
}
|
||||
|
||||
PanelView::VisibilityMode PanelView::visibilityMode() const
|
||||
{
|
||||
return m_visibilityMode;
|
||||
}
|
||||
|
||||
void PanelView::positionPanel()
|
||||
{
|
||||
if (!containment()) {
|
||||
return;
|
||||
}
|
||||
|
||||
QScreen *s = screen();
|
||||
QPoint position;
|
||||
|
||||
switch (containment()->location()) {
|
||||
case Plasma::Types::TopEdge:
|
||||
containment()->setFormFactor(Plasma::Types::Horizontal);
|
||||
|
||||
switch (m_alignment) {
|
||||
case Qt::AlignCenter:
|
||||
position = QPoint(QPoint(s->geometry().center().x(), s->geometry().top()) + QPoint(m_offset - size().width()/2, m_distance));
|
||||
break;
|
||||
case Qt::AlignRight:
|
||||
position = QPoint(s->geometry().topRight() - QPoint(m_offset + size().width(), m_distance));
|
||||
break;
|
||||
case Qt::AlignLeft:
|
||||
default:
|
||||
position = QPoint(s->geometry().topLeft() + QPoint(m_offset, m_distance));
|
||||
}
|
||||
break;
|
||||
|
||||
case Plasma::Types::LeftEdge:
|
||||
containment()->setFormFactor(Plasma::Types::Vertical);
|
||||
|
||||
switch (m_alignment) {
|
||||
case Qt::AlignCenter:
|
||||
position = QPoint(QPoint(s->geometry().left(), s->geometry().center().y()) + QPoint(m_distance, m_offset));
|
||||
break;
|
||||
case Qt::AlignRight:
|
||||
position = QPoint(s->geometry().bottomLeft() - QPoint(m_distance, m_offset + size().height()));
|
||||
break;
|
||||
case Qt::AlignLeft:
|
||||
default:
|
||||
position = QPoint(s->geometry().topLeft() + QPoint(m_distance, m_offset));
|
||||
}
|
||||
break;
|
||||
|
||||
case Plasma::Types::RightEdge:
|
||||
containment()->setFormFactor(Plasma::Types::Vertical);
|
||||
|
||||
switch (m_alignment) {
|
||||
case Qt::AlignCenter:
|
||||
position = QPoint(QPoint(s->geometry().right(), s->geometry().center().y()) - QPoint(width() + m_distance, 0) + QPoint(0, m_offset - size().height()/2));
|
||||
break;
|
||||
case Qt::AlignRight:
|
||||
position = QPoint(s->geometry().bottomRight() - QPoint(width() + m_distance, 0) - QPoint(0, m_offset + size().height()));
|
||||
break;
|
||||
case Qt::AlignLeft:
|
||||
default:
|
||||
position = QPoint(s->geometry().topRight() - QPoint(width() + m_distance, 0) + QPoint(0, m_offset));
|
||||
}
|
||||
break;
|
||||
|
||||
case Plasma::Types::BottomEdge:
|
||||
default:
|
||||
containment()->setFormFactor(Plasma::Types::Horizontal);
|
||||
|
||||
switch (m_alignment) {
|
||||
case Qt::AlignCenter:
|
||||
position = QPoint(QPoint(s->geometry().center().x(), s->geometry().bottom() - height() - m_distance) + QPoint(m_offset - size().width()/2, 1));
|
||||
break;
|
||||
case Qt::AlignRight:
|
||||
position = QPoint(s->geometry().bottomRight() - QPoint(0, height() + m_distance) - QPoint(m_offset + size().width(), 1));
|
||||
break;
|
||||
case Qt::AlignLeft:
|
||||
default:
|
||||
position = QPoint(s->geometry().bottomLeft() - QPoint(0, height() + m_distance) + QPoint(m_offset, 1));
|
||||
}
|
||||
}
|
||||
m_strutsTimer->stop();
|
||||
m_strutsTimer->start(STRUTSTIMERDELAY);
|
||||
setMinimumSize(QSize(0, 0));
|
||||
setMaximumSize(screen()->size());
|
||||
|
||||
if (formFactor() == Plasma::Types::Vertical) {
|
||||
setGeometry(QRect(position, QSize(thickness(), length())));
|
||||
setMinimumSize(QSize(thickness(), m_minLength));
|
||||
setMaximumSize(QSize(thickness(), m_maxLength));
|
||||
|
||||
emit thicknessChanged();
|
||||
emit length();
|
||||
} else {
|
||||
setGeometry(QRect(position, QSize(length(), thickness())));
|
||||
setMinimumSize(QSize(m_minLength, thickness()));
|
||||
setMaximumSize(QSize(m_maxLength, thickness()));
|
||||
|
||||
emit thicknessChanged();
|
||||
emit length();
|
||||
}
|
||||
|
||||
updateUnhideTrigger();
|
||||
}
|
||||
|
||||
void PanelView::restore()
|
||||
{
|
||||
if (!containment()) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
connect(containment(), SIGNAL(destroyed(QObject *)),
|
||||
this, SLOT(deleteLater()));
|
||||
|
||||
static const int MINSIZE = 10;
|
||||
|
||||
m_offset = config().readEntry<int>("offset", 0);
|
||||
if (m_alignment != Qt::AlignCenter) {
|
||||
m_offset = qMax(0, m_offset);
|
||||
}
|
||||
|
||||
m_alignment = (Qt::Alignment)config().readEntry<int>("alignment", Qt::AlignLeft);
|
||||
|
||||
setMinimumSize(QSize(-1, -1));
|
||||
//FIXME: an invalid size doesn't work with QWindows
|
||||
setMaximumSize(screen()->size());
|
||||
|
||||
if (containment()->formFactor() == Plasma::Types::Vertical) {
|
||||
m_maxLength = config().readEntry<int>("maxLength", screen()->size().height());
|
||||
m_minLength = config().readEntry<int>("minLength", screen()->size().height());
|
||||
|
||||
const int maxSize = screen()->size().height() - m_offset;
|
||||
m_maxLength = qBound<int>(MINSIZE, m_maxLength, maxSize);
|
||||
m_minLength = qBound<int>(MINSIZE, m_minLength, maxSize);
|
||||
|
||||
resize(thickness(), qBound<int>(MINSIZE, length(), maxSize));
|
||||
|
||||
setMinimumHeight(m_minLength);
|
||||
setMaximumHeight(m_maxLength);
|
||||
|
||||
//Horizontal
|
||||
} else {
|
||||
m_maxLength = config().readEntry<int>("maxLength", screen()->size().width());
|
||||
m_minLength = config().readEntry<int>("minLength", screen()->size().width());
|
||||
|
||||
const int maxSize = screen()->size().width() - m_offset;
|
||||
m_maxLength = qBound<int>(MINSIZE, m_maxLength, maxSize);
|
||||
m_minLength = qBound<int>(MINSIZE, m_minLength, maxSize);
|
||||
|
||||
resize(qBound<int>(MINSIZE, length(), maxSize), thickness());
|
||||
|
||||
setMinimumWidth(m_minLength);
|
||||
setMaximumWidth(m_maxLength);
|
||||
}
|
||||
|
||||
setVisibilityMode((VisibilityMode)config().readEntry<int>("panelVisibility", (int)NormalPanel));
|
||||
|
||||
emit maximumLengthChanged();
|
||||
emit minimumLengthChanged();
|
||||
emit offsetChanged();
|
||||
emit alignmentChanged();
|
||||
}
|
||||
|
||||
void PanelView::showConfigurationInterface(Plasma::Applet *applet)
|
||||
{
|
||||
if (m_panelConfigView) {
|
||||
m_panelConfigView.data()->hide();
|
||||
m_panelConfigView.data()->deleteLater();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!applet || !applet->containment()) {
|
||||
return;
|
||||
}
|
||||
|
||||
Plasma::Containment *cont = qobject_cast<Plasma::Containment *>(applet);
|
||||
|
||||
if (cont) {
|
||||
m_panelConfigView = new PanelConfigView(cont, this);
|
||||
} else {
|
||||
m_panelConfigView = new PlasmaQuick::ConfigView(applet);
|
||||
}
|
||||
m_panelConfigView.data()->init();
|
||||
m_panelConfigView.data()->show();
|
||||
KWindowSystem::setState(m_panelConfigView.data()->winId(), NET::SkipTaskbar | NET::SkipPager);
|
||||
}
|
||||
|
||||
void PanelView::updateUnhideTrigger()
|
||||
{
|
||||
#if HAVE_X11
|
||||
xcb_connection_t *c = QX11Info::connection();
|
||||
if (!c) {
|
||||
return;
|
||||
}
|
||||
|
||||
const QByteArray effectName = QByteArrayLiteral("_KDE_NET_WM_SCREEN_EDGE_SHOW");
|
||||
xcb_intern_atom_cookie_t atomCookie = xcb_intern_atom_unchecked(c, false, effectName.length(), effectName.constData());
|
||||
|
||||
QScopedPointer<xcb_intern_atom_reply_t, QScopedPointerPodDeleter> atom(xcb_intern_atom_reply(c, atomCookie, NULL));
|
||||
|
||||
if (!atom) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_visibilityMode != AutoHide) {
|
||||
xcb_delete_property(c, winId(), atom->atom);
|
||||
return;
|
||||
}
|
||||
|
||||
KWindowEffects::SlideFromLocation slideLocation = KWindowEffects::NoEdge;
|
||||
uint32_t value = 0;
|
||||
|
||||
switch (location()) {
|
||||
case Plasma::Types::TopEdge:
|
||||
value = 0;
|
||||
slideLocation = KWindowEffects::TopEdge;
|
||||
break;
|
||||
case Plasma::Types::RightEdge:
|
||||
value = 1;
|
||||
slideLocation = KWindowEffects::RightEdge;
|
||||
break;
|
||||
case Plasma::Types::BottomEdge:
|
||||
value = 2;
|
||||
slideLocation = KWindowEffects::BottomEdge;
|
||||
break;
|
||||
case Plasma::Types::LeftEdge:
|
||||
value = 3;
|
||||
slideLocation = KWindowEffects::LeftEdge;
|
||||
break;
|
||||
case Plasma::Types::Floating:
|
||||
default:
|
||||
value = 4;
|
||||
break;
|
||||
}
|
||||
|
||||
KWindowEffects::slideWindow(winId(), slideLocation, -1);
|
||||
xcb_change_property(c, XCB_PROP_MODE_REPLACE, winId(), atom->atom, XCB_ATOM_CARDINAL, 32, 1, &value);
|
||||
#endif
|
||||
}
|
||||
|
||||
void PanelView::resizeEvent(QResizeEvent *ev)
|
||||
{
|
||||
|
||||
if (containment()->formFactor() == Plasma::Types::Vertical) {
|
||||
config().writeEntry("length", ev->size().height());
|
||||
config().writeEntry("thickness", ev->size().width());
|
||||
if (ev->size().height() != ev->oldSize().height()) {
|
||||
emit lengthChanged();
|
||||
}
|
||||
if (ev->size().width() != ev->oldSize().width()) {
|
||||
emit thicknessChanged();
|
||||
}
|
||||
} else {
|
||||
config().writeEntry("length", ev->size().width());
|
||||
config().writeEntry("thickness", ev->size().height());
|
||||
if (ev->size().width() != ev->oldSize().width()) {
|
||||
emit lengthChanged();
|
||||
}
|
||||
if (ev->size().height() != ev->oldSize().height()) {
|
||||
emit thicknessChanged();
|
||||
}
|
||||
}
|
||||
|
||||
m_positionPaneltimer.start();
|
||||
PlasmaQuick::View::resizeEvent(ev);
|
||||
}
|
||||
|
||||
void PanelView::showEvent(QShowEvent *event)
|
||||
{
|
||||
PanelShadows::self()->addWindow(this);
|
||||
PlasmaQuick::View::showEvent(event);
|
||||
KWindowSystem::setOnAllDesktops(winId(), true);
|
||||
}
|
||||
|
||||
bool PanelView::event(QEvent *e)
|
||||
{
|
||||
if (e->type() == QEvent::Enter) {
|
||||
m_unhideTimer.stop();
|
||||
} else if (e->type() == QEvent::Leave) {
|
||||
m_unhideTimer.start();
|
||||
}
|
||||
return View::event(e);
|
||||
}
|
||||
|
||||
void PanelView::unhide()
|
||||
{
|
||||
m_unhideTimer.start();
|
||||
}
|
||||
|
||||
void PanelView::updateStruts()
|
||||
{
|
||||
if (!containment() || !screen()) {
|
||||
return;
|
||||
}
|
||||
|
||||
NETExtendedStrut strut;
|
||||
|
||||
if (m_visibilityMode == NormalPanel) {
|
||||
const QRect thisScreen = corona()->screenGeometry(containment()->screen());
|
||||
const QRect wholeScreen = screen()->virtualGeometry();
|
||||
|
||||
//Extended struts against a screen edge near to another screen are really harmful, so windows maximized under the panel is a lesser pain
|
||||
//TODO: force "windows can cover" in those cases?
|
||||
const int numScreens = corona()->numScreens();
|
||||
for (int i = 0; i < numScreens; ++i) {
|
||||
if (i == containment()->screen()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const QRect otherScreen = corona()->screenGeometry(i);
|
||||
|
||||
switch (location())
|
||||
{
|
||||
case Plasma::Types::TopEdge:
|
||||
if (otherScreen.bottom() <= thisScreen.top()) {
|
||||
KWindowSystem::setExtendedStrut(winId(), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case Plasma::Types::BottomEdge:
|
||||
if (otherScreen.top() >= thisScreen.bottom()) {
|
||||
KWindowSystem::setExtendedStrut(winId(), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case Plasma::Types::RightEdge:
|
||||
if (otherScreen.left() >= thisScreen.right()) {
|
||||
KWindowSystem::setExtendedStrut(winId(), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case Plasma::Types::LeftEdge:
|
||||
if (otherScreen.right() <= thisScreen.left()) {
|
||||
KWindowSystem::setExtendedStrut(winId(), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
}
|
||||
// extended struts are to the combined screen geoms, not the single screen
|
||||
int leftOffset = wholeScreen.x() - thisScreen.x();
|
||||
int rightOffset = wholeScreen.right() - thisScreen.right();
|
||||
int bottomOffset = wholeScreen.bottom() - thisScreen.bottom();
|
||||
int topOffset = wholeScreen.top() - thisScreen.top();
|
||||
// qDebug() << "screen l/r/b/t offsets are:" << leftOffset << rightOffset << bottomOffset << topOffset << location();
|
||||
|
||||
switch (location())
|
||||
{
|
||||
case Plasma::Types::TopEdge:
|
||||
strut.top_width = thickness() + topOffset;
|
||||
strut.top_start = x();
|
||||
strut.top_end = x() + width() - 1;
|
||||
// qDebug() << "setting top edge to" << strut.top_width << strut.top_start << strut.top_end;
|
||||
break;
|
||||
|
||||
case Plasma::Types::BottomEdge:
|
||||
strut.bottom_width = thickness() + bottomOffset;
|
||||
strut.bottom_start = x();
|
||||
strut.bottom_end = x() + width() - 1;
|
||||
// qDebug() << "setting bottom edge to" << strut.bottom_width << strut.bottom_start << strut.bottom_end;
|
||||
break;
|
||||
|
||||
case Plasma::Types::RightEdge:
|
||||
strut.right_width = thickness() + rightOffset;
|
||||
strut.right_start = y();
|
||||
strut.right_end = y() + height() - 1;
|
||||
// qDebug() << "setting right edge to" << strut.right_width << strut.right_start << strut.right_end;
|
||||
break;
|
||||
|
||||
case Plasma::Types::LeftEdge:
|
||||
strut.left_width = thickness() + leftOffset;
|
||||
strut.left_start = y();
|
||||
strut.left_end = y() + height() - 1;
|
||||
// qDebug() << "setting left edge to" << strut.left_width << strut.left_start << strut.left_end;
|
||||
break;
|
||||
|
||||
default:
|
||||
//qDebug() << "where are we?";
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
KWindowSystem::setExtendedStrut(winId(), strut.left_width,
|
||||
strut.left_start,
|
||||
strut.left_end,
|
||||
strut.right_width,
|
||||
strut.right_start,
|
||||
strut.right_end,
|
||||
strut.top_width,
|
||||
strut.top_start,
|
||||
strut.top_end,
|
||||
strut.bottom_width,
|
||||
strut.bottom_start,
|
||||
strut.bottom_end);
|
||||
|
||||
//recreateUnhideTrigger();
|
||||
}
|
||||
|
||||
void PanelView::themeChanged()
|
||||
{
|
||||
//TODO: how to take the shape from the framesvg?
|
||||
KWindowEffects::enableBlurBehind(winId(), true);
|
||||
KWindowEffects::enableBackgroundContrast(winId(), m_theme.backgroundContrastEnabled(),
|
||||
m_theme.backgroundContrast(),
|
||||
m_theme.backgroundIntensity(),
|
||||
m_theme.backgroundSaturation());
|
||||
}
|
||||
|
||||
#include "moc_panelview.cpp"
|
@ -1,137 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* 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 2 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, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef PANELVIEW_H
|
||||
#define PANELVIEW_H
|
||||
|
||||
#include <view.h>
|
||||
#include <QtCore/qpointer.h>
|
||||
#include <Plasma/Theme>
|
||||
#include <QTimer>
|
||||
|
||||
|
||||
#include <configview.h>
|
||||
|
||||
class ShellCorona;
|
||||
|
||||
class PanelView : public PlasmaQuick::View
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(Qt::Alignment alignment READ alignment WRITE setAlignment NOTIFY alignmentChanged)
|
||||
Q_PROPERTY(int offset READ offset WRITE setOffset NOTIFY offsetChanged)
|
||||
Q_PROPERTY(int thickness READ thickness WRITE setThickness NOTIFY thicknessChanged)
|
||||
Q_PROPERTY(int length READ length WRITE setLength NOTIFY lengthChanged)
|
||||
Q_PROPERTY(int maximumLength READ maximumLength WRITE setMaximumLength NOTIFY maximumLengthChanged)
|
||||
Q_PROPERTY(int minimumLength READ minimumLength WRITE setMinimumLength NOTIFY minimumLengthChanged)
|
||||
Q_PROPERTY(int distance READ distance WRITE setDistance NOTIFY distanceChanged)
|
||||
Q_PROPERTY(QScreen *screen READ screen WRITE setScreen NOTIFY screenChangedProxy)
|
||||
Q_PROPERTY(VisibilityMode visibilityMode READ visibilityMode WRITE setVisibilityMode NOTIFY visibilityModeChanged)
|
||||
|
||||
public:
|
||||
|
||||
enum VisibilityMode {
|
||||
NormalPanel = 0,
|
||||
AutoHide,
|
||||
LetWindowsCover,
|
||||
WindowsGoBelow
|
||||
};
|
||||
Q_ENUMS(VisibilityMode)
|
||||
|
||||
explicit PanelView(ShellCorona *corona, QWindow *parent = 0);
|
||||
virtual ~PanelView();
|
||||
|
||||
virtual KConfigGroup config() const;
|
||||
|
||||
Q_INVOKABLE void maximize();
|
||||
|
||||
Qt::Alignment alignment() const;
|
||||
void setAlignment(Qt::Alignment alignment);
|
||||
|
||||
int offset() const;
|
||||
void setOffset(int offset);
|
||||
|
||||
int thickness() const;
|
||||
void setThickness(int thickness);
|
||||
|
||||
int length() const;
|
||||
void setLength(int value);
|
||||
|
||||
int maximumLength() const;
|
||||
void setMaximumLength(int length);
|
||||
|
||||
int minimumLength() const;
|
||||
void setMinimumLength(int length);
|
||||
|
||||
int distance() const;
|
||||
void setDistance(int dist);
|
||||
|
||||
VisibilityMode visibilityMode() const;
|
||||
void setVisibilityMode(PanelView::VisibilityMode mode);
|
||||
|
||||
protected:
|
||||
void resizeEvent(QResizeEvent *ev);
|
||||
void showEvent(QShowEvent *event);
|
||||
bool event(QEvent *e);
|
||||
|
||||
Q_SIGNALS:
|
||||
void alignmentChanged();
|
||||
void offsetChanged();
|
||||
void screenGeometryChanged();
|
||||
void thicknessChanged();
|
||||
void lengthChanged();
|
||||
void maximumLengthChanged();
|
||||
void minimumLengthChanged();
|
||||
void distanceChanged();
|
||||
|
||||
//QWindow does not have a property for screen. Adding this property requires re-implementing the signal
|
||||
void screenChangedProxy(QScreen *screen);
|
||||
void visibilityModeChanged();
|
||||
|
||||
protected Q_SLOTS:
|
||||
/**
|
||||
* It will be called when the configuration is requested
|
||||
*/
|
||||
virtual void showConfigurationInterface(Plasma::Applet *applet);
|
||||
void updateStruts();
|
||||
|
||||
private Q_SLOTS:
|
||||
void themeChanged();
|
||||
void positionPanel();
|
||||
void restore();
|
||||
void updateUnhideTrigger();
|
||||
void unhide();
|
||||
|
||||
|
||||
private:
|
||||
int m_offset;
|
||||
int m_maxLength;
|
||||
int m_minLength;
|
||||
int m_distance;
|
||||
Qt::Alignment m_alignment;
|
||||
QPointer<PlasmaQuick::ConfigView> m_panelConfigView;
|
||||
ShellCorona *m_corona;
|
||||
QTimer *m_strutsTimer;
|
||||
VisibilityMode m_visibilityMode;
|
||||
Plasma::Theme m_theme;
|
||||
QTimer m_positionPaneltimer;
|
||||
QTimer m_unhideTimer;
|
||||
|
||||
static const int STRUTSTIMERDELAY = 200;
|
||||
};
|
||||
|
||||
#endif // PANELVIEW_H
|
@ -1,22 +0,0 @@
|
||||
[Desktop Entry]
|
||||
Exec=plasma-shell --shut-up
|
||||
X-DBUS-StartupType=Unique
|
||||
Name=Plasma Desktop Workspace
|
||||
Name[cs]=Pracovní plocha Plasma
|
||||
Name[de]=Plasma-Arbeitsflächenbereich
|
||||
Name[fi]=Plasma-työpöytä
|
||||
Name[fr]=Espace de travail du bureau Plasma
|
||||
Name[hu]=Plazma asztali munkaterület
|
||||
Name[nl]=Plasma Bureaublad Werkplek
|
||||
Name[pl]=Przestrzeń robocza pulpitu Plazmy
|
||||
Name[pt]=Área de Trabalho do Plasma
|
||||
Name[pt_BR]=Espaço de Trabalho Plasma
|
||||
Name[sk]=Pracovná plocha Plasma
|
||||
Name[sv]=Plasma arbetsområde för skrivbordet
|
||||
Name[uk]=Робочий простір стільниці Плазми
|
||||
Name[x-test]=xxPlasma Desktop Workspacexx
|
||||
Type=Application
|
||||
X-KDE-StartupNotify=false
|
||||
X-DBUS-ServiceName=org.kde.plasma_shell
|
||||
OnlyShowIn=KDE;
|
||||
X-KDE-autostart-phase=0
|
@ -1,216 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "appinterface.h"
|
||||
|
||||
#include <QEventLoop>
|
||||
#include <QTimer>
|
||||
|
||||
#include <solid/device.h>
|
||||
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/Corona>
|
||||
#include <Plasma/DataEngine>
|
||||
#include <Plasma/DataEngineConsumer>
|
||||
#include <Plasma/PluginLoader>
|
||||
#include <Plasma/Theme>
|
||||
|
||||
#ifdef Q_OS_WIN
|
||||
#include <windows.h>
|
||||
#endif
|
||||
|
||||
#ifdef Q_WS_X11
|
||||
#include <X11/Xlib.h>
|
||||
#include <fixx11h.h>
|
||||
#endif
|
||||
|
||||
#include "scriptengine.h"
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
AppInterface::AppInterface(ScriptEngine *env)
|
||||
: QObject(env),
|
||||
m_env(env)
|
||||
{
|
||||
m_theme = new Plasma::Theme(this);
|
||||
}
|
||||
|
||||
int AppInterface::screenCount() const
|
||||
{
|
||||
return m_env->corona()->numScreens();
|
||||
}
|
||||
|
||||
QRectF AppInterface::screenGeometry(int screen) const
|
||||
{
|
||||
return m_env->corona()->screenGeometry(screen);
|
||||
}
|
||||
|
||||
QList<int> AppInterface::activityIds() const
|
||||
{
|
||||
//FIXME: the ints could overflow since Applet::id() returns a uint,
|
||||
// however QScript deals with QList<uint> very, very poorly
|
||||
QList<int> containments;
|
||||
|
||||
foreach (Plasma::Containment *c, m_env->corona()->containments()) {
|
||||
if (!ScriptEngine::isPanel(c)) {
|
||||
containments.append(c->id());
|
||||
}
|
||||
}
|
||||
|
||||
return containments;
|
||||
}
|
||||
|
||||
QList<int> AppInterface::panelIds() const
|
||||
{
|
||||
//FIXME: the ints could overflow since Applet::id() returns a uint,
|
||||
// however QScript deals with QList<uint> very, very poorly
|
||||
QList<int> panels;
|
||||
|
||||
foreach (Plasma::Containment *c, m_env->corona()->containments()) {
|
||||
//qDebug() << "checking" << (QObject*)c << isPanel(c);
|
||||
if (ScriptEngine::isPanel(c)) {
|
||||
panels.append(c->id());
|
||||
}
|
||||
}
|
||||
|
||||
return panels;
|
||||
}
|
||||
|
||||
QString AppInterface::applicationVersion() const
|
||||
{
|
||||
return qApp->applicationVersion();
|
||||
}
|
||||
|
||||
QString AppInterface::platformVersion() const
|
||||
{
|
||||
return 0;//KDE::versionString();
|
||||
}
|
||||
|
||||
int AppInterface::scriptingVersion() const
|
||||
{
|
||||
return PLASMA_DESKTOP_SCRIPTING_VERSION;
|
||||
}
|
||||
|
||||
QString AppInterface::theme() const
|
||||
{
|
||||
return m_theme->themeName();
|
||||
}
|
||||
|
||||
void AppInterface::setTheme(const QString &name)
|
||||
{
|
||||
m_theme->setThemeName(name);
|
||||
}
|
||||
|
||||
bool AppInterface::multihead() const
|
||||
{
|
||||
#ifdef Q_OS_WIN
|
||||
return GetSystemMetrics(SM_CMONITORS) > 1;
|
||||
#else
|
||||
QByteArray multiHead = qgetenv("KDE_MULTIHEAD");
|
||||
if (!multiHead.isEmpty()) {
|
||||
return (multiHead.toLower() == "true");
|
||||
}
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
|
||||
int AppInterface::multiheadScreen() const
|
||||
{
|
||||
int id = -1;
|
||||
|
||||
#ifdef Q_WS_X11
|
||||
if (multihead()) {
|
||||
// with multihead, we "lie" and say that screen 0 is the default screen, in fact, we pretend
|
||||
// we have only one screen at all
|
||||
Display *dpy = XOpenDisplay(NULL);
|
||||
if (dpy) {
|
||||
id = DefaultScreen(dpy);
|
||||
XCloseDisplay(dpy);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
return id;
|
||||
}
|
||||
|
||||
void AppInterface::lockCorona(bool locked)
|
||||
{
|
||||
m_env->corona()->setImmutability(locked ? Plasma::Types::UserImmutable : Plasma::Types::Mutable);
|
||||
}
|
||||
|
||||
bool AppInterface::coronaLocked() const
|
||||
{
|
||||
return m_env->corona()->immutability() != Plasma::Types::Mutable;
|
||||
}
|
||||
|
||||
void AppInterface::sleep(int ms)
|
||||
{
|
||||
QEventLoop loop;
|
||||
QTimer::singleShot(ms, &loop, SLOT(quit()));
|
||||
loop.exec(QEventLoop::ExcludeUserInputEvents);
|
||||
}
|
||||
|
||||
bool AppInterface::hasBattery() const
|
||||
{
|
||||
return !Solid::Device::listFromType(Solid::DeviceInterface::Battery).isEmpty();
|
||||
}
|
||||
|
||||
QStringList AppInterface::knownWidgetTypes() const
|
||||
{
|
||||
if (m_knownWidgets.isEmpty()) {
|
||||
QStringList widgets;
|
||||
KPluginInfo::List infoLs = Plasma::PluginLoader::self()->listAppletInfo(QString());
|
||||
|
||||
foreach (const KPluginInfo &info, infoLs) {
|
||||
widgets.append(info.pluginName());
|
||||
}
|
||||
|
||||
const_cast<AppInterface *>(this)->m_knownWidgets = widgets;
|
||||
}
|
||||
|
||||
return m_knownWidgets;
|
||||
}
|
||||
|
||||
QStringList AppInterface::knownActivityTypes() const
|
||||
{
|
||||
return knownContainmentTypes("desktop");
|
||||
}
|
||||
|
||||
QStringList AppInterface::knownPanelTypes() const
|
||||
{
|
||||
return knownContainmentTypes("panel");
|
||||
}
|
||||
|
||||
QStringList AppInterface::knownContainmentTypes(const QString &type) const
|
||||
{
|
||||
QStringList containments;
|
||||
KPluginInfo::List infoLs = Plasma::PluginLoader::listContainmentsOfType(type);
|
||||
|
||||
foreach (const KPluginInfo &info, infoLs) {
|
||||
containments.append(info.pluginName());
|
||||
}
|
||||
|
||||
return containments;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#include "appinterface.moc"
|
||||
|
@ -1,100 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef APPINTERFACE
|
||||
#define APPINTERFACE
|
||||
|
||||
#include <QObject>
|
||||
#include <QRectF>
|
||||
#include <QStringList>
|
||||
|
||||
namespace Plasma
|
||||
{
|
||||
class Applet;
|
||||
class Containment;
|
||||
class Corona;
|
||||
class Theme;
|
||||
} // namespace Plasma
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class ScriptEngine;
|
||||
|
||||
class AppInterface : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(bool locked READ coronaLocked WRITE lockCorona)
|
||||
Q_PROPERTY(bool hasBattery READ hasBattery)
|
||||
Q_PROPERTY(int screenCount READ screenCount)
|
||||
Q_PROPERTY(QList<int> activityIds READ activityIds)
|
||||
Q_PROPERTY(QList<int> panelIds READ panelIds)
|
||||
Q_PROPERTY(QStringList knownPanelTypes READ knownPanelTypes)
|
||||
Q_PROPERTY(QStringList knownActivityTypes READ knownActivityTypes)
|
||||
Q_PROPERTY(QStringList knownWidgetTypes READ knownWidgetTypes)
|
||||
Q_PROPERTY(QString theme READ theme WRITE setTheme)
|
||||
Q_PROPERTY(QString applicationVersion READ applicationVersion)
|
||||
Q_PROPERTY(QString platformVersion READ platformVersion)
|
||||
Q_PROPERTY(int scriptingVersion READ scriptingVersion)
|
||||
Q_PROPERTY(bool multihead READ multihead)
|
||||
Q_PROPERTY(bool multiheadScreen READ multihead)
|
||||
|
||||
public:
|
||||
AppInterface(ScriptEngine *env);
|
||||
|
||||
bool hasBattery() const;
|
||||
int screenCount() const;
|
||||
QList<int> activityIds() const;
|
||||
QList<int> panelIds() const;
|
||||
|
||||
QStringList knownWidgetTypes() const;
|
||||
QStringList knownActivityTypes() const;
|
||||
QStringList knownPanelTypes() const;
|
||||
QStringList knownContainmentTypes(const QString &type) const;
|
||||
|
||||
QString applicationVersion() const;
|
||||
QString platformVersion() const;
|
||||
int scriptingVersion() const;
|
||||
|
||||
QString theme() const;
|
||||
void setTheme(const QString &name);
|
||||
|
||||
bool multihead() const;
|
||||
int multiheadScreen() const;
|
||||
|
||||
bool coronaLocked() const;
|
||||
|
||||
public Q_SLOTS:
|
||||
QRectF screenGeometry(int screen) const;
|
||||
void lockCorona(bool locked);
|
||||
void sleep(int ms);
|
||||
|
||||
Q_SIGNALS:
|
||||
void print(const QString &string);
|
||||
|
||||
private:
|
||||
ScriptEngine *m_env;
|
||||
QStringList m_knownWidgets;
|
||||
Plasma::Theme *m_theme;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -1,269 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "applet.h"
|
||||
|
||||
#include <QAction>
|
||||
|
||||
#include <kservice.h>
|
||||
#include <kservicetypetrader.h>
|
||||
|
||||
#include <Plasma/Applet>
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/Corona>
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class Applet::Private
|
||||
{
|
||||
public:
|
||||
Private()
|
||||
: configDirty(false),
|
||||
inWallpaperConfig(false),
|
||||
wallpaperConfigDirty(false)
|
||||
{
|
||||
}
|
||||
|
||||
KConfigGroup configGroup;
|
||||
QStringList configGroupPath;
|
||||
KConfigGroup globalConfigGroup;
|
||||
QStringList globalConfigGroupPath;
|
||||
bool configDirty : 1;
|
||||
bool inWallpaperConfig : 1;
|
||||
bool wallpaperConfigDirty : 1;
|
||||
};
|
||||
|
||||
Applet::Applet(QObject *parent)
|
||||
: QObject(parent),
|
||||
d(new Applet::Private)
|
||||
{
|
||||
}
|
||||
|
||||
Applet::~Applet()
|
||||
{
|
||||
delete d;
|
||||
}
|
||||
|
||||
void Applet::setCurrentConfigGroup(const QStringList &groupNames)
|
||||
{
|
||||
Plasma::Applet *app = applet();
|
||||
if (!app) {
|
||||
d->configGroup = KConfigGroup();
|
||||
d->configGroupPath.clear();
|
||||
return;
|
||||
}
|
||||
|
||||
d->configGroup = app->config();
|
||||
d->configGroupPath = groupNames;
|
||||
|
||||
foreach (const QString &groupName, groupNames) {
|
||||
d->configGroup = KConfigGroup(&d->configGroup, groupName);
|
||||
}
|
||||
|
||||
d->inWallpaperConfig = !groupNames.isEmpty() && groupNames.first() == "Wallpaper";
|
||||
}
|
||||
|
||||
QStringList Applet::currentConfigGroup() const
|
||||
{
|
||||
return d->configGroupPath;
|
||||
}
|
||||
|
||||
QStringList Applet::configKeys() const
|
||||
{
|
||||
if (d->configGroup.isValid()) {
|
||||
return d->configGroup.keyList();
|
||||
}
|
||||
|
||||
return QStringList();
|
||||
}
|
||||
|
||||
QStringList Applet::configGroups() const
|
||||
{
|
||||
if (d->configGroup.isValid()) {
|
||||
return d->configGroup.groupList();
|
||||
}
|
||||
|
||||
return QStringList();
|
||||
}
|
||||
|
||||
QVariant Applet::readConfig(const QString &key, const QVariant &def) const
|
||||
{
|
||||
if (d->configGroup.isValid()) {
|
||||
return d->configGroup.readEntry(key, def);
|
||||
} else {
|
||||
return QVariant();
|
||||
}
|
||||
}
|
||||
|
||||
void Applet::writeConfig(const QString &key, const QVariant &value)
|
||||
{
|
||||
if (d->configGroup.isValid()) {
|
||||
if (d->inWallpaperConfig) {
|
||||
d->wallpaperConfigDirty = true;
|
||||
}
|
||||
|
||||
d->configGroup.writeEntry(key, value);
|
||||
d->configDirty = true;
|
||||
}
|
||||
}
|
||||
|
||||
void Applet::setCurrentGlobalConfigGroup(const QStringList &groupNames)
|
||||
{
|
||||
Plasma::Applet *app = applet();
|
||||
if (!app) {
|
||||
d->globalConfigGroup = KConfigGroup();
|
||||
d->globalConfigGroupPath.clear();
|
||||
return;
|
||||
}
|
||||
|
||||
d->globalConfigGroup = app->globalConfig();
|
||||
d->globalConfigGroupPath = groupNames;
|
||||
|
||||
foreach (const QString &groupName, groupNames) {
|
||||
d->globalConfigGroup = KConfigGroup(&d->globalConfigGroup, groupName);
|
||||
}
|
||||
}
|
||||
|
||||
QStringList Applet::currentGlobalConfigGroup() const
|
||||
{
|
||||
return d->globalConfigGroupPath;
|
||||
}
|
||||
|
||||
QStringList Applet::globalConfigKeys() const
|
||||
{
|
||||
if (d->globalConfigGroup.isValid()) {
|
||||
return d->globalConfigGroup.keyList();
|
||||
}
|
||||
|
||||
return QStringList();
|
||||
}
|
||||
|
||||
QStringList Applet::globalConfigGroups() const
|
||||
{
|
||||
if (d->globalConfigGroup.isValid()) {
|
||||
return d->globalConfigGroup.groupList();
|
||||
}
|
||||
|
||||
return QStringList();
|
||||
}
|
||||
|
||||
QVariant Applet::readGlobalConfig(const QString &key, const QVariant &def) const
|
||||
{
|
||||
if (d->globalConfigGroup.isValid()) {
|
||||
return d->globalConfigGroup.readEntry(key, def);
|
||||
} else {
|
||||
return QVariant();
|
||||
}
|
||||
}
|
||||
|
||||
void Applet::writeGlobalConfig(const QString &key, const QVariant &value)
|
||||
{
|
||||
if (d->globalConfigGroup.isValid()) {
|
||||
d->globalConfigGroup.writeEntry(key, value);
|
||||
d->configDirty = true;
|
||||
}
|
||||
}
|
||||
|
||||
void Applet::reloadConfigIfNeeded()
|
||||
{
|
||||
if (d->configDirty) {
|
||||
reloadConfig();
|
||||
}
|
||||
}
|
||||
|
||||
void Applet::reloadConfig()
|
||||
{
|
||||
Plasma::Applet *app = applet();
|
||||
if (app) {
|
||||
KConfigGroup cg = app->config();
|
||||
|
||||
if (!app->isContainment()) {
|
||||
app->restore(cg);
|
||||
}
|
||||
|
||||
app->configChanged();
|
||||
|
||||
if (app->containment() && app->containment()->corona()) {
|
||||
app->containment()->corona()->requestConfigSync();
|
||||
}
|
||||
|
||||
d->configDirty = false;
|
||||
}
|
||||
}
|
||||
|
||||
QString Applet::version() const
|
||||
{
|
||||
Plasma::Applet *app = applet();
|
||||
if (!app) {
|
||||
return QString();
|
||||
}
|
||||
|
||||
QString type = app->pluginInfo().pluginName();
|
||||
KService::List services = KServiceTypeTrader::self()->query("Plasma/Applet", "[X-KDE-PluginInfo-Name] == '" + type + "'");
|
||||
if (services.isEmpty()) {
|
||||
return QString();
|
||||
}
|
||||
|
||||
KPluginInfo info(services.first());
|
||||
return info.version();
|
||||
}
|
||||
|
||||
void Applet::setLocked(bool locked)
|
||||
{
|
||||
Plasma::Applet *app = applet();
|
||||
if (!app) {
|
||||
return;
|
||||
}
|
||||
|
||||
app->setImmutability(locked ? Plasma::Types::UserImmutable : Plasma::Types::Mutable);
|
||||
KConfigGroup cg = app->config();
|
||||
if (!app->isContainment()) {
|
||||
cg = cg.parent();
|
||||
}
|
||||
|
||||
if (cg.isValid()) {
|
||||
cg.writeEntry("immutability", (int)app->immutability());
|
||||
}
|
||||
}
|
||||
|
||||
bool Applet::locked() const
|
||||
{
|
||||
Plasma::Applet *app = applet();
|
||||
if (!app) {
|
||||
return Plasma::Types::Mutable;
|
||||
}
|
||||
|
||||
return app->immutability() != Plasma::Types::Mutable;
|
||||
}
|
||||
|
||||
bool Applet::wallpaperConfigDirty() const
|
||||
{
|
||||
return d->wallpaperConfigDirty;
|
||||
}
|
||||
|
||||
Plasma::Applet *Applet::applet() const
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#include "applet.moc"
|
||||
|
@ -1,84 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef APPLET
|
||||
#define APPLET
|
||||
|
||||
#include <QObject>
|
||||
#include <QWeakPointer>
|
||||
|
||||
#include <kconfiggroup.h>
|
||||
|
||||
|
||||
namespace Plasma
|
||||
{
|
||||
class Applet;
|
||||
} // namespace Plasma
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class Applet : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
Applet(QObject *parent = 0);
|
||||
~Applet();
|
||||
|
||||
QStringList configKeys() const;
|
||||
QStringList configGroups() const;
|
||||
|
||||
void setCurrentConfigGroup(const QStringList &groupNames);
|
||||
QStringList currentConfigGroup() const;
|
||||
|
||||
QStringList globalConfigKeys() const;
|
||||
QStringList globalConfigGroups() const;
|
||||
|
||||
void setCurrentGlobalConfigGroup(const QStringList &groupNames);
|
||||
QStringList currentGlobalConfigGroup() const;
|
||||
|
||||
QString version() const;
|
||||
|
||||
void setLocked(bool locked);
|
||||
bool locked() const;
|
||||
|
||||
bool wallpaperConfigDirty() const;
|
||||
|
||||
virtual Plasma::Applet *applet() const;
|
||||
|
||||
protected:
|
||||
void reloadConfigIfNeeded();
|
||||
|
||||
public Q_SLOTS:
|
||||
virtual QVariant readConfig(const QString &key, const QVariant &def = QString()) const;
|
||||
virtual void writeConfig(const QString &key, const QVariant &value);
|
||||
virtual QVariant readGlobalConfig(const QString &key, const QVariant &def = QString()) const;
|
||||
virtual void writeGlobalConfig(const QString &key, const QVariant &value);
|
||||
virtual void reloadConfig();
|
||||
|
||||
private:
|
||||
class Private;
|
||||
Private * const d;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -1,349 +0,0 @@
|
||||
/****************************************************************************
|
||||
**
|
||||
** Copyright (C) 1992-2007 Trolltech ASA. All rights reserved.
|
||||
**
|
||||
** This file is part of the plugins of the Qt Toolkit.
|
||||
**
|
||||
** This file may be used under the terms of the GNU General Public
|
||||
** License version 2.0 as published by the Free Software Foundation
|
||||
** and appearing in the file LICENSE.GPL included in the packaging of
|
||||
** this file. Please review the following information to ensure GNU
|
||||
** General Public Licensing requirements will be met:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/opensource/
|
||||
**
|
||||
** If you are unsure which license is appropriate for your use, please
|
||||
** review the following information:
|
||||
** http://trolltech.com/products/qt/licenses/licensing/licensingoverview
|
||||
** or contact the sales department at sales@trolltech.com.
|
||||
**
|
||||
** In addition, as a special exception, Trolltech gives you certain
|
||||
** additional rights. These rights are described in the Trolltech GPL
|
||||
** Exception version 1.0, which can be found at
|
||||
** http://www.trolltech.com/products/qt/gplexception/ and in the file
|
||||
** GPL_EXCEPTION.txt in this package.
|
||||
**
|
||||
** In addition, as a special exception, Trolltech, as the sole copyright
|
||||
** holder for Qt Designer, grants users of the Qt/Eclipse Integration
|
||||
** plug-in the right for the Qt/Eclipse Integration to link to
|
||||
** functionality provided by Qt Designer and its related libraries.
|
||||
**
|
||||
** Trolltech reserves all rights not expressly granted herein.
|
||||
**
|
||||
** Trolltech ASA (c) 2007
|
||||
**
|
||||
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
|
||||
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
|
||||
**
|
||||
****************************************************************************/
|
||||
#ifndef QTSCRIPTEXTENSIONS_GLOBAL_H
|
||||
#define QTSCRIPTEXTENSIONS_GLOBAL_H
|
||||
|
||||
#include <QtCore/QSharedData>
|
||||
|
||||
|
||||
#define DECLARE_SELF(Class, __fn__) \
|
||||
Class* self = qscriptvalue_cast<Class*>(ctx->thisObject()); \
|
||||
if (!self) { \
|
||||
return ctx->throwError(QScriptContext::TypeError, \
|
||||
QString::fromLatin1("%0.prototype.%1: this object is not a %0") \
|
||||
.arg(#Class).arg(#__fn__)); \
|
||||
}
|
||||
|
||||
#define DECLARE_SELF2(Class, __fn__, __ret__) \
|
||||
Class* self = qscriptvalue_cast<Class*>(thisObject()); \
|
||||
if (!self) { \
|
||||
context()->throwError(QScriptContext::TypeError, \
|
||||
QString::fromLatin1("%0.prototype.%1: this object is not a %0") \
|
||||
.arg(#Class).arg(#__fn__)); \
|
||||
return __ret__; \
|
||||
}
|
||||
|
||||
|
||||
|
||||
#define ADD_METHOD(__p__, __f__) \
|
||||
__p__.setProperty(#__f__, __p__.engine()->newFunction(__f__))
|
||||
|
||||
#define ADD_GET_METHOD(__p__, __get__) \
|
||||
ADD_METHOD(__p__, __get__)
|
||||
|
||||
#define ADD_GET_SET_METHODS(__p__, __get__, __set__) \
|
||||
do { \
|
||||
ADD_METHOD(__p__, __get__); \
|
||||
ADD_METHOD(__p__, __set__); \
|
||||
} while (0);
|
||||
|
||||
#define ADD_CTOR_FUNCTION(__c__, __f__) ADD_METHOD(__c__, __f__)
|
||||
|
||||
#define ADD_ENUM_VALUE(__c__, __ns__, __v__) \
|
||||
__c__.setProperty(#__v__, QScriptValue(__c__.engine(), __ns__::__v__))
|
||||
|
||||
|
||||
#define BEGIN_DECLARE_METHOD(Class, __mtd__) \
|
||||
static QScriptValue __mtd__(QScriptContext *ctx, QScriptEngine *eng) \
|
||||
{ \
|
||||
DECLARE_SELF(Class, __mtd__);
|
||||
|
||||
#define END_DECLARE_METHOD \
|
||||
}
|
||||
|
||||
|
||||
#define DECLARE_GET_METHOD(Class, __get__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __get__) { \
|
||||
return qScriptValueFromValue(eng, self->__get__()); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_SET_METHOD(Class, T, __set__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __set__) { \
|
||||
self->__set__(qscriptvalue_cast<T>(ctx->argument(0))); \
|
||||
return eng->undefinedValue(); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_GET_SET_METHODS(Class, T, __get__, __set__) \
|
||||
DECLARE_GET_METHOD(Class, /*T,*/ __get__) \
|
||||
DECLARE_SET_METHOD(Class, T, __set__)
|
||||
|
||||
|
||||
|
||||
#define DECLARE_SIMPLE_GET_METHOD(Class, __get__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __get__) { \
|
||||
return QScriptValue(eng, self->__get__()); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_SIMPLE_SET_METHOD(Class, ToType, __set__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __set__) { \
|
||||
self->__set__(ctx->argument(0).ToType()); \
|
||||
return eng->undefinedValue(); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_BOOLEAN_GET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_GET_METHOD(Class, __set__)
|
||||
#define DECLARE_BOOLEAN_SET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_SET_METHOD(Class, toBoolean, __set__)
|
||||
|
||||
#define DECLARE_INT_GET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_GET_METHOD(Class, __set__)
|
||||
#define DECLARE_INT_SET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_SET_METHOD(Class, toInt32, __set__)
|
||||
|
||||
#define DECLARE_NUMBER_GET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_GET_METHOD(Class, __set__)
|
||||
#define DECLARE_NUMBER_SET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_SET_METHOD(Class, toNumber, __set__)
|
||||
|
||||
#define DECLARE_STRING_GET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_GET_METHOD(Class, __set__)
|
||||
#define DECLARE_STRING_SET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_SET_METHOD(Class, toString, __set__)
|
||||
|
||||
#define DECLARE_QOBJECT_GET_METHOD(Class, __get__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __get__) { \
|
||||
return eng->newQObject(self->__get__()); \
|
||||
} END_DECLARE_METHOD
|
||||
#define DECLARE_QOBJECT_SET_METHOD(Class, __set__) \
|
||||
DECLARE_SIMPLE_SET_METHOD(Class, toQObject, __set__)
|
||||
|
||||
#define DECLARE_BOOLEAN_GET_SET_METHODS(Class, __get__, __set__) \
|
||||
DECLARE_BOOLEAN_GET_METHOD(Class, __get__) \
|
||||
DECLARE_BOOLEAN_SET_METHOD(Class, __set__)
|
||||
|
||||
#define DECLARE_NUMBER_GET_SET_METHODS(Class, __get__, __set__) \
|
||||
DECLARE_NUMBER_GET_METHOD(Class, __get__) \
|
||||
DECLARE_NUMBER_SET_METHOD(Class, __set__)
|
||||
|
||||
#define DECLARE_INT_GET_SET_METHODS(Class, __get__, __set__) \
|
||||
DECLARE_INT_GET_METHOD(Class, __get__) \
|
||||
DECLARE_INT_SET_METHOD(Class, __set__)
|
||||
|
||||
#define DECLARE_STRING_GET_SET_METHODS(Class, __get__, __set__) \
|
||||
DECLARE_STRING_GET_METHOD(Class, __get__) \
|
||||
DECLARE_STRING_SET_METHOD(Class, __set__)
|
||||
|
||||
#define DECLARE_QOBJECT_GET_SET_METHODS(Class, __get__, __set__) \
|
||||
DECLARE_QOBJECT_GET_METHOD(Class, __get__) \
|
||||
DECLARE_QOBJECT_SET_METHOD(Class, __set__)
|
||||
|
||||
|
||||
#define DECLARE_VOID_METHOD(Class, __fun__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __fun__) { \
|
||||
self->__fun__(); \
|
||||
return eng->undefinedValue(); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_VOID_NUMBER_METHOD(Class, __fun__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __fun__) { \
|
||||
self->__fun__(ctx->argument(0).toNumber()); \
|
||||
return eng->undefinedValue(); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_VOID_NUMBER_NUMBER_METHOD(Class, __fun__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __fun__) { \
|
||||
self->__fun__(ctx->argument(0).toNumber(), ctx->argument(1).toNumber()); \
|
||||
return eng->undefinedValue(); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_VOID_QUAD_NUMBER_METHOD(Class, __fun__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __fun__) { \
|
||||
self->__fun__(ctx->argument(0).toNumber(), ctx->argument(1).toNumber(), ctx->argument(2).toNumber(), ctx->argument(3).toNumber()); \
|
||||
return eng->undefinedValue(); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_VOID_1ARG_METHOD(Class, ArgType, __fun__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __fun__) { \
|
||||
self->__fun__(qscriptvalue_cast<ArgType>(ctx->argument(0))); \
|
||||
return eng->undefinedValue(); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
#define DECLARE_BOOLEAN_1ARG_METHOD(Class, ArgType, __fun__) \
|
||||
BEGIN_DECLARE_METHOD(Class, __fun__) { \
|
||||
return QScriptValue(eng, self->__fun__(qscriptvalue_cast<ArgType>(ctx->argument(0)))); \
|
||||
} END_DECLARE_METHOD
|
||||
|
||||
|
||||
#define DECLARE_POINTER_METATYPE(T) \
|
||||
Q_DECLARE_METATYPE(T*) \
|
||||
Q_DECLARE_METATYPE(QScript::Pointer<T>::wrapped_pointer_type)
|
||||
|
||||
namespace QScript
|
||||
{
|
||||
|
||||
enum {
|
||||
UserOwnership = 1
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
class Pointer : public QSharedData
|
||||
{
|
||||
public:
|
||||
typedef T* pointer_type;
|
||||
typedef QExplicitlySharedDataPointer<Pointer<T> > wrapped_pointer_type;
|
||||
|
||||
~Pointer()
|
||||
{
|
||||
if (!(m_flags & UserOwnership))
|
||||
delete m_value;
|
||||
}
|
||||
|
||||
operator T*()
|
||||
{
|
||||
return m_value;
|
||||
}
|
||||
|
||||
operator const T*() const
|
||||
{
|
||||
return m_value;
|
||||
}
|
||||
|
||||
static wrapped_pointer_type create(T *value, uint flags = 0)
|
||||
{
|
||||
return wrapped_pointer_type(new Pointer(value, flags));
|
||||
}
|
||||
|
||||
static QScriptValue toScriptValue(QScriptEngine *engine, T* const &source)
|
||||
{
|
||||
if (!source)
|
||||
return engine->nullValue();
|
||||
return engine->newVariant(qVariantFromValue(source));
|
||||
}
|
||||
|
||||
static void fromScriptValue(const QScriptValue &value, T* &target)
|
||||
{
|
||||
if (value.isVariant()) {
|
||||
QVariant var = value.toVariant();
|
||||
if (qVariantCanConvert<T*>(var)) {
|
||||
target = qvariant_cast<T*>(var);
|
||||
} else if (qVariantCanConvert<wrapped_pointer_type>(var)) {
|
||||
target = qvariant_cast<wrapped_pointer_type>(var)->operator T*();
|
||||
} else {
|
||||
// look in prototype chain
|
||||
target = 0;
|
||||
int type = qMetaTypeId<T*>();
|
||||
int pointerType = qMetaTypeId<wrapped_pointer_type>();
|
||||
QScriptValue proto = value.prototype();
|
||||
while (proto.isObject() && proto.isVariant()) {
|
||||
int protoType = proto.toVariant().userType();
|
||||
if ((type == protoType) || (pointerType == protoType)) {
|
||||
QByteArray name = QMetaType::typeName(var.userType());
|
||||
if (name.startsWith("QScript::Pointer<")) {
|
||||
target = (*reinterpret_cast<wrapped_pointer_type*>(var.data()))->operator T*();
|
||||
break;
|
||||
} else {
|
||||
target = static_cast<T*>(var.data());
|
||||
break;
|
||||
}
|
||||
}
|
||||
proto = proto.prototype();
|
||||
}
|
||||
}
|
||||
} else if (value.isQObject()) {
|
||||
QObject *qobj = value.toQObject();
|
||||
QByteArray typeName = QMetaType::typeName(qMetaTypeId<T*>());
|
||||
target = reinterpret_cast<T*>(qobj->qt_metacast(typeName.left(typeName.size()-1)));
|
||||
} else {
|
||||
target = 0;
|
||||
}
|
||||
}
|
||||
|
||||
uint flags() const
|
||||
{ return m_flags; }
|
||||
void setFlags(uint flags)
|
||||
{ m_flags = flags; }
|
||||
void unsetFlags(uint flags)
|
||||
{ m_flags &= ~flags; }
|
||||
|
||||
protected:
|
||||
Pointer(T* value, uint flags)
|
||||
: m_flags(flags), m_value(value)
|
||||
{}
|
||||
|
||||
private:
|
||||
uint m_flags;
|
||||
T* m_value;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
int registerPointerMetaType(
|
||||
QScriptEngine *eng,
|
||||
const QScriptValue &prototype = QScriptValue(),
|
||||
T * /* dummy */ = 0
|
||||
)
|
||||
{
|
||||
QScriptValue (*mf)(QScriptEngine *, T* const &) = Pointer<T>::toScriptValue;
|
||||
void (*df)(const QScriptValue &, T* &) = Pointer<T>::fromScriptValue;
|
||||
const int id = qMetaTypeId<T*>();
|
||||
qScriptRegisterMetaType_helper(
|
||||
eng, id, reinterpret_cast<QScriptEngine::MarshalFunction>(mf),
|
||||
reinterpret_cast<QScriptEngine::DemarshalFunction>(df),
|
||||
prototype);
|
||||
eng->setDefaultPrototype(qMetaTypeId<typename Pointer<T>::wrapped_pointer_type>(), prototype);
|
||||
return id;
|
||||
}
|
||||
|
||||
inline void maybeReleaseOwnership(const QScriptValue &value)
|
||||
{
|
||||
if (value.isVariant()) {
|
||||
QVariant var = value.toVariant();
|
||||
QByteArray name = QMetaType::typeName(var.userType());
|
||||
if (name.startsWith("QScript::Pointer<"))
|
||||
(*reinterpret_cast<Pointer<void*>::wrapped_pointer_type *>(var.data()))->setFlags(UserOwnership);
|
||||
}
|
||||
}
|
||||
|
||||
inline void maybeTakeOwnership(const QScriptValue &value)
|
||||
{
|
||||
if (value.isVariant()) {
|
||||
QVariant var = value.toVariant();
|
||||
QByteArray name = QMetaType::typeName(var.userType());
|
||||
if (name.startsWith("QScript::Pointer<"))
|
||||
(*reinterpret_cast<Pointer<void*>::wrapped_pointer_type *>(var.data()))->unsetFlags(UserOwnership);
|
||||
}
|
||||
}
|
||||
|
||||
template <class T>
|
||||
inline QScriptValue wrapPointer(QScriptEngine *eng, T *ptr, uint flags = 0)
|
||||
{
|
||||
return eng->newVariant(qVariantFromValue(Pointer<T>::create(ptr, flags)));
|
||||
}
|
||||
|
||||
} // namespace QScript
|
||||
|
||||
#endif // QTSCRIPTEXTENSIONS_GLOBAL_H
|
@ -1,188 +0,0 @@
|
||||
/*
|
||||
* Copyright 2011-2012 by Sebastian Kügler <sebas@kde.org>
|
||||
* Copyright 2013 by Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "configgroup.h"
|
||||
#include <QtCore/QTimer>
|
||||
#include <kconfig.h>
|
||||
#include <kconfiggroup.h>
|
||||
#include <ksharedconfig.h>
|
||||
#include <QDebug>
|
||||
|
||||
class ConfigGroupPrivate {
|
||||
|
||||
public:
|
||||
ConfigGroupPrivate(ConfigGroup *q)
|
||||
: q(q),
|
||||
config(0),
|
||||
configGroup(0)
|
||||
{}
|
||||
|
||||
~ConfigGroupPrivate()
|
||||
{
|
||||
delete configGroup;
|
||||
}
|
||||
|
||||
ConfigGroup* q;
|
||||
KSharedConfigPtr config;
|
||||
KConfigGroup *configGroup;
|
||||
QString file;
|
||||
QTimer *synchTimer;
|
||||
QString group;
|
||||
};
|
||||
|
||||
|
||||
ConfigGroup::ConfigGroup(QObject *parent)
|
||||
: QObject(parent),
|
||||
d(new ConfigGroupPrivate(this))
|
||||
{
|
||||
// Delay and compress everything within 5 seconds into one sync
|
||||
d->synchTimer = new QTimer(this);
|
||||
d->synchTimer->setSingleShot(true);
|
||||
d->synchTimer->setInterval(1500);
|
||||
connect(d->synchTimer, SIGNAL(timeout()), SLOT(sync()));
|
||||
}
|
||||
|
||||
ConfigGroup::~ConfigGroup()
|
||||
{
|
||||
if (d->synchTimer->isActive()) {
|
||||
//qDebug() << "SYNC......";
|
||||
d->synchTimer->stop();
|
||||
d->configGroup->sync();
|
||||
}
|
||||
|
||||
delete d;
|
||||
}
|
||||
|
||||
KConfigGroup* ConfigGroup::configGroup()
|
||||
{
|
||||
return d->configGroup;
|
||||
}
|
||||
|
||||
QString ConfigGroup::file() const
|
||||
{
|
||||
return d->file;
|
||||
}
|
||||
|
||||
void ConfigGroup::setFile(const QString& filename)
|
||||
{
|
||||
if (d->file == filename) {
|
||||
return;
|
||||
}
|
||||
d->file = filename;
|
||||
readConfigFile();
|
||||
emit fileChanged();
|
||||
}
|
||||
|
||||
QString ConfigGroup::group() const
|
||||
{
|
||||
return d->group;
|
||||
}
|
||||
|
||||
void ConfigGroup::setGroup(const QString& groupname)
|
||||
{
|
||||
if (d->group == groupname) {
|
||||
return;
|
||||
}
|
||||
d->group = groupname;
|
||||
readConfigFile();
|
||||
emit groupChanged();
|
||||
emit keyListChanged();
|
||||
}
|
||||
|
||||
QStringList ConfigGroup::keyList() const
|
||||
{
|
||||
if (!d->configGroup) {
|
||||
return QStringList();
|
||||
}
|
||||
return d->configGroup->keyList();
|
||||
}
|
||||
|
||||
QStringList ConfigGroup::groupList() const
|
||||
{
|
||||
return d->configGroup->groupList();
|
||||
}
|
||||
|
||||
bool ConfigGroup::readConfigFile()
|
||||
{
|
||||
// Find parent ConfigGroup
|
||||
ConfigGroup* parentGroup = 0;
|
||||
QObject* current = parent();
|
||||
while (current) {
|
||||
parentGroup = qobject_cast<ConfigGroup*>(current);
|
||||
if (parentGroup) {
|
||||
break;
|
||||
}
|
||||
current = current->parent();
|
||||
}
|
||||
|
||||
delete d->configGroup;
|
||||
d->configGroup = 0;
|
||||
|
||||
if (parentGroup) {
|
||||
d->configGroup = new KConfigGroup(parentGroup->configGroup(), d->group);
|
||||
return true;
|
||||
} else {
|
||||
if (d->file.isEmpty()) {
|
||||
qWarning() << "Could not find KConfig Parent: specify a file or parent to another ConfigGroup";
|
||||
return false;
|
||||
}
|
||||
d->config = KSharedConfig::openConfig(d->file);
|
||||
d->configGroup = new KConfigGroup(d->config, d->group);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
// Bound methods and slots
|
||||
|
||||
bool ConfigGroup::writeEntry(const QString& key, const QVariant& value)
|
||||
{
|
||||
if (!d->configGroup) {
|
||||
return false;
|
||||
}
|
||||
|
||||
d->configGroup->writeEntry(key, value);
|
||||
d->synchTimer->start();
|
||||
return true;
|
||||
}
|
||||
|
||||
QVariant ConfigGroup::readEntry(const QString& key)
|
||||
{
|
||||
if (!d->configGroup) {
|
||||
return QVariant();
|
||||
}
|
||||
const QVariant value = d->configGroup->readEntry(key, QVariant(""));
|
||||
//qDebug() << " reading setting: " << key << value;
|
||||
return value;
|
||||
}
|
||||
|
||||
void ConfigGroup::deleteEntry(const QString& key)
|
||||
{
|
||||
d->configGroup->deleteEntry(key);
|
||||
}
|
||||
|
||||
void ConfigGroup::sync()
|
||||
{
|
||||
if (d->configGroup) {
|
||||
//qDebug() << "synching config...";
|
||||
d->configGroup->sync();
|
||||
}
|
||||
}
|
||||
|
||||
#include "configgroup.moc"
|
@ -1,69 +0,0 @@
|
||||
/*
|
||||
* Copyright 2011-2012 by Sebastian Kügler <sebas@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef CONFIGGROUP_H
|
||||
#define CONFIGGROUP_H
|
||||
|
||||
#include <QObject>
|
||||
#include <QVariant>
|
||||
|
||||
class KConfigGroup;
|
||||
class ConfigGroupPrivate;
|
||||
|
||||
class ConfigGroup : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(QString file READ file WRITE setFile NOTIFY fileChanged)
|
||||
Q_PROPERTY(QString group READ group WRITE setGroup NOTIFY groupChanged)
|
||||
Q_PROPERTY(QStringList keyList READ keyList NOTIFY keyListChanged)
|
||||
Q_PROPERTY(QStringList groupList READ groupList NOTIFY groupListChanged)
|
||||
|
||||
public:
|
||||
ConfigGroup(QObject* parent=0);
|
||||
~ConfigGroup();
|
||||
|
||||
KConfigGroup* configGroup();
|
||||
|
||||
QString file() const;
|
||||
void setFile(const QString &filename);
|
||||
QString group() const;
|
||||
void setGroup(const QString &groupname);
|
||||
QStringList keyList() const;
|
||||
QStringList groupList() const;
|
||||
|
||||
Q_INVOKABLE QVariant readEntry(const QString &key);
|
||||
Q_INVOKABLE bool writeEntry(const QString &key, const QVariant &value);
|
||||
Q_INVOKABLE void deleteEntry(const QString& key);
|
||||
|
||||
Q_SIGNALS:
|
||||
void fileChanged();
|
||||
void groupChanged();
|
||||
void keyListChanged();
|
||||
void groupListChanged();
|
||||
|
||||
private:
|
||||
ConfigGroupPrivate* d;
|
||||
|
||||
bool readConfigFile();
|
||||
|
||||
private Q_SLOTS:
|
||||
void sync();
|
||||
};
|
||||
|
||||
#endif
|
@ -1,290 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "containment.h"
|
||||
|
||||
#include <QAction>
|
||||
|
||||
#include <klocalizedstring.h>
|
||||
#include <kactioncollection.h>
|
||||
|
||||
#include <Plasma/Corona>
|
||||
#include <Plasma/Containment>
|
||||
|
||||
#include "scriptengine.h"
|
||||
#include "widget.h"
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class Containment::Private
|
||||
{
|
||||
public:
|
||||
QWeakPointer<Plasma::Containment> containment;
|
||||
QString oldWallpaperPlugin;
|
||||
QString wallpaperPlugin;
|
||||
QString oldWallpaperMode;
|
||||
QString wallpaperMode;
|
||||
};
|
||||
|
||||
Containment::Containment(Plasma::Containment *containment, QObject *parent)
|
||||
: Applet(parent),
|
||||
d(new Containment::Private)
|
||||
{
|
||||
d->containment = containment;
|
||||
setCurrentConfigGroup(QStringList());
|
||||
setCurrentGlobalConfigGroup(QStringList());
|
||||
if (containment) {
|
||||
d->oldWallpaperPlugin = d->wallpaperPlugin = containment->wallpaper();
|
||||
}
|
||||
}
|
||||
|
||||
Containment::~Containment()
|
||||
{
|
||||
if (d->containment) {
|
||||
Plasma::Containment *containment = d->containment.data();
|
||||
if (d->oldWallpaperPlugin != d->wallpaperPlugin ||
|
||||
d->oldWallpaperMode != d->wallpaperMode) {
|
||||
containment->setWallpaper(d->wallpaperPlugin);
|
||||
} else if (wallpaperConfigDirty()) {
|
||||
KConfigGroup cg(containment->config());
|
||||
cg = KConfigGroup(&cg, "Wallpaper");
|
||||
cg = KConfigGroup(&cg, containment->wallpaper());
|
||||
}
|
||||
}
|
||||
|
||||
reloadConfigIfNeeded();
|
||||
delete d;
|
||||
}
|
||||
|
||||
int Containment::screen() const
|
||||
{
|
||||
if (!d->containment) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
return d->containment.data()->screen();
|
||||
}
|
||||
|
||||
QString Containment::wallpaperPlugin() const
|
||||
{
|
||||
return d->wallpaperPlugin;
|
||||
}
|
||||
|
||||
void Containment::setWallpaperPlugin(const QString &wallpaperPlugin)
|
||||
{
|
||||
d->wallpaperPlugin = wallpaperPlugin;
|
||||
}
|
||||
|
||||
|
||||
QString Containment::wallpaperMode() const
|
||||
{
|
||||
return d->wallpaperMode;
|
||||
}
|
||||
|
||||
void Containment::setWallpaperMode(const QString &wallpaperMode)
|
||||
{
|
||||
d->wallpaperMode = wallpaperMode;
|
||||
}
|
||||
|
||||
QString Containment::formFactor() const
|
||||
{
|
||||
if (!d->containment) {
|
||||
return "Planar";
|
||||
}
|
||||
|
||||
switch (d->containment.data()->formFactor()) {
|
||||
case Plasma::Types::Planar:
|
||||
return "planar";
|
||||
break;
|
||||
case Plasma::Types::MediaCenter:
|
||||
return "mediacenter";
|
||||
break;
|
||||
case Plasma::Types::Horizontal:
|
||||
return "horizontal";
|
||||
break;
|
||||
case Plasma::Types::Vertical:
|
||||
return "vertical";
|
||||
break;
|
||||
case Plasma::Types::Application:
|
||||
return "application";
|
||||
break;
|
||||
}
|
||||
|
||||
return "Planar";
|
||||
}
|
||||
|
||||
QList<int> Containment::widgetIds() const
|
||||
{
|
||||
//FIXME: the ints could overflow since Applet::id() returns a uint,
|
||||
// however QScript deals with QList<uint> very, very poory
|
||||
QList<int> w;
|
||||
|
||||
if (d->containment) {
|
||||
foreach (const Plasma::Applet *applet, d->containment.data()->applets()) {
|
||||
w.append(applet->id());
|
||||
}
|
||||
}
|
||||
|
||||
return w;
|
||||
}
|
||||
|
||||
QScriptValue Containment::widgetById(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
if (context->argumentCount() == 0) {
|
||||
return context->throwError(i18n("widgetById requires an id"));
|
||||
}
|
||||
|
||||
const uint id = context->argument(0).toInt32();
|
||||
Containment *c = qobject_cast<Containment*>(context->thisObject().toQObject());
|
||||
|
||||
if (!c) {
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
if (c->d->containment) {
|
||||
foreach (Plasma::Applet *w, c->d->containment.data()->applets()) {
|
||||
if (w->id() == id) {
|
||||
ScriptEngine *env = ScriptEngine::envFor(engine);
|
||||
return env->wrap(w);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
QScriptValue Containment::addWidget(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
if (context->argumentCount() == 0) {
|
||||
return context->throwError(i18n("widgetById requires a name of a widget or a widget object"));
|
||||
}
|
||||
|
||||
Containment *c = qobject_cast<Containment*>(context->thisObject().toQObject());
|
||||
|
||||
if (!c || !c->d->containment) {
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
QScriptValue v = context->argument(0);
|
||||
Plasma::Applet *applet = 0;
|
||||
if (v.isString()) {
|
||||
applet = c->d->containment.data()->createApplet(v.toString());
|
||||
if (applet) {
|
||||
ScriptEngine *env = ScriptEngine::envFor(engine);
|
||||
return env->wrap(applet);
|
||||
}
|
||||
} else if (Widget *widget = qobject_cast<Widget*>(v.toQObject())) {
|
||||
applet = widget->applet();
|
||||
c->d->containment.data()->addApplet(applet);
|
||||
return v;
|
||||
}
|
||||
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
QScriptValue Containment::widgets(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Containment *c = qobject_cast<Containment*>(context->thisObject().toQObject());
|
||||
|
||||
if (!c || !c->d->containment) {
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
const QString widgetType = context->argumentCount() > 0 ? context->argument(0).toString() : QString();
|
||||
QScriptValue widgets = engine->newArray();
|
||||
ScriptEngine *env = ScriptEngine::envFor(engine);
|
||||
int count = 0;
|
||||
|
||||
foreach (Plasma::Applet *widget, c->d->containment.data()->applets()) {
|
||||
if (widgetType.isEmpty() || widget->pluginInfo().pluginName() == widgetType) {
|
||||
widgets.setProperty(count, env->wrap(widget));
|
||||
++count;
|
||||
}
|
||||
}
|
||||
|
||||
widgets.setProperty("length", count);
|
||||
return widgets;
|
||||
}
|
||||
|
||||
uint Containment::id() const
|
||||
{
|
||||
if (!d->containment) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return d->containment.data()->id();
|
||||
}
|
||||
|
||||
QString Containment::name() const
|
||||
{
|
||||
if (!d->containment) {
|
||||
return QString();
|
||||
}
|
||||
|
||||
return d->containment.data()->activity();
|
||||
}
|
||||
|
||||
void Containment::setName(const QString &name)
|
||||
{
|
||||
if (d->containment) {
|
||||
d->containment.data()->setActivity(name);
|
||||
}
|
||||
}
|
||||
|
||||
QString Containment::type() const
|
||||
{
|
||||
if (!d->containment) {
|
||||
return QString();
|
||||
}
|
||||
|
||||
return d->containment.data()->pluginInfo().pluginName();
|
||||
}
|
||||
|
||||
void Containment::remove()
|
||||
{
|
||||
if (d->containment) {
|
||||
d->containment.data()->destroy();
|
||||
}
|
||||
}
|
||||
|
||||
void Containment::showConfigurationInterface()
|
||||
{
|
||||
if (d->containment) {
|
||||
QAction *configAction = d->containment.data()->actions()->action("configure");
|
||||
if (configAction && configAction->isEnabled()) {
|
||||
configAction->trigger();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Plasma::Applet *Containment::applet() const
|
||||
{
|
||||
return d->containment.data();
|
||||
}
|
||||
|
||||
Plasma::Containment *Containment::containment() const
|
||||
{
|
||||
return d->containment.data();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#include "containment.moc"
|
||||
|
@ -1,104 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef CONTAINMENT
|
||||
#define CONTAINMENT
|
||||
|
||||
#include <QScriptContext>
|
||||
#include <QScriptValue>
|
||||
#include <QWeakPointer>
|
||||
|
||||
#include "applet.h"
|
||||
|
||||
namespace Plasma
|
||||
{
|
||||
class Containment;
|
||||
} // namespace Plasma
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class Containment : public Applet
|
||||
{
|
||||
Q_OBJECT
|
||||
///FIXME: add NOTIFY
|
||||
Q_PROPERTY(QString version READ version)
|
||||
Q_PROPERTY(QStringList configKeys READ configKeys)
|
||||
Q_PROPERTY(QStringList configGroups READ configGroups)
|
||||
Q_PROPERTY(QStringList globalConfigKeys READ globalConfigKeys)
|
||||
Q_PROPERTY(QStringList globalConfigGroups READ globalConfigGroups)
|
||||
Q_PROPERTY(QStringList currentConfigGroup WRITE setCurrentConfigGroup READ currentConfigGroup)
|
||||
Q_PROPERTY(QString name READ name WRITE setName)
|
||||
Q_PROPERTY(QString wallpaperPlugin READ wallpaperPlugin WRITE setWallpaperPlugin)
|
||||
Q_PROPERTY(QString wallpaperMode READ wallpaperMode WRITE setWallpaperMode)
|
||||
Q_PROPERTY(bool locked READ locked WRITE setLocked)
|
||||
Q_PROPERTY(QString type READ type)
|
||||
Q_PROPERTY(QString formFactor READ formFactor)
|
||||
Q_PROPERTY(QList<int> widgetIds READ widgetIds)
|
||||
Q_PROPERTY(int screen READ screen)
|
||||
Q_PROPERTY(int id READ id)
|
||||
|
||||
public:
|
||||
Containment(Plasma::Containment *containment, QObject *parent = 0);
|
||||
~Containment();
|
||||
|
||||
uint id() const;
|
||||
QString type() const;
|
||||
QString formFactor() const;
|
||||
QList<int> widgetIds() const;
|
||||
|
||||
QString name() const;
|
||||
void setName(const QString &name);
|
||||
|
||||
int screen() const;
|
||||
|
||||
Plasma::Applet *applet() const;
|
||||
Plasma::Containment *containment() const;
|
||||
|
||||
QString wallpaperPlugin() const;
|
||||
void setWallpaperPlugin(const QString &wallpaperPlugin);
|
||||
QString wallpaperMode() const;
|
||||
void setWallpaperMode(const QString &wallpaperMode);
|
||||
|
||||
static QScriptValue widgetById(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue addWidget(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue widgets(QScriptContext *context, QScriptEngine *engine);
|
||||
|
||||
public Q_SLOTS:
|
||||
void remove();
|
||||
void showConfigurationInterface();
|
||||
|
||||
// from the applet interface
|
||||
QVariant readConfig(const QString &key, const QVariant &def = QString()) const { return Applet::readConfig(key, def); }
|
||||
void writeConfig(const QString &key, const QVariant &value) { Applet::writeConfig(key, value); }
|
||||
|
||||
QVariant readGlobalConfig(const QString &key, const QVariant &def = QString()) const { return Applet::readGlobalConfig(key, def); }
|
||||
void writeGlobalConfig(const QString &key, const QVariant &value) { Applet::writeGlobalConfig(key, value); }
|
||||
|
||||
void reloadConfig() { Applet::reloadConfig(); }
|
||||
|
||||
private:
|
||||
class Private;
|
||||
Private * const d;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -1,63 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "desktopscriptengine.h"
|
||||
|
||||
#include <QApplication>
|
||||
#include <QCursor>
|
||||
#include <QDesktopWidget>
|
||||
|
||||
#include "containment.h"
|
||||
#include "appinterface.h"
|
||||
|
||||
#include "panel.h"
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
DesktopScriptEngine::DesktopScriptEngine(ShellCorona *corona, bool startup, QObject *parent)
|
||||
: ScriptEngine(corona, parent),
|
||||
m_startup(startup)
|
||||
{
|
||||
}
|
||||
|
||||
QScriptValue DesktopScriptEngine::wrap(Plasma::Containment *c)
|
||||
{
|
||||
Containment *wrapper = isPanel(c) ? new Panel(c) : new Containment(c);
|
||||
return wrap(wrapper);
|
||||
}
|
||||
|
||||
QScriptValue DesktopScriptEngine::wrap(Containment *c)
|
||||
{
|
||||
return ScriptEngine::wrap(c);
|
||||
}
|
||||
|
||||
int DesktopScriptEngine::defaultPanelScreen() const
|
||||
{
|
||||
if (m_startup) {
|
||||
return ScriptEngine::defaultPanelScreen();
|
||||
} else {
|
||||
return qApp->desktop()->screenNumber(QCursor::pos());
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#include "desktopscriptengine.moc"
|
||||
|
@ -1,47 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef DESKTOPSCRIPTENGINE
|
||||
#define DESKTOPSCRIPTENGINE
|
||||
|
||||
#include "scriptengine.h"
|
||||
|
||||
class ShellCorona;
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class DesktopScriptEngine : public ScriptEngine
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
DesktopScriptEngine(ShellCorona *corona, bool isStartup = true, QObject *parent = 0);
|
||||
QScriptValue wrap(Plasma::Containment *c);
|
||||
QScriptValue wrap(Containment *c);
|
||||
int defaultPanelScreen() const;
|
||||
|
||||
private:
|
||||
bool m_startup;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -1,121 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "i18n.h"
|
||||
|
||||
#include <QScriptContext>
|
||||
#include <QScriptEngine>
|
||||
|
||||
#include <QDebug>
|
||||
#include <klocalizedstring.h>
|
||||
|
||||
QScriptValue jsi18n(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
|
||||
if (context->argumentCount() < 1) {
|
||||
// qDebug() << i18n("i18n() takes at least one argument");
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
KLocalizedString message = ki18n(context->argument(0).toString().toUtf8());
|
||||
|
||||
const int numArgs = context->argumentCount();
|
||||
for (int i = 1; i < numArgs; ++i) {
|
||||
message = message.subs(context->argument(i).toString());
|
||||
}
|
||||
|
||||
return message.toString();
|
||||
}
|
||||
|
||||
QScriptValue jsi18nc(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
|
||||
if (context->argumentCount() < 2) {
|
||||
// qDebug() << i18n("i18nc() takes at least two arguments");
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
KLocalizedString message = ki18nc(context->argument(0).toString().toUtf8(),
|
||||
context->argument(1).toString().toUtf8());
|
||||
|
||||
const int numArgs = context->argumentCount();
|
||||
for (int i = 2; i < numArgs; ++i) {
|
||||
message = message.subs(context->argument(i).toString());
|
||||
}
|
||||
|
||||
return message.toString();
|
||||
}
|
||||
|
||||
QScriptValue jsi18np(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
|
||||
if (context->argumentCount() < 2) {
|
||||
// qDebug() << i18n("i18np() takes at least two arguments");
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
KLocalizedString message = ki18np(context->argument(0).toString().toUtf8(),
|
||||
context->argument(1).toString().toUtf8());
|
||||
|
||||
const int numArgs = context->argumentCount();
|
||||
for (int i = 2; i < numArgs; ++i) {
|
||||
QScriptValue v = context->argument(i);
|
||||
if (v.isNumber()) {
|
||||
message = message.subs(v.toInt32());
|
||||
} else {
|
||||
message = message.subs(v.toString());
|
||||
}
|
||||
}
|
||||
|
||||
return message.toString();
|
||||
}
|
||||
|
||||
QScriptValue jsi18ncp(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
|
||||
if (context->argumentCount() < 3) {
|
||||
// qDebug() << i18n("i18ncp() takes at least three arguments");
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
KLocalizedString message = ki18ncp(context->argument(0).toString().toUtf8(),
|
||||
context->argument(1).toString().toUtf8(),
|
||||
context->argument(2).toString().toUtf8());
|
||||
|
||||
const int numArgs = context->argumentCount();
|
||||
for (int i = 3; i < numArgs; ++i) {
|
||||
message = message.subs(context->argument(i).toString());
|
||||
}
|
||||
|
||||
return message.toString();
|
||||
}
|
||||
|
||||
void bindI18N(QScriptEngine *engine)
|
||||
{
|
||||
QScriptValue global = engine->globalObject();
|
||||
global.setProperty("i18n", engine->newFunction(jsi18n));
|
||||
global.setProperty("i18nc", engine->newFunction(jsi18nc));
|
||||
global.setProperty("i18np", engine->newFunction(jsi18np));
|
||||
global.setProperty("i18ncp", engine->newFunction(jsi18ncp));
|
||||
}
|
||||
|
@ -1,35 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef JAVASCRIPTBINDI18N_H
|
||||
#define JAVASCRIPTBINDI18N_H
|
||||
|
||||
#include <QScriptValue>
|
||||
|
||||
class QScriptContext;
|
||||
class QScriptEngine;
|
||||
|
||||
QScriptValue jsi18n(QScriptContext *context, QScriptEngine *engine);
|
||||
QScriptValue jsi18nc(QScriptContext *context, QScriptEngine *engine);
|
||||
QScriptValue jsi18np(QScriptContext *context, QScriptEngine *engine);
|
||||
QScriptValue jsi18ncp(QScriptContext *context, QScriptEngine *engine);
|
||||
void bindI18N(QScriptEngine *engine);
|
||||
|
||||
#endif
|
||||
|
@ -1,367 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "panel.h"
|
||||
|
||||
#include <QAction>
|
||||
#include <QQuickItem>
|
||||
|
||||
#include <Plasma/Corona>
|
||||
#include <Plasma/Containment>
|
||||
#include <QScreen>
|
||||
|
||||
#include "shellcorona.h"
|
||||
#include "panelview.h"
|
||||
#include "scriptengine.h"
|
||||
#include "widget.h"
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
Panel::Panel(Plasma::Containment *containment, QObject *parent)
|
||||
: Containment(containment, parent)
|
||||
{
|
||||
m_corona = qobject_cast<ShellCorona *>(containment->corona());
|
||||
}
|
||||
|
||||
Panel::~Panel()
|
||||
{
|
||||
}
|
||||
|
||||
QString Panel::location() const
|
||||
{
|
||||
Plasma::Containment *c = containment();
|
||||
if (!c) {
|
||||
return "floating";
|
||||
}
|
||||
|
||||
switch (c->location()) {
|
||||
case Plasma::Types::Floating:
|
||||
return "floating";
|
||||
break;
|
||||
case Plasma::Types::Desktop:
|
||||
return "desktop";
|
||||
break;
|
||||
case Plasma::Types::FullScreen:
|
||||
return "fullscreen";
|
||||
break;
|
||||
case Plasma::Types::TopEdge:
|
||||
return "top";
|
||||
break;
|
||||
case Plasma::Types::BottomEdge:
|
||||
return "bottom";
|
||||
break;
|
||||
case Plasma::Types::LeftEdge:
|
||||
return "left";
|
||||
break;
|
||||
case Plasma::Types::RightEdge:
|
||||
return "right";
|
||||
break;
|
||||
}
|
||||
|
||||
return "floating";
|
||||
}
|
||||
|
||||
void Panel::setLocation(const QString &locationString)
|
||||
{
|
||||
Plasma::Containment *c = containment();
|
||||
if (!c) {
|
||||
return;
|
||||
}
|
||||
|
||||
const QString lower = locationString.toLower();
|
||||
Plasma::Types::Location loc = Plasma::Types::Floating;
|
||||
Plasma::Types::FormFactor ff = Plasma::Types::Planar;
|
||||
if (lower == "desktop") {
|
||||
loc = Plasma::Types::Desktop;
|
||||
} else if (lower == "fullscreen") {
|
||||
loc = Plasma::Types::FullScreen;
|
||||
} else if (lower == "top") {
|
||||
loc = Plasma::Types::TopEdge;
|
||||
ff = Plasma::Types::Horizontal;
|
||||
} else if (lower == "bottom") {
|
||||
loc = Plasma::Types::BottomEdge;
|
||||
ff = Plasma::Types::Horizontal;
|
||||
} else if (lower == "left") {
|
||||
loc = Plasma::Types::LeftEdge;
|
||||
ff = Plasma::Types::Vertical;
|
||||
} else if (lower == "right") {
|
||||
loc = Plasma::Types::RightEdge;
|
||||
ff = Plasma::Types::Vertical;
|
||||
}
|
||||
|
||||
c->setLocation(loc);
|
||||
c->setFormFactor(ff);
|
||||
}
|
||||
|
||||
PanelView *Panel::panel() const
|
||||
{
|
||||
Plasma::Containment *c = containment();
|
||||
if (!c) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return m_corona->panelView(c);
|
||||
}
|
||||
|
||||
QString Panel::alignment() const
|
||||
{
|
||||
PanelView *v = panel();
|
||||
if (!v) {
|
||||
return "left";
|
||||
}
|
||||
|
||||
switch (v->alignment()) {
|
||||
case Qt::AlignRight:
|
||||
return "right";
|
||||
break;
|
||||
case Qt::AlignCenter:
|
||||
return "center";
|
||||
break;
|
||||
default:
|
||||
return "left";
|
||||
break;
|
||||
}
|
||||
|
||||
return "left";
|
||||
}
|
||||
|
||||
void Panel::setAlignment(const QString &alignment)
|
||||
{
|
||||
PanelView *v = panel();
|
||||
if (v) {
|
||||
bool success = false;
|
||||
|
||||
if (alignment.compare("left", Qt::CaseInsensitive) == 0) {
|
||||
success = true;
|
||||
v->setAlignment(Qt::AlignLeft);
|
||||
} else if (alignment.compare("right", Qt::CaseInsensitive) == 0) {
|
||||
success = true;
|
||||
v->setAlignment(Qt::AlignRight);
|
||||
} else if (alignment.compare("center", Qt::CaseInsensitive) == 0) {
|
||||
success = true;
|
||||
v->setAlignment(Qt::AlignCenter);
|
||||
}
|
||||
|
||||
if (success) {
|
||||
v->setOffset(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int Panel::offset() const
|
||||
{
|
||||
PanelView *v = panel();
|
||||
if (v) {
|
||||
return v->offset();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void Panel::setOffset(int pixels)
|
||||
{
|
||||
Plasma::Containment *c = containment();
|
||||
if (pixels < 0 || !c) {
|
||||
return;
|
||||
}
|
||||
|
||||
QQuickItem *graphicObject = qobject_cast<QQuickItem *>(c->property("_plasma_graphicObject").value<QObject *>());
|
||||
|
||||
if (!graphicObject) {
|
||||
return;
|
||||
}
|
||||
|
||||
PanelView *v = panel();
|
||||
if (v) {
|
||||
QRectF screen = v->screen()->geometry();
|
||||
QSizeF size(graphicObject->width(), graphicObject->height());
|
||||
|
||||
if (c->formFactor() == Plasma::Types::Vertical) {
|
||||
if (pixels > screen.height()) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (size.height() + pixels > screen.height()) {
|
||||
graphicObject->setWidth(size.width());
|
||||
graphicObject->setHeight(screen.height() - pixels);
|
||||
}
|
||||
} else if (pixels > screen.width()) {
|
||||
return;
|
||||
} else if (size.width() + pixels > screen.width()) {
|
||||
size.setWidth(screen.width() - pixels);
|
||||
graphicObject->setWidth(size.width());
|
||||
graphicObject->setHeight(size.height());
|
||||
v->setMinimumSize(size.toSize());
|
||||
v->setMaximumSize(size.toSize());
|
||||
}
|
||||
|
||||
v->setOffset(pixels);
|
||||
}
|
||||
}
|
||||
|
||||
int Panel::length() const
|
||||
{
|
||||
Plasma::Containment *c = containment();
|
||||
if (!c) {
|
||||
return 0;
|
||||
}
|
||||
QQuickItem *graphicObject = qobject_cast<QQuickItem *>(c->property("_plasma_graphicObject").value<QObject *>());
|
||||
|
||||
if (!graphicObject) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (c->formFactor() == Plasma::Types::Vertical) {
|
||||
return graphicObject->height();
|
||||
} else {
|
||||
return graphicObject->width();
|
||||
}
|
||||
}
|
||||
|
||||
void Panel::setLength(int pixels)
|
||||
{
|
||||
Plasma::Containment *c = containment();
|
||||
if (pixels < 0 || !c) {
|
||||
return;
|
||||
}
|
||||
|
||||
QQuickItem *graphicObject = qobject_cast<QQuickItem *>(c->property("_plasma_graphicObject").value<QObject *>());
|
||||
|
||||
if (!graphicObject) {
|
||||
return;
|
||||
}
|
||||
|
||||
PanelView *v = panel();
|
||||
if (v) {
|
||||
QRectF screen = v->screen()->geometry();
|
||||
QSizeF s(graphicObject->width(), graphicObject->height());
|
||||
|
||||
if (c->formFactor() == Plasma::Types::Vertical) {
|
||||
if (pixels > screen.height() - v->offset()) {
|
||||
return;
|
||||
}
|
||||
|
||||
s.setHeight(pixels);
|
||||
} else if (pixels > screen.width() - v->offset()) {
|
||||
return;
|
||||
} else {
|
||||
s.setWidth(pixels);
|
||||
}
|
||||
|
||||
graphicObject->setWidth(s.width());
|
||||
graphicObject->setHeight(s.height());
|
||||
v->setMinimumSize(s.toSize());
|
||||
v->setMaximumSize(s.toSize());
|
||||
}
|
||||
}
|
||||
|
||||
int Panel::height() const
|
||||
{
|
||||
Plasma::Containment *c = containment();
|
||||
if (!c) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
QQuickItem *graphicObject = qobject_cast<QQuickItem *>(c->property("_plasma_graphicObject").value<QObject *>());
|
||||
|
||||
if (!graphicObject) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return c->formFactor() == Plasma::Types::Vertical ? graphicObject->width()
|
||||
: graphicObject->height();
|
||||
}
|
||||
|
||||
void Panel::setHeight(int height)
|
||||
{
|
||||
Plasma::Containment *c = containment();
|
||||
if (height < 16 || !c) {
|
||||
return;
|
||||
}
|
||||
|
||||
QQuickItem *graphicObject = qobject_cast<QQuickItem *>(c->property("_plasma_graphicObject").value<QObject *>());
|
||||
|
||||
if (!graphicObject) {
|
||||
return;
|
||||
}
|
||||
|
||||
PanelView *v = panel();
|
||||
if (v) {
|
||||
QRect screen = v->screen()->geometry();
|
||||
QSizeF size(graphicObject->width(), graphicObject->height());
|
||||
const int max = (c->formFactor() == Plasma::Types::Vertical ? screen.width() : screen.height()) / 3;
|
||||
height = qBound(16, height, max);
|
||||
|
||||
if (c->formFactor() == Plasma::Types::Vertical) {
|
||||
size.setWidth(height);
|
||||
} else {
|
||||
size.setHeight(height);
|
||||
}
|
||||
|
||||
graphicObject->setWidth(size.width());
|
||||
graphicObject->setHeight(size.height());
|
||||
v->setMinimumSize(size.toSize());
|
||||
v->setMaximumSize(size.toSize());
|
||||
}
|
||||
}
|
||||
|
||||
QString Panel::hiding() const
|
||||
{
|
||||
/*PanelView *v = panel();
|
||||
if (v) {
|
||||
switch (v->visibilityMode()) {
|
||||
case PanelView::NormalPanel:
|
||||
return "none";
|
||||
break;
|
||||
case PanelView::AutoHide:
|
||||
return "autohide";
|
||||
break;
|
||||
case PanelView::LetWindowsCover:
|
||||
return "windowscover";
|
||||
break;
|
||||
case PanelView::WindowsGoBelow:
|
||||
return "windowsbelow";
|
||||
break;
|
||||
}
|
||||
}*/
|
||||
|
||||
return "none";
|
||||
}
|
||||
|
||||
void Panel::setHiding(const QString &mode)
|
||||
{
|
||||
/*PanelView *v = panel();
|
||||
if (v) {
|
||||
if (mode.compare("autohide", Qt::CaseInsensitive) == 0) {
|
||||
v->setVisibilityMode(PanelView::AutoHide);
|
||||
} else if (mode.compare("windowscover", Qt::CaseInsensitive) == 0) {
|
||||
v->setVisibilityMode(PanelView::LetWindowsCover);
|
||||
} else if (mode.compare("windowsbelow", Qt::CaseInsensitive) == 0) {
|
||||
v->setVisibilityMode(PanelView::WindowsGoBelow);
|
||||
} else {
|
||||
v->setVisibilityMode(PanelView::NormalPanel);
|
||||
}
|
||||
}*/
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#include "panel.moc"
|
||||
|
@ -1,97 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef PANEL
|
||||
#define PANEL
|
||||
|
||||
#include <QScriptContext>
|
||||
#include <QScriptValue>
|
||||
#include <QWeakPointer>
|
||||
|
||||
#include "containment.h"
|
||||
|
||||
class PanelView;
|
||||
class ShellCorona;
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class Panel : public Containment
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(QStringList configKeys READ configKeys)
|
||||
Q_PROPERTY(QStringList configGroups READ configGroups)
|
||||
Q_PROPERTY(QStringList currentConfigGroup WRITE setCurrentConfigGroup READ currentConfigGroup)
|
||||
|
||||
Q_PROPERTY(QString name READ name WRITE setName)
|
||||
Q_PROPERTY(QString version READ version)
|
||||
Q_PROPERTY(QString type READ type)
|
||||
Q_PROPERTY(QString formFactor READ formFactor)
|
||||
Q_PROPERTY(QList<int> widgetIds READ widgetIds)
|
||||
Q_PROPERTY(int screen READ screen)
|
||||
Q_PROPERTY(QString location READ location WRITE setLocation)
|
||||
Q_PROPERTY(int id READ id)
|
||||
|
||||
// panel properties
|
||||
Q_PROPERTY(QString alignment READ alignment WRITE setAlignment)
|
||||
Q_PROPERTY(int offset READ offset WRITE setOffset)
|
||||
Q_PROPERTY(int length READ length WRITE setLength)
|
||||
Q_PROPERTY(int height READ height WRITE setHeight)
|
||||
Q_PROPERTY(QString hiding READ hiding WRITE setHiding)
|
||||
|
||||
public:
|
||||
Panel(Plasma::Containment *containment, QObject *parent = 0);
|
||||
~Panel();
|
||||
|
||||
QString location() const;
|
||||
void setLocation(const QString &location);
|
||||
|
||||
QString alignment() const;
|
||||
void setAlignment(const QString &alignment);
|
||||
|
||||
int offset() const;
|
||||
void setOffset(int pixels);
|
||||
|
||||
int length() const;
|
||||
void setLength(int pixels);
|
||||
|
||||
int height() const;
|
||||
void setHeight(int height);
|
||||
|
||||
QString hiding() const;
|
||||
void setHiding(const QString &mode);
|
||||
|
||||
public Q_SLOTS:
|
||||
void remove() { Containment::remove(); }
|
||||
void showConfigurationInterface() { Containment::showConfigurationInterface(); }
|
||||
|
||||
// from the applet interface
|
||||
QVariant readConfig(const QString &key, const QVariant &def = QString()) const { return Applet::readConfig(key, def); }
|
||||
void writeConfig(const QString &key, const QVariant &value) { Applet::writeConfig(key, value); }
|
||||
void reloadConfig() { Applet::reloadConfig(); }
|
||||
|
||||
private:
|
||||
PanelView *panel() const;
|
||||
ShellCorona *m_corona;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -1,330 +0,0 @@
|
||||
/*
|
||||
* Copyright 2007 Richard J. Moore <rich@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License version 2 as
|
||||
* published by the Free Software Foundation
|
||||
*
|
||||
* 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include <QtScript/QScriptValue>
|
||||
#include <QtScript/QScriptEngine>
|
||||
#include <QtScript/QScriptContext>
|
||||
#include <QtCore/QRectF>
|
||||
#include "backportglobal.h"
|
||||
|
||||
Q_DECLARE_METATYPE(QRectF*)
|
||||
Q_DECLARE_METATYPE(QRectF)
|
||||
|
||||
static QScriptValue ctor(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
if (ctx->argumentCount() == 4)
|
||||
{
|
||||
qreal x = ctx->argument(0).toNumber();
|
||||
qreal y = ctx->argument(1).toNumber();
|
||||
qreal width = ctx->argument(2).toNumber();
|
||||
qreal height = ctx->argument(3).toNumber();
|
||||
return qScriptValueFromValue(eng, QRectF(x, y, width, height));
|
||||
}
|
||||
|
||||
return qScriptValueFromValue(eng, QRectF());
|
||||
}
|
||||
|
||||
static QScriptValue adjust(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, adjust);
|
||||
qreal dx1 = ctx->argument(0).toNumber();
|
||||
qreal dy1 = ctx->argument(1).toNumber();
|
||||
qreal dx2 = ctx->argument(2).toNumber();
|
||||
qreal dy2 = ctx->argument(3).toNumber();
|
||||
|
||||
self->adjust(dx1, dy1, dx2, dy2);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
static QScriptValue adjusted(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, adjusted);
|
||||
qreal dx1 = ctx->argument(0).toNumber();
|
||||
qreal dy1 = ctx->argument(1).toNumber();
|
||||
qreal dx2 = ctx->argument(2).toNumber();
|
||||
qreal dy2 = ctx->argument(3).toNumber();
|
||||
|
||||
QRectF tmp = self->adjusted(dx1, dy1, dx2, dy2);
|
||||
return qScriptValueFromValue(eng, tmp);
|
||||
}
|
||||
|
||||
static QScriptValue bottom(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, bottom);
|
||||
|
||||
if (ctx->argumentCount() > 0) {
|
||||
int bottom = ctx->argument(0).toInt32();
|
||||
self->setBottom(bottom);
|
||||
}
|
||||
|
||||
return QScriptValue(eng, self->bottom());
|
||||
}
|
||||
|
||||
static QScriptValue top(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, top);
|
||||
|
||||
if (ctx->argumentCount() > 0) {
|
||||
int top = ctx->argument(0).toInt32();
|
||||
self->setTop(top);
|
||||
}
|
||||
|
||||
return QScriptValue(eng, self->top());
|
||||
}
|
||||
|
||||
static QScriptValue contains(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, contains);
|
||||
qreal x = ctx->argument(0).toNumber();
|
||||
qreal y = ctx->argument(1).toNumber();
|
||||
return QScriptValue(eng, self->contains(x, y));
|
||||
}
|
||||
|
||||
static QScriptValue height(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, height);
|
||||
|
||||
if (ctx->argumentCount() > 0) {
|
||||
int height = ctx->argument(0).toInt32();
|
||||
self->setHeight(height);
|
||||
}
|
||||
|
||||
return QScriptValue(eng, self->height());
|
||||
}
|
||||
|
||||
static QScriptValue empty(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, empty);
|
||||
return QScriptValue(eng, self->isEmpty());
|
||||
}
|
||||
|
||||
static QScriptValue null(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, null);
|
||||
return QScriptValue(eng, self->isNull());
|
||||
}
|
||||
|
||||
static QScriptValue valid(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, valid);
|
||||
return QScriptValue(eng, self->isValid());
|
||||
}
|
||||
|
||||
static QScriptValue left(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, left);
|
||||
|
||||
if (ctx->argumentCount() > 0) {
|
||||
int left = ctx->argument(0).toInt32();
|
||||
self->setLeft(left);
|
||||
}
|
||||
|
||||
return QScriptValue(eng, self->left());
|
||||
}
|
||||
|
||||
static QScriptValue moveBottom(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, moveBottom);
|
||||
qreal bottom = ctx->argument(0).toNumber();
|
||||
self->moveBottom(bottom);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
static QScriptValue moveLeft(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, moveLeft);
|
||||
qreal left = ctx->argument(0).toNumber();
|
||||
self->moveBottom(left);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
static QScriptValue moveRight(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, moveRight);
|
||||
qreal right = ctx->argument(0).toNumber();
|
||||
self->moveBottom(right);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
|
||||
static QScriptValue moveTo(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, moveTo);
|
||||
qreal x = ctx->argument(0).toNumber();
|
||||
qreal y = ctx->argument(1).toNumber();
|
||||
self->moveTo(x, y);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
static QScriptValue moveTop(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, moveTop);
|
||||
qreal top = ctx->argument(0).toNumber();
|
||||
self->moveTop(top);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
static QScriptValue right(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, right);
|
||||
|
||||
if (ctx->argumentCount() > 0) {
|
||||
int right = ctx->argument(0).toInt32();
|
||||
self->setRight(right);
|
||||
}
|
||||
|
||||
return QScriptValue(eng, self->right());
|
||||
}
|
||||
|
||||
static QScriptValue setCoords(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, setCoords);
|
||||
qreal x1 = ctx->argument(0).toNumber();
|
||||
qreal y1 = ctx->argument(1).toNumber();
|
||||
qreal x2 = ctx->argument(2).toNumber();
|
||||
qreal y2 = ctx->argument(3).toNumber();
|
||||
self->setCoords(x1, y1, x2, y2);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
static QScriptValue setRect(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, setRect);
|
||||
qreal x = ctx->argument(0).toNumber();
|
||||
qreal y = ctx->argument(1).toNumber();
|
||||
qreal width = ctx->argument(2).toNumber();
|
||||
qreal height = ctx->argument(3).toNumber();
|
||||
self->setRect(x, y, width, height);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
static QScriptValue translate(QScriptContext *ctx, QScriptEngine *)
|
||||
{
|
||||
DECLARE_SELF(QRectF, translate);
|
||||
qreal dx = ctx->argument(0).toNumber();
|
||||
qreal dy = ctx->argument(1).toNumber();
|
||||
self->translate(dx, dy);
|
||||
return QScriptValue();
|
||||
}
|
||||
|
||||
static QScriptValue width(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, width);
|
||||
|
||||
if (ctx->argumentCount() > 0) {
|
||||
int width = ctx->argument(0).toInt32();
|
||||
self->setWidth(width);
|
||||
}
|
||||
|
||||
return QScriptValue(eng, self->width());
|
||||
}
|
||||
|
||||
static QScriptValue x(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, x);
|
||||
|
||||
if (ctx->argumentCount() > 0) {
|
||||
int x = ctx->argument(0).toInt32();
|
||||
self->setX(x);
|
||||
}
|
||||
|
||||
return QScriptValue(eng, self->x());
|
||||
}
|
||||
|
||||
static QScriptValue y(QScriptContext *ctx, QScriptEngine *eng)
|
||||
{
|
||||
DECLARE_SELF(QRectF, y);
|
||||
|
||||
if (ctx->argumentCount() > 0) {
|
||||
int y = ctx->argument(0).toInt32();
|
||||
self->setY(y);
|
||||
}
|
||||
|
||||
return QScriptValue(eng, self->y());
|
||||
}
|
||||
|
||||
/* Not Implemented Yet */
|
||||
// QPointF bottomLeft () const
|
||||
// QPointF bottomRight () const
|
||||
// QPointF center () const
|
||||
// bool contains ( const QPointF & point ) const
|
||||
// bool contains ( const QRectF & rectangle ) const
|
||||
// void getCoords ( qreal * x1, qreal * y1, qreal * x2, qreal * y2 ) const
|
||||
// void getRect ( qreal * x, qreal * y, qreal * width, qreal * height ) const
|
||||
// QRectF intersected ( const QRectF & rectangle ) const
|
||||
// bool intersects ( const QRectF & rectangle ) const
|
||||
// void moveBottomLeft ( const QPointF & position )
|
||||
// void moveBottomRight ( const QPointF & position )
|
||||
// void moveCenter ( const QPointF & position )
|
||||
// void moveTo ( const QPointF & position )
|
||||
// void moveTopLeft ( const QPointF & position )
|
||||
// void moveTopRight ( const QPointF & position )
|
||||
// QRectF normalized () const
|
||||
// void setBottomLeft ( const QPointF & position )
|
||||
// void setBottomRight ( const QPointF & position )
|
||||
// void setSize ( const QSizeF & size )
|
||||
// void setTopLeft ( const QPointF & position )
|
||||
// void setTopRight ( const QPointF & position )
|
||||
// QSizeF size () const
|
||||
// QRect toAlignedRect () const
|
||||
// QRect toRect () const
|
||||
// QPointF topLeft () const
|
||||
// QPointF topRight () const
|
||||
// void translate ( const QPointF & offset )
|
||||
// QRectF translated ( qreal dx, qreal dy ) const
|
||||
// QRectF translated ( const QPointF & offset ) const
|
||||
// QRectF united ( const QRectF & rectangle ) const
|
||||
|
||||
QScriptValue constructQRectFClass(QScriptEngine *eng)
|
||||
{
|
||||
QScriptValue proto = qScriptValueFromValue(eng, QRectF());
|
||||
QScriptValue::PropertyFlags getter = QScriptValue::PropertyGetter;
|
||||
QScriptValue::PropertyFlags setter = QScriptValue::PropertySetter;
|
||||
|
||||
proto.setProperty("adjust", eng->newFunction(adjust));
|
||||
proto.setProperty("adjusted", eng->newFunction(adjusted), getter);
|
||||
proto.setProperty("translate", eng->newFunction(translate));
|
||||
proto.setProperty("setCoords", eng->newFunction(setCoords));
|
||||
proto.setProperty("setRect", eng->newFunction(setRect));
|
||||
|
||||
proto.setProperty("contains", eng->newFunction(contains));
|
||||
|
||||
proto.setProperty("moveBottom", eng->newFunction(moveBottom));
|
||||
proto.setProperty("moveLeft", eng->newFunction(moveLeft));
|
||||
proto.setProperty("moveRight", eng->newFunction(moveRight));
|
||||
proto.setProperty("moveTo", eng->newFunction(moveTo));
|
||||
proto.setProperty("moveTop", eng->newFunction(moveTop));
|
||||
|
||||
proto.setProperty("empty", eng->newFunction(empty), getter);
|
||||
proto.setProperty("null", eng->newFunction(null), getter);
|
||||
proto.setProperty("valid", eng->newFunction(valid), getter);
|
||||
|
||||
proto.setProperty("left", eng->newFunction(left), getter | setter);
|
||||
proto.setProperty("top", eng->newFunction(top), getter | setter);
|
||||
proto.setProperty("bottom", eng->newFunction(bottom), getter | setter);
|
||||
proto.setProperty("right", eng->newFunction(right), getter | setter);
|
||||
proto.setProperty("height", eng->newFunction(height), getter | setter);
|
||||
proto.setProperty("width", eng->newFunction(width), getter | setter);
|
||||
proto.setProperty("x", eng->newFunction(x), getter | setter);
|
||||
proto.setProperty("y", eng->newFunction(y), getter | setter);
|
||||
|
||||
eng->setDefaultPrototype(qMetaTypeId<QRectF>(), proto);
|
||||
eng->setDefaultPrototype(qMetaTypeId<QRectF*>(), proto);
|
||||
|
||||
return eng->newFunction(ctor, proto);
|
||||
}
|
@ -1,816 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "scriptengine.h"
|
||||
|
||||
#include <QApplication>
|
||||
#include <QDesktopWidget>
|
||||
#include <QDir>
|
||||
#include <QDirIterator>
|
||||
#include <QFile>
|
||||
#include <QFileInfo>
|
||||
#include <QScriptValueIterator>
|
||||
#include <QStandardPaths>
|
||||
#include <QFutureWatcher>
|
||||
|
||||
#include <QDebug>
|
||||
#include <klocalizedstring.h>
|
||||
#include <kmimetypetrader.h>
|
||||
#include <kservicetypetrader.h>
|
||||
#include <kshell.h>
|
||||
|
||||
// KIO
|
||||
//#include <kemailsettings.h> // no camelcase include
|
||||
|
||||
#include <Plasma/Applet>
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/Package>
|
||||
#include <Plasma/PluginLoader>
|
||||
#include <qstandardpaths.h>
|
||||
|
||||
#include "appinterface.h"
|
||||
#include "containment.h"
|
||||
#include "configgroup.h"
|
||||
#include "i18n.h"
|
||||
//#include "packages.h"
|
||||
#include "widget.h"
|
||||
#include "../activity.h"
|
||||
#include "../shellcorona.h"
|
||||
|
||||
QScriptValue constructQRectFClass(QScriptEngine *engine);
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
ScriptEngine::ScriptEngine(ShellCorona *corona, QObject *parent)
|
||||
: QScriptEngine(parent),
|
||||
m_corona(corona)
|
||||
{
|
||||
Q_ASSERT(m_corona);
|
||||
AppInterface *interface = new AppInterface(this);
|
||||
connect(interface, SIGNAL(print(QString)), this, SIGNAL(print(QString)));
|
||||
m_scriptSelf = newQObject(interface, QScriptEngine::QtOwnership,
|
||||
QScriptEngine::ExcludeSuperClassProperties |
|
||||
QScriptEngine::ExcludeSuperClassMethods);
|
||||
setupEngine();
|
||||
connect(this, SIGNAL(signalHandlerException(QScriptValue)), this, SLOT(exception(QScriptValue)));
|
||||
bindI18N(this);
|
||||
}
|
||||
|
||||
ScriptEngine::~ScriptEngine()
|
||||
{
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::desktopById(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
if (context->argumentCount() == 0) {
|
||||
return context->throwError(i18n("activityById requires an id"));
|
||||
}
|
||||
|
||||
const uint id = context->argument(0).toInt32();
|
||||
ScriptEngine *env = envFor(engine);
|
||||
foreach (Plasma::Containment *c, env->m_corona->containments()) {
|
||||
if (c->id() == id && !isPanel(c)) {
|
||||
return env->wrap(c);
|
||||
}
|
||||
}
|
||||
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::desktopsForActivity(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
if (context->argumentCount() == 0) {
|
||||
return context->throwError(i18n("containmentsByActivity requires an id"));
|
||||
}
|
||||
|
||||
QScriptValue containments = engine->newArray();
|
||||
int count = 0;
|
||||
|
||||
const QString id = context->argument(0).toString();
|
||||
ScriptEngine *env = envFor(engine);
|
||||
foreach (Plasma::Containment *c, env->m_corona->containments()) {
|
||||
if (c->activity() == id && !isPanel(c)) {
|
||||
containments.setProperty(count, env->wrap(c));
|
||||
++count;
|
||||
}
|
||||
}
|
||||
|
||||
containments.setProperty("length", count);
|
||||
return containments;
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::desktopForScreen(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
if (context->argumentCount() == 0) {
|
||||
return context->throwError(i18n("activityForScreen requires a screen id"));
|
||||
}
|
||||
|
||||
const uint screen = context->argument(0).toInt32();
|
||||
ScriptEngine *env = envFor(engine);
|
||||
return env->wrap(env->m_corona->containmentForScreen(screen));
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::createActivity(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
if (context->argumentCount() < 0) {
|
||||
return context->throwError(i18n("createActivity required the activity name"));
|
||||
}
|
||||
|
||||
const QString name = context->argument(0).toString();
|
||||
const QString plugin = context->argument(1).toString();
|
||||
|
||||
KActivities::Controller controller;
|
||||
|
||||
QFuture<QString> id = controller.addActivity(name);
|
||||
QEventLoop loop;
|
||||
|
||||
QFutureWatcher<QString> *watcher = new QFutureWatcher<QString>();
|
||||
connect(watcher, &QFutureWatcherBase::finished, &loop, &QEventLoop::quit);
|
||||
|
||||
watcher->setFuture(id);
|
||||
|
||||
loop.exec();
|
||||
|
||||
ScriptEngine *env = envFor(engine);
|
||||
Activity *a = new Activity(id, env->m_corona);
|
||||
if (!plugin.isEmpty()) {
|
||||
a->setDefaultPlugin(plugin);
|
||||
}
|
||||
env->m_corona->insertActivity(id, a);
|
||||
|
||||
return QScriptValue(id.result());
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::setCurrentActivity(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
if (context->argumentCount() < 0) {
|
||||
return context->throwError(i18n("setCurrentActivity required the activity id"));
|
||||
}
|
||||
|
||||
const QString id = context->argument(0).toString();
|
||||
|
||||
KActivities::Controller controller;
|
||||
|
||||
QFuture<bool> task = controller.setCurrentActivity(id);
|
||||
QEventLoop loop;
|
||||
|
||||
QFutureWatcher<bool> *watcher = new QFutureWatcher<bool>();
|
||||
connect(watcher, &QFutureWatcherBase::finished, &loop, &QEventLoop::quit);
|
||||
|
||||
watcher->setFuture(task);
|
||||
|
||||
loop.exec();
|
||||
|
||||
return QScriptValue(task.result());
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::activities(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
KActivities::Consumer consumer;
|
||||
|
||||
return qScriptValueFromSequence(engine, consumer.activities());
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::newPanel(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
return createContainment("Panel", "org.kde.panel", context, engine);
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::createContainment(const QString &type, const QString &defaultPlugin,
|
||||
QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
QString plugin = context->argumentCount() > 0 ? context->argument(0).toString() :
|
||||
defaultPlugin;
|
||||
|
||||
bool exists = false;
|
||||
const KPluginInfo::List list = Plasma::PluginLoader::listContainmentsOfType(type);
|
||||
foreach (const KPluginInfo &info, list) {
|
||||
if (info.pluginName() == plugin) {
|
||||
exists = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!exists) {
|
||||
return context->throwError(i18n("Could not find a plugin for %1 named %2.", type, plugin));
|
||||
}
|
||||
|
||||
|
||||
ScriptEngine *env = envFor(engine);
|
||||
Plasma::Containment *c = env->m_corona->createContainment(plugin);
|
||||
if (c) {
|
||||
if (type == "Panel") {
|
||||
// some defaults
|
||||
c->setFormFactor(Plasma::Types::Horizontal);
|
||||
c->setLocation(Plasma::Types::TopEdge);
|
||||
}
|
||||
c->updateConstraints(Plasma::Types::AllConstraints | Plasma::Types::StartupCompletedConstraint);
|
||||
c->flushPendingConstraintsEvents();
|
||||
}
|
||||
|
||||
return env->wrap(c);
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::wrap(Plasma::Applet *w)
|
||||
{
|
||||
Widget *wrapper = new Widget(w);
|
||||
QScriptValue v = newQObject(wrapper, QScriptEngine::ScriptOwnership,
|
||||
QScriptEngine::ExcludeSuperClassProperties |
|
||||
QScriptEngine::ExcludeSuperClassMethods);
|
||||
return v;
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::wrap(Plasma::Containment *c)
|
||||
{
|
||||
Containment *wrapper = new Containment(c);
|
||||
return wrap(wrapper);
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::wrap(Containment *c)
|
||||
{
|
||||
QScriptValue v = newQObject(c, QScriptEngine::ScriptOwnership,
|
||||
QScriptEngine::ExcludeSuperClassProperties |
|
||||
QScriptEngine::ExcludeSuperClassMethods);
|
||||
v.setProperty("widgetById", newFunction(Containment::widgetById));
|
||||
v.setProperty("addWidget", newFunction(Containment::addWidget));
|
||||
v.setProperty("widgets", newFunction(Containment::widgets));
|
||||
|
||||
return v;
|
||||
}
|
||||
|
||||
int ScriptEngine::defaultPanelScreen() const
|
||||
{
|
||||
return qApp ? qApp->desktop()->primaryScreen() : 0;
|
||||
}
|
||||
|
||||
ScriptEngine *ScriptEngine::envFor(QScriptEngine *engine)
|
||||
{
|
||||
QObject *object = engine->globalObject().toQObject();
|
||||
Q_ASSERT(object);
|
||||
|
||||
AppInterface *interface = qobject_cast<AppInterface *>(object);
|
||||
Q_ASSERT(interface);
|
||||
|
||||
ScriptEngine *env = qobject_cast<ScriptEngine *>(interface->parent());
|
||||
Q_ASSERT(env);
|
||||
|
||||
return env;
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::panelById(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
if (context->argumentCount() == 0) {
|
||||
return context->throwError(i18n("panelById requires an id"));
|
||||
}
|
||||
|
||||
const uint id = context->argument(0).toInt32();
|
||||
ScriptEngine *env = envFor(engine);
|
||||
foreach (Plasma::Containment *c, env->m_corona->containments()) {
|
||||
if (c->id() == id && isPanel(c)) {
|
||||
return env->wrap(c);
|
||||
}
|
||||
}
|
||||
|
||||
return engine->undefinedValue();
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::panels(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(context)
|
||||
|
||||
QScriptValue panels = engine->newArray();
|
||||
ScriptEngine *env = envFor(engine);
|
||||
int count = 0;
|
||||
|
||||
foreach (Plasma::Containment *c, env->m_corona->containments()) {
|
||||
if (isPanel(c)) {
|
||||
panels.setProperty(count, env->wrap(c));
|
||||
++count;
|
||||
}
|
||||
}
|
||||
|
||||
panels.setProperty("length", count);
|
||||
return panels;
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::fileExists(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
if (context->argumentCount() == 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const QString path = context->argument(0).toString();
|
||||
if (path.isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
QFile f(KShell::tildeExpand(path));
|
||||
return f.exists();
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::loadTemplate(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
if (context->argumentCount() == 0) {
|
||||
// qDebug() << "no arguments";
|
||||
return false;
|
||||
}
|
||||
|
||||
const QString layout = context->argument(0).toString();
|
||||
if (layout.isEmpty() || layout.contains("'")) {
|
||||
// qDebug() << "layout is empty";
|
||||
return false;
|
||||
}
|
||||
|
||||
const QString constraint = QString("[X-Plasma-Shell] == '%1' and [X-KDE-PluginInfo-Name] == '%2'")
|
||||
.arg(qApp->applicationName(),layout);
|
||||
KService::List offers = KServiceTypeTrader::self()->query("Plasma/LayoutTemplate", constraint);
|
||||
|
||||
if (offers.isEmpty()) {
|
||||
// qDebug() << "offers fail" << constraint;
|
||||
return false;
|
||||
}
|
||||
|
||||
Plasma::Package package = Plasma::PluginLoader::self()->loadPackage("Plasma/LayoutTemplate");
|
||||
KPluginInfo info(offers.first());
|
||||
const QString path = QStandardPaths::locate(QStandardPaths::GenericDataLocation, package.defaultPackageRoot() + '/' + info.pluginName() + '/');
|
||||
if (path.isEmpty()) {
|
||||
// qDebug() << "script path is empty";
|
||||
return false;
|
||||
}
|
||||
package.setPath(path);
|
||||
|
||||
const QString scriptFile = package.filePath("mainscript");
|
||||
if (scriptFile.isEmpty()) {
|
||||
// qDebug() << "scriptfile is empty";
|
||||
return false;
|
||||
}
|
||||
|
||||
QFile file(scriptFile);
|
||||
if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
|
||||
qWarning() << i18n("Unable to load script file: %1", path);
|
||||
return false;
|
||||
}
|
||||
|
||||
QString script = file.readAll();
|
||||
if (script.isEmpty()) {
|
||||
// qDebug() << "script is empty";
|
||||
return false;
|
||||
}
|
||||
|
||||
ScriptEngine *env = envFor(engine);
|
||||
env->globalObject().setProperty("templateName", env->newVariant(info.name()), QScriptValue::ReadOnly | QScriptValue::Undeletable);
|
||||
env->globalObject().setProperty("templateComment", env->newVariant(info.comment()), QScriptValue::ReadOnly | QScriptValue::Undeletable);
|
||||
|
||||
QScriptValue rv = env->newObject();
|
||||
QScriptContext *ctx = env->pushContext();
|
||||
ctx->setThisObject(rv);
|
||||
|
||||
env->evaluateScript(script, path);
|
||||
|
||||
env->popContext();
|
||||
return rv;
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::applicationExists(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
if (context->argumentCount() == 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const QString application = context->argument(0).toString();
|
||||
if (application.isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// first, check for it in $PATH
|
||||
if (!QStandardPaths::findExecutable(application).isEmpty()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (KService::serviceByStorageId(application)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (application.contains("'")) {
|
||||
// apostrophes just screw up the trader lookups below, so check for it
|
||||
return false;
|
||||
}
|
||||
|
||||
// next, consult ksycoca for an app by that name
|
||||
if (!KServiceTypeTrader::self()->query("Application", QString("Name =~ '%1'").arg(application)).isEmpty()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// next, consult ksycoca for an app by that generic name
|
||||
if (!KServiceTypeTrader::self()->query("Application", QString("GenericName =~ '%1'").arg(application)).isEmpty()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
QString ScriptEngine::onlyExec(const QString &commandLine)
|
||||
{
|
||||
if (commandLine.isEmpty()) {
|
||||
return commandLine;
|
||||
}
|
||||
|
||||
return KShell::splitArgs(commandLine, KShell::TildeExpand).first();
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::defaultApplication(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
if (context->argumentCount() == 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const QString application = context->argument(0).toString();
|
||||
if (application.isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const bool storageId = context->argumentCount() < 2 ? false : context->argument(1).toBool();
|
||||
|
||||
// FIXME: there are some pretty horrible hacks below, in the sense that they assume a very
|
||||
// specific implementation system. there is much room for improvement here. see
|
||||
// kdebase-runtime/kcontrol/componentchooser/ for all the gory details ;)
|
||||
if (application.compare("mailer", Qt::CaseInsensitive) == 0) {
|
||||
// KEMailSettings settings;
|
||||
|
||||
// in KToolInvocation, the default is kmail; but let's be friendlier :)
|
||||
// QString command = settings.getSetting(KEMailSettings::ClientProgram);
|
||||
QString command;
|
||||
if (command.isEmpty()) {
|
||||
if (KService::Ptr kontact = KService::serviceByStorageId("kontact")) {
|
||||
return storageId ? kontact->storageId() : onlyExec(kontact->exec());
|
||||
} else if (KService::Ptr kmail = KService::serviceByStorageId("kmail")) {
|
||||
return storageId ? kmail->storageId() : onlyExec(kmail->exec());
|
||||
}
|
||||
}
|
||||
|
||||
if (!command.isEmpty()) {
|
||||
//if (settings.getSetting(KEMailSettings::ClientTerminal) == "true") {
|
||||
if (false) {
|
||||
KConfigGroup confGroup(KSharedConfig::openConfig(), "General");
|
||||
const QString preferredTerminal = confGroup.readPathEntry("TerminalApplication", QString::fromLatin1("konsole"));
|
||||
command = preferredTerminal + QString::fromLatin1(" -e ") + command;
|
||||
}
|
||||
|
||||
return command;
|
||||
}
|
||||
} else if (application.compare("browser", Qt::CaseInsensitive) == 0) {
|
||||
KConfigGroup config(KSharedConfig::openConfig(), "General");
|
||||
QString browserApp = config.readPathEntry("BrowserApplication", QString());
|
||||
if (browserApp.isEmpty()) {
|
||||
const KService::Ptr htmlApp = KMimeTypeTrader::self()->preferredService(QLatin1String("text/html"));
|
||||
if (htmlApp) {
|
||||
browserApp = storageId ? htmlApp->storageId() : htmlApp->exec();
|
||||
}
|
||||
} else if (browserApp.startsWith('!')) {
|
||||
browserApp = browserApp.mid(1);
|
||||
}
|
||||
|
||||
return onlyExec(browserApp);
|
||||
} else if (application.compare("terminal", Qt::CaseInsensitive) == 0) {
|
||||
KConfigGroup confGroup(KSharedConfig::openConfig(), "General");
|
||||
return onlyExec(confGroup.readPathEntry("TerminalApplication", QString::fromLatin1("konsole")));
|
||||
} else if (application.compare("filemanager", Qt::CaseInsensitive) == 0) {
|
||||
KService::Ptr service = KMimeTypeTrader::self()->preferredService("inode/directory");
|
||||
if (service) {
|
||||
return storageId ? service->storageId() : onlyExec(service->exec());
|
||||
}
|
||||
} else if (application.compare("windowmanager", Qt::CaseInsensitive) == 0) {
|
||||
KConfig cfg("ksmserverrc", KConfig::NoGlobals);
|
||||
KConfigGroup confGroup(&cfg, "General");
|
||||
return onlyExec(confGroup.readEntry("windowManager", QString::fromLatin1("kwin")));
|
||||
} else if (KService::Ptr service = KMimeTypeTrader::self()->preferredService(application)) {
|
||||
return storageId ? service->storageId() : onlyExec(service->exec());
|
||||
} else {
|
||||
// try the files in share/apps/kcm_componentchooser/
|
||||
const QStringList services = QStandardPaths::locateAll(QStandardPaths::GenericDataLocation, "kcm_componentchooser/");
|
||||
qDebug() << "ok, trying in" << services;
|
||||
foreach (const QString &service, services) {
|
||||
if (!service.endsWith(".desktop")) {
|
||||
continue;
|
||||
}
|
||||
KConfig config(service, KConfig::SimpleConfig);
|
||||
KConfigGroup cg = config.group(QByteArray());
|
||||
const QString type = cg.readEntry("valueName", QString());
|
||||
//qDebug() << " checking" << service << type << application;
|
||||
if (type.compare(application, Qt::CaseInsensitive) == 0) {
|
||||
KConfig store(cg.readPathEntry("storeInFile", "null"));
|
||||
KConfigGroup storeCg(&store, cg.readEntry("valueSection", QString()));
|
||||
const QString exec = storeCg.readPathEntry(cg.readEntry("valueName", "kcm_componenchooser_null"),
|
||||
cg.readEntry("defaultImplementation", QString()));
|
||||
if (!exec.isEmpty()) {
|
||||
return exec;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::applicationPath(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
if (context->argumentCount() == 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const QString application = context->argument(0).toString();
|
||||
if (application.isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// first, check for it in $PATH
|
||||
const QString path = QStandardPaths::findExecutable(application);
|
||||
if (!path.isEmpty()) {
|
||||
return path;
|
||||
}
|
||||
|
||||
if (KService::Ptr service = KService::serviceByStorageId(application)) {
|
||||
return QStandardPaths::locate(QStandardPaths::ApplicationsLocation, service->entryPath());
|
||||
}
|
||||
|
||||
if (application.contains("'")) {
|
||||
// apostrophes just screw up the trader lookups below, so check for it
|
||||
return QString();
|
||||
}
|
||||
|
||||
// next, consult ksycoca for an app by that name
|
||||
KService::List offers = KServiceTypeTrader::self()->query("Application", QString("Name =~ '%1'").arg(application));
|
||||
if (offers.isEmpty()) {
|
||||
// next, consult ksycoca for an app by that generic name
|
||||
offers = KServiceTypeTrader::self()->query("Application", QString("GenericName =~ '%1'").arg(application));
|
||||
}
|
||||
|
||||
if (!offers.isEmpty()) {
|
||||
KService::Ptr offer = offers.first();
|
||||
return QStandardPaths::locate(QStandardPaths::ApplicationsLocation, offer->entryPath());
|
||||
}
|
||||
|
||||
return QString();
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::userDataPath(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
if (context->argumentCount() == 0) {
|
||||
return QDir::homePath();
|
||||
}
|
||||
|
||||
const QString type = context->argument(0).toString();
|
||||
if (type.isEmpty()) {
|
||||
return QDir::homePath();
|
||||
}
|
||||
|
||||
QStandardPaths::StandardLocation location = QStandardPaths::GenericDataLocation;
|
||||
if (type.compare("desktop", Qt::CaseInsensitive) == 0) {
|
||||
location = QStandardPaths::DesktopLocation;
|
||||
} else if (type.compare("documents", Qt::CaseInsensitive) == 0) {
|
||||
location = QStandardPaths::DocumentsLocation;
|
||||
} else if (type.compare("music", Qt::CaseInsensitive) == 0) {
|
||||
location = QStandardPaths::MusicLocation;
|
||||
} else if (type.compare("video", Qt::CaseInsensitive) == 0) {
|
||||
location = QStandardPaths::MoviesLocation;
|
||||
} else if (type.compare("downloads", Qt::CaseInsensitive) == 0) {
|
||||
location = QStandardPaths::DownloadLocation;
|
||||
} else if (type.compare("pictures", Qt::CaseInsensitive) == 0) {
|
||||
location = QStandardPaths::PicturesLocation;
|
||||
} else if (type.compare("config", Qt::CaseInsensitive) == 0) {
|
||||
location = QStandardPaths::GenericConfigLocation;
|
||||
}
|
||||
if (context->argumentCount() > 1) {
|
||||
QString loc = QStandardPaths::writableLocation(location);
|
||||
loc.append(QDir::separator());
|
||||
loc.append(context->argument(1).toString());
|
||||
return loc;
|
||||
}
|
||||
const QStringList &locations = QStandardPaths::standardLocations(location);
|
||||
return locations.count() ? locations.first() : QString();
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::knownWallpaperPlugins(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(engine)
|
||||
|
||||
QString formFactor;
|
||||
if (context->argumentCount() > 0) {
|
||||
formFactor = context->argument(0).toString();
|
||||
}
|
||||
|
||||
QString constraint;
|
||||
if (!formFactor.isEmpty()) {
|
||||
constraint.append("[X-Plasma-FormFactors] ~~ '").append(formFactor).append("'");
|
||||
}
|
||||
|
||||
KService::List services = KServiceTypeTrader::self()->query("Plasma/Wallpaper", constraint);
|
||||
QScriptValue rv = engine->newArray(services.size());
|
||||
foreach (const KService::Ptr service, services) {
|
||||
QList<KServiceAction> modeActions = service->actions();
|
||||
QScriptValue modes = engine->newArray(modeActions.size());
|
||||
int i = 0;
|
||||
foreach (const KServiceAction &action, modeActions) {
|
||||
modes.setProperty(i++, action.name());
|
||||
}
|
||||
|
||||
rv.setProperty(service->name(), modes);
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::configFile(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
ConfigGroup *file = 0;
|
||||
|
||||
if (context->argumentCount() > 0) {
|
||||
if (context->argument(0).isString()) {
|
||||
file = new ConfigGroup;
|
||||
file->setFile(context->argument(0).toString());
|
||||
if (context->argumentCount() > 1) {
|
||||
file->setGroup(context->argument(1).toString());
|
||||
}
|
||||
} else if (ConfigGroup *parent= qobject_cast<ConfigGroup *>(context->argument(0).toQObject())) {
|
||||
file = new ConfigGroup(parent);
|
||||
}
|
||||
} else {
|
||||
file = new ConfigGroup;
|
||||
}
|
||||
|
||||
QScriptValue v = engine->newQObject(file,
|
||||
QScriptEngine::ScriptOwnership,
|
||||
QScriptEngine::ExcludeSuperClassProperties |
|
||||
QScriptEngine::ExcludeSuperClassMethods);
|
||||
return v;
|
||||
|
||||
}
|
||||
|
||||
void ScriptEngine::setupEngine()
|
||||
{
|
||||
QScriptValue v = globalObject();
|
||||
QScriptValueIterator it(v);
|
||||
while (it.hasNext()) {
|
||||
it.next();
|
||||
// we provide our own print implementation, but we want the rest
|
||||
if (it.name() != "print") {
|
||||
m_scriptSelf.setProperty(it.name(), it.value());
|
||||
}
|
||||
}
|
||||
|
||||
m_scriptSelf.setProperty("QRectF", constructQRectFClass(this));
|
||||
m_scriptSelf.setProperty("createActivity", newFunction(ScriptEngine::createActivity));
|
||||
m_scriptSelf.setProperty("setCurrentActivity", newFunction(ScriptEngine::setCurrentActivity));
|
||||
m_scriptSelf.setProperty("activities", newFunction(ScriptEngine::activities));
|
||||
m_scriptSelf.setProperty("Panel", newFunction(ScriptEngine::newPanel, newObject()));
|
||||
m_scriptSelf.setProperty("desktopsForActivity", newFunction(ScriptEngine::desktopsForActivity));
|
||||
m_scriptSelf.setProperty("desktops", newFunction(ScriptEngine::desktops));
|
||||
m_scriptSelf.setProperty("desktopById", newFunction(ScriptEngine::desktopById));
|
||||
m_scriptSelf.setProperty("desktopForScreen", newFunction(ScriptEngine::desktopForScreen));
|
||||
m_scriptSelf.setProperty("panelById", newFunction(ScriptEngine::panelById));
|
||||
m_scriptSelf.setProperty("panels", newFunction(ScriptEngine::panels));
|
||||
m_scriptSelf.setProperty("fileExists", newFunction(ScriptEngine::fileExists));
|
||||
m_scriptSelf.setProperty("loadTemplate", newFunction(ScriptEngine::loadTemplate));
|
||||
m_scriptSelf.setProperty("applicationExists", newFunction(ScriptEngine::applicationExists));
|
||||
m_scriptSelf.setProperty("defaultApplication", newFunction(ScriptEngine::defaultApplication));
|
||||
m_scriptSelf.setProperty("userDataPath", newFunction(ScriptEngine::userDataPath));
|
||||
m_scriptSelf.setProperty("applicationPath", newFunction(ScriptEngine::applicationPath));
|
||||
m_scriptSelf.setProperty("knownWallpaperPlugins", newFunction(ScriptEngine::knownWallpaperPlugins));
|
||||
m_scriptSelf.setProperty("ConfigFile", newFunction(ScriptEngine::configFile));
|
||||
|
||||
setGlobalObject(m_scriptSelf);
|
||||
}
|
||||
|
||||
bool ScriptEngine::isPanel(const Plasma::Containment *c)
|
||||
{
|
||||
if (!c) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return c->containmentType() == Plasma::Types::PanelContainment ||
|
||||
c->containmentType() == Plasma::Types::CustomPanelContainment;
|
||||
}
|
||||
|
||||
QScriptValue ScriptEngine::desktops(QScriptContext *context, QScriptEngine *engine)
|
||||
{
|
||||
Q_UNUSED(context)
|
||||
|
||||
QScriptValue containments = engine->newArray();
|
||||
ScriptEngine *env = envFor(engine);
|
||||
int count = 0;
|
||||
|
||||
foreach (Plasma::Containment *c, env->corona()->containments()) {
|
||||
if (!isPanel(c)) {
|
||||
containments.setProperty(count, env->wrap(c));
|
||||
++count;
|
||||
}
|
||||
}
|
||||
|
||||
containments.setProperty("length", count);
|
||||
return containments;
|
||||
}
|
||||
|
||||
ShellCorona *ScriptEngine::corona() const
|
||||
{
|
||||
return m_corona;
|
||||
}
|
||||
|
||||
bool ScriptEngine::evaluateScript(const QString &script, const QString &path)
|
||||
{
|
||||
//qDebug() << "evaluating" << m_editor->toPlainText();
|
||||
evaluate(script, path);
|
||||
if (hasUncaughtException()) {
|
||||
//qDebug() << "catch the exception!";
|
||||
QString error = i18n("Error: %1 at line %2\n\nBacktrace:\n%3",
|
||||
uncaughtException().toString(),
|
||||
QString::number(uncaughtExceptionLineNumber()),
|
||||
uncaughtExceptionBacktrace().join("\n "));
|
||||
emit printError(error);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void ScriptEngine::exception(const QScriptValue &value)
|
||||
{
|
||||
//qDebug() << "exception caught!" << value.toVariant();
|
||||
emit printError(value.toVariant().toString());
|
||||
}
|
||||
|
||||
QStringList ScriptEngine::pendingUpdateScripts(ShellCorona *corona)
|
||||
{
|
||||
if (!corona->package().metadata().isValid()) {
|
||||
qWarning() << "Warning: corona package invalid";
|
||||
return QStringList();
|
||||
}
|
||||
|
||||
const QString appName = corona->package().metadata().pluginName();
|
||||
QStringList scripts;
|
||||
|
||||
const QStringList dirs = QStandardPaths::locateAll(QStandardPaths::GenericDataLocation, appName + QStringLiteral("/kpartplugins"), QStandardPaths::LocateDirectory);
|
||||
Q_FOREACH(const QString& dir, dirs) {
|
||||
QDirIterator it(dir, QStringList() << QStringLiteral("*.js"));
|
||||
while (it.hasNext()) {
|
||||
scripts.append(it.next());
|
||||
}
|
||||
}
|
||||
QStringList scriptPaths;
|
||||
|
||||
if (scripts.isEmpty()) {
|
||||
//qDebug() << "no update scripts";
|
||||
return scriptPaths;
|
||||
}
|
||||
|
||||
KConfigGroup cg(KSharedConfig::openConfig(), "Updates");
|
||||
QStringList performed = cg.readEntry("performed", QStringList());
|
||||
const QString localXdgDir = QStandardPaths::writableLocation(QStandardPaths::GenericDataLocation);
|
||||
|
||||
foreach (const QString &script, scripts) {
|
||||
if (performed.contains(script)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (script.startsWith(localXdgDir)) {
|
||||
// qDebug() << "skipping user local script: " << script;
|
||||
continue;
|
||||
}
|
||||
|
||||
scriptPaths.append(script);
|
||||
performed.append(script);
|
||||
}
|
||||
|
||||
cg.writeEntry("performed", performed);
|
||||
KSharedConfig::openConfig()->sync();
|
||||
return scriptPaths;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#include "scriptengine.moc"
|
||||
|
@ -1,107 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef SCRIPTENGINE
|
||||
#define SCRIPTENGINE
|
||||
|
||||
#include <QScriptEngine>
|
||||
#include <QScriptValue>
|
||||
|
||||
#include <kactivities/controller.h>
|
||||
|
||||
#include "../shellcorona.h"
|
||||
|
||||
namespace Plasma
|
||||
{
|
||||
class Applet;
|
||||
class Containment;
|
||||
} // namespace Plasma
|
||||
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class Containment;
|
||||
|
||||
class ScriptEngine : public QScriptEngine
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
ScriptEngine(ShellCorona *corona, QObject *parent = 0);
|
||||
~ScriptEngine();
|
||||
|
||||
static QStringList pendingUpdateScripts(ShellCorona *corona);
|
||||
|
||||
ShellCorona *corona() const;
|
||||
bool evaluateScript(const QString &script, const QString &path = QString());
|
||||
QScriptValue wrap(Plasma::Applet *w);
|
||||
virtual QScriptValue wrap(Plasma::Containment *c);
|
||||
QScriptValue wrap(Containment *c);
|
||||
virtual int defaultPanelScreen() const;
|
||||
|
||||
static bool isPanel(const Plasma::Containment *c);
|
||||
static ScriptEngine *envFor(QScriptEngine *engine);
|
||||
|
||||
Q_SIGNALS:
|
||||
void print(const QString &string);
|
||||
void printError(const QString &string);
|
||||
|
||||
private:
|
||||
void setupEngine();
|
||||
static QString onlyExec(const QString &commandLine);
|
||||
|
||||
// containment accessors
|
||||
static QStringList availableContainments(const QString &type);
|
||||
static QScriptValue createActivity(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue setCurrentActivity(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue activities(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue newPanel(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue desktopsForActivity(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue desktops(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue desktopById(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue desktopForScreen(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue panelById(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue panels(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue fileExists(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue loadTemplate(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue applicationExists(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue defaultApplication(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue applicationPath(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue userDataPath(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue knownWallpaperPlugins(QScriptContext *context, QScriptEngine *engine);
|
||||
static QScriptValue configFile(QScriptContext *context, QScriptEngine *engine);
|
||||
|
||||
// helpers
|
||||
static QScriptValue createContainment(const QString &type, const QString &defautPlugin,
|
||||
QScriptContext *context, QScriptEngine *engine);
|
||||
|
||||
private Q_SLOTS:
|
||||
void exception(const QScriptValue &value);
|
||||
|
||||
private:
|
||||
ShellCorona *m_corona;
|
||||
QScriptValue m_scriptSelf;
|
||||
};
|
||||
|
||||
static const int PLASMA_DESKTOP_SCRIPTING_VERSION = 20;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -1,180 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "widget.h"
|
||||
|
||||
#include <QAction>
|
||||
|
||||
#include <Plasma/Applet>
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/Corona>
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class Widget::Private
|
||||
{
|
||||
public:
|
||||
Private()
|
||||
{
|
||||
}
|
||||
|
||||
QWeakPointer<Plasma::Applet> applet;
|
||||
};
|
||||
|
||||
Widget::Widget(Plasma::Applet *applet, QObject *parent)
|
||||
: Applet(parent),
|
||||
d(new Widget::Private)
|
||||
{
|
||||
d->applet = applet;
|
||||
setCurrentConfigGroup(QStringList());
|
||||
setCurrentGlobalConfigGroup(QStringList());
|
||||
}
|
||||
|
||||
Widget::~Widget()
|
||||
{
|
||||
reloadConfigIfNeeded();
|
||||
delete d;
|
||||
}
|
||||
|
||||
uint Widget::id() const
|
||||
{
|
||||
if (d->applet) {
|
||||
return d->applet.data()->id();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
QString Widget::type() const
|
||||
{
|
||||
if (d->applet) {
|
||||
return d->applet.data()->pluginInfo().pluginName();
|
||||
}
|
||||
|
||||
return QString();
|
||||
}
|
||||
|
||||
void Widget::remove()
|
||||
{
|
||||
if (d->applet) {
|
||||
d->applet.data()->destroy();
|
||||
d->applet.clear();
|
||||
}
|
||||
}
|
||||
|
||||
void Widget::setGlobalShortcut(const QString &shortcut)
|
||||
{
|
||||
if (d->applet) {
|
||||
d->applet.data()->setGlobalShortcut(QKeySequence(shortcut));
|
||||
}
|
||||
}
|
||||
|
||||
QString Widget::globalShorcut() const
|
||||
{
|
||||
if (d->applet) {
|
||||
return d->applet.data()->globalShortcut().toString();
|
||||
}
|
||||
|
||||
return QString();
|
||||
}
|
||||
|
||||
Plasma::Applet *Widget::applet() const
|
||||
{
|
||||
return d->applet.data();
|
||||
}
|
||||
|
||||
int Widget::index() const
|
||||
{
|
||||
if (!d->applet) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
Plasma::Applet *applet = d->applet.data();
|
||||
Plasma::Containment *c = applet->containment();
|
||||
if (!c) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
/*QGraphicsLayout *layout = c->layout();
|
||||
if (!layout) {
|
||||
return - 1;
|
||||
}
|
||||
|
||||
for (int i = 0; i < layout->count(); ++i) {
|
||||
if (layout->itemAt(i) == applet) {
|
||||
return i;
|
||||
}
|
||||
}*/
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
void Widget::setIndex(int index)
|
||||
{
|
||||
if (!d->applet) {
|
||||
return;
|
||||
}
|
||||
|
||||
Plasma::Applet *applet = d->applet.data();
|
||||
Plasma::Containment *c = applet->containment();
|
||||
if (!c) {
|
||||
return;
|
||||
}
|
||||
/*
|
||||
//FIXME: this is hackish. would be nice to define this for gridlayouts too
|
||||
QGraphicsLinearLayout *layout = dynamic_cast<QGraphicsLinearLayout *>(c->layout());
|
||||
if (!layout) {
|
||||
return;
|
||||
}
|
||||
|
||||
layout->insertItem(index, applet);*/
|
||||
}
|
||||
|
||||
QRectF Widget::geometry() const
|
||||
{
|
||||
/*if (d->applet) {
|
||||
return d->applet.data()->geometry();
|
||||
}
|
||||
*/
|
||||
return QRectF();
|
||||
}
|
||||
|
||||
void Widget::setGeometry(const QRectF &geometry)
|
||||
{
|
||||
/*if (d->applet) {
|
||||
d->applet.data()->setGeometry(geometry);
|
||||
KConfigGroup cg = d->applet.data()->config().parent();
|
||||
if (cg.isValid()) {
|
||||
cg.writeEntry("geometry", geometry);
|
||||
}
|
||||
}*/
|
||||
}
|
||||
|
||||
void Widget::showConfigurationInterface()
|
||||
{
|
||||
/* if (d->applet) {
|
||||
d->applet.data()->showConfigurationInterface();
|
||||
}*/
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#include "widget.moc"
|
||||
|
@ -1,90 +0,0 @@
|
||||
/*
|
||||
* Copyright 2009 Aaron Seigo <aseigo@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef WIDGET
|
||||
#define WIDGET
|
||||
|
||||
#include <QWeakPointer>
|
||||
|
||||
#include "applet.h"
|
||||
|
||||
namespace Plasma
|
||||
{
|
||||
class Applet;
|
||||
} // namespace Plasma
|
||||
|
||||
namespace WorkspaceScripting
|
||||
{
|
||||
|
||||
class Widget : public Applet
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(QString type READ type)
|
||||
Q_PROPERTY(QString version READ version)
|
||||
Q_PROPERTY(int id READ id)
|
||||
Q_PROPERTY(QStringList configKeys READ configKeys)
|
||||
Q_PROPERTY(QStringList configGroups READ configGroups)
|
||||
Q_PROPERTY(QStringList globalConfigKeys READ globalConfigKeys)
|
||||
Q_PROPERTY(QStringList globalConfigGroups READ globalConfigGroups)
|
||||
Q_PROPERTY(int index WRITE setIndex READ index)
|
||||
Q_PROPERTY(QRectF geometry WRITE setGeometry READ geometry)
|
||||
Q_PROPERTY(QStringList currentConfigGroup WRITE setCurrentConfigGroup READ currentConfigGroup)
|
||||
Q_PROPERTY(QString globalShortcut WRITE setGlobalShortcut READ globalShorcut)
|
||||
Q_PROPERTY(bool locked READ locked WRITE setLocked)
|
||||
|
||||
public:
|
||||
Widget(Plasma::Applet *applet, QObject *parent = 0);
|
||||
~Widget();
|
||||
|
||||
uint id() const;
|
||||
QString type() const;
|
||||
|
||||
int index() const;
|
||||
void setIndex(int index);
|
||||
|
||||
QRectF geometry() const;
|
||||
void setGeometry(const QRectF &geometry);
|
||||
|
||||
void setGlobalShortcut(const QString &shortcut);
|
||||
QString globalShorcut() const;
|
||||
|
||||
Plasma::Applet *applet() const;
|
||||
|
||||
public Q_SLOTS:
|
||||
void remove();
|
||||
void showConfigurationInterface();
|
||||
|
||||
// from the applet interface
|
||||
QVariant readConfig(const QString &key, const QVariant &def = QString()) const { return Applet::readConfig(key, def); }
|
||||
void writeConfig(const QString &key, const QVariant &value) { Applet::writeConfig(key, value); }
|
||||
|
||||
QVariant readGlobalConfig(const QString &key, const QVariant &def = QString()) const { return Applet::readGlobalConfig(key, def); }
|
||||
void writeGlobalConfig(const QString &key, const QVariant &value) { Applet::writeGlobalConfig(key, value); }
|
||||
|
||||
void reloadConfig() { Applet::reloadConfig(); }
|
||||
|
||||
private:
|
||||
class Private;
|
||||
Private * const d;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -1,874 +0,0 @@
|
||||
/*
|
||||
* Copyright 2008 Aaron Seigo <aseigo@kde.org>
|
||||
* Copyright 2013 Sebastian Kügler <sebas@kde.org>
|
||||
* Copyright 2013 Ivan Cukic <ivan.cukic@kde.org>
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "shellcorona.h"
|
||||
|
||||
#include <QApplication>
|
||||
#include <QDebug>
|
||||
#include <QMenu>
|
||||
#include <QDesktopWidget>
|
||||
#include <QQmlContext>
|
||||
#include <QTimer>
|
||||
#include <QDBusConnection>
|
||||
|
||||
#include <kactioncollection.h>
|
||||
#include <klocalizedstring.h>
|
||||
#include <Plasma/Package>
|
||||
#include <Plasma/PluginLoader>
|
||||
#include <kactivities/controller.h>
|
||||
#include <kactivities/consumer.h>
|
||||
#include <ksycoca.h>
|
||||
#include <kservicetypetrader.h>
|
||||
#include <KGlobalAccel>
|
||||
#include <KAuthorized>
|
||||
#include <KWindowSystem>
|
||||
|
||||
#include "config-ktexteditor.h" // HAVE_KTEXTEDITOR
|
||||
|
||||
|
||||
#include "activity.h"
|
||||
#include "desktopview.h"
|
||||
#include "panelview.h"
|
||||
#include "scripting/desktopscriptengine.h"
|
||||
#include "widgetexplorer/widgetexplorer.h"
|
||||
#include "configview.h"
|
||||
#include "shellpluginloader.h"
|
||||
#include "osd.h"
|
||||
#if HAVE_KTEXTEDITOR
|
||||
#include "interactiveconsole.h"
|
||||
#endif
|
||||
|
||||
#include "plasmashelladaptor.h"
|
||||
|
||||
|
||||
|
||||
static const int s_configSyncDelay = 10000; // 10 seconds
|
||||
|
||||
class ShellCorona::Private {
|
||||
public:
|
||||
Private(ShellCorona *corona)
|
||||
: q(corona),
|
||||
activityController(new KActivities::Controller(q)),
|
||||
activityConsumer(new KActivities::Consumer(q)),
|
||||
addPanelAction(nullptr),
|
||||
addPanelsMenu(nullptr)
|
||||
{
|
||||
appConfigSyncTimer.setSingleShot(true);
|
||||
appConfigSyncTimer.setInterval(s_configSyncDelay);
|
||||
connect(&appConfigSyncTimer, &QTimer::timeout, q, &ShellCorona::syncAppConfig);
|
||||
|
||||
waitingPanelsTimer.setSingleShot(true);
|
||||
waitingPanelsTimer.setInterval(250);
|
||||
connect(&waitingPanelsTimer, &QTimer::timeout, q, &ShellCorona::createWaitingPanels);
|
||||
}
|
||||
|
||||
ShellCorona *q;
|
||||
QString shell;
|
||||
QList<DesktopView *> views;
|
||||
KActivities::Controller *activityController;
|
||||
KActivities::Consumer *activityConsumer;
|
||||
QHash<const Plasma::Containment *, PanelView *> panelViews;
|
||||
KConfigGroup desktopDefaultsConfig;
|
||||
WorkspaceScripting::DesktopScriptEngine *scriptEngine;
|
||||
QList<Plasma::Containment *> waitingPanels;
|
||||
QHash<QString, Activity *> activities;
|
||||
QHash<QString, QHash<int, Plasma::Containment *> > desktopContainments;
|
||||
QAction *addPanelAction;
|
||||
QMenu *addPanelsMenu;
|
||||
Plasma::Package lookNFeelPackage;
|
||||
#if HAVE_KTEXTEDITOR
|
||||
QWeakPointer<InteractiveConsole> console;
|
||||
#endif
|
||||
|
||||
QTimer waitingPanelsTimer;
|
||||
QTimer appConfigSyncTimer;
|
||||
};
|
||||
|
||||
|
||||
WorkspaceScripting::DesktopScriptEngine * ShellCorona::scriptEngine() const
|
||||
{
|
||||
return d->scriptEngine;
|
||||
}
|
||||
|
||||
|
||||
ShellCorona::ShellCorona(QObject *parent)
|
||||
: Plasma::Corona(parent),
|
||||
d(new Private(this))
|
||||
{
|
||||
d->desktopDefaultsConfig = KConfigGroup(KSharedConfig::openConfig(package().filePath("defaults")), "Desktop");
|
||||
|
||||
new PlasmaShellAdaptor(this);
|
||||
|
||||
QDBusConnection dbus = QDBusConnection::sessionBus();
|
||||
dbus.registerObject(QStringLiteral("/PlasmaShell"), this);
|
||||
|
||||
|
||||
// Look for theme config in plasmarc, if it isn't configured, take the theme from the
|
||||
// LookAndFeel package, if either is set, change the default theme
|
||||
|
||||
const QString themeGroupKey = QStringLiteral("Theme");
|
||||
const QString themeNameKey = QStringLiteral("name");
|
||||
|
||||
QString themeName;
|
||||
|
||||
KConfigGroup plasmarc(KSharedConfig::openConfig("plasmarc"), themeGroupKey);
|
||||
themeName = plasmarc.readEntry(themeNameKey, themeName);
|
||||
|
||||
if (themeName.isEmpty()) {
|
||||
const KConfigGroup lnfCfg = KConfigGroup(KSharedConfig::openConfig(
|
||||
lookAndFeelPackage().filePath("defaults")),
|
||||
themeGroupKey
|
||||
);
|
||||
themeName = lnfCfg.readEntry(themeNameKey, themeName);
|
||||
}
|
||||
|
||||
if (!themeName.isEmpty()) {
|
||||
Plasma::Theme *t = new Plasma::Theme(this);
|
||||
t->setThemeName(themeName);
|
||||
}
|
||||
|
||||
connect(this, &ShellCorona::containmentAdded,
|
||||
this, &ShellCorona::handleContainmentAdded);
|
||||
|
||||
d->scriptEngine = new WorkspaceScripting::DesktopScriptEngine(this, true);
|
||||
|
||||
connect(d->scriptEngine, &WorkspaceScripting::ScriptEngine::printError,
|
||||
[=](const QString &msg) {
|
||||
qWarning() << msg;
|
||||
});
|
||||
connect(d->scriptEngine, &WorkspaceScripting::ScriptEngine::print,
|
||||
[=](const QString &msg) {
|
||||
qDebug() << msg;
|
||||
});
|
||||
|
||||
QAction *dashboardAction = actions()->add<QAction>("show dashboard");
|
||||
QObject::connect(dashboardAction, &QAction::triggered,
|
||||
this, &ShellCorona::setDashboardShown);
|
||||
dashboardAction->setText(i18n("Show Dashboard"));
|
||||
|
||||
dashboardAction->setAutoRepeat(true);
|
||||
dashboardAction->setCheckable(true);
|
||||
dashboardAction->setIcon(QIcon::fromTheme("dashboard-show"));
|
||||
dashboardAction->setData(Plasma::Types::ControlAction);
|
||||
KGlobalAccel::self()->setDefaultShortcut(dashboardAction, QList<QKeySequence>() << QKeySequence(Qt::CTRL + Qt::Key_F12));
|
||||
KGlobalAccel::self()->setShortcut(dashboardAction, QList<QKeySequence>() << QKeySequence(Qt::CTRL + Qt::Key_F12));
|
||||
|
||||
|
||||
checkAddPanelAction();
|
||||
connect(KSycoca::self(), SIGNAL(databaseChanged(QStringList)), this, SLOT(checkAddPanelAction(QStringList)));
|
||||
|
||||
|
||||
//Activity stuff
|
||||
QAction *activityAction = actions()->addAction("manage activities");
|
||||
connect(activityAction, &QAction::triggered,
|
||||
this, &ShellCorona::toggleActivityManager);
|
||||
activityAction->setText(i18n("Activities..."));
|
||||
activityAction->setIcon(QIcon::fromTheme("preferences-activities"));
|
||||
activityAction->setData(Plasma::Types::ConfigureAction);
|
||||
activityAction->setShortcut(QKeySequence("alt+d, alt+a"));
|
||||
activityAction->setShortcutContext(Qt::ApplicationShortcut);
|
||||
|
||||
connect(d->activityConsumer, SIGNAL(currentActivityChanged(QString)), this, SLOT(currentActivityChanged(QString)));
|
||||
connect(d->activityConsumer, SIGNAL(activityAdded(QString)), this, SLOT(activityAdded(QString)));
|
||||
connect(d->activityConsumer, SIGNAL(activityRemoved(QString)), this, SLOT(activityRemoved(QString)));
|
||||
|
||||
new Osd(this);
|
||||
}
|
||||
|
||||
ShellCorona::~ShellCorona()
|
||||
{
|
||||
qDeleteAll(d->views);
|
||||
}
|
||||
|
||||
void ShellCorona::setShell(const QString &shell)
|
||||
{
|
||||
if (d->shell == shell) {
|
||||
return;
|
||||
}
|
||||
|
||||
unload();
|
||||
|
||||
d->shell = shell;
|
||||
Plasma::Package package = Plasma::PluginLoader::self()->loadPackage("Plasma/Shell");
|
||||
package.setPath(shell);
|
||||
setPackage(package);
|
||||
|
||||
if (d->activityConsumer->serviceStatus() == KActivities::Consumer::Unknown) {
|
||||
connect(d->activityConsumer, SIGNAL(serviceStatusChanged(Consumer::ServiceStatus)), SLOT(load()), Qt::UniqueConnection);
|
||||
} else {
|
||||
load();
|
||||
}
|
||||
}
|
||||
|
||||
QString ShellCorona::shell() const
|
||||
{
|
||||
return d->shell;
|
||||
}
|
||||
|
||||
void ShellCorona::load()
|
||||
{
|
||||
if (d->shell.isEmpty() ||
|
||||
d->activityConsumer->serviceStatus() == KActivities::Consumer::Unknown) {
|
||||
return;
|
||||
}
|
||||
|
||||
disconnect(d->activityConsumer, SIGNAL(serviceStatusChanged(Consumer::ServiceStatus)), this, SLOT(load()));
|
||||
|
||||
loadLayout("plasma-" + d->shell + "-appletsrc");
|
||||
|
||||
checkActivities();
|
||||
if (containments().isEmpty()) {
|
||||
loadDefaultLayout();
|
||||
foreach(Plasma::Containment* containment, containments()) {
|
||||
containment->setActivity(d->activityConsumer->currentActivity());
|
||||
}
|
||||
}
|
||||
|
||||
processUpdateScripts();
|
||||
foreach(Plasma::Containment* containment, containments()) {
|
||||
if (containment->formFactor() == Plasma::Types::Horizontal ||
|
||||
containment->formFactor() == Plasma::Types::Vertical) {
|
||||
if (!d->waitingPanels.contains(containment)) {
|
||||
d->waitingPanels << containment;
|
||||
}
|
||||
} else {
|
||||
//FIXME ideally fix this, or at least document the crap out of it
|
||||
int screen = containment->lastScreen();
|
||||
if (screen < 0) {
|
||||
screen = d->desktopContainments[containment->activity()].count();
|
||||
}
|
||||
insertContainment(containment->activity(), screen, containment);
|
||||
}
|
||||
}
|
||||
|
||||
for (QScreen *screen : QGuiApplication::screens()) {
|
||||
screenAdded(screen);
|
||||
}
|
||||
connect(qApp, &QGuiApplication::screenAdded,
|
||||
this, &ShellCorona::screenAdded);
|
||||
|
||||
if (!d->waitingPanels.isEmpty()) {
|
||||
d->waitingPanelsTimer.start();
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::unload()
|
||||
{
|
||||
if (d->shell.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
qDeleteAll(containments());
|
||||
}
|
||||
|
||||
KSharedConfig::Ptr ShellCorona::applicationConfig()
|
||||
{
|
||||
return KSharedConfig::openConfig();
|
||||
}
|
||||
|
||||
void ShellCorona::requestApplicationConfigSync()
|
||||
{
|
||||
d->appConfigSyncTimer.start();
|
||||
}
|
||||
|
||||
void ShellCorona::loadDefaultLayout()
|
||||
{
|
||||
const QString script = package().filePath("defaultlayout");
|
||||
QFile file(script);
|
||||
if (file.open(QIODevice::ReadOnly | QIODevice::Text) ) {
|
||||
QString code = file.readAll();
|
||||
qDebug() << "evaluating startup script:" << script;
|
||||
d->scriptEngine->evaluateScript(code);
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::processUpdateScripts()
|
||||
{
|
||||
foreach (const QString &script, WorkspaceScripting::ScriptEngine::pendingUpdateScripts(this)) {
|
||||
d->scriptEngine->evaluateScript(script);
|
||||
}
|
||||
}
|
||||
|
||||
KActivities::Controller *ShellCorona::activityController()
|
||||
{
|
||||
return d->activityController;
|
||||
}
|
||||
|
||||
int ShellCorona::numScreens() const
|
||||
{
|
||||
return QApplication::desktop()->screenCount();
|
||||
}
|
||||
|
||||
QRect ShellCorona::screenGeometry(int id) const
|
||||
{
|
||||
DesktopView *view = 0;
|
||||
foreach (DesktopView *v, d->views) {
|
||||
if (v->containment() && v->containment()->screen() == id) {
|
||||
view = v;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (view) {
|
||||
return view->geometry();
|
||||
} else {
|
||||
return QApplication::desktop()->screenGeometry(id);
|
||||
}
|
||||
}
|
||||
|
||||
QRegion ShellCorona::availableScreenRegion(int id) const
|
||||
{
|
||||
DesktopView *view = 0;
|
||||
foreach (DesktopView *v, d->views) {
|
||||
if (v->containment() && v->containment()->screen() == id) {
|
||||
view = v;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (view) {
|
||||
QRegion r = view->geometry();
|
||||
foreach (PanelView *v, d->panelViews.values()) {
|
||||
if (v->containment()->screen() == id && v->visibilityMode() != PanelView::AutoHide) {
|
||||
r -= v->geometry();
|
||||
}
|
||||
}
|
||||
return r;
|
||||
} else {
|
||||
return QApplication::desktop()->availableGeometry(id);
|
||||
}
|
||||
}
|
||||
|
||||
QRect ShellCorona::availableScreenRect(int id) const
|
||||
{
|
||||
if (id < 0) {
|
||||
id = 0;
|
||||
}
|
||||
|
||||
QRect r(screenGeometry(id));
|
||||
|
||||
foreach (PanelView *view, d->panelViews.values()) {
|
||||
if (view->containment()->screen() == id && view->visibilityMode() != PanelView::AutoHide) {
|
||||
QRect v = view->geometry();
|
||||
switch (view->location()) {
|
||||
case Plasma::Types::TopEdge:
|
||||
if (v.bottom() > r.top()) {
|
||||
r.setTop(v.bottom());
|
||||
}
|
||||
break;
|
||||
|
||||
case Plasma::Types::BottomEdge:
|
||||
if (v.top() < r.bottom()) {
|
||||
r.setBottom(v.top());
|
||||
}
|
||||
break;
|
||||
|
||||
case Plasma::Types::LeftEdge:
|
||||
if (v.right() > r.left()) {
|
||||
r.setLeft(v.right());
|
||||
}
|
||||
break;
|
||||
|
||||
case Plasma::Types::RightEdge:
|
||||
if (v.left() < r.right()) {
|
||||
r.setRight(v.left());
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
PanelView *ShellCorona::panelView(Plasma::Containment *containment) const
|
||||
{
|
||||
return d->panelViews.value(containment);
|
||||
}
|
||||
|
||||
|
||||
///// SLOTS
|
||||
|
||||
void ShellCorona::screenAdded(QScreen *screen)
|
||||
{
|
||||
DesktopView *view = new DesktopView(this, screen);
|
||||
const QString currentActivity = d->activityController->currentActivity();
|
||||
|
||||
if (!d->views.isEmpty() && screen == QGuiApplication::primaryScreen()) {
|
||||
DesktopView* oldPrimaryView = d->views.first();
|
||||
QScreen* oldPrimaryScreen = oldPrimaryView->screen();
|
||||
|
||||
//move any panels that were preivously on the old primary screen to the new primary screen
|
||||
foreach (PanelView *panelView, d->panelViews) {
|
||||
if (oldPrimaryScreen==panelView->screen())
|
||||
panelView->setScreen(screen);
|
||||
}
|
||||
|
||||
Plasma::Containment* primaryContainment = oldPrimaryView->containment();
|
||||
oldPrimaryView->setContainment(0);
|
||||
view->setContainment(primaryContainment);
|
||||
|
||||
d->views.prepend(view);
|
||||
view = oldPrimaryView;
|
||||
} else {
|
||||
d->views.append(view);
|
||||
}
|
||||
|
||||
int screenNum = d->views.count()-1;
|
||||
Plasma::Containment *containment = d->desktopContainments[currentActivity][screenNum];
|
||||
if (!containment) {
|
||||
containment = createContainmentForActivity(currentActivity, screenNum);
|
||||
}
|
||||
|
||||
QAction *removeAction = containment->actions()->action("remove");
|
||||
if (removeAction) {
|
||||
removeAction->deleteLater();
|
||||
}
|
||||
|
||||
view->setContainment(containment);
|
||||
|
||||
connect(screen, SIGNAL(destroyed(QObject*)), SLOT(screenRemoved(QObject*)));
|
||||
view->show();
|
||||
|
||||
emit availableScreenRectChanged();
|
||||
emit availableScreenRegionChanged();
|
||||
}
|
||||
|
||||
|
||||
Plasma::Containment* ShellCorona::createContainmentForActivity(const QString& activity, int screenNum)
|
||||
{
|
||||
if (d->desktopContainments.contains(activity) &&
|
||||
d->desktopContainments[activity].contains(screenNum) &&
|
||||
d->desktopContainments.value(activity).value(screenNum)) {
|
||||
return d->desktopContainments[activity][screenNum];
|
||||
}
|
||||
|
||||
QString plugin = "org.kde.desktopcontainment";
|
||||
if (d->activities.contains(activity)) {
|
||||
// plugin = d->activities.value(activity)->defaultPlugin();
|
||||
}
|
||||
|
||||
Plasma::Containment* containment = createContainment(d->desktopDefaultsConfig.readEntry("Containment", plugin));
|
||||
containment->setActivity(activity);
|
||||
insertContainment(activity, screenNum, containment);
|
||||
|
||||
return containment;
|
||||
}
|
||||
|
||||
void ShellCorona::screenRemoved(QObject *screen)
|
||||
{
|
||||
//desktop containments
|
||||
for (auto i = d->views.begin(); i != d->views.end(); i++) {
|
||||
if ((*i)->screen() == screen) {
|
||||
d->views.erase(i);
|
||||
(*i)->containment()->reactToScreenChange();
|
||||
(*i)->deleteLater();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
//move all panels on a deleted screen to the primary screen
|
||||
//FIXME: this will break when a second screen is added again
|
||||
//as in plasma1, panel should be hidden, panelView deleted.
|
||||
//possibly similar to exportLayout/importLayout of Activities
|
||||
foreach (PanelView *view, d->panelViews) {
|
||||
view->setScreen(QGuiApplication::primaryScreen());
|
||||
}
|
||||
|
||||
emit availableScreenRectChanged();
|
||||
emit availableScreenRegionChanged();
|
||||
|
||||
}
|
||||
|
||||
void ShellCorona::createWaitingPanels()
|
||||
{
|
||||
foreach (Plasma::Containment *cont, d->waitingPanels) {
|
||||
d->panelViews[cont] = new PanelView(this);
|
||||
|
||||
//keep screen suggestions within bounds of screens we actually have
|
||||
int screen = qBound(0, cont->lastScreen(), QGuiApplication::screens().size() -1);
|
||||
|
||||
d->panelViews[cont]->setScreen(QGuiApplication::screens()[screen]);
|
||||
d->panelViews[cont]->setContainment(cont);
|
||||
connect(cont, &PanelView::destroyed,
|
||||
[=](QObject *obj) {
|
||||
d->panelViews.remove(cont);
|
||||
emit availableScreenRectChanged();
|
||||
emit availableScreenRegionChanged();
|
||||
});
|
||||
}
|
||||
d->waitingPanels.clear();
|
||||
emit availableScreenRectChanged();
|
||||
emit availableScreenRegionChanged();
|
||||
}
|
||||
|
||||
void ShellCorona::handleContainmentAdded(Plasma::Containment* c)
|
||||
{
|
||||
connect(c, &Plasma::Containment::showAddWidgetsInterface,
|
||||
this, &ShellCorona::toggleWidgetExplorer);
|
||||
}
|
||||
|
||||
void ShellCorona::toggleWidgetExplorer()
|
||||
{
|
||||
const QPoint cursorPos = QCursor::pos();
|
||||
foreach (DesktopView *view, d->views) {
|
||||
if (view->screen()->geometry().contains(cursorPos)) {
|
||||
//The view QML has to provide something to display the activity explorer
|
||||
view->rootObject()->metaObject()->invokeMethod(view->rootObject(), "toggleWidgetExplorer", Q_ARG(QVariant, QVariant::fromValue(sender())));
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::toggleActivityManager()
|
||||
{
|
||||
const QPoint cursorPos = QCursor::pos();
|
||||
foreach (DesktopView *view, d->views) {
|
||||
if (view->screen()->geometry().contains(cursorPos)) {
|
||||
//The view QML has to provide something to display the activity explorer
|
||||
view->rootObject()->metaObject()->invokeMethod(view->rootObject(), "toggleActivityManager");
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::syncAppConfig()
|
||||
{
|
||||
qDebug() << "Syncing plasma-shellrc config";
|
||||
applicationConfig()->sync();
|
||||
}
|
||||
|
||||
void ShellCorona::setDashboardShown(bool show)
|
||||
{
|
||||
qDebug() << "TODO: Toggling dashboard view";
|
||||
|
||||
QAction *dashboardAction = actions()->action("show dashboard");
|
||||
|
||||
if (dashboardAction) {
|
||||
dashboardAction->setText(show ? i18n("Hide Dashboard") : i18n("Show Dashboard"));
|
||||
}
|
||||
|
||||
foreach (DesktopView *view, d->views) {
|
||||
view->setDashboardShown(show);
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::toggleDashboard()
|
||||
{
|
||||
foreach (DesktopView *view, d->views) {
|
||||
view->setDashboardShown(!view->isDashboardShown());
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::showInteractiveConsole()
|
||||
{
|
||||
if (KSharedConfig::openConfig()->isImmutable() || !KAuthorized::authorize("plasma-desktop/scripting_console")) {
|
||||
return;
|
||||
}
|
||||
|
||||
#if HAVE_KTEXTEDITOR
|
||||
InteractiveConsole *console = d->console.data();
|
||||
if (!console) {
|
||||
d->console = console = new InteractiveConsole(this);
|
||||
}
|
||||
d->console.data()->setMode(InteractiveConsole::PlasmaConsole);
|
||||
|
||||
KWindowSystem::setOnDesktop(console->winId(), KWindowSystem::currentDesktop());
|
||||
console->show();
|
||||
console->raise();
|
||||
KWindowSystem::forceActiveWindow(console->winId());
|
||||
#endif
|
||||
}
|
||||
|
||||
void ShellCorona::loadScriptInInteractiveConsole(const QString &script)
|
||||
{
|
||||
#if HAVE_KTEXTEDITOR
|
||||
showInteractiveConsole();
|
||||
if (d->console) {
|
||||
d->console.data()->loadScript(script);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void ShellCorona::checkActivities()
|
||||
{
|
||||
KActivities::Consumer::ServiceStatus status = d->activityController->serviceStatus();
|
||||
//qDebug() << "$%$%$#%$%$%Status:" << status;
|
||||
if (status != KActivities::Consumer::Running) {
|
||||
//panic and give up - better than causing a mess
|
||||
qDebug() << "ShellCorona::checkActivities is called whilst activity daemon is still connecting";
|
||||
return;
|
||||
}
|
||||
|
||||
QStringList existingActivities = d->activityConsumer->activities();
|
||||
foreach (const QString &id, existingActivities) {
|
||||
activityAdded(id);
|
||||
}
|
||||
|
||||
// Checking whether the result we got is valid. Just in case.
|
||||
Q_ASSERT_X(!existingActivities.isEmpty(), "isEmpty", "There are no activities, and the service is running");
|
||||
Q_ASSERT_X(existingActivities[0] != QStringLiteral("00000000-0000-0000-0000-000000000000"),
|
||||
"null uuid", "There is a nulluuid activity present");
|
||||
|
||||
// Killing the unassigned containments
|
||||
foreach (Plasma::Containment * cont, containments()) {
|
||||
if ((cont->containmentType() == Plasma::Types::DesktopContainment ||
|
||||
cont->containmentType() == Plasma::Types::CustomContainment) &&
|
||||
!existingActivities.contains(cont->activity())) {
|
||||
cont->destroy();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::currentActivityChanged(const QString &newActivity)
|
||||
{
|
||||
qDebug() << "Activity changed:" << newActivity;
|
||||
|
||||
for (int i = 0; i < d->views.count(); ++i) {
|
||||
Plasma::Containment* c = d->desktopContainments[newActivity][i];
|
||||
if (!c) {
|
||||
c = createContainmentForActivity(newActivity, i);
|
||||
}
|
||||
QAction *removeAction = c->actions()->action("remove");
|
||||
if (removeAction) {
|
||||
removeAction->deleteLater();
|
||||
}
|
||||
d->views[i]->setContainment(c);
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::activityAdded(const QString &id)
|
||||
{
|
||||
//TODO more sanity checks
|
||||
if (d->activities.contains(id)) {
|
||||
qDebug() << "you're late." << id;
|
||||
return;
|
||||
}
|
||||
|
||||
Activity *a = new Activity(id, this);
|
||||
d->activities.insert(id, a);
|
||||
}
|
||||
|
||||
void ShellCorona::activityRemoved(const QString &id)
|
||||
{
|
||||
Activity *a = d->activities.take(id);
|
||||
a->deleteLater();
|
||||
}
|
||||
|
||||
Activity *ShellCorona::activity(const QString &id)
|
||||
{
|
||||
return d->activities.value(id);
|
||||
}
|
||||
|
||||
void ShellCorona::insertActivity(const QString &id, Activity *activity)
|
||||
{
|
||||
d->activities.insert(id, activity);
|
||||
Plasma::Containment *c = createContainmentForActivity(id, -1);
|
||||
c->config().writeEntry("lastScreen", 0);
|
||||
}
|
||||
|
||||
void ShellCorona::checkAddPanelAction(const QStringList &sycocaChanges)
|
||||
{
|
||||
if (!sycocaChanges.isEmpty() && !sycocaChanges.contains("services")) {
|
||||
return;
|
||||
}
|
||||
|
||||
delete d->addPanelAction;
|
||||
d->addPanelAction = 0;
|
||||
|
||||
delete d->addPanelsMenu;
|
||||
d->addPanelsMenu = 0;
|
||||
|
||||
KPluginInfo::List panelContainmentPlugins = Plasma::PluginLoader::listContainmentsOfType("Panel");
|
||||
const QString constraint = QString("[X-Plasma-Shell] == '%1' and 'panel' ~in [X-Plasma-ContainmentCategories]")
|
||||
.arg(qApp->applicationName());
|
||||
KService::List templates = KServiceTypeTrader::self()->query("Plasma/LayoutTemplate", constraint);
|
||||
|
||||
if (panelContainmentPlugins.count() + templates.count() == 1) {
|
||||
d->addPanelAction = new QAction(i18n("Add Panel"), this);
|
||||
d->addPanelAction->setData(Plasma::Types::AddAction);
|
||||
connect(d->addPanelAction, SIGNAL(triggered(bool)), this, SLOT(addPanel()));
|
||||
} else if (!panelContainmentPlugins.isEmpty()) {
|
||||
d->addPanelsMenu = new QMenu;
|
||||
d->addPanelAction = d->addPanelsMenu->menuAction();
|
||||
d->addPanelAction->setText(i18n("Add Panel"));
|
||||
d->addPanelAction->setData(Plasma::Types::AddAction);
|
||||
qDebug() << "populateAddPanelsMenu" << panelContainmentPlugins.count();
|
||||
connect(d->addPanelsMenu, SIGNAL(aboutToShow()), this, SLOT(populateAddPanelsMenu()));
|
||||
connect(d->addPanelsMenu, SIGNAL(triggered(QAction*)), this, SLOT(addPanel(QAction*)));
|
||||
}
|
||||
|
||||
if (d->addPanelAction) {
|
||||
d->addPanelAction->setIcon(QIcon::fromTheme("list-add"));
|
||||
actions()->addAction("add panel", d->addPanelAction);
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::addPanel()
|
||||
{
|
||||
KPluginInfo::List panelPlugins = Plasma::PluginLoader::listContainmentsOfType("Panel");
|
||||
|
||||
if (!panelPlugins.isEmpty()) {
|
||||
addPanel(panelPlugins.first().pluginName());
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::addPanel(QAction *action)
|
||||
{
|
||||
const QString plugin = action->data().toString();
|
||||
if (plugin.startsWith("plasma-desktop-template:")) {
|
||||
d->scriptEngine->evaluateScript(plugin.right(plugin.length() - qstrlen("plasma-desktop-template:")));
|
||||
} else if (!plugin.isEmpty()) {
|
||||
addPanel(plugin);
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::addPanel(const QString &plugin)
|
||||
{
|
||||
Plasma::Containment *panel = createContainment(plugin);
|
||||
if (!panel) {
|
||||
return;
|
||||
}
|
||||
|
||||
QList<Plasma::Types::Location> availableLocations;
|
||||
availableLocations << Plasma::Types::LeftEdge << Plasma::Types::TopEdge << Plasma::Types::RightEdge << Plasma::Types::BottomEdge;
|
||||
|
||||
foreach (const Plasma::Containment *cont, d->panelViews.keys()) {
|
||||
availableLocations.removeAll(cont->location());
|
||||
}
|
||||
|
||||
Plasma::Types::Location loc;
|
||||
if (availableLocations.isEmpty()) {
|
||||
loc = Plasma::Types::TopEdge;
|
||||
} else {
|
||||
loc = availableLocations.first();
|
||||
}
|
||||
|
||||
panel->setLocation(loc);
|
||||
switch (loc) {
|
||||
case Plasma::Types::LeftEdge:
|
||||
case Plasma::Types::RightEdge:
|
||||
panel->setFormFactor(Plasma::Types::Vertical);
|
||||
break;
|
||||
default:
|
||||
panel->setFormFactor(Plasma::Types::Horizontal);
|
||||
break;
|
||||
}
|
||||
|
||||
d->waitingPanels << panel;
|
||||
d->waitingPanelsTimer.start();
|
||||
}
|
||||
|
||||
int ShellCorona::screenForContainment(const Plasma::Containment *containment) const
|
||||
{
|
||||
QScreen *screen = nullptr;
|
||||
for (int i = 0; i < d->views.size(); i++) {
|
||||
if (d->views[i]->containment() == containment) {
|
||||
screen = d->views[i]->screen();
|
||||
}
|
||||
}
|
||||
|
||||
if (!screen) {
|
||||
PanelView *view = d->panelViews[containment];
|
||||
if (view) {
|
||||
screen = view->screen();
|
||||
}
|
||||
}
|
||||
|
||||
return screen ? qApp->screens().indexOf(screen) : -1;
|
||||
}
|
||||
|
||||
void ShellCorona::activityOpened()
|
||||
{
|
||||
Activity *activity = qobject_cast<Activity *>(sender());
|
||||
if (activity) {
|
||||
QList<Plasma::Containment*> cs = importLayout(activity->config());
|
||||
for (Plasma::Containment *containment : cs) {
|
||||
insertContainment(activity->name(), containment->lastScreen(), containment);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::activityClosed()
|
||||
{
|
||||
Activity *activity = qobject_cast<Activity *>(sender());
|
||||
if (activity) {
|
||||
KConfigGroup cg = activity->config();
|
||||
exportLayout(cg, d->desktopContainments.value(activity->name()).values());
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::activityRemoved()
|
||||
{
|
||||
//when an activity is removed delete all associated desktop containments
|
||||
Activity *activity = qobject_cast<Activity *>(sender());
|
||||
if (activity) {
|
||||
QHash< int, Plasma::Containment* > containmentHash = d->desktopContainments.take(activity->name());
|
||||
for (auto a : containmentHash) {
|
||||
a->destroy();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ShellCorona::insertContainment(const QString &activity, int screenNum, Plasma::Containment* containment)
|
||||
{
|
||||
d->desktopContainments[activity][screenNum] = containment;
|
||||
|
||||
//when a containment gets deleted update our map of containments
|
||||
connect(containment, &QObject::destroyed, [=](QObject *obj) {
|
||||
// when QObject::destroyed arrives, ~Plasma::Containment has run,
|
||||
// members of Containment are not accessible anymore,
|
||||
// so keep ugly bookeeping by hand
|
||||
auto containment = static_cast<Plasma::Containment*>(obj);
|
||||
for (auto a : d->desktopContainments) {
|
||||
QMutableHashIterator<int, Plasma::Containment *> it(a);
|
||||
while (it.hasNext()) {
|
||||
it.next();
|
||||
if (it.value() == containment) {
|
||||
it.remove();
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
Plasma::Package ShellCorona::lookAndFeelPackage() const
|
||||
{
|
||||
if (!d->lookNFeelPackage.isValid()) {
|
||||
d->lookNFeelPackage = ShellPluginLoader::self()->loadPackage("Plasma/LookAndFeel");
|
||||
//TODO: make loading from config once we have some UI for setting the package
|
||||
d->lookNFeelPackage.setPath("org.kde.lookandfeel");
|
||||
}
|
||||
|
||||
return d->lookNFeelPackage;
|
||||
}
|
||||
|
||||
|
||||
// Desktop corona handler
|
||||
|
||||
|
||||
#include "moc_shellcorona.cpp"
|
||||
|
@ -1,159 +0,0 @@
|
||||
/*
|
||||
* Copyright 2008 Aaron Seigo <aseigo@kde.org>
|
||||
* Copyright 2013 Sebastian Kügler <sebas@kde.org>
|
||||
* Copyright 2013 Ivan Cukic <ivan.cukic@kde.org>
|
||||
* Copyright 2013 Marco Martin <mart@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library General Public License as
|
||||
* published by the Free Software Foundation; either version 2, 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 Library General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef SHELLCORONA_H
|
||||
#define SHELLCORONA_H
|
||||
|
||||
#include "plasma/corona.h"
|
||||
|
||||
#include <Plasma/Package>
|
||||
|
||||
|
||||
namespace Plasma
|
||||
{
|
||||
class Applet;
|
||||
} // namespace Plasma
|
||||
|
||||
class Activity;
|
||||
class PanelView;
|
||||
class QScreen;
|
||||
namespace WorkspaceScripting {
|
||||
class DesktopScriptEngine;
|
||||
}
|
||||
|
||||
namespace KActivities {
|
||||
class Controller;
|
||||
}
|
||||
|
||||
class ShellCorona : public Plasma::Corona
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(QString shell READ shell WRITE setShell)
|
||||
Q_CLASSINFO("D-Bus Interface", "org.kde.PlasmaShell")
|
||||
|
||||
public:
|
||||
explicit ShellCorona(QObject * parent = 0);
|
||||
~ShellCorona();
|
||||
|
||||
/**
|
||||
* Where to save global configuration that doesn't have anything to do with the scene (e.g. views)
|
||||
*/
|
||||
KSharedConfig::Ptr applicationConfig();
|
||||
|
||||
WorkspaceScripting::DesktopScriptEngine * scriptEngine() const;
|
||||
|
||||
int numScreens() const;
|
||||
QRect screenGeometry(int id) const;
|
||||
QRegion availableScreenRegion(int id) const;
|
||||
QRect availableScreenRect(int id) const;
|
||||
|
||||
PanelView *panelView(Plasma::Containment *containment) const;
|
||||
|
||||
KActivities::Controller *activityController();
|
||||
|
||||
Plasma::Package lookAndFeelPackage() const;
|
||||
|
||||
//Those two are a bit of an hack but are just for desktop scripting
|
||||
Activity *activity(const QString &id);
|
||||
void insertActivity(const QString &id, Activity *activity);
|
||||
|
||||
public Q_SLOTS:
|
||||
/**
|
||||
* Request saving applicationConfig on disk, it's event compressed, not immediate
|
||||
*/
|
||||
void requestApplicationConfigSync();
|
||||
|
||||
/**
|
||||
* Sets the shell that the corona should display
|
||||
*/
|
||||
void setShell(const QString & shell);
|
||||
|
||||
/**
|
||||
* Gets the currently shown shell
|
||||
*/
|
||||
QString shell() const;
|
||||
|
||||
///DBUS methods
|
||||
void toggleDashboard();
|
||||
void setDashboardShown(bool show);
|
||||
void showInteractiveConsole();
|
||||
void loadScriptInInteractiveConsole(const QString &script);
|
||||
|
||||
protected Q_SLOTS:
|
||||
void screenAdded(QScreen *screen);
|
||||
void screenRemoved(QObject *screen);
|
||||
|
||||
/**
|
||||
* Loads the layout and performs the needed checks
|
||||
*/
|
||||
void load();
|
||||
|
||||
/**
|
||||
* Unloads everything
|
||||
*/
|
||||
void unload();
|
||||
|
||||
/**
|
||||
* Loads the default (system wide) layout for this user
|
||||
**/
|
||||
void loadDefaultLayout();
|
||||
|
||||
/**
|
||||
* Execute any update script
|
||||
*/
|
||||
void processUpdateScripts();
|
||||
|
||||
int screenForContainment(const Plasma::Containment *containment) const;
|
||||
|
||||
private Q_SLOTS:
|
||||
void createWaitingPanels();
|
||||
void handleContainmentAdded(Plasma::Containment *c);
|
||||
void toggleWidgetExplorer();
|
||||
void toggleActivityManager();
|
||||
void syncAppConfig();
|
||||
void checkActivities();
|
||||
void currentActivityChanged(const QString &newActivity);
|
||||
void activityAdded(const QString &id);
|
||||
void activityRemoved(const QString &id);
|
||||
void checkAddPanelAction(const QStringList &sycocaChanges = QStringList());
|
||||
void addPanel();
|
||||
void addPanel(QAction *action);
|
||||
void addPanel(const QString &plugin);
|
||||
|
||||
void activityOpened();
|
||||
void activityClosed();
|
||||
void activityRemoved();
|
||||
|
||||
private:
|
||||
/**
|
||||
* @returns a new containment associated with the specified @p activity and @p screen.
|
||||
*/
|
||||
Plasma::Containment* createContainmentForActivity(const QString& activity, int screenNum);
|
||||
void insertContainment(const QString &activity, int screenNum, Plasma::Containment *containment);
|
||||
|
||||
class Private;
|
||||
const QScopedPointer<Private> d;
|
||||
};
|
||||
|
||||
#endif // SHELLCORONA_H
|
||||
|
||||
|
@ -1,253 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2013 Ivan Cukic <ivan.cukic(at)kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2,
|
||||
* or (at your option) any later version, as published by the Free
|
||||
* Software Foundation
|
||||
*
|
||||
* 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, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "shellmanager.h"
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
#include <QDebug>
|
||||
#include <QDir>
|
||||
#include <QList>
|
||||
#include <QTimer>
|
||||
|
||||
#include <qplatformdefs.h>
|
||||
#include <QQmlEngine>
|
||||
#include <QQmlComponent>
|
||||
|
||||
#include <config-prefix.h>
|
||||
#include "shellcorona.h"
|
||||
|
||||
#include <kcrash.h>
|
||||
|
||||
static const QString s_shellsDir = QString(QStandardPaths::locate(QStandardPaths::QStandardPaths::GenericDataLocation,
|
||||
"plasma/shells/",
|
||||
QStandardPaths::LocateDirectory));
|
||||
static const QString s_shellLoaderPath = QString("/contents/loader.qml");
|
||||
|
||||
bool ShellManager::s_forceWindowed = false;
|
||||
bool ShellManager::s_noRespawn = false;
|
||||
|
||||
int ShellManager::crashes = 0;
|
||||
|
||||
//
|
||||
// ShellManager
|
||||
//
|
||||
|
||||
class ShellManager::Private {
|
||||
public:
|
||||
Private()
|
||||
: currentHandler(nullptr)
|
||||
{
|
||||
shellUpdateDelay.setInterval(100);
|
||||
shellUpdateDelay.setSingleShot(true);
|
||||
}
|
||||
|
||||
QList<QObject *> handlers;
|
||||
QObject * currentHandler;
|
||||
QTimer shellUpdateDelay;
|
||||
ShellCorona * corona;
|
||||
};
|
||||
|
||||
ShellManager::ShellManager()
|
||||
: d(new Private())
|
||||
{
|
||||
// Using setCrashHandler, we end up in an infinite loop instead of quitting,
|
||||
// use setEmergencySaveFunction instead to avoid this.
|
||||
KCrash::setEmergencySaveFunction(ShellManager::crashHandler);
|
||||
QTimer::singleShot(15 * 1000, this, SLOT(resetCrashCount()));
|
||||
|
||||
connect(
|
||||
&d->shellUpdateDelay, &QTimer::timeout,
|
||||
this, &ShellManager::updateShell
|
||||
);
|
||||
|
||||
d->corona = new ShellCorona(this);
|
||||
|
||||
connect(
|
||||
this, &ShellManager::shellChanged,
|
||||
d->corona, &ShellCorona::setShell
|
||||
);
|
||||
|
||||
loadHandlers();
|
||||
}
|
||||
|
||||
ShellManager::~ShellManager()
|
||||
{
|
||||
// if (d->currentHandler)
|
||||
// d->currentHandler->unload();
|
||||
}
|
||||
|
||||
void ShellManager::loadHandlers()
|
||||
{
|
||||
// TODO: Use corona's qml engine when it switches from QScriptEngine
|
||||
static QQmlEngine * engine = new QQmlEngine(this);
|
||||
|
||||
for (const auto & dir: QDir(s_shellsDir).entryList(QDir::Dirs | QDir::NoDotAndDotDot)) {
|
||||
const QString qmlFile = s_shellsDir + dir + s_shellLoaderPath;
|
||||
// qDebug() << "Making a new instance of " << qmlFile;
|
||||
|
||||
QQmlComponent handlerComponent(engine,
|
||||
QUrl::fromLocalFile(qmlFile)
|
||||
);
|
||||
auto handler = handlerComponent.create();
|
||||
|
||||
// Writing out the errors
|
||||
for (const auto & error: handlerComponent.errors()) {
|
||||
qWarning() << "Error: " << error;
|
||||
}
|
||||
|
||||
if (handler) {
|
||||
registerHandler(handler);
|
||||
}
|
||||
}
|
||||
|
||||
updateShell();
|
||||
}
|
||||
|
||||
void ShellManager::registerHandler(QObject * handler)
|
||||
{
|
||||
// qDebug() << "We got the handler: " << handler->property("shell").toString();
|
||||
|
||||
connect(
|
||||
handler, &QObject::destroyed,
|
||||
this, &ShellManager::deregisterHandler
|
||||
);
|
||||
|
||||
connect(
|
||||
handler, SIGNAL(willingChanged()),
|
||||
this, SLOT(requestShellUpdate())
|
||||
);
|
||||
|
||||
connect(
|
||||
handler, SIGNAL(priorityChanged()),
|
||||
this, SLOT(requestShellUpdate())
|
||||
);
|
||||
|
||||
d->handlers.push_back(handler);
|
||||
}
|
||||
|
||||
void ShellManager::deregisterHandler(QObject * handler)
|
||||
{
|
||||
if (d->handlers.contains(handler)) {
|
||||
d->handlers.removeAll(handler);
|
||||
|
||||
handler->disconnect(this);
|
||||
}
|
||||
|
||||
if (d->currentHandler == handler) {
|
||||
d->currentHandler = nullptr;
|
||||
updateShell();
|
||||
}
|
||||
}
|
||||
|
||||
void ShellManager::requestShellUpdate()
|
||||
{
|
||||
d->shellUpdateDelay.start();
|
||||
}
|
||||
|
||||
void ShellManager::updateShell()
|
||||
{
|
||||
d->shellUpdateDelay.stop();
|
||||
|
||||
if (d->handlers.isEmpty()) {
|
||||
qFatal("We have no shell handlers installed");
|
||||
return;
|
||||
}
|
||||
|
||||
// Finding the handler that has the priority closest to zero.
|
||||
// We will return a handler even if there are no willing ones.
|
||||
|
||||
auto handler =* std::min_element(d->handlers.cbegin(), d->handlers.cend(),
|
||||
[] (QObject * left, QObject * right)
|
||||
{
|
||||
auto willing = [] (QObject * handler)
|
||||
{
|
||||
return handler->property("willing").toBool();
|
||||
};
|
||||
|
||||
auto priority = [] (QObject * handler)
|
||||
{
|
||||
return handler->property("priority").toInt();
|
||||
};
|
||||
|
||||
return
|
||||
// If one is willing and the other is not,
|
||||
// return it - it has the priority
|
||||
willing(left) && !willing(right) ? true :
|
||||
!willing(left) && willing(right) ? false :
|
||||
// otherwise just compare the priorities
|
||||
priority(left) < priority(right);
|
||||
}
|
||||
);
|
||||
|
||||
if (handler == d->currentHandler) return;
|
||||
|
||||
// Activating the new handler and killing the old one
|
||||
if (d->currentHandler) {
|
||||
d->currentHandler->setProperty("loaded", false);
|
||||
}
|
||||
|
||||
d->currentHandler = handler;
|
||||
d->currentHandler->setProperty("loaded", true);
|
||||
|
||||
emit shellChanged(d->currentHandler->property("shell").toString());
|
||||
}
|
||||
|
||||
ShellManager * ShellManager::instance()
|
||||
{
|
||||
static ShellManager manager;
|
||||
return &manager;
|
||||
}
|
||||
|
||||
void ShellManager::setCrashCount(int count)
|
||||
{
|
||||
crashes = count;
|
||||
}
|
||||
|
||||
void ShellManager::resetCrashCount()
|
||||
{
|
||||
crashes = 0;
|
||||
}
|
||||
|
||||
void ShellManager::crashHandler(int signal)
|
||||
{
|
||||
/* plasma-shell restart logic as crash recovery
|
||||
*
|
||||
* We restart plasma-shell after crashes. When it crashes subsequently on startup,
|
||||
* and more than two times in a row, we give up in order to not endlessly loop.
|
||||
* Once the shell process stays alive for at least 15 seconds, we reset the crash
|
||||
* counter, so a later crash, at runtime rather than on startup will still be
|
||||
* recovered from.
|
||||
*
|
||||
* This logic is very similar as to how kwin handles it.
|
||||
*/
|
||||
crashes++;
|
||||
fprintf(stderr, "Application::crashHandler() called with signal %d; recent crashes: %d\n", signal, crashes);
|
||||
char cmd[1024];
|
||||
sprintf(cmd, "%s --crashes %d &",
|
||||
QFile::encodeName(QCoreApplication::applicationFilePath()).constData(), crashes);
|
||||
|
||||
if (crashes < 3 && !s_noRespawn) {
|
||||
sleep(1);
|
||||
system(cmd);
|
||||
} else {
|
||||
fprintf(stderr, "Too many crashes in short order or respawning disabled, not restarting automatically.\n");
|
||||
}
|
||||
|
||||
}
|
@ -1,73 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2013 Ivan Cukic <ivan.cukic(at)kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2,
|
||||
* or (at your option) any later version, as published by the Free
|
||||
* Software Foundation
|
||||
*
|
||||
* 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, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef SHELLMANAGER_H
|
||||
#define SHELLMANAGER_H
|
||||
|
||||
#include <QObject>
|
||||
|
||||
/**
|
||||
* ShellManager creates a ShellCorona instance and manages it.
|
||||
*
|
||||
* Shell manager loads "handlers" from QML files which suggests which shell
|
||||
* corona should currently be active.
|
||||
* For example switching between tablet and desktop shells on hardware changes.
|
||||
*
|
||||
* This class also provides crash handling.
|
||||
*/
|
||||
|
||||
class ShellManager: public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
static ShellManager * instance();
|
||||
~ShellManager();
|
||||
|
||||
void loadHandlers();
|
||||
|
||||
static bool s_forceWindowed;
|
||||
static bool s_noRespawn;
|
||||
|
||||
static void setCrashCount(int count);
|
||||
|
||||
protected Q_SLOTS:
|
||||
void registerHandler(QObject * handler);
|
||||
void deregisterHandler(QObject * handler);
|
||||
|
||||
public Q_SLOTS:
|
||||
void requestShellUpdate();
|
||||
void updateShell();
|
||||
|
||||
Q_SIGNALS:
|
||||
void shellChanged(const QString & shell);
|
||||
|
||||
private Q_SLOTS:
|
||||
void resetCrashCount();
|
||||
|
||||
private:
|
||||
ShellManager();
|
||||
|
||||
class Private;
|
||||
const QScopedPointer<Private> d;
|
||||
|
||||
static int crashes;
|
||||
static void crashHandler(int signal);
|
||||
};
|
||||
|
||||
#endif /* SHELLMANAGER_H */
|
||||
|
@ -1,27 +0,0 @@
|
||||
project(plasmawidgetexplorerplugin)
|
||||
|
||||
set(widgetexplorer_SRC
|
||||
kcategorizeditemsviewmodels.cpp
|
||||
plasmaappletitemmodel.cpp
|
||||
widgetexplorer.cpp
|
||||
widgetexplorerplugin.cpp
|
||||
)
|
||||
|
||||
add_library(plasmawidgetexplorerplugin SHARED ${widgetexplorer_SRC})
|
||||
target_link_libraries(plasmawidgetexplorerplugin
|
||||
Qt5::Core
|
||||
Qt5::Quick
|
||||
Qt5::Qml
|
||||
Qt5::Gui
|
||||
Qt5::Widgets
|
||||
Qt5::Quick
|
||||
Qt5::Qml
|
||||
KF5::Plasma
|
||||
KF5::PlasmaQuick
|
||||
KF5::I18n
|
||||
KF5::Service
|
||||
)
|
||||
|
||||
install(TARGETS plasmawidgetexplorerplugin DESTINATION ${QML_INSTALL_DIR}/org/kde/plasma/private/shell)
|
||||
|
||||
install(FILES qmldir DESTINATION ${QML_INSTALL_DIR}/org/kde/plasma/private/shell)
|
@ -1,249 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2007 Ivan Cukic <ivan.cukic+kde@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library/Lesser General Public License
|
||||
* version 2, or (at your option) any later version, as published by the
|
||||
* Free Software Foundation
|
||||
*
|
||||
* 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 Library/Lesser General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "kcategorizeditemsviewmodels_p.h"
|
||||
#include <klocalizedstring.h>
|
||||
|
||||
#define COLUMN_COUNT 4
|
||||
|
||||
namespace KCategorizedItemsViewModels {
|
||||
|
||||
// AbstractItem
|
||||
|
||||
QString AbstractItem::name() const
|
||||
{
|
||||
return text();
|
||||
}
|
||||
|
||||
QString AbstractItem::id() const
|
||||
{
|
||||
QString plugin = data().toMap()["pluginName"].toString();
|
||||
|
||||
if (plugin.isEmpty()) {
|
||||
return name();
|
||||
}
|
||||
|
||||
return plugin;
|
||||
}
|
||||
|
||||
QString AbstractItem::description() const
|
||||
{
|
||||
return "";
|
||||
}
|
||||
|
||||
bool AbstractItem::isFavorite() const
|
||||
{
|
||||
return passesFiltering(Filter("favorite", true));
|
||||
}
|
||||
|
||||
int AbstractItem::running() const
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
bool AbstractItem::matches(const QString &pattern) const
|
||||
{
|
||||
return
|
||||
name().contains(pattern, Qt::CaseInsensitive) ||
|
||||
description().contains(pattern, Qt::CaseInsensitive);
|
||||
}
|
||||
|
||||
// DefaultFilterModel
|
||||
|
||||
DefaultFilterModel::DefaultFilterModel(QObject *parent) :
|
||||
QStandardItemModel(0, 1, parent)
|
||||
{
|
||||
setHeaderData(1, Qt::Horizontal, i18n("Filters"));
|
||||
//This is to make QML that is understand it
|
||||
QHash<int, QByteArray> newRoleNames = roleNames();
|
||||
newRoleNames[FilterTypeRole] = "filterType";
|
||||
newRoleNames[FilterDataRole] = "filterData";
|
||||
newRoleNames[SeparatorRole] = "separator";
|
||||
|
||||
setRoleNames(newRoleNames);
|
||||
connect(this, SIGNAL(modelReset()),
|
||||
this, SIGNAL(countChanged()));
|
||||
connect(this, SIGNAL(rowsInserted(QModelIndex, int, int)),
|
||||
this, SIGNAL(countChanged()));
|
||||
connect(this, SIGNAL(rowsRemoved(QModelIndex, int, int)),
|
||||
this, SIGNAL(countChanged()));
|
||||
}
|
||||
|
||||
void DefaultFilterModel::addFilter(const QString &caption, const Filter &filter, const QIcon &icon)
|
||||
{
|
||||
QList<QStandardItem *> newRow;
|
||||
QStandardItem *item = new QStandardItem(caption);
|
||||
item->setData(qVariantFromValue<Filter>(filter));
|
||||
if (!icon.isNull()) {
|
||||
item->setIcon(icon);
|
||||
}
|
||||
item->setData(filter.first, FilterTypeRole);
|
||||
item->setData(filter.second, FilterDataRole);
|
||||
|
||||
newRow << item;
|
||||
appendRow(newRow);
|
||||
}
|
||||
|
||||
void DefaultFilterModel::addSeparator(const QString &caption)
|
||||
{
|
||||
QList<QStandardItem *> newRow;
|
||||
QStandardItem *item = new QStandardItem(caption);
|
||||
item->setEnabled(false);
|
||||
item->setData(true, SeparatorRole);
|
||||
|
||||
newRow << item;
|
||||
appendRow(newRow);
|
||||
}
|
||||
|
||||
QVariantHash DefaultFilterModel::get(int row) const
|
||||
{
|
||||
QModelIndex idx = index(row, 0);
|
||||
QVariantHash hash;
|
||||
|
||||
QHash<int, QByteArray>::const_iterator i;
|
||||
for (i = roleNames().constBegin(); i != roleNames().constEnd(); ++i) {
|
||||
hash[i.value()] = data(idx, i.key());
|
||||
}
|
||||
|
||||
return hash;
|
||||
}
|
||||
|
||||
// DefaultItemFilterProxyModel
|
||||
|
||||
DefaultItemFilterProxyModel::DefaultItemFilterProxyModel(QObject *parent)
|
||||
: QSortFilterProxyModel(parent)
|
||||
{
|
||||
}
|
||||
|
||||
void DefaultItemFilterProxyModel::setSourceModel(QAbstractItemModel *sourceModel)
|
||||
{
|
||||
QStandardItemModel *model = qobject_cast<QStandardItemModel*>(sourceModel);
|
||||
|
||||
if (!model) {
|
||||
qWarning() << "Expecting a QStandardItemModel!";
|
||||
return;
|
||||
}
|
||||
|
||||
setRoleNames(sourceModel->roleNames());
|
||||
|
||||
QSortFilterProxyModel::setSourceModel(model);
|
||||
connect(this, SIGNAL(modelReset()),
|
||||
this, SIGNAL(countChanged()));
|
||||
connect(this, SIGNAL(rowsInserted(QModelIndex, int, int)),
|
||||
this, SIGNAL(countChanged()));
|
||||
connect(this, SIGNAL(rowsRemoved(QModelIndex, int, int)),
|
||||
this, SIGNAL(countChanged()));
|
||||
}
|
||||
|
||||
QAbstractItemModel *DefaultItemFilterProxyModel::sourceModel() const
|
||||
{
|
||||
return QSortFilterProxyModel::sourceModel();
|
||||
}
|
||||
|
||||
int DefaultItemFilterProxyModel::columnCount(const QModelIndex &index) const
|
||||
{
|
||||
Q_UNUSED(index);
|
||||
return COLUMN_COUNT;
|
||||
}
|
||||
|
||||
QVariant DefaultItemFilterProxyModel::data(const QModelIndex &index, int role) const
|
||||
{
|
||||
return QSortFilterProxyModel::data(index, role);
|
||||
}
|
||||
|
||||
bool DefaultItemFilterProxyModel::filterAcceptsRow(int sourceRow,
|
||||
const QModelIndex &sourceParent) const
|
||||
{
|
||||
QStandardItemModel *model = (QStandardItemModel *) sourceModel();
|
||||
|
||||
QModelIndex index = sourceModel()->index(sourceRow, 0, sourceParent);
|
||||
|
||||
AbstractItem *item = (AbstractItem *) model->itemFromIndex(index);
|
||||
//qDebug() << "ITEM " << (item ? "IS NOT " : "IS") << " NULL\n";
|
||||
|
||||
return item &&
|
||||
(m_filter.first.isEmpty() || item->passesFiltering(m_filter)) &&
|
||||
(m_searchPattern.isEmpty() || item->matches(m_searchPattern));
|
||||
}
|
||||
|
||||
QVariantHash DefaultItemFilterProxyModel::get(int row) const
|
||||
{
|
||||
QModelIndex idx = index(row, 0);
|
||||
QVariantHash hash;
|
||||
|
||||
QHash<int, QByteArray>::const_iterator i;
|
||||
for (i = roleNames().constBegin(); i != roleNames().constEnd(); ++i) {
|
||||
hash[i.value()] = data(idx, i.key());
|
||||
}
|
||||
|
||||
return hash;
|
||||
}
|
||||
|
||||
bool DefaultItemFilterProxyModel::lessThan(const QModelIndex &left,
|
||||
const QModelIndex &right) const
|
||||
{
|
||||
return
|
||||
sourceModel()->data(left).toString().localeAwareCompare(
|
||||
sourceModel()->data(right).toString()) < 0;
|
||||
}
|
||||
|
||||
void DefaultItemFilterProxyModel::setSearchTerm(const QString &pattern)
|
||||
{
|
||||
m_searchPattern = pattern;
|
||||
invalidateFilter();
|
||||
emit searchTermChanged(pattern);
|
||||
}
|
||||
|
||||
QString DefaultItemFilterProxyModel::searchTerm() const
|
||||
{
|
||||
return m_searchPattern;
|
||||
}
|
||||
|
||||
void DefaultItemFilterProxyModel::setFilter(const Filter &filter)
|
||||
{
|
||||
m_filter = filter;
|
||||
invalidateFilter();
|
||||
emit filterChanged();
|
||||
}
|
||||
|
||||
void DefaultItemFilterProxyModel::setFilterType(const QString type)
|
||||
{
|
||||
m_filter.first = type;
|
||||
invalidateFilter();
|
||||
emit filterChanged();
|
||||
}
|
||||
|
||||
QString DefaultItemFilterProxyModel::filterType() const
|
||||
{
|
||||
return m_filter.first;
|
||||
}
|
||||
|
||||
void DefaultItemFilterProxyModel::setFilterQuery(const QVariant query)
|
||||
{
|
||||
m_filter.second = query;
|
||||
invalidateFilter();
|
||||
emit filterChanged();
|
||||
}
|
||||
|
||||
QVariant DefaultItemFilterProxyModel::filterQuery() const
|
||||
{
|
||||
return m_filter.second;
|
||||
}
|
||||
|
||||
}
|
@ -1,177 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2007 Ivan Cukic <ivan.cukic+kde@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library/Lesser General Public License
|
||||
* version 2, or (at your option) any later version, as published by the
|
||||
* Free Software Foundation
|
||||
*
|
||||
* 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 Library/Lesser General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef PLASMA_KCATEGORIZEDITEMSVIEWMODELS_P_H
|
||||
#define PLASMA_KCATEGORIZEDITEMSVIEWMODELS_P_H
|
||||
|
||||
#include <QtGui/QtGui>
|
||||
#include <QtCore/QtCore>
|
||||
#include <QIcon>
|
||||
|
||||
namespace KCategorizedItemsViewModels {
|
||||
|
||||
typedef QPair<QString, QVariant> Filter;
|
||||
|
||||
/**
|
||||
* Abstract class that needs to be implemented and used with the ItemModel
|
||||
*/
|
||||
class AbstractItem : public QStandardItem
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* Returns a localized string - name of the item
|
||||
*/
|
||||
virtual QString name() const;
|
||||
|
||||
/**
|
||||
* Returns a unique id related to this item
|
||||
*/
|
||||
virtual QString id() const;
|
||||
|
||||
/**
|
||||
* Returns a localized string - description of the item
|
||||
*/
|
||||
virtual QString description() const;
|
||||
|
||||
/**
|
||||
* Returns if the item is flagged as favorite
|
||||
* Default implementation checks if the item passes the Filter("favorite", "1") filter
|
||||
*/
|
||||
virtual bool isFavorite() const;
|
||||
|
||||
/**
|
||||
* Returns the item's number of running applets
|
||||
* Default implementation just returns 0
|
||||
*/
|
||||
virtual int running() const;
|
||||
|
||||
/**
|
||||
* Returns if the item contains string specified by pattern.
|
||||
* Default implementation checks whether name or description contain the
|
||||
* string (not needed to be exactly that string)
|
||||
*/
|
||||
virtual bool matches(const QString &pattern) const;
|
||||
|
||||
/**
|
||||
* sets the favorite flag for the item
|
||||
*/
|
||||
virtual void setFavorite(bool favorite) = 0;
|
||||
/**
|
||||
* sets the number of running applets for the item
|
||||
*/
|
||||
virtual void setRunning(int count) = 0;
|
||||
|
||||
/**
|
||||
* Returns if the item passes the filter specified
|
||||
*/
|
||||
virtual bool passesFiltering(const Filter &filter) const = 0;
|
||||
private:
|
||||
};
|
||||
|
||||
/**
|
||||
* The default implementation of the model containing filters
|
||||
*/
|
||||
class DefaultFilterModel : public QStandardItemModel
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(int count READ count NOTIFY countChanged)
|
||||
public:
|
||||
enum Roles {
|
||||
FilterTypeRole = Qt::UserRole+1,
|
||||
FilterDataRole = Qt::UserRole+2,
|
||||
SeparatorRole = Qt::UserRole+3
|
||||
};
|
||||
DefaultFilterModel(QObject *parent = 0);
|
||||
|
||||
/**
|
||||
* Adds a filter to the model
|
||||
* @param caption The localized string to be displayed as a name of the filter
|
||||
* @param filter The filter structure
|
||||
*/
|
||||
void addFilter(const QString &caption, const Filter &filter, const QIcon &icon = QIcon());
|
||||
|
||||
/**
|
||||
* Adds a separator to the model
|
||||
* @param caption The localized string to be displayed as a name of the separator
|
||||
*/
|
||||
void addSeparator(const QString &caption);
|
||||
|
||||
int count() {return rowCount(QModelIndex());}
|
||||
|
||||
Q_INVOKABLE QVariantHash get(int i) const;
|
||||
|
||||
Q_SIGNALS:
|
||||
void countChanged();
|
||||
};
|
||||
|
||||
/**
|
||||
* Default filter proxy model.
|
||||
*/
|
||||
class DefaultItemFilterProxyModel : public QSortFilterProxyModel
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(QString searchTerm READ searchTerm WRITE setSearchTerm NOTIFY searchTermChanged)
|
||||
Q_PROPERTY(QString filterType READ filterType WRITE setFilterType NOTIFY filterChanged)
|
||||
Q_PROPERTY(QVariant filterQuery READ filterQuery WRITE setFilterQuery NOTIFY filterChanged)
|
||||
Q_PROPERTY(int count READ count NOTIFY countChanged)
|
||||
|
||||
public:
|
||||
DefaultItemFilterProxyModel(QObject *parent = 0);
|
||||
|
||||
bool filterAcceptsRow(int sourceRow, const QModelIndex &sourceParent) const;
|
||||
bool lessThan(const QModelIndex &left, const QModelIndex &right) const;
|
||||
|
||||
void setSearchTerm(const QString &pattern);
|
||||
QString searchTerm() const;
|
||||
|
||||
void setFilterType(const QString type);
|
||||
QString filterType() const;
|
||||
|
||||
void setFilterQuery(const QVariant query);
|
||||
QVariant filterQuery() const;
|
||||
|
||||
void setFilter(const Filter &filter);
|
||||
|
||||
void setSourceModel(QAbstractItemModel *sourceModel);
|
||||
|
||||
QAbstractItemModel *sourceModel() const;
|
||||
|
||||
int columnCount(const QModelIndex &index) const;
|
||||
|
||||
QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const;
|
||||
|
||||
int count() {return rowCount(QModelIndex());}
|
||||
|
||||
Q_INVOKABLE QVariantHash get(int i) const;
|
||||
|
||||
Q_SIGNALS:
|
||||
void searchTermChanged(const QString &term);
|
||||
void filterChanged();
|
||||
void countChanged();
|
||||
|
||||
private:
|
||||
Filter m_filter;
|
||||
QString m_searchPattern;
|
||||
};
|
||||
|
||||
} //end of namespace
|
||||
|
||||
Q_DECLARE_METATYPE(KCategorizedItemsViewModels::Filter)
|
||||
|
||||
#endif /*KCATEGORIZEDITEMSVIEWMODELS_H_*/
|
@ -1,361 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2007 Ivan Cukic <ivan.cukic+kde@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library/Lesser General Public License
|
||||
* version 2, or (at your option) any later version, as published by the
|
||||
* Free Software Foundation
|
||||
*
|
||||
* 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 Library/Lesser General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "plasmaappletitemmodel_p.h"
|
||||
|
||||
#include <QStandardPaths>
|
||||
#include <QFileInfo>
|
||||
|
||||
#include <klocalizedstring.h>
|
||||
#include <kservicetypetrader.h>
|
||||
#include <ksycoca.h>
|
||||
|
||||
PlasmaAppletItem::PlasmaAppletItem(PlasmaAppletItemModel *model,
|
||||
const KPluginInfo& info,
|
||||
FilterFlags flags)
|
||||
: QObject(model),
|
||||
m_model(model),
|
||||
m_info(info),
|
||||
m_runningCount(0),
|
||||
m_favorite(flags & Favorite),
|
||||
m_local(false)
|
||||
{
|
||||
const QString api(m_info.property("X-Plasma-API").toString());
|
||||
if (!api.isEmpty()) {
|
||||
const QString _f = "plasma/plasmoids/" + info.pluginName() + '/';
|
||||
QFileInfo dir(QStandardPaths::locate(QStandardPaths::QStandardPaths::GenericDataLocation,
|
||||
_f,
|
||||
QStandardPaths::LocateDirectory));
|
||||
m_local = dir.exists() && dir.isWritable();
|
||||
}
|
||||
|
||||
//attrs.insert("recommended", flags & Recommended ? true : false);
|
||||
setText(m_info.name() + " - "+ m_info.category().toLower());
|
||||
|
||||
const QString iconName = m_info.icon().isEmpty() ? "application-x-plasma" : info.icon();
|
||||
QIcon icon = QIcon::fromTheme(iconName);
|
||||
setIcon(icon);
|
||||
|
||||
//set plugininfo parts as roles in the model, only way qml can understand it
|
||||
setData(info.name(), PlasmaAppletItemModel::NameRole);
|
||||
setData(info.pluginName(), PlasmaAppletItemModel::PluginNameRole);
|
||||
setData(info.comment(), PlasmaAppletItemModel::DescriptionRole);
|
||||
setData(info.category().toLower(), PlasmaAppletItemModel::CategoryRole);
|
||||
setData(info.license(), PlasmaAppletItemModel::LicenseRole);
|
||||
setData(info.website(), PlasmaAppletItemModel::WebsiteRole);
|
||||
setData(info.version(), PlasmaAppletItemModel::VersionRole);
|
||||
setData(info.author(), PlasmaAppletItemModel::AuthorRole);
|
||||
setData(info.email(), PlasmaAppletItemModel::EmailRole);
|
||||
setData(0, PlasmaAppletItemModel::RunningRole);
|
||||
setData(m_local, PlasmaAppletItemModel::LocalRole);
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::pluginName() const
|
||||
{
|
||||
return m_info.pluginName();
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::name() const
|
||||
{
|
||||
return m_info.name();
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::description() const
|
||||
{
|
||||
return m_info.comment();
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::license() const
|
||||
{
|
||||
return m_info.license();
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::category() const
|
||||
{
|
||||
return m_info.category();
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::website() const
|
||||
{
|
||||
return m_info.website();
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::version() const
|
||||
{
|
||||
return m_info.version();
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::author() const
|
||||
{
|
||||
return m_info.author();
|
||||
}
|
||||
|
||||
QString PlasmaAppletItem::email() const
|
||||
{
|
||||
return m_info.email();
|
||||
}
|
||||
|
||||
int PlasmaAppletItem::running() const
|
||||
{
|
||||
return m_runningCount;
|
||||
}
|
||||
|
||||
void PlasmaAppletItem::setRunning(int count)
|
||||
{
|
||||
m_runningCount = count;
|
||||
setData(count, PlasmaAppletItemModel::RunningRole);
|
||||
emitDataChanged();
|
||||
}
|
||||
|
||||
bool PlasmaAppletItem::matches(const QString &pattern) const
|
||||
{
|
||||
if (m_info.service()) {
|
||||
const QStringList keywords = m_info.property("Keywords").toStringList();
|
||||
foreach (const QString &keyword, keywords) {
|
||||
if (keyword.startsWith(pattern, Qt::CaseInsensitive)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return AbstractItem::matches(pattern);
|
||||
}
|
||||
|
||||
bool PlasmaAppletItem::isFavorite() const
|
||||
{
|
||||
return m_favorite;
|
||||
}
|
||||
|
||||
void PlasmaAppletItem::setFavorite(bool favorite)
|
||||
{
|
||||
if (m_favorite != favorite) {
|
||||
m_favorite = favorite;
|
||||
m_model->setFavorite(m_info.pluginName(), favorite);
|
||||
emitDataChanged();
|
||||
}
|
||||
}
|
||||
|
||||
bool PlasmaAppletItem::isLocal() const
|
||||
{
|
||||
return m_local;
|
||||
}
|
||||
|
||||
bool PlasmaAppletItem::passesFiltering(const KCategorizedItemsViewModels::Filter &filter) const
|
||||
{
|
||||
if (filter.first == "running") {
|
||||
return running();
|
||||
} else if (filter.first == "category") {
|
||||
return m_info.category().toLower() == filter.second;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
QMimeData *PlasmaAppletItem::mimeData() const
|
||||
{
|
||||
QMimeData *data = new QMimeData();
|
||||
QByteArray appletName;
|
||||
appletName += pluginName().toUtf8();
|
||||
data->setData(mimeTypes().at(0), appletName);
|
||||
return data;
|
||||
}
|
||||
|
||||
QStringList PlasmaAppletItem::mimeTypes() const
|
||||
{
|
||||
QStringList types;
|
||||
types << QLatin1String("text/x-plasmoidservicename");
|
||||
return types;
|
||||
}
|
||||
|
||||
PlasmaAppletItemModel* PlasmaAppletItem::appletItemModel()
|
||||
{
|
||||
return m_model;
|
||||
}
|
||||
|
||||
//PlasmaAppletItemModel
|
||||
|
||||
PlasmaAppletItemModel::PlasmaAppletItemModel(QObject * parent)
|
||||
: QStandardItemModel(parent)
|
||||
{
|
||||
KConfig config("plasmarc");
|
||||
m_configGroup = KConfigGroup(&config, "Applet Browser");
|
||||
m_favorites = m_configGroup.readEntry("favorites").split(',');
|
||||
connect(KSycoca::self(), SIGNAL(databaseChanged(QStringList)), this, SLOT(populateModel(QStringList)));
|
||||
|
||||
//This is to make QML that is understand it
|
||||
QHash<int, QByteArray> newRoleNames = roleNames();
|
||||
newRoleNames[NameRole] = "name";
|
||||
newRoleNames[PluginNameRole] = "pluginName";
|
||||
newRoleNames[DescriptionRole] = "description";
|
||||
newRoleNames[CategoryRole] = "category";
|
||||
newRoleNames[LicenseRole] = "license";
|
||||
newRoleNames[WebsiteRole] = "website";
|
||||
newRoleNames[VersionRole] = "version";
|
||||
newRoleNames[AuthorRole] = "author";
|
||||
newRoleNames[EmailRole] = "email";
|
||||
newRoleNames[RunningRole] = "running";
|
||||
newRoleNames[LocalRole] = "local";
|
||||
|
||||
setRoleNames(newRoleNames);
|
||||
|
||||
setSortRole(Qt::DisplayRole);
|
||||
}
|
||||
|
||||
void PlasmaAppletItemModel::populateModel(const QStringList &whatChanged)
|
||||
{
|
||||
if (!whatChanged.isEmpty() && !whatChanged.contains("services")) {
|
||||
return;
|
||||
}
|
||||
|
||||
clear();
|
||||
//qDebug() << "populating model, our application is" << m_application;
|
||||
|
||||
//qDebug() << "number of applets is"
|
||||
// << Plasma::Applet::listAppletInfo(QString(), m_application).count();
|
||||
KService::List services = KServiceTypeTrader::self()->query("Plasma/Applet", QString());
|
||||
|
||||
foreach (const QExplicitlySharedDataPointer<KService> service, services) {
|
||||
KPluginInfo info(service);
|
||||
//qDebug() << info.pluginName() << "NoDisplay" << info.property("NoDisplay").toBool();
|
||||
if (info.property("NoDisplay").toBool() || info.category() == i18n("Containments")) {
|
||||
// we don't want to show the hidden category
|
||||
continue;
|
||||
}
|
||||
|
||||
qDebug() << info.pluginName() << " is the name of the plugin at" << info.entryPath();
|
||||
//qDebug() << info.name() << info.property("X-Plasma-Thumbnail");
|
||||
|
||||
PlasmaAppletItem::FilterFlags flags(PlasmaAppletItem::NoFilter);
|
||||
if (m_favorites.contains(info.pluginName())) {
|
||||
flags |= PlasmaAppletItem::Favorite;
|
||||
}
|
||||
|
||||
appendRow(new PlasmaAppletItem(this, info, flags));
|
||||
}
|
||||
|
||||
emit modelPopulated();
|
||||
}
|
||||
|
||||
void PlasmaAppletItemModel::setRunningApplets(const QHash<QString, int> &apps)
|
||||
{
|
||||
//foreach item, find that string and set the count
|
||||
for (int r = 0; r < rowCount(); ++r) {
|
||||
QStandardItem *i = item(r);
|
||||
PlasmaAppletItem *p = dynamic_cast<PlasmaAppletItem *>(i);
|
||||
|
||||
if (p) {
|
||||
const bool running = apps.value(p->pluginName());
|
||||
p->setRunning(running);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void PlasmaAppletItemModel::setRunningApplets(const QString &name, int count)
|
||||
{
|
||||
for (int r=0; r<rowCount(); ++r) {
|
||||
QStandardItem *i = item(r);
|
||||
PlasmaAppletItem *p = dynamic_cast<PlasmaAppletItem *>(i);
|
||||
if (p && p->pluginName() == name) {
|
||||
p->setRunning(count);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
QStringList PlasmaAppletItemModel::mimeTypes() const
|
||||
{
|
||||
QStringList types;
|
||||
types << QLatin1String("text/x-plasmoidservicename");
|
||||
return types;
|
||||
}
|
||||
|
||||
QSet<QString> PlasmaAppletItemModel::categories() const
|
||||
{
|
||||
QSet<QString> cats;
|
||||
for (int r = 0; r < rowCount(); ++r) {
|
||||
QStandardItem *i = item(r);
|
||||
PlasmaAppletItem *p = dynamic_cast<PlasmaAppletItem *>(i);
|
||||
if (p) {
|
||||
cats.insert(p->category().toLower());
|
||||
}
|
||||
}
|
||||
|
||||
return cats;
|
||||
}
|
||||
|
||||
QMimeData *PlasmaAppletItemModel::mimeData(const QModelIndexList &indexes) const
|
||||
{
|
||||
//qDebug() << "GETTING MIME DATA\n";
|
||||
if (indexes.count() <= 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
QStringList types = mimeTypes();
|
||||
|
||||
if (types.isEmpty()) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
QMimeData *data = new QMimeData();
|
||||
|
||||
QString format = types.at(0);
|
||||
|
||||
QByteArray appletNames;
|
||||
int lastRow = -1;
|
||||
foreach (const QModelIndex &index, indexes) {
|
||||
if (index.row() == lastRow) {
|
||||
continue;
|
||||
}
|
||||
|
||||
lastRow = index.row();
|
||||
PlasmaAppletItem *selectedItem = (PlasmaAppletItem *) itemFromIndex(index);
|
||||
appletNames += '\n' + selectedItem->pluginName().toUtf8();
|
||||
//qDebug() << selectedItem->pluginName() << index.column() << index.row();
|
||||
}
|
||||
|
||||
data->setData(format, appletNames);
|
||||
return data;
|
||||
}
|
||||
|
||||
void PlasmaAppletItemModel::setFavorite(const QString &plugin, bool favorite)
|
||||
{
|
||||
if (favorite) {
|
||||
if (!m_favorites.contains(plugin)) {
|
||||
m_favorites.append(plugin);
|
||||
}
|
||||
} else {
|
||||
m_favorites.removeAll(plugin);
|
||||
}
|
||||
|
||||
m_configGroup.writeEntry("favorites", m_favorites.join(","));
|
||||
m_configGroup.sync();
|
||||
}
|
||||
|
||||
void PlasmaAppletItemModel::setApplication(const QString &app)
|
||||
{
|
||||
m_application = app;
|
||||
populateModel();
|
||||
}
|
||||
|
||||
QString &PlasmaAppletItemModel::Application()
|
||||
{
|
||||
return m_application;
|
||||
}
|
||||
|
||||
//#include <plasmaappletitemmodel_p.moc>
|
||||
|
@ -1,124 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2007 Ivan Cukic <ivan.cukic+kde@gmail.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library/Lesser General Public License
|
||||
* version 2, or (at your option) any later version, as published by the
|
||||
* Free Software Foundation
|
||||
*
|
||||
* 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 Library/Lesser General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef PLASMA_PLASMAAPPLETITEMMODEL_P_H
|
||||
#define PLASMA_PLASMAAPPLETITEMMODEL_P_H
|
||||
|
||||
#include <kplugininfo.h>
|
||||
#include <Plasma/Applet>
|
||||
#include "kcategorizeditemsviewmodels_p.h"
|
||||
|
||||
class PlasmaAppletItemModel;
|
||||
|
||||
/**
|
||||
* Implementation of the KCategorizedItemsViewModels::AbstractItem
|
||||
*/
|
||||
class PlasmaAppletItem : public QObject, public KCategorizedItemsViewModels::AbstractItem
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
enum FilterFlag {
|
||||
NoFilter = 0,
|
||||
Favorite = 1
|
||||
};
|
||||
|
||||
Q_DECLARE_FLAGS(FilterFlags, FilterFlag)
|
||||
|
||||
PlasmaAppletItem(PlasmaAppletItemModel *model, const KPluginInfo& info, FilterFlags flags = NoFilter);
|
||||
|
||||
QString pluginName() const;
|
||||
QString name() const;
|
||||
QString category() const;
|
||||
QString description() const;
|
||||
QString license() const;
|
||||
QString website() const;
|
||||
QString version() const;
|
||||
QString author() const;
|
||||
QString email() const;
|
||||
|
||||
int running() const;
|
||||
bool isLocal() const;
|
||||
bool isFavorite() const;
|
||||
void setFavorite(bool favorite);
|
||||
PlasmaAppletItemModel* appletItemModel();
|
||||
bool matches(const QString &pattern) const;
|
||||
|
||||
//set how many instances of this applet are running
|
||||
void setRunning(int count);
|
||||
bool passesFiltering(const KCategorizedItemsViewModels::Filter & filter) const;
|
||||
QMimeData *mimeData() const;
|
||||
QStringList mimeTypes() const;
|
||||
|
||||
private:
|
||||
PlasmaAppletItemModel * m_model;
|
||||
KPluginInfo m_info;
|
||||
int m_runningCount;
|
||||
bool m_favorite;
|
||||
bool m_local;
|
||||
};
|
||||
|
||||
class PlasmaAppletItemModel : public QStandardItemModel
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
enum Roles {
|
||||
NameRole = Qt::UserRole+1,
|
||||
PluginNameRole = Qt::UserRole+2,
|
||||
DescriptionRole = Qt::UserRole+3,
|
||||
CategoryRole = Qt::UserRole+4,
|
||||
LicenseRole = Qt::UserRole+5,
|
||||
WebsiteRole = Qt::UserRole+6,
|
||||
VersionRole = Qt::UserRole+7,
|
||||
AuthorRole = Qt::UserRole+8,
|
||||
EmailRole = Qt::UserRole+9,
|
||||
RunningRole = Qt::UserRole+10,
|
||||
LocalRole = Qt::UserRole+11
|
||||
};
|
||||
|
||||
explicit PlasmaAppletItemModel(QObject * parent = 0);
|
||||
|
||||
QStringList mimeTypes() const;
|
||||
QSet<QString> categories() const;
|
||||
|
||||
QMimeData *mimeData(const QModelIndexList &indexes) const;
|
||||
|
||||
void setFavorite(const QString &plugin, bool favorite);
|
||||
void setApplication(const QString &app);
|
||||
void setRunningApplets(const QHash<QString, int> &apps);
|
||||
void setRunningApplets(const QString &name, int count);
|
||||
|
||||
QString &Application();
|
||||
|
||||
Q_SIGNALS:
|
||||
void modelPopulated();
|
||||
|
||||
private:
|
||||
QString m_application;
|
||||
QStringList m_favorites;
|
||||
KConfigGroup m_configGroup;
|
||||
|
||||
private Q_SLOTS:
|
||||
void populateModel(const QStringList &whatChanged = QStringList());
|
||||
};
|
||||
|
||||
Q_DECLARE_OPERATORS_FOR_FLAGS(PlasmaAppletItem::FilterFlags)
|
||||
|
||||
#endif /*PLASMAAPPLETSMODEL_H_*/
|
@ -1,2 +0,0 @@
|
||||
module org.kde.plasma.private.shell
|
||||
plugin plasmawidgetexplorerplugin
|
@ -1,469 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2007 by Ivan Cukic <ivan.cukic+kde@gmail.com>
|
||||
* Copyright (C) 2009 by Ana Cecília Martins <anaceciliamb@gmail.com>
|
||||
* Copyright 2013 by Sebastian Kügler <sebas@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library/Lesser General Public License
|
||||
* version 2, or (at your option) any later version, as published by the
|
||||
* Free Software Foundation
|
||||
*
|
||||
* 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 Library/Lesser General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "widgetexplorer.h"
|
||||
|
||||
#include <QQmlEngine>
|
||||
#include <QQmlContext>
|
||||
#include <QQmlExpression>
|
||||
#include <QQmlProperty>
|
||||
|
||||
#include <klocalizedstring.h>
|
||||
#include <kservicetypetrader.h>
|
||||
|
||||
#include <Plasma/Applet>
|
||||
#include <Plasma/Corona>
|
||||
#include <Plasma/Containment>
|
||||
#include <Plasma/Package>
|
||||
#include <Plasma/PackageStructure>
|
||||
#include <qstandardpaths.h>
|
||||
|
||||
#include <view.h>
|
||||
#include "kcategorizeditemsviewmodels_p.h"
|
||||
#include "plasmaappletitemmodel_p.h"
|
||||
|
||||
using namespace KCategorizedItemsViewModels;
|
||||
using namespace Plasma;
|
||||
|
||||
WidgetAction::WidgetAction(QObject *parent)
|
||||
: QAction(parent)
|
||||
{
|
||||
}
|
||||
|
||||
WidgetAction::WidgetAction(const QIcon &icon, const QString &text, QObject *parent)
|
||||
: QAction(icon, text, parent)
|
||||
{
|
||||
}
|
||||
|
||||
class WidgetExplorerPrivate
|
||||
{
|
||||
|
||||
public:
|
||||
WidgetExplorerPrivate(WidgetExplorer *w)
|
||||
: q(w),
|
||||
containment(0),
|
||||
itemModel(w),
|
||||
filterModel(w),
|
||||
view(0)
|
||||
{
|
||||
}
|
||||
|
||||
void initFilters();
|
||||
void initRunningApplets();
|
||||
void containmentDestroyed();
|
||||
|
||||
/**
|
||||
* Tracks a new running applet
|
||||
*/
|
||||
void appletAdded(Plasma::Applet *applet);
|
||||
|
||||
/**
|
||||
* A running applet is no more
|
||||
*/
|
||||
void appletRemoved(Plasma::Applet *applet);
|
||||
|
||||
WidgetExplorer *q;
|
||||
QString application;
|
||||
Plasma::Containment *containment;
|
||||
|
||||
QHash<QString, int> runningApplets; // applet name => count
|
||||
//extra hash so we can look up the names of deleted applets
|
||||
QHash<Plasma::Applet *,QString> appletNames;
|
||||
//QWeakPointer<Plasma::OpenWidgetAssistant> openAssistant;
|
||||
Plasma::Package *package;
|
||||
|
||||
PlasmaAppletItemModel itemModel;
|
||||
KCategorizedItemsViewModels::DefaultFilterModel filterModel;
|
||||
DefaultItemFilterProxyModel filterItemModel;
|
||||
PlasmaQuickView *view;
|
||||
};
|
||||
|
||||
void WidgetExplorerPrivate::initFilters()
|
||||
{
|
||||
filterModel.addFilter(i18n("All Widgets"),
|
||||
KCategorizedItemsViewModels::Filter(), QIcon::fromTheme("plasma"));
|
||||
|
||||
// Filters: Special
|
||||
filterModel.addFilter(i18n("Running"),
|
||||
KCategorizedItemsViewModels::Filter("running", true),
|
||||
QIcon::fromTheme("dialog-ok"));
|
||||
|
||||
filterModel.addSeparator(i18n("Categories:"));
|
||||
|
||||
typedef QPair<QString, QString> catPair;
|
||||
QMap<QString, catPair > categories;
|
||||
QSet<QString> existingCategories = itemModel.categories();
|
||||
//foreach (const QString &category, Plasma::Applet::listCategories(application)) {
|
||||
QStringList cats;
|
||||
KService::List services = KServiceTypeTrader::self()->query("Plasma/Applet", QString());
|
||||
|
||||
foreach (const QExplicitlySharedDataPointer<KService> service, services) {
|
||||
KPluginInfo info(service);
|
||||
if (info.property("NoDisplay").toBool() || info.category() == i18n("Containments") ||
|
||||
info.category().isEmpty()) {
|
||||
// we don't want to show the hidden category
|
||||
continue;
|
||||
}
|
||||
const QString c = info.category();
|
||||
if (-1 == cats.indexOf(c)) {
|
||||
cats << c;
|
||||
}
|
||||
}
|
||||
qWarning() << "TODO: port listCategories()";
|
||||
foreach (const QString &category, cats) {
|
||||
const QString lowerCaseCat = category.toLower();
|
||||
if (existingCategories.contains(lowerCaseCat)) {
|
||||
const QString trans = i18n(category.toLocal8Bit());
|
||||
categories.insert(trans.toLower(), qMakePair(trans, lowerCaseCat));
|
||||
qDebug() << "Categories: << " << lowerCaseCat;
|
||||
}
|
||||
}
|
||||
|
||||
foreach (const catPair &category, categories) {
|
||||
filterModel.addFilter(category.first,
|
||||
KCategorizedItemsViewModels::Filter("category", category.second));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
QObject *WidgetExplorer::widgetsModel() const
|
||||
{
|
||||
return &d->filterItemModel;
|
||||
}
|
||||
|
||||
QObject *WidgetExplorer::filterModel() const
|
||||
{
|
||||
return &d->filterModel;
|
||||
}
|
||||
|
||||
QList <QObject *> WidgetExplorer::widgetsMenuActions()
|
||||
{
|
||||
QList <QObject *> actionList;
|
||||
|
||||
QSignalMapper *mapper = new QSignalMapper(this);
|
||||
QObject::connect(mapper, SIGNAL(mapped(QString)), this, SLOT(downloadWidgets(QString)));
|
||||
|
||||
WidgetAction *action = new WidgetAction(QIcon::fromTheme("applications-internet"),
|
||||
i18n("Download New Plasma Widgets"), this);
|
||||
QObject::connect(action, SIGNAL(triggered(bool)), mapper, SLOT(map()));
|
||||
mapper->setMapping(action, QString());
|
||||
actionList << action;
|
||||
|
||||
KService::List offers = KServiceTypeTrader::self()->query("Plasma/PackageStructure");
|
||||
foreach (const KService::Ptr &service, offers) {
|
||||
//qDebug() << service->property("X-Plasma-ProvidesWidgetBrowser");
|
||||
if (service->property("X-Plasma-ProvidesWidgetBrowser").toBool()) {
|
||||
WidgetAction *action = new WidgetAction(QIcon::fromTheme("applications-internet"),
|
||||
i18nc("%1 is a type of widgets, as defined by "
|
||||
"e.g. some plasma-packagestructure-*.desktop files",
|
||||
"Download New %1", service->name()), this);
|
||||
QObject::connect(action, SIGNAL(triggered(bool)), mapper, SLOT(map()));
|
||||
mapper->setMapping(action, service->property("X-KDE-PluginInfo-Name").toString());
|
||||
actionList << action;
|
||||
}
|
||||
}
|
||||
|
||||
action = new WidgetAction(this);
|
||||
action->setSeparator(true);
|
||||
actionList << action;
|
||||
|
||||
action = new WidgetAction(QIcon::fromTheme("package-x-generic"),
|
||||
i18n("Install Widget From Local File..."), this);
|
||||
QObject::connect(action, SIGNAL(triggered(bool)), this, SLOT(openWidgetFile()));
|
||||
actionList << action;
|
||||
|
||||
return actionList;
|
||||
}
|
||||
|
||||
QList<QObject *> WidgetExplorer::extraActions() const
|
||||
{
|
||||
QList<QObject *> actionList;
|
||||
// foreach (QAction *action, actions()) { // FIXME: where did actions() come from?
|
||||
// actionList << action;
|
||||
// }
|
||||
qWarning() << "extraactions needs reimplementation";
|
||||
return actionList;
|
||||
}
|
||||
|
||||
void WidgetExplorerPrivate::initRunningApplets()
|
||||
{
|
||||
//get applets from corona, count them, send results to model
|
||||
if (!containment) {
|
||||
return;
|
||||
}
|
||||
|
||||
Plasma::Corona *c = containment->corona();
|
||||
|
||||
//we've tried our best to get a corona
|
||||
//we don't want just one containment, we want them all
|
||||
if (!c) {
|
||||
qDebug() << "can't happen";
|
||||
return;
|
||||
}
|
||||
|
||||
appletNames.clear();
|
||||
runningApplets.clear();
|
||||
QList<Containment*> containments = c->containments();
|
||||
foreach (Containment *containment, containments) {
|
||||
QObject::connect(containment, SIGNAL(appletAdded(Plasma::Applet*)), q, SLOT(appletAdded(Plasma::Applet*)));
|
||||
QObject::connect(containment, SIGNAL(appletRemoved(Plasma::Applet*)), q, SLOT(appletRemoved(Plasma::Applet*)));
|
||||
|
||||
foreach (Applet *applet, containment->applets()) {
|
||||
if (applet->pluginInfo().isValid()) {
|
||||
runningApplets[applet->pluginInfo().pluginName()]++;
|
||||
} else {
|
||||
qDebug() << "Invalid plugininfo. :(";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//qDebug() << runningApplets;
|
||||
itemModel.setRunningApplets(runningApplets);
|
||||
}
|
||||
|
||||
void WidgetExplorerPrivate::containmentDestroyed()
|
||||
{
|
||||
containment = 0;
|
||||
}
|
||||
|
||||
void WidgetExplorerPrivate::appletAdded(Plasma::Applet *applet)
|
||||
{
|
||||
QString name = applet->pluginInfo().pluginName();
|
||||
|
||||
runningApplets[name]++;
|
||||
appletNames.insert(applet, name);
|
||||
itemModel.setRunningApplets(name, runningApplets[name]);
|
||||
}
|
||||
|
||||
void WidgetExplorerPrivate::appletRemoved(Plasma::Applet *applet)
|
||||
{
|
||||
QString name = appletNames.take(applet);
|
||||
|
||||
int count = 0;
|
||||
if (runningApplets.contains(name)) {
|
||||
count = runningApplets[name] - 1;
|
||||
|
||||
if (count < 1) {
|
||||
runningApplets.remove(name);
|
||||
} else {
|
||||
runningApplets[name] = count;
|
||||
}
|
||||
}
|
||||
|
||||
itemModel.setRunningApplets(name, count);
|
||||
}
|
||||
|
||||
//WidgetExplorer
|
||||
|
||||
WidgetExplorer::WidgetExplorer(QObject *parent)
|
||||
: QObject(parent),
|
||||
d(new WidgetExplorerPrivate(this))
|
||||
{
|
||||
//FIXME: delay
|
||||
setApplication();
|
||||
d->initRunningApplets();
|
||||
|
||||
d->filterItemModel.setSortCaseSensitivity(Qt::CaseInsensitive);
|
||||
d->filterItemModel.setDynamicSortFilter(true);
|
||||
d->filterItemModel.setSourceModel(&d->itemModel);
|
||||
d->filterItemModel.sort(0);
|
||||
}
|
||||
|
||||
WidgetExplorer::~WidgetExplorer()
|
||||
{
|
||||
delete d;
|
||||
}
|
||||
|
||||
|
||||
void WidgetExplorer::setApplication(const QString &app)
|
||||
{
|
||||
if (d->application == app && !app.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
d->application = app;
|
||||
d->itemModel.setApplication(app);
|
||||
d->initFilters();
|
||||
|
||||
d->itemModel.setRunningApplets(d->runningApplets);
|
||||
emit applicationChanged();
|
||||
}
|
||||
|
||||
QString WidgetExplorer::application()
|
||||
{
|
||||
return d->application;
|
||||
}
|
||||
|
||||
void WidgetExplorer::setContainment(Plasma::Containment *containment)
|
||||
{
|
||||
if (d->containment != containment) {
|
||||
if (d->containment) {
|
||||
d->containment->disconnect(this);
|
||||
}
|
||||
|
||||
d->containment = containment;
|
||||
|
||||
if (d->containment) {
|
||||
connect(d->containment, SIGNAL(destroyed(QObject*)), this, SLOT(containmentDestroyed()));
|
||||
connect(d->containment, SIGNAL(immutabilityChanged(Plasma::Types::ImmutabilityType)), this, SLOT(immutabilityChanged(Plasma::Types::ImmutabilityType)));
|
||||
|
||||
}
|
||||
|
||||
d->initRunningApplets();
|
||||
emit containmentChanged();
|
||||
}
|
||||
}
|
||||
|
||||
Containment *WidgetExplorer::containment() const
|
||||
{
|
||||
return d->containment;
|
||||
}
|
||||
|
||||
Plasma::Corona *WidgetExplorer::corona() const
|
||||
{
|
||||
if (d->containment) {
|
||||
return d->containment->corona();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void WidgetExplorer::addApplet(const QString &pluginName)
|
||||
{
|
||||
const QString p = "plasma/plasmoids/"+pluginName;
|
||||
qWarning() << "--------> load applet: " << pluginName << " relpath: " << p;
|
||||
|
||||
QStringList dirs = QStandardPaths::locateAll(QStandardPaths::GenericDataLocation, p, QStandardPaths::LocateDirectory);
|
||||
|
||||
qDebug() << " .. pathes: " << dirs;
|
||||
if (!dirs.count()) {
|
||||
qWarning() << "Failed to find plasmoid path for " << pluginName;
|
||||
return;
|
||||
}
|
||||
Plasma::Applet *applet = Plasma::Applet::loadPlasmoid(dirs.first());
|
||||
|
||||
if (applet) {
|
||||
if (d->containment) {
|
||||
d->containment->addApplet(applet);
|
||||
} else {
|
||||
qWarning() << "No containment set (but the applet loaded).";
|
||||
}
|
||||
} else {
|
||||
qWarning() << "Failed to load applet" << pluginName << dirs;
|
||||
}
|
||||
}
|
||||
|
||||
void WidgetExplorer::immutabilityChanged(Plasma::Types::ImmutabilityType type)
|
||||
{
|
||||
if (type != Plasma::Types::Mutable) {
|
||||
emit shouldClose();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void WidgetExplorer::downloadWidgets(const QString &type)
|
||||
{
|
||||
Plasma::PackageStructure *installer = 0;
|
||||
|
||||
if (!type.isEmpty()) {
|
||||
QString constraint = QString("'%1' == [X-KDE-PluginInfo-Name]").arg(type);
|
||||
KService::List offers = KServiceTypeTrader::self()->query("Plasma/PackageStructure",
|
||||
constraint);
|
||||
if (offers.isEmpty()) {
|
||||
//qDebug() << "could not find requested PackageStructure plugin" << type;
|
||||
} else {
|
||||
KService::Ptr service = offers.first();
|
||||
QString error;
|
||||
// FIXME: port install to plasma2
|
||||
// installer = service->createInstance<Plasma::PackageStructure>(topLevelWidget(),
|
||||
// QVariantList(), &error);
|
||||
if (installer) {
|
||||
// connect(installer, SIGNAL(newWidgetBrowserFinished()),
|
||||
// installer, SLOT(deleteLater()));
|
||||
} else {
|
||||
//qDebug() << "found, but could not load requested PackageStructure plugin" << type
|
||||
// << "; reported error was" << error;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (installer) {
|
||||
//installer->createNewWidgetBrowser();
|
||||
} else {
|
||||
// we don't need to delete the default Applet::packageStructure as that
|
||||
// belongs to the applet
|
||||
// Plasma::Applet::packageStructure()->createNewWidgetBrowser();
|
||||
/**
|
||||
for reference in a libplasma2 world, the above line equates to this:
|
||||
|
||||
KNS3::DownloadDialog *knsDialog = m_knsDialog.data();
|
||||
if (!knsDialog) {
|
||||
m_knsDialog = knsDialog = new KNS3::DownloadDialog("plasmoids.knsrc", parent);
|
||||
connect(knsDialog, SIGNAL(accepted()), this, SIGNAL(newWidgetBrowserFinished()));
|
||||
}
|
||||
|
||||
knsDialog->show();
|
||||
knsDialog->raise();
|
||||
*/
|
||||
}
|
||||
emit shouldClose();
|
||||
}
|
||||
|
||||
void WidgetExplorer::openWidgetFile()
|
||||
{
|
||||
/*
|
||||
Plasma::OpenWidgetAssistant *assistant = d->openAssistant.data();
|
||||
if (!assistant) {
|
||||
assistant = new Plasma::OpenWidgetAssistant(0);
|
||||
d->openAssistant = assistant;
|
||||
}
|
||||
|
||||
KWindowSystem::setOnDesktop(assistant->winId(), KWindowSystem::currentDesktop());
|
||||
assistant->setAttribute(Qt::WA_DeleteOnClose, true);
|
||||
assistant->show();
|
||||
assistant->raise();
|
||||
assistant->setFocus();
|
||||
*/
|
||||
emit shouldClose();
|
||||
}
|
||||
|
||||
void WidgetExplorer::uninstall(const QString &pluginName)
|
||||
{
|
||||
const QString packageRoot = QStandardPaths::writableLocation(QStandardPaths::GenericDataLocation) + "/plasma/plasmoids/";
|
||||
|
||||
Plasma::Package pkg;
|
||||
pkg.setPath(packageRoot);
|
||||
pkg.uninstall(pluginName, packageRoot);
|
||||
|
||||
//FIXME: moreefficient way rather a linear scan?
|
||||
for (int i = 0; i < d->itemModel.rowCount(); ++i) {
|
||||
QStandardItem *item = d->itemModel.item(i);
|
||||
if (item->data(PlasmaAppletItemModel::PluginNameRole).toString() == pluginName) {
|
||||
d->itemModel.takeRow(i);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#include "moc_widgetexplorer.cpp"
|
@ -1,156 +0,0 @@
|
||||
/*
|
||||
* Copyright (C) 2007 by Ivan Cukic <ivan.cukic+kde@gmail.com>
|
||||
* Copyright (C) 2009 by Ana Cecília Martins <anaceciliamb@gmail.com>
|
||||
* Copyright 2013 by Sebastian Kügler <sebas@kde.org>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Library/Lesser General Public License
|
||||
* version 2, or (at your option) any later version, as published by the
|
||||
* Free Software Foundation
|
||||
*
|
||||
* 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 Library/Lesser General Public
|
||||
* License along with this program; if not, write to the
|
||||
* Free Software Foundation, Inc.,
|
||||
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef WIDGETEXPLORER_H
|
||||
#define WIDGETEXPLORER_H
|
||||
|
||||
#include <QAction>
|
||||
#include <QObject>
|
||||
|
||||
#include "plasmaappletitemmodel_p.h"
|
||||
|
||||
namespace Plasma {
|
||||
class Corona;
|
||||
class Containment;
|
||||
class Applet;
|
||||
}
|
||||
class WidgetExplorerPrivate;
|
||||
class PlasmaQuickView;
|
||||
|
||||
//We need to access the separator property that is not exported by QAction
|
||||
class WidgetAction : public QAction
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(bool separator READ isSeparator WRITE setSeparator NOTIFY separatorChanged)
|
||||
|
||||
public:
|
||||
WidgetAction(QObject *parent = 0);
|
||||
WidgetAction(const QIcon &icon, const QString &text, QObject *parent);
|
||||
|
||||
Q_SIGNALS:
|
||||
void separatorChanged();
|
||||
};
|
||||
|
||||
class WidgetExplorer : public QObject
|
||||
{
|
||||
|
||||
Q_OBJECT
|
||||
|
||||
/**
|
||||
* Model that lists all applets
|
||||
*/
|
||||
Q_PROPERTY(QObject * widgetsModel READ widgetsModel CONSTANT)
|
||||
|
||||
/**
|
||||
* Model that lists all applets filters and categories
|
||||
*/
|
||||
Q_PROPERTY(QObject * filterModel READ filterModel CONSTANT)
|
||||
|
||||
/**
|
||||
* Actions for adding widgets, like download plasma widgets, download google gadgets, install from local file
|
||||
*/
|
||||
Q_PROPERTY(QList<QObject *> widgetsMenuActions READ widgetsMenuActions NOTIFY widgetsMenuActionsChanged)
|
||||
|
||||
/**
|
||||
* Extra actions assigned by the shell, like switch to activity manager
|
||||
*/
|
||||
Q_PROPERTY(QList<QObject *> extraActions READ extraActions NOTIFY extraActionsChanged)
|
||||
|
||||
/**
|
||||
* The application that owns the widget list. different application may show different lists
|
||||
*/
|
||||
Q_PROPERTY(QString application READ application WRITE setApplication NOTIFY applicationChanged)
|
||||
|
||||
Q_PROPERTY(Plasma::Containment *containment READ containment WRITE setContainment NOTIFY containmentChanged)
|
||||
|
||||
public:
|
||||
explicit WidgetExplorer(QObject *parent = 0);
|
||||
~WidgetExplorer();
|
||||
|
||||
QString application();
|
||||
|
||||
/**
|
||||
* Populates the widget list for the given application. This must be called
|
||||
* before the widget explorer will be usable as the widget list will remain
|
||||
* empty up to that point.
|
||||
*
|
||||
* @arg application the application which the widgets should be loaded for.
|
||||
*/
|
||||
void setApplication(const QString &application = QString());
|
||||
|
||||
/**
|
||||
* Changes the current default containment to add applets to
|
||||
*
|
||||
* @arg containment the new default
|
||||
*/
|
||||
void setContainment(Plasma::Containment *containment);
|
||||
|
||||
/**
|
||||
* @return the current default containment to add applets to
|
||||
*/
|
||||
Plasma::Containment *containment() const;
|
||||
/**
|
||||
* @return the current corona this widget is added to
|
||||
*/
|
||||
Plasma::Corona *corona() const;
|
||||
|
||||
QObject *widgetsModel() const;
|
||||
QObject *filterModel() const;
|
||||
|
||||
QList <QObject *> widgetsMenuActions();
|
||||
QList <QObject *> extraActions() const;
|
||||
|
||||
/**
|
||||
* Uninstall a plasmoid with a given plugin name. only user-installed ones are uninstallable
|
||||
*/
|
||||
Q_INVOKABLE void uninstall(const QString &pluginName);
|
||||
|
||||
Q_SIGNALS:
|
||||
void widgetsMenuActionsChanged();
|
||||
void extraActionsChanged();
|
||||
void shouldClose();
|
||||
void viewChanged();
|
||||
void applicationChanged();
|
||||
void containmentChanged();
|
||||
|
||||
public Q_SLOTS:
|
||||
/**
|
||||
* Adds currently selected applets
|
||||
*/
|
||||
void addApplet(const QString &pluginName);
|
||||
void openWidgetFile();
|
||||
void downloadWidgets(const QString &type);
|
||||
|
||||
protected Q_SLOTS:
|
||||
void immutabilityChanged(Plasma::Types::ImmutabilityType);
|
||||
|
||||
private:
|
||||
Q_PRIVATE_SLOT(d, void appletAdded(Plasma::Applet*))
|
||||
Q_PRIVATE_SLOT(d, void appletRemoved(Plasma::Applet*))
|
||||
Q_PRIVATE_SLOT(d, void containmentDestroyed())
|
||||
|
||||
WidgetExplorerPrivate * const d;
|
||||
friend class WidgetExplorerPrivate;
|
||||
};
|
||||
|
||||
|
||||
#endif // WIDGETEXPLORER_H
|
@ -1,36 +0,0 @@
|
||||
/*
|
||||
Copyright 2014 by David Edmundson <davidedmundson@kde.org>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
*/
|
||||
|
||||
#include "widgetexplorerplugin.h"
|
||||
|
||||
#include <QtQml>
|
||||
|
||||
#include "widgetexplorer.h"
|
||||
#include <plasma/containment.h>
|
||||
|
||||
void WidgetExplorerPlugin::registerTypes(const char *uri)
|
||||
{
|
||||
Q_ASSERT(uri == QLatin1String("org.kde.plasma.private.shell"));
|
||||
|
||||
qmlRegisterType<Plasma::Containment>();
|
||||
qmlRegisterType<WidgetExplorer>(uri, 2, 0, "WidgetExplorer");
|
||||
}
|
@ -1,37 +0,0 @@
|
||||
/*
|
||||
Copyright 2014 by David Edmundson <davidedmundson@kde.org>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
*/
|
||||
|
||||
#ifndef WIDGETEXPLORERPLUGIN_H
|
||||
#define WIDGETEXPLORERPLUGIN_H
|
||||
|
||||
#include <QQmlExtensionPlugin>
|
||||
|
||||
class WidgetExplorerPlugin : public QQmlExtensionPlugin
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PLUGIN_METADATA(IID "org.qt-project.Qt.QQmlExtensionInterface")
|
||||
|
||||
public:
|
||||
void registerTypes(const char *uri);
|
||||
};
|
||||
|
||||
#endif
|
Loading…
Reference in New Issue
Block a user