528 lines
11 KiB
C#
528 lines
11 KiB
C#
using System;
|
|
using System.Text;
|
|
using Server;
|
|
using Server.Commands;
|
|
using Server.Network;
|
|
using System.Collections.Generic;
|
|
using Server.Mobiles;
|
|
using Server.Targeting;
|
|
using Server.Items;
|
|
|
|
namespace Server.Engines.XmlSpawner2
|
|
{
|
|
public interface IXmlAttachment
|
|
{
|
|
ASerial Serial { get; }
|
|
|
|
string Name { get; set; }
|
|
|
|
TimeSpan Expiration { get; set; }
|
|
|
|
DateTime ExpirationEnd { get; }
|
|
|
|
DateTime CreationTime { get; }
|
|
|
|
bool Deleted { get; }
|
|
|
|
bool DoDelete { get; set; }
|
|
|
|
bool CanActivateInBackpack { get; }
|
|
|
|
bool CanActivateEquipped { get; }
|
|
|
|
bool CanActivateInWorld { get; }
|
|
|
|
bool HandlesOnSpeech { get; }
|
|
|
|
void OnSpeech(SpeechEventArgs args);
|
|
|
|
bool HandlesOnMovement { get; }
|
|
|
|
void OnMovement(MovementEventArgs args);
|
|
|
|
bool HandlesOnKill { get; }
|
|
|
|
void OnKill(Mobile killed, Mobile killer);
|
|
|
|
void OnBeforeKill(Mobile killed, Mobile killer);
|
|
|
|
bool HandlesOnKilled { get; }
|
|
|
|
void OnKilled(Mobile killed, Mobile killer);
|
|
|
|
void OnBeforeKilled(Mobile killed, Mobile killer);
|
|
|
|
/*
|
|
bool HandlesOnSkillUse { get; }
|
|
|
|
void OnSkillUse( Mobile m, Skill skill, bool success);
|
|
*/
|
|
|
|
object AttachedTo { get; set; }
|
|
|
|
object OwnedBy { get; set; }
|
|
|
|
bool CanEquip(Mobile from);
|
|
|
|
void OnEquip(Mobile from);
|
|
|
|
void OnRemoved(object parent);
|
|
|
|
void OnAttach();
|
|
|
|
void OnReattach();
|
|
|
|
void OnUse(Mobile from);
|
|
|
|
void OnUser(object target);
|
|
|
|
bool BlockDefaultOnUse(Mobile from, object target);
|
|
|
|
bool OnDragLift(Mobile from, Item item);
|
|
|
|
string OnIdentify(Mobile from);
|
|
|
|
string DisplayedProperties(Mobile from);
|
|
|
|
void AddProperties(ObjectPropertyList list);
|
|
|
|
string AttachedBy { get; }
|
|
|
|
void OnDelete();
|
|
|
|
void Delete();
|
|
|
|
void InvalidateParentProperties();
|
|
|
|
void SetAttachedBy(string name);
|
|
|
|
void OnTrigger(object activator, Mobile from);
|
|
|
|
void OnWeaponHit(Mobile attacker, Mobile defender, BaseWeapon weapon, int damageGiven);
|
|
|
|
int OnArmorHit(Mobile attacker, Mobile defender, Item armor, BaseWeapon weapon, int damageGiven);
|
|
|
|
void Serialize(GenericWriter writer);
|
|
|
|
void Deserialize(GenericReader reader);
|
|
}
|
|
|
|
public abstract class XmlAttachment : IXmlAttachment
|
|
{
|
|
// ----------------------------------------------
|
|
// Private fields
|
|
// ----------------------------------------------
|
|
private ASerial m_Serial;
|
|
|
|
private string m_Name;
|
|
|
|
private object m_AttachedTo;
|
|
|
|
private object m_OwnedBy;
|
|
|
|
private string m_AttachedBy;
|
|
|
|
private bool m_Deleted;
|
|
|
|
private AttachmentTimer m_ExpirationTimer;
|
|
|
|
private TimeSpan m_Expiration = TimeSpan.Zero; // no expiration by default
|
|
|
|
private DateTime m_ExpirationEnd;
|
|
|
|
private DateTime m_CreationTime; // when the attachment was made
|
|
|
|
// ----------------------------------------------
|
|
// Public properties
|
|
// ----------------------------------------------
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public DateTime CreationTime { get { return m_CreationTime; } }
|
|
|
|
public bool Deleted { get { return m_Deleted; } }
|
|
|
|
public bool DoDelete { get { return false; } set { if (value == true) Delete(); } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public int SerialValue { get { return m_Serial.Value; } }
|
|
|
|
public ASerial Serial { get { return m_Serial; } set { m_Serial = value; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public TimeSpan Expiration
|
|
{
|
|
get
|
|
{
|
|
// if the expiration timer is running then return the remaining time
|
|
if (m_ExpirationTimer != null)
|
|
{
|
|
return m_ExpirationEnd - DateTime.UtcNow;
|
|
}
|
|
else
|
|
return m_Expiration;
|
|
}
|
|
set
|
|
{
|
|
m_Expiration = value;
|
|
// if it is already attached to something then set the expiration timer
|
|
if (m_AttachedTo != null)
|
|
{
|
|
DoTimer(m_Expiration);
|
|
}
|
|
}
|
|
}
|
|
|
|
public DateTime ExpirationEnd
|
|
{
|
|
get { return m_ExpirationEnd; }
|
|
}
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual bool CanActivateInBackpack { get { return true; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual bool CanActivateEquipped { get { return true; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual bool CanActivateInWorld { get { return true; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual bool HandlesOnSpeech { get { return false; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual bool HandlesOnMovement { get { return false; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual bool HandlesOnKill { get { return false; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual bool HandlesOnKilled { get { return false; } }
|
|
|
|
/*
|
|
[CommandProperty( AccessLevel.GameMaster )]
|
|
public virtual bool HandlesOnSkillUse { get{return false; } }
|
|
*/
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual string Name { get { return m_Name; } set { m_Name = value; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual object Attached { get { return m_AttachedTo; } }
|
|
|
|
public virtual object AttachedTo { get { return m_AttachedTo; } set { m_AttachedTo = value; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual string AttachedBy { get { return m_AttachedBy; } }
|
|
|
|
public virtual object OwnedBy { get { return m_OwnedBy; } set { m_OwnedBy = value; } }
|
|
|
|
[CommandProperty(AccessLevel.GameMaster)]
|
|
public virtual object Owner { get { return m_OwnedBy; } }
|
|
|
|
// ----------------------------------------------
|
|
// Private methods
|
|
// ----------------------------------------------
|
|
private void DoTimer(TimeSpan delay)
|
|
{
|
|
m_ExpirationEnd = DateTime.UtcNow + delay;
|
|
|
|
if (m_ExpirationTimer != null)
|
|
m_ExpirationTimer.Stop();
|
|
|
|
m_ExpirationTimer = new AttachmentTimer(this, delay);
|
|
m_ExpirationTimer.Start();
|
|
}
|
|
|
|
// a timer that can be implement limited lifetime attachments
|
|
private class AttachmentTimer : Timer
|
|
{
|
|
private XmlAttachment m_Attachment;
|
|
|
|
public AttachmentTimer(XmlAttachment attachment, TimeSpan delay)
|
|
: base(delay)
|
|
{
|
|
Priority = TimerPriority.OneSecond;
|
|
|
|
m_Attachment = attachment;
|
|
}
|
|
|
|
protected override void OnTick()
|
|
{
|
|
m_Attachment.Delete();
|
|
}
|
|
}
|
|
|
|
// ----------------------------------------------
|
|
// Constructors
|
|
// ----------------------------------------------
|
|
public XmlAttachment()
|
|
{
|
|
m_CreationTime = DateTime.UtcNow;
|
|
|
|
// get the next unique serial id
|
|
m_Serial = ASerial.NewSerial();
|
|
|
|
// register the attachment in the serial keyed dictionary
|
|
XmlAttach.HashSerial(m_Serial, this);
|
|
}
|
|
|
|
// needed for deserialization
|
|
public XmlAttachment(ASerial serial)
|
|
{
|
|
m_Serial = serial;
|
|
}
|
|
|
|
// ----------------------------------------------
|
|
// Public methods
|
|
// ----------------------------------------------
|
|
|
|
public static void Initialize()
|
|
{
|
|
XmlAttach.CleanUp();
|
|
}
|
|
|
|
public virtual bool CanEquip(Mobile from)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
public virtual void OnEquip(Mobile from)
|
|
{
|
|
}
|
|
|
|
public virtual void OnRemoved(object parent)
|
|
{
|
|
}
|
|
|
|
public virtual void OnAttach()
|
|
{
|
|
// start up the expiration timer on attachment
|
|
if (m_Expiration > TimeSpan.Zero)
|
|
DoTimer(m_Expiration);
|
|
}
|
|
|
|
public virtual void OnReattach()
|
|
{
|
|
}
|
|
|
|
public virtual void OnUse(Mobile from)
|
|
{
|
|
}
|
|
|
|
public virtual void OnUser(object target)
|
|
{
|
|
}
|
|
|
|
public virtual bool BlockDefaultOnUse(Mobile from, object target)
|
|
{
|
|
return false;
|
|
}
|
|
|
|
public virtual bool OnDragLift(Mobile from, Item item)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
public void SetAttachedBy(string name)
|
|
{
|
|
m_AttachedBy = name;
|
|
}
|
|
|
|
public virtual void OnSpeech(SpeechEventArgs args)
|
|
{
|
|
}
|
|
|
|
public virtual void OnMovement(MovementEventArgs args)
|
|
{
|
|
}
|
|
|
|
public virtual void OnKill(Mobile killed, Mobile killer)
|
|
{
|
|
}
|
|
|
|
public virtual void OnBeforeKill(Mobile killed, Mobile killer)
|
|
{
|
|
}
|
|
|
|
public virtual void OnKilled(Mobile killed, Mobile killer)
|
|
{
|
|
}
|
|
|
|
public virtual void OnBeforeKilled(Mobile killed, Mobile killer)
|
|
{
|
|
}
|
|
|
|
/*
|
|
public virtual void OnSkillUse( Mobile m, Skill skill, bool success)
|
|
{
|
|
}
|
|
*/
|
|
|
|
public virtual void OnWeaponHit(Mobile attacker, Mobile defender, BaseWeapon weapon, int damageGiven)
|
|
{
|
|
}
|
|
|
|
public virtual int OnArmorHit(Mobile attacker, Mobile defender, Item armor, BaseWeapon weapon, int damageGiven)
|
|
{
|
|
return 0;
|
|
}
|
|
|
|
public virtual string OnIdentify(Mobile from)
|
|
{
|
|
return null;
|
|
}
|
|
|
|
public virtual string DisplayedProperties(Mobile from)
|
|
{
|
|
return OnIdentify(from);
|
|
}
|
|
|
|
|
|
public virtual void AddProperties(ObjectPropertyList list)
|
|
{
|
|
}
|
|
|
|
public void InvalidateParentProperties()
|
|
{
|
|
if (AttachedTo is Item)
|
|
{
|
|
((Item)AttachedTo).InvalidateProperties();
|
|
}
|
|
}
|
|
|
|
public void SafeItemDelete(Item item)
|
|
{
|
|
Timer.DelayCall(TimeSpan.Zero, new TimerStateCallback(DeleteItemCallback), new object[] { item });
|
|
|
|
}
|
|
|
|
public void DeleteItemCallback(object state)
|
|
{
|
|
object[] args = (object[])state;
|
|
|
|
Item item = args[0] as Item;
|
|
|
|
if (item != null)
|
|
{
|
|
// delete the item
|
|
item.Delete();
|
|
}
|
|
}
|
|
|
|
public void SafeMobileDelete(Mobile mob)
|
|
{
|
|
Timer.DelayCall(TimeSpan.Zero, new TimerStateCallback(DeleteMobileCallback), new object[] { mob });
|
|
|
|
}
|
|
|
|
public void DeleteMobileCallback(object state)
|
|
{
|
|
object[] args = (object[])state;
|
|
|
|
Mobile mob = args[0] as Mobile;
|
|
|
|
if (mob != null)
|
|
{
|
|
// delete the mobile
|
|
mob.Delete();
|
|
}
|
|
}
|
|
|
|
public void Delete()
|
|
{
|
|
if (m_Deleted) return;
|
|
|
|
m_Deleted = true;
|
|
|
|
if (m_ExpirationTimer != null)
|
|
m_ExpirationTimer.Stop();
|
|
|
|
OnDelete();
|
|
|
|
// dereference the attachment object
|
|
AttachedTo = null;
|
|
OwnedBy = null;
|
|
}
|
|
|
|
public virtual void OnDelete()
|
|
{
|
|
}
|
|
|
|
public virtual void OnTrigger(object activator, Mobile from)
|
|
{
|
|
}
|
|
|
|
public virtual void Serialize(GenericWriter writer)
|
|
{
|
|
writer.Write((int)2);
|
|
// version 2
|
|
writer.Write(m_AttachedBy);
|
|
// version 1
|
|
if (OwnedBy is Item)
|
|
{
|
|
writer.Write((int)0);
|
|
writer.Write((Item)OwnedBy);
|
|
}
|
|
else
|
|
if (OwnedBy is Mobile)
|
|
{
|
|
writer.Write((int)1);
|
|
writer.Write((Mobile)OwnedBy);
|
|
}
|
|
else
|
|
writer.Write((int)-1);
|
|
|
|
// version 0
|
|
writer.Write(Name);
|
|
// if there are any active timers, then serialize
|
|
writer.Write(m_Expiration);
|
|
if (m_ExpirationTimer != null)
|
|
{
|
|
writer.Write(m_ExpirationEnd - DateTime.UtcNow);
|
|
}
|
|
else
|
|
{
|
|
writer.Write(TimeSpan.Zero);
|
|
}
|
|
writer.Write(m_CreationTime);
|
|
}
|
|
|
|
public virtual void Deserialize(GenericReader reader)
|
|
{
|
|
int version = reader.ReadInt();
|
|
|
|
switch (version)
|
|
{
|
|
case 2:
|
|
m_AttachedBy = reader.ReadString();
|
|
goto case 1;
|
|
case 1:
|
|
int owned = reader.ReadInt();
|
|
if (owned == 0)
|
|
{
|
|
OwnedBy = reader.ReadItem();
|
|
}
|
|
else
|
|
if (owned == 1)
|
|
{
|
|
OwnedBy = reader.ReadMobile();
|
|
}
|
|
else
|
|
OwnedBy = null;
|
|
|
|
goto case 0;
|
|
case 0:
|
|
// version 0
|
|
Name = (string)reader.ReadString();
|
|
m_Expiration = reader.ReadTimeSpan();
|
|
TimeSpan remaining = (TimeSpan)reader.ReadTimeSpan();
|
|
|
|
if (remaining > TimeSpan.Zero)
|
|
DoTimer(remaining);
|
|
|
|
m_CreationTime = reader.ReadDateTime();
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|