[kwin] Add isEffectSupported method to Effects DBus interface
EffectsHandlerImpl::isEffectsSupported performs the check whether the effect with the given name is supported by the current compositor. The check is the following: * if effect is already loaded, it is supported * if the effect cannot be found, it is not supported * if it's a scripted effect, it's always supported * if it's a built-in effect, we ask BuiltInEffects::supported * for all other effects we resolve the library and the supported method The idea behind providing this functionality in the DBus interface is to allow filtering in the effects KCM for the effects which are supported by the current compositor. In addition a areEffectsSupported method is added which takes a list of names and returns a list of bools. REVIEW: 116665
This commit is contained in:
parent
098620832a
commit
e3271ec2e1
3 changed files with 95 additions and 5 deletions
86
effects.cpp
86
effects.cpp
|
@ -1395,6 +1395,21 @@ QStringList EffectsHandlerImpl::listOfEffects() const
|
|||
return listOfModules;
|
||||
}
|
||||
|
||||
KService::Ptr EffectsHandlerImpl::findEffectService(const QString &internalName) const
|
||||
{
|
||||
QString constraint = QStringLiteral("[X-KDE-PluginInfo-Name] == '%1'").arg(internalName);
|
||||
KService::List offers = KServiceTypeTrader::self()->query(QStringLiteral("KWin/Effect"), constraint);
|
||||
if (offers.isEmpty()) {
|
||||
return KService::Ptr();
|
||||
}
|
||||
return offers.first();
|
||||
}
|
||||
|
||||
bool EffectsHandlerImpl::isScriptedEffect(KService::Ptr service) const
|
||||
{
|
||||
return service->property(QStringLiteral("X-Plasma-API")).toString() == QStringLiteral("javascript");
|
||||
}
|
||||
|
||||
bool EffectsHandlerImpl::loadEffect(const QString& name, bool checkDefault)
|
||||
{
|
||||
makeOpenGLContextCurrent();
|
||||
|
@ -1415,15 +1430,13 @@ bool EffectsHandlerImpl::loadEffect(const QString& name, bool checkDefault)
|
|||
qDebug() << "Trying to load " << name;
|
||||
QString internalname = name.toLower();
|
||||
|
||||
QString constraint = QStringLiteral("[X-KDE-PluginInfo-Name] == '%1'").arg(internalname);
|
||||
KService::List offers = KServiceTypeTrader::self()->query(QStringLiteral("KWin/Effect"), constraint);
|
||||
if (offers.isEmpty()) {
|
||||
KService::Ptr service = findEffectService(internalname);
|
||||
if (!service) {
|
||||
qCritical() << "Couldn't find effect " << name << endl;
|
||||
return false;
|
||||
}
|
||||
KService::Ptr service = offers.first();
|
||||
|
||||
if (service->property(QStringLiteral("X-Plasma-API")).toString() == QStringLiteral("javascript")) {
|
||||
if (isScriptedEffect(service)) {
|
||||
// this is a scripted effect - use different loader
|
||||
return loadScriptedEffect(name, service.data());
|
||||
}
|
||||
|
@ -1606,6 +1619,69 @@ bool EffectsHandlerImpl::isEffectLoaded(const QString& name) const
|
|||
return false;
|
||||
}
|
||||
|
||||
bool EffectsHandlerImpl::isEffectSupported(const QString &name)
|
||||
{
|
||||
// if the effect is loaded, it is obviously supported
|
||||
auto it = std::find_if(loaded_effects.constBegin(), loaded_effects.constEnd(), [name](const EffectPair &pair) {
|
||||
return pair.first == name;
|
||||
});
|
||||
if (it != loaded_effects.constEnd()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
const QString internalName = name.toLower();
|
||||
KService::Ptr service = findEffectService(name.toLower());
|
||||
if (!service) {
|
||||
// effect not found
|
||||
return false;
|
||||
}
|
||||
|
||||
if (isScriptedEffect(service)) {
|
||||
// scripted effects are generally supported
|
||||
return true;
|
||||
}
|
||||
|
||||
// next checks might require a context
|
||||
makeOpenGLContextCurrent();
|
||||
m_compositor->addRepaintFull();
|
||||
|
||||
// try builtin effects
|
||||
const QByteArray builtInName = internalName.mid(13).toUtf8(); // drop kwin4_effect_
|
||||
if (BuiltInEffects::available(builtInName)) {
|
||||
return BuiltInEffects::supported(builtInName);
|
||||
}
|
||||
|
||||
// try remaining effects
|
||||
KLibrary* library = findEffectLibrary(service.data());
|
||||
if (!library) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const QString supported_symbol = QStringLiteral("effect_supported_") + name;
|
||||
KLibrary::void_function_ptr supported_func = library->resolveFunction(supported_symbol.toAscii().data());
|
||||
|
||||
bool supported = true;
|
||||
|
||||
if (supported_func) {
|
||||
typedef bool (*t_supportedfunc)();
|
||||
t_supportedfunc supportedFunction = reinterpret_cast<t_supportedfunc>(supported_func);
|
||||
supported = supportedFunction();
|
||||
}
|
||||
|
||||
library->unload();
|
||||
|
||||
return supported;
|
||||
}
|
||||
|
||||
QList< bool > EffectsHandlerImpl::areEffectsSupported(const QStringList &names)
|
||||
{
|
||||
QList< bool > retList;
|
||||
for (const QString &name : names) {
|
||||
retList << isEffectSupported(name);
|
||||
}
|
||||
return retList;
|
||||
}
|
||||
|
||||
void EffectsHandlerImpl::reloadEffect(Effect *effect)
|
||||
{
|
||||
QString effectName;
|
||||
|
|
|
@ -31,6 +31,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|||
#include <QHash>
|
||||
#include <QQueue>
|
||||
#include <Plasma/FrameSvg>
|
||||
#include <KService>
|
||||
|
||||
namespace Plasma {
|
||||
class Theme;
|
||||
|
@ -220,6 +221,8 @@ public Q_SLOTS:
|
|||
Q_SCRIPTABLE void toggleEffect(const QString& name);
|
||||
Q_SCRIPTABLE void unloadEffect(const QString& name);
|
||||
Q_SCRIPTABLE bool isEffectLoaded(const QString& name) const;
|
||||
Q_SCRIPTABLE bool isEffectSupported(const QString& name);
|
||||
Q_SCRIPTABLE QList<bool> areEffectsSupported(const QStringList &names);
|
||||
Q_SCRIPTABLE QString supportInformation(const QString& name) const;
|
||||
Q_SCRIPTABLE QString debug(const QString& name, const QString& parameter = QString()) const;
|
||||
|
||||
|
@ -265,6 +268,8 @@ private Q_SLOTS:
|
|||
void slotEffectsQueried();
|
||||
|
||||
private:
|
||||
KService::Ptr findEffectService(const QString &internalName) const;
|
||||
bool isScriptedEffect(KService::Ptr service) const;
|
||||
typedef QVector< Effect*> EffectsList;
|
||||
typedef EffectsList::const_iterator EffectsIterator;
|
||||
Effect *loadBuiltInEffect(const QByteArray &name, bool checkDefault);
|
||||
|
|
|
@ -26,6 +26,15 @@
|
|||
<arg type="b" direction="out"/>
|
||||
<arg name="name" type="s" direction="in"/>
|
||||
</method>
|
||||
<method name="isEffectSupported">
|
||||
<arg type="b" direction="out"/>
|
||||
<arg name="name" type="s" direction="in"/>
|
||||
</method>
|
||||
<method name="areEffectsSupported">
|
||||
<arg type="ab" direction="out"/>
|
||||
<annotation name="org.qtproject.QtDBus.QtTypeName.Out0" value="QList<bool>"/>
|
||||
<arg name="names" type="as" direction="in"/>
|
||||
</method>
|
||||
<method name="supportInformation">
|
||||
<arg type="s" direction="out"/>
|
||||
<arg name="name" type="s" direction="in"/>
|
||||
|
|
Loading…
Reference in a new issue