Qt Everywhere: WebAssembly et WebGL Streaming

Qt Everywhere - c'est le nom des archives avec les sources Qt. WebAssembly et WebGL en streaming seront livrés en 5.12.0 et partout, les sons sont différents. J'ai donc demandé de prototyper quelque chose. Un prototype de chat sur les sockets Web a été rapidement déployé pour tester la prise en charge du réseau. Sous le chat, il y aura des instructions pour assembler et lancer un projet sur WebAssembly, un exemple d'appel de JavaScript à partir de C ++.


Assemblage Qt avec WebAssembly


Vous devez d'abord mettre la chaîne d'outils emscripten , que nous collecterons Qt. N'oubliez pas de définir des variables d'environnement pour que qmake trouve emcc. Le script de configure a été exécuté avec les paramètres suivants:


 ./configure \ -prefix /home/dmitry/Qt/5.12.0/wasm \ -xplatform wasm-emscripten \ -confirm-license -opensource \ -nomake tests \ -c++std c++1z \ -nomake examples \ -release \ -no-dbus \ -skip qtxmlpatterns \ -skip qttools 

Plus loin qu'ailleurs:


 $ make $ make install 

Montage et lancement du projet


 $ ~/Qt/5.12.0/wasm/bin/qmake $ make $ emrun chat.html 

Code dépendant de la plateforme


Coudre l'url sur laquelle le backend est suspendu n'est pas très bon, car veulent fonctionner sur un port arbitraire. En cas de travail à partir du navigateur, vous devez prendre location.hostname et location.port pour déterminer où le backend s'exécute. Pour ce faire, vous devrez écrire un peu en JavaScript.


Pour les amateurs de définitions, il y a Q_OS_WASM , mais je préfère retirer le code en pimpl et fichiers individuels. Pimpl est superflu ici, mais je vais diffuser le code dans différents fichiers


Obtenons une sorte de config


 //config.h #pragma once #include <QtCore/QUrl> class Config { public: static QUrl wsUrl(); }; 

et deux implémentations


 //config.cpp #include <QtCore/QCoreApplication> #include <QtCore/QCommandLineParser> #include "config.h" QUrl Config::wsUrl() { QCommandLineParser parser; QCommandLineOption wsOption(QStringList() << "u" << "url" , "WebSocket url" , "url" , "ws://localhost:1234"); parser.addOption(wsOption); parser.process(*QCoreApplication::instance()); return QUrl(parser.value(wsOption)); } 

 //config_wasm.cpp #include <QtCore/QByteArray> #include <emscripten/emscripten.h> #include <emscripten/html5.h> #include "config.h" QUrl Config::wsUrl() { QByteArray buff(1024, 0); EM_ASM_({ var url = "ws://"+ window.location.hostname + ":" + window.location.port + "/ws"; stringToUTF8(url, $0, $1); }, buff.data(), buff.size()); return QUrl(QString::fromUtf8(buff)); } 

Reste à s'inscrire dans le fichier pro


 wasm { SOURCES += config_wasm.cpp } else { SOURCES += config.cpp } 

EM_ASM_ est EM_ASM_ magie EM_ASM_ qui vous permet d'appeler du code JavaScript à partir de C ++. Bien que cela puisse se faire sans JavaScript


 emscripten::val location = emscripten::val::global("location"); auto host = QString::fromStdString(location["host"].as<string>()); auto protocol = QString::fromStdString(location["protocol"].as<string>()); 

Prise en charge du navigateur


Navigateurs de bureau: il démarre et fonctionne sous Chrome, Firefox, Safari, Edge (ici j'ai dû activer des fonctions expérimentales JavaScript). Selon le matériel, il peut y avoir des retards importants dans la compilation de WebAssembly.


Dans Chrome sur Andorid, la compilation de WebAssembly peut prendre quelques minutes. J'ai immédiatement remarqué le manque de prise en charge des navigateurs mobiles, à savoir qu'il n'y a pas d'appel au clavier système lorsque j'essaie de saisir du texte.


Safari sur iOS 12 ici l'application se bloque au stade de la compilation WebAssembly et je n'ai pas debazhit. Théoriquement, vous pouvez passer à asm.js, mais cela nécessite une étude distincte.


Qt Quick WebGL


Le blog s'est positionné comme VNC sur les sockets web avec rendu sur WebGL. Des dépendances Qt WebSockets et Qt compilées avec le support pour OpenGL ES 2 i.e. Conduire sur du matériel sans GPU sera pénible. Pour le prendre en charge, il suffit de mettre Qt WebGL Streaming Plugin dans le programme d'installation en ligne et d'exécuter l'application avec l' -platform webgl ou -platform webgl:port=80 , si vous devez spécifier le port.


Mais cette technologie a ses limites:


  • retards ou décalage d'entrée notoire;
  • manque de support d'application sur Qt Widgets;
  • absence de transmission sonore;
  • une connexion utilisateur par processus, c'est-à-dire dans le deuxième onglet n'entre plus, le préchargeur tourne.

J'ai également remarqué que le fps s'affaissait lors de l'animation de StackView lors des transitions entre les écrans. Avantage du streaming WebGL:


  • serveur intégré;
  • effort minimum. Je n'ai pas eu à compiler Qt à partir des sources et à reconstruire séparément l'application existante.

Utilisations pour WebAssembly et WebGL Streaming


Wt alternative lorsqu'il existe une application prête à l'emploi en C ++ et que vous devez y attacher l'interface Web. Par exemple, l'interface Web de la chaise berçante torrent.


Interface Web pour une maison intelligente. Ce n'est pas pour rien que MQTT a été livré à Qt, mais un exemple mqtt_simpleclient sur msorvig / qt-webassembly-examples . Vous pouvez avoir un code d'interface utilisateur commun qui fonctionne sur la tablette et dans le navigateur.


Le code est disponible sur GitHub , des binaires préparés au même endroit.

Source: https://habr.com/ru/post/fr430954/


All Articles