summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/Mobs/Monster.cpp1
-rw-r--r--src/Mobs/Monster.h8
-rw-r--r--src/Protocol/Protocol18x.cpp63
-rw-r--r--src/WorldStorage/NBTChunkSerializer.cpp33
-rwxr-xr-xsrc/WorldStorage/WSSAnvil.cpp79
5 files changed, 156 insertions, 28 deletions
diff --git a/src/Mobs/Monster.cpp b/src/Mobs/Monster.cpp
index cb4edb951..4befe307d 100644
--- a/src/Mobs/Monster.cpp
+++ b/src/Mobs/Monster.cpp
@@ -101,6 +101,7 @@ cMonster::cMonster(const AString & a_ConfigName, eMonsterType a_MobType, const A
, m_TicksSinceLastDamaged(100)
, m_BurnsInDaylight(false)
, m_RelativeWalkSpeed(1)
+ , m_Age(1)
{
if (!a_ConfigName.empty())
{
diff --git a/src/Mobs/Monster.h b/src/Mobs/Monster.h
index 1076c9544..2832a1570 100644
--- a/src/Mobs/Monster.h
+++ b/src/Mobs/Monster.h
@@ -112,10 +112,14 @@ public:
void SetRelativeWalkSpeed(double a_WalkSpeed) { m_RelativeWalkSpeed = a_WalkSpeed; } // tolua_export
// Overridables to handle ageable mobs
- virtual bool IsBaby (void) const { return false; }
virtual bool IsTame (void) const { return false; }
virtual bool IsSitting (void) const { return false; }
+ bool IsBaby (void) const { return m_Age < 0; }
+ char GetAge (void) const { return m_Age; }
+ void SetAge(char a_Age) { m_Age = a_Age; }
+
+
// tolua_begin
/** Returns true if the monster has a custom name. */
@@ -270,6 +274,8 @@ protected:
bool m_BurnsInDaylight;
double m_RelativeWalkSpeed;
+ char m_Age;
+
/** Adds a random number of a_Item between a_Min and a_Max to itemdrops a_Drops*/
void AddRandomDropItem(cItems & a_Drops, unsigned int a_Min, unsigned int a_Max, short a_Item, short a_ItemHealth = 0);
diff --git a/src/Protocol/Protocol18x.cpp b/src/Protocol/Protocol18x.cpp
index 99bba63e3..4708d67c9 100644
--- a/src/Protocol/Protocol18x.cpp
+++ b/src/Protocol/Protocol18x.cpp
@@ -3341,7 +3341,7 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEUInt8(Bat.IsHanging() ? 1 : 0);
break;
} // case mtBat
-
+
case mtCreeper:
{
auto & Creeper = reinterpret_cast<const cCreeper &>(a_Mob);
@@ -3351,7 +3351,7 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEUInt8(Creeper.IsCharged() ? 1 : 0);
break;
} // case mtCreeper
-
+
case mtEnderman:
{
auto & Enderman = reinterpret_cast<const cEnderman &>(a_Mob);
@@ -3363,7 +3363,7 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEUInt8(Enderman.IsScreaming() ? 1 : 0);
break;
} // case mtEnderman
-
+
case mtGhast:
{
auto & Ghast = reinterpret_cast<const cGhast &>(a_Mob);
@@ -3371,7 +3371,7 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEUInt8(Ghast.IsCharging());
break;
} // case mtGhast
-
+
case mtHorse:
{
auto & Horse = reinterpret_cast<const cHorse &>(a_Mob);
@@ -3388,10 +3388,6 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
{
Flags |= 0x08;
}
- if (Horse.IsBaby())
- {
- Flags |= 0x10;
- }
if (Horse.IsEating())
{
Flags |= 0x20;
@@ -3415,6 +3411,9 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEInt32(Appearance);
a_Pkt.WriteBEUInt8(0x56); // Int at index 22
a_Pkt.WriteBEInt32(Horse.GetHorseArmour());
+
+ a_Pkt.WriteBEUInt8(0x0c);
+ a_Pkt.WriteBEInt8(Horse.GetAge());
break;
} // case mtHorse
@@ -3426,17 +3425,38 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
break;
} // case mtMagmaCube
+ case mtOcelot:
+ {
+ auto & Ocelot = reinterpret_cast<const cOcelot &>(a_Mob);
+ a_Pkt.WriteBEUInt8(0x0c);
+ a_Pkt.WriteBEInt8(Ocelot.GetAge());
+ break;
+ } // case mtOcelot
+
case mtPig:
{
auto & Pig = reinterpret_cast<const cPig &>(a_Mob);
+ a_Pkt.WriteBEUInt8(0x0c);
+ a_Pkt.WriteBEInt8(Pig.GetAge());
a_Pkt.WriteBEUInt8(0x10);
a_Pkt.WriteBEUInt8(Pig.IsSaddled() ? 1 : 0);
break;
} // case mtPig
-
+
+ case mtRabbit:
+ {
+ auto & Rabbit = reinterpret_cast<const cRabbit &>(a_Mob);
+ a_Pkt.WriteBEUInt8(0x0c);
+ a_Pkt.WriteBEInt8(Rabbit.GetAge());
+ break;
+ } // case mtRabbit
+
case mtSheep:
{
auto & Sheep = reinterpret_cast<const cSheep &>(a_Mob);
+ a_Pkt.WriteBEUInt8(0x0c);
+ a_Pkt.WriteBEInt8(Sheep.GetAge());
+
a_Pkt.WriteBEUInt8(0x10);
Byte SheepMetadata = 0;
SheepMetadata = Sheep.GetFurColor();
@@ -3447,7 +3467,7 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEUInt8(SheepMetadata);
break;
} // case mtSheep
-
+
case mtSkeleton:
{
auto & Skeleton = reinterpret_cast<const cSkeleton &>(a_Mob);
@@ -3455,7 +3475,7 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEUInt8(Skeleton.IsWither() ? 1 : 0);
break;
} // case mtSkeleton
-
+
case mtSlime:
{
auto & Slime = reinterpret_cast<const cSlime &>(a_Mob);
@@ -3469,9 +3489,11 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
auto & Villager = reinterpret_cast<const cVillager &>(a_Mob);
a_Pkt.WriteBEUInt8(0x50);
a_Pkt.WriteBEInt32(Villager.GetVilType());
+ a_Pkt.WriteBEUInt8(0x0c);
+ a_Pkt.WriteBEInt8(Villager.GetAge());
break;
} // case mtVillager
-
+
case mtWitch:
{
auto & Witch = reinterpret_cast<const cWitch &>(a_Mob);
@@ -3489,7 +3511,7 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEFloat(static_cast<float>(a_Mob.GetHealth()));
break;
} // case mtWither
-
+
case mtWolf:
{
auto & Wolf = reinterpret_cast<const cWolf &>(a_Mob);
@@ -3515,20 +3537,31 @@ void cProtocol180::WriteMobMetadata(cPacketizer & a_Pkt, const cMonster & a_Mob)
a_Pkt.WriteBEUInt8(Wolf.IsBegging() ? 1 : 0);
a_Pkt.WriteBEUInt8(0x14);
a_Pkt.WriteBEUInt8(Wolf.GetCollarColor());
+
+ a_Pkt.WriteBEUInt8(0x0c);
+ a_Pkt.WriteBEInt8(Wolf.GetAge());
break;
} // case mtWolf
-
+
case mtZombie:
{
auto & Zombie = reinterpret_cast<const cZombie &>(a_Mob);
a_Pkt.WriteBEUInt8(0x0c);
- a_Pkt.WriteBEUInt8(Zombie.IsBaby() ? 1 : 0);
+ a_Pkt.WriteBEInt8(Zombie.IsBaby() ? 1 : -1);
a_Pkt.WriteBEUInt8(0x0d);
a_Pkt.WriteBEUInt8(Zombie.IsVillagerZombie() ? 1 : 0);
a_Pkt.WriteBEUInt8(0x0e);
a_Pkt.WriteBEUInt8(Zombie.IsConverting() ? 1 : 0);
break;
} // case mtZombie
+
+ case mtZombiePigman:
+ {
+ auto & ZombiePigman = reinterpret_cast<const cZombiePigman &>(a_Mob);
+ a_Pkt.WriteBEUInt8(0x0c);
+ a_Pkt.WriteBEInt8(ZombiePigman.IsBaby() ? 1 : -1);
+ break;
+ } // case mtZombiePigman
} // switch (a_Mob.GetType())
}
diff --git a/src/WorldStorage/NBTChunkSerializer.cpp b/src/WorldStorage/NBTChunkSerializer.cpp
index 10231ae3b..234c60d62 100644
--- a/src/WorldStorage/NBTChunkSerializer.cpp
+++ b/src/WorldStorage/NBTChunkSerializer.cpp
@@ -554,6 +554,7 @@ void cNBTChunkSerializer::AddMonsterEntity(cMonster * a_Monster)
m_Writer.AddInt ("Style", Horse.GetHorseStyle());
m_Writer.AddInt ("ArmorType", Horse.GetHorseArmour());
m_Writer.AddByte("Saddle", Horse.IsSaddled());
+ m_Writer.AddByte("Age", Horse.GetAge());
break;
}
case mtMagmaCube:
@@ -565,6 +566,7 @@ void cNBTChunkSerializer::AddMonsterEntity(cMonster * a_Monster)
{
m_Writer.AddByte("Sheared", ((const cSheep *)a_Monster)->IsSheared());
m_Writer.AddByte("Color", ((const cSheep *)a_Monster)->GetFurColor());
+ m_Writer.AddByte("Age", ((const cSheep *)a_Monster)->GetAge());
break;
}
case mtSlime:
@@ -580,6 +582,7 @@ void cNBTChunkSerializer::AddMonsterEntity(cMonster * a_Monster)
case mtVillager:
{
m_Writer.AddInt("Profession", ((const cVillager *)a_Monster)->GetVilType());
+ m_Writer.AddByte("Age", ((const cVillager *)a_Monster)->GetAge());
break;
}
case mtWither:
@@ -601,13 +604,37 @@ void cNBTChunkSerializer::AddMonsterEntity(cMonster * a_Monster)
m_Writer.AddByte("Sitting", Wolf.IsSitting() ? 1 : 0);
m_Writer.AddByte("Angry", Wolf.IsAngry() ? 1 : 0);
m_Writer.AddByte("CollarColor", (unsigned char)Wolf.GetCollarColor());
+ m_Writer.AddByte("Age", Wolf.GetAge());
break;
}
case mtZombie:
{
m_Writer.AddByte("IsVillager", (((const cZombie *)a_Monster)->IsVillagerZombie() ? 1 : 0));
- m_Writer.AddByte("IsBaby", (((const cZombie *)a_Monster)->IsBaby() ? 1 : 0));
m_Writer.AddByte("IsConverting", (((const cZombie *)a_Monster)->IsConverting() ? 1 : 0));
+ m_Writer.AddByte("Age", (((const cZombie *)a_Monster)->GetAge()));
+ break;
+ }
+ case mtZombiePigman:
+ {
+ m_Writer.AddByte("Age", (((const cZombiePigman *)a_Monster)->GetAge()));
+ break;
+ }
+ case mtOcelot:
+ {
+ const cOcelot & Ocelot = *((cOcelot *)a_Monster);
+ m_Writer.AddByte("Age", Ocelot.GetAge());
+ break;
+ }
+ case mtPig:
+ {
+ const cPig & Pig = *((cPig *)a_Monster);
+ m_Writer.AddByte("Age", Pig.GetAge());
+ break;
+ }
+ case mtRabbit:
+ {
+ const cRabbit & Rabbit = *((cRabbit *)a_Monster);
+ m_Writer.AddByte("Age", Rabbit.GetAge());
break;
}
case mtInvalidType:
@@ -621,15 +648,11 @@ void cNBTChunkSerializer::AddMonsterEntity(cMonster * a_Monster)
case mtGuardian:
case mtIronGolem:
case mtMooshroom:
- case mtOcelot:
- case mtPig:
- case mtRabbit:
case mtSilverfish:
case mtSnowGolem:
case mtSpider:
case mtSquid:
case mtWitch:
- case mtZombiePigman:
{
// Other mobs have no special tags.
break;
diff --git a/src/WorldStorage/WSSAnvil.cpp b/src/WorldStorage/WSSAnvil.cpp
index 4912d20f6..e99b2611b 100755
--- a/src/WorldStorage/WSSAnvil.cpp
+++ b/src/WorldStorage/WSSAnvil.cpp
@@ -2256,7 +2256,14 @@ void cWSSAnvil::LoadHorseFromNBT(cEntityList & a_Entities, const cParsedNBT & a_
{
return;
}
-
+
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
a_Entities.push_back(Monster.release());
}
@@ -2346,6 +2353,13 @@ void cWSSAnvil::LoadOcelotFromNBT(cEntityList & a_Entities, const cParsedNBT & a
return;
}
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
a_Entities.push_back(Monster.release());
}
@@ -2365,7 +2379,14 @@ void cWSSAnvil::LoadPigFromNBT(cEntityList & a_Entities, const cParsedNBT & a_NB
{
return;
}
-
+
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
a_Entities.push_back(Monster.release());
}
@@ -2385,7 +2406,14 @@ void cWSSAnvil::LoadRabbitFromNBT(cEntityList & a_Entities, const cParsedNBT & a
{
return;
}
-
+
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
a_Entities.push_back(Monster.release());
}
@@ -2418,7 +2446,14 @@ void cWSSAnvil::LoadSheepFromNBT(cEntityList & a_Entities, const cParsedNBT & a_
{
Monster->SetSheared(a_NBT.GetByte(ShearedIdx) != 0);
}
-
+
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
a_Entities.push_back(Monster.release());
}
@@ -2583,7 +2618,15 @@ void cWSSAnvil::LoadVillagerFromNBT(cEntityList & a_Entities, const cParsedNBT &
{
return;
}
-
+
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
+
a_Entities.push_back(Monster.release());
}
@@ -2683,6 +2726,14 @@ void cWSSAnvil::LoadWolfFromNBT(cEntityList & a_Entities, const cParsedNBT & a_N
}
}
}
+
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
a_Entities.push_back(Monster.release());
}
@@ -2710,7 +2761,14 @@ void cWSSAnvil::LoadZombieFromNBT(cEntityList & a_Entities, const cParsedNBT & a
{
return;
}
-
+
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
a_Entities.push_back(Monster.release());
}
@@ -2730,7 +2788,14 @@ void cWSSAnvil::LoadPigZombieFromNBT(cEntityList & a_Entities, const cParsedNBT
{
return;
}
-
+
+ int AgeableIdx = a_NBT.FindChildByName(a_TagIdx, "Age");
+ if (AgeableIdx > 0)
+ {
+ Byte Age = a_NBT.GetByte(AgeableIdx);
+ Monster->SetAge(Age);
+ }
+
a_Entities.push_back(Monster.release());
}