[kcmkwin/kwindecoration] Import a new decoration configuration module
Following features are supported: * finds all plugins ** finds all themes for a theme-engine plugin * renders previews for the plugin/themes * loads currently used plugin/theme * saves selected plugin/theme * triggers config reload in KWin Following features are currently not supported: * Search * Plugin configuration * GHNS * Button configuration
This commit is contained in:
parent
fcec334b3c
commit
8dd0a8163f
26 changed files with 2476 additions and 2285 deletions
|
@ -22,6 +22,7 @@ find_package(Qt5 ${QT_MIN_VERSION} CONFIG REQUIRED COMPONENTS
|
||||||
Core
|
Core
|
||||||
DBus
|
DBus
|
||||||
Quick
|
Quick
|
||||||
|
QuickWidgets
|
||||||
Script
|
Script
|
||||||
UiTools
|
UiTools
|
||||||
Widgets
|
Widgets
|
||||||
|
|
|
@ -1,23 +1,14 @@
|
||||||
# KI18N Translation Domain for this library
|
# KI18N Translation Domain for this library
|
||||||
add_definitions(-DTRANSLATION_DOMAIN=\"kcmkwindecoration\")
|
add_definitions(-DTRANSLATION_DOMAIN=\"kcmkwindecoration\")
|
||||||
|
|
||||||
# need a header file from Aurorae sources
|
add_subdirectory(declarative-plugin)
|
||||||
include_directories(
|
|
||||||
${KWIN_SOURCE_DIR}/clients/aurorae/src/lib
|
|
||||||
../utils/
|
|
||||||
)
|
|
||||||
|
|
||||||
set(AURORAE_SOURCE_DIR ${KWIN_SOURCE_DIR}/clients/aurorae/src/lib/)
|
|
||||||
|
|
||||||
set(kcm_kwindecoration_PART_SRCS
|
set(kcm_kwindecoration_PART_SRCS
|
||||||
kwindecoration.cpp
|
kcm.cpp
|
||||||
buttons.cpp
|
buttons.cpp
|
||||||
buttonsconfigdialog.cpp
|
# buttonsconfigdialog.cpp
|
||||||
configdialog.cpp
|
configdialog.cpp
|
||||||
preview.cpp
|
|
||||||
decorationmodel.cpp
|
decorationmodel.cpp
|
||||||
${AURORAE_SOURCE_DIR}/auroraetheme.cpp
|
|
||||||
${AURORAE_SOURCE_DIR}/themeconfig.cpp
|
|
||||||
)
|
)
|
||||||
|
|
||||||
ki18n_wrap_ui(kcm_kwindecoration_PART_SRCS
|
ki18n_wrap_ui(kcm_kwindecoration_PART_SRCS
|
||||||
|
@ -29,14 +20,17 @@ ki18n_wrap_ui(kcm_kwindecoration_PART_SRCS
|
||||||
|
|
||||||
add_library(kcm_kwindecoration MODULE ${kcm_kwindecoration_PART_SRCS})
|
add_library(kcm_kwindecoration MODULE ${kcm_kwindecoration_PART_SRCS})
|
||||||
target_link_libraries(kcm_kwindecoration
|
target_link_libraries(kcm_kwindecoration
|
||||||
kdecorations
|
KDecoration2::KDecoration
|
||||||
Qt5::DBus
|
Qt5::DBus
|
||||||
Qt5::Quick
|
Qt5::Quick
|
||||||
|
Qt5::QuickWidgets
|
||||||
Qt5::UiTools
|
Qt5::UiTools
|
||||||
KF5::Completion
|
KF5::Completion
|
||||||
KF5::ConfigWidgets
|
KF5::ConfigWidgets
|
||||||
KF5::I18n
|
KF5::I18n
|
||||||
KF5::NewStuff
|
KF5::NewStuff
|
||||||
|
KF5::WindowSystem
|
||||||
|
KF5::Service
|
||||||
)
|
)
|
||||||
install(TARGETS kcm_kwindecoration DESTINATION ${PLUGIN_INSTALL_DIR} )
|
install(TARGETS kcm_kwindecoration DESTINATION ${PLUGIN_INSTALL_DIR} )
|
||||||
|
|
||||||
|
@ -45,7 +39,4 @@ install(TARGETS kcm_kwindecoration DESTINATION ${PLUGIN_INSTALL_DIR} )
|
||||||
install( FILES kwindecoration.desktop DESTINATION ${SERVICES_INSTALL_DIR} )
|
install( FILES kwindecoration.desktop DESTINATION ${SERVICES_INSTALL_DIR} )
|
||||||
install( FILES
|
install( FILES
|
||||||
qml/main.qml
|
qml/main.qml
|
||||||
qml/AuroraeDecoration.qml
|
|
||||||
qml/AuroraePreview.qml
|
|
||||||
qml/DecorationPreview.qml
|
|
||||||
DESTINATION ${DATA_INSTALL_DIR}/kwin/kcm_kwindecoration)
|
DESTINATION ${DATA_INSTALL_DIR}/kwin/kcm_kwindecoration)
|
||||||
|
|
20
kcmkwin/kwindecoration/declarative-plugin/CMakeLists.txt
Normal file
20
kcmkwin/kwindecoration/declarative-plugin/CMakeLists.txt
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
set(plugin_SRCS
|
||||||
|
previewbridge.cpp
|
||||||
|
previewclient.cpp
|
||||||
|
previewitem.cpp
|
||||||
|
previewsettings.cpp
|
||||||
|
plugin.cpp
|
||||||
|
)
|
||||||
|
|
||||||
|
add_library(kdecorationprivatedeclarative SHARED ${plugin_SRCS})
|
||||||
|
target_link_libraries(kdecorationprivatedeclarative
|
||||||
|
KDecoration2::KDecoration
|
||||||
|
KDecoration2::KDecoration2Private
|
||||||
|
Qt5::Quick
|
||||||
|
KF5::CoreAddons
|
||||||
|
KF5::ConfigWidgets
|
||||||
|
KF5::Service
|
||||||
|
)
|
||||||
|
|
||||||
|
install(TARGETS kdecorationprivatedeclarative DESTINATION ${QML_INSTALL_DIR}/org/kde/kwin/private/kdecoration )
|
||||||
|
install(FILES qmldir DESTINATION ${QML_INSTALL_DIR}/org/kde/kwin/private/kdecoration )
|
51
kcmkwin/kwindecoration/declarative-plugin/plugin.cpp
Normal file
51
kcmkwin/kwindecoration/declarative-plugin/plugin.cpp
Normal file
|
@ -0,0 +1,51 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#include "plugin.h"
|
||||||
|
#include "previewbridge.h"
|
||||||
|
#include "previewclient.h"
|
||||||
|
#include "previewitem.h"
|
||||||
|
#include "previewsettings.h"
|
||||||
|
|
||||||
|
#include <KDecoration2/Decoration>
|
||||||
|
#include <KDecoration2/DecorationShadow>
|
||||||
|
|
||||||
|
#include <qqml.h>
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
|
||||||
|
void Plugin::registerTypes(const char *uri)
|
||||||
|
{
|
||||||
|
Q_ASSERT(QLatin1String(uri) == QLatin1String("org.kde.kwin.private.kdecoration"));
|
||||||
|
qmlRegisterType<KDecoration2::Preview::PreviewBridge>(uri, 1, 0, "Bridge");
|
||||||
|
qmlRegisterType<KDecoration2::Preview::Settings>(uri, 1, 0, "Settings");
|
||||||
|
qmlRegisterType<KDecoration2::Preview::PreviewItem>(uri, 1, 0, "Decoration");
|
||||||
|
qmlRegisterType<KDecoration2::Preview::PreviewClient>();
|
||||||
|
qmlRegisterType<KDecoration2::Decoration>();
|
||||||
|
qmlRegisterType<KDecoration2::DecorationShadow>();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#include "plugin.moc"
|
||||||
|
|
41
kcmkwin/kwindecoration/declarative-plugin/plugin.h
Normal file
41
kcmkwin/kwindecoration/declarative-plugin/plugin.h
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#ifndef KDECOARTIONS_PREVIEW_PLUGIN_H
|
||||||
|
#define KDECOARTIONS_PREVIEW_PLUGIN_H
|
||||||
|
|
||||||
|
#include <QQmlExtensionPlugin>
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
|
||||||
|
class Plugin : public QQmlExtensionPlugin
|
||||||
|
{
|
||||||
|
Q_PLUGIN_METADATA(IID "org.kde.kdecoration2")
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
void registerTypes(const char *uri) override;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
165
kcmkwin/kwindecoration/declarative-plugin/previewbridge.cpp
Normal file
165
kcmkwin/kwindecoration/declarative-plugin/previewbridge.cpp
Normal file
|
@ -0,0 +1,165 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#include "previewbridge.h"
|
||||||
|
#include "previewclient.h"
|
||||||
|
#include "previewitem.h"
|
||||||
|
#include "previewsettings.h"
|
||||||
|
|
||||||
|
#include <KDecoration2/DecoratedClient>
|
||||||
|
#include <KDecoration2/Decoration>
|
||||||
|
|
||||||
|
#include <KPluginLoader>
|
||||||
|
#include <KPluginFactory>
|
||||||
|
#include <KPluginTrader>
|
||||||
|
|
||||||
|
#include <QDebug>
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
|
||||||
|
static const QString s_pluginName = QStringLiteral("org.kde.kdecoration2");
|
||||||
|
|
||||||
|
PreviewBridge::PreviewBridge(QObject *parent)
|
||||||
|
: DecorationBridge(parent)
|
||||||
|
, m_lastCreatedClient(nullptr)
|
||||||
|
, m_lastCreatedSettings(nullptr)
|
||||||
|
, m_valid(false)
|
||||||
|
{
|
||||||
|
connect(this, &PreviewBridge::pluginChanged, this, &PreviewBridge::createFactory);
|
||||||
|
}
|
||||||
|
|
||||||
|
PreviewBridge::~PreviewBridge() = default;
|
||||||
|
|
||||||
|
std::unique_ptr<DecoratedClientPrivate> PreviewBridge::createClient(DecoratedClient *client, Decoration *decoration)
|
||||||
|
{
|
||||||
|
auto ptr = std::unique_ptr<PreviewClient>(new PreviewClient(client, decoration));
|
||||||
|
m_lastCreatedClient = ptr.get();
|
||||||
|
return std::move(ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewBridge::update(Decoration *decoration, const QRect &geometry)
|
||||||
|
{
|
||||||
|
Q_UNUSED(geometry)
|
||||||
|
auto it = std::find_if(m_previewItems.constBegin(), m_previewItems.constEnd(), [decoration](PreviewItem *item) {
|
||||||
|
return item->decoration() == decoration;
|
||||||
|
});
|
||||||
|
if (it != m_previewItems.constEnd()) {
|
||||||
|
(*it)->update();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
std::unique_ptr<DecorationSettingsPrivate> PreviewBridge::settings(DecorationSettings *parent)
|
||||||
|
{
|
||||||
|
auto ptr = std::unique_ptr<PreviewSettings>(new PreviewSettings(parent));
|
||||||
|
m_lastCreatedSettings = ptr.get();
|
||||||
|
return std::move(ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewBridge::registerPreviewItem(PreviewItem *item)
|
||||||
|
{
|
||||||
|
m_previewItems.append(item);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewBridge::unregisterPreviewItem(PreviewItem *item)
|
||||||
|
{
|
||||||
|
m_previewItems.removeAll(item);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewBridge::setPlugin(const QString &plugin)
|
||||||
|
{
|
||||||
|
if (m_plugin == plugin) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_plugin = plugin;
|
||||||
|
qDebug() << "Plugin changed to: " << m_plugin;
|
||||||
|
emit pluginChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
QString PreviewBridge::theme() const
|
||||||
|
{
|
||||||
|
return m_theme;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewBridge::setTheme(const QString &theme)
|
||||||
|
{
|
||||||
|
if (m_theme == theme) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_theme = theme;
|
||||||
|
emit themeChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
QString PreviewBridge::plugin() const
|
||||||
|
{
|
||||||
|
return m_plugin;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewBridge::createFactory()
|
||||||
|
{
|
||||||
|
m_factory.clear();
|
||||||
|
if (m_plugin.isNull()) {
|
||||||
|
setValid(false);
|
||||||
|
qDebug() <<"Plugin not set";
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const auto offers = KPluginTrader::self()->query(s_pluginName,
|
||||||
|
s_pluginName,
|
||||||
|
QStringLiteral("[X-KDE-PluginInfo-Name] == '%1'").arg(m_plugin));
|
||||||
|
if (offers.isEmpty()) {
|
||||||
|
setValid(false);
|
||||||
|
qDebug() << "no offers";
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
KPluginLoader loader(offers.first().libraryPath());
|
||||||
|
m_factory = loader.factory();
|
||||||
|
qDebug() << "Factory: " << !m_factory.isNull();
|
||||||
|
setValid(!m_factory.isNull());
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewBridge::isValid() const
|
||||||
|
{
|
||||||
|
return m_valid;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewBridge::setValid(bool valid)
|
||||||
|
{
|
||||||
|
if (m_valid == valid) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_valid = valid;
|
||||||
|
emit validChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
Decoration *PreviewBridge::createDecoration(QObject *parent)
|
||||||
|
{
|
||||||
|
if (!m_valid) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
QVariantMap args({ {QStringLiteral("bridge"), QVariant::fromValue(this)} });
|
||||||
|
if (!m_theme.isNull()) {
|
||||||
|
args.insert(QStringLiteral("theme"), m_theme);
|
||||||
|
}
|
||||||
|
return m_factory->create<KDecoration2::Decoration>(parent, QVariantList({args}));
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
92
kcmkwin/kwindecoration/declarative-plugin/previewbridge.h
Normal file
92
kcmkwin/kwindecoration/declarative-plugin/previewbridge.h
Normal file
|
@ -0,0 +1,92 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#ifndef KDECOARTIONS_PREVIEW_BRIDGE_H
|
||||||
|
#define KDECOARTIONS_PREVIEW_BRIDGE_H
|
||||||
|
|
||||||
|
#include <KDecoration2/Private/DecorationBridge>
|
||||||
|
|
||||||
|
#include <QList>
|
||||||
|
#include <QPointer>
|
||||||
|
|
||||||
|
class KPluginFactory;
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
|
||||||
|
class PreviewClient;
|
||||||
|
class PreviewItem;
|
||||||
|
class PreviewSettings;
|
||||||
|
|
||||||
|
class PreviewBridge : public DecorationBridge
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
Q_PROPERTY(QString plugin READ plugin WRITE setPlugin NOTIFY pluginChanged)
|
||||||
|
Q_PROPERTY(QString theme READ theme WRITE setTheme NOTIFY themeChanged)
|
||||||
|
Q_PROPERTY(bool valid READ isValid NOTIFY validChanged)
|
||||||
|
public:
|
||||||
|
explicit PreviewBridge(QObject *parent = nullptr);
|
||||||
|
virtual ~PreviewBridge();
|
||||||
|
std::unique_ptr<DecoratedClientPrivate> createClient(DecoratedClient *client, Decoration *decoration) override;
|
||||||
|
void update(Decoration* decoration, const QRect& geometry) override;
|
||||||
|
std::unique_ptr<DecorationSettingsPrivate> settings(DecorationSettings *parent) override;
|
||||||
|
|
||||||
|
PreviewClient *lastCreatedClient() {
|
||||||
|
return m_lastCreatedClient;
|
||||||
|
}
|
||||||
|
PreviewSettings *lastCreatedSettings() {
|
||||||
|
return m_lastCreatedSettings;
|
||||||
|
}
|
||||||
|
|
||||||
|
void registerPreviewItem(PreviewItem *item);
|
||||||
|
void unregisterPreviewItem(PreviewItem *item);
|
||||||
|
|
||||||
|
void setPlugin(const QString &plugin);
|
||||||
|
QString plugin() const;
|
||||||
|
void setTheme(const QString &theme);
|
||||||
|
QString theme() const;
|
||||||
|
bool isValid() const;
|
||||||
|
|
||||||
|
KDecoration2::Decoration *createDecoration(QObject *parent = nullptr);
|
||||||
|
|
||||||
|
Q_SIGNALS:
|
||||||
|
void pluginChanged();
|
||||||
|
void themeChanged();
|
||||||
|
void validChanged();
|
||||||
|
|
||||||
|
private:
|
||||||
|
void createFactory();
|
||||||
|
void setValid(bool valid);
|
||||||
|
PreviewClient *m_lastCreatedClient;
|
||||||
|
PreviewSettings *m_lastCreatedSettings;
|
||||||
|
QList<PreviewItem*> m_previewItems;
|
||||||
|
QString m_plugin;
|
||||||
|
QString m_theme;
|
||||||
|
QPointer<KPluginFactory> m_factory;
|
||||||
|
bool m_valid;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Q_DECLARE_METATYPE(KDecoration2::Preview::PreviewBridge *)
|
||||||
|
|
||||||
|
#endif
|
463
kcmkwin/kwindecoration/declarative-plugin/previewclient.cpp
Normal file
463
kcmkwin/kwindecoration/declarative-plugin/previewclient.cpp
Normal file
|
@ -0,0 +1,463 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#include "previewclient.h"
|
||||||
|
#include <KDecoration2/Decoration>
|
||||||
|
#include <KDecoration2/DecoratedClient>
|
||||||
|
|
||||||
|
#include <KColorScheme>
|
||||||
|
#include <KColorSchemeManager>
|
||||||
|
|
||||||
|
#include <QDebug>
|
||||||
|
#include <QModelIndex>
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
|
||||||
|
PreviewClient::PreviewClient(DecoratedClient *c, Decoration *decoration)
|
||||||
|
: QObject(decoration)
|
||||||
|
, DecoratedClientPrivate(c, decoration)
|
||||||
|
, m_colorSchemeManager(new KColorSchemeManager(this))
|
||||||
|
, m_colorSchemeIndex(0)
|
||||||
|
, m_icon(QIcon::fromTheme(QStringLiteral("start-here-kde")))
|
||||||
|
, m_iconName(m_icon.name())
|
||||||
|
, m_active(true)
|
||||||
|
, m_closeable(true)
|
||||||
|
, m_keepBelow(false)
|
||||||
|
, m_keepAbove(false)
|
||||||
|
, m_maximizable(true)
|
||||||
|
, m_maximizedHorizontally(false)
|
||||||
|
, m_maximizedVertically(false)
|
||||||
|
, m_minimizable(true)
|
||||||
|
, m_modal(false)
|
||||||
|
, m_movable(true)
|
||||||
|
, m_resizable(true)
|
||||||
|
, m_shadeable(true)
|
||||||
|
, m_shaded(false)
|
||||||
|
, m_providesContextHelp(false)
|
||||||
|
, m_desktop(1)
|
||||||
|
, m_width(0)
|
||||||
|
, m_height(0)
|
||||||
|
, m_bordersTopEdge(false)
|
||||||
|
, m_bordersLeftEdge(false)
|
||||||
|
, m_bordersRightEdge(false)
|
||||||
|
, m_bordersBottomEdge(false)
|
||||||
|
{
|
||||||
|
connect(this, &PreviewClient::captionChanged, c, &DecoratedClient::captionChanged);
|
||||||
|
connect(this, &PreviewClient::activeChanged, c, &DecoratedClient::activeChanged);
|
||||||
|
connect(this, &PreviewClient::closeableChanged, c, &DecoratedClient::closeableChanged);
|
||||||
|
connect(this, &PreviewClient::keepAboveChanged, c, &DecoratedClient::keepAboveChanged);
|
||||||
|
connect(this, &PreviewClient::keepBelowChanged, c, &DecoratedClient::keepBelowChanged);
|
||||||
|
connect(this, &PreviewClient::maximizableChanged, c, &DecoratedClient::maximizeableChanged);
|
||||||
|
connect(this, &PreviewClient::maximizedChanged, c, &DecoratedClient::maximizedChanged);
|
||||||
|
connect(this, &PreviewClient::maximizedVerticallyChanged, c, &DecoratedClient::maximizedVerticallyChanged);
|
||||||
|
connect(this, &PreviewClient::maximizedHorizontallyChanged, c, &DecoratedClient::maximizedHorizontallyChanged);
|
||||||
|
connect(this, &PreviewClient::minimizableChanged, c, &DecoratedClient::minimizeableChanged);
|
||||||
|
// connect(this, &PreviewClient::modalChanged, c, &DecoratedClient::modalChanged);
|
||||||
|
connect(this, &PreviewClient::movableChanged, c, &DecoratedClient::moveableChanged);
|
||||||
|
connect(this, &PreviewClient::onAllDesktopsChanged, c, &DecoratedClient::onAllDesktopsChanged);
|
||||||
|
connect(this, &PreviewClient::resizableChanged, c, &DecoratedClient::resizeableChanged);
|
||||||
|
connect(this, &PreviewClient::shadeableChanged, c, &DecoratedClient::shadeableChanged);
|
||||||
|
connect(this, &PreviewClient::shadedChanged, c, &DecoratedClient::shadedChanged);
|
||||||
|
connect(this, &PreviewClient::providesContextHelpChanged, c, &DecoratedClient::providesContextHelpChanged);
|
||||||
|
connect(this, &PreviewClient::onAllDesktopsChanged, c, &DecoratedClient::onAllDesktopsChanged);
|
||||||
|
connect(this, &PreviewClient::widthChanged, c, &DecoratedClient::widthChanged);
|
||||||
|
connect(this, &PreviewClient::heightChanged, c, &DecoratedClient::heightChanged);
|
||||||
|
connect(this, &PreviewClient::iconChanged, c, &DecoratedClient::iconChanged);
|
||||||
|
connect(this, &PreviewClient::paletteChanged, c, &DecoratedClient::paletteChanged);
|
||||||
|
// connect(this, &PreviewClient::, c, &DecoratedClient::);
|
||||||
|
connect(this, &PreviewClient::maximizedVerticallyChanged, this,
|
||||||
|
[this]() {
|
||||||
|
emit maximizedChanged(isMaximized());
|
||||||
|
}
|
||||||
|
);
|
||||||
|
connect(this, &PreviewClient::maximizedHorizontallyChanged, this,
|
||||||
|
[this]() {
|
||||||
|
emit maximizedChanged(isMaximized());
|
||||||
|
}
|
||||||
|
);
|
||||||
|
connect(this, &PreviewClient::iconNameChanged, this,
|
||||||
|
[this]() {
|
||||||
|
m_icon = QIcon::fromTheme(m_iconName);
|
||||||
|
emit iconChanged(m_icon);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
connect(this, &PreviewClient::desktopChanged, this,
|
||||||
|
[this]() {
|
||||||
|
emit onAllDesktopsChanged(isOnAllDesktops());
|
||||||
|
}
|
||||||
|
);
|
||||||
|
connect(this, &PreviewClient::colorSchemeIndexChanged, this,
|
||||||
|
[this]() {
|
||||||
|
const QModelIndex index = m_colorSchemeManager->model()->index(m_colorSchemeIndex, 0);
|
||||||
|
qDebug() << "Scheme: " << index.data(Qt::UserRole).toString();
|
||||||
|
m_palette = KColorScheme::createApplicationPalette(KSharedConfig::openConfig(index.data(Qt::UserRole).toString()));
|
||||||
|
emit paletteChanged(m_palette);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
connect(decoration, &Decoration::titleBarDoubleClicked, this,
|
||||||
|
[this]() {
|
||||||
|
if (!isMaximizeable()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const bool maximize = !isMaximized();
|
||||||
|
setMaximizedHorizontally(maximize);
|
||||||
|
setMaximizedVertically(maximize);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
auto emitEdgesChanged = [this, c]() {
|
||||||
|
c->borderingScreenEdgesChanged(borderingScreenEdges());
|
||||||
|
};
|
||||||
|
connect(this, &PreviewClient::bordersTopEdgeChanged, this, emitEdgesChanged);
|
||||||
|
connect(this, &PreviewClient::bordersLeftEdgeChanged, this, emitEdgesChanged);
|
||||||
|
connect(this, &PreviewClient::bordersRightEdgeChanged, this, emitEdgesChanged);
|
||||||
|
connect(this, &PreviewClient::bordersBottomEdgeChanged, this, emitEdgesChanged);
|
||||||
|
}
|
||||||
|
|
||||||
|
PreviewClient::~PreviewClient() = default;
|
||||||
|
|
||||||
|
void PreviewClient::setIcon(const QIcon &pixmap)
|
||||||
|
{
|
||||||
|
m_icon = pixmap;
|
||||||
|
emit iconChanged(m_icon);
|
||||||
|
}
|
||||||
|
|
||||||
|
int PreviewClient::width() const
|
||||||
|
{
|
||||||
|
return m_width;
|
||||||
|
}
|
||||||
|
|
||||||
|
int PreviewClient::height() const
|
||||||
|
{
|
||||||
|
return m_height;
|
||||||
|
}
|
||||||
|
|
||||||
|
QString PreviewClient::caption() const
|
||||||
|
{
|
||||||
|
return m_caption;
|
||||||
|
}
|
||||||
|
|
||||||
|
WId PreviewClient::decorationId() const
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int PreviewClient::desktop() const
|
||||||
|
{
|
||||||
|
return m_desktop;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::setDesktop(int desktop)
|
||||||
|
{
|
||||||
|
if (desktop == 0) {
|
||||||
|
desktop = 1;
|
||||||
|
}
|
||||||
|
if (m_desktop == desktop) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_desktop = desktop;
|
||||||
|
emit desktopChanged(m_desktop);
|
||||||
|
}
|
||||||
|
|
||||||
|
QIcon PreviewClient::icon() const
|
||||||
|
{
|
||||||
|
return m_icon;
|
||||||
|
}
|
||||||
|
|
||||||
|
QString PreviewClient::iconName() const
|
||||||
|
{
|
||||||
|
return m_iconName;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isActive() const
|
||||||
|
{
|
||||||
|
return m_active;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isCloseable() const
|
||||||
|
{
|
||||||
|
return m_closeable;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isKeepAbove() const
|
||||||
|
{
|
||||||
|
return m_keepAbove;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isKeepBelow() const
|
||||||
|
{
|
||||||
|
return m_keepBelow;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isMaximizeable() const
|
||||||
|
{
|
||||||
|
return m_maximizable;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isMaximized() const
|
||||||
|
{
|
||||||
|
return isMaximizedHorizontally() && isMaximizedVertically();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isMaximizedHorizontally() const
|
||||||
|
{
|
||||||
|
return m_maximizedHorizontally;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isMaximizedVertically() const
|
||||||
|
{
|
||||||
|
return m_maximizedVertically;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isMinimizeable() const
|
||||||
|
{
|
||||||
|
return m_minimizable;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isModal() const
|
||||||
|
{
|
||||||
|
return m_modal;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isMoveable() const
|
||||||
|
{
|
||||||
|
return m_movable;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isOnAllDesktops() const
|
||||||
|
{
|
||||||
|
return desktop() == -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isResizeable() const
|
||||||
|
{
|
||||||
|
return m_resizable;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isShadeable() const
|
||||||
|
{
|
||||||
|
return m_shadeable;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::isShaded() const
|
||||||
|
{
|
||||||
|
return m_shaded;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::providesContextHelp() const
|
||||||
|
{
|
||||||
|
return m_providesContextHelp;
|
||||||
|
}
|
||||||
|
|
||||||
|
WId PreviewClient::windowId() const
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
QPalette PreviewClient::palette() const
|
||||||
|
{
|
||||||
|
return m_palette;
|
||||||
|
}
|
||||||
|
|
||||||
|
QAbstractItemModel *PreviewClient::colorSchemeModel() const
|
||||||
|
{
|
||||||
|
return m_colorSchemeManager->model();
|
||||||
|
}
|
||||||
|
|
||||||
|
int PreviewClient::colorSchemeIndex() const
|
||||||
|
{
|
||||||
|
return m_colorSchemeIndex;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::setColorSchemeIndex(int index)
|
||||||
|
{
|
||||||
|
if (m_colorSchemeIndex == index) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_colorSchemeIndex = index;
|
||||||
|
emit colorSchemeIndexChanged(m_colorSchemeIndex);
|
||||||
|
}
|
||||||
|
|
||||||
|
Qt::Edges PreviewClient::borderingScreenEdges() const
|
||||||
|
{
|
||||||
|
Qt::Edges edges;
|
||||||
|
if (m_bordersBottomEdge) {
|
||||||
|
edges |= Qt::BottomEdge;
|
||||||
|
}
|
||||||
|
if (m_bordersLeftEdge) {
|
||||||
|
edges |= Qt::LeftEdge;
|
||||||
|
}
|
||||||
|
if (m_bordersRightEdge) {
|
||||||
|
edges |= Qt::RightEdge;
|
||||||
|
}
|
||||||
|
if (m_bordersTopEdge) {
|
||||||
|
edges |= Qt::TopEdge;
|
||||||
|
}
|
||||||
|
return edges;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::bordersBottomEdge() const
|
||||||
|
{
|
||||||
|
return m_bordersBottomEdge;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::bordersLeftEdge() const
|
||||||
|
{
|
||||||
|
return m_bordersLeftEdge;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::bordersRightEdge() const
|
||||||
|
{
|
||||||
|
return m_bordersRightEdge;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewClient::bordersTopEdge() const
|
||||||
|
{
|
||||||
|
return m_bordersTopEdge;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::setBordersBottomEdge(bool enabled)
|
||||||
|
{
|
||||||
|
if (m_bordersBottomEdge == enabled) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_bordersBottomEdge = enabled;
|
||||||
|
emit bordersBottomEdgeChanged(enabled);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::setBordersLeftEdge(bool enabled)
|
||||||
|
{
|
||||||
|
if (m_bordersLeftEdge == enabled) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_bordersLeftEdge = enabled;
|
||||||
|
emit bordersLeftEdgeChanged(enabled);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::setBordersRightEdge(bool enabled)
|
||||||
|
{
|
||||||
|
if (m_bordersRightEdge == enabled) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_bordersRightEdge = enabled;
|
||||||
|
emit bordersRightEdgeChanged(enabled);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::setBordersTopEdge(bool enabled)
|
||||||
|
{
|
||||||
|
if (m_bordersTopEdge == enabled) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_bordersTopEdge = enabled;
|
||||||
|
emit bordersTopEdgeChanged(enabled);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestClose()
|
||||||
|
{
|
||||||
|
emit closeRequested();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestContextHelp()
|
||||||
|
{
|
||||||
|
qDebug() << "context help requested";
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestMaximize(Qt::MouseButtons buttons)
|
||||||
|
{
|
||||||
|
if (buttons.testFlag(Qt::LeftButton)) {
|
||||||
|
const bool set = !isMaximized();
|
||||||
|
setMaximizedHorizontally(set);
|
||||||
|
setMaximizedVertically(set);
|
||||||
|
} else if (buttons.testFlag(Qt::RightButton)) {
|
||||||
|
setMaximizedHorizontally(!isMaximizedHorizontally());
|
||||||
|
} else if (buttons.testFlag(Qt::MiddleButton)) {
|
||||||
|
setMaximizedVertically(!isMaximizedVertically());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestMinimize()
|
||||||
|
{
|
||||||
|
emit minimizeRequested();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestToggleKeepAbove()
|
||||||
|
{
|
||||||
|
setKeepAbove(!isKeepAbove());
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestToggleKeepBelow()
|
||||||
|
{
|
||||||
|
setKeepBelow(!isKeepBelow());
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestShowWindowMenu()
|
||||||
|
{
|
||||||
|
emit showWindowMenuRequested();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestToggleOnAllDesktops()
|
||||||
|
{
|
||||||
|
setDesktop(isOnAllDesktops() ? 1 : -1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewClient::requestToggleShade()
|
||||||
|
{
|
||||||
|
setShaded(!isShaded());
|
||||||
|
}
|
||||||
|
|
||||||
|
#define SETTER(type, name, variable) \
|
||||||
|
void PreviewClient::name(type variable) \
|
||||||
|
{ \
|
||||||
|
if (m_##variable == variable) { \
|
||||||
|
return; \
|
||||||
|
} \
|
||||||
|
qDebug() << "Setting " << #variable << ":" << variable;\
|
||||||
|
m_##variable = variable; \
|
||||||
|
emit variable##Changed(m_##variable); \
|
||||||
|
}
|
||||||
|
|
||||||
|
#define SETTER2(name, variable) SETTER(bool, name, variable)
|
||||||
|
|
||||||
|
SETTER(const QString &, setCaption, caption)
|
||||||
|
SETTER(const QString &, setIconName, iconName)
|
||||||
|
SETTER(int, setWidth, width)
|
||||||
|
SETTER(int, setHeight, height)
|
||||||
|
|
||||||
|
SETTER2(setActive, active)
|
||||||
|
SETTER2(setCloseable, closeable)
|
||||||
|
SETTER2(setMaximizable, maximizable)
|
||||||
|
SETTER2(setKeepBelow, keepBelow)
|
||||||
|
SETTER2(setKeepAbove, keepAbove)
|
||||||
|
SETTER2(setMaximizedHorizontally, maximizedHorizontally)
|
||||||
|
SETTER2(setMaximizedVertically, maximizedVertically)
|
||||||
|
SETTER2(setMinimizable, minimizable)
|
||||||
|
SETTER2(setModal, modal)
|
||||||
|
SETTER2(setMovable, movable)
|
||||||
|
SETTER2(setResizable, resizable)
|
||||||
|
SETTER2(setShadeable, shadeable)
|
||||||
|
SETTER2(setShaded, shaded)
|
||||||
|
SETTER2(setProvidesContextHelp, providesContextHelp)
|
||||||
|
|
||||||
|
#undef SETTER2
|
||||||
|
#undef SETTER
|
||||||
|
|
||||||
|
} // namespace Preview
|
||||||
|
} // namespace KDecoration2
|
212
kcmkwin/kwindecoration/declarative-plugin/previewclient.h
Normal file
212
kcmkwin/kwindecoration/declarative-plugin/previewclient.h
Normal file
|
@ -0,0 +1,212 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#ifndef KDECOARTIONS_PREVIEW_CLIENT_H
|
||||||
|
#define KDECOARTIONS_PREVIEW_CLIENT_H
|
||||||
|
|
||||||
|
#include <KDecoration2/Private/DecoratedClientPrivate>
|
||||||
|
#include <QObject>
|
||||||
|
#include <QPalette>
|
||||||
|
|
||||||
|
class KColorSchemeManager;
|
||||||
|
class QAbstractItemModel;
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
class PreviewClient : public QObject, public DecoratedClientPrivate
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
Q_PROPERTY(KDecoration2::Decoration *decoration READ decoration CONSTANT)
|
||||||
|
Q_PROPERTY(QString caption READ caption WRITE setCaption NOTIFY captionChanged)
|
||||||
|
Q_PROPERTY(QIcon icon READ icon WRITE setIcon NOTIFY iconChanged)
|
||||||
|
Q_PROPERTY(QString iconName READ iconName WRITE setIconName NOTIFY iconNameChanged)
|
||||||
|
Q_PROPERTY(QAbstractItemModel *colorSchemeModel READ colorSchemeModel CONSTANT)
|
||||||
|
Q_PROPERTY(int colorSchemeIndex READ colorSchemeIndex WRITE setColorSchemeIndex NOTIFY colorSchemeIndexChanged)
|
||||||
|
Q_PROPERTY(bool active READ isActive WRITE setActive NOTIFY activeChanged)
|
||||||
|
Q_PROPERTY(bool closeable READ isCloseable WRITE setCloseable NOTIFY closeableChanged)
|
||||||
|
Q_PROPERTY(bool keepAbove READ isKeepAbove WRITE setKeepAbove NOTIFY keepAboveChanged)
|
||||||
|
Q_PROPERTY(bool keepBelow READ isKeepBelow WRITE setKeepBelow NOTIFY keepBelowChanged)
|
||||||
|
Q_PROPERTY(bool maximizable READ isMaximizeable WRITE setMaximizable NOTIFY maximizableChanged)
|
||||||
|
Q_PROPERTY(bool maximized READ isMaximized NOTIFY maximizedChanged)
|
||||||
|
Q_PROPERTY(bool maximizedVertically READ isMaximizedVertically WRITE setMaximizedVertically NOTIFY maximizedVerticallyChanged)
|
||||||
|
Q_PROPERTY(bool maximizedHorizontally READ isMaximizedHorizontally WRITE setMaximizedHorizontally NOTIFY maximizedHorizontallyChanged)
|
||||||
|
Q_PROPERTY(bool minimizable READ isMinimizeable WRITE setMinimizable NOTIFY minimizableChanged)
|
||||||
|
Q_PROPERTY(bool modal READ isModal WRITE setModal NOTIFY modalChanged)
|
||||||
|
Q_PROPERTY(bool movable READ isMoveable WRITE setMovable NOTIFY movableChanged)
|
||||||
|
Q_PROPERTY(int desktop READ desktop WRITE setDesktop NOTIFY desktopChanged)
|
||||||
|
Q_PROPERTY(bool onAllDesktops READ isOnAllDesktops NOTIFY onAllDesktopsChanged)
|
||||||
|
Q_PROPERTY(bool resizable READ isResizeable WRITE setResizable NOTIFY resizableChanged)
|
||||||
|
Q_PROPERTY(bool shadeable READ isShadeable WRITE setShadeable NOTIFY shadeableChanged)
|
||||||
|
Q_PROPERTY(bool shaded READ isShaded WRITE setShaded NOTIFY shadedChanged)
|
||||||
|
Q_PROPERTY(bool providesContextHelp READ providesContextHelp WRITE setProvidesContextHelp NOTIFY providesContextHelpChanged)
|
||||||
|
Q_PROPERTY(int width READ width WRITE setWidth NOTIFY widthChanged)
|
||||||
|
Q_PROPERTY(int height READ height WRITE setHeight NOTIFY heightChanged)
|
||||||
|
Q_PROPERTY(bool bordersTopEdge READ bordersTopEdge WRITE setBordersTopEdge NOTIFY bordersTopEdgeChanged)
|
||||||
|
Q_PROPERTY(bool bordersLeftEdge READ bordersLeftEdge WRITE setBordersLeftEdge NOTIFY bordersLeftEdgeChanged)
|
||||||
|
Q_PROPERTY(bool bordersRightEdge READ bordersRightEdge WRITE setBordersRightEdge NOTIFY bordersRightEdgeChanged)
|
||||||
|
Q_PROPERTY(bool bordersBottomEdge READ bordersBottomEdge WRITE setBordersBottomEdge NOTIFY bordersBottomEdgeChanged)
|
||||||
|
public:
|
||||||
|
explicit PreviewClient(DecoratedClient *client, Decoration *decoration);
|
||||||
|
virtual ~PreviewClient();
|
||||||
|
|
||||||
|
QString caption() const override;
|
||||||
|
WId decorationId() const override;
|
||||||
|
WId windowId() const override;
|
||||||
|
int desktop() const override;
|
||||||
|
QIcon icon() const override;
|
||||||
|
bool isActive() const override;
|
||||||
|
bool isCloseable() const override;
|
||||||
|
bool isKeepAbove() const override;
|
||||||
|
bool isKeepBelow() const override;
|
||||||
|
bool isMaximizeable() const override;
|
||||||
|
bool isMaximized() const override;
|
||||||
|
bool isMaximizedVertically() const override;
|
||||||
|
bool isMaximizedHorizontally() const override;
|
||||||
|
bool isMinimizeable() const override;
|
||||||
|
bool isModal() const override;
|
||||||
|
bool isMoveable() const override;
|
||||||
|
bool isOnAllDesktops() const override;
|
||||||
|
bool isResizeable() const override;
|
||||||
|
bool isShadeable() const override;
|
||||||
|
bool isShaded() const override;
|
||||||
|
bool providesContextHelp() const override;
|
||||||
|
|
||||||
|
int width() const override;
|
||||||
|
int height() const override;
|
||||||
|
QPalette palette() const override;
|
||||||
|
Qt::Edges borderingScreenEdges() const override;
|
||||||
|
|
||||||
|
void requestClose() override;
|
||||||
|
void requestContextHelp() override;
|
||||||
|
void requestMaximize(Qt::MouseButtons buttons) override;
|
||||||
|
void requestMinimize() override;
|
||||||
|
void requestToggleKeepAbove() override;
|
||||||
|
void requestToggleKeepBelow() override;
|
||||||
|
void requestToggleShade() override;
|
||||||
|
void requestShowWindowMenu() override;
|
||||||
|
void requestToggleOnAllDesktops() override;
|
||||||
|
|
||||||
|
void setCaption(const QString &caption);
|
||||||
|
void setActive(bool active);
|
||||||
|
void setCloseable(bool closeable);
|
||||||
|
void setMaximizable(bool maximizable);
|
||||||
|
void setKeepBelow(bool keepBelow);
|
||||||
|
void setKeepAbove(bool keepAbove);
|
||||||
|
void setMaximizedHorizontally(bool maximized);
|
||||||
|
void setMaximizedVertically(bool maximized);
|
||||||
|
void setMinimizable(bool minimizable);
|
||||||
|
void setModal(bool modal);
|
||||||
|
void setMovable(bool movable);
|
||||||
|
void setResizable(bool resizable);
|
||||||
|
void setShadeable(bool shadeable);
|
||||||
|
void setShaded(bool shaded);
|
||||||
|
void setProvidesContextHelp(bool contextHelp);
|
||||||
|
void setDesktop(int desktop);
|
||||||
|
|
||||||
|
void setWidth(int width);
|
||||||
|
void setHeight(int height);
|
||||||
|
|
||||||
|
QString iconName() const;
|
||||||
|
void setIconName(const QString &icon);
|
||||||
|
void setIcon(const QIcon &icon);
|
||||||
|
|
||||||
|
QAbstractItemModel *colorSchemeModel() const;
|
||||||
|
int colorSchemeIndex() const;
|
||||||
|
void setColorSchemeIndex(int index);
|
||||||
|
|
||||||
|
bool bordersTopEdge() const;
|
||||||
|
bool bordersLeftEdge() const;
|
||||||
|
bool bordersRightEdge() const;
|
||||||
|
bool bordersBottomEdge() const;
|
||||||
|
|
||||||
|
void setBordersTopEdge(bool enabled);
|
||||||
|
void setBordersLeftEdge(bool enabled);
|
||||||
|
void setBordersRightEdge(bool enabled);
|
||||||
|
void setBordersBottomEdge(bool enabled);
|
||||||
|
|
||||||
|
Q_SIGNALS:
|
||||||
|
void captionChanged(const QString &);
|
||||||
|
void iconChanged(const QIcon &);
|
||||||
|
void iconNameChanged(const QString &);
|
||||||
|
void activeChanged(bool);
|
||||||
|
void closeableChanged(bool);
|
||||||
|
void keepAboveChanged(bool);
|
||||||
|
void keepBelowChanged(bool);
|
||||||
|
void maximizableChanged(bool);
|
||||||
|
void maximizedChanged(bool);
|
||||||
|
void maximizedVerticallyChanged(bool);
|
||||||
|
void maximizedHorizontallyChanged(bool);
|
||||||
|
void minimizableChanged(bool);
|
||||||
|
void modalChanged(bool);
|
||||||
|
void movableChanged(bool);
|
||||||
|
void onAllDesktopsChanged(bool);
|
||||||
|
void resizableChanged(bool);
|
||||||
|
void shadeableChanged(bool);
|
||||||
|
void shadedChanged(bool);
|
||||||
|
void providesContextHelpChanged(bool);
|
||||||
|
void desktopChanged(int);
|
||||||
|
void widthChanged(int);
|
||||||
|
void heightChanged(int);
|
||||||
|
void colorSchemeIndexChanged(int);
|
||||||
|
void paletteChanged(const QPalette&);
|
||||||
|
void bordersTopEdgeChanged(bool);
|
||||||
|
void bordersLeftEdgeChanged(bool);
|
||||||
|
void bordersRightEdgeChanged(bool);
|
||||||
|
void bordersBottomEdgeChanged(bool);
|
||||||
|
|
||||||
|
void showWindowMenuRequested();
|
||||||
|
void minimizeRequested();
|
||||||
|
void closeRequested();
|
||||||
|
|
||||||
|
private:
|
||||||
|
KColorSchemeManager *m_colorSchemeManager;
|
||||||
|
int m_colorSchemeIndex;
|
||||||
|
QString m_caption;
|
||||||
|
QIcon m_icon;
|
||||||
|
QString m_iconName;
|
||||||
|
QPalette m_palette;
|
||||||
|
bool m_active;
|
||||||
|
bool m_closeable;
|
||||||
|
bool m_keepBelow;
|
||||||
|
bool m_keepAbove;
|
||||||
|
bool m_maximizable;
|
||||||
|
bool m_maximizedHorizontally;
|
||||||
|
bool m_maximizedVertically;
|
||||||
|
bool m_minimizable;
|
||||||
|
bool m_modal;
|
||||||
|
bool m_movable;
|
||||||
|
bool m_resizable;
|
||||||
|
bool m_shadeable;
|
||||||
|
bool m_shaded;
|
||||||
|
bool m_providesContextHelp;
|
||||||
|
int m_desktop;
|
||||||
|
int m_width;
|
||||||
|
int m_height;
|
||||||
|
bool m_bordersTopEdge;
|
||||||
|
bool m_bordersLeftEdge;
|
||||||
|
bool m_bordersRightEdge;
|
||||||
|
bool m_bordersBottomEdge;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace Preview
|
||||||
|
} // namespace KDecoration2
|
||||||
|
|
||||||
|
#endif
|
374
kcmkwin/kwindecoration/declarative-plugin/previewitem.cpp
Normal file
374
kcmkwin/kwindecoration/declarative-plugin/previewitem.cpp
Normal file
|
@ -0,0 +1,374 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#include "previewitem.h"
|
||||||
|
#include "previewbridge.h"
|
||||||
|
#include "previewsettings.h"
|
||||||
|
#include "previewclient.h"
|
||||||
|
#include <KDecoration2/Decoration>
|
||||||
|
#include <KDecoration2/DecorationSettings>
|
||||||
|
#include <KDecoration2/DecorationShadow>
|
||||||
|
#include <KDecoration2/DecoratedClient>
|
||||||
|
#include <QCursor>
|
||||||
|
#include <QPainter>
|
||||||
|
#include <QQmlContext>
|
||||||
|
#include <QQmlEngine>
|
||||||
|
|
||||||
|
#include <QDebug>
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
|
||||||
|
PreviewItem::PreviewItem(QQuickItem *parent)
|
||||||
|
: QQuickPaintedItem(parent)
|
||||||
|
, m_decoration(nullptr)
|
||||||
|
, m_windowColor(QPalette().background().color())
|
||||||
|
{
|
||||||
|
setAcceptHoverEvents(true);
|
||||||
|
setFiltersChildMouseEvents(true);
|
||||||
|
setAcceptedMouseButtons(Qt::MouseButtons(~Qt::NoButton));
|
||||||
|
connect(this, &PreviewItem::widthChanged, this, &PreviewItem::syncSize);
|
||||||
|
connect(this, &PreviewItem::heightChanged, this, &PreviewItem::syncSize);
|
||||||
|
connect(this, &PreviewItem::bridgeChanged, this, &PreviewItem::createDecoration);
|
||||||
|
connect(this, &PreviewItem::settingsChanged, this, &PreviewItem::createDecoration);
|
||||||
|
}
|
||||||
|
|
||||||
|
PreviewItem::~PreviewItem()
|
||||||
|
{
|
||||||
|
if (m_bridge){
|
||||||
|
m_bridge->unregisterPreviewItem(this);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::componentComplete()
|
||||||
|
{
|
||||||
|
QQuickPaintedItem::componentComplete();
|
||||||
|
createDecoration();
|
||||||
|
if (m_decoration) {
|
||||||
|
m_decoration->setSettings(m_settings->settings());
|
||||||
|
m_decoration->init();
|
||||||
|
syncSize();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::createDecoration()
|
||||||
|
{
|
||||||
|
if (m_bridge.isNull() || m_settings.isNull() || m_decoration) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_decoration = m_bridge->createDecoration(this);
|
||||||
|
if (!m_decoration) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_decoration->setProperty("visualParent", QVariant::fromValue(this));
|
||||||
|
m_client = m_bridge->lastCreatedClient();
|
||||||
|
connect(m_decoration, &Decoration::bordersChanged, this, &PreviewItem::syncSize);
|
||||||
|
connect(m_decoration, &Decoration::shadowChanged, this, &PreviewItem::syncSize);
|
||||||
|
emit decorationChanged(m_decoration);
|
||||||
|
}
|
||||||
|
|
||||||
|
Decoration *PreviewItem::decoration() const
|
||||||
|
{
|
||||||
|
return m_decoration;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::setDecoration(Decoration *deco)
|
||||||
|
{
|
||||||
|
if (m_decoration == deco) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
auto updateSlot = static_cast<void (QQuickItem::*)()>(&QQuickItem::update);
|
||||||
|
if (m_decoration) {
|
||||||
|
disconnect(m_decoration, &Decoration::bordersChanged, this, updateSlot);
|
||||||
|
}
|
||||||
|
m_decoration = deco;
|
||||||
|
m_decoration->setProperty("visualParent", QVariant::fromValue(this));
|
||||||
|
connect(m_decoration, &Decoration::bordersChanged, this, updateSlot);
|
||||||
|
connect(m_decoration, &Decoration::windowFrameSectionChanged, this,
|
||||||
|
[this](Qt::WindowFrameSection section) {
|
||||||
|
switch (section) {
|
||||||
|
case Qt::TopRightSection:
|
||||||
|
case Qt::BottomLeftSection:
|
||||||
|
setCursor(Qt::SizeBDiagCursor);
|
||||||
|
return;
|
||||||
|
case Qt::TopLeftSection:
|
||||||
|
case Qt::BottomRightSection:
|
||||||
|
setCursor(Qt::SizeFDiagCursor);
|
||||||
|
return;
|
||||||
|
case Qt::TopSection:
|
||||||
|
case Qt::BottomSection:
|
||||||
|
setCursor(Qt::SizeVerCursor);
|
||||||
|
return;
|
||||||
|
case Qt::LeftSection:
|
||||||
|
case Qt::RightSection:
|
||||||
|
setCursor(Qt::SizeHorCursor);
|
||||||
|
return;
|
||||||
|
default:
|
||||||
|
setCursor(Qt::ArrowCursor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
);
|
||||||
|
emit decorationChanged(m_decoration);
|
||||||
|
}
|
||||||
|
|
||||||
|
QColor PreviewItem::windowColor() const
|
||||||
|
{
|
||||||
|
return m_windowColor;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::setWindowColor(const QColor &color)
|
||||||
|
{
|
||||||
|
if (m_windowColor == color) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_windowColor = color;
|
||||||
|
emit windowColorChanged(m_windowColor);
|
||||||
|
update();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::paint(QPainter *painter)
|
||||||
|
{
|
||||||
|
if (!m_decoration) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
int paddingLeft = 0;
|
||||||
|
int paddingTop = 0;
|
||||||
|
int paddingRight = 0;
|
||||||
|
int paddingBottom = 0;
|
||||||
|
paintShadow(painter, paddingLeft, paddingRight, paddingTop, paddingBottom);
|
||||||
|
m_decoration->paint(painter);
|
||||||
|
if (m_drawBackground) {
|
||||||
|
painter->fillRect(m_decoration->borderLeft(), m_decoration->borderTop(),
|
||||||
|
width() - m_decoration->borderLeft() - m_decoration->borderRight() - paddingLeft - paddingRight,
|
||||||
|
height() - m_decoration->borderTop() - m_decoration->borderBottom() - paddingTop - paddingBottom,
|
||||||
|
m_windowColor);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::paintShadow(QPainter *painter, int &paddingLeft, int &paddingRight, int &paddingTop, int &paddingBottom)
|
||||||
|
{
|
||||||
|
const DecorationShadow *shadow = ((const Decoration*)(m_decoration))->shadow();
|
||||||
|
if (!shadow) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
paddingLeft = shadow->paddingLeft();
|
||||||
|
paddingTop = shadow->paddingTop();
|
||||||
|
paddingRight = shadow->paddingRight();
|
||||||
|
paddingBottom = shadow->paddingBottom();
|
||||||
|
const QImage img = shadow->shadow();
|
||||||
|
if (img.isNull()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const QRect topLeft = QRect(QPoint(0, 0), shadow->topLeft());
|
||||||
|
const QRect top = QRect(QPoint(topLeft.width(), 0), shadow->top());
|
||||||
|
const QRect topRight = QRect(QPoint(topLeft.width() + top.width(), 0), shadow->topRight());
|
||||||
|
const QRect right = QRect(QPoint(topLeft.width() + top.width(), topRight.height()), shadow->right());
|
||||||
|
const QRect left = QRect(QPoint(0, topLeft.height()), shadow->left());
|
||||||
|
const QRect bottomLeft = QRect(QPoint(0, topLeft.height() + left.height()), shadow->bottomLeft());
|
||||||
|
const QRect bottom = QRect(QPoint(bottomLeft.width(), img.height() - shadow->bottom().height()), shadow->bottom());
|
||||||
|
const QRect bottomRight = QRect(QPoint(bottomLeft.width() + bottom.width(), topRight.height() + right.height()), shadow->bottomRight());
|
||||||
|
|
||||||
|
painter->translate(paddingLeft, paddingTop);
|
||||||
|
|
||||||
|
// top left
|
||||||
|
painter->drawImage(QPoint(-paddingLeft, -paddingTop), img, topLeft);
|
||||||
|
// top
|
||||||
|
painter->drawImage(QRect(-paddingLeft + topLeft.width(), -paddingTop, width() - topLeft.width() - topRight.width(), top.height()), img, top);
|
||||||
|
// top right
|
||||||
|
painter->drawImage(QPoint(width() - topRight.width() - paddingLeft, -paddingTop), img, topRight);
|
||||||
|
// right
|
||||||
|
painter->drawImage(QRect(width() - right.width() - paddingLeft, -paddingTop + topRight.height(), right.width(), height() - topRight.height() - bottomRight.height()), img, right);
|
||||||
|
// bottom right
|
||||||
|
painter->drawImage(QPoint(width() - paddingLeft - bottomRight.width(), height() - paddingTop - bottomRight.height()), img, bottomRight);
|
||||||
|
// bottom
|
||||||
|
painter->drawImage(QRect(-paddingLeft + bottomLeft.width(), height() - bottom.height() - paddingTop, width() - bottomLeft.width() - bottomRight.width(), bottom.height()), img, bottom);
|
||||||
|
// bottom left
|
||||||
|
painter->drawImage(QPoint(-paddingLeft, height() - bottomLeft.height() - paddingTop), img, bottomLeft);
|
||||||
|
// left
|
||||||
|
painter->drawImage(QRect(-paddingLeft, -paddingTop + topLeft.height(), left.width(), height() - topLeft.height() - bottomLeft.height()), img, left);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::mouseDoubleClickEvent(QMouseEvent *event)
|
||||||
|
{
|
||||||
|
if (const DecorationShadow *shadow = ((const Decoration*)(m_decoration))->shadow()) {
|
||||||
|
QMouseEvent e(event->type(),
|
||||||
|
event->localPos() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->button(),
|
||||||
|
event->buttons(),
|
||||||
|
event->modifiers());
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), &e);
|
||||||
|
} else {
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), event);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::mousePressEvent(QMouseEvent *event)
|
||||||
|
{
|
||||||
|
if (const DecorationShadow *shadow = ((const Decoration*)(m_decoration))->shadow()) {
|
||||||
|
QMouseEvent e(event->type(),
|
||||||
|
event->localPos() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->button(),
|
||||||
|
event->buttons(),
|
||||||
|
event->modifiers());
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), &e);
|
||||||
|
} else {
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), event);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::mouseReleaseEvent(QMouseEvent *event)
|
||||||
|
{
|
||||||
|
if (const DecorationShadow *shadow = ((const Decoration*)(m_decoration))->shadow()) {
|
||||||
|
QMouseEvent e(event->type(),
|
||||||
|
event->localPos() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->button(),
|
||||||
|
event->buttons(),
|
||||||
|
event->modifiers());
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), &e);
|
||||||
|
} else {
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), event);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::mouseMoveEvent(QMouseEvent *event)
|
||||||
|
{
|
||||||
|
if (const DecorationShadow *shadow = ((const Decoration*)(m_decoration))->shadow()) {
|
||||||
|
QMouseEvent e(event->type(),
|
||||||
|
event->localPos() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->button(),
|
||||||
|
event->buttons(),
|
||||||
|
event->modifiers());
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), &e);
|
||||||
|
} else {
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), event);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::hoverEnterEvent(QHoverEvent *event)
|
||||||
|
{
|
||||||
|
if (const DecorationShadow *shadow = ((const Decoration*)(m_decoration))->shadow()) {
|
||||||
|
QHoverEvent e(event->type(),
|
||||||
|
event->posF() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->oldPosF() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->modifiers());
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), &e);
|
||||||
|
} else {
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), event);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::hoverLeaveEvent(QHoverEvent *event)
|
||||||
|
{
|
||||||
|
if (const DecorationShadow *shadow = ((const Decoration*)(m_decoration))->shadow()) {
|
||||||
|
QHoverEvent e(event->type(),
|
||||||
|
event->posF() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->oldPosF() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->modifiers());
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), &e);
|
||||||
|
} else {
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), event);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::hoverMoveEvent(QHoverEvent *event)
|
||||||
|
{
|
||||||
|
if (const DecorationShadow *shadow = ((const Decoration*)(m_decoration))->shadow()) {
|
||||||
|
QHoverEvent e(event->type(),
|
||||||
|
event->posF() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->oldPosF() - QPointF(shadow->paddingLeft(), shadow->paddingTop()),
|
||||||
|
event->modifiers());
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), &e);
|
||||||
|
} else {
|
||||||
|
QCoreApplication::instance()->sendEvent(decoration(), event);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewItem::isDrawingBackground() const
|
||||||
|
{
|
||||||
|
return m_drawBackground;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::setDrawingBackground(bool set)
|
||||||
|
{
|
||||||
|
if (m_drawBackground == set) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_drawBackground = set;
|
||||||
|
emit drawingBackgroundChanged(set);
|
||||||
|
}
|
||||||
|
|
||||||
|
PreviewBridge *PreviewItem::bridge() const
|
||||||
|
{
|
||||||
|
return m_bridge.data();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::setBridge(PreviewBridge *bridge)
|
||||||
|
{
|
||||||
|
if (m_bridge == bridge) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (m_bridge) {
|
||||||
|
m_bridge->unregisterPreviewItem(this);
|
||||||
|
}
|
||||||
|
m_bridge = bridge;
|
||||||
|
if (m_bridge) {
|
||||||
|
m_bridge->registerPreviewItem(this);
|
||||||
|
}
|
||||||
|
emit bridgeChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
Settings *PreviewItem::settings() const
|
||||||
|
{
|
||||||
|
return m_settings.data();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::setSettings(Settings *settings)
|
||||||
|
{
|
||||||
|
if (m_settings == settings) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_settings = settings;
|
||||||
|
emit settingsChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
PreviewClient *PreviewItem::client()
|
||||||
|
{
|
||||||
|
return m_client.data();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewItem::syncSize()
|
||||||
|
{
|
||||||
|
if (!m_client) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
int widthOffset = 0;
|
||||||
|
int heightOffset = 0;
|
||||||
|
auto shadow = m_decoration->shadow();
|
||||||
|
if (shadow) {
|
||||||
|
widthOffset = shadow->paddingLeft() + shadow->paddingRight();
|
||||||
|
heightOffset = shadow->paddingTop() + shadow->paddingBottom();
|
||||||
|
}
|
||||||
|
m_client->setWidth(width() - m_decoration->borderLeft() - m_decoration->borderRight() - widthOffset);
|
||||||
|
m_client->setHeight(height() - m_decoration->borderTop() - m_decoration->borderBottom() - heightOffset);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
100
kcmkwin/kwindecoration/declarative-plugin/previewitem.h
Normal file
100
kcmkwin/kwindecoration/declarative-plugin/previewitem.h
Normal file
|
@ -0,0 +1,100 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#ifndef KDECOARTIONS_PREVIEW_ITEM_H
|
||||||
|
#define KDECOARTIONS_PREVIEW_ITEM_H
|
||||||
|
|
||||||
|
#include <QQuickPaintedItem>
|
||||||
|
#include <QPointer>
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
class Decoration;
|
||||||
|
class DecorationSettings;
|
||||||
|
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
class PreviewBridge;
|
||||||
|
class PreviewClient;
|
||||||
|
class Settings;
|
||||||
|
|
||||||
|
class PreviewItem : public QQuickPaintedItem
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
Q_PROPERTY(KDecoration2::Decoration *decoration READ decoration NOTIFY decorationChanged)
|
||||||
|
Q_PROPERTY(KDecoration2::Preview::PreviewBridge *bridge READ bridge WRITE setBridge NOTIFY bridgeChanged)
|
||||||
|
Q_PROPERTY(KDecoration2::Preview::Settings *settings READ settings WRITE setSettings NOTIFY settingsChanged)
|
||||||
|
Q_PROPERTY(KDecoration2::Preview::PreviewClient *client READ client)
|
||||||
|
Q_PROPERTY(QColor windowColor READ windowColor WRITE setWindowColor NOTIFY windowColorChanged)
|
||||||
|
Q_PROPERTY(bool drawBackground READ isDrawingBackground WRITE setDrawingBackground NOTIFY drawingBackgroundChanged)
|
||||||
|
public:
|
||||||
|
PreviewItem(QQuickItem *parent = nullptr);
|
||||||
|
virtual ~PreviewItem();
|
||||||
|
void paint(QPainter *painter);
|
||||||
|
|
||||||
|
KDecoration2::Decoration *decoration() const;
|
||||||
|
void setDecoration(KDecoration2::Decoration *deco);
|
||||||
|
|
||||||
|
QColor windowColor() const;
|
||||||
|
void setWindowColor(const QColor &color);
|
||||||
|
|
||||||
|
bool isDrawingBackground() const;
|
||||||
|
void setDrawingBackground(bool set);
|
||||||
|
|
||||||
|
PreviewBridge *bridge() const;
|
||||||
|
void setBridge(PreviewBridge *bridge);
|
||||||
|
|
||||||
|
Settings *settings() const;
|
||||||
|
void setSettings(Settings *settings);
|
||||||
|
|
||||||
|
PreviewClient *client();
|
||||||
|
|
||||||
|
Q_SIGNALS:
|
||||||
|
void decorationChanged(KDecoration2::Decoration *deco);
|
||||||
|
void windowColorChanged(const QColor &color);
|
||||||
|
void drawingBackgroundChanged(bool);
|
||||||
|
void bridgeChanged();
|
||||||
|
void settingsChanged();
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void mouseDoubleClickEvent(QMouseEvent *event) override;
|
||||||
|
void mouseMoveEvent(QMouseEvent *event) override;
|
||||||
|
void mousePressEvent(QMouseEvent *event) override;
|
||||||
|
void mouseReleaseEvent(QMouseEvent *event) override;
|
||||||
|
void hoverEnterEvent(QHoverEvent *event) override;
|
||||||
|
void hoverLeaveEvent(QHoverEvent *event) override;
|
||||||
|
void hoverMoveEvent(QHoverEvent *event) override;
|
||||||
|
void componentComplete() override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
void paintShadow(QPainter *painter, int &paddingLeft, int &paddingRight, int &paddingTop, int &paddingBottom);
|
||||||
|
void syncSize();
|
||||||
|
void createDecoration();
|
||||||
|
Decoration *m_decoration;
|
||||||
|
QColor m_windowColor;
|
||||||
|
bool m_drawBackground = true;
|
||||||
|
QPointer<KDecoration2::Preview::PreviewBridge> m_bridge;
|
||||||
|
QPointer<KDecoration2::Preview::Settings> m_settings;
|
||||||
|
QPointer<KDecoration2::Preview::PreviewClient> m_client;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // Preview
|
||||||
|
} // KDecoration2
|
||||||
|
|
||||||
|
#endif
|
325
kcmkwin/kwindecoration/declarative-plugin/previewsettings.cpp
Normal file
325
kcmkwin/kwindecoration/declarative-plugin/previewsettings.cpp
Normal file
|
@ -0,0 +1,325 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#include "previewsettings.h"
|
||||||
|
#include "previewbridge.h"
|
||||||
|
|
||||||
|
#include <QFontDatabase>
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
|
||||||
|
ButtonsModel::ButtonsModel(const QList< DecorationButtonType > &buttons, QObject *parent)
|
||||||
|
: QAbstractListModel(parent)
|
||||||
|
, m_buttons(buttons)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
ButtonsModel::~ButtonsModel() = default;
|
||||||
|
|
||||||
|
int ButtonsModel::rowCount(const QModelIndex &parent) const
|
||||||
|
{
|
||||||
|
if (parent.isValid()) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return m_buttons.count();
|
||||||
|
}
|
||||||
|
|
||||||
|
QVariant ButtonsModel::data(const QModelIndex &index, int role) const
|
||||||
|
{
|
||||||
|
if (!index.isValid() ||
|
||||||
|
index.row() < 0 ||
|
||||||
|
index.row() >= m_buttons.count() ||
|
||||||
|
index.column() != 0) {
|
||||||
|
return QVariant();
|
||||||
|
}
|
||||||
|
switch (role) {
|
||||||
|
case Qt::DisplayRole:
|
||||||
|
return QVariant::fromValue(m_buttons.at(index.row()));
|
||||||
|
case Qt::UserRole:
|
||||||
|
return QVariant::fromValue(m_buttons.at(index.row()));
|
||||||
|
}
|
||||||
|
return QVariant();
|
||||||
|
}
|
||||||
|
|
||||||
|
QHash< int, QByteArray > ButtonsModel::roleNames() const
|
||||||
|
{
|
||||||
|
QHash<int, QByteArray> roles;
|
||||||
|
roles.insert(Qt::DisplayRole, QByteArrayLiteral("display"));
|
||||||
|
return roles;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ButtonsModel::remove(int row)
|
||||||
|
{
|
||||||
|
if (row < 0 || row >= m_buttons.count()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
beginRemoveRows(QModelIndex(), row, row);
|
||||||
|
m_buttons.removeAt(row);
|
||||||
|
endRemoveRows();
|
||||||
|
}
|
||||||
|
|
||||||
|
void ButtonsModel::down(int index)
|
||||||
|
{
|
||||||
|
if (m_buttons.count() < 2 || index == m_buttons.count() -1) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
beginMoveRows(QModelIndex(), index, index, QModelIndex(), index + 2);
|
||||||
|
m_buttons.move(index, index + 1);
|
||||||
|
endMoveRows();
|
||||||
|
}
|
||||||
|
|
||||||
|
void ButtonsModel::up(int index)
|
||||||
|
{
|
||||||
|
if (m_buttons.count() < 2 || index == 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
beginMoveRows(QModelIndex(), index, index, QModelIndex(), index -1);
|
||||||
|
m_buttons.move(index, index - 1);
|
||||||
|
endMoveRows();
|
||||||
|
}
|
||||||
|
|
||||||
|
void ButtonsModel::add(DecorationButtonType type)
|
||||||
|
{
|
||||||
|
beginInsertRows(QModelIndex(), m_buttons.count(), m_buttons.count());
|
||||||
|
m_buttons.append(type);
|
||||||
|
endInsertRows();
|
||||||
|
}
|
||||||
|
|
||||||
|
BorderSizesModel::BorderSizesModel(QObject *parent)
|
||||||
|
: QAbstractListModel(parent)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
BorderSizesModel::~BorderSizesModel() = default;
|
||||||
|
|
||||||
|
QVariant BorderSizesModel::data(const QModelIndex &index, int role) const
|
||||||
|
{
|
||||||
|
if (!index.isValid() || index.row() < 0 || index.row() >= m_borders.count() || index.column() != 0) {
|
||||||
|
return QVariant();
|
||||||
|
}
|
||||||
|
if (role != Qt::DisplayRole && role != Qt::UserRole) {
|
||||||
|
return QVariant();
|
||||||
|
}
|
||||||
|
return QVariant::fromValue<BorderSize>(m_borders.at(index.row()));
|
||||||
|
}
|
||||||
|
|
||||||
|
int BorderSizesModel::rowCount(const QModelIndex &parent) const
|
||||||
|
{
|
||||||
|
if (parent.isValid()) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return m_borders.count();
|
||||||
|
}
|
||||||
|
|
||||||
|
QHash< int, QByteArray > BorderSizesModel::roleNames() const
|
||||||
|
{
|
||||||
|
QHash<int, QByteArray> roles;
|
||||||
|
roles.insert(Qt::DisplayRole, QByteArrayLiteral("display"));
|
||||||
|
return roles;
|
||||||
|
}
|
||||||
|
|
||||||
|
PreviewSettings::PreviewSettings(DecorationSettings *parent)
|
||||||
|
: QObject()
|
||||||
|
, DecorationSettingsPrivate(parent)
|
||||||
|
, m_alphaChannelSupported(true)
|
||||||
|
, m_onAllDesktopsAvailable(true)
|
||||||
|
, m_closeOnDoubleClick(false)
|
||||||
|
, m_leftButtons(new ButtonsModel(QList<DecorationButtonType>({
|
||||||
|
DecorationButtonType::Menu,
|
||||||
|
DecorationButtonType::OnAllDesktops
|
||||||
|
}), this))
|
||||||
|
, m_rightButtons(new ButtonsModel(QList<DecorationButtonType>({
|
||||||
|
DecorationButtonType::QuickHelp,
|
||||||
|
DecorationButtonType::Minimize,
|
||||||
|
DecorationButtonType::Maximize,
|
||||||
|
DecorationButtonType::Close
|
||||||
|
}), this))
|
||||||
|
, m_availableButtons(new ButtonsModel(QList<DecorationButtonType>({
|
||||||
|
DecorationButtonType::Menu,
|
||||||
|
DecorationButtonType::ApplicationMenu,
|
||||||
|
DecorationButtonType::OnAllDesktops,
|
||||||
|
DecorationButtonType::Minimize,
|
||||||
|
DecorationButtonType::Maximize,
|
||||||
|
DecorationButtonType::Close,
|
||||||
|
DecorationButtonType::QuickHelp,
|
||||||
|
DecorationButtonType::Shade,
|
||||||
|
DecorationButtonType::KeepBelow,
|
||||||
|
DecorationButtonType::KeepAbove
|
||||||
|
}), this))
|
||||||
|
, m_borderSizes(new BorderSizesModel(this))
|
||||||
|
, m_borderSize(int(BorderSize::Normal))
|
||||||
|
, m_font(QFontDatabase::systemFont(QFontDatabase::TitleFont))
|
||||||
|
{
|
||||||
|
connect(this, &PreviewSettings::alphaChannelSupportedChanged, parent, &DecorationSettings::alphaChannelSupportedChanged);
|
||||||
|
connect(this, &PreviewSettings::onAllDesktopsAvailableChanged, parent, &DecorationSettings::onAllDesktopsAvailableChanged);
|
||||||
|
connect(this, &PreviewSettings::closeOnDoubleClickOnMenuChanged, parent, &DecorationSettings::closeOnDoubleClickOnMenuChanged);
|
||||||
|
connect(this, &PreviewSettings::fontChanged, parent, &DecorationSettings::fontChanged);
|
||||||
|
auto updateLeft = [this, parent]() {
|
||||||
|
parent->decorationButtonsLeftChanged(decorationButtonsLeft());
|
||||||
|
};
|
||||||
|
auto updateRight = [this, parent]() {
|
||||||
|
parent->decorationButtonsRightChanged(decorationButtonsRight());
|
||||||
|
};
|
||||||
|
connect(m_leftButtons, &QAbstractItemModel::rowsRemoved, this, updateLeft);
|
||||||
|
connect(m_leftButtons, &QAbstractItemModel::rowsMoved, this, updateLeft);
|
||||||
|
connect(m_leftButtons, &QAbstractItemModel::rowsInserted, this, updateLeft);
|
||||||
|
connect(m_rightButtons, &QAbstractItemModel::rowsRemoved, this, updateRight);
|
||||||
|
connect(m_rightButtons, &QAbstractItemModel::rowsMoved, this, updateRight);
|
||||||
|
connect(m_rightButtons, &QAbstractItemModel::rowsInserted, this, updateRight);
|
||||||
|
}
|
||||||
|
|
||||||
|
PreviewSettings::~PreviewSettings() = default;
|
||||||
|
|
||||||
|
bool PreviewSettings::isAlphaChannelSupported() const
|
||||||
|
{
|
||||||
|
return m_alphaChannelSupported;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PreviewSettings::isOnAllDesktopsAvailable() const
|
||||||
|
{
|
||||||
|
return m_onAllDesktopsAvailable;
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewSettings::setAlphaChannelSupported(bool supported)
|
||||||
|
{
|
||||||
|
if (m_alphaChannelSupported == supported) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_alphaChannelSupported = supported;
|
||||||
|
emit alphaChannelSupportedChanged(m_alphaChannelSupported);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewSettings::setOnAllDesktopsAvailable(bool available)
|
||||||
|
{
|
||||||
|
if (m_onAllDesktopsAvailable == available) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_onAllDesktopsAvailable = available;
|
||||||
|
emit onAllDesktopsAvailableChanged(m_onAllDesktopsAvailable);
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewSettings::setCloseOnDoubleClickOnMenu(bool enabled)
|
||||||
|
{
|
||||||
|
if (m_closeOnDoubleClick == enabled) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_closeOnDoubleClick = enabled;
|
||||||
|
emit closeOnDoubleClickOnMenuChanged(enabled);
|
||||||
|
}
|
||||||
|
|
||||||
|
QList< DecorationButtonType > PreviewSettings::decorationButtonsLeft() const
|
||||||
|
{
|
||||||
|
return m_leftButtons->buttons();
|
||||||
|
}
|
||||||
|
|
||||||
|
QList< DecorationButtonType > PreviewSettings::decorationButtonsRight() const
|
||||||
|
{
|
||||||
|
return m_rightButtons->buttons();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewSettings::addButtonToLeft(int row)
|
||||||
|
{
|
||||||
|
QModelIndex index = m_availableButtons->index(row);
|
||||||
|
if (!index.isValid()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_leftButtons->add(index.data(Qt::UserRole).value<DecorationButtonType>());
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewSettings::addButtonToRight(int row)
|
||||||
|
{
|
||||||
|
QModelIndex index = m_availableButtons->index(row);
|
||||||
|
if (!index.isValid()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_rightButtons->add(index.data(Qt::UserRole).value<DecorationButtonType>());
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewSettings::setBorderSizesIndex(int index)
|
||||||
|
{
|
||||||
|
if (m_borderSize == index) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_borderSize = index;
|
||||||
|
emit borderSizesIndexChanged(index);
|
||||||
|
emit decorationSettings()->borderSizeChanged(borderSize());
|
||||||
|
}
|
||||||
|
|
||||||
|
BorderSize PreviewSettings::borderSize() const
|
||||||
|
{
|
||||||
|
return m_borderSizes->index(m_borderSize).data(Qt::UserRole).value<BorderSize>();
|
||||||
|
}
|
||||||
|
|
||||||
|
void PreviewSettings::setFont(const QFont &font)
|
||||||
|
{
|
||||||
|
if (m_font == font) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_font = font;
|
||||||
|
emit fontChanged(m_font);
|
||||||
|
}
|
||||||
|
|
||||||
|
Settings::Settings(QObject *parent)
|
||||||
|
: QObject(parent)
|
||||||
|
{
|
||||||
|
connect(this, &Settings::bridgeChanged, this, &Settings::createSettings);
|
||||||
|
}
|
||||||
|
|
||||||
|
Settings::~Settings() = default;
|
||||||
|
|
||||||
|
void Settings::setBridge(PreviewBridge *bridge)
|
||||||
|
{
|
||||||
|
if (m_bridge == bridge) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
m_bridge = bridge;
|
||||||
|
emit bridgeChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
PreviewBridge *Settings::bridge() const
|
||||||
|
{
|
||||||
|
return m_bridge.data();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Settings::createSettings()
|
||||||
|
{
|
||||||
|
if (m_bridge.isNull()) {
|
||||||
|
m_settings.clear();
|
||||||
|
} else {
|
||||||
|
m_settings = QSharedPointer<KDecoration2::DecorationSettings>::create(m_bridge.data());
|
||||||
|
}
|
||||||
|
emit settingsChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
QSharedPointer<DecorationSettings> Settings::settings() const
|
||||||
|
{
|
||||||
|
return m_settings;
|
||||||
|
}
|
||||||
|
|
||||||
|
DecorationSettings *Settings::settingsPointer() const
|
||||||
|
{
|
||||||
|
return m_settings.data();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
184
kcmkwin/kwindecoration/declarative-plugin/previewsettings.h
Normal file
184
kcmkwin/kwindecoration/declarative-plugin/previewsettings.h
Normal file
|
@ -0,0 +1,184 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#ifndef KDECOARTIONS_PREVIEW_SETTINGS_H
|
||||||
|
#define KDECOARTIONS_PREVIEW_SETTINGS_H
|
||||||
|
|
||||||
|
#include <KDecoration2/Private/DecorationSettingsPrivate>
|
||||||
|
#include <KDecoration2/DecorationSettings>
|
||||||
|
#include <QObject>
|
||||||
|
#include <QAbstractListModel>
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
class PreviewBridge;
|
||||||
|
|
||||||
|
class ButtonsModel : public QAbstractListModel
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
explicit ButtonsModel(const QList< DecorationButtonType > &buttons, QObject *parent = 0);
|
||||||
|
virtual ~ButtonsModel();
|
||||||
|
QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
|
||||||
|
int rowCount(const QModelIndex& parent = QModelIndex()) const override;
|
||||||
|
QHash< int, QByteArray > roleNames() const override;
|
||||||
|
|
||||||
|
QList< DecorationButtonType > buttons() const {
|
||||||
|
return m_buttons;
|
||||||
|
}
|
||||||
|
|
||||||
|
Q_INVOKABLE void remove(int index);
|
||||||
|
Q_INVOKABLE void up(int index);
|
||||||
|
Q_INVOKABLE void down(int index);
|
||||||
|
|
||||||
|
void add(DecorationButtonType type);
|
||||||
|
|
||||||
|
private:
|
||||||
|
QList< DecorationButtonType > m_buttons;
|
||||||
|
};
|
||||||
|
|
||||||
|
class BorderSizesModel : public QAbstractListModel
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
explicit BorderSizesModel(QObject *parent = 0);
|
||||||
|
virtual ~BorderSizesModel();
|
||||||
|
QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override;
|
||||||
|
int rowCount(const QModelIndex& parent = QModelIndex()) const override;
|
||||||
|
QHash< int, QByteArray > roleNames() const override;
|
||||||
|
private:
|
||||||
|
QList<BorderSize> m_borders = QList<BorderSize>({
|
||||||
|
BorderSize::None,
|
||||||
|
BorderSize::NoSides,
|
||||||
|
BorderSize::Tiny,
|
||||||
|
BorderSize::Normal,
|
||||||
|
BorderSize::Large,
|
||||||
|
BorderSize::VeryLarge,
|
||||||
|
BorderSize::Huge,
|
||||||
|
BorderSize::VeryHuge,
|
||||||
|
BorderSize::Oversized
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
class PreviewSettings : public QObject, public DecorationSettingsPrivate
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
Q_PROPERTY(bool onAllDesktopsAvailable READ isOnAllDesktopsAvailable WRITE setOnAllDesktopsAvailable NOTIFY onAllDesktopsAvailableChanged)
|
||||||
|
Q_PROPERTY(bool alphaChannelSupported READ isAlphaChannelSupported WRITE setAlphaChannelSupported NOTIFY alphaChannelSupportedChanged)
|
||||||
|
Q_PROPERTY(bool closeOnDoubleClickOnMenu READ isCloseOnDoubleClickOnMenu WRITE setCloseOnDoubleClickOnMenu NOTIFY closeOnDoubleClickOnMenuChanged)
|
||||||
|
Q_PROPERTY(QAbstractItemModel *leftButtonsModel READ leftButtonsModel CONSTANT)
|
||||||
|
Q_PROPERTY(QAbstractItemModel *rightButtonsModel READ rightButtonsModel CONSTANT)
|
||||||
|
Q_PROPERTY(QAbstractItemModel *availableButtonsModel READ availableButtonsModel CONSTANT)
|
||||||
|
Q_PROPERTY(QAbstractItemModel *borderSizesModel READ borderSizesModel CONSTANT)
|
||||||
|
Q_PROPERTY(int borderSizesIndex READ borderSizesIndex WRITE setBorderSizesIndex NOTIFY borderSizesIndexChanged)
|
||||||
|
Q_PROPERTY(QFont font READ font WRITE setFont NOTIFY fontChanged)
|
||||||
|
public:
|
||||||
|
explicit PreviewSettings(DecorationSettings *parent);
|
||||||
|
virtual ~PreviewSettings();
|
||||||
|
bool isAlphaChannelSupported() const override;
|
||||||
|
bool isOnAllDesktopsAvailable() const override;
|
||||||
|
bool isCloseOnDoubleClickOnMenu() const override {
|
||||||
|
return m_closeOnDoubleClick;
|
||||||
|
}
|
||||||
|
BorderSize borderSize() const override;
|
||||||
|
|
||||||
|
void setOnAllDesktopsAvailable(bool available);
|
||||||
|
void setAlphaChannelSupported(bool supported);
|
||||||
|
void setCloseOnDoubleClickOnMenu(bool enabled);
|
||||||
|
|
||||||
|
QAbstractItemModel *leftButtonsModel() const {
|
||||||
|
return m_leftButtons;
|
||||||
|
}
|
||||||
|
QAbstractItemModel *rightButtonsModel() const {
|
||||||
|
return m_rightButtons;
|
||||||
|
}
|
||||||
|
QAbstractItemModel *availableButtonsModel() const {
|
||||||
|
return m_availableButtons;
|
||||||
|
}
|
||||||
|
QAbstractItemModel *borderSizesModel() const {
|
||||||
|
return m_borderSizes;
|
||||||
|
}
|
||||||
|
|
||||||
|
QList< DecorationButtonType > decorationButtonsLeft() const override;
|
||||||
|
QList< DecorationButtonType > decorationButtonsRight() const override;
|
||||||
|
|
||||||
|
Q_INVOKABLE void addButtonToLeft(int row);
|
||||||
|
Q_INVOKABLE void addButtonToRight(int row);
|
||||||
|
|
||||||
|
int borderSizesIndex() const {
|
||||||
|
return m_borderSize;
|
||||||
|
}
|
||||||
|
void setBorderSizesIndex(int index);
|
||||||
|
|
||||||
|
QFont font() const {
|
||||||
|
return m_font;
|
||||||
|
}
|
||||||
|
void setFont(const QFont &font);
|
||||||
|
|
||||||
|
Q_SIGNALS:
|
||||||
|
void onAllDesktopsAvailableChanged(bool);
|
||||||
|
void alphaChannelSupportedChanged(bool);
|
||||||
|
void closeOnDoubleClickOnMenuChanged(bool);
|
||||||
|
void borderSizesIndexChanged(int);
|
||||||
|
void fontChanged(const QFont &);
|
||||||
|
|
||||||
|
private:
|
||||||
|
bool m_alphaChannelSupported;
|
||||||
|
bool m_onAllDesktopsAvailable;
|
||||||
|
bool m_closeOnDoubleClick;
|
||||||
|
ButtonsModel *m_leftButtons;
|
||||||
|
ButtonsModel *m_rightButtons;
|
||||||
|
ButtonsModel *m_availableButtons;
|
||||||
|
BorderSizesModel *m_borderSizes;
|
||||||
|
int m_borderSize;
|
||||||
|
QFont m_font;
|
||||||
|
};
|
||||||
|
|
||||||
|
class Settings : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
Q_PROPERTY(KDecoration2::Preview::PreviewBridge *bridge READ bridge WRITE setBridge NOTIFY bridgeChanged)
|
||||||
|
Q_PROPERTY(KDecoration2::DecorationSettings *settings READ settingsPointer NOTIFY settingsChanged)
|
||||||
|
public:
|
||||||
|
explicit Settings(QObject *parent = nullptr);
|
||||||
|
virtual ~Settings();
|
||||||
|
|
||||||
|
PreviewBridge *bridge() const;
|
||||||
|
void setBridge(PreviewBridge *bridge);
|
||||||
|
|
||||||
|
QSharedPointer<DecorationSettings> settings() const;
|
||||||
|
DecorationSettings *settingsPointer() const;
|
||||||
|
|
||||||
|
Q_SIGNALS:
|
||||||
|
void bridgeChanged();
|
||||||
|
void settingsChanged();
|
||||||
|
|
||||||
|
private:
|
||||||
|
void createSettings();
|
||||||
|
QPointer<PreviewBridge> m_bridge;
|
||||||
|
QSharedPointer<KDecoration2::DecorationSettings> m_settings;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
2
kcmkwin/kwindecoration/declarative-plugin/qmldir
Normal file
2
kcmkwin/kwindecoration/declarative-plugin/qmldir
Normal file
|
@ -0,0 +1,2 @@
|
||||||
|
module org.kde.kwin.private.kdecoration
|
||||||
|
plugin kdecorationprivatedeclarative
|
|
@ -1,370 +1,164 @@
|
||||||
/********************************************************************
|
/*
|
||||||
KWin - the KDE window manager
|
* Copyright 2014 Martin Gräßlin <mgraesslin@kde.org>
|
||||||
This file is part of the KDE project.
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
Copyright (C) 2009 Martin Gräßlin <mgraesslin@kde.org>
|
* modify it under the terms of the GNU General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2 of
|
||||||
This program is free software; you can redistribute it and/or modify
|
* the License or (at your option) version 3 or any later version
|
||||||
it under the terms of the GNU General Public License as published by
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
(at your option) any later version.
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
This program is distributed in the hope that it will be useful,
|
* This program is distributed in the hope that it will be useful,
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
GNU General Public License for more details.
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*********************************************************************/
|
*/
|
||||||
#include "decorationmodel.h"
|
#include "decorationmodel.h"
|
||||||
#include "preview.h"
|
// KDecoration2
|
||||||
// kwin
|
#include <KDecoration2/DecorationSettings>
|
||||||
#include <kdecorationfactory.h>
|
#include <KDecoration2/Decoration>
|
||||||
// Qt
|
|
||||||
#include <QDir>
|
|
||||||
#include <QFileInfo>
|
|
||||||
#include <QApplication>
|
|
||||||
#include <QStandardPaths>
|
|
||||||
// KDE
|
// KDE
|
||||||
#include <KConfigGroup>
|
|
||||||
#include <KDesktopFile>
|
|
||||||
#include <KLocalizedString>
|
|
||||||
#include <KServiceTypeTrader>
|
|
||||||
#include <KPluginInfo>
|
#include <KPluginInfo>
|
||||||
|
#include <KPluginLoader>
|
||||||
|
#include <KPluginFactory>
|
||||||
#include <KPluginTrader>
|
#include <KPluginTrader>
|
||||||
#include "kwindecoration.h"
|
// Qt
|
||||||
|
#include <QDebug>
|
||||||
|
|
||||||
/* WARNING -------------------------------------------------------------------------
|
namespace KDecoration2
|
||||||
* it is *ABSOLUTELY* mandatory to manage loadPlugin() and destroyPreviousPlugin()
|
|
||||||
* using disablePreview()
|
|
||||||
*
|
|
||||||
* loadPlugin() moves the present factory pointer to "old_fact" which is then deleted
|
|
||||||
* by the succeeding destroyPreviousPlugin()
|
|
||||||
*
|
|
||||||
* So if you loaded a new plugin and that changed the current factory, call disablePreview()
|
|
||||||
* BEFORE the following destroyPreviousPlugin() destroys the factory for the current m_preview->deco->factory
|
|
||||||
* (which is invoked on deco deconstruction)
|
|
||||||
* WARNING ------------------------------------------------------------------------ */
|
|
||||||
|
|
||||||
static const QString s_auroraePluginName = QStringLiteral("aurorae");
|
|
||||||
|
|
||||||
namespace KWin
|
|
||||||
{
|
{
|
||||||
|
|
||||||
DecorationModel::DecorationModel(KSharedConfigPtr config, QObject* parent)
|
namespace Configuration
|
||||||
|
{
|
||||||
|
static const QString s_pluginName = QStringLiteral("org.kde.kdecoration2");
|
||||||
|
|
||||||
|
DecorationsModel::DecorationsModel(QObject *parent)
|
||||||
: QAbstractListModel(parent)
|
: QAbstractListModel(parent)
|
||||||
, m_plugins(new KDecorationPreviewPlugins(config))
|
|
||||||
, m_preview(new KDecorationPreview())
|
|
||||||
, m_customButtons(false)
|
|
||||||
, m_options(new KDecorationPreviewOptions)
|
|
||||||
{
|
{
|
||||||
QHash<int, QByteArray> roleNames;
|
|
||||||
roleNames[Qt::DisplayRole] = "display";
|
|
||||||
roleNames[TypeRole] = "type";
|
|
||||||
roleNames[AuroraeNameRole] = "auroraeThemeName";
|
|
||||||
roleNames[QmlMainScriptRole] = "mainScript";
|
|
||||||
roleNames[BorderSizeRole] = "borderSize";
|
|
||||||
roleNames[ButtonSizeRole] = "buttonSize";
|
|
||||||
roleNames[LibraryNameRole] = "library";
|
|
||||||
setRoleNames(roleNames);
|
|
||||||
m_config = KSharedConfig::openConfig("auroraerc");
|
|
||||||
findDecorations();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
DecorationModel::~DecorationModel()
|
DecorationsModel::~DecorationsModel() = default;
|
||||||
|
|
||||||
|
int DecorationsModel::rowCount(const QModelIndex &parent) const
|
||||||
{
|
{
|
||||||
delete m_preview;
|
if (parent.isValid()) {
|
||||||
delete m_plugins;
|
return 0;
|
||||||
|
}
|
||||||
|
return m_plugins.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
void DecorationModel::reload()
|
QVariant DecorationsModel::data(const QModelIndex &index, int role) const
|
||||||
{
|
{
|
||||||
m_decorations.clear();
|
if (!index.isValid() || index.column() != 0 || index.row() < 0 || index.row() >= int(m_plugins.size())) {
|
||||||
findDecorations();
|
return QVariant();
|
||||||
|
}
|
||||||
|
const Data &d = m_plugins.at(index.row());
|
||||||
|
switch (role) {
|
||||||
|
case Qt::DisplayRole:
|
||||||
|
return d.visibleName;
|
||||||
|
case Qt::UserRole +4:
|
||||||
|
return d.pluginName;
|
||||||
|
case Qt::UserRole +5:
|
||||||
|
return d.themeName;
|
||||||
|
}
|
||||||
|
|
||||||
|
return QVariant();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Find all theme desktop files in all 'data' dirs owned by kwin.
|
QHash< int, QByteArray > DecorationsModel::roleNames() const
|
||||||
// And insert these into a DecorationInfo structure
|
{
|
||||||
void DecorationModel::findDecorations()
|
QHash<int, QByteArray> roles({
|
||||||
|
{Qt::DisplayRole, QByteArrayLiteral("display")},
|
||||||
|
{Qt::UserRole + 4, QByteArrayLiteral("plugin")},
|
||||||
|
{Qt::UserRole + 5, QByteArrayLiteral("theme")}
|
||||||
|
});
|
||||||
|
return roles;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool isThemeEngine(const QVariantMap &decoSettingsMap)
|
||||||
|
{
|
||||||
|
auto it = decoSettingsMap.find(QStringLiteral("themes"));
|
||||||
|
if (it == decoSettingsMap.end()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return it.value().toBool();
|
||||||
|
}
|
||||||
|
|
||||||
|
static QString themeListKeyword(const QVariantMap &decoSettingsMap)
|
||||||
|
{
|
||||||
|
auto it = decoSettingsMap.find(QStringLiteral("themeListKeyword"));
|
||||||
|
if (it == decoSettingsMap.end()) {
|
||||||
|
return QString();
|
||||||
|
}
|
||||||
|
return it.value().toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
void DecorationsModel::init()
|
||||||
{
|
{
|
||||||
beginResetModel();
|
beginResetModel();
|
||||||
const auto decorations = KPluginTrader::self()->query(QStringLiteral("kwin/kdecorations"));
|
const auto plugins = KPluginTrader::self()->query(s_pluginName, s_pluginName);
|
||||||
for (const KPluginInfo &plugin : decorations) {
|
for (const auto &info : plugins) {
|
||||||
if (plugin.pluginName() == s_auroraePluginName) {
|
KPluginLoader loader(info.libraryPath());
|
||||||
// read the Aurorae themes
|
KPluginFactory *factory = loader.factory();
|
||||||
findAuroraeThemes();
|
if (!factory) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
DecorationModelData data;
|
auto metadata = loader.metaData().value(QStringLiteral("MetaData")).toObject().value(s_pluginName);
|
||||||
data.name = plugin.name();
|
if (!metadata.isUndefined()) {
|
||||||
data.pluginName = plugin.pluginName();
|
const auto decoSettingsMap = metadata.toObject().toVariantMap();
|
||||||
data.type = DecorationModelData::NativeDecoration;
|
if (isThemeEngine(decoSettingsMap)) {
|
||||||
data.borderSize = KDecorationDefines::BorderNormal;
|
const QString keyword = themeListKeyword(decoSettingsMap);
|
||||||
data.closeDblClick = false;
|
if (keyword.isNull()) {
|
||||||
data.comment = plugin.comment();
|
// We cannot list the themes
|
||||||
data.author = plugin.author();
|
continue;
|
||||||
data.email = plugin.email();
|
}
|
||||||
data.version = plugin.version();
|
QScopedPointer<QObject> themeFinder(factory->create<QObject>(keyword));
|
||||||
data.license = plugin.license();
|
if (themeFinder.isNull()) {
|
||||||
data.website = plugin.website();
|
continue;
|
||||||
m_decorations.append(data);
|
}
|
||||||
}
|
QVariant themes = themeFinder->property("themes");
|
||||||
|
if (!themes.isValid()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
const auto themesMap = themes.toMap();
|
||||||
|
for (auto it = themesMap.begin(); it != themesMap.end(); ++it) {
|
||||||
|
Data d;
|
||||||
|
d.pluginName = info.pluginName();
|
||||||
|
d.themeName = it.value().toString();
|
||||||
|
d.visibleName = it.key();
|
||||||
|
m_plugins.emplace_back(std::move(d));
|
||||||
|
}
|
||||||
|
|
||||||
KService::List offers = KServiceTypeTrader::self()->query("KWin/Decoration");
|
// it's a theme engine, we don't want to show this entry
|
||||||
foreach (KService::Ptr service, offers) {
|
continue;
|
||||||
DecorationModelData data;
|
}
|
||||||
data.name = service->name();
|
|
||||||
data.pluginName = s_auroraePluginName;
|
|
||||||
data.type = DecorationModelData::QmlDecoration;
|
|
||||||
data.auroraeName = service->property("X-KDE-PluginInfo-Name").toString();
|
|
||||||
QString scriptName = service->property("X-Plasma-MainScript").toString();
|
|
||||||
data.configTranslationDomain = service->property(QStringLiteral("X-KWin-Config-TranslationDomain")).toString();
|
|
||||||
data.qmlPath = QStandardPaths::locate(QStandardPaths::GenericDataLocation, "kwin/decorations/" + data.auroraeName + "/contents/" + scriptName);
|
|
||||||
if (data.qmlPath.isEmpty()) {
|
|
||||||
// not a valid QML theme
|
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
KConfigGroup config(m_config, data.auroraeName);
|
Data data;
|
||||||
data.borderSize = (KDecorationDefines::BorderSize)config.readEntry< int >("BorderSize", KDecorationDefines::BorderNormal);
|
data.pluginName = info.pluginName();
|
||||||
data.buttonSize = (KDecorationDefines::BorderSize)config.readEntry< int >("ButtonSize", KDecorationDefines::BorderNormal);
|
data.visibleName = info.name().isEmpty() ? info.pluginName() : info.name();
|
||||||
data.closeDblClick = config.readEntry< bool >("CloseOnDoubleClickMenuButton", false);
|
|
||||||
data.comment = service->comment();
|
m_plugins.emplace_back(std::move(data));
|
||||||
KPluginInfo info(service);
|
|
||||||
data.author = info.author();
|
|
||||||
data.email= info.email();
|
|
||||||
data.version = info.version();
|
|
||||||
data.license = info.license();
|
|
||||||
data.website = info.website();
|
|
||||||
m_decorations.append(data);
|
|
||||||
}
|
}
|
||||||
qSort(m_decorations.begin(), m_decorations.end(), DecorationModelData::less);
|
|
||||||
endResetModel();
|
endResetModel();
|
||||||
}
|
}
|
||||||
|
|
||||||
void DecorationModel::findAuroraeThemes()
|
QModelIndex DecorationsModel::findDecoration(const QString &pluginName, const QString &themeName) const
|
||||||
{
|
{
|
||||||
// get all destop themes
|
auto it = std::find_if(m_plugins.cbegin(), m_plugins.cend(),
|
||||||
QStringList themes;
|
[pluginName, themeName](const Data &d) {
|
||||||
const QStringList dirs = QStandardPaths::locateAll(QStandardPaths::GenericDataLocation, "aurorae/themes/", QStandardPaths::LocateDirectory);
|
return d.pluginName == pluginName && d.themeName == themeName;
|
||||||
QStringList themeDirectories;
|
|
||||||
for (const QString & dir : dirs) {
|
|
||||||
QDir directory = QDir(dir);
|
|
||||||
for (const QString &themeDir : directory.entryList(QDir::AllDirs | QDir::NoDotAndDotDot)) {
|
|
||||||
themeDirectories << dir + themeDir;
|
|
||||||
}
|
}
|
||||||
|
);
|
||||||
|
if (it == m_plugins.cend()) {
|
||||||
|
return QModelIndex();
|
||||||
}
|
}
|
||||||
for (const QString &dir : themeDirectories) {
|
const auto distance = std::distance(m_plugins.cbegin(), it);
|
||||||
for (const QString & file : QDir(dir).entryList(QStringList() << QStringLiteral("metadata.desktop"))) {
|
return createIndex(distance, 0);
|
||||||
themes.append(dir + '/' + file);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
foreach (const QString & theme, themes) {
|
|
||||||
int themeSepIndex = theme.lastIndexOf('/', -1);
|
|
||||||
QString themeRoot = theme.left(themeSepIndex);
|
|
||||||
int themeNameSepIndex = themeRoot.lastIndexOf('/', -1);
|
|
||||||
QString packageName = themeRoot.right(themeRoot.length() - themeNameSepIndex - 1);
|
|
||||||
|
|
||||||
KDesktopFile df(theme);
|
|
||||||
QString name = df.readName();
|
|
||||||
if (name.isEmpty()) {
|
|
||||||
name = packageName;
|
|
||||||
}
|
|
||||||
|
|
||||||
DecorationModelData data;
|
|
||||||
data.name = name;
|
|
||||||
data.pluginName = s_auroraePluginName;
|
|
||||||
data.type = DecorationModelData::AuroraeDecoration;
|
|
||||||
data.auroraeName = packageName;
|
|
||||||
KConfigGroup config(m_config, data.auroraeName);
|
|
||||||
data.borderSize = (KDecorationDefines::BorderSize)config.readEntry< int >("BorderSize", KDecorationDefines::BorderNormal);
|
|
||||||
data.buttonSize = (KDecorationDefines::BorderSize)config.readEntry< int >("ButtonSize", KDecorationDefines::BorderNormal);
|
|
||||||
data.closeDblClick = config.readEntry< bool >("CloseOnDoubleClickMenuButton", false);
|
|
||||||
metaData(data, df);
|
|
||||||
m_decorations.append(data);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void DecorationModel::metaData(DecorationModelData& data, const KDesktopFile& df)
|
|
||||||
{
|
|
||||||
data.comment = df.readComment();
|
|
||||||
data.author = df.desktopGroup().readEntry("X-KDE-PluginInfo-Author", QString());
|
|
||||||
data.email = df.desktopGroup().readEntry("X-KDE-PluginInfo-Email", QString());
|
|
||||||
data.version = df.desktopGroup().readEntry("X-KDE-PluginInfo-Version", QString());
|
|
||||||
data.license = df.desktopGroup().readEntry("X-KDE-PluginInfo-License", QString());
|
|
||||||
data.website = df.desktopGroup().readEntry("X-KDE-PluginInfo-Website", QString());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int DecorationModel::rowCount(const QModelIndex& parent) const
|
|
||||||
{
|
|
||||||
Q_UNUSED(parent)
|
|
||||||
return m_decorations.count();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
QVariant DecorationModel::data(const QModelIndex& index, int role) const
|
|
||||||
{
|
|
||||||
if (!index.isValid())
|
|
||||||
return QVariant();
|
|
||||||
|
|
||||||
switch(role) {
|
|
||||||
case Qt::DisplayRole:
|
|
||||||
case NameRole:
|
|
||||||
return m_decorations[ index.row()].name;
|
|
||||||
case LibraryNameRole:
|
|
||||||
return m_decorations[ index.row()].pluginName;
|
|
||||||
case TypeRole:
|
|
||||||
return m_decorations[ index.row()].type;
|
|
||||||
case AuroraeNameRole:
|
|
||||||
return m_decorations[ index.row()].auroraeName;
|
|
||||||
case PackageDescriptionRole:
|
|
||||||
return m_decorations[ index.row()].comment;
|
|
||||||
case PackageAuthorRole:
|
|
||||||
return m_decorations[ index.row()].author;
|
|
||||||
case PackageEmailRole:
|
|
||||||
return m_decorations[ index.row()].email;
|
|
||||||
case PackageWebsiteRole:
|
|
||||||
return m_decorations[ index.row()].website;
|
|
||||||
case PackageVersionRole:
|
|
||||||
return m_decorations[ index.row()].version;
|
|
||||||
case PackageLicenseRole:
|
|
||||||
return m_decorations[ index.row()].license;
|
|
||||||
case BorderSizeRole:
|
|
||||||
return static_cast< int >(m_decorations[ index.row()].borderSize);
|
|
||||||
case BorderSizesRole: {
|
|
||||||
QList< QVariant > sizes;
|
|
||||||
const bool mustDisablePreview = m_plugins->factory() && m_plugins->factory() == m_preview->factory();
|
|
||||||
if (m_plugins->loadPlugin(m_decorations[index.row()].pluginName) && m_plugins->factory()) {
|
|
||||||
foreach (KDecorationDefines::BorderSize size, m_plugins->factory()->borderSizes()) // krazy:exclude=foreach
|
|
||||||
sizes << int(size);
|
|
||||||
if (mustDisablePreview) // it's nuked with destroyPreviousPlugin()
|
|
||||||
m_preview->disablePreview(); // so we need to get rid of m_preview->deco first
|
|
||||||
m_plugins->destroyPreviousPlugin();
|
|
||||||
}
|
|
||||||
return sizes;
|
|
||||||
}
|
|
||||||
case ButtonSizeRole:
|
|
||||||
if (m_decorations[ index.row()].type == DecorationModelData::AuroraeDecoration ||
|
|
||||||
m_decorations[ index.row()].type == DecorationModelData::QmlDecoration)
|
|
||||||
return static_cast< int >(m_decorations[ index.row()].buttonSize);
|
|
||||||
else
|
|
||||||
return QVariant();
|
|
||||||
case QmlMainScriptRole:
|
|
||||||
return m_decorations[ index.row()].qmlPath;
|
|
||||||
case CloseOnDblClickRole:
|
|
||||||
return m_decorations[index.row()].closeDblClick;
|
|
||||||
case ConfigTranslationDomain:
|
|
||||||
return m_decorations[index.row()].configTranslationDomain;
|
|
||||||
default:
|
|
||||||
return QVariant();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool DecorationModel::setData(const QModelIndex& index, const QVariant& value, int role)
|
|
||||||
{
|
|
||||||
if (!index.isValid() || (role != BorderSizeRole && role != ButtonSizeRole && role != CloseOnDblClickRole))
|
|
||||||
return QAbstractItemModel::setData(index, value, role);
|
|
||||||
|
|
||||||
const DecorationModelData::DecorationType type = m_decorations[ index.row()].type;
|
|
||||||
|
|
||||||
if (role == BorderSizeRole) {
|
|
||||||
m_decorations[ index.row()].borderSize = (KDecorationDefines::BorderSize)value.toInt();
|
|
||||||
if (type == DecorationModelData::AuroraeDecoration || type == DecorationModelData::QmlDecoration) {
|
|
||||||
KConfigGroup config(m_config, m_decorations[ index.row()].auroraeName);
|
|
||||||
config.writeEntry("BorderSize", value.toInt());
|
|
||||||
config.sync();
|
|
||||||
}
|
|
||||||
emit dataChanged(index, index);
|
|
||||||
emit configChanged(m_decorations[ index.row()].auroraeName);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (role == ButtonSizeRole && (type == DecorationModelData::AuroraeDecoration || type == DecorationModelData::QmlDecoration)) {
|
|
||||||
m_decorations[ index.row()].buttonSize = (KDecorationDefines::BorderSize)value.toInt();
|
|
||||||
KConfigGroup config(m_config, m_decorations[ index.row()].auroraeName);
|
|
||||||
config.writeEntry("ButtonSize", value.toInt());
|
|
||||||
config.sync();
|
|
||||||
emit dataChanged(index, index);
|
|
||||||
emit configChanged(m_decorations[ index.row()].auroraeName);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (role == CloseOnDblClickRole && (type == DecorationModelData::AuroraeDecoration || type == DecorationModelData::QmlDecoration)) {
|
|
||||||
if (m_decorations[ index.row()].closeDblClick == value.toBool()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
m_decorations[ index.row()].closeDblClick = value.toBool();
|
|
||||||
KConfigGroup config(m_config, m_decorations[ index.row()].auroraeName);
|
|
||||||
config.writeEntry("CloseOnDoubleClickMenuButton", value.toBool());
|
|
||||||
config.sync();
|
|
||||||
emit dataChanged(index, index);
|
|
||||||
emit configChanged(m_decorations[ index.row()].auroraeName);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return QAbstractItemModel::setData(index, value, role);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void DecorationModel::changeButtons(const KWin::DecorationButtons *buttons)
|
|
||||||
{
|
|
||||||
m_customButtons = buttons->customPositions();
|
|
||||||
m_options->setCustomTitleButtonsEnabled(m_customButtons);
|
|
||||||
m_options->setCustomTitleButtons(buttons->leftButtons(), buttons->rightButtons());
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecorationModel::setButtons(bool custom, const QList<KDecorationDefines::DecorationButton> &left, const QList<KDecorationDefines::DecorationButton> &right)
|
|
||||||
{
|
|
||||||
m_customButtons = custom;
|
|
||||||
m_options->setCustomTitleButtons(left, right);
|
|
||||||
}
|
|
||||||
|
|
||||||
QModelIndex DecorationModel::indexOfLibrary(const QString& libraryName) const
|
|
||||||
{
|
|
||||||
for (int i = 0; i < m_decorations.count(); i++) {
|
|
||||||
if (m_decorations.at(i).pluginName.compare(libraryName) == 0)
|
|
||||||
return index(i);
|
|
||||||
}
|
|
||||||
return QModelIndex();
|
|
||||||
}
|
|
||||||
|
|
||||||
QModelIndex DecorationModel::indexOfName(const QString& decoName) const
|
|
||||||
{
|
|
||||||
for (int i = 0; i < m_decorations.count(); i++) {
|
|
||||||
if (m_decorations.at(i).name.compare(decoName) == 0)
|
|
||||||
return index(i);
|
|
||||||
}
|
|
||||||
return QModelIndex();
|
|
||||||
}
|
|
||||||
|
|
||||||
QModelIndex DecorationModel::indexOfAuroraeName(const QString &auroraeName, const QString &type) const
|
|
||||||
{
|
|
||||||
for (int i = 0; i < m_decorations.count(); i++) {
|
|
||||||
const DecorationModelData& data = m_decorations.at(i);
|
|
||||||
if (type == "aurorae" && data.type == DecorationModelData::AuroraeDecoration &&
|
|
||||||
data.auroraeName.compare(auroraeName) == 0)
|
|
||||||
return index(i);
|
|
||||||
if (type == "qml" && data.type == DecorationModelData::QmlDecoration &&
|
|
||||||
data.auroraeName.compare(auroraeName) == 0)
|
|
||||||
return index(i);
|
|
||||||
}
|
|
||||||
return QModelIndex();
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecorationModel::setBorderSize(const QModelIndex& index, KDecorationDefines::BorderSize size)
|
|
||||||
{
|
|
||||||
if (!index.isValid() || m_decorations[ index.row()].type == DecorationModelData::AuroraeDecoration || m_decorations[ index.row()].type == DecorationModelData::QmlDecoration)
|
|
||||||
return;
|
|
||||||
m_decorations[ index.row()].borderSize = size;
|
|
||||||
}
|
|
||||||
|
|
||||||
QVariant DecorationModel::readConfig(const QString &themeName, const QString &key, const QVariant &defaultValue)
|
|
||||||
{
|
|
||||||
return m_config->group(themeName).readEntry(key, defaultValue);
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecorationModel::notifyConfigChanged(const QModelIndex &index)
|
|
||||||
{
|
|
||||||
if (!index.isValid()) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
emit configChanged(m_decorations[index.row()].auroraeName);
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace KWin
|
|
||||||
|
|
|
@ -1,139 +1,59 @@
|
||||||
/********************************************************************
|
/*
|
||||||
KWin - the KDE window manager
|
* Copyright 2014 Martin Gräßlin <mgraesslin@kde.org>
|
||||||
This file is part of the KDE project.
|
*
|
||||||
|
* 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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#ifndef KDECORATION_DECORATIONS_MODEL_H
|
||||||
|
#define KDECORATION_DECORATIONS_MODEL_H
|
||||||
|
|
||||||
Copyright (C) 2009 Martin Gräßlin <mgraesslin@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, see <http://www.gnu.org/licenses/>.
|
|
||||||
*********************************************************************/
|
|
||||||
|
|
||||||
#ifndef KWIN_DECORATIONMODEL_H
|
|
||||||
#define KWIN_DECORATIONMODEL_H
|
|
||||||
#include <QAbstractListModel>
|
#include <QAbstractListModel>
|
||||||
#include <QPixmap>
|
|
||||||
#include <KConfig>
|
|
||||||
#include <KSharedConfig>
|
|
||||||
#include <kdecoration.h>
|
|
||||||
|
|
||||||
class QWidget;
|
namespace KDecoration2
|
||||||
class KDesktopFile;
|
|
||||||
class KDecorationPlugins;
|
|
||||||
class KDecorationPreview;
|
|
||||||
class KDecorationPreviewOptions;
|
|
||||||
|
|
||||||
namespace KWin
|
|
||||||
{
|
{
|
||||||
|
|
||||||
class DecorationButtons;
|
namespace Configuration
|
||||||
|
|
||||||
class DecorationModelData
|
|
||||||
{
|
{
|
||||||
public:
|
|
||||||
enum DecorationType {
|
|
||||||
NativeDecoration = 0,
|
|
||||||
AuroraeDecoration = 1,
|
|
||||||
QmlDecoration = 2
|
|
||||||
};
|
|
||||||
QString name;
|
|
||||||
QString pluginName;
|
|
||||||
DecorationType type;
|
|
||||||
QString comment;
|
|
||||||
QString author;
|
|
||||||
QString email;
|
|
||||||
QString website;
|
|
||||||
QString version;
|
|
||||||
QString license;
|
|
||||||
QString auroraeName;
|
|
||||||
QString qmlPath;
|
|
||||||
QString configTranslationDomain;
|
|
||||||
KDecorationDefines::BorderSize borderSize;
|
|
||||||
KDecorationDefines::BorderSize buttonSize;
|
|
||||||
/**
|
|
||||||
* Whether the window gets closed on double clicking the Menu Button.
|
|
||||||
* Only applies for Aurorae and QML Decoration.
|
|
||||||
**/
|
|
||||||
bool closeDblClick;
|
|
||||||
|
|
||||||
static bool less(const DecorationModelData& a, const DecorationModelData& b) {
|
class DecorationsModel : public QAbstractListModel
|
||||||
return a.name < b.name;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
class DecorationModel : public QAbstractListModel
|
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
public:
|
public:
|
||||||
enum {
|
explicit DecorationsModel(QObject *parent = nullptr);
|
||||||
NameRole = Qt::UserRole,
|
virtual ~DecorationsModel();
|
||||||
LibraryNameRole = Qt::UserRole + 1,
|
|
||||||
TypeRole = Qt::UserRole + 3,
|
|
||||||
AuroraeNameRole = Qt::UserRole + 4,
|
|
||||||
PackageDescriptionRole = Qt::UserRole + 5,
|
|
||||||
PackageAuthorRole = Qt::UserRole + 6,
|
|
||||||
PackageEmailRole = Qt::UserRole + 7,
|
|
||||||
PackageWebsiteRole = Qt::UserRole + 8,
|
|
||||||
PackageVersionRole = Qt::UserRole + 9,
|
|
||||||
PackageLicenseRole = Qt::UserRole + 10,
|
|
||||||
BorderSizeRole = Qt::UserRole + 11,
|
|
||||||
BorderSizesRole = Qt::UserRole + 12,
|
|
||||||
ButtonSizeRole = Qt::UserRole + 13,
|
|
||||||
QmlMainScriptRole = Qt::UserRole + 14,
|
|
||||||
CloseOnDblClickRole = Qt::UserRole + 15,
|
|
||||||
ConfigTranslationDomain = Qt::UserRole + 16
|
|
||||||
};
|
|
||||||
explicit DecorationModel(KSharedConfigPtr config, QObject* parent = nullptr);
|
|
||||||
~DecorationModel();
|
|
||||||
|
|
||||||
virtual QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const;
|
QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override;
|
||||||
virtual int rowCount(const QModelIndex& parent = QModelIndex()) const;
|
int rowCount(const QModelIndex &parent = QModelIndex()) const override;
|
||||||
virtual bool setData(const QModelIndex& index, const QVariant& value, int role = Qt::EditRole);
|
QHash< int, QByteArray > roleNames() const override;
|
||||||
|
|
||||||
void reload();
|
QModelIndex findDecoration(const QString &pluginName, const QString &themeName = QString()) const;
|
||||||
|
|
||||||
/**
|
public Q_SLOTS:
|
||||||
* Changes the button state and regenerates the preview.
|
void init();
|
||||||
*/
|
|
||||||
void changeButtons(const DecorationButtons *buttons);
|
|
||||||
/**
|
|
||||||
* Changes the button state without regenerating the preview.
|
|
||||||
*/
|
|
||||||
void setButtons(bool custom, const QList<KDecorationDefines::DecorationButton>& left, const QList<KDecorationDefines::DecorationButton>& right);
|
|
||||||
|
|
||||||
void setBorderSize(const QModelIndex& index, KDecorationDefines::BorderSize size);
|
|
||||||
|
|
||||||
QModelIndex indexOfLibrary(const QString& libraryName) const;
|
|
||||||
QModelIndex indexOfName(const QString& decoName) const;
|
|
||||||
QModelIndex indexOfAuroraeName(const QString& auroraeName, const QString& type) const;
|
|
||||||
|
|
||||||
Q_INVOKABLE QVariant readConfig(const QString &themeName, const QString &key, const QVariant &defaultValue = QVariant());
|
|
||||||
|
|
||||||
void notifyConfigChanged(const QModelIndex &index);
|
|
||||||
|
|
||||||
Q_SIGNALS:
|
|
||||||
void configChanged(QString themeName);
|
|
||||||
private:
|
private:
|
||||||
void findDecorations();
|
struct Data {
|
||||||
void findAuroraeThemes();
|
QString pluginName;
|
||||||
void metaData(DecorationModelData& data, const KDesktopFile& df);
|
QString themeName;
|
||||||
QList<DecorationModelData> m_decorations;
|
QString visibleName;
|
||||||
KDecorationPlugins* m_plugins;
|
};
|
||||||
KDecorationPreview* m_preview;
|
std::vector<Data> m_plugins;
|
||||||
bool m_customButtons;
|
|
||||||
KSharedConfigPtr m_config;
|
|
||||||
QScopedPointer<KDecorationPreviewOptions> m_options;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace KWin
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#endif // KWIN_DECORATIONMODEL_H
|
#endif
|
||||||
|
|
128
kcmkwin/kwindecoration/kcm.cpp
Normal file
128
kcmkwin/kwindecoration/kcm.cpp
Normal file
|
@ -0,0 +1,128 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#include "kcm.h"
|
||||||
|
#include "decorationmodel.h"
|
||||||
|
|
||||||
|
// KDE
|
||||||
|
#include <KConfigGroup>
|
||||||
|
#include <KPluginFactory>
|
||||||
|
#include <KSharedConfig>
|
||||||
|
// Qt
|
||||||
|
#include <QDBusConnection>
|
||||||
|
#include <QDBusMessage>
|
||||||
|
#include <QQmlContext>
|
||||||
|
#include <QQmlEngine>
|
||||||
|
#include <QQuickItem>
|
||||||
|
#include <QQuickWidget>
|
||||||
|
#include <QStandardPaths>
|
||||||
|
#include <QVBoxLayout>
|
||||||
|
|
||||||
|
K_PLUGIN_FACTORY(KDecorationFactory,
|
||||||
|
registerPlugin<KDecoration2::Configuration::ConfigurationModule>();
|
||||||
|
)
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
|
||||||
|
namespace Configuration
|
||||||
|
{
|
||||||
|
static const QString s_pluginName = QStringLiteral("org.kde.kdecoration2");
|
||||||
|
static const QString s_defaultPlugin = QStringLiteral("org.kde.breeze");
|
||||||
|
|
||||||
|
ConfigurationModule::ConfigurationModule(QWidget *parent, const QVariantList &args)
|
||||||
|
: KCModule(parent, args)
|
||||||
|
, m_view(new QQuickWidget(this))
|
||||||
|
, m_model(new DecorationsModel(this))
|
||||||
|
{
|
||||||
|
m_view->rootContext()->setContextProperty(QStringLiteral("decorationsModel"), m_model);
|
||||||
|
m_view->rootContext()->setContextProperty("highlightColor", QPalette().color(QPalette::Highlight));
|
||||||
|
m_view->setResizeMode(QQuickWidget::SizeRootObjectToView);
|
||||||
|
m_view->setSource(QUrl::fromLocalFile(QStandardPaths::locate(QStandardPaths::GenericDataLocation, QStringLiteral("kwin/kcm_kwindecoration/main.qml"))));
|
||||||
|
if (m_view->status() == QQuickWidget::Ready) {
|
||||||
|
auto listView = m_view->rootObject()->findChild<QQuickItem*>("listView");
|
||||||
|
if (listView) {
|
||||||
|
connect(listView, SIGNAL(currentIndexChanged()), this, SLOT(changed()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
QVBoxLayout *l = new QVBoxLayout(this);
|
||||||
|
l->addWidget(m_view);
|
||||||
|
QMetaObject::invokeMethod(m_model, "init", Qt::QueuedConnection);
|
||||||
|
}
|
||||||
|
|
||||||
|
ConfigurationModule::~ConfigurationModule() = default;
|
||||||
|
|
||||||
|
void ConfigurationModule::showEvent(QShowEvent *ev)
|
||||||
|
{
|
||||||
|
KCModule::showEvent(ev);
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConfigurationModule::load()
|
||||||
|
{
|
||||||
|
const KConfigGroup config = KSharedConfig::openConfig("kwinrc")->group(s_pluginName);
|
||||||
|
const QString plugin = config.readEntry("library", s_defaultPlugin);
|
||||||
|
const QString theme = config.readEntry("theme", QString());
|
||||||
|
const QModelIndex index = m_model->findDecoration(plugin, theme);
|
||||||
|
if (auto listView = m_view->rootObject()->findChild<QQuickItem*>("listView")) {
|
||||||
|
listView->setProperty("currentIndex", index.isValid() ? index.row() : -1);
|
||||||
|
}
|
||||||
|
KCModule::load();
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConfigurationModule::save()
|
||||||
|
{
|
||||||
|
if (auto listView = m_view->rootObject()->findChild<QQuickItem*>("listView")) {
|
||||||
|
const int currentIndex = listView->property("currentIndex").toInt();
|
||||||
|
if (currentIndex != -1) {
|
||||||
|
const QModelIndex index = m_model->index(currentIndex, 0);
|
||||||
|
if (index.isValid()) {
|
||||||
|
KConfigGroup config = KSharedConfig::openConfig("kwinrc")->group(s_pluginName);
|
||||||
|
config.writeEntry("library", index.data(Qt::UserRole + 4).toString());
|
||||||
|
const QString theme = index.data(Qt::UserRole +5).toString();
|
||||||
|
if (theme.isEmpty()) {
|
||||||
|
config.deleteEntry("theme");
|
||||||
|
} else {
|
||||||
|
config.writeEntry("theme", theme);
|
||||||
|
}
|
||||||
|
config.sync();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
KCModule::save();
|
||||||
|
// Send signal to all kwin instances
|
||||||
|
QDBusMessage message = QDBusMessage::createSignal(QStringLiteral("/KWin"),
|
||||||
|
QStringLiteral("org.kde.KWin"),
|
||||||
|
QStringLiteral("reloadConfig"));
|
||||||
|
QDBusConnection::sessionBus().send(message);
|
||||||
|
}
|
||||||
|
|
||||||
|
void ConfigurationModule::defaults()
|
||||||
|
{
|
||||||
|
if (auto listView = m_view->rootObject()->findChild<QQuickItem*>("listView")) {
|
||||||
|
const QModelIndex index = m_model->findDecoration(s_defaultPlugin);
|
||||||
|
listView->setProperty("currentIndex", index.isValid() ? index.row() : -1);
|
||||||
|
}
|
||||||
|
KCModule::defaults();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#include "kcm.moc"
|
61
kcmkwin/kwindecoration/kcm.h
Normal file
61
kcmkwin/kwindecoration/kcm.h
Normal file
|
@ -0,0 +1,61 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2014 Martin Gräßlin <mgraesslin@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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#ifndef KDECORATIONS_KCM_H
|
||||||
|
#define KDECORATIONS_KCM_H
|
||||||
|
|
||||||
|
#include <kcmodule.h>
|
||||||
|
|
||||||
|
class QQuickWidget;
|
||||||
|
|
||||||
|
namespace KDecoration2
|
||||||
|
{
|
||||||
|
namespace Preview
|
||||||
|
{
|
||||||
|
class PreviewBridge;
|
||||||
|
}
|
||||||
|
namespace Configuration
|
||||||
|
{
|
||||||
|
class DecorationsModel;
|
||||||
|
|
||||||
|
class ConfigurationModule : public KCModule
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
explicit ConfigurationModule(QWidget *parent = nullptr, const QVariantList &args = QVariantList());
|
||||||
|
virtual ~ConfigurationModule();
|
||||||
|
|
||||||
|
public Q_SLOTS:
|
||||||
|
void defaults() override;
|
||||||
|
void load() override;
|
||||||
|
void save() override;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void showEvent(QShowEvent *ev) override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
QQuickWidget *m_view;
|
||||||
|
DecorationsModel *m_model;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -1,600 +0,0 @@
|
||||||
/*
|
|
||||||
This is the new kwindecoration kcontrol module
|
|
||||||
|
|
||||||
Copyright (c) 2001
|
|
||||||
Karol Szwed <gallium@kde.org>
|
|
||||||
http://gallium.n3.net/
|
|
||||||
Copyright 2009, 2010 Martin Gräßlin <mgraesslin@kde.org>
|
|
||||||
|
|
||||||
Supports new kwin configuration plugins, and titlebar button position
|
|
||||||
modification via dnd interface.
|
|
||||||
|
|
||||||
Based on original "kwintheme" (Window Borders)
|
|
||||||
Copyright (C) 2001 Rik Hemsley (rikkus) <rik@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.
|
|
||||||
|
|
||||||
*/
|
|
||||||
// own
|
|
||||||
#include "kwindecoration.h"
|
|
||||||
#include "buttonsconfigdialog.h"
|
|
||||||
#include "configdialog.h"
|
|
||||||
#include "decorationmodel.h"
|
|
||||||
#include "auroraetheme.h"
|
|
||||||
#include "preview.h"
|
|
||||||
// Qt
|
|
||||||
#include <QtDBus/QtDBus>
|
|
||||||
#include <QSortFilterProxyModel>
|
|
||||||
#include <QScrollBar>
|
|
||||||
#include <QUiLoader>
|
|
||||||
#include <QtCore/QStandardPaths>
|
|
||||||
#include <QQmlContext>
|
|
||||||
#include <QQuickItem>
|
|
||||||
#include <QQuickView>
|
|
||||||
// KDE
|
|
||||||
#include <KAboutData>
|
|
||||||
#include <kconfigloader.h>
|
|
||||||
#include <KLocalizedString>
|
|
||||||
#include <KLocalizedTranslator>
|
|
||||||
#include <KMessageBox>
|
|
||||||
#include <KNewStuff3/KNS3/DownloadDialog>
|
|
||||||
#include <KConfigDialogManager>
|
|
||||||
#include <KPluginFactory>
|
|
||||||
|
|
||||||
// KCModule plugin interface
|
|
||||||
// =========================
|
|
||||||
K_PLUGIN_FACTORY(KWinDecoFactory,
|
|
||||||
registerPlugin<KWin::KWinDecorationModule>();
|
|
||||||
)
|
|
||||||
|
|
||||||
namespace KWin
|
|
||||||
{
|
|
||||||
|
|
||||||
static const QString s_defaultPluginName = QStringLiteral("Oxygen");
|
|
||||||
|
|
||||||
KWinDecorationForm::KWinDecorationForm(QWidget* parent)
|
|
||||||
: QWidget(parent)
|
|
||||||
{
|
|
||||||
setupUi(this);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
KWinDecorationModule::KWinDecorationModule(QWidget* parent, const QVariantList &)
|
|
||||||
: KCModule(parent)
|
|
||||||
, kwinConfig(KSharedConfig::openConfig("kwinrc"))
|
|
||||||
, m_showTooltips(false)
|
|
||||||
, m_model(nullptr)
|
|
||||||
, m_proxyModel(nullptr)
|
|
||||||
, m_configLoaded(false)
|
|
||||||
, m_decorationButtons(new DecorationButtons(this))
|
|
||||||
, m_listView(new QQuickView())
|
|
||||||
, m_translator(new KLocalizedTranslator(this))
|
|
||||||
{
|
|
||||||
qmlRegisterType<Aurorae::AuroraeTheme>("org.kde.kwin.aurorae", 0, 1, "AuroraeTheme");
|
|
||||||
qmlRegisterType<PreviewItem>("org.kde.kwin.kcmdecoration", 0, 1, "PreviewItem");
|
|
||||||
m_ui = new KWinDecorationForm(this);
|
|
||||||
m_ui->configureDecorationButton->setIcon(QIcon::fromTheme("configure"));
|
|
||||||
m_ui->configureButtonsButton->setIcon(QIcon::fromTheme("configure"));
|
|
||||||
m_ui->ghnsButton->setIcon(QIcon::fromTheme("get-hot-new-stuff"));
|
|
||||||
QWidget *container = QWidget::createWindowContainer(m_listView.data(), m_ui->decorationList->viewport());
|
|
||||||
QVBoxLayout *containerLayout = new QVBoxLayout(m_ui->decorationList->viewport());
|
|
||||||
containerLayout->addWidget(container);
|
|
||||||
QVBoxLayout* layout = new QVBoxLayout(this);
|
|
||||||
layout->addWidget(m_ui);
|
|
||||||
|
|
||||||
KAboutData *about =
|
|
||||||
new KAboutData(QStringLiteral("kcmkwindecoration"),
|
|
||||||
i18n("Window Decoration Control Module"),
|
|
||||||
QString(), QString(), KAboutLicense::GPL,
|
|
||||||
i18n("(c) 2001 Karol Szwed"));
|
|
||||||
about->addAuthor(i18n("Karol Szwed"), QString(), "gallium@kde.org");
|
|
||||||
setAboutData(about);
|
|
||||||
|
|
||||||
QCoreApplication::instance()->installTranslator(m_translator);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
KWinDecorationModule::~KWinDecorationModule()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KWinDecorationModule::showEvent(QShowEvent *ev)
|
|
||||||
{
|
|
||||||
KCModule::showEvent(ev);
|
|
||||||
init();
|
|
||||||
}
|
|
||||||
|
|
||||||
void KWinDecorationModule::init()
|
|
||||||
{
|
|
||||||
if (m_model) {
|
|
||||||
// init already called
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
const QString mainQmlPath = QStandardPaths::locate(QStandardPaths::GenericDataLocation, "kwin/kcm_kwindecoration/main.qml");
|
|
||||||
if (mainQmlPath.isNull()) {
|
|
||||||
KMessageBox::error(this, i18n("<h1>Installation error</h1>"
|
|
||||||
"The resource<h2>kwin/kcm_kwindecoration/main.qml</h2>could not be located in any application data path."
|
|
||||||
"<h2>Please contact your distribution</h2>"
|
|
||||||
"The application will now abort"), i18n("Installation Error"));
|
|
||||||
abort();
|
|
||||||
}
|
|
||||||
KConfigGroup style(kwinConfig, "Style");
|
|
||||||
|
|
||||||
// Set up the decoration lists and other UI settings
|
|
||||||
m_model = new DecorationModel(kwinConfig, this);
|
|
||||||
m_proxyModel = new QSortFilterProxyModel(this);
|
|
||||||
m_proxyModel->setSourceModel(m_model);
|
|
||||||
m_proxyModel->setFilterCaseSensitivity(Qt::CaseInsensitive);
|
|
||||||
|
|
||||||
m_listView->setResizeMode(QQuickView::SizeRootObjectToView);
|
|
||||||
m_listView->rootContext()->setContextProperty("decorationModel", m_proxyModel);
|
|
||||||
m_listView->rootContext()->setContextProperty("decorationBaseModel", m_model);
|
|
||||||
m_listView->rootContext()->setContextProperty("options", m_decorationButtons);
|
|
||||||
m_listView->rootContext()->setContextProperty("highlightColor", m_ui->decorationList->palette().color(QPalette::Highlight));
|
|
||||||
m_listView->rootContext()->setContextProperty("auroraeSource", QStandardPaths::locate(QStandardPaths::GenericDataLocation, "kwin/aurorae/aurorae.qml"));
|
|
||||||
m_listView->rootContext()->setContextProperty("decorationActiveCaptionColor", KDecoration::options()->color(ColorFont, true));
|
|
||||||
m_listView->rootContext()->setContextProperty("decorationInactiveCaptionColor", KDecoration::options()->color(ColorFont, false));
|
|
||||||
m_listView->rootContext()->setContextProperty("decorationActiveTitleBarColor", KDecoration::options()->color(ColorTitleBar, true));
|
|
||||||
m_listView->rootContext()->setContextProperty("decorationInactiveTitleBarColor", KDecoration::options()->color(ColorTitleBar, false));
|
|
||||||
m_listView->setSource(QUrl::fromLocalFile(mainQmlPath));
|
|
||||||
|
|
||||||
readConfig(style);
|
|
||||||
|
|
||||||
connect(m_listView->rootObject(), SIGNAL(currentIndexChanged()), SLOT(slotSelectionChanged()));
|
|
||||||
connect(m_ui->configureButtonsButton, SIGNAL(clicked(bool)), this, SLOT(slotConfigureButtons()));
|
|
||||||
connect(m_ui->ghnsButton, SIGNAL(clicked(bool)), SLOT(slotGHNSClicked()));
|
|
||||||
connect(m_ui->searchEdit, SIGNAL(textChanged(QString)), m_proxyModel, SLOT(setFilterFixedString(QString)));
|
|
||||||
connect(m_ui->searchEdit, SIGNAL(textChanged(QString)), m_listView->rootObject(), SLOT(returnToBounds()), Qt::QueuedConnection);
|
|
||||||
connect(m_ui->searchEdit, SIGNAL(textChanged(QString)), SLOT(updateScrollbarRange()), Qt::QueuedConnection);
|
|
||||||
connect(m_ui->configureDecorationButton, SIGNAL(clicked(bool)), SLOT(slotConfigureDecoration()));
|
|
||||||
|
|
||||||
m_ui->decorationList->disconnect(m_ui->decorationList->verticalScrollBar());
|
|
||||||
m_ui->decorationList->verticalScrollBar()->disconnect(m_ui->decorationList);
|
|
||||||
connect(m_listView->rootObject(), SIGNAL(contentYChanged()), SLOT(updateScrollbarValue()));
|
|
||||||
connect(m_listView->rootObject(), SIGNAL(contentHeightChanged()), SLOT(updateScrollbarRange()));
|
|
||||||
connect(m_ui->decorationList->verticalScrollBar(), SIGNAL(rangeChanged(int,int)), SLOT(updateScrollbarRange()));
|
|
||||||
connect(m_ui->decorationList->verticalScrollBar(), SIGNAL(valueChanged(int)), SLOT(updateViewPosition(int)));
|
|
||||||
|
|
||||||
m_ui->decorationList->installEventFilter(this);
|
|
||||||
m_ui->decorationList->viewport()->installEventFilter(this);
|
|
||||||
QMetaObject::invokeMethod(this, "updatePreviews", Qt::QueuedConnection);
|
|
||||||
updateScrollbarRange();
|
|
||||||
}
|
|
||||||
|
|
||||||
// This is the selection handler setting
|
|
||||||
void KWinDecorationModule::slotSelectionChanged()
|
|
||||||
{
|
|
||||||
emit KCModule::changed(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Reads the kwin config settings, and sets all UI controls to those settings
|
|
||||||
// Updating the config plugin if required
|
|
||||||
void KWinDecorationModule::readConfig(const KConfigGroup & conf)
|
|
||||||
{
|
|
||||||
m_showTooltips = conf.readEntry("ShowToolTips", true);
|
|
||||||
|
|
||||||
// Find the corresponding decoration name to that of
|
|
||||||
// the current plugin library name
|
|
||||||
|
|
||||||
QString libraryName = conf.readEntry("PluginLib", s_defaultPluginName);
|
|
||||||
|
|
||||||
if (libraryName.isEmpty()) {
|
|
||||||
// Selected decoration doesn't exist, use the default
|
|
||||||
libraryName = s_defaultPluginName;
|
|
||||||
}
|
|
||||||
|
|
||||||
const int bsize = conf.readEntry("BorderSize", (int)BorderNormal);
|
|
||||||
BorderSize borderSize = BorderNormal;
|
|
||||||
if (bsize >= BorderTiny && bsize < BordersCount)
|
|
||||||
borderSize = static_cast< BorderSize >(bsize);
|
|
||||||
if (libraryName == "aurorae") {
|
|
||||||
KConfig auroraeConfig("auroraerc");
|
|
||||||
KConfigGroup group(&auroraeConfig, "Engine");
|
|
||||||
const QString themeName = group.readEntry("ThemeName", "example-deco");
|
|
||||||
const QString type = group.readEntry("EngineType", "aurorae");
|
|
||||||
const QModelIndex index = m_proxyModel->mapFromSource(m_model->indexOfAuroraeName(themeName, type));
|
|
||||||
if (index.isValid()) {
|
|
||||||
m_listView->rootObject()->setProperty("currentIndex", index.row());
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
const QModelIndex index = m_proxyModel->mapFromSource(m_model->indexOfLibrary(libraryName));
|
|
||||||
if (index.isValid()) {
|
|
||||||
m_model->setBorderSize(index, borderSize);
|
|
||||||
m_listView->rootObject()->setProperty("currentIndex", index.row());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Buttons tab
|
|
||||||
// ============
|
|
||||||
m_decorationButtons->setCustomPositions(conf.readEntry("CustomButtonPositions", false));
|
|
||||||
// Menu and onAllDesktops buttons are default on LHS
|
|
||||||
m_decorationButtons->setLeftButtons(KDecorationOptions::readDecorationButtons(conf, "ButtonsOnLeft",
|
|
||||||
KDecorationOptions::defaultTitleButtonsLeft()));
|
|
||||||
// Help, Minimize, Maximize and Close are default on RHS
|
|
||||||
m_decorationButtons->setRightButtons(KDecorationOptions::readDecorationButtons(conf, "ButtonsOnRight",
|
|
||||||
KDecorationOptions::defaultTitleButtonsRight()));
|
|
||||||
if (m_configLoaded)
|
|
||||||
m_model->changeButtons(m_decorationButtons);
|
|
||||||
else {
|
|
||||||
m_configLoaded = true;
|
|
||||||
m_model->setButtons(m_decorationButtons->customPositions(), m_decorationButtons->leftButtons(), m_decorationButtons->rightButtons());
|
|
||||||
}
|
|
||||||
|
|
||||||
emit KCModule::changed(false);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Writes the selected user configuration to the kwin config file
|
|
||||||
void KWinDecorationModule::writeConfig(KConfigGroup & conf)
|
|
||||||
{
|
|
||||||
const QModelIndex index = m_proxyModel->mapToSource(m_proxyModel->index(m_listView->rootObject()->property("currentIndex").toInt(), 0));
|
|
||||||
const QString libName = m_model->data(index, DecorationModel::LibraryNameRole).toString();
|
|
||||||
|
|
||||||
// General settings
|
|
||||||
conf.writeEntry("PluginLib", libName);
|
|
||||||
conf.writeEntry("CustomButtonPositions", m_decorationButtons->customPositions());
|
|
||||||
conf.writeEntry("ShowToolTips", m_showTooltips);
|
|
||||||
|
|
||||||
// Button settings
|
|
||||||
KDecorationOptions::writeDecorationButtons(conf, "ButtonsOnLeft", m_decorationButtons->leftButtons());
|
|
||||||
KDecorationOptions::writeDecorationButtons(conf, "ButtonsOnRight", m_decorationButtons->rightButtons());
|
|
||||||
conf.writeEntry("BorderSize",
|
|
||||||
static_cast<int>(m_model->data(index, DecorationModel::BorderSizeRole).toInt()));
|
|
||||||
|
|
||||||
if (m_model->data(index, DecorationModel::TypeRole).toInt() == DecorationModelData::AuroraeDecoration ||
|
|
||||||
m_model->data(index, DecorationModel::TypeRole).toInt() == DecorationModelData::QmlDecoration) {
|
|
||||||
KConfig auroraeConfig("auroraerc");
|
|
||||||
KConfigGroup group(&auroraeConfig, "Engine");
|
|
||||||
group.writeEntry("ThemeName", m_model->data(index, DecorationModel::AuroraeNameRole).toString());
|
|
||||||
if (m_model->data(index, DecorationModel::TypeRole).toInt() == DecorationModelData::QmlDecoration) {
|
|
||||||
group.writeEntry("EngineType", "qml");
|
|
||||||
} else {
|
|
||||||
group.deleteEntry("EngineType");
|
|
||||||
}
|
|
||||||
group.sync();
|
|
||||||
}
|
|
||||||
|
|
||||||
// We saved, so tell kcmodule that there have been no new user changes made.
|
|
||||||
emit KCModule::changed(false);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Virutal functions required by KCModule
|
|
||||||
void KWinDecorationModule::load()
|
|
||||||
{
|
|
||||||
const KConfigGroup config(kwinConfig, "Style");
|
|
||||||
|
|
||||||
// Reset by re-reading the config
|
|
||||||
readConfig(config);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void KWinDecorationModule::save()
|
|
||||||
{
|
|
||||||
KConfigGroup config(kwinConfig, "Style");
|
|
||||||
writeConfig(config);
|
|
||||||
config.sync();
|
|
||||||
|
|
||||||
// Send signal to all kwin instances
|
|
||||||
QDBusMessage message =
|
|
||||||
QDBusMessage::createSignal("/KWin", "org.kde.KWin", "reloadConfig");
|
|
||||||
QDBusConnection::sessionBus().send(message);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void KWinDecorationModule::defaults()
|
|
||||||
{
|
|
||||||
// Set the KDE defaults
|
|
||||||
m_showTooltips = true;
|
|
||||||
const QModelIndex index = m_proxyModel->mapFromSource(m_model->indexOfName(i18n("Oxygen")));
|
|
||||||
if (index.isValid())
|
|
||||||
m_listView->rootObject()->setProperty("currentIndex", index.row());
|
|
||||||
|
|
||||||
m_decorationButtons->resetToDefaults();
|
|
||||||
|
|
||||||
m_model->changeButtons(m_decorationButtons);
|
|
||||||
|
|
||||||
emit changed(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
QString KWinDecorationModule::quickHelp() const
|
|
||||||
{
|
|
||||||
return i18n("<h1>Window Manager Decoration</h1>"
|
|
||||||
"<p>This module allows you to choose the window border decorations, "
|
|
||||||
"as well as titlebar button positions and custom decoration options.</p>"
|
|
||||||
"To choose a theme for your window decoration click on its name and apply your choice by clicking the \"Apply\" button below."
|
|
||||||
" If you do not want to apply your choice you can click the \"Reset\" button to discard your changes."
|
|
||||||
"<p>You can configure each theme. There are different options specific for each theme.</p>"
|
|
||||||
"<p>On the \"Buttons\" tab check the \"Use custom titlebar button positions\" box "
|
|
||||||
"and you can change the positions of the buttons to your liking.</p>");
|
|
||||||
}
|
|
||||||
|
|
||||||
void KWinDecorationModule::slotConfigureButtons()
|
|
||||||
{
|
|
||||||
QPointer< KWinDecorationButtonsConfigDialog > configDialog = new KWinDecorationButtonsConfigDialog(m_decorationButtons, m_showTooltips, this);
|
|
||||||
if (configDialog->exec() == QDialog::Accepted) {
|
|
||||||
m_decorationButtons->setCustomPositions(configDialog->customPositions());
|
|
||||||
m_showTooltips = configDialog->showTooltips();
|
|
||||||
m_decorationButtons->setLeftButtons(configDialog->buttonsLeft());
|
|
||||||
m_decorationButtons->setRightButtons(configDialog->buttonsRight());
|
|
||||||
m_model->changeButtons(m_decorationButtons);
|
|
||||||
emit changed(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
delete configDialog;
|
|
||||||
}
|
|
||||||
|
|
||||||
void KWinDecorationModule::slotGHNSClicked()
|
|
||||||
{
|
|
||||||
QPointer<KNS3::DownloadDialog> downloadDialog = new KNS3::DownloadDialog("aurorae.knsrc", this);
|
|
||||||
if (downloadDialog->exec() == QDialog::Accepted) {
|
|
||||||
if (!downloadDialog->changedEntries().isEmpty()) {
|
|
||||||
const QModelIndex index = m_proxyModel->mapToSource(m_proxyModel->index(m_listView->rootObject()->property("currentIndex").toInt(), 0));
|
|
||||||
const QString libraryName = m_model->data(index, DecorationModel::LibraryNameRole).toString();
|
|
||||||
bool aurorae = m_model->data(index, DecorationModel::TypeRole).toInt() == DecorationModelData::AuroraeDecoration;
|
|
||||||
bool qml = m_model->data(index, DecorationModel::TypeRole).toInt() == DecorationModelData::QmlDecoration;
|
|
||||||
const QString auroraeName = m_model->data(index, DecorationModel::AuroraeNameRole).toString();
|
|
||||||
m_model->reload();
|
|
||||||
if (aurorae) {
|
|
||||||
const QModelIndex proxyIndex = m_proxyModel->mapFromSource(m_model->indexOfAuroraeName(auroraeName, "aurorae"));
|
|
||||||
if (proxyIndex.isValid())
|
|
||||||
m_listView->rootObject()->setProperty("currentIndex", proxyIndex.row());
|
|
||||||
} else if (qml) {
|
|
||||||
const QModelIndex proxyIndex = m_proxyModel->mapFromSource(m_model->indexOfAuroraeName(auroraeName, "qml"));
|
|
||||||
if (proxyIndex.isValid())
|
|
||||||
m_listView->rootObject()->setProperty("currentIndex", proxyIndex.row());
|
|
||||||
} else {
|
|
||||||
const QModelIndex proxyIndex = m_proxyModel->mapFromSource(m_model->indexOfLibrary(libraryName));
|
|
||||||
if (proxyIndex.isValid())
|
|
||||||
m_listView->rootObject()->setProperty("currentIndex", proxyIndex.row());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
delete downloadDialog;
|
|
||||||
}
|
|
||||||
|
|
||||||
void KWinDecorationModule::slotConfigureDecoration()
|
|
||||||
{
|
|
||||||
const QModelIndex index = m_proxyModel->mapToSource(m_proxyModel->index(m_listView->rootObject()->property("currentIndex").toInt(), 0));
|
|
||||||
bool reload = false;
|
|
||||||
if (index.data(DecorationModel::TypeRole).toInt() == DecorationModelData::AuroraeDecoration ||
|
|
||||||
index.data(DecorationModel::TypeRole).toInt() == DecorationModelData::QmlDecoration) {
|
|
||||||
QPointer<QDialog> dlg = new QDialog(this);
|
|
||||||
dlg->setWindowTitle(i18n("Decoration Options"));
|
|
||||||
KWinAuroraeConfigForm *form = new KWinAuroraeConfigForm(dlg);
|
|
||||||
form->enableNoSideBorderSupport(index.data(DecorationModel::TypeRole).toInt() == DecorationModelData::QmlDecoration);
|
|
||||||
dlg->setLayout(new QVBoxLayout);
|
|
||||||
QDialogButtonBox* buttons = new QDialogButtonBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel, dlg.data());
|
|
||||||
connect(buttons, SIGNAL(accepted()), dlg, SLOT(accept()));
|
|
||||||
connect(buttons, SIGNAL(rejected()), dlg, SLOT(reject()));
|
|
||||||
dlg->layout()->addWidget(form);
|
|
||||||
dlg->layout()->addWidget(buttons);
|
|
||||||
|
|
||||||
form->borderSizesCombo->setCurrentIndex(index.data(DecorationModel::BorderSizeRole).toInt());
|
|
||||||
form->buttonSizesCombo->setCurrentIndex(index.data(DecorationModel::ButtonSizeRole).toInt());
|
|
||||||
form->closeWindowsDoubleClick->setChecked(index.data(DecorationModel::CloseOnDblClickRole).toBool());
|
|
||||||
form->doubleClickMessage->setCloseButtonVisible(true);
|
|
||||||
form->doubleClickMessage->setText(i18n("Close by double clicking:\n To open the menu, keep the button pressed until it appears."));
|
|
||||||
form->doubleClickMessage->setVisible(false);
|
|
||||||
connect(form->closeWindowsDoubleClick, &QCheckBox::toggled, [form](bool toggled) {
|
|
||||||
if (!toggled) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
form->doubleClickMessage->animatedShow();
|
|
||||||
});
|
|
||||||
// in case of QmlDecoration look for a config.ui in the package structure
|
|
||||||
KConfigDialogManager *configManager = nullptr;
|
|
||||||
if (index.data(DecorationModel::TypeRole).toInt() == DecorationModelData::QmlDecoration) {
|
|
||||||
const QString packageName = index.data(DecorationModel::AuroraeNameRole).toString();
|
|
||||||
const QString uiPath = QStandardPaths::locate(QStandardPaths::GenericDataLocation, "kwin/decorations/" + packageName + "/contents/ui/config.ui");
|
|
||||||
const QString configPath = QStandardPaths::locate(QStandardPaths::GenericDataLocation, "kwin/decorations/" + packageName + "/contents/config/main.xml");
|
|
||||||
if (!uiPath.isEmpty() && !configPath.isEmpty()) {
|
|
||||||
// load the KConfigSkeleton
|
|
||||||
QFile configFile(configPath);
|
|
||||||
KSharedConfigPtr auroraeConfig = KSharedConfig::openConfig("auroraerc");
|
|
||||||
KConfigGroup configGroup = auroraeConfig->group(packageName);
|
|
||||||
KConfigLoader *skeleton = new KConfigLoader(configGroup, &configFile, dlg);
|
|
||||||
// load the ui file
|
|
||||||
m_translator->setTranslationDomain(index.data(DecorationModel::ConfigTranslationDomain).toString());
|
|
||||||
QUiLoader *loader = new QUiLoader(dlg);
|
|
||||||
loader->setLanguageChangeEnabled(true);
|
|
||||||
QFile uiFile(uiPath);
|
|
||||||
uiFile.open(QFile::ReadOnly);
|
|
||||||
QWidget *customConfigForm = loader->load(&uiFile, form);
|
|
||||||
m_translator->addContextToMonitor(customConfigForm->objectName());
|
|
||||||
uiFile.close();
|
|
||||||
form->layout()->addWidget(customConfigForm);
|
|
||||||
// connect the ui file with the skeleton
|
|
||||||
configManager = new KConfigDialogManager(customConfigForm, skeleton);
|
|
||||||
configManager->updateWidgets();
|
|
||||||
|
|
||||||
// send a custom event to the translator to retranslate using our translator
|
|
||||||
QEvent le(QEvent::LanguageChange);
|
|
||||||
QCoreApplication::sendEvent(customConfigForm, &le);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (dlg->exec() == QDialog::Accepted) {
|
|
||||||
m_model->setData(index, form->borderSizesCombo->currentIndex(), DecorationModel::BorderSizeRole);
|
|
||||||
m_model->setData(index, form->buttonSizesCombo->currentIndex(), DecorationModel::ButtonSizeRole);
|
|
||||||
m_model->setData(index, form->closeWindowsDoubleClick->isChecked(), DecorationModel::CloseOnDblClickRole);
|
|
||||||
if (configManager && configManager->hasChanged()) {
|
|
||||||
// we have a config manager and the settings changed
|
|
||||||
configManager->updateSettings();
|
|
||||||
m_model->notifyConfigChanged(index);
|
|
||||||
}
|
|
||||||
reload = true;
|
|
||||||
}
|
|
||||||
delete dlg;
|
|
||||||
} else {
|
|
||||||
QString name = index.data(DecorationModel::LibraryNameRole).toString();
|
|
||||||
QList< QVariant > borderSizes = index.data(DecorationModel::BorderSizesRole).toList();
|
|
||||||
const KDecorationDefines::BorderSize size =
|
|
||||||
static_cast<KDecorationDefines::BorderSize>(index.data(DecorationModel::BorderSizeRole).toInt());
|
|
||||||
QPointer< KWinDecorationConfigDialog > configDialog =
|
|
||||||
new KWinDecorationConfigDialog(name, borderSizes, size, this);
|
|
||||||
if (configDialog->exec() == QDialog::Accepted) {
|
|
||||||
m_model->setData(index, configDialog->borderSize(), DecorationModel::BorderSizeRole);
|
|
||||||
reload = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
delete configDialog;
|
|
||||||
}
|
|
||||||
if (reload) {
|
|
||||||
save();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KWinDecorationModule::eventFilter(QObject *o, QEvent *e)
|
|
||||||
{
|
|
||||||
if (o == m_ui->decorationList) {
|
|
||||||
if (e->type() == QEvent::Resize)
|
|
||||||
updateScrollbarRange();
|
|
||||||
else if (e->type() == QEvent::KeyPress) {
|
|
||||||
int d = 0;
|
|
||||||
const int currentRow = m_listView->rootObject()->property("currentIndex").toInt();
|
|
||||||
const int key = static_cast<QKeyEvent*>(e)->key();
|
|
||||||
switch (key) {
|
|
||||||
case Qt::Key_Home:
|
|
||||||
d = -currentRow;
|
|
||||||
break;
|
|
||||||
case Qt::Key_End:
|
|
||||||
d = m_proxyModel->rowCount() - (1 + currentRow);
|
|
||||||
break;
|
|
||||||
case Qt::Key_Up:
|
|
||||||
d = -1;
|
|
||||||
break;
|
|
||||||
case Qt::Key_Down:
|
|
||||||
d = 1;
|
|
||||||
break;
|
|
||||||
case Qt::Key_PageUp:
|
|
||||||
case Qt::Key_PageDown:
|
|
||||||
d = 150;
|
|
||||||
if (QObject *decoItem = m_listView->rootObject()->findChild<QObject*>("decorationItem")) {
|
|
||||||
QVariant v = decoItem->property("height");
|
|
||||||
if (v.isValid())
|
|
||||||
d = v.toInt();
|
|
||||||
}
|
|
||||||
if (d > 0)
|
|
||||||
d = qMax(m_ui->decorationList->height() / d, 1);
|
|
||||||
if (key == Qt::Key_PageUp)
|
|
||||||
d = -d;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (d) {
|
|
||||||
d = qMin(qMax(0, currentRow + d), m_proxyModel->rowCount());
|
|
||||||
m_listView->rootObject()->setProperty("currentIndex", d);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (m_ui->decorationList->viewport()) {
|
|
||||||
if (e->type() == QEvent::Wheel) {
|
|
||||||
return static_cast<QWheelEvent*>(e)->orientation() == Qt::Horizontal;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return KCModule::eventFilter(o, e);
|
|
||||||
}
|
|
||||||
|
|
||||||
void KWinDecorationModule::updateScrollbarRange()
|
|
||||||
{
|
|
||||||
m_ui->decorationList->verticalScrollBar()->blockSignals(true);
|
|
||||||
const bool atMinimum = m_listView->rootObject()->property("atYBeginning").toBool();
|
|
||||||
const int h = m_listView->rootObject()->property("contentHeight").toInt();
|
|
||||||
const int y = atMinimum ? m_listView->rootObject()->property("contentY").toInt() : 0;
|
|
||||||
m_ui->decorationList->verticalScrollBar()->setRange(y, y + h - m_ui->decorationList->height());
|
|
||||||
m_ui->decorationList->verticalScrollBar()->setPageStep(m_ui->decorationList->verticalScrollBar()->maximum()/m_model->rowCount());
|
|
||||||
m_ui->decorationList->verticalScrollBar()->blockSignals(false);
|
|
||||||
}
|
|
||||||
|
|
||||||
void KWinDecorationModule::updateScrollbarValue()
|
|
||||||
{
|
|
||||||
const int v = m_listView->rootObject()->property("contentY").toInt();
|
|
||||||
m_ui->decorationList->verticalScrollBar()->blockSignals(true); // skippig this will kill kinetic scrolling but the scrollwidth is too low
|
|
||||||
m_ui->decorationList->verticalScrollBar()->setValue(v);
|
|
||||||
m_ui->decorationList->verticalScrollBar()->blockSignals(false);
|
|
||||||
}
|
|
||||||
|
|
||||||
void KWinDecorationModule::updateViewPosition(int v)
|
|
||||||
{
|
|
||||||
m_listView->rootObject()->setProperty("contentY", v);
|
|
||||||
}
|
|
||||||
|
|
||||||
DecorationButtons::DecorationButtons(QObject *parent)
|
|
||||||
: QObject(parent)
|
|
||||||
, m_customPositions(false)
|
|
||||||
, m_leftButtons()
|
|
||||||
, m_rightButtons()
|
|
||||||
{
|
|
||||||
setLeftButtons(KDecorationOptions::defaultTitleButtonsLeft());
|
|
||||||
setRightButtons(KDecorationOptions::defaultTitleButtonsRight());
|
|
||||||
}
|
|
||||||
|
|
||||||
DecorationButtons::~DecorationButtons()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
bool DecorationButtons::customPositions() const
|
|
||||||
{
|
|
||||||
return m_customPositions;
|
|
||||||
}
|
|
||||||
|
|
||||||
const QList<KDecorationDefines::DecorationButton> &DecorationButtons::leftButtons() const
|
|
||||||
{
|
|
||||||
return m_leftButtons;
|
|
||||||
}
|
|
||||||
|
|
||||||
const QList<KDecorationDefines::DecorationButton> &DecorationButtons::rightButtons() const
|
|
||||||
{
|
|
||||||
return m_rightButtons;
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecorationButtons::setCustomPositions(bool set)
|
|
||||||
{
|
|
||||||
if (m_customPositions == set) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
m_customPositions = set;
|
|
||||||
emit customPositionsChanged();
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecorationButtons::setLeftButtons(const QList<DecorationButton> &leftButtons)
|
|
||||||
{
|
|
||||||
if (m_leftButtons == leftButtons) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
m_leftButtons = leftButtons;
|
|
||||||
emit leftButtonsChanged();
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecorationButtons::setRightButtons(const QList<DecorationButton> &rightButtons)
|
|
||||||
{
|
|
||||||
if (m_rightButtons == rightButtons) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
m_rightButtons = rightButtons;
|
|
||||||
emit rightButtonsChanged();
|
|
||||||
}
|
|
||||||
|
|
||||||
void DecorationButtons::resetToDefaults()
|
|
||||||
{
|
|
||||||
setCustomPositions(false);
|
|
||||||
setLeftButtons(KDecorationOptions::defaultTitleButtonsLeft());
|
|
||||||
setRightButtons(KDecorationOptions::defaultTitleButtonsRight());
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace KWin
|
|
||||||
|
|
||||||
#include "kwindecoration.moc"
|
|
|
@ -1,143 +0,0 @@
|
||||||
/*
|
|
||||||
This is the new kwindecoration kcontrol module
|
|
||||||
|
|
||||||
Copyright (c) 2001
|
|
||||||
Karol Szwed <gallium@kde.org>
|
|
||||||
http://gallium.n3.net/
|
|
||||||
Copyright 2009, 2010 Martin Gräßlin <mgraesslin@kde.org>
|
|
||||||
|
|
||||||
Supports new kwin configuration plugins, and titlebar button position
|
|
||||||
modification via dnd interface.
|
|
||||||
|
|
||||||
Based on original "kwintheme" (Window Borders)
|
|
||||||
Copyright (C) 2001 Rik Hemsley (rikkus) <rik@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 KWINDECORATION_H
|
|
||||||
#define KWINDECORATION_H
|
|
||||||
|
|
||||||
#include <kcmodule.h>
|
|
||||||
#include <KSharedConfig>
|
|
||||||
|
|
||||||
#include <kdecoration.h>
|
|
||||||
|
|
||||||
#include "ui_decoration.h"
|
|
||||||
|
|
||||||
class QQuickView;
|
|
||||||
class QSortFilterProxyModel;
|
|
||||||
class KLocalizedTranslator;
|
|
||||||
namespace KWin
|
|
||||||
{
|
|
||||||
|
|
||||||
class DecorationModel;
|
|
||||||
|
|
||||||
class KWinDecorationForm : public QWidget, public Ui::KWinDecorationForm
|
|
||||||
{
|
|
||||||
Q_OBJECT
|
|
||||||
|
|
||||||
public:
|
|
||||||
explicit KWinDecorationForm(QWidget* parent);
|
|
||||||
};
|
|
||||||
|
|
||||||
class DecorationButtons : public QObject, public KDecorationDefines
|
|
||||||
{
|
|
||||||
Q_OBJECT
|
|
||||||
Q_PROPERTY(bool customButtonPositions READ customPositions WRITE setCustomPositions NOTIFY customPositionsChanged)
|
|
||||||
public:
|
|
||||||
explicit DecorationButtons(QObject *parent = nullptr);
|
|
||||||
virtual ~DecorationButtons();
|
|
||||||
|
|
||||||
bool customPositions() const;
|
|
||||||
const QList<DecorationButton> &leftButtons() const;
|
|
||||||
const QList<DecorationButton> &rightButtons() const;
|
|
||||||
|
|
||||||
void setCustomPositions(bool set);
|
|
||||||
void setLeftButtons(const QList<KDecorationDefines::DecorationButton> &buttons);
|
|
||||||
void setRightButtons(const QList<KDecorationDefines::DecorationButton> &buttons);
|
|
||||||
|
|
||||||
public Q_SLOTS:
|
|
||||||
void resetToDefaults();
|
|
||||||
|
|
||||||
Q_SIGNALS:
|
|
||||||
void customPositionsChanged();
|
|
||||||
void leftButtonsChanged();
|
|
||||||
void rightButtonsChanged();
|
|
||||||
|
|
||||||
private:
|
|
||||||
bool m_customPositions;
|
|
||||||
QList<DecorationButton> m_leftButtons;
|
|
||||||
QList<DecorationButton> m_rightButtons;
|
|
||||||
};
|
|
||||||
|
|
||||||
class KWinDecorationModule : public KCModule, public KDecorationDefines
|
|
||||||
{
|
|
||||||
Q_OBJECT
|
|
||||||
|
|
||||||
public:
|
|
||||||
KWinDecorationModule(QWidget* parent, const QVariantList &);
|
|
||||||
~KWinDecorationModule();
|
|
||||||
|
|
||||||
virtual void load();
|
|
||||||
virtual void save();
|
|
||||||
virtual void defaults();
|
|
||||||
|
|
||||||
QString quickHelp() const;
|
|
||||||
|
|
||||||
Q_SIGNALS:
|
|
||||||
void pluginLoad(const KConfigGroup& conf);
|
|
||||||
void pluginSave(KConfigGroup &conf);
|
|
||||||
void pluginDefaults();
|
|
||||||
|
|
||||||
protected:
|
|
||||||
bool eventFilter(QObject *o, QEvent *e);
|
|
||||||
virtual void showEvent(QShowEvent *ev);
|
|
||||||
|
|
||||||
protected Q_SLOTS:
|
|
||||||
// Allows us to turn "save" on
|
|
||||||
void slotSelectionChanged();
|
|
||||||
void slotConfigureButtons();
|
|
||||||
void slotGHNSClicked();
|
|
||||||
void slotConfigureDecoration();
|
|
||||||
|
|
||||||
private:
|
|
||||||
void init();
|
|
||||||
void readConfig(const KConfigGroup& conf);
|
|
||||||
void writeConfig(KConfigGroup &conf);
|
|
||||||
private Q_SLOTS:
|
|
||||||
void updateScrollbarRange();
|
|
||||||
void updateScrollbarValue();
|
|
||||||
void updateViewPosition(int v);
|
|
||||||
private:
|
|
||||||
KSharedConfigPtr kwinConfig;
|
|
||||||
|
|
||||||
KWinDecorationForm* m_ui;
|
|
||||||
bool m_showTooltips;
|
|
||||||
|
|
||||||
DecorationModel* m_model;
|
|
||||||
QSortFilterProxyModel* m_proxyModel;
|
|
||||||
bool m_configLoaded;
|
|
||||||
DecorationButtons *m_decorationButtons;
|
|
||||||
|
|
||||||
QScopedPointer<QQuickView> m_listView;
|
|
||||||
|
|
||||||
KLocalizedTranslator *m_translator;
|
|
||||||
};
|
|
||||||
|
|
||||||
} //namespace
|
|
||||||
|
|
||||||
#endif
|
|
|
@ -1,630 +0,0 @@
|
||||||
/*
|
|
||||||
*
|
|
||||||
* Copyright (c) 2003 Lubos Lunak <l.lunak@kde.org>
|
|
||||||
* Copyright (c) 2013 Martin Gräßlin <mgraesslin@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 "preview.h"
|
|
||||||
|
|
||||||
#include <KLocalizedString>
|
|
||||||
#include <kconfig.h>
|
|
||||||
#include <QApplication>
|
|
||||||
#include <QPainter>
|
|
||||||
#include <QMouseEvent>
|
|
||||||
|
|
||||||
#include <kdecorationfactory.h>
|
|
||||||
|
|
||||||
static const int SMALL_OFFSET = 10;
|
|
||||||
static const int LARGE_OFFSET = 40;
|
|
||||||
|
|
||||||
PreviewItem::PreviewItem(QQuickItem *parent)
|
|
||||||
: QQuickPaintedItem(parent)
|
|
||||||
, m_plugins(new KDecorationPreviewPlugins(KSharedConfig::openConfig(QStringLiteral("kwinrc"))))
|
|
||||||
, m_activeBridge(new KDecorationPreviewBridge(this, true))
|
|
||||||
, m_inactiveBridge(new KDecorationPreviewBridge(this, false))
|
|
||||||
, m_activeDecoration(nullptr)
|
|
||||||
, m_inactiveDecoration(nullptr)
|
|
||||||
, m_activeEntered(nullptr)
|
|
||||||
, m_inactiveEntered(nullptr)
|
|
||||||
{
|
|
||||||
setFlag(ItemHasContents, true);
|
|
||||||
setAcceptHoverEvents(true);
|
|
||||||
connect(this, &PreviewItem::libraryChanged, this, &PreviewItem::loadDecorationPlugin);
|
|
||||||
}
|
|
||||||
|
|
||||||
PreviewItem::~PreviewItem()
|
|
||||||
{
|
|
||||||
delete m_activeDecoration;
|
|
||||||
delete m_inactiveDecoration;
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::setLibraryName(const QString &library)
|
|
||||||
{
|
|
||||||
if (library == m_libraryName || library.isEmpty()) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
m_libraryName = library;
|
|
||||||
emit libraryChanged();
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::loadDecorationPlugin()
|
|
||||||
{
|
|
||||||
const bool loaded = m_plugins->loadPlugin(m_libraryName);
|
|
||||||
if (!loaded) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
m_plugins->destroyPreviousPlugin();
|
|
||||||
connect(m_plugins->factory(), &KDecorationFactory::recreateDecorations,
|
|
||||||
this, &PreviewItem::recreateDecorations, Qt::QueuedConnection);
|
|
||||||
recreateDecorations();
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::recreateDecorations()
|
|
||||||
{
|
|
||||||
delete m_activeDecoration;
|
|
||||||
delete m_inactiveDecoration;
|
|
||||||
m_activeEntered = nullptr;
|
|
||||||
m_inactiveEntered = nullptr;
|
|
||||||
m_activeDecoration = m_plugins->createDecoration(m_activeBridge.data());
|
|
||||||
m_inactiveDecoration = m_plugins->createDecoration(m_inactiveBridge.data());
|
|
||||||
|
|
||||||
if (m_activeDecoration) {
|
|
||||||
m_activeDecoration->init();
|
|
||||||
if (m_activeDecoration->widget()) {
|
|
||||||
m_activeDecoration->widget()->installEventFilter(this);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (m_inactiveDecoration) {
|
|
||||||
m_inactiveDecoration->init();
|
|
||||||
if (m_inactiveDecoration->widget()) {
|
|
||||||
m_inactiveDecoration->widget()->installEventFilter(this);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
updatePreview();
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::geometryChanged(const QRectF& newGeometry, const QRectF& oldGeometry)
|
|
||||||
{
|
|
||||||
QQuickPaintedItem::geometryChanged(newGeometry, oldGeometry);
|
|
||||||
updatePreview();
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::updatePreview()
|
|
||||||
{
|
|
||||||
if (width() == 0 && height() == 0) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (!m_activeDecoration && !m_inactiveDecoration) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
const QSize size(width() - 50, height() - 50);
|
|
||||||
updateSize(size, m_activeDecoration, m_activeBuffer);
|
|
||||||
updateSize(size, m_inactiveDecoration, m_inactiveBuffer);
|
|
||||||
|
|
||||||
render(&m_activeBuffer, m_activeDecoration);
|
|
||||||
render(&m_inactiveBuffer, m_inactiveDecoration);
|
|
||||||
update();
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::updateSize(const QSize &baseSize, KDecoration *decoration, QImage &buffer)
|
|
||||||
{
|
|
||||||
if (!decoration) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
int left, right, top, bottom;
|
|
||||||
left = right = top = bottom = 0;
|
|
||||||
decoration->padding(left, right, top, bottom);
|
|
||||||
const QSize size = baseSize + QSize(left + right, top + bottom);
|
|
||||||
if (decoration->geometry().size() != size) {
|
|
||||||
decoration->resize(size);
|
|
||||||
}
|
|
||||||
if (buffer.isNull() || buffer.size() != size) {
|
|
||||||
buffer = QImage(size, QImage::Format_ARGB32_Premultiplied);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::render(QImage* image, KDecoration* decoration)
|
|
||||||
{
|
|
||||||
image->fill(Qt::transparent);
|
|
||||||
decoration->render(image, QRegion());
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::paint(QPainter *painter)
|
|
||||||
{
|
|
||||||
int paddingLeft, paddingRigth, paddingTop, paddingBottom;
|
|
||||||
paddingLeft = paddingRigth = paddingTop = paddingBottom = 0;
|
|
||||||
if (m_inactiveDecoration) {
|
|
||||||
m_inactiveDecoration->padding(paddingLeft, paddingRigth, paddingTop, paddingBottom);
|
|
||||||
}
|
|
||||||
|
|
||||||
painter->drawImage(LARGE_OFFSET - paddingLeft, SMALL_OFFSET - paddingTop, m_inactiveBuffer);
|
|
||||||
|
|
||||||
paddingLeft = paddingRigth = paddingTop = paddingBottom = 0;
|
|
||||||
if (m_activeDecoration) {
|
|
||||||
m_activeDecoration->padding(paddingLeft, paddingRigth, paddingTop, paddingBottom);
|
|
||||||
}
|
|
||||||
painter->drawImage(SMALL_OFFSET - paddingLeft, LARGE_OFFSET - paddingTop, m_activeBuffer);
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::hoverMoveEvent(QHoverEvent* event)
|
|
||||||
{
|
|
||||||
QQuickItem::hoverMoveEvent(event);
|
|
||||||
const int w = width() - LARGE_OFFSET - SMALL_OFFSET;
|
|
||||||
const int h = height() - LARGE_OFFSET - SMALL_OFFSET;
|
|
||||||
forwardMoveEvent(event, QRect(SMALL_OFFSET, LARGE_OFFSET, w, h), m_activeDecoration, &m_activeEntered);
|
|
||||||
forwardMoveEvent(event, QRect(LARGE_OFFSET, SMALL_OFFSET, w, h), m_inactiveDecoration, &m_inactiveEntered);
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::forwardMoveEvent(QHoverEvent *event, const QRect &geo, KDecoration *deco, QWidget **entered)
|
|
||||||
{
|
|
||||||
auto leaveEvent = [](QWidget **widget) {
|
|
||||||
if (!(*widget)) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
// send old one a leave event
|
|
||||||
QEvent leave(QEvent::Leave);
|
|
||||||
QApplication::sendEvent(*widget, &leave);
|
|
||||||
*widget = nullptr;
|
|
||||||
};
|
|
||||||
if (geo.contains(event->pos()) && deco && deco->widget()) {
|
|
||||||
int paddingLeft, paddingRigth, paddingTop, paddingBottom;
|
|
||||||
paddingLeft = paddingRigth = paddingTop = paddingBottom = 0;
|
|
||||||
deco->padding(paddingLeft, paddingRigth, paddingTop, paddingBottom);
|
|
||||||
const QPoint widgetPos = event->pos() - geo.topLeft() + QPoint(paddingLeft, paddingTop);
|
|
||||||
if (QWidget *widget = deco->widget()->childAt(widgetPos)) {
|
|
||||||
if (widget != *entered) {
|
|
||||||
leaveEvent(entered);
|
|
||||||
// send enter event
|
|
||||||
*entered = widget;
|
|
||||||
QEnterEvent enter(widgetPos - widget->geometry().topLeft(), widgetPos, event->pos());
|
|
||||||
QApplication::sendEvent(*entered, &enter);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
leaveEvent(entered);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
leaveEvent(entered);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void PreviewItem::updateDecoration(KDecorationPreviewBridge *bridge)
|
|
||||||
{
|
|
||||||
if (bridge == m_activeBridge.data()) {
|
|
||||||
render(&m_activeBuffer, m_activeDecoration);
|
|
||||||
} else if (bridge == m_inactiveBridge.data()) {
|
|
||||||
render(&m_inactiveBuffer, m_inactiveDecoration);
|
|
||||||
}
|
|
||||||
update();
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecorationPreview::KDecorationPreview(QWidget* parent)
|
|
||||||
: QWidget(parent)
|
|
||||||
{
|
|
||||||
bridge[Active] = new KDecorationPreviewBridge(this, true);
|
|
||||||
bridge[Inactive] = new KDecorationPreviewBridge(this, false);
|
|
||||||
|
|
||||||
deco[Active] = deco[Inactive] = NULL;
|
|
||||||
|
|
||||||
setMinimumSize(100, 100);
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecorationPreview::~KDecorationPreview()
|
|
||||||
{
|
|
||||||
for (int i = 0; i < NumWindows; i++) {
|
|
||||||
delete deco[i];
|
|
||||||
delete bridge[i];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreview::disablePreview()
|
|
||||||
{
|
|
||||||
delete deco[Active];
|
|
||||||
delete deco[Inactive];
|
|
||||||
deco[Active] = deco[Inactive] = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecorationFactory *KDecorationPreview::factory() const
|
|
||||||
{
|
|
||||||
return deco[Active] ? deco[Active]->factory() : 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
QRect KDecorationPreview::windowGeometry(bool active) const
|
|
||||||
{
|
|
||||||
QWidget *widget = active ? deco[Active]->widget() : deco[Inactive]->widget();
|
|
||||||
return widget->geometry();
|
|
||||||
}
|
|
||||||
|
|
||||||
QRegion KDecorationPreview::unobscuredRegion(bool active, const QRegion& r) const
|
|
||||||
{
|
|
||||||
Q_UNUSED(active)
|
|
||||||
return r;
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecorationPreviewBridge::KDecorationPreviewBridge(KDecorationPreview* p, bool a)
|
|
||||||
: preview(p)
|
|
||||||
, m_previewItem(nullptr)
|
|
||||||
, active(a)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecorationPreviewBridge::KDecorationPreviewBridge(PreviewItem *p, bool a)
|
|
||||||
: preview(nullptr)
|
|
||||||
, m_previewItem(p)
|
|
||||||
, active(a)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
Qt::WindowFlags KDecorationPreviewBridge::initialWFlags() const
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isActive() const
|
|
||||||
{
|
|
||||||
return active;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isCloseable() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isMaximizable() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecoration::MaximizeMode KDecorationPreviewBridge::maximizeMode() const
|
|
||||||
{
|
|
||||||
return KDecoration::MaximizeRestore;
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecoration::QuickTileMode KDecorationPreviewBridge::quickTileMode() const
|
|
||||||
{
|
|
||||||
return KDecoration::QuickTileNone;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isMinimizable() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::providesContextHelp() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
int KDecorationPreviewBridge::desktop() const
|
|
||||||
{
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isOnAllDesktopsAvailable() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isModal() const
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isShadeable() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isShade() const
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isSetShade() const
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::keepAbove() const
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::keepBelow() const
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isMovable() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isResizable() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
NET::WindowType KDecorationPreviewBridge::windowType(unsigned long) const
|
|
||||||
{
|
|
||||||
return NET::Normal;
|
|
||||||
}
|
|
||||||
|
|
||||||
QIcon KDecorationPreviewBridge::icon() const
|
|
||||||
{
|
|
||||||
return QIcon::fromTheme(QStringLiteral("xorg"));
|
|
||||||
}
|
|
||||||
|
|
||||||
QString KDecorationPreviewBridge::caption() const
|
|
||||||
{
|
|
||||||
return active ? i18n("Active Window") : i18n("Inactive Window");
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::processMousePressEvent(QMouseEvent*)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::showWindowMenu(const QRect &)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::showWindowMenu(const QPoint &)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::showApplicationMenu(const QPoint &)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::menuAvailable() const
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::performWindowOperation(WindowOperation)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::setMask(const QRegion& reg, int mode)
|
|
||||||
{
|
|
||||||
Q_UNUSED(reg)
|
|
||||||
Q_UNUSED(mode)
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::isPreview() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
QRect KDecorationPreviewBridge::geometry() const
|
|
||||||
{
|
|
||||||
if (preview) {
|
|
||||||
return preview->windowGeometry(active);
|
|
||||||
}
|
|
||||||
return QRect();
|
|
||||||
}
|
|
||||||
|
|
||||||
QRect KDecorationPreviewBridge::iconGeometry() const
|
|
||||||
{
|
|
||||||
return QRect();
|
|
||||||
}
|
|
||||||
|
|
||||||
QRegion KDecorationPreviewBridge::unobscuredRegion(const QRegion& r) const
|
|
||||||
{
|
|
||||||
return preview->unobscuredRegion(active, r);
|
|
||||||
}
|
|
||||||
|
|
||||||
WId KDecorationPreviewBridge::windowId() const
|
|
||||||
{
|
|
||||||
return 0; // no decorated window
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::closeWindow()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::maximize(MaximizeMode)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::minimize()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::showContextHelp()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::setDesktop(int)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::titlebarDblClickOperation()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::titlebarMouseWheelOperation(int)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::setShade(bool)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::setKeepAbove(bool)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::setKeepBelow(bool)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
int KDecorationPreviewBridge::currentDesktop() const
|
|
||||||
{
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::grabXServer(bool)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewBridge::compositingActive() const
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
QRect KDecorationPreviewBridge::transparentRect() const
|
|
||||||
{
|
|
||||||
return QRect();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Window tabbing
|
|
||||||
|
|
||||||
int KDecorationPreviewBridge::tabCount() const
|
|
||||||
{
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
QString KDecorationPreviewBridge::caption(int) const
|
|
||||||
{
|
|
||||||
return active ? "Active Window" : "Inactive Window";
|
|
||||||
}
|
|
||||||
|
|
||||||
QIcon KDecorationPreviewBridge::icon(int) const
|
|
||||||
{
|
|
||||||
return icon();
|
|
||||||
}
|
|
||||||
|
|
||||||
long KDecorationPreviewBridge::tabId(int) const
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
long KDecorationPreviewBridge::currentTabId() const
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::setCurrentTab(long)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::tab_A_before_B(long, long)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::tab_A_behind_B(long, long)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::untab(long, const QRect&)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::closeTab(long)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::closeTabGroup()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::showWindowMenu(const QPoint &, long)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewBridge::update(const QRegion&)
|
|
||||||
{
|
|
||||||
if (m_previewItem) {
|
|
||||||
// call update
|
|
||||||
m_previewItem->updateDecoration(this);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecoration::WindowOperation KDecorationPreviewBridge::buttonToWindowOperation(Qt::MouseButtons)
|
|
||||||
{
|
|
||||||
return KDecoration::NoOp;
|
|
||||||
}
|
|
||||||
|
|
||||||
QPalette KDecorationPreviewBridge::palette() const
|
|
||||||
{
|
|
||||||
return QApplication::palette();
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecorationPreviewOptions::KDecorationPreviewOptions()
|
|
||||||
{
|
|
||||||
customBorderSize = BordersCount; // invalid
|
|
||||||
customButtonsChanged = false; // invalid
|
|
||||||
customButtons = true;
|
|
||||||
customTitleButtonsLeft.clear(); // invalid
|
|
||||||
customTitleButtonsRight.clear(); // invalid
|
|
||||||
updateSettings();
|
|
||||||
}
|
|
||||||
|
|
||||||
KDecorationPreviewOptions::~KDecorationPreviewOptions()
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewOptions::updateSettings()
|
|
||||||
{
|
|
||||||
KConfig cfg("kwinrc");
|
|
||||||
KDecorationOptions::updateSettings(&cfg);
|
|
||||||
|
|
||||||
// set custom border size/buttons
|
|
||||||
if (customBorderSize != BordersCount)
|
|
||||||
setBorderSize(customBorderSize);
|
|
||||||
if (customButtonsChanged)
|
|
||||||
setCustomButtonPositions(customButtons);
|
|
||||||
if (customButtons) {
|
|
||||||
if (!customTitleButtonsLeft.isEmpty())
|
|
||||||
setTitleButtonsLeft(customTitleButtonsLeft);
|
|
||||||
if (!customTitleButtonsRight.isEmpty())
|
|
||||||
setTitleButtonsRight(customTitleButtonsRight);
|
|
||||||
} else {
|
|
||||||
setTitleButtonsLeft(KDecorationOptions::defaultTitleButtonsLeft());
|
|
||||||
setTitleButtonsRight(KDecorationOptions::defaultTitleButtonsRight());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewOptions::setCustomBorderSize(BorderSize size)
|
|
||||||
{
|
|
||||||
customBorderSize = size;
|
|
||||||
|
|
||||||
updateSettings();
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewOptions::setCustomTitleButtonsEnabled(bool enabled)
|
|
||||||
{
|
|
||||||
customButtonsChanged = true;
|
|
||||||
customButtons = enabled;
|
|
||||||
|
|
||||||
updateSettings();
|
|
||||||
}
|
|
||||||
|
|
||||||
void KDecorationPreviewOptions::setCustomTitleButtons(const QList<DecorationButton> &left, const QList<DecorationButton> &right)
|
|
||||||
{
|
|
||||||
customTitleButtonsLeft = left;
|
|
||||||
customTitleButtonsRight = right;
|
|
||||||
|
|
||||||
updateSettings();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool KDecorationPreviewPlugins::provides(Requirement)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
#include "preview.moc"
|
|
|
@ -1,210 +0,0 @@
|
||||||
/*
|
|
||||||
*
|
|
||||||
* Copyright (c) 2003 Lubos Lunak <l.lunak@kde.org>
|
|
||||||
* Copyright (c) 2013 Martin Gräßlin <mgraesslin@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 KWINDECORATION_PREVIEW_H
|
|
||||||
#define KWINDECORATION_PREVIEW_H
|
|
||||||
|
|
||||||
#include <QWidget>
|
|
||||||
#include <QQuickPaintedItem>
|
|
||||||
#include <kdecoration.h>
|
|
||||||
#include <kdecorationbridge.h>
|
|
||||||
#include <kdecoration_plugins_p.h>
|
|
||||||
|
|
||||||
class KDecorationPreviewBridge;
|
|
||||||
class KDecorationPreviewOptions;
|
|
||||||
class QMouseEvent;
|
|
||||||
|
|
||||||
class PreviewItem : public QQuickPaintedItem
|
|
||||||
{
|
|
||||||
Q_OBJECT
|
|
||||||
Q_PROPERTY(QString library READ libraryName WRITE setLibraryName NOTIFY libraryChanged)
|
|
||||||
public:
|
|
||||||
PreviewItem(QQuickItem *parent = nullptr);
|
|
||||||
virtual ~PreviewItem();
|
|
||||||
virtual void paint(QPainter *painter);
|
|
||||||
|
|
||||||
void setLibraryName(const QString &library);
|
|
||||||
const QString &libraryName() const {
|
|
||||||
return m_libraryName;
|
|
||||||
}
|
|
||||||
void updateDecoration(KDecorationPreviewBridge *bridge);
|
|
||||||
|
|
||||||
Q_SIGNALS:
|
|
||||||
void libraryChanged();
|
|
||||||
|
|
||||||
protected:
|
|
||||||
virtual void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry);
|
|
||||||
virtual void hoverMoveEvent(QHoverEvent *event);
|
|
||||||
|
|
||||||
private Q_SLOTS:
|
|
||||||
void loadDecorationPlugin();
|
|
||||||
void recreateDecorations();
|
|
||||||
|
|
||||||
private:
|
|
||||||
void updatePreview();
|
|
||||||
void updateSize(const QSize &size, KDecoration *decoration, QImage &buffer);
|
|
||||||
void render(QImage *image, KDecoration *decoration);
|
|
||||||
void forwardMoveEvent(QHoverEvent *event, const QRect &geo, KDecoration *deco, QWidget **entered);
|
|
||||||
QScopedPointer<KDecorationPlugins> m_plugins;
|
|
||||||
QScopedPointer<KDecorationPreviewBridge> m_activeBridge;
|
|
||||||
QScopedPointer<KDecorationPreviewBridge> m_inactiveBridge;
|
|
||||||
KDecoration *m_activeDecoration;
|
|
||||||
KDecoration *m_inactiveDecoration;
|
|
||||||
QWidget *m_activeEntered;
|
|
||||||
QWidget *m_inactiveEntered;
|
|
||||||
QString m_libraryName;
|
|
||||||
QImage m_activeBuffer;
|
|
||||||
QImage m_inactiveBuffer;
|
|
||||||
};
|
|
||||||
|
|
||||||
class KDecorationPreview
|
|
||||||
: public QWidget
|
|
||||||
{
|
|
||||||
Q_OBJECT
|
|
||||||
public:
|
|
||||||
// Note: Windows can't be added or removed without making changes to
|
|
||||||
// the code, since parts of it assume there's just an active
|
|
||||||
// and an inactive window.
|
|
||||||
enum Windows { Inactive = 0, Active, NumWindows };
|
|
||||||
|
|
||||||
explicit KDecorationPreview(QWidget* parent = nullptr);
|
|
||||||
virtual ~KDecorationPreview();
|
|
||||||
void disablePreview();
|
|
||||||
KDecorationFactory *factory() const;
|
|
||||||
QRegion unobscuredRegion(bool, const QRegion&) const;
|
|
||||||
QRect windowGeometry(bool) const;
|
|
||||||
private:
|
|
||||||
KDecorationPreviewBridge* bridge[NumWindows];
|
|
||||||
KDecoration* deco[NumWindows];
|
|
||||||
};
|
|
||||||
|
|
||||||
class KDecorationPreviewBridge
|
|
||||||
: public KDecorationBridge
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
KDecorationPreviewBridge(KDecorationPreview* preview, bool active);
|
|
||||||
KDecorationPreviewBridge(PreviewItem* preview, bool active);
|
|
||||||
virtual bool isActive() const override;
|
|
||||||
virtual bool isCloseable() const override;
|
|
||||||
virtual bool isMaximizable() const override;
|
|
||||||
virtual MaximizeMode maximizeMode() const override;
|
|
||||||
virtual QuickTileMode quickTileMode() const override;
|
|
||||||
virtual bool isMinimizable() const override;
|
|
||||||
virtual bool providesContextHelp() const override;
|
|
||||||
virtual int desktop() const override;
|
|
||||||
bool isOnAllDesktopsAvailable() const override;
|
|
||||||
virtual bool isModal() const override;
|
|
||||||
virtual bool isShadeable() const override;
|
|
||||||
virtual bool isShade() const override;
|
|
||||||
virtual bool isSetShade() const override;
|
|
||||||
virtual bool keepAbove() const override;
|
|
||||||
virtual bool keepBelow() const override;
|
|
||||||
virtual bool isMovable() const override;
|
|
||||||
virtual bool isResizable() const override;
|
|
||||||
virtual NET::WindowType windowType(unsigned long supported_types) const override;
|
|
||||||
virtual QIcon icon() const override;
|
|
||||||
virtual QString caption() const override;
|
|
||||||
virtual void processMousePressEvent(QMouseEvent*) override;
|
|
||||||
virtual void showWindowMenu(const QRect &) override;
|
|
||||||
virtual void showWindowMenu(const QPoint &) override;
|
|
||||||
virtual void showApplicationMenu(const QPoint &) override;
|
|
||||||
virtual bool menuAvailable() const override;
|
|
||||||
virtual void performWindowOperation(WindowOperation) override;
|
|
||||||
virtual void setMask(const QRegion&, int) override;
|
|
||||||
virtual bool isPreview() const override;
|
|
||||||
virtual QRect geometry() const override;
|
|
||||||
virtual QRect iconGeometry() const override;
|
|
||||||
virtual QRegion unobscuredRegion(const QRegion& r) const override;
|
|
||||||
virtual WId windowId() const override;
|
|
||||||
virtual void closeWindow() override;
|
|
||||||
virtual void maximize(MaximizeMode mode) override;
|
|
||||||
virtual void minimize() override;
|
|
||||||
virtual void showContextHelp() override;
|
|
||||||
virtual void setDesktop(int desktop) override;
|
|
||||||
virtual void titlebarDblClickOperation() override;
|
|
||||||
virtual void titlebarMouseWheelOperation(int delta) override;
|
|
||||||
virtual void setShade(bool set) override;
|
|
||||||
virtual void setKeepAbove(bool) override;
|
|
||||||
virtual void setKeepBelow(bool) override;
|
|
||||||
virtual int currentDesktop() const override;
|
|
||||||
virtual Qt::WindowFlags initialWFlags() const override;
|
|
||||||
virtual void grabXServer(bool grab) override;
|
|
||||||
|
|
||||||
virtual bool compositingActive() const override;
|
|
||||||
virtual QRect transparentRect() const override;
|
|
||||||
|
|
||||||
virtual void update(const QRegion ®ion) override;
|
|
||||||
virtual QPalette palette() const override;
|
|
||||||
|
|
||||||
// Window tabbing
|
|
||||||
virtual QString caption(int idx) const override;
|
|
||||||
virtual void closeTab(long id) override;
|
|
||||||
virtual void closeTabGroup() override;
|
|
||||||
virtual long currentTabId() const override;
|
|
||||||
virtual QIcon icon(int idx) const override;
|
|
||||||
virtual void setCurrentTab(long id) override;
|
|
||||||
virtual void showWindowMenu(const QPoint &, long id) override;
|
|
||||||
virtual void tab_A_before_B(long A, long B) override;
|
|
||||||
virtual void tab_A_behind_B(long A, long B) override;
|
|
||||||
virtual int tabCount() const override;
|
|
||||||
virtual long tabId(int idx) const override;
|
|
||||||
virtual void untab(long id, const QRect& newGeom) override;
|
|
||||||
virtual WindowOperation buttonToWindowOperation(Qt::MouseButtons button) override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
KDecorationPreview* preview;
|
|
||||||
PreviewItem *m_previewItem;
|
|
||||||
bool active;
|
|
||||||
};
|
|
||||||
|
|
||||||
class KDecorationPreviewOptions
|
|
||||||
: public KDecorationOptions
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
KDecorationPreviewOptions();
|
|
||||||
virtual ~KDecorationPreviewOptions();
|
|
||||||
void updateSettings();
|
|
||||||
|
|
||||||
void setCustomBorderSize(BorderSize size);
|
|
||||||
void setCustomTitleButtonsEnabled(bool enabled);
|
|
||||||
void setCustomTitleButtons(const QList<DecorationButton> &left, const QList<DecorationButton> &right);
|
|
||||||
|
|
||||||
private:
|
|
||||||
BorderSize customBorderSize;
|
|
||||||
bool customButtonsChanged;
|
|
||||||
bool customButtons;
|
|
||||||
QList<DecorationButton> customTitleButtonsLeft;
|
|
||||||
QList<DecorationButton> customTitleButtonsRight;
|
|
||||||
};
|
|
||||||
|
|
||||||
class KDecorationPreviewPlugins
|
|
||||||
: public KDecorationPlugins
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
explicit KDecorationPreviewPlugins(const KSharedConfigPtr &cfg);
|
|
||||||
virtual bool provides(Requirement);
|
|
||||||
};
|
|
||||||
|
|
||||||
inline KDecorationPreviewPlugins::KDecorationPreviewPlugins(const KSharedConfigPtr &cfg)
|
|
||||||
: KDecorationPlugins(cfg)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
|
@ -1,73 +0,0 @@
|
||||||
/********************************************************************
|
|
||||||
Copyright (C) 2012 Martin Gräßlin <mgraesslin@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, see <http://www.gnu.org/licenses/>.
|
|
||||||
*********************************************************************/
|
|
||||||
import QtQuick 2.0
|
|
||||||
|
|
||||||
Item {
|
|
||||||
property alias active: decoration.active
|
|
||||||
property alias source: auroraeLoader.source
|
|
||||||
QtObject {
|
|
||||||
signal configChanged
|
|
||||||
id: decoration
|
|
||||||
property bool active: false
|
|
||||||
property string caption: display
|
|
||||||
property int desktop: 1
|
|
||||||
property variant icon: "xorg"
|
|
||||||
property bool closeable: true
|
|
||||||
property bool maximizeable: true
|
|
||||||
property bool minimizeable: true
|
|
||||||
property bool modal: false
|
|
||||||
property bool moveable: true
|
|
||||||
property bool onAllDesktops: false
|
|
||||||
property bool preview: true
|
|
||||||
property bool resizeable: true
|
|
||||||
property bool setShade: false
|
|
||||||
property bool shade: false
|
|
||||||
property bool shadeable: false
|
|
||||||
property bool keepAbove: false
|
|
||||||
property bool keepBelow: false
|
|
||||||
property bool maximized: false
|
|
||||||
property bool providesContextHelp: true
|
|
||||||
property bool appMenu: true
|
|
||||||
property string leftButtons: "MS"
|
|
||||||
property string rightButtons: "HIA__X"
|
|
||||||
function titleMouseMoved() {}
|
|
||||||
function readConfig(key, defaultValue) {
|
|
||||||
if (key == "BorderSize") {
|
|
||||||
return borderSize;
|
|
||||||
} else if (key == "ButtonSize") {
|
|
||||||
return buttonSize;
|
|
||||||
} else {
|
|
||||||
return decorationBaseModel.readConfig(auroraeThemeName, key, defaultValue);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// just to not cause warnings
|
|
||||||
signal buttonsChanged()
|
|
||||||
signal fontChanged()
|
|
||||||
}
|
|
||||||
Loader {
|
|
||||||
id: auroraeLoader
|
|
||||||
anchors.fill: parent
|
|
||||||
}
|
|
||||||
Connections {
|
|
||||||
target: decorationBaseModel
|
|
||||||
onConfigChanged: {
|
|
||||||
if (auroraeThemeName == themeName) {
|
|
||||||
decoration.configChanged();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,52 +0,0 @@
|
||||||
/********************************************************************
|
|
||||||
Copyright (C) 2012 Martin Gräßlin <mgraesslin@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, see <http://www.gnu.org/licenses/>.
|
|
||||||
*********************************************************************/
|
|
||||||
import QtQuick 2.0
|
|
||||||
import org.kde.kwin.aurorae 0.1
|
|
||||||
|
|
||||||
Item {
|
|
||||||
id: aurorae
|
|
||||||
AuroraeTheme {
|
|
||||||
id: auroraeTheme
|
|
||||||
Component.onCompleted: {
|
|
||||||
auroraeTheme.loadTheme(auroraeThemeName);
|
|
||||||
inactiveAurorae.source = auroraeSource;
|
|
||||||
activeAurorae.source = auroraeSource;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
AuroraeDecoration {
|
|
||||||
id: inactiveAurorae
|
|
||||||
active: false
|
|
||||||
anchors {
|
|
||||||
fill: parent
|
|
||||||
leftMargin: 40 - auroraeTheme.paddingLeft
|
|
||||||
rightMargin: 10 - auroraeTheme.paddingRight
|
|
||||||
topMargin: 10 - auroraeTheme.paddingTop
|
|
||||||
bottomMargin: 40 - auroraeTheme.paddingBottom
|
|
||||||
}
|
|
||||||
}
|
|
||||||
AuroraeDecoration {
|
|
||||||
id: activeAurorae
|
|
||||||
active: true
|
|
||||||
anchors {
|
|
||||||
fill: parent
|
|
||||||
leftMargin: 10 - auroraeTheme.paddingLeft
|
|
||||||
rightMargin: 40 - auroraeTheme.paddingRight
|
|
||||||
topMargin: 40 - auroraeTheme.paddingTop
|
|
||||||
bottomMargin: 10 - auroraeTheme.paddingBottom
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,47 +0,0 @@
|
||||||
/********************************************************************
|
|
||||||
Copyright (C) 2012 Martin Gräßlin <mgraesslin@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, see <http://www.gnu.org/licenses/>.
|
|
||||||
*********************************************************************/
|
|
||||||
import QtQuick 2.0
|
|
||||||
|
|
||||||
Item {
|
|
||||||
id: decorationPreview
|
|
||||||
AuroraeDecoration {
|
|
||||||
id: inactiveDecoration
|
|
||||||
active: false
|
|
||||||
anchors {
|
|
||||||
fill: parent
|
|
||||||
leftMargin: 40
|
|
||||||
rightMargin: 10
|
|
||||||
topMargin: 10
|
|
||||||
bottomMargin: 40
|
|
||||||
}
|
|
||||||
}
|
|
||||||
AuroraeDecoration {
|
|
||||||
id: activeDecoration
|
|
||||||
active: true
|
|
||||||
anchors {
|
|
||||||
fill: parent
|
|
||||||
leftMargin: 10
|
|
||||||
rightMargin: 40
|
|
||||||
topMargin: 40
|
|
||||||
bottomMargin: 10
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Component.onCompleted: {
|
|
||||||
inactiveDecoration.source = mainScript;
|
|
||||||
activeDecoration.source = mainScript;
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,63 +1,85 @@
|
||||||
/********************************************************************
|
/*
|
||||||
Copyright (C) 2012 Martin Gräßlin <mgraesslin@kde.org>
|
* Copyright 2014 Martin Gräßlin <mgraesslin@kde.org>
|
||||||
Copyright (C) 2012 Nuno Pinheiro <nuno@oxygen-icons.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) version 3 or any later version
|
||||||
|
* accepted by the membership of KDE e.V. (or its successor approved
|
||||||
|
* by the membership of KDE e.V.), which shall act as a proxy
|
||||||
|
* defined in Section 14 of version 3 of the license.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
import QtQuick 2.1
|
||||||
|
import QtQuick.Controls 1.2
|
||||||
|
import org.kde.kwin.private.kdecoration 1.0 as KDecoration
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
ScrollView {
|
||||||
it under the terms of the GNU General Public License as published by
|
ListView {
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
id: listView
|
||||||
(at your option) any later version.
|
objectName: "listView"
|
||||||
|
model: decorationsModel
|
||||||
This program is distributed in the hope that it will be useful,
|
highlight: Rectangle {
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
width: listView.width
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
height: 150
|
||||||
General Public License for more details.
|
color: highlightColor
|
||||||
|
opacity: 0.5
|
||||||
You should have received a copy of the GNU General Public License
|
}
|
||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
highlightMoveDuration: 250
|
||||||
*********************************************************************/
|
boundsBehavior: Flickable.StopAtBounds
|
||||||
import QtQuick 2.0
|
delegate: Item {
|
||||||
import org.kde.kwin.kcmdecoration 0.1
|
width: listView.width
|
||||||
|
height: 150
|
||||||
ListView {
|
KDecoration.Bridge {
|
||||||
id: listView
|
id: bridgeItem
|
||||||
x: 0
|
plugin: model["plugin"]
|
||||||
y: 0
|
theme: model["theme"]
|
||||||
model: decorationModel
|
}
|
||||||
highlight: Rectangle {
|
KDecoration.Settings {
|
||||||
width: listView.width
|
id: settingsItem
|
||||||
height: 150
|
bridge: bridgeItem
|
||||||
color: highlightColor
|
}
|
||||||
opacity: 0.5
|
KDecoration.Decoration {
|
||||||
}
|
id: inactivePreview
|
||||||
highlightMoveDuration: 250
|
bridge: bridgeItem
|
||||||
boundsBehavior: Flickable.StopAtBounds
|
settings: settingsItem
|
||||||
delegate: Item {
|
anchors.fill: parent
|
||||||
objectName: "decorationItem"
|
Component.onCompleted: {
|
||||||
width: listView.width
|
client.caption = Qt.binding(function() { return model["display"]; });
|
||||||
height: 150
|
client.active = false;
|
||||||
PreviewItem {
|
anchors.leftMargin = Qt.binding(function() { return 40 - (inactivePreview.decoration.shadow ? inactivePreview.decoration.shadow.paddingLeft : 0);});
|
||||||
id: preview
|
anchors.rightMargin = Qt.binding(function() { return 10 - (inactivePreview.decoration.shadow ? inactivePreview.decoration.shadow.paddingRight : 0);});
|
||||||
anchors.fill: parent
|
anchors.topMargin = Qt.binding(function() { return 10 - (inactivePreview.decoration.shadow ? inactivePreview.decoration.shadow.paddingTop : 0);});
|
||||||
visible: type == 0
|
anchors.bottomMargin = Qt.binding(function() { return 40 - (inactivePreview.decoration.shadow ? inactivePreview.decoration.shadow.paddingBottom : 0);});
|
||||||
Component.onCompleted: {
|
|
||||||
if (type == 0) {
|
|
||||||
preview.library = model.library;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
KDecoration.Decoration {
|
||||||
Loader {
|
id: activePreview
|
||||||
source: type == 1 ? "AuroraePreview.qml" : ""
|
bridge: bridgeItem
|
||||||
anchors.fill: parent
|
settings: settingsItem
|
||||||
}
|
anchors.fill: parent
|
||||||
Loader {
|
Component.onCompleted: {
|
||||||
source: type == 2 ? "DecorationPreview.qml" : ""
|
client.caption = Qt.binding(function() { return model["display"]; });
|
||||||
anchors.fill: parent
|
client.active = true;
|
||||||
}
|
anchors.leftMargin = Qt.binding(function() { return 10 - (activePreview.decoration.shadow ? activePreview.decoration.shadow.paddingLeft : 0);});
|
||||||
MouseArea {
|
anchors.rightMargin = Qt.binding(function() { return 40 - (activePreview.decoration.shadow ? activePreview.decoration.shadow.paddingRight : 0);});
|
||||||
hoverEnabled: false
|
anchors.topMargin = Qt.binding(function() { return 40 - (activePreview.decoration.shadow ? activePreview.decoration.shadow.paddingTop : 0);});
|
||||||
anchors.fill: parent
|
anchors.bottomMargin = Qt.binding(function() { return 10 - (activePreview.decoration.shadow ? activePreview.decoration.shadow.paddingBottom : 0);});
|
||||||
onClicked: {
|
}
|
||||||
listView.currentIndex = index;
|
}
|
||||||
|
MouseArea {
|
||||||
|
hoverEnabled: false
|
||||||
|
anchors.fill: parent
|
||||||
|
onClicked: {
|
||||||
|
listView.currentIndex = index;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue