VS plugin mod for Basic Armour
Révision | f0a27eed8378aef611fa20877feb634cff0f2a63 (tree) |
---|---|
l'heure | 2019-06-13 10:59:43 |
Auteur | melchior <melchior@user...> |
Commiter | melchior |
Modified client event handling use non-polling method
Change variable casing for renderer (consistency)
@@ -14,7 +14,7 @@ namespace ArmourMod | ||
14 | 14 | { |
15 | 15 | public class ArmourMeshRenderer : IRenderer |
16 | 16 | { |
17 | - protected ICoreClientAPI ClientApi { get; set; } | |
17 | + protected ICoreClientAPI ClientAPI { get; set; } | |
18 | 18 | private Dictionary<AssetLocation,ArmourModelData> Armoury; |
19 | 19 | private bool enabled = true; |
20 | 20 |
@@ -30,7 +30,7 @@ namespace ArmourMod | ||
30 | 30 | |
31 | 31 | public ArmourMeshRenderer(ICoreClientAPI capi,Dictionary<AssetLocation,ArmourModelData> armoury ) |
32 | 32 | { |
33 | - this.ClientApi = capi; | |
33 | + this.ClientAPI = capi; | |
34 | 34 | this.Armoury = armoury; |
35 | 35 | //Pre-cached up ALL the damm armours; Mesh + Texture, Translations, Origins, other important parameters |
36 | 36 | } |
@@ -39,8 +39,8 @@ namespace ArmourMod | ||
39 | 39 | { |
40 | 40 | if (enabled) { |
41 | 41 | try { |
42 | - for (int i = 0; i < ClientApi.World.AllOnlinePlayers.Length; i++) { | |
43 | - var aPlayer = ClientApi.World.AllOnlinePlayers[i]; | |
42 | + for (int i = 0; i < ClientAPI.World.AllOnlinePlayers.Length; i++) { | |
43 | + var aPlayer = ClientAPI.World.AllOnlinePlayers[i]; | |
44 | 44 | |
45 | 45 | if (aPlayer?.Entity == null) continue;//Out of range |
46 | 46 |
@@ -52,12 +52,12 @@ namespace ArmourMod | ||
52 | 52 | EntityArmourPlayer armouredPlayer = aPlayer.Entity as EntityArmourPlayer; |
53 | 53 | |
54 | 54 | if (armouredPlayer == null) { |
55 | - ClientApi.Logger.Error("Could not cast EntityPlayer to EntityArmourPlayer"); | |
55 | + ClientAPI.Logger.Error("Could not cast EntityPlayer to EntityArmourPlayer"); | |
56 | 56 | return; |
57 | 57 | } |
58 | 58 | |
59 | 59 | if (armouredPlayer.RenderableWornArmours == null) { |
60 | - ClientApi.Logger.Error("RenderableWornArmours was NULL!"); | |
60 | + ClientAPI.Logger.Error("RenderableWornArmours was NULL!"); | |
61 | 61 | return; |
62 | 62 | } |
63 | 63 |
@@ -70,7 +70,7 @@ namespace ArmourMod | ||
70 | 70 | |
71 | 71 | } catch (Exception problem) |
72 | 72 | { |
73 | - ClientApi.Logger.Error("ArmourMeshRenderer FAULT: {0} Disabling.", problem.Message); | |
73 | + ClientAPI.Logger.Error("ArmourMeshRenderer FAULT: {0} Disabling.", problem.Message); | |
74 | 74 | enabled = false; |
75 | 75 | } |
76 | 76 | } |
@@ -84,10 +84,10 @@ namespace ArmourMod | ||
84 | 84 | /// <param name="isShadowPass">If set to <c>true</c> is shadow pass.</param> |
85 | 85 | private void RenderWornArmour(EntityArmourPlayer armouredPlayer, EntityShapeRenderer entityShapeRender, bool isShadowPass) |
86 | 86 | { |
87 | - IRenderAPI rpi = ClientApi.Render; | |
87 | + IRenderAPI rpi = ClientAPI.Render; | |
88 | 88 | IStandardShaderProgram prog = null; |
89 | 89 | |
90 | - if ( ClientApi.World.Player.Entity.EntityId == armouredPlayer.EntityId ) { | |
90 | + if ( ClientAPI.World.Player.Entity.EntityId == armouredPlayer.EntityId ) { | |
91 | 91 | //Is current player in First-person.... skip rendering |
92 | 92 | if ( rpi.CameraType == EnumCameraMode.FirstPerson ) return; |
93 | 93 | } |
@@ -95,7 +95,7 @@ namespace ArmourMod | ||
95 | 95 | foreach(var wornItemTuple in armouredPlayer.RenderableWornArmours) { |
96 | 96 | |
97 | 97 | if ( !Armoury.ContainsKey( wornItemTuple.Value.Code ) ) { |
98 | - ClientApi.Logger.Warning( "Armoury Item Missing KEY: {0} ! ** RENDER ABORTED **", wornItemTuple.Value.Code ); | |
98 | + ClientAPI.Logger.Warning( "Armoury Item Missing KEY: {0} ! ** RENDER ABORTED **", wornItemTuple.Value.Code ); | |
99 | 99 | return; |
100 | 100 | } |
101 | 101 |
@@ -113,7 +113,7 @@ namespace ArmourMod | ||
113 | 113 | |
114 | 114 | default: |
115 | 115 | attachPoise = null; |
116 | - ClientApi.Logger.Warning( "Unsupported armour Attachment Type: {0} ! ** RENDER ABORTED **", wornItemTuple.Key.ToString() ); | |
116 | + ClientAPI.Logger.Warning( "Unsupported armour Attachment Type: {0} ! ** RENDER ABORTED **", wornItemTuple.Key.ToString() ); | |
117 | 117 | return; |
118 | 118 | } |
119 | 119 |
@@ -129,7 +129,7 @@ namespace ArmourMod | ||
129 | 129 | armourModelMatrix.Set(entityShapeRender.ModelMat); |
130 | 130 | armourModelMatrix.Mul(attachPoise.AnimModelMatrix); |
131 | 131 | |
132 | - viewMatrix.Set( ClientApi.Render.CameraMatrixOriginf ); | |
132 | + viewMatrix.Set( ClientAPI.Render.CameraMatrixOriginf ); | |
133 | 133 | |
134 | 134 | |
135 | 135 | if ( isShadowPass ) { |
@@ -151,8 +151,8 @@ namespace ArmourMod | ||
151 | 151 | |
152 | 152 | var headMatrix = Mat4f.Create( ); |
153 | 153 | Mat4f.Identity(headMatrix); |
154 | - Mat4f.RotateY(headMatrix, headMatrix, ClientApi.World.Player.Entity.HeadYaw); | |
155 | - Mat4f.RotateZ(headMatrix, headMatrix, ClientApi.World.Player.Entity.HeadPitch); | |
154 | + Mat4f.RotateY(headMatrix, headMatrix, ClientAPI.World.Player.Entity.HeadYaw); | |
155 | + Mat4f.RotateZ(headMatrix, headMatrix, ClientAPI.World.Player.Entity.HeadPitch); | |
156 | 156 | |
157 | 157 | armourModelMatrix |
158 | 158 | .Scale( armourData.Armour_Transform.ScaleXYZ.X, armourData.Armour_Transform.ScaleXYZ.Y, armourData.Armour_Transform.ScaleXYZ.Z ) |
@@ -175,16 +175,16 @@ namespace ArmourMod | ||
175 | 175 | |
176 | 176 | |
177 | 177 | if ( isShadowPass ) { |
178 | - armourModelMatrix.Mul(ClientApi.Render.CurrentShadowProjectionMatrix); | |
179 | - ClientApi.Render.CurrentActiveShader.UniformMatrix( "mvpMatrix", armourModelMatrix.Values ); | |
180 | - ClientApi.Render.CurrentActiveShader.Uniform( "origin", new Vec3f());//OpenGL version of CONST/GLOBAL <-- what is VALUE??? | |
178 | + armourModelMatrix.Mul(ClientAPI.Render.CurrentShadowProjectionMatrix); | |
179 | + ClientAPI.Render.CurrentActiveShader.UniformMatrix( "mvpMatrix", armourModelMatrix.Values ); | |
180 | + ClientAPI.Render.CurrentActiveShader.Uniform( "origin", new Vec3f());//OpenGL version of CONST/GLOBAL <-- what is VALUE??? | |
181 | 181 | } else { |
182 | 182 | prog.ModelMatrix = armourModelMatrix.Values; |
183 | 183 | prog.ViewMatrix = viewMatrix.Values; |
184 | - prog.ProjectionMatrix = ClientApi.Render.CurrentProjectionMatrix; | |
184 | + prog.ProjectionMatrix = ClientAPI.Render.CurrentProjectionMatrix; | |
185 | 185 | } |
186 | 186 | |
187 | - ClientApi.Render.RenderMesh( armourData.ArmourMeshReference ); | |
187 | + ClientAPI.Render.RenderMesh( armourData.ArmourMeshReference ); | |
188 | 188 | |
189 | 189 | |
190 | 190 | if ( !isShadowPass ) |
@@ -197,7 +197,7 @@ namespace ArmourMod | ||
197 | 197 | //Manually clean up Meshs' |
198 | 198 | foreach(ArmourModelData armr in Armoury.Values) |
199 | 199 | { |
200 | - ClientApi.Render.DeleteMesh( armr.ArmourMeshReference ); | |
200 | + ClientAPI.Render.DeleteMesh( armr.ArmourMeshReference ); | |
201 | 201 | } |
202 | 202 | |
203 | 203 | } |
@@ -11,8 +11,7 @@ using Vintagestory.API.Server; | ||
11 | 11 | namespace ArmourMod |
12 | 12 | { |
13 | 13 | public class EntityArmourPlayer : EntityPlayer |
14 | - { | |
15 | - private static string _clientHookIdKey = @"ClientDelayHookId"; | |
14 | + { | |
16 | 15 | protected ICoreAPI CoreAPI; |
17 | 16 | protected ICoreClientAPI ClientAPI; |
18 | 17 | protected ICoreServerAPI ServerAPI; |
@@ -24,9 +23,6 @@ namespace ArmourMod | ||
24 | 23 | //Pre-compute values; |
25 | 24 | private DamageFilter finalFilter; |
26 | 25 | |
27 | - private bool slotEventAttached; | |
28 | - | |
29 | - | |
30 | 26 | internal ArmourModConfig CachedConfiguration |
31 | 27 | { |
32 | 28 | get |
@@ -39,32 +35,9 @@ namespace ArmourMod | ||
39 | 35 | } |
40 | 36 | } |
41 | 37 | |
42 | - private long CachedClientCallbackId | |
43 | - { | |
44 | - get | |
45 | - { | |
46 | - if (ClientAPI.ObjectCache.ContainsKey(_clientHookIdKey + ClientAPI.World.Player.PlayerUID)) | |
47 | - { | |
48 | - return (long)ClientAPI.ObjectCache[_clientHookIdKey + ClientAPI.World.Player.PlayerUID]; | |
49 | - } else { | |
50 | - return -1L; | |
51 | - } | |
52 | - } | |
53 | - set | |
54 | - { | |
55 | - if (ClientAPI.ObjectCache.ContainsKey(_clientHookIdKey + ClientAPI.World.Player.PlayerUID)) | |
56 | - { | |
57 | - Logger.Error("Trying to register duplicate callback-id [value: {0}]", value); ; | |
58 | - } | |
59 | - else | |
60 | - { | |
61 | - ClientAPI.ObjectCache[_clientHookIdKey + ClientAPI.World.Player.PlayerUID] = value; | |
62 | - } | |
63 | - } | |
64 | - } | |
38 | + public bool OwnEventsAttached { get; internal set;} | |
65 | 39 | |
66 | - | |
67 | - public Dictionary<EnumCharacterDressType,Item> RenderableWornArmours { get; private set;}//Needs to be client side | |
40 | + public Dictionary<EnumCharacterDressType, Item> RenderableWornArmours { get; private set; }//Needs to be client side | |
68 | 41 | |
69 | 42 | public override void Initialize(Vintagestory.API.Common.Entities.EntityProperties properties, ICoreAPI api, long chunkindex3d) |
70 | 43 | { |
@@ -78,38 +51,17 @@ namespace ArmourMod | ||
78 | 51 | this.ClientAPI = api as ICoreClientAPI; |
79 | 52 | this.RenderableWornArmours = new Dictionary<EnumCharacterDressType, Item>(); // BEFORE RENDERER GETS THERE! |
80 | 53 | Logger.VerboseDebug("Renderable Worn Armours Dict assigned"); |
54 | + | |
55 | + ClientAPI.Event.PlayerEntitySpawn += HandlePlayerSpawn; | |
56 | + ClientAPI.Event.PlayerEntityDespawn += HandlePlayerDespawn; | |
81 | 57 | } |
82 | 58 | |
83 | 59 | if (CoreAPI.Side.IsServer( )) { |
84 | 60 | this.ServerAPI = api as ICoreServerAPI; |
85 | - //from Config set values; | |
86 | - //ServerAPI.ModLoader. | |
87 | - //ArmourModHookin._domain | |
88 | 61 | } |
89 | 62 | } |
90 | 63 | |
91 | - public override void OnGameTick(float dt) | |
92 | - { | |
93 | - base.OnGameTick(dt); | |
94 | - | |
95 | 64 | |
96 | - if (CoreAPI.Side.IsClient( )) { | |
97 | - | |
98 | - if (ClientAPI.World.Player != null) { | |
99 | - | |
100 | - if (this.CachedClientCallbackId > 0) { | |
101 | - #if DEBUG | |
102 | - Logger.VerboseDebug("[OnEntityLoaded] Duplicate event attach prevented"); | |
103 | - #endif | |
104 | - } else { | |
105 | - this.CachedClientCallbackId = ClientAPI.Event.RegisterGameTickListener(ClientDelayHook, 250); | |
106 | - #if DEBUG | |
107 | - Logger.VerboseDebug("[OnEntityLoaded] oneShotDelayId: {0}", this.CachedClientCallbackId); | |
108 | - #endif | |
109 | - } | |
110 | - } | |
111 | - } | |
112 | - } | |
113 | 65 | |
114 | 66 | |
115 | 67 | public override void OnEntitySpawn() |
@@ -296,32 +248,6 @@ namespace ArmourMod | ||
296 | 248 | return false; |
297 | 249 | } |
298 | 250 | |
299 | - | |
300 | - protected void ClientDelayHook(float delay) | |
301 | - { | |
302 | - #if DEBUG | |
303 | - Logger.VerboseDebug("[clientDelayHook] oneShotDelayId: {0}", this.CachedClientCallbackId); | |
304 | - #endif | |
305 | - | |
306 | - if (this.GearInventory == null) { | |
307 | - Logger.Error("ClientDelayHook: base.GearInventory IS NULL! "); | |
308 | - | |
309 | - return; | |
310 | - } | |
311 | - | |
312 | - if (slotEventAttached == false) { | |
313 | - slotEventAttached = true; | |
314 | - #if DEBUG | |
315 | - Logger.VerboseDebug("Attached ClientWatchSlotModified (ClientDelayHook)"); | |
316 | - #endif | |
317 | - this.GearInventory.SlotModified += ClientWatchSlotModified; | |
318 | - } | |
319 | - | |
320 | - ClientAPI.Event.UnregisterGameTickListener(this.CachedClientCallbackId); | |
321 | - | |
322 | - PopulateWornArmourModels( ); | |
323 | - } | |
324 | - | |
325 | 251 | private void ServerWatchSlotModified (int slotId) |
326 | 252 | { |
327 | 253 | var watchedSlot = this.GearInventory[slotId]; |
@@ -356,7 +282,7 @@ namespace ArmourMod | ||
356 | 282 | } |
357 | 283 | } |
358 | 284 | |
359 | - private void ClientWatchSlotModified (int slotId) | |
285 | + protected void ClientWatchSlotModified (int slotId) | |
360 | 286 | { |
361 | 287 | #if DEBUG |
362 | 288 | Logger.VerboseDebug( "(Client) WatchSlotModified:{0} PlayerID: {1} InventoryID: {2}", slotId, ClientAPI.World.Player.PlayerUID,this.GearInventory.InventoryID ); |
@@ -378,14 +304,62 @@ namespace ArmourMod | ||
378 | 304 | } |
379 | 305 | } |
380 | 306 | |
381 | - /* | |
382 | - private void WatchSlotNotified(int slotId) | |
307 | + /// <summary> | |
308 | + /// Add Watcher for armour change -- could be _ANY_ player (not just self!) | |
309 | + /// </summary> | |
310 | + /// <remarks>Client side</remarks> | |
311 | + /// <param name="byPlayer">By player.</param> | |
312 | + private void HandlePlayerSpawn(IClientPlayer byPlayer) | |
313 | + { | |
314 | + Logger.VerboseDebug("Handling Spawn for: {0}", byPlayer.PlayerName); | |
315 | + | |
316 | + if (byPlayer.Entity != null && byPlayer.Entity is EntityArmourPlayer) { | |
317 | + EntityArmourPlayer targetPlayer = byPlayer.Entity as EntityArmourPlayer;//CHECK: Cast from - not actual instance? | |
318 | + | |
319 | + if (targetPlayer.GearInventory == null) { | |
320 | + Logger.Error("HandlePlayerSpawn: base.GearInventory IS NULL! "); | |
321 | + | |
322 | + return; | |
323 | + } | |
324 | + | |
325 | + if (targetPlayer.PlayerUID == ClientAPI.World.Player.PlayerUID) | |
326 | + { | |
327 | + if (targetPlayer.OwnEventsAttached == false) { | |
328 | + targetPlayer.OwnEventsAttached = true; | |
329 | + #if DEBUG | |
330 | + Logger.VerboseDebug("Attached event: (ClientWatchSlotModified) for {0}", byPlayer.PlayerName); | |
331 | + #endif | |
332 | + targetPlayer.GearInventory.SlotModified += targetPlayer.ClientWatchSlotModified; | |
333 | + PopulateWornArmourModels(targetPlayer); | |
334 | + } else { | |
335 | + #if DEBUG | |
336 | + Logger.VerboseDebug("Duplicate event: (ClientWatchSlotModified) for {0}", byPlayer.PlayerName); | |
337 | + #endif | |
338 | + } | |
339 | + } else { | |
340 | + if (targetPlayer.OwnEventsAttached == false) { | |
341 | + targetPlayer.OwnEventsAttached = true; | |
342 | + #if DEBUG | |
343 | + Logger.VerboseDebug("Non-local Attached event: (ClientWatchSlotModified) for {0}", byPlayer.PlayerName); | |
344 | + #endif | |
345 | + targetPlayer.GearInventory.SlotModified += targetPlayer.ClientWatchSlotModified; | |
346 | + PopulateWornArmourModels(targetPlayer); | |
347 | + } else { | |
348 | + #if DEBUG | |
349 | + Logger.VerboseDebug("Non-local Duplicate event: (ClientWatchSlotModified) for {0}", byPlayer.PlayerName); | |
350 | + #endif | |
351 | + } | |
352 | + } | |
353 | + } | |
354 | + } | |
355 | + | |
356 | + | |
357 | + private void HandlePlayerDespawn(IClientPlayer byPlayer) | |
383 | 358 | { |
384 | - var watchedSlot = base.GearInventory[slotId]; | |
359 | + //Unlink watcher event | |
360 | + Logger.VerboseDebug("Handling Despawn for: {0}", byPlayer.PlayerName); | |
385 | 361 | |
386 | - Logger.VerboseDebug( "WatchSlotNotified:{0}", slotId ); | |
387 | 362 | } |
388 | - */ | |
389 | 363 | |
390 | 364 | |
391 | 365 |
@@ -484,26 +458,26 @@ namespace ArmourMod | ||
484 | 458 | /// Client Side rendering; What armours are visibly worn |
485 | 459 | /// </summary> |
486 | 460 | /// <returns>The worn armour models.</returns> |
487 | - private void PopulateWornArmourModels() | |
461 | + internal void PopulateWornArmourModels(EntityArmourPlayer targetPlayer) | |
488 | 462 | { |
489 | - if ( this.GearInventory != null && this.GearInventory.Count > 0 ) { | |
490 | - foreach(var itemSlot in this.GearInventory ) { | |
463 | + if ( targetPlayer.GearInventory != null && targetPlayer.GearInventory.Count > 0 ) { | |
464 | + foreach(var itemSlot in targetPlayer.GearInventory ) { | |
491 | 465 | |
492 | - int slotId = this.GearInventory.GetSlotId( itemSlot ); | |
466 | + int slotId = targetPlayer.GearInventory.GetSlotId( itemSlot ); | |
493 | 467 | if ( !itemSlot.Empty ) { |
494 | 468 | |
495 | 469 | if ( itemSlot.StorageType == EnumItemStorageFlags.Outfit && itemSlot.Itemstack.Class == EnumItemClass.Item ) { |
496 | 470 | |
497 | 471 | if ( CheckIfClothesIsArmour(itemSlot) ) |
498 | - { | |
472 | + { | |
499 | 473 | #if DEBUG |
500 | - Logger.VerboseDebug( "Now wearing armour:{0}", itemSlot.Itemstack.Item.Code.ToString( ) ); | |
474 | + Logger.VerboseDebug( "{0} is wearing armour: {1}", targetPlayer.Player.PlayerName, itemSlot.Itemstack.Item.Code.ToString( ) ); | |
501 | 475 | #endif |
502 | 476 | |
503 | 477 | if (RenderableWornArmours.ContainsKey(( EnumCharacterDressType )slotId)) { |
504 | 478 | Logger.Warning("DUPLICATE assignment; Armour in slot: {0} named: {1}", slotId, itemSlot.Itemstack.Item.Code.ToString( )); |
505 | 479 | } else { |
506 | - RenderableWornArmours.Add(( EnumCharacterDressType )slotId, itemSlot.Itemstack.Item); | |
480 | + targetPlayer.RenderableWornArmours.Add(( EnumCharacterDressType )slotId, itemSlot.Itemstack.Item); | |
507 | 481 | } |
508 | 482 | } |
509 | 483 | } |