Go Back   RunUO - Ultima Online Emulation > RunUO > Script Support

Script Support Get support for modifying RunUO Scripts, or writing your own!

Reply
 
Thread Tools Display Modes
Old 08-19-2007, 12:08 AM   #1 (permalink)
Forum Novice
 
Join Date: Dec 2005
Posts: 559
Default Strange CTF Bug

I am using the CTF system (upgraded to 2.0). I have no bugs with the game itself; however, whenever I restart the shard, the CTF automatically starts itself, forcing me to [endgame every time I restart. I have no idea why it's doing this. Here is my CTFGame.cs:

Code:
using Server;
using System;
using System.Collections;
using Server.Gumps;
using Server.Targeting;
using Server.Commands;
using Server.Regions;

namespace Server.Items
{
	public class CTFGame : Item
	{
		private static int m_GameReg = 1;
		private static ArrayList m_Registry = new ArrayList();
        private GameRegion m_Region;

		//public static ArrayList Registry{ get{ return m_Registry; } }

		public static void Initialize()
		{
			EventSink.PlayerDeath += new PlayerDeathEventHandler( OnPlayerDeath );

			CommandSystem.Register( "endgame", AccessLevel.GameMaster, new CommandEventHandler( EndGame_Command ) );
            CommandSystem.Register("startgame", AccessLevel.GameMaster, new CommandEventHandler(StartGame_Command));
            CommandSystem.Register("Team", AccessLevel.Player, new CommandEventHandler(TeamMessage_Command));
            CommandSystem.Register("t", AccessLevel.Player, new CommandEventHandler(TeamMessage_Command));
		}

		private static void TeamMessage_Command( CommandEventArgs e )
		{
			string msg = e.ArgString;
			if ( msg == null )
				return;
			msg = msg.Trim();
			if ( msg.Length <= 0 )
				return;
			
			CTFTeam team = FindTeamFor( e.Mobile );
			if ( team != null )
			{
				msg = String.Format( "Team [{0}]: {1}", e.Mobile.Name, msg );
				for(int m=0;m<team.Members.Count;m++)
					((Mobile)team.Members[m]).SendMessage( msg );
			}
		}

		private static void EndGame_Command( CommandEventArgs e )
		{
			e.Mobile.BeginTarget( -1, false, TargetFlags.None, new TargetCallback( EndGame_Target ) );
			e.Mobile.SendMessage( "Target the game control stone to END a game." );
		}

		private static void EndGame_Target( Mobile from, object o )
		{
			if ( o is CTFGame )
			{
				CTFGame game = (CTFGame)o;
				game.EndGame();
				from.SendMessage( "The game has been ended." );
			}
			else
			{
				from.BeginTarget( -1, false, TargetFlags.None, new TargetCallback( EndGame_Target ) );
				from.SendMessage( "Target the game stone." );
			}
		}

		private static void StartGame_Command( CommandEventArgs e )
		{
			if ( e.Arguments.Length < 1 )
			{
				e.Mobile.SendMessage( "Usage: startgame <ResetTeams>" );
				e.Mobile.SendMessage( "So, if you want to start the game and force everyone to choose a new team, do [startgame true" );
			}
			
			string str = e.GetString( 0 ).ToUpper().Trim();
			bool reset;
			if ( str == "YES" || str == "TRUE" || str == "Y" || str == "T" || str == "1" )
				reset = true;
			else
				reset = false;

			e.Mobile.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( StartGame_Target ), reset );
			e.Mobile.SendMessage( "Target the game control stone to START a game." );
		}

		private static void StartGame_Target( Mobile from, object o, object state )
		{
			bool reset = state is bool ? (bool)state : false;

			if ( o is CTFGame )
			{
				CTFGame game = (CTFGame)o;
				game.StartGame( reset );
				from.SendMessage( "The game has been started." );
			}
			else
			{
				from.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( StartGame_Target ), reset );
				from.SendMessage( "Target the game stone." );
			}
		}

		private static void OnPlayerDeath( PlayerDeathEventArgs e )
		{
			CTFTeam team = FindTeamFor( e.Mobile );
			if ( team != null )
				new DeathTimer( e.Mobile, team ).Start();
		}

		public static CTFTeam FindTeamFor( Mobile m )
		{
			for(int i=0;i<m_Registry.Count;i++)
			{
				CTFGame game = (CTFGame)m_Registry[i];
				CTFTeam team = game.GetTeam( m );
				if ( team != null )
					return team;
			}

			return null;
		}

		private ArrayList m_Teams;
		private int m_Game;

		private bool m_DeathPoint;
		private bool m_GiveRobe;
		private bool m_Open;
		private bool m_Running;
		private bool m_MsgStaff;
		private int m_MaxScore;
		private TimeSpan m_Length;
        private int m_GameType;

		private DateTime m_StartTime;

		private Timer m_GameTimer, m_ScoreTimer;

		[Constructable]
		public CTFGame( int numTeams ) : base( 0xEDC )
		{
			m_Game = m_GameReg++;
			m_Teams = new ArrayList( numTeams );
			m_Length = TimeSpan.FromHours( 1.0 );

			for(int i=0;i<numTeams;i++)
				m_Teams.Add( new CTFTeam( this, i ) );

			Movable = false;
			Name = "Game Control Stone";

			m_Registry.Add( this );

			m_Running = m_Open = false;
            m_GameType = 1;
		}

		public CTFGame( Serial serial ) : base( serial )
		{
		}

		public override void Serialize( GenericWriter writer )
		{
			base.Serialize( writer );

			writer.Write( (int)1 );//version

			writer.Write( m_MaxScore );

			writer.Write( m_Game );
			writer.Write( m_DeathPoint );
			writer.Write( m_GiveRobe );
			writer.Write( m_Open );
			writer.Write( m_MsgStaff );
			writer.Write( m_Length );

			writer.Write( (int)m_Teams.Count );
			for (int i=0;i<m_Teams.Count;i++)
				((CTFTeam)m_Teams[i]).Serialize( writer );
		}

		public override void Deserialize( GenericReader reader )
		{
			base.Deserialize( reader );

			int version = reader.ReadInt();

			switch ( version )
			{
				case 1:
				{
					m_MaxScore = reader.ReadInt();
					goto case 0;
				}
				case 0:
				{
					m_Game = reader.ReadInt();
					m_DeathPoint = reader.ReadBool();
					m_GiveRobe = reader.ReadBool();
					m_Open = reader.ReadBool();
					m_MsgStaff = reader.ReadBool();
					m_Length = reader.ReadTimeSpan();

					int len = reader.ReadInt();
					m_Teams = new ArrayList( len );
					for (int i=0;i<len;i++)
						m_Teams.Add( new CTFTeam( reader ) );
					break;
				}
			}

			EventSink.PlayerDeath += new PlayerDeathEventHandler( OnPlayerDeath );
			m_Registry.Add( this );

			m_Running = m_Open = false;
			Timer.DelayCall( TimeSpan.Zero, new TimerCallback( ResetGame ) );
		}

		[CommandProperty( AccessLevel.Counselor )]
		public bool Running { get { return m_Running; } }

		public override void OnAfterDelete()
		{
			for(int t=0;t<m_Teams.Count;t++)
			{
				CTFTeam team = (CTFTeam)m_Teams[t];
				while ( team.Members.Count > 0 )
					LeaveGame( (Mobile)team.Members[0] );
			}

            if (m_Region != null)
            {
                m_Region.Unregister();
                m_Region = null;
            }
					
			m_Registry.Remove( this );
			m_Teams.Clear();

			base.OnAfterDelete();
		}

		public void LeaveGame( Mobile m )
		{
			CTFTeam t = GetTeam( m );
			if ( t != null )
				t.RemoveMember( m );

			if ( m.AccessLevel == AccessLevel.Player && !m.Blessed )
			{
				if ( m.Alive )
				{
					m.Kill();
					if ( m.Corpse != null && !m.Corpse.Deleted )
						m.Corpse.Delete();
				}
				m.Resurrect();
			}
			
			Item robe = m.FindItemOnLayer( Layer.OuterTorso );
			if ( robe is CTFRobe )
				robe.Delete();
			if ( m.Backpack != null )
			{
				Item[] robes = m.Backpack.FindItemsByType( typeof( CTFRobe ) );
				for(int i=0;i<robes.Length;i++)
					robes[i].Delete();
			}

			m.Delta( MobileDelta.Noto );
		}

		public void PlayerMessage( string message, params object[] args )
		{
			PlayerMessage( String.Format( message, args ) );
		}

		public void PlayerMessage( string message )
		{
			message = "Game: " + message;
			for (int i=0;i<m_Teams.Count;i++)
			{
				CTFTeam team = (CTFTeam)m_Teams[i];
				for (int j=0;j<team.Members.Count;j++)
					((Mobile)team.Members[j]).SendMessage( 0x489, message );
			}

			if ( m_MsgStaff )
				Server.Commands.CommandHandlers.BroadcastMessage( AccessLevel.Counselor, 0x489, message );
		}

		public override void OnSingleClick( Mobile from )
		{
			if ( m_Open )
				LabelTo( from, "Time left: {0:00}:{1:00}:{2:00}", (int)(TimeLeft.TotalSeconds/60/60), (int)(TimeLeft.TotalSeconds/60)%60, (int)(TimeLeft.TotalSeconds)%60 );
			base.OnSingleClick( from );
		}

		public int GameNumber{ get{ return m_Game; } }
		public ArrayList Teams{ get{ return m_Teams; } }
		public TimeSpan TimeLeft{ get{ return m_Length - (DateTime.Now-m_StartTime); } }

		[CommandProperty( AccessLevel.Seer )]
		public bool DeathPoint{ get{ return m_DeathPoint; } set { m_DeathPoint = value; } }

		[CommandProperty( AccessLevel.Seer )]
		public bool GiveRobe{ get{ return m_GiveRobe; } set{ m_GiveRobe = value; } }

		[CommandProperty( AccessLevel.Seer )]
		public bool MessageStaff{ get{ return m_MsgStaff; } set{ m_MsgStaff = value; } }

		[CommandProperty( AccessLevel.Seer )]
		public TimeSpan Length{ get{ return m_Length; } set{ m_Length = value; } }

        [CommandProperty(AccessLevel.Seer)]
        public int GameType{ get { return m_GameType; } set { if(value == 1 || value == 2) m_GameType = value; } }

		[CommandProperty( AccessLevel.Seer )]
		public int MaxScore
		{ 
			get
			{ 
				if ( m_MaxScore <= 0 )
					return int.MaxValue;
				else
					return m_MaxScore; 
			} 
			set{ m_MaxScore = value; } 
		}

		[CommandProperty( AccessLevel.Seer )]
		public int TeamCount
		{
			get { return m_Teams.Count; }
			set
			{
				if ( value > m_Teams.Count )
				{
					for (int i=m_Teams.Count;i<value;i++)
						m_Teams.Add( new CTFTeam( this, i ) );
				}
			}
		}

		[CommandProperty( AccessLevel.Seer )]
		public bool OpenJoin
		{
			get { return m_Open; }
			set { m_Open = value; }
		}

		public bool IsInGame( CTFTeam team )
		{
			return m_Teams != null ? m_Teams.Contains( team ) : false;
		}

		public bool IsInGame( Mobile m )
		{
			return GetTeam( m ) != null;
		}

		public CTFTeam GetTeam( int uid )
		{
			if ( m_Teams != null )
			{
				for (int i=0;i<m_Teams.Count;i++)
				{
					CTFTeam team = (CTFTeam)m_Teams[i];
					if ( team.UId == uid )
						return team;
				}
			}
			return null;
		}

		public CTFTeam GetTeam( Mobile m )
		{
			if ( m_Teams != null )
			{
				for (int i=0;i<m_Teams.Count;i++)
				{
					CTFTeam team = (CTFTeam)m_Teams[i];
					if ( team.Members.Contains( m ) )
						return team;
				}
			}
			return null;
		}

		public override void OnDoubleClick( Mobile from )
		{
			if ( from.AccessLevel >= AccessLevel.Seer )
				from.SendGump( new PropertiesGump( from, this ) );
		}

		public void SwitchTeams( Mobile from, CTFTeam team )
		{
			CTFTeam old = GetTeam( from );
			if ( old == team )
				return;
			else if ( old != null )
				old.RemoveMember( from );

			team.AddMember( from );
			from.Delta( MobileDelta.Noto );

			Item robe = from.FindItemOnLayer( Layer.OuterTorso );
			if ( robe is CTFRobe )
			{
				robe.Name = team.Name + " Game Robe";
				robe.Hue = team.Hue;
			}
			else
			{
				if ( robe != null )
				{
					if ( robe.Movable )
						from.AddToBackpack( robe );
					else
						robe.Delete();
				}
				
				robe = new CTFRobe( team );
				from.EquipItem( robe );
			}
		}

		public int TeamSize
		{
			get
			{
				int count = 0;
				for (int i=0;i<this.Teams.Count;i++)
					count += ((CTFTeam)m_Teams[i]).ActiveMemberCount;

				count /= Teams.Count;
				return count + 5;
			}
		}

		public void EndGame()
		{
			if ( !m_Running )
				return;

			CTFTeam Winner = null;
			
			if ( m_GameTimer != null )
			{
				m_GameTimer.Stop();
				m_GameTimer = null;
			}

			if ( m_ScoreTimer != null )
			{
				m_ScoreTimer.Stop();
				m_ScoreTimer = null;
			}

			for (int i=0;i<m_Teams.Count;i++)
			{
				CTFTeam team = (CTFTeam)m_Teams[i];
				if ( team.Flag != null )
					team.Flag.ReturnToHome();

				if ( Winner == null || team.Points > Winner.Points )
					Winner = team;
			}

			if ( Winner != null )
			{
				PlayerMessage( "The game is over.  The winner is {0} with {1} points!", Winner.Name, Winner.Points );

				
				// Uncomment this and mofiy as nessessary to give prize(s) to the winning team members.
				for (int j=0;j<Winner.Members.Count;j++)
				{
					Mobile m = (Mobile)Winner.Members[j];

					m.BankBox.AddItem( new BankCheck( 25000 ) );
				}
				
			}
			else
			{
				PlayerMessage( "The game is over." );
			}
			
			m_Running = false;
		}

		public void StartGame( bool resetTeams )
		{
			m_Running = false;

			if ( m_GameTimer != null )
				m_GameTimer.Stop();

			if ( m_ScoreTimer != null )
				m_ScoreTimer.Stop();

			if ( resetTeams )
			{
				PlayerMessage( "The game will start in 30 seconds, please select your team." );

				int teamSize = this.TeamSize;
				ArrayList players = new ArrayList();
				for(int i=0;i<m_Teams.Count;i++)
				{
					CTFTeam t = (CTFTeam)m_Teams[i];
					for (int j=0;j<t.Members.Count;j++)
					{
						Mobile m = (Mobile)t.Members[i];
						m.Frozen = true;
						m.SendGump( new GameTeamSelector( this, teamSize ) );
						players.Add( m );
					}

					t.Members.Clear();
				}

				new StartTimer( this, players ).Start();
			}
			else
			{
				ResetGame();
			}

            if (m_GameType == 1)
                m_Region = new GameRegion(1);
            else
                m_Region = new GameRegion(2);
		}

		private class StartTimer : Timer
		{
			public static TimeSpan StartDelay = TimeSpan.FromMinutes( 0.5 );
			private CTFGame m_Game;
			private ArrayList m_List;

			public StartTimer( CTFGame game, ArrayList list ) : base( StartDelay )
			{
				m_Game = game;
				m_List = list;
				Priority = TimerPriority.TwoFiftyMS;
			}
			
			protected override void OnTick()
			{
				int sm = -1, ns = -1;
				int[] amc = new int[m_Game.m_Teams.Count];
				for(int i=0;i<m_Game.m_Teams.Count;i++)
				{
					amc[i] = ((CTFTeam)m_Game.m_Teams[i]).ActiveMemberCount;
					if ( sm == -1 || amc[i] < amc[sm] )
					{
						ns = sm;
						sm = i;
					}
					else if ( amc[i] < amc[ns] )
					{
						ns = i;
					}
				}

				for (int i=0;i<m_List.Count;i++)
				{
					Mobile m = (Mobile)m_List[i];

					m.Frozen = false;
					m.CloseGump( typeof( GameTeamSelector ) );

					if ( m_Game.GetTeam( m ) == null )
					{
						int t;
						if ( m.NetState == null )
						{
							t = Utility.Random( amc.Length );
						}
						else
						{
							if ( amc[sm] >= amc[ns] )
								t = Utility.Random( amc.Length );
							else
								t = sm;
							amc[t]++;
						}

						CTFTeam team = (CTFTeam)m_Game.m_Teams[t];

						m_Game.SwitchTeams( m, team );
						m.SendMessage( "You have joined team {0}!", team.Name );
					}
				}
				m_Game.ResetGame();
			}
		}

		public void ResetGame()
		{
			PlayerMessage( "The game has started." );
			
			m_StartTime = DateTime.Now;

			m_GameTimer = Timer.DelayCall( Length, new TimerCallback( EndGame ) );
			m_Running = true;

			if ( m_ScoreTimer == null )
				m_ScoreTimer = new ScoreTimer( this );
			m_ScoreTimer.Start();

			for (int i=0;i<m_Teams.Count;i++)
			{
				CTFTeam team = (CTFTeam)m_Teams[i];

				team.Points = 0;
				if ( team.Flag != null )
					team.Flag.ReturnToHome();

				for(int j=0;j<team.Members.Count;j++)
				{
					Mobile m = (Mobile)team.Members[j];

					m.Kill();
					if ( m.Corpse != null && !m.Corpse.Deleted )
						m.Corpse.Delete();

					m.LogoutLocation = team.Home;
					m.Location = team.Home;
					m.Location = team.Home;
					m.Map = team.Map;
					
					m.Resurrect();

					m.Hits = m.HitsMax;
					m.Mana = m.ManaMax;
					m.Stam = m.StamMax;
				}
			}
		}

		private class DeathTimer : Timer
		{
			public static TimeSpan DeathDelay =  TimeSpan.FromSeconds( 30 );

			private CTFTeam m_Team;
			private Mobile m_Mob;

			public DeathTimer( Mobile m, CTFTeam t ) : base( DeathDelay )
			{
				m_Mob = m;
				m_Team = t;
				Priority = TimerPriority.TwoFiftyMS;
			}

			protected override void OnTick()
			{
				if ( m_Mob.Corpse != null && !m_Mob.Corpse.Deleted )
					m_Mob.Corpse.Delete();

				if ( !m_Mob.Alive )
				{
					m_Mob.Location = m_Team.Home;
					m_Mob.Map = m_Team.Map;
					m_Mob.Resurrect();
					m_Mob.Hits = m_Mob.HitsMax/2;
					m_Mob.Mana = m_Mob.ManaMax/2;
				}

				if ( m_Team.Game.DeathPoint )
					--m_Team.Points;
			}
		}

		private class ScoreTimer : Timer
		{
			private CTFGame m_Game;

			public ScoreTimer( CTFGame g ) : base( TimeSpan.FromMinutes( 5.0 ), TimeSpan.FromMinutes( 5.0 ) )
			{
				m_Game = g;
			}

			protected override void OnTick()
			{
				m_Game.PlayerMessage( "Time left: {0:0}:{1:00}:{2:00}  <>  Scores:", (int)(m_Game.TimeLeft.TotalSeconds/60/60), (int)(m_Game.TimeLeft.TotalSeconds/60)%60, (int)(m_Game.TimeLeft.TotalSeconds)%60 );
				for (int i=0;i<m_Game.Teams.Count;i++)
				{
					CTFTeam team = (CTFTeam)m_Game.Teams[i];
					m_Game.PlayerMessage( "Team {0}: {1} points", team.Name, team.Points );
				}
			}
		}
	}
}
Thanks in advance for all of your help!
__________________
ICQ/AIM: 220600512
orange white green
Pius Valentine is offline   Reply With Quote
Reply

Bookmarks


Currently Active Users Viewing This Thread: 1 (0 members and 1 guests)
 
Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are Off
Pingbacks are Off
Refbacks are Off



Powered by vBulletin® Version 3.7.0
Copyright ©2000 - 2010, Jelsoft Enterprises Ltd.
SEO by vBSEO 3.2.0 RC5