한국어
Qt
 

Qt Framework은 프로세스간 통신(IPC)을 위한 몇 가지 방법을 제공하는데 이 글에서는 Qt D-Bus에 대해 설명한다. 

 

D-Bus는 리눅스용으로 개발된 메세지 버스 시스템으로 RPC(Remote Procedure Call) 및 프로세스간의 통신(IPC) 방법으로 사용된다. 리눅스계열에서 주로 사용되며 꽤 오래 전에 윈도우에서도 사용할 수 있도록 포팅이 진행되었다. 

 

이 글에서는 윈도우즈 기반에서 Qt D-Bus를 사용, 설명할 것이므로 먼저 윈도우즈에서 D-Bus를 사용하기 위한 방법을 알아본다. 윈도우즈 기반에서 설명하긴하지만 Qt D-Bus는 리눅스건 윈도우즈건 플랫폼에 무관하게 사용할 수 있다. (D-Bus기본 개념은 이 글을 참조)

 

최신 소스코드(git://anongit.freedesktop.org/git/dbus/dbus)를 직접 컴파일 후 사용할 수 도 있고, 비공식이긴하지만 패키징된 설치파일을 다운로드받아 사용할 수 있는 방법이 있다.( 여기서는 오래된 버전이긴 하지만 간단히 비공식 설치파일을 다운로드 받아 설치한다.)

 

아래 주소를 방문하면 윈도우즈용 설치파일과 간단한 예제 응용프로그램도 다운로드 받을 수 있다. 윈도우즈용 설치파일을 다운로드 받아 설치한다.

https://code.google.com/archive/p/dbus-windows-installer/downloads

 

install_D-Bus.png

 

설치가 완료된 이후 C:\Program Files (x86)\D-Bus\bin 에는 dbus-daemon.exe을 포함한 몇가지 유틸리티도 설치되어 있다.

D-Bus_bin.png

 

D-Bus를 사용하려면 dbus-daemon이 실행되어 있어야 한다.

윈도우즈 명령 프롬프트(cmd)를 열어서 먼저 dbus-env.bat과 dbus-daemon --session 을 차례로 명령한다.

excute_dbus-daemon.png

 


 

이제 Qt D-Bus를 사용하기 위해 두개의 간단한 프로젝트를 생성한다. 프로젝트 폴더 구조는 다음과 같다.

lightsystem.png

 

하나는 on, off 상태에 따라 동작되는 light이고, 다른 하나는 이조명을 제어하는 switch 이다.

light.png switch.png

 

이 간단한 프로젝트들은 Qt D-Bus을 이용하여 light system으로 통합된다.

 

MyLight Class

MyLight객체는 상태를 나타내는 프로퍼티를 가지며 setter와 getter를 제공한다. 이 헤더파일은 D-Bus의 인터페이스로 사용될 것이다.

light.h

#include <QObject>

class MyLight : public QObject
{
    Q_OBJECT
    Q_PROPERTY(bool isOn READ getIsOn WRITE setIsOn NOTIFY lightChanged)

public:
    explicit MyLight(QObject *parent = nullptr);

    bool getIsOn() const;
    void setIsOn(bool isOn);

signals:
    void lightChanged();

public slots:
    void turnOn();
    void turnOff();

private:
    bool mIsOn;
};

 

Qt용 명령 프롬프트를 실행하고 아래와 같은 명령으로 interface xml파일을 생성할 수 있다.

qdbuscpp2xml light\light.h

 

출력된 내용을 복사해서 프로젝트의 inferface디렉토리에 light.xml 파일로 생성한다. 이 light.xml은 light에서 ADAPTOR로 사용되고 switch에서는 INTERFACE로 사용된다.

qdbuscpp2xml.png

 

light프로젝트 파일(.pro)에 아래 내용을 추가한다.

QT += dbus
CONFIG += c++11
 
DBUS_ADAPTORS += ../interface/light.xml

 

MyLight 생성자에서 MyLightAdaptor를 생성한다.(컴파일이 실행시에 light_adaptor.h파일이 만들어진다.)

light.cpp

#include "light.h"
#include "light_adaptor.h"


MyLight::MyLight(QObject *parent)
    : QObject(parent),
      mIsOn(false)
{
    // Create interface adaptor
    new MyLightAdaptor(this);
}


bool MyLight::getIsOn() const
{
    return mIsOn;
}


void MyLight::setIsOn(bool isOn)
{
    if(mIsOn != isOn){
        mIsOn = isOn;
        emit lightChanged();
    }
}


void MyLight::turnOn()
{
    setIsOn(true);
}


void MyLight::turnOff()
{
    setIsOn(false);
}

 

main.cpp에서는 D-Bus의 세션버스에 MyLight 객체 및 서비스를 등록한다.

main.cpp

#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QtDBus>


#include <QtQml>
#include "light.h"


int main(int argc, char *argv[])
{
    QGuiApplication app(argc, argv);

    QQmlApplicationEngine engine;

    // Create new instance
    MyLight myLight;

    engine.rootContext()->setContextProperty("myLight", &myLight);

    // Connect to session bus
    QDBusConnection connection = QDBusConnection::sessionBus();
    connection.registerObject("/light", &myLight);
    connection.registerService("cong.service.light");

    engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
    if (engine.rootObjects().isEmpty())
        return -1;

    return app.exec();
}

 

이제 light를 컴파일 및 실행하고 서비스가 정상적으로 등록되어 있는지 확인하기 위해서  QDBusViewer를 실행 해 본다. (Qt가 설치된 곳에 있다.)

Qt D-Bus는 기본 D-Bus 컨셉을 유지하면서도 D-Bus의 저수준 API를 캡슐화하여 Qt 개발자에게 익숙한 시그널, 슬롯, 프로퍼티 개념을 제공하고 있다. Method를 각각 더블클릭해서 light가 on, off됨을 확인 할 수 있다.

QDBusViewer.png

 

switch프로젝트 파일(.pro)에는 아래 내용을 추가한다.

QT += dbus
CONFIG += c++11
 
DBUS_INTERFACES += ../interface/light.xml

 

LightController Class

controller객체는 조명을 제어하기위한 on, off 인터페이스만 제공하고 private멤버인 D-Bus의 interface 객체를 가진다.

lightcontroller.h

#include <QObject>

#include "light_interface.h"

class LightController : public QObject
{
    Q_OBJECT
public:
    explicit LightController(QObject *parent = nullptr);

private:
    local::MyLight *theLight;

public slots:
    void turnOn();
    void turnOff();
};

 

생성자에서 세션버스에 등록된 서비스 및 오브젝트 path의 interface를 생성한다.

lightcontroller.cpp

#include "lightcontroller.h"


LightController::LightController(QObject *parent) : QObject(parent)
{
    theLight = new local::MyLight("cong.service.light", "/light",
                                            QDBusConnection::sessionBus(), this);
}


void LightController::turnOn()
{
    theLight->turnOn();
}


void LightController::turnOff()
{
    theLight->turnOff();
}

 

LightController객체를 생성하고 qml에서 사용할 수 있도록 한다.

main.cpp

#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QtQml>
#include "lightcontroller.h"


int main(int argc, char *argv[])
{
    QGuiApplication app(argc, argv);

    QQmlApplicationEngine engine;

    LightController controller;
    engine.rootContext()->setContextProperty("controller", &controller);

    engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
    if (engine.rootObjects().isEmpty())
        return -1;

    return app.exec();
}

 

switch를 컴파일 및 실행하고 on, off 버튼을 클릭해보자!

jwplayer

번호 제목 글쓴이 날짜 조회 수
공지 Qt프로그래밍(QtQuick) Beginner를 위한 글 읽는 순서 운영자 2019.01.05 86174
30 QTextCodec클래스를 사용하여 유니코드와 EUC-KR 변환 makersweb 2019.03.25 2907
» Windows에서 Qt D-Bus를 사용하여 프로세스간 통신(IPC) file makersweb 2019.05.02 4510
28 Q_D매크로와 d-pointer file makersweb 2019.05.07 762
27 Qt기반의 오픈소스 프로젝트들 makersweb 2019.05.15 5462
26 QtSerialPort를 사용한 시리얼(Serial)통신 [3] makersweb 2019.05.21 11974
25 Qt기반의 오픈소스 프로젝트들 - 2 운영자 2019.07.21 4021
24 [Qt News] Qt 6 기술 비전 (Technical vision for Qt 6) [2] j2doll 2019.08.08 2122
23 [Qt News] Qt for Python을 위한 기술 비전 j2doll 2019.08.20 1626
22 컨테이너에 적재된 객체를 편리하게 삭제하기 makersweb 2019.09.18 1671
21 많은 리소스를 사용하는 Qt프로젝트에서 고려해봐야 할 qmake 옵션 makersweb 2019.10.11 1236
20 QOpenVirtualkeyboard(Qt 5용 한글 및 영문, 숫자 가상키보드) file makersweb 2019.11.27 2251
19 Qt Marketplace 발표 makersweb 2019.12.02 617
18 Qt의 오픈소스 라이센스 소개 file makersweb 2019.12.15 12621
17 Qt 멀티 스레드 프로그래밍 시 유의해야 할 몇 가지 makersweb 2020.01.13 4895
16 2020년에 변경되는 Qt 오퍼 (Qt offering changes 2020) [2] j2doll 2020.01.31 723
15 QOpenGLWidget 을 투명하게 적용 file makersweb 2020.02.05 1044
14 콘솔에서 사용자 입력받기 file makersweb 2020.03.22 51857
13 Qt기반의 서버와 클라이언트간 SOAP(Simple Object Access Protocol) file makersweb 2020.05.11 978
12 UI 폼(Form)작성 시 탭 순서(Tab Order) 설정 file makersweb 2020.08.24 2811
11 Qt 를 사용하거나 기반으로 하는 응용프로그램 file makersweb 2021.01.30 3850