将二进制数据从QML传递到C

Pass binary data from QML to C++

本文关键字:QML 二进制 数据      更新时间:2023-10-16

我在qml内部的javascript中有一个'binary String',代表我想传递给C 的原始字节(要在已建立的插座上发送)。

我正在使用这样的代码:

// QML
onSomeSignal: {
  var proto = new MyMessage();  // https://github.com/dcodeIO/protobuf.js
  var bbuf  = proto.encode();   // https://github.com/dcodeIO/bytebuffer.js
  var bytes = bbuf.toBinary();
  messageBridge.send(bytes);
}
// C++
void MessageBridge::send(const QString& data) {
    if(m_tcpSocket->state() == QAbstractSocket::ConnectedState) {
        m_tcpSocket->write(encodeVarint32(data.length()).toLocal8Bit());
        m_tcpSocket->write(data.toLocal8Bit());
    }
}

但是,我发现将JavaScript字符串转换为QString有时会更改字节(大概是由于编码)。

以下代码有效,但效率低下,将字节缓冲区转换为二进制字符串,然后将JS数组转换为QvariantList,然后将零件填充QByTearray。

// QML
onSomeSignal: {
  var bytes = (new MyMessage()).encode().toBinary();
  var bytea = [];
  for (var i=bytes.length;i--;) bytea[i] = bytes.charCodeAt(i);
  messageBridge.send(bytes);
}
// C++
void MessageBridge::send(const QVariantList& data) {
    if(m_tcpSocket->state() == QAbstractSocket::ConnectedState) {
        m_tcpSocket->write(encodeVarint32(data.length()).toLocal8Bit());
        m_tcpSocket->write(data.toLocal8Bit());
        QByteArray bytes(data.length(),'');
        for (int i=0; i<data.length(); i++) bytes[i] = data[i].toInt();
        m_tcpSocket->write(bytes);
    }
}

ByteBuffer或二进制字符串从QML/JavaScript传递到QT/C 的有效方法是什么,它可以给我一些我可以写入QTcpSocket的东西?

qt 5.7不了解从C 到QML的QByTearray,因此它将其包装到不透明的QVariant中,使其在QML中毫无用处,除了以后的时间将其传递回C 。

QT 5.8 增加了对QbyTearray类型的支持。当从C 传递到QML时,作为返回变量或信号参数,QByTearray将转换为阵列延迟。这对于Protobufs很有用,因为Protobuf的JavaScript API可以直接解码ArrayBuffer类型。

// QML
onSomeSignal: {
    var bytes = new MyMessage();
    messageBridge.send(bytes.toArrayBuffer());
}

和数组缓冲区将非常适合QByTearray:

// C++
void MessageBridge::send(const QByteBuffer& data) {
    if (m_tcpSocket->state() == QAbstractSocket::ConnectedState) {
        m_tcpSocket->write(encodeVarint32(data.size()).toLocal8Bit());
        m_tcpSocket->write(data);
}

现在,请告诉我如何从C 中的QByTeBuffer转到QML信号中的有用Protobuf.js对象:)