RunUO Community

This is a sample guest message. Register a free account today to become a member! Once signed in, you'll be able to participate on this site by adding your own topics and posts, as well as connect with other members through your own private inbox!

Enhanced client + custom gumps

Vorspire

Knight
I took the liberty of constructing the lesser known packets that differ between classic and enhanced clients, some of them might not be known in general, but here they are;

C#:
	#region Support KR
	public sealed class KRHealthbarPoison : Packet
	{
		public KRHealthbarPoison(Mobile m)
			: base(0x16)
		{
			EnsureCapacity(12);

			m_Stream.Write(m.Serial);
			m_Stream.Write((short)0x01);

			m_Stream.Write((short)0x01);

			Poison p = m.Poison;

			if (p != null)
			{
				m_Stream.Write((byte)(p.RealLevel + 1));
			}
			else
			{
				m_Stream.Write((byte)0x00);
			}
		}
	}

	public sealed class KRHealthbarYellow : Packet
	{
		public KRHealthbarYellow(Mobile m)
			: base(0x16)
		{
			EnsureCapacity(12);

			m_Stream.Write(m.Serial);
			m_Stream.Write((short)0x01);

			m_Stream.Write((short)0x02);

			if (m.Blessed || m.YellowHealthbar)
			{
				m_Stream.Write((byte)0x01);
			}
			else
			{
				m_Stream.Write((byte)0x00);
			}
		}
	}

	public sealed class KRVerification : Packet
	{
		public static readonly Packet Instance = SetStatic(new KRVerification());

		public KRVerification()
			: base(0xE3, 77)
		{
			// First 2 - Size
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x4D);

			// Next ones... I have no idea from now on
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x03);
			m_Stream.Write((byte)0x02);
			m_Stream.Write((byte)0x01);
			m_Stream.Write((byte)0x03);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x13);
			m_Stream.Write((byte)0x02);
			m_Stream.Write((byte)0x11);

			// Next 16
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0xFC);
			m_Stream.Write((byte)0x2F);
			m_Stream.Write((byte)0xE3);
			m_Stream.Write((byte)0x81);
			m_Stream.Write((byte)0x93);
			m_Stream.Write((byte)0xCB);
			m_Stream.Write((byte)0xAF);
			m_Stream.Write((byte)0x98);
			m_Stream.Write((byte)0xDD);
			m_Stream.Write((byte)0x83);
			m_Stream.Write((byte)0x13);
			m_Stream.Write((byte)0xD2);
			m_Stream.Write((byte)0x9E);
			m_Stream.Write((byte)0xEA);
			m_Stream.Write((byte)0xE4);

			// Next 16
			m_Stream.Write((byte)0x13);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x10);
			m_Stream.Write((byte)0x78);
			m_Stream.Write((byte)0x13);
			m_Stream.Write((byte)0xB7);
			m_Stream.Write((byte)0x7B);
			m_Stream.Write((byte)0xCE);
			m_Stream.Write((byte)0xA8);
			m_Stream.Write((byte)0xD7);
			m_Stream.Write((byte)0xBC);
			m_Stream.Write((byte)0x52);
			m_Stream.Write((byte)0xDE);
			m_Stream.Write((byte)0x38);

			// Next 16
			m_Stream.Write((byte)0x30);
			m_Stream.Write((byte)0xEA);
			m_Stream.Write((byte)0xE9);
			m_Stream.Write((byte)0x1E);
			m_Stream.Write((byte)0xA3);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x20);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x00);
			m_Stream.Write((byte)0x10);
			m_Stream.Write((byte)0x5A);
			m_Stream.Write((byte)0xCE);
			m_Stream.Write((byte)0x3E);

			// Next 13
			m_Stream.Write((byte)0xE3);
			m_Stream.Write((byte)0x97);
			m_Stream.Write((byte)0x92);
			m_Stream.Write((byte)0xE4);
			m_Stream.Write((byte)0x8A);
			m_Stream.Write((byte)0xF1);
			m_Stream.Write((byte)0x9A);
			m_Stream.Write((byte)0xD3);
			m_Stream.Write((byte)0x04);
			m_Stream.Write((byte)0x41);
			m_Stream.Write((byte)0x03);
			m_Stream.Write((byte)0xCB);
			m_Stream.Write((byte)0x53);
		}
	}

	public sealed class KRDropConfirm : Packet
	{
		public static readonly Packet Instance = SetStatic(new KRDropConfirm());

		public KRDropConfirm()
			: base(0x29, 1)
		{ }
	}

	public sealed class KRPetWindow : Packet
	{
		public KRPetWindow(Mobile owner, params Mobile[] pets)
			: base(0x31)
		{
			EnsureCapacity(8 + (pets.Length * 5));

			m_Stream.Write(owner.Serial);

			m_Stream.Write((byte)pets.Length);

			foreach (Mobile pet in pets)
			{
				m_Stream.Write(pet.Serial);
				m_Stream.Write((byte)0x01);
			}
		}
	}

	public enum KRWaypointType
	{
		None = 0x0,
		Corpse = 0x01,
		Party = 0x02,
		Unknown = 0x03,
		Quest = 0x04,
		QuestDestination = 0x05,
		Resurrection = 0x06
	}

	public sealed class KRDisplayWaypoint : Packet
	{
		public KRDisplayWaypoint(Serial serial, Point3D loc, Map map, KRWaypointType type, string label)
			: base(0xE5)
		{
			bool ignore = false;
			int cliloc = 1062613;

			switch (type)
			{
				case KRWaypointType.Corpse:
					cliloc = 1046414;
					break;
				case KRWaypointType.Resurrection:
				case KRWaypointType.QuestDestination:
				case KRWaypointType.Quest:
				case KRWaypointType.Party:
				case KRWaypointType.None:
					ignore = true;
					break;
			}

			EnsureCapacity(25);

			m_Stream.Write(serial);

			m_Stream.Write((short)loc.X);
			m_Stream.Write((short)loc.Y);
			m_Stream.Write((sbyte)loc.Z);

			m_Stream.Write((byte)map.MapID);

			m_Stream.Write((short)type);

			m_Stream.Write(ignore);

			m_Stream.Write(cliloc);
			m_Stream.WriteLittleUniNull(label);

			m_Stream.Write((short)0); // terminate
		}
	}

	public sealed class KRHideWaypoint : Packet
	{
		public KRHideWaypoint(Serial serial)
			: base(0xE6, 5)
		{
			m_Stream.Write(serial);
		}
	}

	public sealed class KRUIHighlight : Packet
	{
		public KRUIHighlight(Mobile user, short element, Serial dest)
			: base(0xE7, 12)
		{
			m_Stream.Write(user.Serial);
			m_Stream.Write(element);
			m_Stream.Write(dest);
			m_Stream.Write((byte)0x01);
		}
	}

	public sealed class KRUIToggleHighlight : Packet
	{
		public static KRUIToggleHighlight Inventory(Mobile user, short element, int dest)
		{
			return new KRUIToggleHighlight(user, element, "ToggleInventory", dest);
		}

		public static KRUIToggleHighlight Paperdoll(Mobile user, short element, int dest)
		{
			return new KRUIToggleHighlight(user, element, "TogglePaperdoll", dest);
		}

		public static KRUIToggleHighlight Map(Mobile user, short element, int dest)
		{
			return new KRUIToggleHighlight(user, element, "ToggleMap", dest);
		}

		public KRUIToggleHighlight(Mobile user, short element, string desc, int dest)
			: base(0xE9, 75)
		{
			m_Stream.Write(element);
			m_Stream.Write(user.Serial);

			m_Stream.WriteAsciiFixed(desc, 64);

			m_Stream.Write(dest);
		}
	}

	public sealed class KRHotbar : Packet
	{
		public static readonly Packet Enable = SetStatic(new KRHotbar(true));
		public static readonly Packet Disable = SetStatic(new KRHotbar(false));

		public KRHotbar(bool enable)
			: base(0xEA, 3)
		{
			m_Stream.Write((short)(enable ? 0x01 : 0x00));
		}
	}

	public sealed class KRSlotCooldown : Packet
	{
		public KRSlotCooldown(Item item, int duration)
			: this(item.ItemID, duration)
		{ }

		public KRSlotCooldown(int id, int duration)
			: base(0xBF)
		{
			m_Stream.Write((short)0x31);
			m_Stream.Write((short)0x01);

			m_Stream.Write(id);
			m_Stream.Write(duration);
		}
	}

	public sealed class KRStatLockInfo : Packet
	{
		public KRStatLockInfo(Mobile m)
			: base(0xBF)
		{
			EnsureCapacity(17);

			m_Stream.Write((short)0x19);

			m_Stream.Write((byte)0x05);

			m_Stream.Write(m.Serial);
			m_Stream.Write((byte)0);

			int lockBits = 0;

			lockBits |= (int)m.StrLock << 4;
			lockBits |= (int)m.DexLock << 2;
			lockBits |= (int)m.IntLock;

			m_Stream.Write((byte)lockBits);

			if (lockBits == 0xFF)
			{
				m_Stream.Write((byte)m.GetPacketFlags());
				m_Stream.Write((short)m.GetIdleAnimation()); //Animation
				m_Stream.Write((short)5); //Frame Count
			}
			else
			{
				m_Stream.Fill(5);
			}
		}
	}
	#endregion

Various documentation for these packets on the internet is wrong, the order of some bytes are wrong, due to poorly copy/pasted web page templates that didn't really get filled in correctly.
These packets are accurate and the corrections against the documentation mistakes have been made.

KR support is standard on shards that I work with now, still trying to figure out how to fix gumps though - the EC doesn't preserve the layers order in which the gumps are coded - it seems to give priority to specific entries, like buttons always appear at the front, even if you code them behind a background element.
 
Top