Benutzerdefinierte Datenkanäle mit Holographic Remoting und der OpenXR-API

Verwenden Sie benutzerdefinierte Datenkanäle, um benutzerdefinierte Daten über eine eingerichtete Remotingverbindung zu senden.

Wichtig

Benutzerdefinierte Datenkanäle erfordern eine benutzerdefinierte Remote-App und eine benutzerdefinierte Player-App. Dies ermöglicht die Kommunikation zwischen den beiden benutzerdefinierten Apps.

Tipp

Ein einfaches Ping-Pong-Beispiel finden Sie in den Remote- und Playerbeispielen im GitHub-Repository für Holographic Remoting-Beispiele. Entfernen Sie die Auskommentierung #define ENABLE_CUSTOM_DATA_CHANNEL_SAMPLE in den Dateien OpenXrProgramm.cpp und SamplePlayerMain.h, um den Beispielcode zu aktivieren.

Erstellen eines benutzerdefinierten Datenkanals

Ein benutzerdefinierter Datenkanal wird durch das Handle XrRemotingDataChannelMSFT definiert:

XrRemotingDataChannelMSFT m_userDataChannel;

Nachdem eine Verbindung erfolgreich hergestellt wurde, können neue Datenkanäle über die -Funktion erstellt xrCreateRemotingDataChannelMSFT werden:

XrRemotingDataChannelCreateInfoMSFT channelInfo{static_cast<XrStructureType>(XR_TYPE_REMOTING_DATA_CHANNEL_CREATE_INFO_MSFT)};
channelInfo.channelId = 0;
channelInfo.channelPriority = XR_REMOTING_DATA_CHANNEL_PRIORITY_LOW_MSFT;
CHECK_XRCMD(m_extensions.xrCreateRemotingDataChannelMSFT(m_instance.Get(), m_systemId, &channelInfo, &m_userDataChannel));

Benutzerdefinierte Datenkanäle können über den Player und die Remoteanwendung erstellt werden, auch wenn sich die Laufzeiten unterscheiden. Wenn ein Datenkanal von der Playerseite erstellt wird, wird die Remoteseite mit der Ereignisstruktur XrEventDataRemotingDataChannelCreatedMSFT benachrichtigt:

XrEventDataBuffer eventData{};
while (pollEvent(eventData)) 
{
    switch (eventData.type) 
    {
        case XR_TYPE_EVENT_DATA_REMOTING_DATA_CHANNEL_CREATED_MSFT: 
        {
            auto channelCreatedEventData = reinterpret_cast<const XrEventDataRemotingDataChannelCreatedMSFT*>(&eventData);
            m_userDataChannel = channelCreatedEventData->channel;
            break;
        }
    }
}

Der Anfangszustand XrRemotingDataChannelStatusMSFT nach dem Aufruf von xrCreateRemotingDataChannelMSFT ist XR_REMOTING_DATA_CHANNEL_STATUS_OPEN_PENDING_MSFT. Nachdem der Datenkanal vollständig eingerichtet wurde, wechselt der Zustand des Kanals zu XR_REMOTING_DATA_CHANNEL_STATUS_OPENED_MSFT. Die XrEventDataRemotingDataChannelOpenedMSFT Ereignisstruktur wird in der Ereigniswarteschlange platziert, wenn der Zustand eines zuvor erstellten Datenkanals von zu XR_REMOTING_DATA_CHANNEL_STATUS_OPEN_PENDING_MSFT wechselt XR_REMOTING_DATA_CHANNEL_STATUS_OPENED_MSFT.

Kanalstatus

Die xrGetRemotingDataChannelStateMSFT -Funktion kann zum Abfragen des Datenkanalzustands verwendet werden:

XrRemotingDataChannelStateMSFT channelState{static_cast<XrStructureType>(XR_TYPE_REMOTING_DATA_CHANNEL_STATE_MSFT)};
CHECK_XRCMD(m_extensions.xrGetRemotingDataChannelStateMSFT(m_userDataChannel, &channelState));

Senden von Daten

Wenn der Kanal geöffnet ist, wird xrSendRemotingDataMSFT die Funktion verwendet, um Daten an die Playerseite zu senden:

if (channelState.connectionStatus == XR_REMOTING_DATA_CHANNEL_STATUS_OPENED_MSFT) {
    // Only send the packet if the send queue is smaller than 1MiB
    if (channelState.sendQueueSize >= 1 * 1024 * 1024) {
        return;
    }
    uint8_t data[] = {1};

    XrRemotingDataChannelSendDataInfoMSFT sendInfo{
        static_cast<XrStructureType>(XR_TYPE_REMOTING_DATA_CHANNEL_SEND_DATA_INFO_MSFT)};
    sendInfo.data = data;
    sendInfo.size = sizeof(data);
    sendInfo.guaranteedDelivery = true;
    CHECK_XRCMD(m_extensions.xrSendRemotingDataMSFT(m_userDataChannel, &sendInfo));
}

Hinweis

Die Daten, die Sie über einen benutzerdefinierten Datenkanal senden, nutzen die Bandbreite mit anderen Datenkanälen, die Holographic Remoting verwendet.

Abrufen von Daten

Jedes Mal, wenn Daten über einen Datenkanal eintreffen, wird eine XrEventDataRemotingDataChannelDataReceivedMSFT Ereignisstruktur in die Ereigniswarteschlange platziert. Empfangene Pakete können mit der -Funktion abgerufen xrRetrieveRemotingDataMSFT werden:

XrEventDataBuffer eventData{};
while (pollEvent(eventData)) 
{
    switch (eventData.type) 
    {
        case XR_TYPE_EVENT_DATA_REMOTING_DATA_CHANNEL_DATA_RECEIVED_MSFT: 
        {
            auto dataReceivedEventData = reinterpret_cast<const XrEventDataRemotingDataChannelDataReceivedMSFT*>(&eventData);
            std::vector<uint8_t> packet(dataReceivedEventData->size);
            uint32_t dataBytesCount;
            CHECK_XRCMD(m_extensions.xrRetrieveRemotingDataMSFT(dataReceivedEventData->channel,
                                                                dataReceivedEventData->packetId,
                                                                static_cast<uint32_t>(packet.size()),
                                                                &dataBytesCount,
                                                                packet.data()));
            break;
        }
    }
}

Zerstören eines Datenkanals

Sie können einen Datenkanal mit zerstören xrDestroyRemotingDataChannelMSFT:

CHECK_XRCMD(m_extensions.xrDestroyRemotingDataChannelMSFT(m_userDataChannel));

Das XrRemotingDataChannelMSFT Handle ist nach dem Aufruf ungültig xrDestroyRemotingDataChannelMSFT , und das Datenkanalhand handle darf danach nicht mehr verwendet werden.

wird XrEventDataRemotingDataChannelClosedMSFT in der Ereigniswarteschlange platziert, falls die Playerseite den Datenkanal schließt oder zerstört. Der Datenkanalzustand wechselt zu XR_REMOTING_DATA_CHANNEL_STATUS_CLOSED_MSFT. Für einen geschlossenen Datenkanal bleibt das XrRemotingDataChannelMSFT Handle gültig.

Weitere Informationen