diff --git a/Assets/Scripts/Data/QExtensions.cs b/Assets/Scripts/Data/QExtensions.cs index b5b0807..8580da2 100644 --- a/Assets/Scripts/Data/QExtensions.cs +++ b/Assets/Scripts/Data/QExtensions.cs @@ -58,6 +58,6 @@ public static class QExtensions public static Quaternion ToUnityRotation(this QVec3 angles) { - return Quaternion.Euler(angles.x, 90 - angles.y, -angles.z); + return Quaternion.Euler(angles.x, -angles.y, -angles.z); } } diff --git a/Assets/Scripts/Game/Entity.cs b/Assets/Scripts/Game/Entity.cs index ec5005f..977313d 100644 --- a/Assets/Scripts/Game/Entity.cs +++ b/Assets/Scripts/Game/Entity.cs @@ -48,14 +48,14 @@ public class Entity UpdateAnimation(0); } - public void UpdateAnimation(int frameNum) + public void UpdateAnimation(float frameNum) { if (aliasModel != null) { aliasModel.Animate(frameNum, out Mesh mesh, out float blendWeight); meshRenderer.sharedMesh = mesh; - if (mesh.blendShapeCount > 0) + if (mesh != null && mesh.blendShapeCount > 0) meshRenderer.SetBlendShapeWeight(0, blendWeight); } } diff --git a/Assets/Scripts/Game/GameState.cs b/Assets/Scripts/Game/GameState.cs index 950156b..66457d2 100644 --- a/Assets/Scripts/Game/GameState.cs +++ b/Assets/Scripts/Game/GameState.cs @@ -99,7 +99,7 @@ public class GameState // TODO: obtain Mesh from brush submodel and assign it to MeshRenderer } - public void UpdateEntityAnimation(int entityNum, int frameNum) + public void UpdateEntityAnimation(int entityNum, float frameNum) { if (entities.TryGetValue(entityNum, out var entity)) { diff --git a/Assets/Scripts/Modules/GameModule.Interop.cs b/Assets/Scripts/Modules/GameModule.Interop.cs index c673003..ae41626 100644 --- a/Assets/Scripts/Modules/GameModule.Interop.cs +++ b/Assets/Scripts/Modules/GameModule.Interop.cs @@ -16,6 +16,7 @@ public partial class GameModule : CallbackHandler SetEntityModel = CreateCallback(Callback_GameSetEntityModel), SetEntityTransform = CreateCallback(Callback_GameSetEntityTransform), RemoveEntity = CreateCallback(Callback_GameRemoveEntity), + UpdateEntityAnimation = CreateCallback(Callback_GameUpdateEntityAnimation), }; RegisterCallbacks(callbacks); @@ -32,6 +33,7 @@ public partial class GameModule : CallbackHandler public IntPtr SetEntityModel; public IntPtr SetEntityTransform; public IntPtr RemoveEntity; + public IntPtr UpdateEntityAnimation; } [UnmanagedFunctionPointer(CallingConvention.Cdecl)] @@ -60,4 +62,13 @@ public partial class GameModule : CallbackHandler { GetSelf(target).RemoveEntity(entityNum); } + + [UnmanagedFunctionPointer(CallingConvention.Cdecl)] + private delegate void GameUpdateEntityAnimationCallback(IntPtr target, int entityNum, float frameNum); + + [MonoPInvokeCallback(typeof(GameUpdateEntityAnimationCallback))] + private static void Callback_GameUpdateEntityAnimation(IntPtr target, int entityNum, float frameNum) + { + GetSelf(target).UpdateEntityAnimation(entityNum, frameNum); + } } diff --git a/Assets/Scripts/Modules/GameModule.cs b/Assets/Scripts/Modules/GameModule.cs index b091962..31501e4 100644 --- a/Assets/Scripts/Modules/GameModule.cs +++ b/Assets/Scripts/Modules/GameModule.cs @@ -58,4 +58,9 @@ public partial class GameModule { uq.GameState.RemoveEntity(entityNum); } + + private void UpdateEntityAnimation(int entityNum, float frameNum) + { + uq.GameState.UpdateEntityAnimation(entityNum, frameNum); + } } diff --git a/Assets/Scripts/Modules/RenderModule.cs b/Assets/Scripts/Modules/RenderModule.cs index b1e36b0..62598cb 100644 --- a/Assets/Scripts/Modules/RenderModule.cs +++ b/Assets/Scripts/Modules/RenderModule.cs @@ -138,6 +138,8 @@ public partial class RenderModule if (cam == null) return; + angles.y -= 90; // Don't know why this correction is necessary + cam.transform.position = origin.ToUnityPosition(); cam.transform.rotation = angles.ToUnityRotation(); } diff --git a/Assets/Scripts/Support/AliasModel.cs b/Assets/Scripts/Support/AliasModel.cs index c083f44..23b7a97 100644 --- a/Assets/Scripts/Support/AliasModel.cs +++ b/Assets/Scripts/Support/AliasModel.cs @@ -38,7 +38,7 @@ public class AliasModel if (!FindAnimation(frameIndex, out mesh, out int startFrame)) return; - if (mesh.blendShapeCount == 0) + if (mesh == null || mesh.blendShapeCount == 0) return; int numFrames = mesh.GetBlendShapeFrameCount(0); @@ -52,15 +52,14 @@ public class AliasModel for (int i = 0; i < animationMeshes.Count; ++i) { - startFrame = animationMeshes[i].Item1; - if (frameIndex >= startFrame) - { - mesh = animationMeshes[i].Item2; + if (animationMeshes[i].Item1 > frameIndex) return true; - } + + startFrame = animationMeshes[i].Item1; + mesh = animationMeshes[i].Item2; } - return false; // Shouldn't happen + return true; } public void Dispose() diff --git a/engine/Quake/cl_main.c b/engine/Quake/cl_main.c index 94521d6..c00f8c9 100644 --- a/engine/Quake/cl_main.c +++ b/engine/Quake/cl_main.c @@ -71,6 +71,8 @@ CL_ClearState */ void CL_ClearState (void) { + int num; + if (!sv.active) Host_ClearMemory (); @@ -88,6 +90,10 @@ void CL_ClearState (void) //johnfitz -- cl_entities is now dynamically allocated cl_max_edicts = CLAMP (MIN_EDICTS,(int)max_edicts.value,MAX_EDICTS); cl_entities = (entity_t *) Hunk_AllocName (cl_max_edicts*sizeof(entity_t), "cl_entities"); + for (num = 0; num < cl_max_edicts; num++) + { + cl_entities[num].num = num; + } //johnfitz } @@ -582,7 +588,7 @@ void CL_RelinkEntities (void) cl_numvisedicts++; } - UQ_Game_SetEntityTransform(i, ent->origin, ent->angles); + //UQ_Game_SetEntityTransform(i, ent->origin, ent->angles); } } diff --git a/engine/Quake/client.h b/engine/Quake/client.h index 853820b..e798179 100644 --- a/engine/Quake/client.h +++ b/engine/Quake/client.h @@ -375,6 +375,7 @@ void Chase_UpdateForDrawing (void); //johnfitz void UQ_Game_SetEntityModel(int entityNum, const char *modelName); void UQ_Game_SetEntityTransform(int entityNum, vec3_t origin, vec3_t angles); void UQ_Game_RemoveEntity(int entityNum); +void UQ_Game_UpdateEntityAnimation(int entityNum, float frameNum); #endif /* _CLIENT_H_ */ diff --git a/engine/Quake/r_alias.c b/engine/Quake/r_alias.c index e40ae50..6e1b01f 100644 --- a/engine/Quake/r_alias.c +++ b/engine/Quake/r_alias.c @@ -470,7 +470,7 @@ void R_SetupAliasFrame (aliashdr_t *paliashdr, int frame, lerpdata_t *lerpdata) } else //don't lerp { - lerpdata->blend = 1; + lerpdata->blend = 0; lerpdata->pose1 = posenum; lerpdata->pose2 = posenum; } @@ -641,6 +641,9 @@ void R_DrawAliasModel (entity_t *e) R_SetupAliasFrame (paliashdr, e->frame, &lerpdata); R_SetupEntityTransform (e, &lerpdata); + UQ_Game_SetEntityTransform(e->num, lerpdata.origin, lerpdata.angles); + UQ_Game_UpdateEntityAnimation(e->num, (float)lerpdata.pose1 + lerpdata.blend); + // // cull it // diff --git a/engine/Quake/render.h b/engine/Quake/render.h index 55aded4..6699f2c 100644 --- a/engine/Quake/render.h +++ b/engine/Quake/render.h @@ -48,6 +48,7 @@ typedef struct efrag_s typedef struct entity_s { + int num; // cache entity number in the entity itself qboolean forcelink; // model changed int update_type; diff --git a/engine/UniQuake/game_uniquake.c b/engine/UniQuake/game_uniquake.c index 4057c4a..493432e 100644 --- a/engine/UniQuake/game_uniquake.c +++ b/engine/UniQuake/game_uniquake.c @@ -9,6 +9,7 @@ typedef struct unity_gamecalls_s void(*SetEntityModel)(void *target, int entityNum, const char *modelName); void(*SetEntityTransform)(void *target, int entityNum, vec3_t origin, vec3_t angles); void(*RemoveEntity)(void *target, int entityNum); + void(*UpdateEntityAnimation)(void *target, int entityNum, float frameNum); } unity_gamecalls_t; const unity_gamecalls_t *unity_gamecalls; @@ -27,3 +28,8 @@ void UQ_Game_RemoveEntity(int entityNum) { unity_gamecalls->RemoveEntity(unity_gamecalls->target, entityNum); } + +void UQ_Game_UpdateEntityAnimation(int entityNum, float frameNum) +{ + unity_gamecalls->UpdateEntityAnimation(unity_gamecalls->target, entityNum, frameNum); +}