diff --git a/app/qml/DevicePage.qml b/app/qml/DevicePage.qml index 065adc74..3b6d9247 100644 --- a/app/qml/DevicePage.qml +++ b/app/qml/DevicePage.qml @@ -1,137 +1,144 @@ /* * Copyright 2015 Aleix Pol Gonzalez * * 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 . */ import QtQuick 2.2 import QtQuick.Controls 2.1 import QtQuick.Layouts 1.1 import org.kde.kirigami 2.0 as Kirigami import org.kde.kdeconnect 1.0 Kirigami.Page { id: deviceView property QtObject currentDevice title: currentDevice.name actions.contextualActions: deviceLoader.item.actions leftPadding: 0 rightPadding: 0 topPadding: 0 bottomPadding: 0 Loader { id: deviceLoader anchors.fill: parent Layout.fillHeight: true Layout.fillWidth: true sourceComponent: deviceView.currentDevice.hasPairingRequests ? pairDevice : deviceView.currentDevice.isTrusted ? trustedDevice : untrustedDevice Component { id: trustedDevice ColumnLayout { property list actions: [ Kirigami.Action { onTriggered: deviceView.currentDevice.unpair() text: i18n("Unpair") }, Kirigami.Action { text: i18n("Send Ping") onTriggered: { deviceView.currentDevice.pluginCall("ping", "sendPing"); } } ] id: trustedView spacing: 0 Layout.fillHeight: true Layout.fillWidth: true PluginItem { label: i18n("Multimedia control") interfaceFactory: MprisDbusInterfaceFactory component: "qrc:/qml/mpris.qml" pluginName: "mprisremote" } PluginItem { label: i18n("Remote input") interfaceFactory: RemoteControlDbusInterfaceFactory component: "qrc:/qml/mousepad.qml" pluginName: "remotecontrol" } PluginItem { label: i18n("Presentation Remote") interfaceFactory: RemoteKeyboardDbusInterfaceFactory component: "qrc:/qml/presentationRemote.qml" pluginName: "remotecontrol" } PluginItem { readonly property var lockIface: LockDeviceDbusInterfaceFactory.create(deviceView.currentDevice.id()) pluginName: "lockdevice" label: lockIface.isLocked ? i18n("Unlock") : i18n("Lock") onClicked: { lockIface.isLocked = !lockIface.isLocked; } } PluginItem { readonly property var findmyphoneIface: FindMyPhoneDbusInterfaceFactory.create(deviceView.currentDevice.id()) pluginName: "findmyphone" label: i18n("Find Device") onClicked: { findmyphoneIface.ring() } } + PluginItem { + label: i18n("Run command") + interfaceFactory: RemoteCommandsDbusInterfaceFactory + component: "qrc:/qml/runcommand.qml" + pluginName: "remotecommands" + } + Item { Layout.fillHeight: true } } } Component { id: untrustedDevice Item { readonly property var actions: [] Button { anchors.centerIn: parent text: i18n("Pair") onClicked: deviceView.currentDevice.requestPair() } } } Component { id: pairDevice Item { readonly property var actions: [] RowLayout { anchors.centerIn: parent Button { text: i18n("Accept") onClicked: deviceView.currentDevice.acceptPairing() } Button { text: i18n("Reject") onClicked: deviceView.currentDevice.rejectPairing() } } } } } } diff --git a/app/qml/runcommand.qml b/app/qml/runcommand.qml new file mode 100644 index 00000000..5b30ea5e --- /dev/null +++ b/app/qml/runcommand.qml @@ -0,0 +1,53 @@ +/* + * Copyright 2018 Nicolas Fella + * + * 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 . + */ + +import QtQuick 2.2 +import QtQuick.Controls 2.2 +import QtQuick.Layouts 1.1 +import org.kde.kirigami 2.0 as Kirigami +import org.kde.kdeconnect 1.0 + +Kirigami.Page +{ + id: root + title: i18n("Run command") + property QtObject pluginInterface + + actions.main: Kirigami.Action { + icon.name: "document-edit" + text: i18n("Edit commands") + onTriggered: pluginInterface.editCommands() + } + + ListView { + anchors.fill: parent + model: RemoteCommandsModel { + deviceId: pluginInterface.deviceId + } + delegate: Kirigami.BasicListItem { + width: ListView.view.width + label: name + "\n" + command + onClicked: pluginInterface.triggerCommand(key) + reserveSpaceForIcon: false + } + } + +} + diff --git a/app/resources.qrc b/app/resources.qrc index 847061c7..3ada61ab 100644 --- a/app/resources.qrc +++ b/app/resources.qrc @@ -1,12 +1,13 @@ qml/main.qml qml/mpris.qml qml/mousepad.qml qml/presentationRemote.qml qml/PluginItem.qml qml/DevicePage.qml qml/FindDevicesPage.qml + qml/runcommand.qml diff --git a/interfaces/CMakeLists.txt b/interfaces/CMakeLists.txt index 6010bc62..886759d3 100644 --- a/interfaces/CMakeLists.txt +++ b/interfaces/CMakeLists.txt @@ -1,85 +1,87 @@ project(KDEConnectInterfaces) function(geninterface source_h output_h) set(xml_file ${CMAKE_CURRENT_BINARY_DIR}/${output_h}.xml) qt5_generate_dbus_interface( ${source_h} ${xml_file}) list(APPEND libkdeconnect_HEADERS ${CMAKE_CURRENT_BINARY_DIR}/${output_h}) set_source_files_properties(${xml_file} PROPERTIES NO_NAMESPACE true) qt5_add_dbus_interface(libkdeconnect_SRC ${xml_file} ${output_h}) set(libkdeconnect_SRC ${libkdeconnect_SRC} PARENT_SCOPE) set(libkdeconnect_HEADERS ${libkdeconnect_HEADERS} PARENT_SCOPE) endfunction() set(libkdeconnect_SRC dbusinterfaces.cpp devicesmodel.cpp notificationsmodel.cpp devicessortproxymodel.cpp conversationmessage.cpp + remotecommandsmodel.cpp # modeltest.cpp ) set(libkdeconnect_public_HEADERS KDEConnect/DevicesModel KDEConnect/NotificationsModel ) set(libkdeconnect_HEADERS devicesmodel.h notificationsmodel.h conversationmessage.h dbusinterfaces.h + remotecommandsmodel.h ${CMAKE_CURRENT_BINARY_DIR}/kdeconnectinterfaces_export.h ) geninterface(${CMAKE_SOURCE_DIR}/core/daemon.h daemoninterface) geninterface(${CMAKE_SOURCE_DIR}/core/device.h deviceinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/battery/batterydbusinterface.h devicebatteryinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/sftp/sftpplugin.h devicesftpinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/notifications/notificationsdbusinterface.h devicenotificationsinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/findmyphone/findmyphoneplugin.h devicefindmyphoneinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/notifications/notification.h notificationinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/mprisremote/mprisremoteplugin.h mprisremoteinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/remotecontrol/remotecontrolplugin.h remotecontrolinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/lockdevice/lockdeviceplugin.h lockdeviceinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/remotecommands/remotecommandsplugin.h remotecommandsinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/remotekeyboard/remotekeyboardplugin.h remotekeyboardinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/telephony/telephonyplugin.h telephonyinterface) geninterface(${CMAKE_SOURCE_DIR}/plugins/telephony/conversationsdbusinterface.h conversationsinterface) add_library(kdeconnectinterfaces SHARED ${libkdeconnect_SRC}) set_target_properties(kdeconnectinterfaces PROPERTIES VERSION ${KDECONNECT_VERSION} SOVERSION ${KDECONNECT_VERSION_MAJOR} ) generate_export_header(kdeconnectinterfaces EXPORT_FILE_NAME ${CMAKE_CURRENT_BINARY_DIR}/kdeconnectinterfaces_export.h BASE_NAME KDEConnectInterfaces) target_link_libraries(kdeconnectinterfaces LINK_PUBLIC Qt5::Gui Qt5::DBus LINK_PRIVATE KF5::ConfigCore KF5::I18n ) configure_file(KDEConnectConfig.cmake.in ${CMAKE_BINARY_DIR}/interfaces/KDEConnectConfig.cmake @ONLY) ecm_setup_version( "${KDECONNECT_VERSION_MAJOR}.${KDECONNECT_VERSION_MINOR}.${KDECONNECT_VERSION_PATCH}" VARIABLE_PREFIX KDECONNECTINTERFACES VERSION_HEADER "${CMAKE_CURRENT_BINARY_DIR}/kdeconnectinterfaces_version.h" PACKAGE_VERSION_FILE "${CMAKE_CURRENT_BINARY_DIR}/KDEConnectConfigVersion.cmake" SOVERSION ${KDECONNECT_VERSION_MAJOR}) install(TARGETS kdeconnectinterfaces EXPORT kdeconnectLibraryTargets ${INSTALL_TARGETS_DEFAULT_ARGS} LIBRARY NAMELINK_SKIP) ## Don't install header files until API/ABI policy is defined # # install(FILES ${libkdeconnect_HEADERS} DESTINATION ${INCLUDE_INSTALL_DIR}/kdeconnect COMPONENT Devel) # install(FILES ${libkdeconnect_public_HEADERS} DESTINATION ${INCLUDE_INSTALL_DIR}/KDEConnect COMPONENT Devel) # install(FILES ${CMAKE_BINARY_DIR}/interfaces/KDEConnectConfig.cmake # ${CMAKE_BINARY_DIR}/interfaces/KDEConnectConfigVersion.cmake # DESTINATION ${LIB_INSTALL_DIR}/cmake/KDEConnect) diff --git a/interfaces/remotecommandsmodel.cpp b/interfaces/remotecommandsmodel.cpp new file mode 100644 index 00000000..1dbe0062 --- /dev/null +++ b/interfaces/remotecommandsmodel.cpp @@ -0,0 +1,153 @@ +/** + * Copyright 2018 Nicolas Fella + * + * 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 . + */ + +#include "remotecommandsmodel.h" +#include "interfaces_debug.h" + +#include +#include + +RemoteCommandsModel::RemoteCommandsModel(QObject* parent) + : QAbstractListModel(parent) + , m_dbusInterface(nullptr) +{ + + connect(this, &QAbstractItemModel::rowsInserted, + this, &RemoteCommandsModel::rowsChanged); + connect(this, &QAbstractItemModel::rowsRemoved, + this, &RemoteCommandsModel::rowsChanged); + + QDBusServiceWatcher* watcher = new QDBusServiceWatcher(DaemonDbusInterface::activatedService(), + QDBusConnection::sessionBus(), QDBusServiceWatcher::WatchForOwnerChange, this); + connect(watcher, &QDBusServiceWatcher::serviceRegistered, this, &RemoteCommandsModel::refreshCommandList); + connect(watcher, &QDBusServiceWatcher::serviceUnregistered, this, &RemoteCommandsModel::clearCommands); +} + +QHash RemoteCommandsModel::roleNames() const +{ + //Role names for QML + QHash names = QAbstractItemModel::roleNames(); + names.insert(KeyRole, "key"); + names.insert(NameRole, "name"); + names.insert(CommandRole, "command"); + return names; +} + +RemoteCommandsModel::~RemoteCommandsModel() +{ +} + +QString RemoteCommandsModel::deviceId() const +{ + return m_deviceId; +} + +void RemoteCommandsModel::setDeviceId(const QString& deviceId) +{ + m_deviceId = deviceId; + + if (m_dbusInterface) { + delete m_dbusInterface; + } + + m_dbusInterface = new RemoteCommandsDbusInterface(deviceId, this); + + connect(m_dbusInterface, &OrgKdeKdeconnectDeviceRemotecommandsInterface::commandsChanged, + this, &RemoteCommandsModel::refreshCommandList); + + refreshCommandList(); + + Q_EMIT deviceIdChanged(deviceId); +} + +void RemoteCommandsModel::refreshCommandList() +{ + if (!m_dbusInterface) { + return; + } + + clearCommands(); + + if (!m_dbusInterface->isValid()) { + qCWarning(KDECONNECT_INTERFACES) << "dbus interface not valid"; + return; + } + + const auto cmds = QJsonDocument::fromJson(m_dbusInterface->commands()).object(); + + beginResetModel(); + + for (auto it = cmds.constBegin(), itEnd = cmds.constEnd(); it!=itEnd; ++it) { + const QJsonObject cont = it->toObject(); + Command command; + command.key = it.key(); + command.name = cont.value(QStringLiteral("name")).toString(); + command.command = cont.value(QStringLiteral("command")).toString(); + m_commandList.append(command); + } + + endResetModel(); +} + +QVariant RemoteCommandsModel::data(const QModelIndex& index, int role) const +{ + if (!index.isValid() + || index.row() < 0 + || index.row() >= m_commandList.count()) + { + return QVariant(); + } + + if (!m_dbusInterface || !m_dbusInterface->isValid()) { + return QVariant(); + } + + Command command = m_commandList[index.row()]; + + switch (role) { + case KeyRole: + return command.key; + case NameRole: + return command.name; + case CommandRole: + return command.command; + default: + return QVariant(); + } +} + +int RemoteCommandsModel::rowCount(const QModelIndex& parent) const +{ + if (parent.isValid()) { + //Return size 0 if we are a child because this is not a tree + return 0; + } + + return m_commandList.count(); +} + +void RemoteCommandsModel::clearCommands() +{ + if (!m_commandList.isEmpty()) { + beginRemoveRows(QModelIndex(), 0, m_commandList.size() - 1); + m_commandList.clear(); + endRemoveRows(); + } +} diff --git a/interfaces/remotecommandsmodel.h b/interfaces/remotecommandsmodel.h new file mode 100644 index 00000000..d999e8cc --- /dev/null +++ b/interfaces/remotecommandsmodel.h @@ -0,0 +1,72 @@ +/** + * Copyright 2018 Nicolas Fella + * + * 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 . + */ + +#ifndef REMOTECOMMANDSMODEL_H +#define REMOTECOMMANDSMODEL_H + +#include + +#include "interfaces/dbusinterfaces.h" + +struct Command { + QString key; + QString name; + QString command; +}; + +class KDECONNECTINTERFACES_EXPORT RemoteCommandsModel + : public QAbstractListModel +{ + Q_OBJECT + Q_PROPERTY(QString deviceId READ deviceId WRITE setDeviceId NOTIFY deviceIdChanged) + +public: + enum ModelRoles { + KeyRole, + NameRole, + CommandRole + }; + + explicit RemoteCommandsModel(QObject* parent = nullptr); + ~RemoteCommandsModel() override; + + QString deviceId() const; + void setDeviceId(const QString& deviceId); + + QVariant data(const QModelIndex& index, int role) const override; + int rowCount(const QModelIndex& parent = QModelIndex()) const override; + + QHash roleNames() const override; + +private Q_SLOTS: + void refreshCommandList(); + void clearCommands(); + +Q_SIGNALS: + void deviceIdChanged(const QString& value); + void rowsChanged(); + +private: + RemoteCommandsDbusInterface* m_dbusInterface; + QVector m_commandList; + QString m_deviceId; +}; + +#endif // DEVICESMODEL_H diff --git a/plasmoid/declarativeplugin/kdeconnectdeclarativeplugin.cpp b/plasmoid/declarativeplugin/kdeconnectdeclarativeplugin.cpp index dd9f2fc3..6728b5ce 100644 --- a/plasmoid/declarativeplugin/kdeconnectdeclarativeplugin.cpp +++ b/plasmoid/declarativeplugin/kdeconnectdeclarativeplugin.cpp @@ -1,141 +1,152 @@ /** * Copyright 2013 Albert Vaca * * 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 . */ #include "kdeconnectdeclarativeplugin.h" #include #include #include #include #include #include "objectfactory.h" #include "responsewaiter.h" #include "interfaces/devicessortproxymodel.h" #include "interfaces/devicesmodel.h" #include "interfaces/notificationsmodel.h" +#include QObject* createDeviceDbusInterface(const QVariant& deviceId) { return new DeviceDbusInterface(deviceId.toString()); } QObject* createDeviceBatteryDbusInterface(const QVariant& deviceId) { return new DeviceBatteryDbusInterface(deviceId.toString()); } QObject* createFindMyPhoneInterface(const QVariant& deviceId) { return new FindMyPhoneDeviceDbusInterface(deviceId.toString()); } QObject* createRemoteKeyboardInterface(const QVariant& deviceId) { return new RemoteKeyboardDbusInterface(deviceId.toString()); } QObject* createSftpInterface(const QVariant& deviceId) { return new SftpDbusInterface(deviceId.toString()); } QObject* createRemoteControlInterface(const QVariant& deviceId) { return new RemoteControlDbusInterface(deviceId.toString()); } QObject* createMprisInterface(const QVariant& deviceId) { return new MprisDbusInterface(deviceId.toString()); } QObject* createDeviceLockInterface(const QVariant& deviceId) { Q_ASSERT(!deviceId.toString().isEmpty()); return new LockDeviceDbusInterface(deviceId.toString()); } QObject* createTelephonyInterface(const QVariant& deviceId) { return new TelephonyDbusInterface(deviceId.toString()); } QObject* createDBusResponse() { return new DBusAsyncResponse(); } +QObject* createRemoteCommandsInterface(const QVariant& deviceId) +{ + return new RemoteCommandsDbusInterface(deviceId.toString()); +} + void KdeConnectDeclarativePlugin::registerTypes(const char* uri) { qmlRegisterType(uri, 1, 0, "DevicesModel"); qmlRegisterType(uri, 1, 0, "NotificationsModel"); + qmlRegisterType(uri, 1, 0, "RemoteCommandsModel"); qmlRegisterType(uri, 1, 0, "DBusAsyncResponse"); qmlRegisterType(uri, 1, 0, "DevicesSortProxyModel"); qmlRegisterUncreatableType(uri, 1, 0, "MprisDbusInterface", QStringLiteral("You're not supposed to instantiate interfacess")); qmlRegisterUncreatableType(uri, 1, 0, "LockDeviceDbusInterface", QStringLiteral("You're not supposed to instantiate interfacess")); qmlRegisterUncreatableType(uri, 1, 0, "FindMyPhoneDbusInterface", QStringLiteral("You're not supposed to instantiate interfacess")); qmlRegisterUncreatableType(uri, 1, 0, "RemoteKeyboardDbusInterface", QStringLiteral("You're not supposed to instantiate interfacess")); qmlRegisterUncreatableType(uri, 1, 0, "DeviceDbusInterface", QStringLiteral("You're not supposed to instantiate interfacess")); + qmlRegisterUncreatableType(uri, 1, 0, "RemoteCommandsDbusInterface", QStringLiteral("You're not supposed to instantiate interfacess")); qmlRegisterSingletonType(uri, 1, 0, "DaemonDbusInterface", [](QQmlEngine*, QJSEngine*) -> QObject* { return new DaemonDbusInterface; } ); } void KdeConnectDeclarativePlugin::initializeEngine(QQmlEngine* engine, const char* uri) { QQmlExtensionPlugin::initializeEngine(engine, uri); - + engine->rootContext()->setContextProperty(QStringLiteral("DeviceDbusInterfaceFactory") , new ObjectFactory(engine, createDeviceDbusInterface)); - + engine->rootContext()->setContextProperty(QStringLiteral("DeviceBatteryDbusInterfaceFactory") , new ObjectFactory(engine, createDeviceBatteryDbusInterface)); - + engine->rootContext()->setContextProperty(QStringLiteral("FindMyPhoneDbusInterfaceFactory") , new ObjectFactory(engine, createFindMyPhoneInterface)); engine->rootContext()->setContextProperty(QStringLiteral("SftpDbusInterfaceFactory") , new ObjectFactory(engine, createSftpInterface)); engine->rootContext()->setContextProperty(QStringLiteral("RemoteKeyboardDbusInterfaceFactory") , new ObjectFactory(engine, createRemoteKeyboardInterface)); engine->rootContext()->setContextProperty(QStringLiteral("MprisDbusInterfaceFactory") , new ObjectFactory(engine, createMprisInterface)); engine->rootContext()->setContextProperty(QStringLiteral("RemoteControlDbusInterfaceFactory") , new ObjectFactory(engine, createRemoteControlInterface)); engine->rootContext()->setContextProperty(QStringLiteral("LockDeviceDbusInterfaceFactory") , new ObjectFactory(engine, createDeviceLockInterface)); engine->rootContext()->setContextProperty(QStringLiteral("TelephonyDbusInterfaceFactory") , new ObjectFactory(engine, createTelephonyInterface)); - + engine->rootContext()->setContextProperty(QStringLiteral("DBusResponseFactory") - , new ObjectFactory(engine, createDBusResponse)); - + , new ObjectFactory(engine, createDBusResponse)); + engine->rootContext()->setContextProperty(QStringLiteral("DBusResponseWaiter") , DBusResponseWaiter::instance()); + + engine->rootContext()->setContextProperty(QStringLiteral("RemoteCommandsDbusInterfaceFactory") + , new ObjectFactory(engine, createRemoteCommandsInterface)); } diff --git a/plugins/remotecommands/remotecommandsplugin.cpp b/plugins/remotecommands/remotecommandsplugin.cpp index 76839f32..12cf1f59 100644 --- a/plugins/remotecommands/remotecommandsplugin.cpp +++ b/plugins/remotecommands/remotecommandsplugin.cpp @@ -1,85 +1,93 @@ /** * Copyright 2016 Aleix Pol Gonzalez * * 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 . */ #include "remotecommandsplugin.h" #include #include #include #include #include #include #include #include #include #include #define PACKET_TYPE_RUNCOMMAND_REQUEST QLatin1String("kdeconnect.runcommand.request") K_PLUGIN_FACTORY_WITH_JSON( KdeConnectPluginFactory, "kdeconnect_remotecommands.json", registerPlugin< RemoteCommandsPlugin >(); ) Q_LOGGING_CATEGORY(KDECONNECT_PLUGIN_REMOTECOMMANDS, "kdeconnect.plugin.remotecommands") RemoteCommandsPlugin::RemoteCommandsPlugin(QObject* parent, const QVariantList& args) : KdeConnectPlugin(parent, args) , m_commands("{}") + , m_canAddCommand(false) { } RemoteCommandsPlugin::~RemoteCommandsPlugin() = default; bool RemoteCommandsPlugin::receivePacket(const NetworkPacket& np) { if (np.has(QStringLiteral("commandList"))) { + m_canAddCommand = np.get(QStringLiteral("canAddCommand")); setCommands(np.get(QStringLiteral("commandList"))); return true; } return false; } void RemoteCommandsPlugin::connected() { NetworkPacket np(PACKET_TYPE_RUNCOMMAND_REQUEST, {{"requestCommandList", true}}); sendPacket(np); } QString RemoteCommandsPlugin::dbusPath() const { return "/modules/kdeconnect/devices/" + device()->id() + "/remotecommands"; } void RemoteCommandsPlugin::setCommands(const QByteArray& cmds) { if (m_commands != cmds) { m_commands = cmds; Q_EMIT commandsChanged(m_commands); } } void RemoteCommandsPlugin::triggerCommand(const QString& key) { NetworkPacket np(PACKET_TYPE_RUNCOMMAND_REQUEST, {{ "key", key }}); sendPacket(np); } +void RemoteCommandsPlugin::editCommands() +{ + NetworkPacket np(PACKET_TYPE_RUNCOMMAND_REQUEST, {{ "setup", true }}); + sendPacket(np); +} + #include "remotecommandsplugin.moc" diff --git a/plugins/remotecommands/remotecommandsplugin.h b/plugins/remotecommands/remotecommandsplugin.h index bc32b23b..116d4d83 100644 --- a/plugins/remotecommands/remotecommandsplugin.h +++ b/plugins/remotecommands/remotecommandsplugin.h @@ -1,60 +1,67 @@ /** * Copyright 2016 Aleix Pol Gonzalez * * 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 . */ #ifndef REMOTECOMMANDSPLUGIN_H #define REMOTECOMMANDSPLUGIN_H #include #include #include #include #include #include #include class Q_DECL_EXPORT RemoteCommandsPlugin : public KdeConnectPlugin { Q_OBJECT Q_CLASSINFO("D-Bus Interface", "org.kde.kdeconnect.device.remotecommands") Q_PROPERTY(QByteArray commands READ commands NOTIFY commandsChanged) + Q_PROPERTY(QString deviceId READ deviceId CONSTANT) + Q_PROPERTY(bool canAddCommand READ canAddCommand CONSTANT) public: explicit RemoteCommandsPlugin(QObject* parent, const QVariantList& args); ~RemoteCommandsPlugin() override; Q_SCRIPTABLE void triggerCommand(const QString& key); + Q_SCRIPTABLE void editCommands(); + QByteArray commands() const { return m_commands; } + QString deviceId() const { return device()->id(); } + bool canAddCommand() const { return m_canAddCommand; } bool receivePacket(const NetworkPacket& np) override; void connected() override; QString dbusPath() const override; Q_SIGNALS: void commandsChanged(const QByteArray& commands); private: void setCommands(const QByteArray& commands); QByteArray m_commands; + bool m_canAddCommand; }; #endif