From f26f7a4348c14a0502bdb3fc23594500deb68c51 Mon Sep 17 00:00:00 2001 From: hondacrx Date: Tue, 8 May 2018 15:36:23 -0400 Subject: [PATCH] Core/Misc: Fixed rotation of many gameobjects summoned in garrison and various scripts --- Source/Framework/GameMath/Quaternion.cs | 12 +++++++++++- Source/Game/AI/SmartScripts/SmartScript.cs | 4 ++-- Source/Game/BattleGrounds/BattleGround.cs | 2 +- Source/Game/Chat/Commands/GameObjectCommands.cs | 4 ++-- Source/Game/Entities/GameObject/GameObject.cs | 15 ++++++++++----- Source/Game/Entities/Transport.cs | 2 +- Source/Game/Garrisons/Garrisons.cs | 6 ++++-- Source/Game/Spells/SpellEffects.cs | 8 ++++---- .../InstanceTrialOfTheChampion.cs | 6 +++--- .../TrialOfTheCrusader/TrialOfTheCrusader.cs | 4 ++-- .../Nexus/EyeOfEternity/EyeOfEternity.cs | 2 +- Source/Scripts/Spells/Items.cs | 2 +- Source/Scripts/World/ItemScripts.cs | 2 +- Source/Scripts/World/NpcSpecial.cs | 2 +- 14 files changed, 44 insertions(+), 27 deletions(-) diff --git a/Source/Framework/GameMath/Quaternion.cs b/Source/Framework/GameMath/Quaternion.cs index 4e894091f..8d1afa3b8 100644 --- a/Source/Framework/GameMath/Quaternion.cs +++ b/Source/Framework/GameMath/Quaternion.cs @@ -476,10 +476,15 @@ namespace Framework.GameMath public Quaternion ToUnit() { Quaternion copyOfThis = this; - copyOfThis *= rsq(dot(this)); + copyOfThis.unitize(); return copyOfThis; } + public void unitize() + { + this *= rsq(dot(this)); + } + float dot(Quaternion other) { return (float)((X * other.X) + (Y * other.Y) + (Z * other.Z) + (W * other.W)); @@ -490,6 +495,11 @@ namespace Framework.GameMath return 1.0f / (float)Math.Sqrt(x); } + public static Quaternion fromEulerAnglesZYX(float z, float y, float x) + { + return new Quaternion(Matrix3.fromEulerAnglesZYX(z, y, x)); + } + #region Public Static Complex Special Functions /// /// Calculates the logarithm of a given quaternion. diff --git a/Source/Game/AI/SmartScripts/SmartScript.cs b/Source/Game/AI/SmartScripts/SmartScript.cs index 80d4e7415..800839de2 100644 --- a/Source/Game/AI/SmartScripts/SmartScript.cs +++ b/Source/Game/AI/SmartScripts/SmartScript.cs @@ -1286,7 +1286,7 @@ namespace Game.AI continue; Position pos = obj.GetPositionWithOffset(new Position(e.Target.x, e.Target.y, e.Target.z, e.Target.o)); - Quaternion rot = new Quaternion(Matrix3.fromEulerAnglesZYX(pos.GetOrientation(), 0.0f, 0.0f)); + Quaternion rot = Quaternion.fromEulerAnglesZYX(pos.GetOrientation(), 0.0f, 0.0f); summoner.SummonGameObject(e.Action.summonGO.entry, pos, rot, e.Action.summonGO.despawnTime); } } @@ -1294,7 +1294,7 @@ namespace Game.AI if (e.GetTargetType() != SmartTargets.Position) break; - Quaternion rot1 = new Quaternion(Matrix3.fromEulerAnglesZYX(e.Target.o, 0.0f, 0.0f)); + Quaternion rot1 = Quaternion.fromEulerAnglesZYX(e.Target.o, 0.0f, 0.0f); summoner.SummonGameObject(e.Action.summonGO.entry, new Position(e.Target.x, e.Target.y, e.Target.z, e.Target.o), rot1, e.Action.summonGO.despawnTime); break; } diff --git a/Source/Game/BattleGrounds/BattleGround.cs b/Source/Game/BattleGrounds/BattleGround.cs index 8ac243f29..8b22df28c 100644 --- a/Source/Game/BattleGrounds/BattleGround.cs +++ b/Source/Game/BattleGrounds/BattleGround.cs @@ -1325,7 +1325,7 @@ namespace Game.BattleGrounds Log.outDebug(LogFilter.Battleground, "Battleground.AddObject: gameoobject [entry: {0}, object type: {1}] for BG (map: {2}) has zeroed rotation fields, " + "orientation used temporally, but please fix the spawn", entry, type, m_MapId); - rotation = new Quaternion(Matrix3.fromEulerAnglesZYX(o, 0.0f, 0.0f)); + rotation = Quaternion.fromEulerAnglesZYX(o, 0.0f, 0.0f); } // Must be created this way, adding to godatamap would add it to the base map of the instance diff --git a/Source/Game/Chat/Commands/GameObjectCommands.cs b/Source/Game/Chat/Commands/GameObjectCommands.cs index 24e899fb4..fd79413e5 100644 --- a/Source/Game/Chat/Commands/GameObjectCommands.cs +++ b/Source/Game/Chat/Commands/GameObjectCommands.cs @@ -473,7 +473,7 @@ namespace Game.Chat Player player = handler.GetPlayer(); Map map = player.GetMap(); - GameObject obj = GameObject.CreateGameObject(objectInfo.entry, map, player, new Quaternion(Matrix3.fromEulerAnglesZYX(player.GetOrientation(), 0.0f, 0.0f)), 255, GameObjectState.Ready); + GameObject obj = GameObject.CreateGameObject(objectInfo.entry, map, player, Quaternion.fromEulerAnglesZYX(player.GetOrientation(), 0.0f, 0.0f), 255, GameObjectState.Ready); if (!obj) return false; @@ -517,7 +517,7 @@ namespace Game.Chat if (spawntime != 0) spawntm = spawntime; - Quaternion rotation = new Quaternion(Matrix3.fromEulerAnglesZYX(player.GetOrientation(), 0.0f, 0.0f)); + Quaternion rotation = Quaternion.fromEulerAnglesZYX(player.GetOrientation(), 0.0f, 0.0f); if (Global.ObjectMgr.GetGameObjectTemplate(id) == null) { diff --git a/Source/Game/Entities/GameObject/GameObject.cs b/Source/Game/Entities/GameObject/GameObject.cs index 76cf59d2f..f3e07daea 100644 --- a/Source/Game/Entities/GameObject/GameObject.cs +++ b/Source/Game/Entities/GameObject/GameObject.cs @@ -234,7 +234,7 @@ namespace Game.Entities return false; } - SetWorldRotation(rotation); + SetWorldRotation(rotation.X, rotation.Y, rotation.Z, rotation.W); GameObjectAddon gameObjectAddon = Global.ObjectMgr.GetGameObjectAddon(GetSpawnId()); // For most of gameobjects is (0, 0, 0, 1) quaternion, there are only some transports with not standard rotation @@ -2067,9 +2067,14 @@ namespace Game.Entities m_packedRotation = z | (y << 21) | (x << 42); } - public void SetWorldRotation(Quaternion quaternion) + public void SetWorldRotation(float qx, float qy, float qz, float qw) { - m_worldRotation = quaternion.ToUnit(); + Quaternion rotation = new Quaternion(qx, qy, qz, qw); + rotation.unitize(); + m_worldRotation.X = rotation.X; + m_worldRotation.Y = rotation.Y; + m_worldRotation.Z = rotation.Z; + m_worldRotation.W = rotation.W; UpdatePackedRotation(); } @@ -2083,8 +2088,8 @@ namespace Game.Entities public void SetWorldRotationAngles(float z_rot, float y_rot, float x_rot) { - Quaternion quat = new Quaternion(Matrix3.fromEulerAnglesZYX(z_rot, y_rot, x_rot)); - SetWorldRotation(quat); + Quaternion quat = Quaternion.fromEulerAnglesZYX(z_rot, y_rot, x_rot); + SetWorldRotation(quat.X, quat.Y, quat.Z, quat.W); } public void ModifyHealth(int change, Unit attackerOrHealer = null, uint spellId = 0) diff --git a/Source/Game/Entities/Transport.cs b/Source/Game/Entities/Transport.cs index aff39f5be..e6b19e16f 100644 --- a/Source/Game/Entities/Transport.cs +++ b/Source/Game/Entities/Transport.cs @@ -129,7 +129,7 @@ namespace Game.Entities SetGoType(GameObjectTypes.MapObjTransport); SetGoAnimProgress(animprogress); SetName(goinfo.name); - SetWorldRotation(Quaternion.WAxis); + SetWorldRotation(0.0f, 0.0f, 0.0f, 1.0f); SetParentRotation(Quaternion.WAxis); m_model = CreateModel(); diff --git a/Source/Game/Garrisons/Garrisons.cs b/Source/Game/Garrisons/Garrisons.cs index 30ec2f7ac..60dc12b7e 100644 --- a/Source/Game/Garrisons/Garrisons.cs +++ b/Source/Game/Garrisons/Garrisons.cs @@ -269,6 +269,7 @@ namespace Game.Garrisons plotInfo.PacketInfo.GarrPlotInstanceID = garrPlotInstanceId; plotInfo.PacketInfo.PlotPos.Relocate(gameObject.Pos.X, gameObject.Pos.Y, gameObject.Pos.Z, 2 * (float)Math.Acos(gameObject.Rot[3])); plotInfo.PacketInfo.PlotType = plot.PlotType; + plotInfo.Rotation = new Quaternion(gameObject.Rot[0], gameObject.Rot[1], gameObject.Rot[2], gameObject.Rot[3]); plotInfo.EmptyGameObjectId = gameObject.Id; plotInfo.GarrSiteLevelPlotInstId = plots[i].Id; } @@ -707,7 +708,7 @@ namespace Game.Garrisons return null; } - GameObject go = GameObject.CreateGameObject(entry, map, PacketInfo.PlotPos, Quaternion.WAxis, 255, GameObjectState.Ready); + GameObject go = GameObject.CreateGameObject(entry, map, PacketInfo.PlotPos, Rotation, 255, GameObjectState.Ready); if (!go) return null; @@ -717,7 +718,7 @@ namespace Game.Garrisons if (finalizeInfo != null) { Position pos2 = finalizeInfo.factionInfo[faction].Pos; - GameObject finalizer = GameObject.CreateGameObject(finalizeInfo.factionInfo[faction].GameObjectId, map, pos2, Quaternion.WAxis, 255, GameObjectState.Ready); + GameObject finalizer = GameObject.CreateGameObject(finalizeInfo.factionInfo[faction].GameObjectId, map, pos2, Quaternion.fromEulerAnglesZYX(pos2.GetOrientation(), 0.0f, 0.0f), 255, GameObjectState.Ready); if (finalizer) { // set some spell id to make the object delete itself after use @@ -845,6 +846,7 @@ namespace Game.Garrisons } public GarrisonPlotInfo PacketInfo; + public Quaternion Rotation; public uint EmptyGameObjectId; public uint GarrSiteLevelPlotInstId; public Building BuildingInfo; diff --git a/Source/Game/Spells/SpellEffects.cs b/Source/Game/Spells/SpellEffects.cs index c3da30b24..cb1a24648 100644 --- a/Source/Game/Spells/SpellEffects.cs +++ b/Source/Game/Spells/SpellEffects.cs @@ -2849,7 +2849,7 @@ namespace Game.Spells Map map = target.GetMap(); Position pos = new Position(x, y, z, target.GetOrientation()); - Quaternion rotation = new Quaternion(Matrix3.fromEulerAnglesZYX(target.GetOrientation(), 0.0f, 0.0f)); + Quaternion rotation = Quaternion.fromEulerAnglesZYX(target.GetOrientation(), 0.0f, 0.0f); GameObject go = GameObject.CreateGameObject((uint)effectInfo.MiscValue, map, pos, rotation, 255, GameObjectState.Ready); if (!go) return; @@ -3509,7 +3509,7 @@ namespace Game.Spells posZ = m_caster.GetPositionZ(), Orientation = m_caster.GetOrientation() }; - Quaternion rotation = new Quaternion(Matrix3.fromEulerAnglesZYX(pos.GetOrientation(), 0.0f, 0.0f)); + Quaternion rotation = Quaternion.fromEulerAnglesZYX(pos.GetOrientation(), 0.0f, 0.0f); GameObject go = GameObject.CreateGameObject((uint)effectInfo.MiscValue, map, pos, rotation, 0, GameObjectState.Ready); if (!go) @@ -3850,7 +3850,7 @@ namespace Game.Spells Map map = m_caster.GetMap(); Position pos = new Position(x, y, z, m_caster.GetOrientation()); - Quaternion rotation = new Quaternion(Matrix3.fromEulerAnglesZYX(m_caster.GetOrientation(), 0.0f, 0.0f)); + Quaternion rotation = Quaternion.fromEulerAnglesZYX(m_caster.GetOrientation(), 0.0f, 0.0f); GameObject go = GameObject.CreateGameObject((uint)effectInfo.MiscValue, map, pos, rotation, 255, GameObjectState.Ready); if (!go) return; @@ -4537,7 +4537,7 @@ namespace Game.Spells m_caster.GetPosition(out fx, out fy, out fz); Position pos = new Position(fx, fy, fz, m_caster.GetOrientation()); - Quaternion rotation = new Quaternion(Matrix3.fromEulerAnglesZYX(m_caster.GetOrientation(), 0.0f, 0.0f)); + Quaternion rotation = Quaternion.fromEulerAnglesZYX(m_caster.GetOrientation(), 0.0f, 0.0f); GameObject go = GameObject.CreateGameObject(name_id, cMap, pos, rotation, 255, GameObjectState.Ready); if (!go) return; diff --git a/Source/Scripts/Northrend/CrusadersColiseum/TrialOfTheChampion/InstanceTrialOfTheChampion.cs b/Source/Scripts/Northrend/CrusadersColiseum/TrialOfTheChampion/InstanceTrialOfTheChampion.cs index d13a60fd9..c1a8547c6 100644 --- a/Source/Scripts/Northrend/CrusadersColiseum/TrialOfTheChampion/InstanceTrialOfTheChampion.cs +++ b/Source/Scripts/Northrend/CrusadersColiseum/TrialOfTheChampion/InstanceTrialOfTheChampion.cs @@ -156,7 +156,7 @@ namespace Scripts.Northrend.CrusadersColiseum.TrialOfTheChampion { pAnnouncer.GetMotionMaster().MovePoint(0, 748.309f, 619.487f, 411.171f); pAnnouncer.SetFlag(UnitFields.NpcFlags, NPCFlags.Gossip); - pAnnouncer.SummonGameObject(instance.IsHeroic() ? GameObjectIds.CHAMPIONS_LOOT_H : GameObjectIds.CHAMPIONS_LOOT, 746.59f, 618.49f, 411.09f, 1.42f, Quaternion.WAxis, 90000); + pAnnouncer.SummonGameObject(instance.IsHeroic() ? GameObjectIds.CHAMPIONS_LOOT_H : GameObjectIds.CHAMPIONS_LOOT, 746.59f, 618.49f, 411.09f, 1.42f, Quaternion.fromEulerAnglesZYX(1.42f, 0.0f, 0.0f), 90000); } } } @@ -182,7 +182,7 @@ namespace Scripts.Northrend.CrusadersColiseum.TrialOfTheChampion { pAnnouncer.GetMotionMaster().MovePoint(0, 748.309f, 619.487f, 411.171f); pAnnouncer.SetFlag(UnitFields.NpcFlags, NPCFlags.Gossip); - pAnnouncer.SummonGameObject(instance.IsHeroic() ? GameObjectIds.EADRIC_LOOT_H : GameObjectIds.EADRIC_LOOT, 746.59f, 618.49f, 411.09f, 1.42f, Quaternion.WAxis, 90000); + pAnnouncer.SummonGameObject(instance.IsHeroic() ? GameObjectIds.EADRIC_LOOT_H : GameObjectIds.EADRIC_LOOT, 746.59f, 618.49f, 411.09f, 1.42f, Quaternion.fromEulerAnglesZYX(1.42f, 0.0f, 0.0f), 90000); } } break; @@ -194,7 +194,7 @@ namespace Scripts.Northrend.CrusadersColiseum.TrialOfTheChampion { pAnnouncer.GetMotionMaster().MovePoint(0, 748.309f, 619.487f, 411.171f); pAnnouncer.SetFlag(UnitFields.NpcFlags, NPCFlags.Gossip); - pAnnouncer.SummonGameObject(instance.IsHeroic() ? GameObjectIds.PALETRESS_LOOT_H : GameObjectIds.PALETRESS_LOOT, 746.59f, 618.49f, 411.09f, 1.42f, Quaternion.WAxis, 90000); + pAnnouncer.SummonGameObject(instance.IsHeroic() ? GameObjectIds.PALETRESS_LOOT_H : GameObjectIds.PALETRESS_LOOT, 746.59f, 618.49f, 411.09f, 1.42f, Quaternion.fromEulerAnglesZYX(1.42f, 0.0f, 0.0f), 90000); } } break; diff --git a/Source/Scripts/Northrend/CrusadersColiseum/TrialOfTheCrusader/TrialOfTheCrusader.cs b/Source/Scripts/Northrend/CrusadersColiseum/TrialOfTheCrusader/TrialOfTheCrusader.cs index ba206d923..8ef4375b7 100644 --- a/Source/Scripts/Northrend/CrusadersColiseum/TrialOfTheCrusader/TrialOfTheCrusader.cs +++ b/Source/Scripts/Northrend/CrusadersColiseum/TrialOfTheCrusader/TrialOfTheCrusader.cs @@ -338,7 +338,7 @@ namespace Scripts.Northrend.CrusadersColiseum.TrialOfTheCrusader Creature tirion = instance.GetCreature(TirionGUID); if (tirion) { - GameObject chest = tirion.SummonGameObject(tributeChest, 805.62f, 134.87f, 142.16f, 3.27f, Quaternion.WAxis, Time.Week); + GameObject chest = tirion.SummonGameObject(tributeChest, 805.62f, 134.87f, 142.16f, 3.27f, Quaternion.fromEulerAnglesZYX(3.27f, 0.0f, 0.0f), Time.Week); if (chest) chest.SetRespawnTime((int)chest.GetRespawnDelay()); } @@ -1479,7 +1479,7 @@ namespace Scripts.Northrend.CrusadersColiseum.TrialOfTheCrusader case 6000: me.SummonCreature(CreatureIds.TirionFordring, MiscData.EndSpawnLoc[0]); me.SummonCreature(CreatureIds.ArgentMage, MiscData.EndSpawnLoc[1]); - me.SummonGameObject(GameObjectIds.PortalToDalaran, MiscData.EndSpawnLoc[2], Quaternion.WAxis, 0); + me.SummonGameObject(GameObjectIds.PortalToDalaran, MiscData.EndSpawnLoc[2], Quaternion.fromEulerAnglesZYX(MiscData.EndSpawnLoc[2].GetOrientation(), 0.0f, 0.0f), 0); _updateTimer = 20 * Time.InMilliseconds; _instance.SetData(DataTypes.Event, 6005); break; diff --git a/Source/Scripts/Northrend/Nexus/EyeOfEternity/EyeOfEternity.cs b/Source/Scripts/Northrend/Nexus/EyeOfEternity/EyeOfEternity.cs index 9f8ee6b43..1a1632b0b 100644 --- a/Source/Scripts/Northrend/Nexus/EyeOfEternity/EyeOfEternity.cs +++ b/Source/Scripts/Northrend/Nexus/EyeOfEternity/EyeOfEternity.cs @@ -143,7 +143,7 @@ namespace Scripts.Northrend.Nexus.EyeOfEternity // There is no other way afaik... void SpawnGameObject(uint entry, Position pos) { - GameObject go = GameObject.CreateGameObject(entry, instance, pos, Quaternion.WAxis, 255, GameObjectState.Ready); + GameObject go = GameObject.CreateGameObject(entry, instance, pos, Quaternion.fromEulerAnglesZYX(pos.GetOrientation(), 0.0f, 0.0f), 255, GameObjectState.Ready); if (go) instance.AddToMap(go); } diff --git a/Source/Scripts/Spells/Items.cs b/Source/Scripts/Spells/Items.cs index 0c4f5b2dc..6ef5c3b7f 100644 --- a/Source/Scripts/Spells/Items.cs +++ b/Source/Scripts/Spells/Items.cs @@ -2216,7 +2216,7 @@ namespace Scripts.Spells.Items { if (target.IsDead() && !target.IsPet()) { - GetCaster().SummonGameObject(ObjectIds.ImprisonedDoomguard, target, Quaternion.WAxis, (uint)(target.GetRespawnTime() - Time.UnixTime)); + GetCaster().SummonGameObject(ObjectIds.ImprisonedDoomguard, target, Quaternion.fromEulerAnglesZYX(target.GetOrientation(), 0.0f, 0.0f), (uint)(target.GetRespawnTime() - Time.UnixTime)); target.DespawnOrUnsummon(); } } diff --git a/Source/Scripts/World/ItemScripts.cs b/Source/Scripts/World/ItemScripts.cs index b4001e319..6797efa1f 100644 --- a/Source/Scripts/World/ItemScripts.cs +++ b/Source/Scripts/World/ItemScripts.cs @@ -251,7 +251,7 @@ namespace Scripts.World float x, y, z; go.GetClosePoint(out x, out y, out z, go.GetObjectSize() / 3, 7.0f); - go.SummonGameObject(ItemScriptConst.GoHighQualityFur, go, Quaternion.WAxis, 1); + go.SummonGameObject(ItemScriptConst.GoHighQualityFur, go, Quaternion.fromEulerAnglesZYX(go.GetOrientation(), 0.0f, 0.0f), 1); TempSummon summon = player.SummonCreature(ItemScriptConst.NpcNesingwaryTrapper, x, y, z, go.GetOrientation(), TempSummonType.DeadDespawn, 1000); if (summon) { diff --git a/Source/Scripts/World/NpcSpecial.cs b/Source/Scripts/World/NpcSpecial.cs index 7cc59d501..e7ceaef24 100644 --- a/Source/Scripts/World/NpcSpecial.cs +++ b/Source/Scripts/World/NpcSpecial.cs @@ -1941,7 +1941,7 @@ namespace Scripts.World.NpcSpecial float displacement = 0.7f; for (byte i = 0; i < 4; i++) - me.SummonGameObject(GetFireworkGameObjectId(), me.GetPositionX() + (i % 2 == 0 ? displacement : -displacement), me.GetPositionY() + (i > 1 ? displacement : -displacement), me.GetPositionZ() + 4.0f, me.GetOrientation(), Quaternion.WAxis, 1); + me.SummonGameObject(GetFireworkGameObjectId(), me.GetPositionX() + (i % 2 == 0 ? displacement : -displacement), me.GetPositionY() + (i > 1 ? displacement : -displacement), me.GetPositionZ() + 4.0f, me.GetOrientation(), Quaternion.fromEulerAnglesZYX(me.GetOrientation(), 0.0f, 0.0f), 1); } else //me.CastSpell(me, GetFireworkSpell(me.GetEntry()), true);