从 QML App 运行系统命令

Dan*_*olm 17 c++ application-development qml ubuntu-touch

我想从我的应用程序内部运行系统命令。假设使用 SSH 在远程服务器上运行命令。但这不是重点。关键是我不知道如何从应用程序运行任何类型的命令。我在邮件列表中询问,他们推荐我使用 C++ 构建 QML 扩展。但是我不懂 C++,似乎我必须学习这么多才能运行一个简单的命令。

在 Python 中(如在 PHP 中),很容易运行系统命令。在我的 Touch 应用程序中还有其他方法可以做到这一点,或者有人可以帮助我更多吗?或者也许对我的问题有更好的解决方案?

mha*_*119 13

这不是 QML 支持的东西,典型的答案是编写一个 C++ 插件来处理这种事情。

但是,SDK 团队正在规划各种扩展以提供给 QML 应用程序开发人员,这可能是他们在您可以使用的通用插件中实现的内容。

  • 那将不胜感激!我开始寻找一种调用 Python 脚本的方法,但我只能找到一个运行 QML 的 Python 脚本,而不是相反。 (2认同)
  • 我在 14.04 中尝试过 QProcess Launcher 概念并且它工作正常:http://askubuntu.com/a/446736/20275 (2认同)

Jas*_*nti 11

更新:对于 14.04,请参阅 int_ua 的简化答案。

原文:

http://talk.maemo.org/showthread.php?t=87580 上有一个关于如何将扩展添加到 QML 的基本概述。我决定使用 ubuntu-sdk 试一试,这略有不同。我将在下面记录。

对于这个项目,我在 QtCreator 中选择了Ubuntu Touch/Simple UI with C++ Backend。这将创建一个包含两个独立部分的项目,后端和使用 QML 编写的 touchui 前端。在后端,我们将为 Launcher 类添加两个文件。

启动器.h:

#ifndef LAUNCHER_H
#define LAUNCHER_H

#include <QObject>
#include <QProcess>

class Launcher : public QObject
{
    Q_OBJECT
public:
    explicit Launcher(QObject *parent = 0);
    Q_INVOKABLE QString launch(const QString &program);

private:
    QProcess *m_process;
};

#endif // LAUNCHER_H
Run Code Online (Sandbox Code Playgroud)

启动器.cpp:

#include "launcher.h"

Launcher::Launcher(QObject *parent) :
    QObject(parent),
    m_process(new QProcess(this))
{
}

QString Launcher::launch(const QString &program)
{
    m_process->start(program);
    m_process->waitForFinished(-1);
    QByteArray bytes = m_process->readAllStandardOutput();
    QString output = QString::fromLocal8Bit(bytes);
    return output;
}
Run Code Online (Sandbox Code Playgroud)

这个类只是使用 QProcess 来执行一个程序,等待它完成,读取它的标准输出,然后将它作为一个字符串返回。

接下来我们需要修改 backend/backend.cpp 以包含该类。这需要两行。附加一个包含:

#include "launcher.h"
Run Code Online (Sandbox Code Playgroud)

并在BackendPlugin::registerTypes添加一行:

qmlRegisterType<Launcher>(uri, 1, 0, "Launcher");
Run Code Online (Sandbox Code Playgroud)

应该已经有一行用于 MyType,这是包含的示例。在此之后,我们应该能够构建后端。唯一剩下的就是在 main.qml 文件中使用它。为此,我添加了一行:

Launcher { id: myLauncher }
Run Code Online (Sandbox Code Playgroud)

和按钮的 onClick 处理程序,设置:

myType.helloWorld = myLauncher.launch("date");
Run Code Online (Sandbox Code Playgroud)

此时,剩下的就是启动并测试它。这是我遇到问题的地方,因为 QtCreator 默认情况下似乎没有正确设置所有内容。在我的解决方法中,在终端中导航到您的 QtCreator 项目目录并:

mkdir -p Ubuntu/Example
Run Code Online (Sandbox Code Playgroud)

然后将 libUbuntuExample.so 文件从 ProjectBuildDir/backend 复制到 Ubuntu/Example,并将 qmldir 文件从 ProjectName/backend/qmldir 复制。然后你可以运行:

qmlscene -I . ProjectName/touchui/main.qml
Run Code Online (Sandbox Code Playgroud)

我确信可能有一种简单的方法来装配这一切,以便构建/运行正常工作。


int*_*_ua 7

Ubuntu 14.04

QProcess Launcher 类型的概念现在在 Trusty with ubuntu-sdk-teamPPA 中没有问题。只需创建QML Extension Library + Tabbed UI项目(不要在项目名称中使用连字符),替换内容

mytype.h

#ifndef LAUNCHER_H
#define LAUNCHER_H

#include <QObject>
#include <QProcess>

class Launcher : public QObject
{
    Q_OBJECT

public:
    explicit Launcher(QObject *parent = 0);
    ~Launcher();
    Q_INVOKABLE QString launch(const QString &program);

protected:
    QProcess *m_process;
};

#endif // LAUNCHER_H
Run Code Online (Sandbox Code Playgroud)

mytype.cpp

#include "mytype.h"

Launcher::Launcher(QObject *parent) :
    QObject(parent),
    m_process(new QProcess(this))
{

}

QString Launcher::launch(const QString &program)
{
    m_process->start(program);
    m_process->waitForFinished(-1);
    QByteArray bytes = m_process->readAllStandardOutput();
    QString output = QString::fromLocal8Bit(bytes);
    return output;
}

Launcher::~Launcher() {

}
Run Code Online (Sandbox Code Playgroud)

和变革qmlRegisterTypebackend.cpp

qmlRegisterType<Launcher>(uri, 1, 0, "Launcher");
Run Code Online (Sandbox Code Playgroud)

接下来,只需清除MyTypeQML 文件中的所有残留物并添加

        Rectangle {

          Launcher {
             id: qprocess
          }

          Text {
            anchors.centerIn: parent
            text: qprocess.launch("which bash")
          }
        }
Run Code Online (Sandbox Code Playgroud)

无论你喜欢和

import projectname 1.0
Run Code Online (Sandbox Code Playgroud)

在一开始的时候。

可选的

我也使用这个包装器:

function exec(command) {
    return qprocess.launch("sh -c \"" + command + " < /dev/null \"")
}
Run Code Online (Sandbox Code Playgroud)

如果您需要 root 访问权限,请添加pkexec.