C++ 通过C+中的信号/插槽接收LCM消息+;用Qt?

C++ 通过C+中的信号/插槽接收LCM消息+;用Qt?,c++,qt,lcm-data-marshalling,C++,Qt,Lcm Data Marshalling,在我的应用程序中,我接收来自LCM(轻量级通信和编组)的消息,这些消息包含应用程序中多个使用者的数据。我设想将LCM处理程序作为一个单例使用,这样每个类都可以使用一个实例。例如,每个消费者类别将具有: QObject::connect(LCMHandler::getInstance(), SIGNAL(messageReceived()), this, SLOT(processMessage())); 其中lcmhandler.h为: class LCMHan

在我的应用程序中,我接收来自LCM(轻量级通信和编组)的消息,这些消息包含应用程序中多个使用者的数据。我设想将LCM处理程序作为一个单例使用,这样每个类都可以使用一个实例。例如,每个消费者类别将具有:

QObject::connect(LCMHandler::getInstance(), SIGNAL(messageReceived()),
                 this, SLOT(processMessage()));
其中
lcmhandler.h
为:

class LCMHandler : public QObject
{
    Q_OBJECT
public:
    static LCMHandler* getInstance();
    LCMHandler();
    ~LCMHandler() {}

    void handleMessage(const lcm::ReceiveBuffer* rbuf,
                       const std::string &chan,
                       const example::example_t *msg);

signals:
    void messageReceived();

private:
    static LCMReceiver* _instance;
};
LCMHandler* LCMHandler::_instance = 0;

LCMHandler::LCMHandler()
{
    lcm::LCM lcm;
    if(lcm.good())
    {
        lcm.subscribe("MyChannel", &LCMHandler::handleMessage, this);
        while(0 == lcm.handle());
    } else {
        std::cerr << "LCM Error" << std::endl;
    }
}

LCMHandler* LCMHandler::getInstance() {
    if (!_instance) {
        _instance = new LCMHandler();
    }
    return _instance;
}

void LCMHandler::handleMessage(const lcm::ReceiveBuffer *rbuf,
                               const std::string &chan,
                               const hlelcm::transponder_t *msg)
{

    std::cout << "Received message on channel " <<  chan.c_str() << std::endl;
    emit messageReceived();
}
void Consumer::processMessage() {
    std::cout << "Message received" << std::endl;
}
lcmhandler.cpp
是:

class LCMHandler : public QObject
{
    Q_OBJECT
public:
    static LCMHandler* getInstance();
    LCMHandler();
    ~LCMHandler() {}

    void handleMessage(const lcm::ReceiveBuffer* rbuf,
                       const std::string &chan,
                       const example::example_t *msg);

signals:
    void messageReceived();

private:
    static LCMReceiver* _instance;
};
LCMHandler* LCMHandler::_instance = 0;

LCMHandler::LCMHandler()
{
    lcm::LCM lcm;
    if(lcm.good())
    {
        lcm.subscribe("MyChannel", &LCMHandler::handleMessage, this);
        while(0 == lcm.handle());
    } else {
        std::cerr << "LCM Error" << std::endl;
    }
}

LCMHandler* LCMHandler::getInstance() {
    if (!_instance) {
        _instance = new LCMHandler();
    }
    return _instance;
}

void LCMHandler::handleMessage(const lcm::ReceiveBuffer *rbuf,
                               const std::string &chan,
                               const hlelcm::transponder_t *msg)
{

    std::cout << "Received message on channel " <<  chan.c_str() << std::endl;
    emit messageReceived();
}
void Consumer::processMessage() {
    std::cout << "Message received" << std::endl;
}
它从不执行,
handleMessage(…)
无限循环。类似地,QtUI从不加载,因为handleMessage正忙于循环


处理传入消息的最佳方式是什么?我应该避免对
LCMHandler
使用单例吗?要使此实现工作,我需要更改什么?

将LCM构造函数的内容移动到另一个函数:

LCMHandler::beginCommunication()
{
    lcm::LCM lcm;
    if(lcm.good())
    {
        //QObject base class call.
        moveToThread( &_myLocalQThread );

        _myLocalThread.start();

        lcm.subscribe("MyChannel", &LCMHandler::handleMessage, this);

        _isActive = true;

        // This is blocking, we don't want it to interfere with
        // the QApplication loop
        while(0 == lcm.handle());
    } 
    else 
    {
        std::cerr << "LCM Error" << std::endl;
    }

    _isActive = false;
}

将LCM构造函数的内容移动到另一个函数:

LCMHandler::beginCommunication()
{
    lcm::LCM lcm;
    if(lcm.good())
    {
        //QObject base class call.
        moveToThread( &_myLocalQThread );

        _myLocalThread.start();

        lcm.subscribe("MyChannel", &LCMHandler::handleMessage, this);

        _isActive = true;

        // This is blocking, we don't want it to interfere with
        // the QApplication loop
        while(0 == lcm.handle());
    } 
    else 
    {
        std::cerr << "LCM Error" << std::endl;
    }

    _isActive = false;
}

看起来,如果在它的构造函数中阻塞,那么单例可能需要在它自己的线程中生存?而(0==lcm.handle());看起来,如果在它的构造函数中阻塞,那么单例可能需要在它自己的线程中生存?而(0==lcm.handle());