public Item(int id, uint gbid, ItemType type) { ItemId = id; Gbid = unchecked((int)gbid); Count = 1; Type = type; AffixList = new List<Affix>(); Attributes = new GameAttributeMap(); }
/// <summary> /// Equips an item in an equipment slot /// </summary> public void EquipItem(Item item, int slot) { _equipment[slot] = item.DynamicID; item.Owner = _owner; item.SetInventoryLocation(slot, 0, 0); item.Attributes[GameAttributeB.Item_Equipped] = true; if (slot == (int)EquipmentSlotId.Off_Hand) { if (_equipment[(int)EquipmentSlotId.Main_Hand] != 0) { Item mainWeapon = GetEquipment(EquipmentSlotId.Main_Hand); GameAttributeMap other = new GameAttributeMap(); mainWeapon.Attributes[GameAttribute.Damage_Weapon_Delta_Total_MainHand] = mainWeapon.Attributes[GameAttribute.Damage_Weapon_Delta_Total]; mainWeapon.Attributes[GameAttribute.Damage_Weapon_Delta_Total_OffHand] = 0; item.Attributes[GameAttribute.Damage_Weapon_Delta_Total_OffHand] = item.Attributes[GameAttribute.Damage_Weapon_Delta_Total]; item.Attributes[GameAttribute.Damage_Weapon_Delta_Total_MainHand] = 0; mainWeapon.Attributes[GameAttribute.Damage_Weapon_Min_Total_MainHand] = mainWeapon.Attributes[GameAttribute.Damage_Weapon_Min_Total]; mainWeapon.Attributes[GameAttribute.Damage_Weapon_Min_Total_OffHand] = 0; item.Attributes[GameAttribute.Damage_Weapon_Min_Total_OffHand] = item.Attributes[GameAttribute.Damage_Weapon_Min_Total]; item.Attributes[GameAttribute.Damage_Weapon_Min_Total_MainHand] = 0; other.SendChangedMessage((mainWeapon.Owner as Player).InGameClient, mainWeapon.DynamicID); } } else if (slot == (int)EquipmentSlotId.Main_Hand) { if (_equipment[(int)EquipmentSlotId.Off_Hand] != 0) { Item offHandWeapon = GetEquipment(EquipmentSlotId.Off_Hand); item.Attributes[GameAttribute.Damage_Weapon_Delta_Total_MainHand] = item.Attributes[GameAttribute.Damage_Weapon_Delta_Total]; offHandWeapon.Attributes[GameAttribute.Damage_Weapon_Delta_Total_OffHand] = offHandWeapon.Attributes[GameAttribute.Damage_Weapon_Delta_Total]; item.Attributes[GameAttribute.Damage_Weapon_Min_Total_MainHand] = item.Attributes[GameAttribute.Damage_Weapon_Min_Total]; offHandWeapon.Attributes[GameAttribute.Damage_Weapon_Min_Total_OffHand] = offHandWeapon.Attributes[GameAttribute.Damage_Weapon_Min_Total]; offHandWeapon.Attributes[GameAttribute.Held_In_OffHand] = true; item.Attributes[GameAttribute.Damage_Weapon_Min_Total_OffHand] = 0; item.Attributes[GameAttribute.Damage_Weapon_Delta_Total_OffHand] = 0; offHandWeapon.Attributes[GameAttribute.Damage_Weapon_Delta_Total_MainHand] = 0; offHandWeapon.Attributes[GameAttribute.Damage_Weapon_Min_Total_MainHand] = 0; offHandWeapon.Attributes.SendChangedMessage((offHandWeapon.Owner as Player).InGameClient, offHandWeapon.DynamicID); } } if (item.Owner is Player) { item.Attributes.SendChangedMessage((item.Owner as Player).InGameClient, item.DynamicID); // flag item as equipped, so as not to shown in red color } _equippedMap = null; // compute stats (depends on items) AttributeMath.ComputeStats(_owner, GetEquippedMap()); }
public static Item CreateGold(Player player, int amount) { var item = Cook(player, "Gold1", 0x00000178, ItemType.Gold); item.Attributes[GameAttribute.Gold] = amount; GameAttributeMap map = new GameAttributeMap(); map[GameAttribute.Gold] = amount; map.SendMessage(player.InGameClient, item.DynamicID); return item; }
// FIXME: Hardcoded hell. /komiga public void Die(Mooege.Core.GS.Player.Player player) { var killAni = new int[]{ 0x2cd7, 0x2cd4, 0x01b378, 0x2cdc, 0x02f2, 0x2ccf, 0x2cd0, 0x2cd1, 0x2cd2, 0x2cd3, 0x2cd5, 0x01b144, 0x2cd6, 0x2cd8, 0x2cda, 0x2cd9 }; this.World.BroadcastIfRevealed(new PlayEffectMessage() { ActorID = this.DynamicID, Field1 = 0x0, Field2 = 0x2, }, this); this.World.BroadcastIfRevealed(new PlayEffectMessage() { ActorID = this.DynamicID, Field1 = 0xc, }, this); this.World.BroadcastIfRevealed(new PlayHitEffectMessage() { ActorID = this.DynamicID, HitDealer = player.DynamicID, Field2 = 0x2, Field3 = false, }, this); this.World.BroadcastIfRevealed(new FloatingNumberMessage() { ActorID = this.DynamicID, Number = 9001.0f, Type = FloatingNumberMessage.FloatType.White, }, this); this.World.BroadcastIfRevealed(new ANNDataMessage(Opcodes.ANNDataMessage13) { ActorID = this.DynamicID }, this); this.World.BroadcastIfRevealed(new PlayAnimationMessage() { ActorID = this.DynamicID, Field1 = 0xb, Field2 = 0, tAnim = new PlayAnimationMessageSpec[1] { new PlayAnimationMessageSpec() { Field0 = 0x2, Field1 = killAni[RandomHelper.Next(killAni.Length)], Field2 = 0x0, Field3 = 1f } } }, this); this.World.BroadcastIfRevealed(new ANNDataMessage(Opcodes.ANNDataMessage24) { ActorID = this.DynamicID, }, this); GameAttributeMap attribs = new GameAttributeMap(); attribs[GameAttribute.Hitpoints_Cur] = 0f; attribs[GameAttribute.Could_Have_Ragdolled] = true; attribs[GameAttribute.Deleted_On_Server] = true; foreach (var msg in attribs.GetMessageList(this.DynamicID)) this.World.BroadcastIfRevealed(msg, this); this.World.BroadcastIfRevealed(new PlayEffectMessage() { ActorID = this.DynamicID, Field1 = 0xc, }, this); this.World.BroadcastIfRevealed(new PlayEffectMessage() { ActorID = this.DynamicID, Field1 = 0x37, }, this); this.World.BroadcastIfRevealed(new PlayHitEffectMessage() { ActorID = this.DynamicID, HitDealer = player.DynamicID, Field2 = 0x2, Field3 = false, }, this); this.World.SpawnRandomDrop(player, this.Position); this.World.SpawnGold(player, this.Position); this.Destroy(); }
// TODO: The inventory's gold item should not be created here. /komiga public void PickUpGold(uint itemID) { Item collectedItem = _owner.GroundItems[itemID]; if (_goldItem == null) { ItemTypeGenerator itemGenerator = new ItemTypeGenerator(_owner.InGameClient); _goldItem = itemGenerator.CreateItem("Gold1", 0x00000178, ItemType.Gold); _goldItem.Count = collectedItem.Count; _goldItem.Owner = _owner; _goldItem.SetInventoryLocation(18, 0, 0); // Equipment slot 18 ==> Gold _goldItem.Reveal(_owner); } else { _goldItem.Count += collectedItem.Count; } GameAttributeMap attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = _goldItem.Count; attributes.SendMessage(_owner.InGameClient, _goldItem.DynamicID); }
/// <summary> /// Transfers an amount from one stack to another /// </summary> public void OnInventoryStackTransferMessage(InventoryStackTransferMessage msg) { Item itemFrom = _owner.World.GetItem(msg.FromID); Item itemTo = _owner.World.GetItem(msg.ToID); itemFrom.Attributes[GameAttribute.ItemStackQuantityLo] -= (int)msg.Amount; itemTo.Attributes[GameAttribute.ItemStackQuantityLo] -= (int)msg.Amount; // TODO: This needs to change the attribute on the item itself. /komiga // Update source GameAttributeMap attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = itemFrom.Attributes[GameAttribute.ItemStackQuantityLo]; attributes.SendMessage(_owner.InGameClient, itemFrom.DynamicID); // TODO: This needs to change the attribute on the item itself. /komiga // Update target attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = itemTo.Attributes[GameAttribute.ItemStackQuantityLo]; attributes.SendMessage(_owner.InGameClient, itemTo.DynamicID); }
public void Handle(GameClient client) { Mooege.Core.GS.Universe.Hero hero = client.Player.Hero; switch (this.Id) { case 0x0030: // Sent with DwordDataMessage(0x0125, Value:0) and SimpleMessage(0x0125) { #region hardcoded1 #region HirelingInfo client.SendMessage(new HirelingInfoUpdateMessage() { Id = 0x009D, Field0 = 0x00000001, Field1 = false, Field2 = -1, Field3 = 0x00000000, }); client.SendMessage(new HirelingInfoUpdateMessage() { Id = 0x009D, Field0 = 0x00000002, Field1 = false, Field2 = -1, Field3 = 0x00000000, }); client.SendMessage(new HirelingInfoUpdateMessage() { Id = 0x009D, Field0 = 0x00000003, Field1 = false, Field2 = -1, Field3 = 0x00000000, }); #endregion #region Player Attribute Values GameAttributeMap attributes = new GameAttributeMap(); attributes[GameAttribute.Banter_Cooldown, 0xFFFFF] = 0x000007C9; attributes[GameAttribute.Buff_Active, 0x20CBE] = true; attributes[GameAttribute.Buff_Active, 0x33C40] = false; attributes[GameAttribute.Immobolize] = false; attributes[GameAttribute.Untargetable] = false; attributes[GameAttribute.CantStartDisplayedPowers] = false; attributes[GameAttribute.Buff_Icon_Start_Tick0, 0x20CBE] = 0xC1; attributes[GameAttribute.Disabled] = false; attributes[GameAttribute.Hidden] = false; attributes[GameAttribute.Buff_Icon_Count0, 0x33C40] = 0; attributes[GameAttribute.Buff_Icon_End_Tick0, 0x20CBE] = 0x7C9; attributes[GameAttribute.Loading] = false; attributes[GameAttribute.Buff_Icon_End_Tick0, 0x33C40] = 0; attributes[GameAttribute.Invulnerable] = false; attributes[GameAttribute.Buff_Icon_Count0, 0x20CBE] = 1; attributes[GameAttribute.Buff_Icon_Start_Tick0, 0x33C40] = 0; attributes.SendMessage(client, hero.DynamicId); #endregion client.SendMessage(new ACDCollFlagsMessage() { Id = 0x00A6, Field0 = hero.DynamicId, Field1 = 0x00000008, }); client.SendMessage(new DWordDataMessage() { Id = 0x0089, Field0 = 0x000000C1, }); #endregion client.FlushOutgoingBuffer(); #region hardcoded2 client.SendMessage(new TrickleMessage() { Id = 0x0042, Field0 = hero.DynamicId, Field1 = client.Player.Hero.ClassSNO, Field2 = new WorldPlace() { Field0 = new Vector3D() { X = 3143.75f, Y = 2828.75f, Z = 59.07559f, }, Field1 = client.Player.Hero.WorldId, }, Field3 = 0x00000000, Field4 = 0x00026186, Field5 = 1f, Field6 = 0x00000001, Field7 = 0x00000024, Field10 = unchecked((int)0x8DFA5D13), Field12 = 0x0000F063, }); client.SendMessage(new DWordDataMessage() { Id = 0x0089, Field0 = 0x000000D1, }); #endregion client.FlushOutgoingBuffer(); } break; case 0x0028: // Logout complete (sent when delay timer expires on client side) if (client.IsLoggingOut) { client.SendMessageNow(new QuitGameMessage() { Id = 0x0003, // Field0 - quit reason? // 0 - logout // 1 - kicked by party leader // 2 - disconnected due to client-server (version?) missmatch Field0 = 0, }); } break; default: throw new NotImplementedException(); } }
public void SpawnMob(GameClient client, int mobId) // this shoudn't even rely on client or it's position though i know this is just a hack atm ;) /raist. { int nId = mobId; if (client.Player.Hero.Position == null) return; if (client.ObjectIdsSpawned == null) { client.ObjectIdsSpawned = new List<int>(); client.ObjectIdsSpawned.Add(client.ObjectId - 100); client.ObjectIdsSpawned.Add(client.ObjectId); } client.ObjectId++; client.ObjectIdsSpawned.Add(client.ObjectId); #region ACDEnterKnown Hittable Zombie client.SendMessage(new ACDEnterKnownMessage() { Id = 0x003B, Field0 = client.ObjectId, Field1 = nId, Field2 = 0x8, Field3 = 0x0, Field4 = new WorldLocationMessageData() { Field0 = 1.35f, Field1 = new PRTransform() { Field0 = new Quaternion() { Amount = 0.768145f, Axis = new Vector3D() { X = 0f, Y = 0f, Z = -0.640276f, }, }, ReferencePoint = new Vector3D() { X = client.Player.Hero.Position.X + 5, Y = client.Player.Hero.Position.Y + 5, Z = client.Player.Hero.Position.Z, }, }, Field2 = 0x772E0000, }, Field5 = null, Field6 = new GBHandle() { Field0 = 1, Field1 = 1, }, Field7 = 0x00000001, Field8 = nId, Field9 = 0x0, Field10 = 0x0, Field11 = 0x0, Field12 = 0x0, Field13 = 0x0 }); client.SendMessage(new AffixMessage() { Id = 0x48, Field0 = client.ObjectId, Field1 = 0x1, aAffixGBIDs = new int[0] }); client.SendMessage(new AffixMessage() { Id = 0x48, Field0 = client.ObjectId, Field1 = 0x2, aAffixGBIDs = new int[0] }); client.SendMessage(new ACDCollFlagsMessage { Id = 0xa6, Field0 = client.ObjectId, Field1 = 0x1 }); GameAttributeMap attribs = new GameAttributeMap(); attribs[GameAttribute.Untargetable] = false; attribs[GameAttribute.Uninterruptible] = true; attribs[GameAttribute.Buff_Visual_Effect, 1048575] = true; attribs[GameAttribute.Buff_Icon_Count0, 30582] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30286] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30285] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30284] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30283] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30290] = 1; attribs[GameAttribute.Buff_Icon_Count0, 79486] = 1; attribs[GameAttribute.Buff_Active, 30286] = true; attribs[GameAttribute.Buff_Active, 30285] = true; attribs[GameAttribute.Buff_Active, 30284] = true; attribs[GameAttribute.Buff_Active, 30283] = true; attribs[GameAttribute.Buff_Active, 30290] = true; attribs[GameAttribute.Hitpoints_Max_Total] = 4.546875f; attribs[GameAttribute.Buff_Active, 79486] = true; attribs[GameAttribute.Hitpoints_Max] = 4.546875f; attribs[GameAttribute.Hitpoints_Total_From_Level] = 0f; attribs[GameAttribute.Hitpoints_Cur] = 4.546875f; attribs[GameAttribute.Invulnerable] = true; attribs[GameAttribute.Buff_Active, 30582] = true; attribs[GameAttribute.TeamID] = 10; attribs[GameAttribute.Level] = 1; attribs.SendMessage(client, client.ObjectId); client.SendMessage(new ACDGroupMessage { Id = 0xb8, Field0 = client.ObjectId, Field1 = unchecked((int)0xb59b8de4), Field2 = unchecked((int)0xffffffff) }); client.SendMessage(new ANNDataMessage { Id = 0x3e, Field0 = client.ObjectId }); client.SendMessage(new ACDTranslateFacingMessage { Id = 0x70, Field0 = client.ObjectId, Field1 = (float)(RandomHelper.NextDouble() * 2.0 * Math.PI), Field2 = false }); client.SendMessage(new SetIdleAnimationMessage { Id = 0xa5, Field0 = client.ObjectId, Field1 = 0x11150 }); client.SendMessage(new SNONameDataMessage { Id = 0xd3, Field0 = new SNOName { Field0 = 0x1, Field1 = nId } }); #endregion client.PacketId += 30 * 2; client.SendMessage(new DWordDataMessage() { Id = 0x89, Field0 = client.PacketId, }); client.Tick += 20; client.SendMessage(new EndOfTickMessage() { Id = 0x008D, Field0 = client.Tick - 20, Field1 = client.Tick }); }
public GameAttributeMap AddMap(GameAttributeMap map) { Dictionary<KeyId, GameAttributeValue> mapValues = map._attributeValues; if (mapValues.Count == 0) { return this; } var e = mapValues.GetEnumerator(); while (e.MoveNext()) { if (_attributeValues.ContainsKey(e.Current.Key)) { if (mapValues[e.Current.Key].ValueF != 0f) { // guess it's float _attributeValues[e.Current.Key] = new GameAttributeValue(_attributeValues[e.Current.Key].ValueF + mapValues[e.Current.Key].ValueF); } else if (mapValues[e.Current.Key].Value != 0) { // guess it's int or true boolean _attributeValues[e.Current.Key] = new GameAttributeValue(_attributeValues[e.Current.Key].Value + mapValues[e.Current.Key].Value); } // 0 in both fields means nothing to add } else { _attributeValues.Add(e.Current.Key, e.Current.Value); } } return this; }
public GameAttributeMap CombineMap(GameAttributeMap map) { Dictionary<KeyId, GameAttributeValue> mapValues = map._attributeValues; if (mapValues.Count == 0) { return this; } var e = mapValues.GetEnumerator(); while (e.MoveNext()) { if (_attributeValues.ContainsKey(e.Current.Key)) { _attributeValues[e.Current.Key] = e.Current.Value; } else { _attributeValues.Add(e.Current.Key, e.Current.Value); } _changedAttributes.Add(e.Current.Key); } return this; }
public void PickUpGold(int itemId) { Item collectedItem = _owner.InGameClient.items[itemId]; Item goldItem; if (_goldObjectId == 0) { Logger.Debug("creating gold item"); ItemTypeGenerator itemGenerator = new ItemTypeGenerator(_owner.InGameClient); goldItem = itemGenerator.CreateItem("Gold1", 0x00000178, ItemType.Gold); _goldObjectId = goldItem.ItemId; goldItem.Count = collectedItem.Count; goldItem.RevealInInventory(_owner, 0, 0, 18); // Equipment slot 18 ==> Gold } else { goldItem = _owner.InGameClient.items[_goldObjectId]; goldItem.Count += collectedItem.Count; } GameAttributeMap attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = goldItem.Count; attributes.SendMessage(_owner.InGameClient, _goldObjectId); }
/// <summary> /// Transfers an amount from one stack to another /// </summary> public void OnInventoryStackTransferMessage(InventoryStackTransferMessage msg) { _owner.InGameClient.items[msg.Field0].Count = (_owner.InGameClient.items[msg.Field0].Count) - ((int)msg.Field2); _owner.InGameClient.items[msg.Field1].Count = _owner.InGameClient.items[msg.Field1].Count + (int)msg.Field2; // Update source GameAttributeMap attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = _owner.InGameClient.items[msg.Field0].Count; attributes.SendMessage(_owner.InGameClient, msg.Field0); // Update target attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = _owner.InGameClient.items[msg.Field1].Count; attributes.SendMessage(_owner.InGameClient, msg.Field1); _owner.InGameClient.PacketId += 10 * 2; _owner.InGameClient.SendMessage(new DWordDataMessage() { Id = 0x89, Field0 = _owner.InGameClient.PacketId, }); }
public static GameAttributeMap ComputeEquipment(Player player, List<GameAttributeMap> equipped) { // TODO: add non-basic stats of items, use AddMap method, figure out exception for offHand weapon GameAttributeMap map = new GameAttributeMap(); if (equipped.Count != 0) { foreach (GameAttributeMap m in equipped) { map.AddMap(m); /* // compute weapon to temp map for (int damageType = 0; damageType < 7; damageType++) { map[GameAttribute.Damage_Weapon_Min_Total, damageType] += m[GameAttribute.Damage_Weapon_Min_Total, damageType]; map[GameAttribute.Damage_Weapon_Max_Total, damageType] += m[GameAttribute.Damage_Weapon_Max_Total, damageType]; map[GameAttribute.Damage_Weapon_Delta_Total, damageType] += (m[GameAttribute.Damage_Weapon_Max_Total, damageType] - m[GameAttribute.Damage_Weapon_Min_Total, damageType]); } map[GameAttribute.Damage_Weapon_Min_Total_All] += m[GameAttribute.Damage_Weapon_Min_Total_All]; map[GameAttribute.Damage_Weapon_Delta_Total_All] += m[GameAttribute.Damage_Weapon_Delta_Total_All]; map[GameAttribute.Attacks_Per_Second_Item_Total] += m[GameAttribute.Attacks_Per_Second_Item_Total]; // dual wield map[GameAttribute.Damage_Weapon_Delta_Total_MainHand] += m[GameAttribute.Damage_Weapon_Delta_Total_MainHand]; map[GameAttribute.Damage_Weapon_Min_Total_MainHand] += m[GameAttribute.Damage_Weapon_Min_Total_MainHand]; map[GameAttribute.Damage_Weapon_Delta_Total_OffHand] += m[GameAttribute.Damage_Weapon_Delta_Total_OffHand]; map[GameAttribute.Damage_Weapon_Min_Total_OffHand] += m[GameAttribute.Damage_Weapon_Min_Total_OffHand]; // compute armor to temp map map[GameAttribute.Armor_Item_Total] += m[GameAttribute.Armor_Item_Total]; // compute block to temp map map[GameAttribute.Block_Amount_Item_Delta] += m[GameAttribute.Block_Amount_Item_Delta]; map[GameAttribute.Block_Amount_Item_Min] += m[GameAttribute.Block_Amount_Item_Min]; map[GameAttribute.Block_Chance_Item_Total] += m[GameAttribute.Block_Chance_Item_Total]; */ } } return map; }
public static void ComputeStats(Player player, GameAttributeMap equippedMap, bool initialSetting = false) { // player.Attributes.CombineMap(equippedMap); // for all other attributes - not possible (doubling value of map in few instances) GameAttributeMap attribs = new GameAttributeMap(); // basic stats // attribs[GameAttribute.Attack_Bonus] = 0; // attribs[GameAttribute.Attack_Bonus_Percent] = 0; // attribs[GameAttribute.Attack_Reduction_Percent] = 0; // attribs[GameAttribute.Stats_All_Bonus] = 0f; attribs[GameAttribute.Attack] = (float)Math.Floor(((player.InitialAttack + equippedMap[GameAttribute.Stats_All_Bonus] + equippedMap[GameAttribute.Attack] + player.Attributes[GameAttribute.Attack_Bonus] + equippedMap[GameAttribute.Attack_Bonus]) * (1 + player.Attributes[GameAttribute.Attack_Bonus_Percent] + equippedMap[GameAttribute.Attack_Bonus_Percent])) * (1 - player.Attributes[GameAttribute.Attack_Reduction_Percent] - equippedMap[GameAttribute.Attack_Reduction_Percent])); // ((Attack.Agg + Stats_All_Bonus + Attack_Bonus) * (1 + Attack_Bonus_Percent)) * (1 - Attack_Reduction_Percent) // bonus + reduction can come from outside too (skills/monsters) attribs[GameAttribute.Defense] = (float)Math.Floor(((player.InitialDefense + equippedMap[GameAttribute.Stats_All_Bonus] + equippedMap[GameAttribute.Defense] + player.Attributes[GameAttribute.Defense_Bonus] + equippedMap[GameAttribute.Defense_Bonus]) * (1 + player.Attributes[GameAttribute.Defense_Bonus_Percent] + equippedMap[GameAttribute.Defense_Bonus_Percent])) * (1 - player.Attributes[GameAttribute.Defense_Reduction_Percent] - equippedMap[GameAttribute.Defense_Reduction_Percent])); attribs[GameAttribute.Precision] = (float)Math.Floor(((player.InitialPrecision + equippedMap[GameAttribute.Stats_All_Bonus] + equippedMap[GameAttribute.Precision] + player.Attributes[GameAttribute.Precision_Bonus] + equippedMap[GameAttribute.Precision_Bonus]) * (1 + player.Attributes[GameAttribute.Precision_Bonus_Percent] + equippedMap[GameAttribute.Precision_Bonus_Percent])) * (1 - player.Attributes[GameAttribute.Precision_Reduction_Percent] - equippedMap[GameAttribute.Precision_Reduction_Percent])); attribs[GameAttribute.Vitality] = (float)Math.Floor(((player.InitialVitality + equippedMap[GameAttribute.Stats_All_Bonus] + equippedMap[GameAttribute.Vitality] + player.Attributes[GameAttribute.Vitality_Bonus] + equippedMap[GameAttribute.Vitality_Bonus]) * (1 + player.Attributes[GameAttribute.Vitality_Bonus_Percent] + equippedMap[GameAttribute.Vitality_Bonus_Percent])) * (1 - player.Attributes[GameAttribute.Vitality_Reduction_Percent] - equippedMap[GameAttribute.Vitality_Reduction_Percent])); // armor attribs[GameAttribute.Armor] = 0f; // class's basic armor w/o ANY items TODO: find out // attribs[GameAttribute.Armor_Bonus_Percent] = 0; // from skills attribs[GameAttribute.Armor_Total] = (float)Math.Floor((player.Attributes[GameAttribute.Armor] + equippedMap[GameAttribute.Armor_Item_Total] * (equippedMap[GameAttribute.Armor_Bonus_Percent] + 1)));// FLOOR((Armor + Armor_Item_Total) * (Armor_Bonus_Percent + 1)) // hitpoints attribs[GameAttribute.Hitpoints_Total_From_Level] = (player.Attributes[GameAttribute.Level] - 1) * player.Attributes[GameAttribute.Hitpoints_Factor_Level]; attribs[GameAttribute.Hitpoints_Total_From_Vitality] = attribs[GameAttribute.Vitality] * player.Attributes[GameAttribute.Hitpoints_Factor_Vitality]; attribs[GameAttribute.Hitpoints_Max_Total] = (player.Attributes[GameAttribute.Hitpoints_Max] + attribs[GameAttribute.Hitpoints_Total_From_Level] + attribs[GameAttribute.Hitpoints_Total_From_Vitality] + player.Attributes[GameAttribute.Hitpoints_Max_Bonus] + equippedMap[GameAttribute.Hitpoints_Max_Bonus]) * (1 + player.Attributes[GameAttribute.Hitpoints_Max_Percent_Bonus] + equippedMap[GameAttribute.Hitpoints_Max_Percent_Bonus_Item]); if (initialSetting) { attribs[GameAttribute.Hitpoints_Cur] = attribs[GameAttribute.Hitpoints_Max_Total]; // heal to full } // block attribs[GameAttribute.Block_Amount_Bonus_Percent] = player.Attributes[GameAttribute.Block_Amount_Bonus_Percent] + equippedMap[GameAttribute.Block_Amount_Bonus_Percent]; // equipment OR player attribs[GameAttribute.Block_Amount] = player.Attributes[GameAttribute.Block_Amount]; // TODO: can it be on equipment too? attribs[GameAttribute.Block_Amount_Total_Min] = (player.Attributes[GameAttribute.Block_Amount] + equippedMap[GameAttribute.Block_Amount_Item_Min]) * (1 + attribs[GameAttribute.Block_Amount_Bonus_Percent]) ; // (Block_Amount + Block_Amount_Item_Min + Block_Amount_Item_Bonus) * (1 + Block_Amount_Bonus_Percent) attribs[GameAttribute.Block_Amount_Total_Max] = (player.Attributes[GameAttribute.Block_Amount] + equippedMap[GameAttribute.Block_Amount_Item_Min] + equippedMap[GameAttribute.Block_Amount_Item_Delta] + equippedMap[GameAttribute.Block_Amount_Item_Bonus]) * (1 + attribs[GameAttribute.Block_Amount_Bonus_Percent]); // (Block_Amount + Block_Amount_Item_Min + Block_Amount_Item_Delta + Block_Amount_Item_Bonus) * (1 + Block_Amount_Bonus_Percent) attribs[GameAttribute.Block_Chance] = player.Attributes[GameAttribute.Block_Chance]; // TODO: can it be on equipment too? attribs[GameAttribute.Block_Chance_Total] = attribs[GameAttribute.Block_Chance] + equippedMap[GameAttribute.Block_Chance_Item_Total];//Block_Chance + Block_Chance_Item_Total // compute resource ComputeResourceRegen(player, player.ResourceID); // compute damage, TODO: dual wield, total values for (int i = 0; i < 7; i++) { attribs[GameAttribute.Damage_Min, i] = player.Attributes[GameAttribute.Damage_Min, i]; // from player attribs[GameAttribute.Damage_Type_Percent_Bonus, i] = 0;// elemental attribs[GameAttribute.Damage_Bonus_Min, i] = player.Attributes[GameAttribute.Damage_Bonus_Min, i] + equippedMap[GameAttribute.Damage_Bonus_Min, i]; // from player and equipment attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, i] = equippedMap[GameAttribute.Damage_Weapon_Min_Total, i]; attribs[GameAttribute.Damage_Min_Subtotal, i] = attribs[GameAttribute.Damage_Min, i] + attribs[GameAttribute.Damage_Bonus_Min, i] + attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, i]; //elemental Damage_Min + Damage_Bonus_Min + Damage_Weapon_Min_Total_CurrentHand attribs[GameAttribute.Damage_Min_Total, i] = attribs[GameAttribute.Damage_Min_Subtotal, i] + attribs[GameAttribute.Damage_Type_Percent_Bonus, i] * attribs[GameAttribute.Damage_Min_Subtotal, i]; //elemental Damage_Min_Subtotal + Damage_Type_Percent_Bonus * Damage_Min_Subtotal#Physical attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, i] = equippedMap[GameAttribute.Damage_Weapon_Delta_Total, i]; // elemental attribs[GameAttribute.Damage_Delta, i] = equippedMap[GameAttribute.Damage_Delta, i]; // elemental , from e.g. rings 2-4 dmg? attribs[GameAttribute.Damage_Delta_Total, i] = (float)Math.Max(attribs[GameAttribute.Damage_Delta, i] - attribs[GameAttribute.Damage_Bonus_Min, i] + attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, i], 0); // elemental Max(Damage_Delta - Damage_Bonus_Min + Damage_Weapon_Delta_Total_CurrentHand, 0) /* attribs[GameAttribute.Damage_Weapon_Delta_Total_MainHand, i] = equippedMap[GameAttribute.Damage_Weapon_Delta_Total_MainHand]; // elemental attribs[GameAttribute.Damage_Weapon_Delta_Total_OffHand, i] = equippedMap[GameAttribute.Damage_Weapon_Delta_Total_OffHand]; // elemental attribs[GameAttribute.Damage_Weapon_Min_Total_MainHand, i] = equippedMap[GameAttribute.Damage_Weapon_Min_Total_MainHand]; attribs[GameAttribute.Damage_Weapon_Min_Total_OffHand, i] = equippedMap[GameAttribute.Damage_Weapon_Min_Total_OffHand]; */ } // TODO: critical /* attribs[GameAttribute.Crit_Percent_Base] = 0f; attribs[GameAttribute.Crit_Percent_Cap] = 0f; attribs[GameAttribute.Crit_Percent_Bonus_Capped] = 0f; attribs[GameAttribute.Crit_Percent_Bonus_Uncapped] = 0f; */ // w/ criticals one item 43.y DPS, second weapon sets to 2.x DPS, offhand needs to calculate ALL, not reduction? or _OffHand/_MainHand needs to be computed? // w/o criticals 33.6 DPS, 1.81 DPS // compute attacks per second attribs[GameAttribute.Attacks_Per_Second_Percent] = player.Attributes[GameAttribute.Attacks_Per_Second_Percent]; // player attribs[GameAttribute.Attacks_Per_Second_Bonus] = player.Attributes[GameAttribute.Attacks_Per_Second_Bonus]; // player attribs[GameAttribute.Attacks_Per_Second] = player.Attributes[GameAttribute.Attacks_Per_Second]; // ??? basic attack w/o items? // TODO: dual wield, (critical dmg with chance should compute client, current effects should be percent + bonus from player) attribs[GameAttribute.Attacks_Per_Second_Item_CurrentHand] = equippedMap[GameAttribute.Attacks_Per_Second_Item_Total]; attribs[GameAttribute.Attacks_Per_Second_Total] = (((attribs[GameAttribute.Attacks_Per_Second_Item_CurrentHand] > 0) ? attribs[GameAttribute.Attacks_Per_Second_Item_CurrentHand] : attribs[GameAttribute.Attacks_Per_Second]) + attribs[GameAttribute.Attacks_Per_Second_Bonus] + equippedMap[GameAttribute.Attacks_Per_Second_Item_Bonus]) * (float)Math.Max(0.1, (1 + attribs[GameAttribute.Attacks_Per_Second_Percent])); // (((Attacks_Per_Second_Item_CurrentHand > 0.0) ? Attacks_Per_Second_Item_CurrentHand : Attacks_Per_Second) + Attacks_Per_Second_Bonus + Attacks_Per_Second_Item_Bonus) * Max(0.1, (1 + Attacks_Per_Second_Percent)) // store to attributes player.Attributes.CombineMap(attribs); }
//uncomment this constructor to show all portals in the world, even those that will crash the client on entry //useful for determining which actor the portal is. //public Portal() //{ // TargetPos = new Vector3D(); //} public void Reveal(Hero hero) { if (PortalMessage != null && ActorRef != null && TargetPos!=null) //targetpos!=null in this case is used to detect if the portal has been completely initialized to have a target //if it doesn't have one, it won't be displayed - otherwise the client would crash from this. { //Logger.Info("Revealing portal: " + PortalMessage.AsText()); ActorRef.Reveal(hero); hero.InGameClient.SendMessage(new AffixMessage() { Id = 0x48, Field0 = ActorRef.DynamicId, Field1 = 1, aAffixGBIDs = new int[0] }); hero.InGameClient.SendMessage(new AffixMessage() { Id = 0x48, Field0 = ActorRef.DynamicId, Field1 = 2, aAffixGBIDs = new int[0] }); hero.InGameClient.SendMessage(PortalMessage); hero.InGameClient.SendMessage(new ACDCollFlagsMessage() { Id = 0x00A6, Field0 = ActorRef.DynamicId, Field1 = 0x00000001, }); GameAttributeMap attributes = new GameAttributeMap(); attributes[GameAttribute.MinimapActive] = true; attributes[GameAttribute.Hitpoints_Max_Total] = 1f; attributes[GameAttribute.Hitpoints_Max] = 0.0009994507f; attributes[GameAttribute.Hitpoints_Total_From_Level] = 3.051758E-05f; attributes[GameAttribute.Hitpoints_Cur] = 0.0009994507f; attributes[GameAttribute.TeamID] = 1; attributes[GameAttribute.Level] = 1; attributes.SendMessage(hero.InGameClient, ActorRef.DynamicId); hero.InGameClient.SendMessage(new ACDGroupMessage() { Id = 0x00B8, Field0 = ActorRef.DynamicId, Field1 = -1, Field2 = -1, }); hero.InGameClient.SendMessage(new ANNDataMessage() { Id = 0x003E, Field0 = ActorRef.DynamicId, }); hero.InGameClient.SendMessage(new ACDTranslateFacingMessage() { Id = 0x0070, Field0 = ActorRef.DynamicId, Field1 = 0f, Field2 = false, }); } hero.InGameClient.FlushOutgoingBuffer(); }
/// <summary> /// Greets the player and sends the client initial data it needs to get-ingame. /// </summary> /// <param name="message"></param> public void Greet(JoinBNetGameMessage message) { Logger.Debug("Greeting player with toon-name: {0} and positioning him to {1}", this.Hero.Properties.Name, Hero.Position); // send versions message Client.SendMessageNow(new VersionsMessage(message.SNOPackHash)); // send connection established message. Client.SendMessage(new ConnectionEstablishedMessage() { Field0 = 0x00000000, Field1 = 0x4BB91A16, SNOPackHash = message.SNOPackHash, }); // game setup message. Client.SendMessage(new GameSetupMessage() { Field0 = 0x00000077, }); Client.SendMessage(new SavePointInfoMessage() { snoLevelArea = -1, }); Client.SendMessage(new HearthPortalInfoMessage() { snoLevelArea = -1, Field1 = -1, }); // transition player to act so client can load act related data? /raist Client.SendMessage(new ActTransitionMessage() { Field0 = 0x00000000, Field1 = true, }); //reveal world to the toon if (Hero.CurrentWorld != null) Hero.CurrentWorld.Reveal(this.Hero); // send newplayermessage. Client.SendMessage(new NewPlayerMessage() { Id = 0x0031, Field0 = 0x00000000, //Party frame (0x00000000 hide, 0x00000001 show) Field1 = "", //Owner name? ToonName = this.Hero.Properties.Name, Field3 = 0x00000002, //party frame class Field4 = 0x00000004, //party frame level snoActorPortrait = this.Hero.ClassSNO, //party frame portrait Field6 = 0x00000001, Field7 = this.Hero.GetStateData(), Field8 = false, //announce party join Field9 = 0x00000001, Field10 = this.Hero.Id, }); // reveal the hero Hero.Reveal(this.Hero); Client.SendMessage(new ACDCollFlagsMessage() { Field0 = this.Hero.Id, Field1 = 0x00000000, }); GameAttributeMap attribs = new GameAttributeMap(); attribs[GameAttribute.SkillKit] = Client.Player.Hero.SkillKit; attribs[GameAttribute.Buff_Active, 0x33C40] = true; attribs[GameAttribute.Skill, 0x7545] = 1; attribs[GameAttribute.Skill_Total, 0x7545] = 1; attribs[GameAttribute.Resistance_Total, 0x226] = 0.5f; attribs[GameAttribute.Resistance, 0x226] = 0.5f; attribs[GameAttribute.Immobolize] = true; attribs[GameAttribute.Untargetable] = true; attribs[GameAttribute.Skill_Total, 0x76B7] = 1; attribs[GameAttribute.Skill, 0x76B7] = 1; attribs[GameAttribute.Skill, 0x6DF] = 1; attribs[GameAttribute.Buff_Active, 0xCE11] = true; attribs[GameAttribute.CantStartDisplayedPowers] = true; attribs[GameAttribute.Skill_Total, 0x216FA] = 1; attribs[GameAttribute.Skill, 0x176C4] = 1; //-- attribs[GameAttribute.Skill, 0x216FA] = 1; attribs[GameAttribute.Skill_Total, 0x176C4] = 1; attribs[GameAttribute.Skill_Total, 0x6DF] = 1; attribs[GameAttribute.Resistance, 0xDE] = 0.5f; attribs[GameAttribute.Resistance_Total, 0xDE] = 0.5f; attribs[GameAttribute.Get_Hit_Recovery] = 6f; attribs[GameAttribute.Get_Hit_Recovery_Per_Level] = 1f; attribs[GameAttribute.Get_Hit_Recovery_Base] = 5f; attribs[GameAttribute.Skill, 0x7780] = 1; attribs[GameAttribute.Get_Hit_Max] = 60f; attribs[GameAttribute.Skill_Total, 0x7780] = 1; attribs[GameAttribute.Get_Hit_Max_Per_Level] = 10f; attribs[GameAttribute.Get_Hit_Max_Base] = 50f; attribs[GameAttribute.Resistance_Total, 0] = 3.051758E-05f; // im pretty sure key = 0 doesnt do anything since the lookup is (attributeId | (key << 12)), maybe this is some base resistance? /cm attribs[GameAttribute.Resistance_Total, 1] = 3.051758E-05f; //-- attribs[GameAttribute.Resistance_Total, 2] = 3.051758E-05f; attribs[GameAttribute.Resistance_Total, 3] = 3.051758E-05f; attribs[GameAttribute.Resistance_Total, 4] = 3.051758E-05f; attribs[GameAttribute.Resistance_Total, 5] = 3.051758E-05f; attribs[GameAttribute.Resistance_Total, 6] = 3.051758E-05f; attribs[GameAttribute.Dodge_Rating_Total] = 3.051758E-05f; attribs[GameAttribute.IsTrialActor] = true; attribs[GameAttribute.Buff_Visual_Effect, 0xFFFFF] = true; attribs[GameAttribute.Crit_Percent_Cap] = 0x3F400000; attribs[GameAttribute.Resource_Cur, Client.Player.Hero.ResourceID] = 200f; attribs[GameAttribute.Resource_Max, Client.Player.Hero.ResourceID] = 200f; attribs[GameAttribute.Resource_Max_Total, Client.Player.Hero.ResourceID] = 200f; attribs[GameAttribute.Damage_Weapon_Min_Total_All] = 2f; attribs[GameAttribute.Damage_Weapon_Delta_Total_All] = 1f; attribs[GameAttribute.Resource_Regen_Total, Client.Player.Hero.ResourceID] = 3.051758E-05f; //-- attribs[GameAttribute.Resource_Effective_Max, Client.Player.Hero.ResourceID] = 200f; attribs[GameAttribute.Damage_Min_Subtotal, 0xFFFFF] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Total, 0xFFFFF] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, 0xFFFFF] = 3.051758E-05f; attribs[GameAttribute.Attacks_Per_Second_Item_CurrentHand] = 1.199219f; attribs[GameAttribute.Attacks_Per_Second_Item_Total_MainHand] = 1.199219f; attribs[GameAttribute.Attacks_Per_Second_Total] = 1.199219f; attribs[GameAttribute.Attacks_Per_Second] = 1f; attribs[GameAttribute.Attacks_Per_Second_Item_MainHand] = 1.199219f; attribs[GameAttribute.Attacks_Per_Second_Item_Total] = 1.199219f; attribs[GameAttribute.Buff_Icon_End_Tick0, 0x00033C40] = 0x000003FB; attribs[GameAttribute.Attacks_Per_Second_Item_Subtotal] = 3.051758E-05f; attribs[GameAttribute.Attacks_Per_Second_Item] = 3.051758E-05f; attribs[GameAttribute.Buff_Icon_Start_Tick0, 0x00033C40] = 0x00000077; attribs[GameAttribute.Hit_Chance] = 1f; //-- attribs[GameAttribute.Casting_Speed_Total] = 1f; attribs[GameAttribute.Casting_Speed] = 1f; attribs[GameAttribute.Movement_Scalar_Total] = 1f; attribs[GameAttribute.Skill_Total, 0x0002EC66] = 0; attribs[GameAttribute.Movement_Scalar_Capped_Total] = 1f; attribs[GameAttribute.Movement_Scalar_Subtotal] = 1f; attribs[GameAttribute.Strafing_Rate_Total] = 3.051758E-05f; attribs[GameAttribute.Sprinting_Rate_Total] = 3.051758E-05f; attribs[GameAttribute.Running_Rate_Total] = 0.3598633f; attribs[GameAttribute.Damage_Weapon_Min_Total_MainHand, 0] = 2f; attribs[GameAttribute.Walking_Rate_Total] = 0.2797852f; attribs[GameAttribute.Damage_Weapon_Delta_Total_MainHand, 0] = 1f; attribs[GameAttribute.Damage_Delta_Total, 1] = 3.051758E-05f; attribs[GameAttribute.Damage_Delta_Total, 2] = 3.051758E-05f; attribs[GameAttribute.Damage_Delta_Total, 3] = 3.051758E-05f; //-- attribs[GameAttribute.Damage_Delta_Total, 4] = 3.051758E-05f; attribs[GameAttribute.Damage_Delta_Total, 5] = 3.051758E-05f; attribs[GameAttribute.Damage_Delta_Total, 6] = 3.051758E-05f; attribs[GameAttribute.Damage_Delta_Total, 0] = 1f; attribs[GameAttribute.Running_Rate] = 0.3598633f; attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, 1] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, 2] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, 3] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, 4] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, 5] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, 6] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Min_Total_CurrentHand, 0] = 2f; attribs[GameAttribute.Walking_Rate] = 0.2797852f; attribs[GameAttribute.Damage_Min_Total, 1] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Total, 2] = 3.051758E-05f; //-- attribs[GameAttribute.Damage_Min_Total, 3] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Total, 4] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Total, 5] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Total, 6] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, 1] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, 2] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, 3] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, 4] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, 5] = 3.051758E-05f; attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, 6] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Total, 0] = 2f; attribs[GameAttribute.Damage_Weapon_Delta_Total_CurrentHand, 0] = 1f; attribs[GameAttribute.Movement_Scalar] = 1f; attribs[GameAttribute.Damage_Min_Subtotal, 1] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Subtotal, 2] = 3.051758E-05f; //-- attribs[GameAttribute.Damage_Min_Subtotal, 3] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Subtotal, 4] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Subtotal, 5] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Subtotal, 6] = 3.051758E-05f; attribs[GameAttribute.Damage_Min_Subtotal, 0] = 2f; attribs[GameAttribute.Damage_Weapon_Delta, 0] = 1f; attribs[GameAttribute.Damage_Weapon_Delta_SubTotal, 0] = 1f; attribs[GameAttribute.Damage_Weapon_Max, 0] = 3f; attribs[GameAttribute.Damage_Weapon_Max_Total, 0] = 3f; attribs[GameAttribute.Damage_Weapon_Delta_Total, 0] = 1f; attribs[GameAttribute.Trait, 0x0000CE11] = 1; attribs[GameAttribute.Damage_Weapon_Min, 0] = 2f; attribs[GameAttribute.Damage_Weapon_Min_Total, 0] = 2f; attribs[GameAttribute.Skill, 0x0000CE11] = 1; attribs[GameAttribute.Skill_Total, 0x0000CE11] = 1; //-- attribs[GameAttribute.Resource_Type_Primary] = Client.Player.Hero.ResourceID; attribs[GameAttribute.Hitpoints_Max_Total] = 76f; attribs[GameAttribute.Hitpoints_Max] = 40f; attribs[GameAttribute.Hitpoints_Total_From_Level] = 3.051758E-05f; attribs[GameAttribute.Hitpoints_Total_From_Vitality] = 36f; attribs[GameAttribute.Hitpoints_Factor_Vitality] = 4f; attribs[GameAttribute.Hitpoints_Factor_Level] = 4f; attribs[GameAttribute.Hitpoints_Cur] = 76f; attribs[GameAttribute.Disabled] = true; attribs[GameAttribute.Loading] = true; attribs[GameAttribute.Invulnerable] = true; attribs[GameAttribute.TeamID] = 2; attribs[GameAttribute.Skill_Total, 0xFFFFF] = 1; attribs[GameAttribute.Skill, 0xFFFFF] = 1; attribs[GameAttribute.Buff_Icon_Count0, 0x0000CE11] = 1; //-- attribs[GameAttribute.Hidden] = true; attribs[GameAttribute.Level_Cap] = 13; attribs[GameAttribute.Level] = Client.Player.Hero.Properties.Level; attribs[GameAttribute.Experience_Next] = 1200; attribs[GameAttribute.Experience_Granted] = 1000; attribs[GameAttribute.Armor_Total] = 0; attribs[GameAttribute.Defense] = 10f; attribs[GameAttribute.Buff_Icon_Count0, 0x00033C40] = 1; attribs[GameAttribute.Vitality] = 9f; attribs[GameAttribute.Precision] = 11f; attribs[GameAttribute.Attack] = 10f; attribs[GameAttribute.Shared_Stash_Slots] = 14; attribs[GameAttribute.Backpack_Slots] = 60; attribs[GameAttribute.General_Cooldown] = 0; attribs.SendMessage(Client, this.Hero.Id); Client.SendMessage(new ACDGroupMessage() { Id = 0x00B8, Field0 = this.Hero.Id, Field1 = -1, Field2 = -1, }); Client.SendMessage(new ANNDataMessage() { Id = 0x003E, Field0 = this.Hero.Id, }); Client.SendMessage(new ACDTranslateFacingMessage() { Id = 0x0070, Field0 = this.Hero.Id, Field1 = 3.022712f, Field2 = false, }); Client.SendMessage(new PlayerEnterKnownMessage() { Field0 = 0x00000000, Field1 = this.Hero.Id, }); Client.SendMessage(Hero.GetVisualInventory()); Client.SendMessage(new PlayerActorSetInitialMessage() { Field0 = this.Hero.Id, Field1 = 0x00000000, }); Client.SendMessage(new SNONameDataMessage() { Id = 0x00D3, Field0 = new SNOName() { Field0 = 0x00000001, Field1 = Client.Player.Hero.ClassSNO, }, }); Client.FlushOutgoingBuffer(); Client.SendMessage(new DWordDataMessage() // TICK { Id = 0x0089, Field0 = 0x00000077, }); Client.FlushOutgoingBuffer(); Client.SendMessage(new AttributeSetValueMessage() { Field0 = this.Hero.Id, Field1 = new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x005B], // Hitpoints_Healed_Target Int = 0x00000000, Float = 76f, }, }); Client.SendMessage(new DWordDataMessage() // TICK { Id = 0x0089, Field0 = 0x0000007D, }); Client.FlushOutgoingBuffer(); }
private void OnToonTargetChange(GameClient client, TargetMessage message) { //Logger.Info("Player interaction with " + message.AsText()); Portal p=GetPortal(message.Field1); if (p!=null) { //we have a transition between worlds here ChangeToonWorld(client, p.TargetWorldID, p.TargetPos); //targetpos will always be valid as otherwise the portal wouldn't be targetable return; } else if (client.ObjectIdsSpawned == null || !client.ObjectIdsSpawned.Contains(message.Field1)) return; client.ObjectIdsSpawned.Remove(message.Field1); var killAni = new int[]{ 0x2cd7, 0x2cd4, 0x01b378, 0x2cdc, 0x02f2, 0x2ccf, 0x2cd0, 0x2cd1, 0x2cd2, 0x2cd3, 0x2cd5, 0x01b144, 0x2cd6, 0x2cd8, 0x2cda, 0x2cd9 }; client.SendMessage(new PlayEffectMessage() { Id = 0x7a, Field0 = message.Field1, Field1 = 0x0, Field2 = 0x2, }); client.SendMessage(new PlayEffectMessage() { Id = 0x7a, Field0 = message.Field1, Field1 = 0xc, }); client.SendMessage(new PlayHitEffectMessage() { Id = 0x7b, Field0 = message.Field1, Field1 = 0x789E00E2, Field2 = 0x2, Field3 = false, }); client.SendMessage(new FloatingNumberMessage() { Id = 0xd0, Field0 = message.Field1, Field1 = 9001.0f, Field2 = 0, }); client.SendMessage(new ANNDataMessage() { Id = 0x6d, Field0 = message.Field1, }); int ani = killAni[RandomHelper.Next(killAni.Length)]; //Logger.Info("Ani used: " + ani); client.SendMessage(new PlayAnimationMessage() { Id = 0x6c, Field0 = message.Field1, Field1 = 0xb, Field2 = 0, tAnim = new PlayAnimationMessageSpec[1] { new PlayAnimationMessageSpec() { Field0 = 0x2, Field1 = ani, Field2 = 0x0, Field3 = 1f } } }); client.PacketId += 10 * 2; client.SendMessage(new DWordDataMessage() { Id = 0x89, Field0 = client.PacketId, }); client.SendMessage(new ANNDataMessage() { Id = 0xc5, Field0 = message.Field1, }); GameAttributeMap attribs = new GameAttributeMap(); attribs[GameAttribute.Hitpoints_Cur] = 0f; attribs[GameAttribute.Could_Have_Ragdolled] = true; attribs[GameAttribute.Deleted_On_Server] = true; attribs.SendMessage(client, message.Field1); client.SendMessage(new PlayEffectMessage() { Id = 0x7a, Field0 = message.Field1, Field1 = 0xc, }); client.SendMessage(new PlayEffectMessage() { Id = 0x7a, Field0 = message.Field1, Field1 = 0x37, }); client.SendMessage(new PlayHitEffectMessage() { Id = 0x7b, Field0 = message.Field1, Field1 = 0x789E00E2, Field2 = 0x2, Field3 = false, }); client.PacketId += 10 * 2; client.SendMessage(new DWordDataMessage() { Id = 0x89, Field0 = client.PacketId, }); }
/// <summary> /// Greets the player and sends the client initial data it needs to get-ingame. /// </summary> /// <param name="message"></param> public void Greet(JoinBNetGameMessage message) { Logger.Debug("Greeting player with toon-name: {0} and positioning him to {1}", this.Hero.Properties.Name, Hero.Position); // send versions message Client.SendMessageNow(new VersionsMessage(message.SNOPackHash)); // send connection established message. Client.SendMessage(new ConnectionEstablishedMessage() { Field0 = 0x00000000, Field1 = 0x4BB91A16, SNOPackHash = message.SNOPackHash, }); // game setup message. Client.SendMessage(new GameSetupMessage() { Field0 = 0x00000077, }); Client.SendMessage(new SavePointInfoMessage() { snoLevelArea = -1, }); Client.SendMessage(new HearthPortalInfoMessage() { snoLevelArea = -1, Field1 = -1, }); // transition player to act so client can load act related data? /raist Client.SendMessage(new ActTransitionMessage() { Field0 = 0x00000000, Field1 = true, }); //reveal world to the toon if (Hero.CurrentWorld != null) Hero.CurrentWorld.Reveal(this.Hero); // send newplayermessage. Client.SendMessage(new NewPlayerMessage() { Id = 0x0031, Field0 = 0x00000000, //Party frame (0x00000000 hide, 0x00000001 show) Field1 = "", //Owner name? ToonName = this.Hero.Properties.Name, Field3 = 0x00000002, //party frame class Field4 = 0x00000004, //party frame level snoActorPortrait = this.Hero.ClassSNO, //party frame portrait Field6 = 0x00000001, Field7 = this.Hero.GetStateData(), Field8 = false, //announce party join Field9 = 0x00000001, Field10 = 0x789E00E2, }); // reveal the hero Hero.Reveal(this.Hero); Client.SendMessage(new ACDCollFlagsMessage() { Id = 0x00A6, Field0 = 0x789E00E2, Field1 = 0x00000000, }); GameAttributeMap attribs = new GameAttributeMap(); attribs[GameAttribute.SkillKit] = Client.Player.Hero.SkillKit; attribs[GameAttribute.Buff_Active, 0x33C40] = true; attribs[GameAttribute.Skill, 0x7545] = 1; attribs[GameAttribute.Skill_Total, 0x7545] = 1; attribs[GameAttribute.Resistance_Total, 0x226] = 0.5f; attribs[GameAttribute.Resistance, 0x226] = 0.5f; attribs[GameAttribute.Immobolize] = true; attribs[GameAttribute.Untargetable] = true; attribs[GameAttribute.Skill_Total, 0x76B7] = 1; attribs[GameAttribute.Skill, 0x76B7] = 1; attribs[GameAttribute.Skill, 0x6DF] = 1; attribs[GameAttribute.Buff_Active, 0xCE11] = true; attribs[GameAttribute.CantStartDisplayedPowers] = true; attribs[GameAttribute.Skill_Total, 0x216FA] = 1; attribs[GameAttribute.Skill, 0x176C4] = 1; attribs[GameAttribute.Skill, 0x216FA] = 1; attribs[GameAttribute.Skill_Total, 0x176C4] = 1; attribs[GameAttribute.Skill_Total, 0x6DF] = 1; attribs[GameAttribute.Resistance, 0xDE] = 0.5f; attribs[GameAttribute.Resistance_Total, 0xDE] = 0.5f; attribs[GameAttribute.Get_Hit_Recovery] = 6f; attribs[GameAttribute.Get_Hit_Recovery_Per_Level] = 1f; attribs[GameAttribute.Get_Hit_Recovery_Base] = 5f; attribs[GameAttribute.Skill, 0x7780] = 1; attribs[GameAttribute.Get_Hit_Max] = 60f; attribs[GameAttribute.Skill_Total, 0x7780] = 1; attribs[GameAttribute.Get_Hit_Max_Per_Level] = 10f; attribs[GameAttribute.Get_Hit_Max_Base] = 50f; attribs[GameAttribute.Resistance_Total, 0] = 3.051758E-05f; // im pretty sure key = 0 doesnt do anything since the lookup is (attributeId | (key << 12)), maybe this is some base resistance? /cm attribs[GameAttribute.Resistance_Total, 1] = 3.051758E-05f; attribs.SendMessage(Client, 0x789E00E2); Client.SendMessage(new AttributesSetValuesMessage() { Id = 0x004D, Field0 = 0x789E00E2, atKeyVals = new NetAttributeKeyValue[15] { new NetAttributeKeyValue() { Field0 = 0x00000002, Attribute = GameAttribute.Attributes[0x003E], // Resistance_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000003, Attribute = GameAttribute.Attributes[0x003E], // Resistance_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000004, Attribute = GameAttribute.Attributes[0x003E], // Resistance_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000005, Attribute = GameAttribute.Attributes[0x003E], // Resistance_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000006, Attribute = GameAttribute.Attributes[0x003E], // Resistance_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x00BE], // Dodge_Rating_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x02BA], // IsTrialActor Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Field0 = 0x000FFFFF, Attribute = GameAttribute.Attributes[0x01B9], // Buff_Visual_Effect Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x00A8], // Crit_Percent_Cap Int = 0x3F400000, Float = 0f, }, new NetAttributeKeyValue() { Field0 = Client.Player.Hero.ResourceID, Attribute = GameAttribute.Attributes[0x005E], // Resource_Cur Int = 0x43480000, Float = 0f, }, new NetAttributeKeyValue() { Field0 = Client.Player.Hero.ResourceID, Attribute = GameAttribute.Attributes[0x005F], // Resource_Max Int = 0x00000000, Float = 200f, }, new NetAttributeKeyValue() { Field0 = Client.Player.Hero.ResourceID, Attribute = GameAttribute.Attributes[0x0061], // Resource_Max_Total Int = 0x43480000, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x009D], // Damage_Weapon_Min_Total_All Int = 0x00000000, Float = 2f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0099], // Damage_Weapon_Delta_Total_All Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Field0 = Client.Player.Hero.ResourceID, Attribute = GameAttribute.Attributes[0x0068], // Resource_Regen_Total Int = 0x00000000, Float = 3.051758E-05f, }, }, }); Client.SendMessage(new AttributesSetValuesMessage() { Id = 0x004D, Field0 = 0x789E00E2, atKeyVals = new NetAttributeKeyValue[15] { new NetAttributeKeyValue() { Field0 = Client.Player.Hero.ResourceID, Attribute = GameAttribute.Attributes[0x006B], // Resource_Effective_Max Int = 0x00000000, Float = 200f, }, new NetAttributeKeyValue() { Field0 = 0x000FFFFF, Attribute = GameAttribute.Attributes[0x0092], // Damage_Min_Subtotal Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x000FFFFF, Attribute = GameAttribute.Attributes[0x0091], // Damage_Min_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x000FFFFF, Attribute = GameAttribute.Attributes[0x0190], // Damage_Weapon_Min_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x018F], // Attacks_Per_Second_Item_CurrentHand Int = 0x00000000, Float = 1.199219f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0189], // Attacks_Per_Second_Item_Total_MainHand Int = 0x00000000, Float = 1.199219f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0089], // Attacks_Per_Second_Total Int = 0x00000000, Float = 1.199219f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0087], // Attacks_Per_Second Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0187], // Attacks_Per_Second_Item_MainHand Int = 0x00000000, Float = 1.199219f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0086], // Attacks_Per_Second_Item_Total Int = 0x00000000, Float = 1.199219f, }, new NetAttributeKeyValue() { Field0 = 0x00033C40, Attribute = GameAttribute.Attributes[0x01BE], // Buff_Icon_End_Tick0 Int = 0x000003FB, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0084], // Attacks_Per_Second_Item_Subtotal Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0082], // Attacks_Per_Second_Item Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00033C40, Attribute = GameAttribute.Attributes[0x01BA], // Buff_Icon_Start_Tick0 Int = 0x00000077, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0081], // Hit_Chance Int = 0x00000000, Float = 1f, }, }, }); Client.SendMessage(new AttributesSetValuesMessage() { Id = 0x004D, Field0 = 0x789E00E2, atKeyVals = new NetAttributeKeyValue[15] { new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x007F], // Casting_Speed_Total Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x007D], // Casting_Speed Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x007B], // Movement_Scalar_Total Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Field0 = 0x0002EC66, Attribute = GameAttribute.Attributes[0x0042], // Skill_Total Int = 0x00000000, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0079], // Movement_Scalar_Capped_Total Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0078], // Movement_Scalar_Subtotal Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0076], // Strafing_Rate_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0075], // Sprinting_Rate_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0074], // Running_Rate_Total Int = 0x00000000, Float = 0.3598633f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x018B], // Damage_Weapon_Min_Total_MainHand Int = 0x00000000, Float = 2f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0073], // Walking_Rate_Total Int = 0x00000000, Float = 0.2797852f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x018D], // Damage_Weapon_Delta_Total_MainHand Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Field0 = 0x00000001, Attribute = GameAttribute.Attributes[0x008E], // Damage_Delta_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000002, Attribute = GameAttribute.Attributes[0x008E], // Damage_Delta_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000003, Attribute = GameAttribute.Attributes[0x008E], // Damage_Delta_Total Int = 0x00000000, Float = 3.051758E-05f, }, }, }); Client.SendMessage(new AttributesSetValuesMessage() { Id = 0x004D, Field0 = 0x789E00E2, atKeyVals = new NetAttributeKeyValue[15] { new NetAttributeKeyValue() { Field0 = 0x00000004, Attribute = GameAttribute.Attributes[0x008E], // Damage_Delta_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000005, Attribute = GameAttribute.Attributes[0x008E], // Damage_Delta_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000006, Attribute = GameAttribute.Attributes[0x008E], // Damage_Delta_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x008E], // Damage_Delta_Total Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0070], // Running_Rate Int = 0x00000000, Float = 0.3598633f, }, new NetAttributeKeyValue() { Field0 = 0x00000001, Attribute = GameAttribute.Attributes[0x0190], // Damage_Weapon_Min_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000002, Attribute = GameAttribute.Attributes[0x0190], // Damage_Weapon_Min_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000003, Attribute = GameAttribute.Attributes[0x0190], // Damage_Weapon_Min_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000004, Attribute = GameAttribute.Attributes[0x0190], // Damage_Weapon_Min_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000005, Attribute = GameAttribute.Attributes[0x0190], // Damage_Weapon_Min_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000006, Attribute = GameAttribute.Attributes[0x0190], // Damage_Weapon_Min_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0190], // Damage_Weapon_Min_Total_CurrentHand Int = 0x00000000, Float = 2f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x006F], // Walking_Rate Int = 0x00000000, Float = 0.2797852f, }, new NetAttributeKeyValue() { Field0 = 0x00000001, Attribute = GameAttribute.Attributes[0x0091], // Damage_Min_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000002, Attribute = GameAttribute.Attributes[0x0091], // Damage_Min_Total Int = 0x00000000, Float = 3.051758E-05f, }, }, }); Client.SendMessage(new AttributesSetValuesMessage() { Id = 0x004D, Field0 = 0x789E00E2, atKeyVals = new NetAttributeKeyValue[15] { new NetAttributeKeyValue() { Field0 = 0x00000003, Attribute = GameAttribute.Attributes[0x0091], // Damage_Min_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000004, Attribute = GameAttribute.Attributes[0x0091], // Damage_Min_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000005, Attribute = GameAttribute.Attributes[0x0091], // Damage_Min_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000006, Attribute = GameAttribute.Attributes[0x0091], // Damage_Min_Total Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000001, Attribute = GameAttribute.Attributes[0x0191], // Damage_Weapon_Delta_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000002, Attribute = GameAttribute.Attributes[0x0191], // Damage_Weapon_Delta_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000003, Attribute = GameAttribute.Attributes[0x0191], // Damage_Weapon_Delta_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000004, Attribute = GameAttribute.Attributes[0x0191], // Damage_Weapon_Delta_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000005, Attribute = GameAttribute.Attributes[0x0191], // Damage_Weapon_Delta_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000006, Attribute = GameAttribute.Attributes[0x0191], // Damage_Weapon_Delta_Total_CurrentHand Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0091], // Damage_Min_Total Int = 0x00000000, Float = 2f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0191], // Damage_Weapon_Delta_Total_CurrentHand Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x006E], // Movement_Scalar Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Field0 = 0x00000001, Attribute = GameAttribute.Attributes[0x0092], // Damage_Min_Subtotal Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000002, Attribute = GameAttribute.Attributes[0x0092], // Damage_Min_Subtotal Int = 0x00000000, Float = 3.051758E-05f, }, }, }); Client.SendMessage(new AttributesSetValuesMessage() { Id = 0x004D, Field0 = 0x789E00E2, atKeyVals = new NetAttributeKeyValue[15] { new NetAttributeKeyValue() { Field0 = 0x00000003, Attribute = GameAttribute.Attributes[0x0092], // Damage_Min_Subtotal Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000004, Attribute = GameAttribute.Attributes[0x0092], // Damage_Min_Subtotal Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000005, Attribute = GameAttribute.Attributes[0x0092], // Damage_Min_Subtotal Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000006, Attribute = GameAttribute.Attributes[0x0092], // Damage_Min_Subtotal Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0092], // Damage_Min_Subtotal Int = 0x00000000, Float = 2f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0094], // Damage_Weapon_Delta Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0095], // Damage_Weapon_Delta_SubTotal Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0096], // Damage_Weapon_Max Int = 0x00000000, Float = 3f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0097], // Damage_Weapon_Max_Total Int = 0x00000000, Float = 3f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x0098], // Damage_Weapon_Delta_Total Int = 0x00000000, Float = 1f, }, new NetAttributeKeyValue() { Field0 = 0x0000CE11, Attribute = GameAttribute.Attributes[0x027B], // Trait Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x009B], // Damage_Weapon_Min Int = 0x00000000, Float = 2f, }, new NetAttributeKeyValue() { Field0 = 0x00000000, Attribute = GameAttribute.Attributes[0x009C], // Damage_Weapon_Min_Total Int = 0x00000000, Float = 2f, }, new NetAttributeKeyValue() { Field0 = 0x0000CE11, Attribute = GameAttribute.Attributes[0x0041], // Skill Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Field0 = 0x0000CE11, Attribute = GameAttribute.Attributes[0x0042], // Skill_Total Int = 0x00000001, Float = 0f, }, }, }); Client.SendMessage(new AttributesSetValuesMessage() { Id = 0x004D, Field0 = 0x789E00E2, atKeyVals = new NetAttributeKeyValue[15] { new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x005C], // Resource_Type_Primary Int = Client.Player.Hero.ResourceID, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0056], // Hitpoints_Max_Total Int = 0x00000000, Float = 76f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0054], // Hitpoints_Max Int = 0x00000000, Float = 40f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0051], // Hitpoints_Total_From_Level Int = 0x00000000, Float = 3.051758E-05f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0050], // Hitpoints_Total_From_Vitality Int = 0x00000000, Float = 36f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x004F], // Hitpoints_Factor_Vitality Int = 0x00000000, Float = 4f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x004E], // Hitpoints_Factor_Level Int = 0x00000000, Float = 4f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x004D], // Hitpoints_Cur Int = 0x00000000, Float = 76f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x024C], // Disabled Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0046], // Loading Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0045], // Invulnerable Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0043], // TeamID Int = 0x00000002, Float = 0f, }, new NetAttributeKeyValue() { Field0 = 0x000FFFFF, Attribute = GameAttribute.Attributes[0x0042], // Skill_Total Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Field0 = 0x000FFFFF, Attribute = GameAttribute.Attributes[0x0041], // Skill Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Field0 = 0x0000CE11, Attribute = GameAttribute.Attributes[0x0230], // Buff_Icon_Count0 Int = 0x00000001, Float = 0f, }, }, }); Client.SendMessage(new AttributesSetValuesMessage() { Id = 0x004D, Field0 = 0x789E00E2, atKeyVals = new NetAttributeKeyValue[14] { new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x012C], // Hidden Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0027], // Level_Cap Int = 0x0000000D, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0026], // Level Int = Client.Player.Hero.Properties.Level, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0022], // Experience_Next Int = 0x000004B0, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0021], // Experience_Granted Int = 0x000003E8, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0020], // Armor_Total Int = 0x00000000, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x000C], // Defense Int = 0x00000000, Float = 10f, }, new NetAttributeKeyValue() { Field0 = 0x00033C40, Attribute = GameAttribute.Attributes[0x0230], // Buff_Icon_Count0 Int = 0x00000001, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x000B], // Vitality Int = 0x00000000, Float = 9f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x000A], // Precision Int = 0x00000000, Float = 11f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0009], // Attack Int = 0x00000000, Float = 10f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0008], // Shared_Stash_Slots Int = 0x0000000E, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0007], // Backpack_Slots Int = 0x0000003C, Float = 0f, }, new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x0103], // General_Cooldown Int = 0x00000000, Float = 0f, }, }, }); Client.SendMessage(new ACDGroupMessage() { Id = 0x00B8, Field0 = 0x789E00E2, Field1 = -1, Field2 = -1, }); Client.SendMessage(new ANNDataMessage() { Id = 0x003E, Field0 = 0x789E00E2, }); Client.SendMessage(new ACDTranslateFacingMessage() { Id = 0x0070, Field0 = 0x789E00E2, Field1 = 3.022712f, Field2 = false, }); Client.SendMessage(new PlayerEnterKnownMessage() { Id = 0x003D, Field0 = 0x00000000, Field1 = 0x789E00E2, }); Client.SendMessage(new PlayerActorSetInitialMessage() { Id = 0x0039, Field0 = 0x789E00E2, Field1 = 0x00000000, }); Client.SendMessage(new SNONameDataMessage() { Id = 0x00D3, Field0 = new SNOName() { Field0 = 0x00000001, Field1 = Client.Player.Hero.ClassSNO, }, }); Client.FlushOutgoingBuffer(); Client.SendMessage(new DWordDataMessage() // TICK { Id = 0x0089, Field0 = 0x00000077, }); Client.FlushOutgoingBuffer(); Client.SendMessage(new AttributeSetValueMessage() { Id = 0x004C, Field0 = 0x789E00E2, Field1 = new NetAttributeKeyValue() { Attribute = GameAttribute.Attributes[0x005B], // Hitpoints_Healed_Target Int = 0x00000000, Float = 76f, }, }); Client.SendMessage(new DWordDataMessage() // TICK { Id = 0x0089, Field0 = 0x0000007D, }); Client.FlushOutgoingBuffer(); }
protected override void EffectStartingAction() { World.BroadcastInclusive(new ANNDataMessage(Opcodes.ANNDataMessage13) { ActorID = Actor.DynamicID }, Actor); this.World.BroadcastInclusive(new PlayAnimationMessage() { ActorID = Actor.DynamicID, Field1 = 0xb, Field2 = 0, tAnim = new PlayAnimationMessageSpec[1] { new PlayAnimationMessageSpec() { Field0 = 0x2, Field1 = (AnimationSNO != -1 ? AnimationSNO : killAni[RandomHelper.Next(killAni.Length)]), Field2 = 0, Field3 = 1f } } }, Actor); this.World.BroadcastInclusive(new ANNDataMessage(Opcodes.ANNDataMessage24) { ActorID = Actor.DynamicID, }, Actor); GameAttributeMap attribs = new GameAttributeMap(); Actor.Attributes[GameAttribute.Hitpoints_Cur] = 0f; Actor.Attributes[GameAttribute.Could_Have_Ragdolled] = true; Actor.Attributes[GameAttribute.Deleted_On_Server] = true; Actor.Attributes[GameAttribute.Queue_Death] = true; Actor.Update(); // NEEDED to show anim this.World.BroadcastInclusive(new PlayEffectMessage() { ActorId = Actor.DynamicID, Effect = Effect.Unknown12 }, Actor); this.World.BroadcastInclusive(new PlayEffectMessage() { ActorId = Actor.DynamicID, Effect = Effect.Burned2 }, Actor); if ((Killer != null) && (Type != 0)) { this.World.BroadcastInclusive(new PlayHitEffectMessage() { ActorID = Actor.DynamicID, HitDealer = Killer.DynamicID, Field2 = Type, Field3 = false, }, Actor); } if (Actor is Mooege.Core.GS.Actors.Monster) { // play lore if 1st kill for player var players = Actor.GetPlayersInRange(); if (players != null) { var y = MPQStorage.Data.Assets[SNOGroup.Monster].FirstOrDefault(x => (x.Value.Data as Mooege.Common.MPQ.FileFormats.Monster).ActorSNO == Actor.SNOId); if (y.Value != null) { int loreSNO = (y.Value.Data as Mooege.Common.MPQ.FileFormats.Monster).SNOLore; if (loreSNO != -1) { foreach (var player in players.Where(player => !player.LearnedLore.m_snoLoreLearned.Contains(loreSNO))) { // play lore to player player.InGameClient.SendMessage(new Mooege.Net.GS.Message.Definitions.Quest.LoreMessage {Id = 212, snoLore = loreSNO }); // add lore to player's lores int loreIndex = 0; while ((loreIndex < player.LearnedLore.m_snoLoreLearned.Length) && (player.LearnedLore.m_snoLoreLearned[loreIndex] != 0)) { loreIndex++; } if (loreIndex < player.LearnedLore.m_snoLoreLearned.Length) { player.LearnedLore.m_snoLoreLearned[loreIndex] = loreSNO; player.LearnedLore.Count++; // Count player.UpdateHeroState(); } } } } } (Actor as Mooege.Core.GS.Actors.Monster).Die(); } else if (Actor is EffectActor) { (Actor as EffectActor).Die(); } else if (Actor is Player) { // TODO: death of player } }
public void SpawnMob(GameClient client, int mobId) // this shoudn't even rely on client or it's position though i know this is just a hack atm ;) /raist. { int nId = mobId; if (client.Player.Hero.Position == null) return; if (client.ObjectIdsSpawned == null) { client.ObjectIdsSpawned = new List<int>(); // why is this necessary? //client.ObjectIdsSpawned.Add(client.ObjectId - 100); client.ObjectIdsSpawned.Add(this.NextObjectId); } int objectId = this.NextObjectId; client.ObjectIdsSpawned.Add(objectId); #region ACDEnterKnown Hittable Zombie Vector3D pos = client.Player.Hero.Position; BasicNPC mob = new BasicNPC(objectId, mobId, new WorldPlace { Field0 = new Vector3D(pos.X - 5, pos.Y - 5, pos.Z), }); GetWorld(client.Player.Hero.WorldId).AddNpc(mob); mob.Reveal(client); client.SendMessage(new AffixMessage() { Id = 0x48, Field0 = objectId, Field1 = 0x1, aAffixGBIDs = new int[0] }); client.SendMessage(new AffixMessage() { Id = 0x48, Field0 = objectId, Field1 = 0x2, aAffixGBIDs = new int[0] }); client.SendMessage(new ACDCollFlagsMessage { Id = 0xa6, Field0 = objectId, Field1 = 0x1 }); GameAttributeMap attribs = new GameAttributeMap(); attribs[GameAttribute.Untargetable] = false; attribs[GameAttribute.Uninterruptible] = true; attribs[GameAttribute.Buff_Visual_Effect, 1048575] = true; attribs[GameAttribute.Buff_Icon_Count0, 30582] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30286] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30285] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30284] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30283] = 1; attribs[GameAttribute.Buff_Icon_Count0, 30290] = 1; attribs[GameAttribute.Buff_Icon_Count0, 79486] = 1; attribs[GameAttribute.Buff_Active, 30286] = true; attribs[GameAttribute.Buff_Active, 30285] = true; attribs[GameAttribute.Buff_Active, 30284] = true; attribs[GameAttribute.Buff_Active, 30283] = true; attribs[GameAttribute.Buff_Active, 30290] = true; attribs[GameAttribute.Hitpoints_Max_Total] = 4.546875f; attribs[GameAttribute.Buff_Active, 79486] = true; attribs[GameAttribute.Hitpoints_Max] = 4.546875f; attribs[GameAttribute.Hitpoints_Total_From_Level] = 0f; attribs[GameAttribute.Hitpoints_Cur] = 4.546875f; attribs[GameAttribute.Invulnerable] = true; attribs[GameAttribute.Buff_Active, 30582] = true; attribs[GameAttribute.TeamID] = 10; attribs[GameAttribute.Level] = 1; attribs.SendMessage(client, objectId); client.SendMessage(new ACDGroupMessage { Id = 0xb8, Field0 = objectId, Field1 = unchecked((int)0xb59b8de4), Field2 = unchecked((int)0xffffffff) }); client.SendMessage(new ANNDataMessage { Id = 0x3e, Field0 = objectId }); client.SendMessage(new ACDTranslateFacingMessage { Id = 0x70, Field0 = objectId, Field1 = (float)(RandomHelper.NextDouble() * 2.0 * Math.PI), Field2 = false }); client.SendMessage(new SetIdleAnimationMessage { Id = 0xa5, Field0 = objectId, Field1 = 0x11150 }); client.SendMessage(new SNONameDataMessage { Id = 0xd3, Field0 = new SNOName { Field0 = 0x1, Field1 = nId } }); #endregion client.PacketId += 30 * 2; client.SendMessage(new DWordDataMessage() { Id = 0x89, Field0 = client.PacketId, }); client.Tick += 20; client.SendMessage(new EndOfTickMessage() { Id = 0x008D, Field0 = client.Tick - 20, Field1 = client.Tick }); }
// FIXME: Hardcoded hell. /komiga public void Die(Player player) { /*var killAni = new int[]{ 0x2cd7, 0x2cd4, 0x01b378, 0x2cdc, 0x02f2, 0x2ccf, 0x2cd0, 0x2cd1, 0x2cd2, 0x2cd3, 0x2cd5, 0x01b144, 0x2cd6, 0x2cd8, 0x2cda, 0x2cd9 };*/ this.World.BroadcastIfRevealed(new PlayEffectMessage() { ActorId = this.DynamicID, Effect = Effect.Hit, OptionalParameter = 0x2, }, this); this.World.BroadcastIfRevealed(new PlayEffectMessage() { ActorId = this.DynamicID, Effect = Effect.Unknown12, }, this); this.World.BroadcastIfRevealed(new PlayHitEffectMessage() { ActorID = this.DynamicID, HitDealer = player.DynamicID, Field2 = 0x2, Field3 = false, }, this); this.World.BroadcastIfRevealed(new FloatingNumberMessage() { ActorID = this.DynamicID, Number = 9001.0f, Type = FloatingNumberMessage.FloatType.White, }, this); this.World.BroadcastIfRevealed(new ANNDataMessage(Opcodes.ANNDataMessage13) { ActorID = this.DynamicID }, this); player.UpdateExp(this.Attributes[GameAttribute.Experience_Granted]); player.ExpBonusData.Update(player.GBHandle.Type, this.GBHandle.Type); this.World.BroadcastIfRevealed(new PlayAnimationMessage() { ActorID = this.DynamicID, Field1 = 0xb, Field2 = 0, tAnim = new PlayAnimationMessageSpec[1] { new PlayAnimationMessageSpec() { Field0 = 0x2, Field1 = Animset.GetRandomDeath(),//killAni[RandomHelper.Next(killAni.Length)], Field2 = 0x0, Field3 = 1f } } }, this); this.World.BroadcastIfRevealed(new ANNDataMessage(Opcodes.ANNDataMessage24) { ActorID = this.DynamicID, }, this); GameAttributeMap attribs = new GameAttributeMap(); attribs[GameAttribute.Hitpoints_Cur] = 0f; attribs[GameAttribute.Could_Have_Ragdolled] = true; attribs[GameAttribute.Deleted_On_Server] = true; foreach (var msg in attribs.GetMessageList(this.DynamicID)) this.World.BroadcastIfRevealed(msg, this); this.World.SpawnRandomItemDrop(player, this.Position); this.World.SpawnGold(player, this.Position); if (RandomHelper.Next(1, 100) < 20) this.World.SpawnHealthGlobe(player, this.Position); this.Destroy(); }
internal GameAttributeMap GetEquippedMap() { if (_equippedMap == null) { _equippedMap = AttributeMath.ComputeEquipment(_owner, GetEquippedItemsAttributes()); } return _equippedMap; }
// TODO: The inventory's gold item should not be created here. /komiga public void PickUpGold(uint itemID) { Item collectedItem = _owner.World.GetItem(itemID); Item sumGoldItem = _equipment.AddGoldItem(collectedItem); GameAttributeMap attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = sumGoldItem.Attributes[GameAttribute.ItemStackQuantityLo]; attributes.SendMessage(_owner.InGameClient, sumGoldItem.DynamicID); }
/// <summary> /// Transfers an amount from one stack to another /// </summary> public void OnInventoryStackTransferMessage(InventoryStackTransferMessage msg) { Item itemFrom = this.Items[msg.FromID]; Item itemTo = this.Items[msg.ToID]; itemFrom.Count = (itemFrom.Count) - ((int)msg.Amount); itemTo.Count = itemTo.Count + (int)msg.Amount; // TODO: This needs to change the attribute on the item itself. /komiga // Update source GameAttributeMap attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = itemFrom.Count; attributes.SendMessage(_owner.InGameClient, itemFrom.DynamicID); // TODO: This needs to change the attribute on the item itself. /komiga // Update target attributes = new GameAttributeMap(); attributes[GameAttribute.ItemStackQuantityLo] = itemTo.Count; attributes.SendMessage(_owner.InGameClient, itemTo.DynamicID); _owner.InGameClient.PacketId += 10 * 2; _owner.InGameClient.SendMessage(new DWordDataMessage() { Id = 0x89, Field0 = _owner.InGameClient.PacketId, }); }