Pass mouse movements to engine, warp cursor in frontend qmlfrontend
authorunc0rr
Wed, 10 Jan 2018 23:49:47 +0100
branchqmlfrontend
changeset 12890 9c259fb4d405
parent 12884 66171ce586cc
child 12892 0088bcccd19a
Pass mouse movements to engine, warp cursor in frontend
hedgewars/hwLibrary.pas
hedgewars/uCursor.pas
hedgewars/uWorld.pas
qmlfrontend/flib.h
qmlfrontend/gameview.cpp
qmlfrontend/gameview.h
qmlfrontend/hwengine.cpp
--- a/hedgewars/hwLibrary.pas	Sun Jan 07 09:48:26 2018 +0100
+++ b/hedgewars/hwLibrary.pas	Wed Jan 10 23:49:47 2018 +0100
@@ -39,6 +39,7 @@
     , uFLIPC
     , uPhysFSLayer
     , uFLUICallback
+    , uCursor
     ;
 
 {$INCLUDE "config.inc"}
@@ -64,7 +65,8 @@
     ipcRemoveBarrierFromEngineQueue,
     RunEngine,
     GameTick,
-    ResizeWindow
+    ResizeWindow,
+    updateMousePosition
     ;
 
 begin
--- a/hedgewars/uCursor.pas	Sun Jan 07 09:48:26 2018 +0100
+++ b/hedgewars/uCursor.pas	Wed Jan 10 23:49:47 2018 +0100
@@ -4,16 +4,17 @@
 
 procedure init;
 procedure resetPosition;
-procedure updatePosition;
 procedure handlePositionUpdate(x, y: LongInt);
 
+function updateMousePosition(cx, cy, x, y: LongInt): boolean; cdecl; export;
+
 implementation
 
-uses SDLh, uVariables;
+uses SDLh, uVariables, uTypes;
 
 procedure init;
 begin
-    resetPosition();
+    //resetPosition();
 end;
 
 procedure resetPosition;
@@ -24,22 +25,26 @@
     // This fixes it, but we might have overlooked a related
     // bug somewhere else.
     // No big deal since this function is (so far) only called once.
-    SDL_WarpMouse((cScreenWidth div 2) + 1, cScreenHeight div 2);
-    SDL_WarpMouse(cScreenWidth div 2, cScreenHeight div 2);
+    //SDL_WarpMouse((cScreenWidth div 2) + 1, cScreenHeight div 2);
+    //SDL_WarpMouse(cScreenWidth div 2, cScreenHeight div 2);
 end;
 
-procedure updatePosition;
-var x, y: LongInt;
+function updateMousePosition(cx, cy, x, y: LongInt): boolean; cdecl; export;
 begin
-    SDL_GetMouseState(@x, @y);
+    if (GameState <> gsConfirm)
+            and (GameState <> gsSuspend)
+            and (GameState <> gsExit)
+            and (GameState <> gsLandgen)
+            and (GameState <> gsStart)
+            and cHasFocus
+            and (not (CurrentTeam^.ExtDriven and isCursorVisible and (not bShowAmmoMenu) and autoCameraOn)) 
+            and ((x <> cx) or (y <> cy)) then
+    begin
+        handlePositionUpdate(x - cx, y - cy);
 
-    if(x <> cScreenWidth div 2) or (y <> cScreenHeight div 2) then
-    begin
-        handlePositionUpdate(x - cScreenWidth div 2, y - cScreenHeight div 2);
-
-        if cHasFocus then
-            SDL_WarpMouse(cScreenWidth div 2, cScreenHeight div 2);
-    end
+        updateMousePosition:= true
+    end else
+        updateMousePosition:= false
 end;
 
 procedure handlePositionUpdate(x, y: LongInt);
--- a/hedgewars/uWorld.pas	Sun Jan 07 09:48:26 2018 +0100
+++ b/hedgewars/uWorld.pas	Wed Jan 10 23:49:47 2018 +0100
@@ -1776,10 +1776,6 @@
 var EdgesDist, wdy, shs,z, amNumOffsetX, amNumOffsetY, dstX: LongInt;
     inbtwnTrgtAttks: Boolean;
 begin
-{$IFNDEF MOBILE}
-if (not (CurrentTeam^.ExtDriven and isCursorVisible and (not bShowAmmoMenu) and autoCameraOn)) and cHasFocus and (GameState <> gsConfirm) then
-    uCursor.updatePosition();
-{$ENDIF}
 z:= round(200/zoom);
 inbtwnTrgtAttks := ((GameFlags and gfInfAttack) <> 0) and (CurrentHedgehog <> nil) and ((CurrentHedgehog^.Gear = nil) or (CurrentHedgehog^.Gear <> FollowGear)) and ((Ammoz[CurrentHedgehog^.CurAmmoType].Ammo.Propz and ammoprop_NeedTarget) <> 0);
 if autoCameraOn and (not PlacingHogs) and (FollowGear <> nil) and (not isCursorVisible) and (not bShowAmmoMenu) and (not fastUntilLag) and (not inbtwnTrgtAttks) then
--- a/qmlfrontend/flib.h	Sun Jan 07 09:48:26 2018 +0100
+++ b/qmlfrontend/flib.h	Wed Jan 10 23:49:47 2018 +0100
@@ -30,6 +30,7 @@
 typedef void ipcToEngineRaw_t(const char* msg, uint32_t len);
 typedef void ipcSetEngineBarrier_t();
 typedef void ipcRemoveBarrierFromEngineQueue_t();
+typedef bool updateMousePosition_t(int32_t centerX, int32_t centerY, int32_t x, int32_t y);
 
 typedef void registerUIMessagesCallback_t(void* context, void (*)(void* context, MessageType mt, const char* msg, uint32_t len));
 typedef void flibInit_t(const char* localPrefix, const char* userPrefix);
--- a/qmlfrontend/gameview.cpp	Sun Jan 07 09:48:26 2018 +0100
+++ b/qmlfrontend/gameview.cpp	Wed Jan 10 23:49:47 2018 +0100
@@ -1,5 +1,7 @@
 #include "gameview.h"
 
+#include <QCursor>
+#include <QTimer>
 #include <QtGui/QOpenGLContext>
 #include <QtGui/QOpenGLShaderProgram>
 #include <QtQuick/qquickwindow.h>
@@ -9,6 +11,7 @@
 extern "C" {
 extern GameTick_t* flibGameTick;
 extern ResizeWindow_t* flibResizeWindow;
+extern updateMousePosition_t* flibUpdateMousePosition;
 }
 
 GameView::GameView()
@@ -22,8 +25,14 @@
 void GameView::tick(quint32 delta)
 {
     m_delta = delta;
-    if (window())
-        window()->update();
+
+    if (window()) {
+        QTimer* timer = new QTimer(this);
+        connect(timer, &QTimer::timeout, window(), &QQuickWindow::update);
+        timer->start(100);
+
+        //window()->update();
+    }
 }
 
 void GameView::handleWindowChanged(QQuickWindow* win)
@@ -53,8 +62,16 @@
         connect(window(), &QQuickWindow::beforeRendering, m_renderer, &GameViewRenderer::paint, Qt::DirectConnection);
     }
 
-    if (m_windowChanged)
-        m_renderer->setViewportSize(window()->size() * window()->devicePixelRatio());
+    if (m_windowChanged) {
+        QSize windowSize = window()->size();
+        m_renderer->setViewportSize(windowSize * window()->devicePixelRatio());
+        m_centerX = windowSize.width() / 2;
+        m_centerY = windowSize.height() / 2;
+    }
+
+    QPoint mousePos = mapFromGlobal(QCursor::pos()).toPoint();
+    if (flibUpdateMousePosition(m_centerX, m_centerY, mousePos.x(), mousePos.y()))
+        QCursor::setPos(mapToGlobal(QPointF(m_centerX, m_centerY)).toPoint());
 
     m_renderer->tick(m_delta);
 }
--- a/qmlfrontend/gameview.h	Sun Jan 07 09:48:26 2018 +0100
+++ b/qmlfrontend/gameview.h	Wed Jan 10 23:49:47 2018 +0100
@@ -47,6 +47,8 @@
     quint32 m_delta;
     GameViewRenderer* m_renderer;
     bool m_windowChanged;
+    qint32 m_centerX;
+    qint32 m_centerY;
 };
 
 #endif // GAMEVIEW_H
--- a/qmlfrontend/hwengine.cpp	Sun Jan 07 09:48:26 2018 +0100
+++ b/qmlfrontend/hwengine.cpp	Wed Jan 10 23:49:47 2018 +0100
@@ -13,6 +13,7 @@
 RunEngine_t* flibRunEngine;
 GameTick_t* flibGameTick;
 ResizeWindow_t* flibResizeWindow;
+updateMousePosition_t* flibUpdateMousePosition;
 ipcToEngineRaw_t* flibIpcToEngineRaw;
 ipcSetEngineBarrier_t* flibIpcSetEngineBarrier;
 ipcRemoveBarrierFromEngineQueue_t* flibIpcRemoveBarrierFromEngineQueue;
@@ -42,6 +43,7 @@
     flibRunEngine = (RunEngine_t*)hwlib.resolve("RunEngine");
     flibGameTick = (GameTick_t*)hwlib.resolve("GameTick");
     flibResizeWindow = (ResizeWindow_t*)hwlib.resolve("ResizeWindow");
+    flibUpdateMousePosition = (updateMousePosition_t*)hwlib.resolve("updateMousePosition");
     flibIpcToEngineRaw = (ipcToEngineRaw_t*)hwlib.resolve("ipcToEngineRaw");
     flibIpcSetEngineBarrier = (ipcSetEngineBarrier_t*)hwlib.resolve("ipcSetEngineBarrier");
     flibIpcRemoveBarrierFromEngineQueue = (ipcRemoveBarrierFromEngineQueue_t*)hwlib.resolve("ipcRemoveBarrierFromEngineQueue");