SFML to Qt...
-
Hi..
I'm using SFML to make simple games (like Atari games), SFML is not a Game Engine, it has many libraries to handle graphics, audio, network, etc... well I guess you know about this...
Can I do the same with Qt ?... I have used Qt only to develop desktop programs... I'm not looking for a Game Engine itself... just want to handle things as did in SFML...
Greetings..
-
Check out Felgo: https://felgo.com/games
-
Qt has classes that simplify of using OpenGL. It has classes like QVector, QMatrix4x4 and QQuaternion for working with linear algebra. It has classes for working with textures, sounds, databases, network (for example the QWebSocket class) and so on. It is not very complicated to make a sprite animation or skeletal animation in OpenGL and Qt. You can import 3D models from Blender using dae (COLLADA) format because Qt has a built-in parser of XML. Qt can build your games to Android and iOS more easy than SFML. I tried to build to Android and it is really easy. Just love Qt and do simple games and demos for practice everyday. If you need some examples with Qt and OpenGL you can start here: https://forum.qt.io/topic/124737/where-can-i-find-a-good-qt-opengl-tutorial/3
I wrote a simple example that creates an empty OpenGL window and plays music: https://rextester.com/RJLN8376
// Add this line to .pro: // QT += multimedia // win32: LIBS += -lopengl32 #ifdef _WIN32 #include <windows.h> extern "C" __declspec(dllexport) DWORD NvOptimusEnablement = 0x00000001; extern "C" __declspec(dllexport) DWORD AmdPowerXpressRequestHighPerformance = 0x00000001; #endif #include <QtWidgets/QApplication> #include <QtWidgets/QOpenGLWidget> #include <QtMultimedia/QMediaPlayer> #include <QtCore/QUrl> class Window : public QOpenGLWidget { public: Window() { setWindowTitle("Music"); resize(500, 500); } private: QMediaPlayer _mediaPlayer; void initializeGL() override { glClearColor(0.5f, 0.5f, 0.5f, 1.0f); _mediaPlayer.setMedia(QUrl("qrc:/assets/audio/music.wav")); _mediaPlayer.play(); } void paintGL() override { glClear(GL_COLOR_BUFFER_BIT); } void resizeGL(int w, int h) override { glViewport(0, 0, w, h); } }; int main(int argc, char *argv[]) { QApplication a(argc, argv); Window w; w.show(); return a.exec(); }
-
You can use QPainter for graphics but it is 2D graphics only and it has not such power that OpenGL/GLSL has.
This is my example how to create a sprite animation using QPainter and QTimer: Example of sprite animation on QPainter written in Qt5 C++, PyQt5, PySide2, JavaScript and TypeScript
-
@8Observer8 said in SFML to Qt...:
I wrote a simple example that creates an empty OpenGL window and plays music: https://rextester.com/RJLN8376
I translated this example to PyQt5 and PySide2:
PyQt5: https://rextester.com/PQYYR60228
import sys from OpenGL import GL as gl from PyQt5.QtWidgets import QApplication, QOpenGLWidget from PyQt5.QtMultimedia import QMediaPlayer, QMediaContent from PyQt5.QtCore import Qt, QUrl class Window(QOpenGLWidget): def __init__(self): super().__init__() self.setWindowTitle("Media Player") self.resize(500, 500) def initializeGL(self): gl.glClearColor(0.5, 0.5, 0.5, 1.0) self.media_player = QMediaPlayer() self.media_player.setMedia(QMediaContent(QUrl("assets/audio/music.wav"))) self.media_player.play() def paintGL(self): gl.glClear(gl.GL_COLOR_BUFFER_BIT) def resizeGL(self, w, h): gl.glViewport(0, 0, w, h) QApplication.setAttribute(Qt.AA_UseDesktopOpenGL) app = QApplication(sys.argv) window = Window() window.show() sys.exit(app.exec_())
PySide2: https://rextester.com/HYZM49802
import sys from OpenGL import GL as gl from PySide2.QtWidgets import QApplication, QOpenGLWidget from PySide2.QtMultimedia import QMediaPlayer, QMediaContent from PySide2.QtCore import Qt, QUrl class Window(QOpenGLWidget): def __init__(self): super().__init__() self.setWindowTitle("Media Player") self.resize(500, 500) def initializeGL(self): gl.glClearColor(0.5, 0.5, 0.5, 1.0) self.media_player = QMediaPlayer() self.media_player.setMedia(QMediaContent(QUrl("assets/audio/music.wav"))) self.media_player.play() def paintGL(self): gl.glClear(gl.GL_COLOR_BUFFER_BIT) def resizeGL(self, w, h): gl.glViewport(0, 0, w, h) QApplication.setAttribute(Qt.AA_UseDesktopOpenGL) app = QApplication(sys.argv) window = Window() window.show() sys.exit(app.exec_())
-
You can build Qt from source: Qt 5.15.2 Source (962 MB) It will allow you to build your games to one executable file. For example, I build the example about to Release for Windows: MediaPlayer.zip It requires only 8 MB. To compress your EXE to such size you can use UPX and this command:
upx.exe --best --force MediaPlayer_Qt5Cpp.exe -o MediaPlayer.exe
Unzip this zip file: Qt 5.15.2 Source (962 MB), open the command line terminal in this folder and copy this command:
configure -prefix "C:\Qt5.15.2_Static" -static -static-runtime -release -opensource -confirm-license -qt-zlib -qt-pcre -qt-libpng -qt-libjpeg -qt-freetype -opengl desktop -sql-odbc -sql-sqlite -nomake tools -nomake examples -nomake tests -no-angle -skip qt3d -skip qtcanvas3d -skip qtcanvas3d -skip qtdatavis3d -skip qtlocation -skip qtwayland -skip qtwebchannel -skip qtwebengine -skip declarative -skip quickcontrols
It requires a few minutes to configure. Run this command:
mingw32-make
It requires 4 hours on my laptop. Run this command:mingw32-make install
. It requires 20 minutes. Create a new Kit in Qt Creator settings and browseC:\Qt5.15.2_Static\bin\qmake.exe
I can show how to setup Box2D and Bullet physics engines in Qt Creator for using them with OpenGL.
-
@8Observer8 said in SFML to Qt...:
I can show how to setup Box2D and Bullet physics engines in Qt Creator for using them with OpenGL.
To setup Box2D and Bullet physics engines you need to add (to .pro file) paths to include, libs folders and write what libraries you need to include:
For Box2D:
INCLUDEPATH += "E:\Libs\box2d-2.4.0-mingw-32bit\include" LIBS += -L"E:\Libs\box2d-2.4.0-mingw-32bit\lib" LIBS += -lbox2d
For Bullet:
INCLUDEPATH += "E:\Libs\bullet3-2.89-mingw-32bit\include" LIBS += -L"E:\Libs\bullet3-2.89-mingw-32bit\lib" LIBS += -lBulletDynamics -lBulletCollision -lLinearMath
You need to build Box2D and Bullet from source by yourself using CMake GUI (or cmake from terminal). Just select "src" and "dist" folder in CMake GUI and click on "Configure" and "Generate" buttons. Run
mingw32-make
in terminal. I will get "libs" for these libraries. -
You can use SFML inside of Qt. It allows to use everything from Qt. For example, signal/slots like in Godot Engine. Just copy
QSfmlWidget.h
andQSfmlWidget.cpp
in your project and inherit your Widget from theQSfmlWidget
class. Override to methods in your widget:onInit()
andonUpdate()
.If you want to use QtWebSockets with SFML see my example: Qt SFML. Example of connection with local and remote JavaScript server with WebSockets
The next example shows how draw a rectangle with SFML from Qt widget:
Include SFML to your Qt Widgets Application in .pro file:
QT += core gui INCLUDEPATH += "E:\Libs\SFML-2.5.1-mingw-32bit\include" LIBS += -L"E:\Libs\SFML-2.5.1-mingw-32bit\lib" LIBS += -lsfml-system -lsfml-graphics -lsfml-window
main.cpp
#include <QtWidgets/QApplication> #include "Widget.h" int main(int argc, char *argv[]) { QApplication a(argc, argv); Widget w; w.show(); return a.exec(); }
Widget.h
#ifndef WIDGET_H #define WIDGET_H #include "QSfmlWidget.h" class Widget : public QSfmlWidget { Q_OBJECT public: Widget(QWidget *parent = nullptr); void onInit() override; void onUpdate() override; private: sf::RectangleShape m_rect; }; #endif // WIDGET_H
Widget.cpp
#include "Widget.h" Widget::Widget(QWidget *parent) : QSfmlWidget(parent) { setWindowTitle("SFML, Qt5, C++"); setFixedSize(QSize(400, 400)); } void Widget::onInit() { m_rect.setPosition(100, 200); m_rect.setSize(sf::Vector2f(100, 50)); m_rect.setFillColor(sf::Color::Red); } void Widget::onUpdate() { sf::RenderWindow::draw(m_rect); }
QSfmlWidget.h
#ifndef QSFMLWIDGET_H #define QSFMLWIDGET_H #include <QtCore/QObject> #include <QtCore/QTimer> #include <QtWidgets/QWidget> #include "SFML/Graphics.hpp" class QSfmlWidget : public QWidget, public sf::RenderWindow { Q_OBJECT public: explicit QSfmlWidget(QWidget *parent = nullptr); virtual QPaintEngine * paintEngine() const override; virtual void showEvent(QShowEvent *event) override; virtual void paintEvent(QPaintEvent *event) override; virtual void onInit(); virtual void onUpdate(); private: QTimer m_timer; bool m_initialized; }; #endif // QSFMLWIDGET_H
QSfmlWidget.cpp
#include "QSfmlWidget.h" QSfmlWidget::QSfmlWidget(QWidget *parent) : QWidget(parent) , m_initialized(false) { setAttribute(Qt::WA_PaintOnScreen); setAttribute(Qt::WA_OpaquePaintEvent); setAttribute(Qt::WA_NoSystemBackground); setFocusPolicy(Qt::StrongFocus); } QPaintEngine *QSfmlWidget::paintEngine() const { return nullptr; } void QSfmlWidget::showEvent(QShowEvent *event) { Q_UNUSED(event); if (!m_initialized) { sf::RenderWindow::create(reinterpret_cast<sf::WindowHandle>(winId())); onInit(); connect(&m_timer, SIGNAL(timeout()), this, SLOT(repaint())); m_timer.start(); m_initialized = true; } } void QSfmlWidget::paintEvent(QPaintEvent *event) { Q_UNUSED(event); RenderWindow::clear(sf::Color::White); onUpdate(); RenderWindow::display(); } void QSfmlWidget::onInit() { // To be overriden } void QSfmlWidget::onUpdate() { // To be overriden }
-
I did many games in Qt/C++ which can be alse created in SFML. If you want to see: https://forum.qt.io/topic/137223/simple-qt-c-games