qt 處理序間通訊

來源:互聯網
上載者:User

Qt中仍可以利用傳統的處理序間通訊方式(共用記憶體..)
· 在案頭環境中,在傳統的處理序間通訊方式的基礎上發展了更為方便的物件導向的通訊方式
-
KDE環境:DCOP
-
GNOME環境:Bonobo
· DBUS:freedesktop開源項目的Linux IPC通訊機制,KDE和GNOME環境都能支援
· Qt Embedded中定義了一種自己的輕量級的處理序間通訊機制QCOP

QCOP:
· QCOP利用QcopChannel類來實現.
· QcopChannel從Qobject類繼承而來
-
提供了靜態函數send()來發送需要傳遞的訊息和資料
-
靜態函數isRegistered()來查詢某個Channel是否已經被註冊
-
當從channel中接收訊息和資料時,我們需要構造一個QcopChannel的子類並重寫receive()函數,或者提供一個槽並利用connect()函數將receive()訊號串連起來
·利用QCOP可以方便的結合qt本身的訊號和槽的機制,使用非常方便
·但對於非QT程式與Qt程式的通訊,則只能使用其他IPC方式
QCOP樣本:
在一個進程中發送訊息和資料:

QbyteArray data;
QdataStream out(&data,QIODevice::WriteOnly);
out<<celNum;
QcopChannel::send(“/System/Temperature”,”ConvertCelTOFah(int)”,data);

在另一個進程中接收訊息和資料:

QcopChannel *channel=new QcopChannel(“/System/Temperature”,this);

connect(channel,SIGNAL(received(const Qstring &, constQbyteArray&)), this,SLOT(handleMsg(const Qstring&,const QbyteArray&)));

下面是一個樣本:

//CopServ.h
作為服務端運行 –qws
#ifndef CONVERSION_SCREEN_H
#define CONVERSION_SCREEN_H

#include <QWidget>

class CopServ : public QWidget
{

Q_OBJECT

public:

CopServ();

~CopServ() {};

private slots:

void launchFah();

void launchCel();

private:

void createScreen();

void launchApp(const char* path);
};

#endif //CONVERSION_SCREEN_H

//CopServ.cpp程式主體
#include <QPushButton>
#include <QSlider>
#include <QLabel>
#include <QDial>
#include <QLCDNumber>
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QGridLayout>
#include <QSettings>
#include <QApplication>
#include <QCoreApplication>
#include <unistd.h>
#include <sys/types.h>

#include "CopServ.h"

CopServ::CopServ() : QWidget()
{

createScreen();
}

void CopServ::createScreen()
{

QPushButton* celBtn = new QPushButton("Cel");

QPushButton* fahBtn = new QPushButton("Fah");

QPushButton* quitBtn = new QPushButton("Quit");

QGridLayout *mainLayout = new QGridLayout;

mainLayout->addWidget(celBtn, 0, 0);

mainLayout->addWidget(fahBtn, 0, 1);

mainLayout->addWidget(quitBtn, 1, 0);

setLayout(mainLayout);

connect(celBtn, SIGNAL(clicked()), this, SLOT(launchCel()));

connect(fahBtn, SIGNAL(clicked()), this, SLOT(launchFah()));

connect(quitBtn, SIGNAL(clicked()), qApp, SLOT(quit()));

setGeometry(0, 50, 240, 320);

setWindowTitle("Server Window");
}

void CopServ::launchApp(const char* path)
//啟動子程式
{

if (path == NULL)

{

qDebug("Launch path is NULL!/n");

}


pid_t pid = fork();
//建立子進程

if (pid == 0)

{

qDebug("new process forked. PID is:%d/n", getpid());

int result = execl(path, path, 0);

if (result < 0)

{

qDebug("failed to launch application!/n");

}

_exit(-1);

}
}

void CopServ::launchCel()
{

launchApp("./cel/cel");
}
void CopServ::launchFah()
{

launchApp("./fah/fah");
}

//main.cpp
#include <QApplication>
#include "CopServ.h"

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

QApplication app(argc, argv, QApplication::GuiServer);

CopServ screen;
//
screen.setGeometry(0, 0, 240, 320);

screen.show();

return app.exec();
}

//Cel.h
//子程式1的標頭檔
#ifndef CEL_H
#define CEL_H

#include <QWidget>

class QSlider;
class QHBoxLayout;

class Cel : public QWidget
{

Q_OBJECT

public:

Cel();

~Cel() {};

private slots:

void handleMsg(const QString &message, const QByteArray &data);

void sendMsg(int celNum);
//槽

private:

void fahToCel(int fahNum);

void createScreen();

void createCel();

void listenChannel();

QSlider* slider;

QHBoxLayout* celLayout;
};

//Cel.cpp
#endif //CEL_H
#include <QPushButton>
#include <QSlider>
#include <QLabel>
#include <QLCDNumber>
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QApplication>
#include <QCopChannel>
#include <QDataStream>
#include <QByteArray>

#include "Cel.h"

Cel::Cel() : QWidget()
{

createScreen();

listenChannel();
}

void Cel::createScreen()
{

QPushButton* quitBtn = new QPushButton("Quit");

createCel();

QVBoxLayout *mainLayout = new QVBoxLayout;

mainLayout->addWidget(quitBtn);

mainLayout->addLayout(celLayout);

setLayout(mainLayout);

slider->setFocus();

connect(quitBtn, SIGNAL(clicked()), qApp, SLOT(quit()));

setWindowTitle("Celsius");
}

void Cel::createCel()
{

slider = new QSlider(Qt::Vertical);

slider->setRange(0, 100);

slider->setValue(0);

slider->setTickPosition(QSlider::TicksLeft);

QLabel* celLabel = new QLabel("0");

celLayout = new QHBoxLayout;

celLayout->addWidget(celLabel, 0, Qt::AlignRight);

celLayout->addWidget(slider, 0, Qt::AlignLeft);

celLayout->setSpacing(10);

connect(slider, SIGNAL(valueChanged(int)), celLabel, SLOT(setNum(int)));

connect(slider, SIGNAL(valueChanged(int)), this, SLOT(sendMsg(int)));
}

void Cel::fahToCel(int fahNum)
{

int celNum = (fahNum - 32) * 5 / 9;

slider->setValue(celNum);
}

void Cel::listenChannel()
{

QCopChannel *channel = new QCopChannel("/System/Temperature", this);//註冊Channel

connect(channel, SIGNAL(received(const QString &, const QByteArray &)),

this, SLOT(handleMsg(const QString &, const QByteArray &)));
}

void Cel::handleMsg(const QString &message, const QByteArray &data)//處理收到資訊
{

QDataStream in(data);

if (message == "ConvertFahToCel(int)")

{

int fahNum;

in >> fahNum;

fahToCel(fahNum);

}
}

void Cel::sendMsg(int celNum)
//發送資訊
{

QByteArray data;

QDataStream out(&data, QIODevice::WriteOnly);

out << celNum;

QCopChannel::send("/System/Temperature", "ConvertCelToFah(int)", data);
}
#include <QApplication>

#include "Cel.h"

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

QApplication app(argc, argv/*, QApplication::GuiClient*/);

Cel screen;

screen.setGeometry(0, 25, 100, 250);

screen.show();

return app.exec();
}

 

//Fah.h 子程式2的標頭檔
#ifndef FAH_H
#define FAH_H

#include <QWidget>

class QDial;
class QVBoxLayout;

class Fah : public QWidget
{

Q_OBJECT

public:

Fah();

~Fah() {};

private slots:

void handleMsg(const QString &message, const QByteArray &data);

void sendMsg(int fahNum);
//自訂槽

private:

void celToFah(int celNum);

void createScreen();

void createFah();

void listenChannel();

QDial* dial;

QVBoxLayout* fahLayout;
};

#endif //FAH_H
#include <QPushButton>
#include <QDial>
#include <QLCDNumber>
#include <QVBoxLayout>
#include <QApplication>
#include <QCopChannel>
#include <QDataStream>
#include <QByteArray>

#include "Fah.h"

Fah::Fah() : QWidget()
{

createScreen();

listenChannel();
}

void Fah::createScreen()
{

QPushButton* quitBtn = new QPushButton("Quit");

createFah();

QVBoxLayout *mainLayout = new QVBoxLayout;

mainLayout->addWidget(quitBtn);

mainLayout->addLayout(fahLayout);

setLayout(mainLayout);

dial->setFocus();

connect(quitBtn, SIGNAL(clicked()), qApp, SLOT(quit()));

setWindowTitle("Fahrenheit");
}

void Fah::createFah()
{

QLCDNumber* lcdNum = new QLCDNumber(3);

lcdNum->setSegmentStyle(QLCDNumber::Filled);

lcdNum->display(32);

dial = new QDial;

dial->setRange(32, 212);

dial->setValue(32);

dial->setNotchesVisible(true);

fahLayout = new QVBoxLayout;

fahLayout->addWidget(lcdNum, 0, Qt::AlignBottom | Qt::AlignHCenter);

fahLayout->addWidget(dial);

fahLayout->setSpacing(10);

connect(dial, SIGNAL(valueChanged(int)), lcdNum, SLOT(display(int)));

connect(dial, SIGNAL(valueChanged(int)), this, SLOT(sendMsg(int)));
}

void Fah::celToFah(int celNum)
{

int fahNum = (celNum * 9 / 5) + 32;

dial->setValue(fahNum);
}

void Fah::listenChannel()
{

QCopChannel *channel = new QCopChannel("/System/Temperature", this);

connect(channel, SIGNAL(received(const QString &, const QByteArray &)),

this, SLOT(handleMsg(const QString &, const QByteArray &)));
}

void Fah::handleMsg(const QString &message, const QByteArray &data)
{

QDataStream in(data);

if (message == "ConvertCelToFah(int)")

{

int celNum;

in >> celNum;

celToFah(celNum);

}
}

void Fah::sendMsg(int fahNum)
{

QByteArray data;

QDataStream out(&data, QIODevice::WriteOnly);

out << fahNum;

QCopChannel::send("/System/Temperature", "ConvertFahToCel(int)", data);
}

#include <QApplication>

#include "Fah.h"

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

QApplication app(argc, argv);

Fah screen;

screen.setGeometry(130, 25, 100, 250);

screen.show();

return app.exec();
}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.