/// <summary>
        /// Adds a new InSim object to the EventHelper.
        /// </summary>
        /// <param name="settings">The settings for this InSim object.</param>
        /// <returns>The new InSim object</returns>
        public InSim AddInSim(InSimSettings settings)
        {
            var insim = new InSim();

            connections.Add(new Connection(insim, settings));
            return(insim);
        }
        public static void MCI(InSim insim, IS_MCI MCI)
        {
            try
            {
                foreach (CompCar car in MCI.Info)
                {
                    Players NPL;
                    if (Players._players.TryGetValue(car.PLID, out NPL))
                    {
                        foreach (Connections Conn in Connections._connections.Values)
                        {
                            if (Conn.PLID == car.PLID)
                            {
                                Conn.X = (car.X / 65536);
                                Conn.Y = (car.Y / 65536);
                                Conn.Z = (car.Z / 65536);

                                Conn.Heading = ((car.Heading / 256) + 128);
                                Conn.Angle   = (car.AngVel / 16384);

                                Conn.Speed = car.Speed;
                            }
                        }
                    }
                }
            }
            catch (InSimException IEx) { Logger.Error(IEx.Message, Logger.Types.NCN); }
        }
 private void HandlePacket(InSim insim, IS_NPL packet) {
     // add new player to player list
     players[packet.PLID] = new Player(
         packet.PLID,
         StringHelper.StripColors(packet.PName),
         CarHelper.GetFullCarName(packet.CName));
 }
Beispiel #4
0
 private void CarDataIn(InSim insim, IS_MCI mci)
 {
     //Console.WriteLine("IS_MSI pack received");
     for (int i = 0; i < mci.NumC; i++)
     {
         if (allCars.GetCarID(mci.Info[i].PLID) != -1)
         {
             // Milimeters precision
             allCars.UpdateCarRawCoordinates(mci.Info[i].PLID, mci.Info[i].X / 65.535, mci.Info[i].Y / 65.535, mci.Info[i].Z / 65.535);
             // Meters precision
             allCars.UpdateCarCoordinates(mci.Info[i].PLID, mci.Info[i].X / 65535, mci.Info[i].Y / 65535, mci.Info[i].Z / 65535);
             allCars.UpdateCarSpeed(mci.Info[i].PLID, mci.Info[i].Speed);
             allCars.UpdateCarHeading(mci.Info[i].PLID, mci.Info[i].Heading / 182); // Somehow makes it 360 degrees. Will come back later
             allCars.CarCalculations(mci.Info[i].PLID);
         }
         else
         {
             // This will spam a bit while starting program, but necessary later on;
             Console.WriteLine("Requesting info");
             _inSim.Send(
                 new IS_TINY
             {
                 SubT = TinyType.TINY_NPL,
                 ReqI = 1
             }
                 );
         }
     }
 }
Beispiel #5
0
        void ConnectionLeave(InSim insim, IS_CNL CNL)
        {
            try
            {
                _connections.Remove(CNL.UCID);

                if (ConnectedToSQL)
                {
                    try { SqlInfo.UpdateUser(_connections[CNL.UCID].UName, StringHelper.StripColors(_connections[CNL.UCID].PName), _connections[CNL.UCID].TotalDistance, _connections[CNL.UCID].points); }
                    catch (Exception EX)
                    {
                        if (!SqlInfo.IsConnectionStillAlive())
                        {
                            ConnectedToSQL = false;
                            SQLReconnectTimer.Start();
                        }
                        else
                        {
                            LogTextToFile("error", "CNL - Exception: " + EX, false);
                        }
                    }
                }
            }
            catch (Exception e) { LogTextToFile("error", "CNL - Exception: " + e, false); }
        }
Beispiel #6
0
        public static void NPL(InSim insim, IS_NPL NPL)
        {
            try
            {
                if (Players._players.ContainsKey(NPL.PLID))
                {
                    Players._players[NPL.PLID].UCID  = NPL.UCID;
                    Players._players[NPL.PLID].PLID  = NPL.PLID;
                    Players._players[NPL.PLID].PName = NPL.PName;
                    Players._players[NPL.PLID].CName = NPL.CName;
                }
                else
                {
                    Players._players.Add(NPL.PLID, new Players
                    {
                        UCID  = NPL.UCID,
                        PLID  = NPL.PLID,
                        PName = NPL.PName,
                        CName = NPL.CName
                    });
                }

                foreach (Connections Conn in Connections._connections.Values)
                {
                    if (Conn.UCID == NPL.UCID)
                    {
                        Conn.PLID = NPL.PLID;
                    }
                }
            }
            catch (InSimException IEx) { Logger.Error(IEx.Message, Logger.Types.NPL); }
        }
Beispiel #7
0
        // Player laps
        void Res(InSim insim, IS_RES RES)
        {
            try
            {
                var conn = GetConnection(RES.PLID);

                if (PointSystem == true)
                {
                    if (RES.Confirm == ConfirmationFlags.CONF_PENALTY_30)
                    {
                        insim.Send(conn.UCID, "^8You've been fined ^1-1 ^8points for ^230-SECOND PENALTY");
                        conn.points      -= 1;
                        conn.Disqualified = true;
                    }

                    if (RES.Confirm == ConfirmationFlags.CONF_PENALTY_45)
                    {
                        insim.Send(conn.UCID, "^8You've been fined ^1-4 ^8points for ^245-SECOND PENALTY");
                        conn.points      -= 4;
                        conn.Disqualified = true;
                    }
                }
            }
            catch (Exception e) { LogTextToFile("InSim-Errors", "[" + RES.PLID + "] " + " NCN - Exception: " + e, false); }
        }
Beispiel #8
0
        void HotLapValidity(InSim insim, IS_HLV HLV)
        {
            Connections CurrentConnection = GetConnection(HLV.PLID);

            if (TrackName != "")
            {
                if (HLV.HLVC == HlvcFlags.Wall)
                {
                    if (CurrentConnection.SentMSG == false)
                    {
                        insim.Send(CurrentConnection.UCID, "^3CAR CONTACT WITH WALL, HOTLAP INVALIDATED.");
                        CurrentConnection.SentMSG = true;
                    }
                }
            }

            if (HLV.HLVC == HlvcFlags.Ground)
            {
                if (CurrentConnection.SentMSG == false)
                {
                    insim.Send(CurrentConnection.UCID, "^3CAR CONTACT WITH GRASS, HOTLAP INVALIDATED.");
                    CurrentConnection.SentMSG = true;
                }
            }
        }
Beispiel #9
0
        // Race win pos
        void Result(InSim insim, IS_RES RES)
        {
            try
            {
                Connections CurrentConnection = GetConnection(RES.PLID);

                if (CurrentConnection.SentMSG == false)
                {
                    if (RES.ResultNum == 0)
                    {
                        // insim.Send(255, "" + _connections[CurrentConnection.UCID].PName + " ^8finished 1st!");
                        CurrentConnection.points += 4;
                    }
                    else if (RES.ResultNum == 1)
                    {
                        // insim.Send(255, "" + _connections[CurrentConnection.UCID].PName + " ^8finished 2nd!");
                        CurrentConnection.points += 3;
                    }
                    else if (RES.ResultNum == 2)
                    {
                        // insim.Send(255, "" + _connections[CurrentConnection.UCID].PName + " ^8finished 2nd!");
                        CurrentConnection.points += 2;
                    }
                    else if (RES.ResultNum == 3)
                    {
                        // insim.Send(255, "" + _connections[CurrentConnection.UCID].PName + " ^8finished 2nd!");
                        CurrentConnection.points += 1;
                    }
                }

                UpdateGui(CurrentConnection.UCID, true);
            }
            catch (Exception e)
            { LogTextToFile("error", "[" + RES.PLID + "] " + "" + "() BFN - Exception: " + e, false); }
        }
Beispiel #10
0
        // BuTton FunctioN (IS_BFN, SHIFT+I SHIFT+B)
        void ClientRenames(InSim insim, IS_CPR CPR)
        {
            try
            {
                _connections[CPR.UCID].PName = CPR.PName;

                if (ConnectedToSQL)
                {
                    try { SqlInfo.UpdateUser(_connections[CPR.UCID].UName, StringHelper.StripColors(_connections[CPR.UCID].PName), _connections[CPR.UCID].TotalDistance, _connections[CPR.UCID].points); }
                    catch (Exception EX)
                    {
                        if (!SqlInfo.IsConnectionStillAlive())
                        {
                            ConnectedToSQL = false;
                            SQLReconnectTimer.Start();
                        }
                        else
                        {
                            LogTextToFile("error", "CNL - Exception: " + EX, false);
                        }
                    }
                }

                UpdateGui(CPR.UCID, true);
            }
            catch (Exception e)
            { LogTextToFile("error", "[" + CPR.UCID + "] " + StringHelper.StripColors(_connections[CPR.UCID].PName) + "(" + _connections[CPR.UCID].UName + ") BFN - Exception: " + e, false); }
        }
Beispiel #11
0
        // Player joins race or enter track
        void NewPlayer(InSim insim, IS_NPL packet)
        {
            try
            {
                if (_players.ContainsKey(packet.PLID))
                {
                    // Leaving pits, just update NPL object.
                    _players[packet.PLID].UCID  = packet.UCID;
                    _players[packet.PLID].PLID  = packet.PLID;
                    _players[packet.PLID].PName = packet.PName;
                    _players[packet.PLID].CName = packet.CName;
                    _players[packet.PLID].Plate = packet.Plate;
                }
                else
                {
                    // Add new player.
                    _players.Add(packet.PLID, new Players
                    {
                        UCID  = packet.UCID,
                        PLID  = packet.PLID,
                        PName = packet.PName,
                        CName = packet.CName,
                        Plate = packet.Plate
                    });
                }
            }
            catch (Exception e)
            {
                var conn = _players[packet.UCID];
                conn.NoColPlayername = StringHelper.StripColors(conn.PName);

                LogTextToFile("error", "[" + conn.UCID + "] " + conn.NoColPlayername + "(" + _connections[packet.UCID].UName + ") NPL - Exception: " + e, false);
            }
        }
 private void HandlePacket(InSim insim, IS_ISM packet) {
     // joined multiplayer host, request players and state be sent
     insim.Send(
         new IS_TINY { ReqI = 1, SubT= TinyType.TINY_NPL }, // request player packets
         new IS_TINY { ReqI = 1, SubT= TinyType.TINY_SST } // request state packet
     );
 }
 public void RCC_RemoveAll(InSim _inSim)
 {
     _inSim.Send(
         new IS_MST {
         Msg = "/rcc_all", ReqI = 1
     }
         );
 }
 public void SendCommandMessage(InSim _inSim, string message)
 {
     _inSim.Send(
         new IS_MST {
         Msg = message, ReqI = 1
     }
         );
 }
 public void SendLocalMessage(InSim _inSim, string message)
 {
     _inSim.Send(
         new IS_MSL {
         Msg = message, ReqI = 1
     }
         );
 }
 public void RCM_ShowAll(InSim _inSim)
 {
     _inSim.Send(
         new IS_MST {
         Msg = "/rcm_all", ReqI = 1
     }
         );
 }
 public void RCM_SetMessage(InSim _inSim, string text)
 {
     _inSim.Send(
         new IS_MST {
         Msg = "/rcm " + text, ReqI = 1
     }
         );
 }
 public void SendToPitLane(InSim _inSim, string name)
 {
     _inSim.Send(
         new IS_MST {
         Msg = "/pitlane " + name, ReqI = 1
     }
         );
 }
Beispiel #19
0
 // Player laps
 void Res(InSim insim, IS_RES RES)
 {
     try
     {
         var conn = GetConnection(RES.PLID);
     }
     catch (Exception e) { LogTextToFile("InSim-Errors", "[" + RES.PLID + "] " + " NCN - Exception: " + e, false); }
 }
 public static void CNL(InSim insim, IS_CNL CNL)
 {
     try
     {
         Connections._connections.Remove(CNL.UCID);
     }
     catch (InSimException IEx) { Logger.Error(IEx.Message, Logger.Types.CNL); }
 }
Beispiel #21
0
        public CruiseEngine()
        {
            _inSim = new InSim();
            _time  = new TimeManagement();

            allCars    = new AllCars();
            buttons    = new Buttons();
            chat       = new String[100];
            chatBuffer = new String[100];
            count      = 0;
            players    = new PlayerInfo();

            parameters      = new Parameters();
            commands        = new Commands();
            calculations    = new Calculations();
            drag            = new Events.Drag();
            carAheadWarning = new Systems.CarAhead();

            activePLID  = -1;
            activePLID2 = -1;
            active      = true;

            lastCrashNameA = "";
            lastCrashNameB = "";

            avgSpeeds = new double[5];

            _inSim.Bind <IS_MSO>(MessageOut);
            _inSim.Bind <IS_MCI>(CarDataIn);
            _inSim.Bind <IS_STA>(PlayerInfo);
            _inSim.Bind <IS_NPL>(NewPlayer);
            _inSim.Bind <IS_NCN>(NewConnection);
            _inSim.Bind <IS_CNL>(Disconnected);
            _inSim.Bind <IS_PLP>(PlayerPits);
            _inSim.Bind <IS_PLL>(PlayerSpectates);
            _inSim.Bind <IS_CRS>(CarReset);
            _inSim.Bind <IS_PIT>(PITStop);
            _inSim.Bind <IS_PSF>(PITFInished);
            _inSim.Bind <IS_CON>(Crash);
            _inSim.Bind <IS_TOC>(CarTakeOver);
            _inSim.Bind <IS_BTC>(ButtonPressed);
            _inSim.Bind <IS_BTT>(ButtonText);

            // Initialize InSim
            _inSim.Initialize(new InSimSettings
            {
                Host     = "127.0.0.1",
                Port     = 29999,
                Admin    = "ed",
                Interval = 250,
                Flags    = InSimFlags.ISF_MCI + (int)InSimFlags.ISF_LOCAL + (int)InSimFlags.ISF_CON
            });

            // For now, this will give enough time to make a connection without trying to run any inSim commands
            Thread.Sleep(500);
            run();
        }
Beispiel #22
0
 private static void InSimMessageHandler(InSim insim, IS_MSO packet)
 {
     if (packet.UserType == UserType.MSO_O && packet.Msg == "clear")
     {
         var fileName = Assembly.GetExecutingAssembly().Location;
         System.Diagnostics.Process.Start(fileName);
         Environment.Exit(0);
     }
 }
Beispiel #23
0
        private void ButtonGorunumu(InSim insim, IS_MCI mci)
        {
            try
            {
                IS_NCN   conn     = new IS_NCN();
                string[] buttons1 =
                {
                    string.Format(textBox1.Text),
                    string.Format(textBox2.Text),
                    string.Format(textBox3.Text),
                    string.Format(textBox4.Text),
                };

                for (byte i = 0, id = 1, top = (byte)numericUpDown1.Value; i < buttons1.Length; i++, id++, top += (byte)numericUpDown5.Value)
                {
                    insim.Send(new IS_BTN
                    {
                        ReqI    = 255,
                        UCID    = conn.UCID,
                        ClickID = id,
                        BStyle  = ButtonStyles.ISB_DARK | ButtonStyles.ISB_LEFT,
                        T       = top,
                        L       = (byte)numericUpDown2.Value,
                        W       = (byte)numericUpDown3.Value,
                        H       = (byte)numericUpDown4.Value,
                        Text    = buttons1[i],
                    });
                }


                string[] buttons2 =
                {
                    string.Format(textBox5.Text),
                    string.Format(textBox6.Text),
                    string.Format(textBox7.Text),
                    string.Format(textBox8.Text),
                };

                for (byte i = 0, id = 5, top = (byte)numericUpDown6.Value; i < buttons2.Length; i++, id++, top += (byte)numericUpDown10.Value)
                {
                    insim.Send(new IS_BTN
                    {
                        ReqI    = 255,
                        UCID    = conn.UCID,
                        ClickID = id,
                        BStyle  = ButtonStyles.ISB_DARK | ButtonStyles.ISB_LEFT,
                        T       = top,
                        L       = (byte)numericUpDown7.Value,
                        W       = (byte)numericUpDown8.Value,
                        H       = (byte)numericUpDown9.Value,
                        Text    = buttons2[i],
                    });
                }
            }
            catch { }
        }
 public void RequestSTA(InSim _inSim)
 {
     _inSim.Send(
         new IS_TINY
     {
         SubT = TinyType.TINY_SST,
         ReqI = 1
     }
         );
 }
Beispiel #25
0
 // Removes PLID from player and removes the car with same PLID
 private void PlayerSpectates(InSim insim, IS_PLL pll)
 {
     if (allCars.GetCarID(pll.PLID) != -1)
     {
         string text = players.GetNameByPLID(pll.PLID) + "^3 went to spectate and drove " + (allCars.GetCarByPLID(pll.PLID).GetDistance()) + " meters";
         commands.SendLocalMessage(_inSim, text);
         players.RemoveCarByPLID(pll.PLID);
         allCars.RemoveCarByPLID(pll.PLID);
     }
 }
 public void RequestPlayersOnTrack(InSim _inSim)
 {
     _inSim.Send(
         new IS_TINY
     {
         SubT = TinyType.TINY_NPL,
         ReqI = 1
     }
         );
 }
 public void RequestAllConnections(InSim _inSim)
 {
     _inSim.Send(
         new IS_TINY
     {
         SubT = TinyType.TINY_NCN,
         ReqI = 1
     }
         );
 }
Beispiel #28
0
        // Player Leave
        void PlayerLeave(InSim insim, IS_PLL PLL)
        {
            try
            {
                Connections CurrentConnection = GetConnection(PLL.PLID);

                CurrentConnection.OnTrack = false;
            }
            catch (Exception e)
            { LogTextToFile("error", "[PLL] " + StringHelper.StripColors(_connections[PLL.PLID].PName) + "(" + _connections[PLL.PLID].UName + ") PLL - Exception: " + e, false); }
        }
Beispiel #29
0
        public BatchHelper(InSim insim)
        {
            if (insim == null)
            {
                throw new ArgumentNullException("insim");
            }

            this.insim = insim;

            BatchSize  = 2048; // bytes
            BatchDelay = 100;  // milliseconds
        }
Beispiel #30
0
 private void ButtonText(InSim insim, IS_BTT btt)
 {
     try
     {
         drag.distanceToDrive = Convert.ToInt32(btt.Text);
     }
     catch (Exception e)
     {
         drag.distanceToDrive = 0;
         Console.WriteLine("Could not convert number. Letters or symbols present in text");
         Console.WriteLine(e);
     }
 }
        public RaceControl() {
            insim = new InSim();

            // bind packet events.
            insim.Bind<IS_ISM>(HandlePacket);
            insim.Bind<IS_STA>(HandlePacket);
            insim.Bind<IS_NPL>(HandlePacket);
            insim.Bind<IS_PLL>(HandlePacket);
            insim.Bind<IS_LAP>(HandlePacket);
            insim.Bind<IS_SPX>(HandlePacket);

            players = new Dictionary<byte, Player>(32);
        }
Beispiel #32
0
        // BuTton FunctioN (IS_BFN, SHIFT + I)
        void ClearButtons(InSim insim, IS_BFN BFN)
        {
            try
            {
                insim.Send(BFN.UCID, "^8InSim buttons cleared ^7(SHIFT + I)");
            }
            catch (Exception e)
            {
                var conn = _players[BFN.UCID];
                conn.NoColPlayername = StringHelper.StripColors(conn.PName);

                LogTextToFile("error", "[" + conn.UCID + "] " + conn.NoColPlayername + "(" + _connections[BFN.UCID].UName + ") BFN - Exception: " + e, false);
            }
        }
Beispiel #33
0
 private void OnStateChange(InSim insim, IS_STA STA)
 {
     try
     {
         if (TrackName != STA.Track)
         {
             TrackName = STA.Track;
             insim.Send(new IS_TINY {
                 SubT = TinyType.TINY_AXI, ReqI = 255
             });
         }
     }
     catch (Exception EX) { LogTextToFile("packetError", "STA - " + EX.Message); }
 }
        private void HandlePacket(InSim insim, IS_SPX packet) {
            // get player from players list and add new split
            var player = players[packet.PLID];

            player.AddSplit(packet.Split, packet.STime);
        }
Beispiel #35
0
        public void updatePIT(InSim.Decoder.PIT pitDec)
        {
            int CurrIdxSplit;

            if (this.finished == true)
                return;
            this.numStop = pitDec.NumStop;
            CurrIdxSplit = this.pit.Add(new Pit(pitDec.LapsDone, pitDec.Flags, pitDec.Penalty, pitDec.NumStop, pitDec.rearL, pitDec.rearR, pitDec.frontL, pitDec.frontR, pitDec.Work));
        }
 private void HandlePacket(InSim insim, IS_STA packet) {
     // occurs when LFS state changes, store current track
     currentTrack = TrackHelper.GetFullTrackName(packet.Track);
 }
Beispiel #37
0
//        void Loop(System.Net.Sockets.UdpClient uc)
        void Loop(InSim.Connect insimConnection )
        {

            bool InRace = false;
            bool InQual = false;
            bool flagFirst = true;
            bool flagShowInfo = true;


//            System.Net.IPEndPoint remoteEP = new System.Net.IPEndPoint(System.Net.IPAddress.Any, 0);

            while (true)
            {
//                byte[] recvPacket = uc.Receive(ref remoteEP);
                byte[] recvPacket = insimConnection.Receive();
#if MONO
#else
                if (remoteEP.Port != ((System.Net.IPEndPoint)uc.Client.RemoteEndPoint).Port)
                {
                    Console.WriteLine("Received UDP packet from unknown port {0}", ((System.Net.IPEndPoint)uc.Client.RemoteEndPoint).Port);
                    continue;
                }
#endif

                if (recvPacket.Length > 3)
                {
                    string packetHead = insimConnection.packetHead(recvPacket);
                    uint verifyID = insimConnection.verifyID(recvPacket);
//                    if (packetHead != "MCI")
//                        Console.WriteLine(packetHead);
                    switch (packetHead)
                    {
                        case "TINY"://confirm ack with ack
// Keep ALIVE
                            InSim.Decoder.TINY tiny = new InSim.Decoder.TINY(recvPacket);
// Keep alive connection
                            if (tiny.SubT == "TINY_NONE")
                            {
                                byte[] stiny = InSim.Encoder.TINY_NONE();
                                insimConnection.Send(stiny, stiny.Length);
                            }
                            break;

                        case "RST":

                            InSim.Decoder.RST rst = new InSim.Decoder.RST(recvPacket);
                            if (debugmode)
                                Console.WriteLine("Race STart : Lap " + rst.RaceLaps + " Qual :" + rst.QualMins);

/* Décalé sur REO à cause de posGrid */
                        // If in Race and new restart, Generate Stat ( For live lfsStat )
                        // On End of Race, générate Statistics
                            if (InRace == true)
							{
								InRace = false;
                                Console.WriteLine("End OF RACE by Race STart");
#if WINDOWS
								Console.Title = consoleTitle;
#endif
								switch (exportOnRaceSTart)
								{
									case "yes":
										if (askForFileNameOnRST)
										{
											Console.Write("> Enter name of stats: ");
											exportRaceStats(Console.ReadLine());
										}
										else
										{
											exportRaceStats(generateFileName());
										}
										break;

									case "ask":
										Console.Write("> Export Stats? [yes/no]: ");
										string answer = Console.ReadLine();

										if (answer.Equals("yes", StringComparison.OrdinalIgnoreCase)
											|| answer.Equals("y", StringComparison.OrdinalIgnoreCase))
										{
											if (askForFileNameOnRST)
											{
												Console.Write("> Enter name of stats: ");
												exportRaceStats(Console.ReadLine());
											}
											else
											{
												exportRaceStats(generateFileName());
											}
										}
										break;

									case "no":
										break;
								}
                            }
/**/
                            // On End of Race, générate Statistics
                            if (InQual == true)
							{
								InQual = false;
                                Console.WriteLine("End OF Qual by Race STart");
#if WINDOWS
                                Console.Title = consoleTitle;
#endif
								switch (exportOnRaceSTart)
								{
									case "yes":
										if (askForFileNameOnRST)
										{
											Console.Write("> Enter name of stats: ");
											exportQualStats(Console.ReadLine());
										}
										else
										{
											exportQualStats(generateFileName());
										}
										break;

									case "ask":
										Console.Write("> Export Stats? [yes/no]: ");
										string answer = Console.ReadLine();

										if (answer.Equals("yes", StringComparison.OrdinalIgnoreCase)
											|| answer.Equals("y", StringComparison.OrdinalIgnoreCase))
										{
											if (askForFileNameOnRST)
											{
												Console.Write("> Enter name of stats: ");
												exportQualStats(Console.ReadLine());
											}
											else
											{
												exportQualStats(generateFileName());
											}
										}
										break;

									case "no":
										break;
								}
                            }

                            Console.WriteLine("Race STart");
#if WINDOWS
                            Console.Title = "Lap : 1";
#endif
                            if (rst.RaceLaps != 0)
                            {
                                InRace = true;
                                InQual = false;
                            }
                            if (rst.QualMins != 0)
                            {
                                InQual = true;
                                InRace = false;
                            }
                            raceStat.Clear();
                            UCIDToUN.Clear();
                            PLIDToUCID.Clear();
// Get All Connections
                            byte[] rstncn = InSim.Encoder.NCN();
                            insimConnection.Send(rstncn, rstncn.Length);
                            // Get All Players
                            byte[] rstnpl = InSim.Encoder.NPL();
                            insimConnection.Send(rstnpl, rstnpl.Length);
// Get Reo
                            byte[] nplreo = InSim.Encoder.REO();
                            insimConnection.Send(nplreo, nplreo.Length);

                            break;

                        case "REN":
                            if(debugmode)Console.WriteLine("Race ENd (return to entry screen)");
                            break;

                        case "NCN":
                            InSim.Decoder.NCN newConnection = new InSim.Decoder.NCN(recvPacket);
                            
                            if (debugmode) Console.WriteLine(string.Format("New ConN Username:{0} Nickname:{1} ConnectionNumber:{2}",newConnection.userName,newConnection.nickName,newConnection.UCID));

//                            Console.WriteLine( newConnection.UCID.ToString() + " ConN Username <" + newConnection.userName + ">  nickName <" + newConnection.nickName  + ">" );
// On reconnect player, RAZ infos et restart
                            UCIDToUN[newConnection.UCID] = new UN(newConnection.userName, newConnection.nickName);
                            if (newConnection.UCID == 0)
                                currInfoRace.HName = newConnection.nickName;
                            break;

                        case "CNL":
                            if(debugmode)Console.WriteLine("ConN Leave (end connection is moved down into this slot)");
                            InSim.Decoder.CNL lostConnection = new InSim.Decoder.CNL(recvPacket);
                            if (debugmode) Console.WriteLine(string.Format("Username:{0} Nickname:{1} ConnectionNumber:{2}",
                                    (UCIDToUN[lostConnection.UCID] as UN ).userName,
                                    (UCIDToUN[lostConnection.UCID] as UN).nickName, 
                                    lostConnection.UCID)
                            );
                            break;

                        case "NPL":
                            int LastPosGrid;
                            if(debugmode)Console.WriteLine("New PLayer joining race (if number already exists, then leaving pits)");
                            InSim.Decoder.NPL newPlayer = new InSim.Decoder.NPL(recvPacket);
                            int removePLID = PLIDbyNickName(newPlayer.nickName);
//                            Console.WriteLine("Nick:" + newPlayer.nickName);
//                            Console.WriteLine("Old PLID:" + removePLID + " New : " + newPlayer.PLID);
                            LastPosGrid = 0;
                            if (InRace == true)
                            {
                                if (removePLID > 0)
                                {
                                    if ((raceStat[removePLID] as raceStats).finished == false)
                                    {
                                        LastPosGrid = (raceStat[removePLID] as raceStats).gridPos;
                                        raceStat.Remove(removePLID);
                                        PLIDToUCID.Remove(removePLID);
                                    }
                                    else
                                    {
                                        if (newPlayer.PLID != removePLID)
                                        {
                                            raceStat[newPlayer.PLID] = raceStat[removePLID];
                                            (raceStat[newPlayer.PLID] as raceStats).PLID = newPlayer.PLID;
                                            raceStat.Remove(removePLID);
                                            PLIDToUCID.Remove(removePLID);
                                        }
                                    }
                                }
                            }
                            if (InQual == true)
                            {
                                if (removePLID > 0)
                                {
                                    if (newPlayer.PLID != removePLID)
                                    {
                                        raceStat[newPlayer.PLID] = raceStat[removePLID];
                                        (raceStat[newPlayer.PLID] as raceStats).PLID = newPlayer.PLID;
                                        raceStat.Remove(removePLID);
                                        PLIDToUCID.Remove(removePLID);
                                    }
                                }
                            }

                            PLIDToUCID[newPlayer.PLID] = newPlayer.UCID;
                            string nplUserName = UserNameByUCID( newPlayer.UCID);

                            if (!raceStat.ContainsKey(newPlayer.PLID))
                            {
                                raceStat[newPlayer.PLID] = new raceStats ( newPlayer.UCID , newPlayer.PLID  );
                                if( LastPosGrid != 0 )
                                    (raceStat[newPlayer.PLID] as raceStats).gridPos = LastPosGrid;
                            }
                            (raceStat[newPlayer.PLID] as raceStats).UCID = newPlayer.UCID;
                            (raceStat[newPlayer.PLID] as raceStats).userName = nplUserName;
                            (raceStat[newPlayer.PLID] as raceStats).nickName = newPlayer.nickName;
                            (raceStat[newPlayer.PLID] as raceStats).allUN[nplUserName] = new UN(nplUserName, newPlayer.nickName);
                            (raceStat[newPlayer.PLID] as raceStats).CName = newPlayer.CName;
                            (raceStat[newPlayer.PLID] as raceStats).Plate = newPlayer.Plate;
                            if( InQual )
                                (raceStat[newPlayer.PLID] as raceStats).finPLID = newPlayer.PLID;

                            string addInfo = "";
                            for (int i = 1; i < 13; i++)
                            {
                                if (((uint)(newPlayer.Flags) & (uint)(2 << i)) != 0)
                                    addInfo += ((InSim.Decoder.NPL.PlayerFlags)(2 << i)).ToString() + " ";
                            }
                            (raceStat[newPlayer.PLID] as raceStats).sFlags = addInfo;
                            break;

                        case "PLP":
                            if(debugmode)Console.WriteLine("PLayer Pits (go to settings - stays in player list)");

                            InSim.Decoder.PLP plp = new InSim.Decoder.PLP(recvPacket);
                            break;

                        case "PLL":
                            if(debugmode)Console.WriteLine("PLayer Leave race (spectate - leaves player list, all are shunted down)");

                            InSim.Decoder.PLL pll = new InSim.Decoder.PLL(recvPacket);
                            break;

                        case "CPR":
                            InSim.Decoder.CPR cpr = new InSim.Decoder.CPR(recvPacket);

                            (UCIDToUN[cpr.UCID] as UN).nickName = cpr.newNickName;
                            if (UCIDToPLID(cpr.UCID) != -1)
                                (raceStat[UCIDToPLID(cpr.UCID)] as raceStats).nickName = cpr.newNickName;
                            if (debugmode) Console.WriteLine(string.Format("Conn Player {0} Rename from {1} to {2}, id:{3}", (UCIDToUN[cpr.UCID] as UN).userName, (UCIDToUN[cpr.UCID] as UN).nickName, cpr.newNickName, cpr.UCID));
                            break;

                        case "CLR":
                            if(debugmode)Console.WriteLine("CLear Race - all players removed from race in one go");

                            raceStat.Clear();

                            break;
                        case "PIT": // NEW PIT : (pit stop)
                            InSim.Decoder.PIT pitDec = new InSim.Decoder.PIT(recvPacket);
                            string pitNickName = (UCIDToUN[(int)PLIDToUCID[pitDec.PLID]] as UN).nickName;
                            string pitUserName = (UCIDToUN[(int)PLIDToUCID[pitDec.PLID]] as UN).userName;
                            (raceStat[pitDec.PLID] as raceStats).updatePIT(pitDec);
                            if (debugmode) Console.WriteLine("PIT OF " + (UCIDToUN[pitDec.PLID] as UN).nickName);
//                            Console.WriteLine("PIT OF >" + pitNickName + "< >" + pitUserName + "<");

                            break;
                        case "PSF": // NEW PSF : (pit stop finished)
                            InSim.Decoder.PSF pitFin = new InSim.Decoder.PSF(recvPacket);
                            (raceStat[pitFin.PLID] as raceStats).updatePSF(pitFin.PLID, pitFin.STime );
                            break;

                        case "LAP":

                            InSim.Decoder.LAP lapDec = new InSim.Decoder.LAP(recvPacket);
                            string lapNickName = (UCIDToUN[(int)PLIDToUCID[lapDec.PLID]] as UN).nickName;
                            string lapUserName = (UCIDToUN[(int)PLIDToUCID[lapDec.PLID]] as UN).userName;
                            if (debugmode) Console.WriteLine("LAP time " + lapUserName);
// In qual use RES instead of Lap
                            if (InQual == true)
                            {
                                break;
                            }
                           (raceStat[lapDec.PLID] as raceStats).UpdateLap((lapDec.LTime), (raceStat[lapDec.PLID] as raceStats).numStop, lapDec.LapsDone );
                           if (flagShowInfo)
                               Console.WriteLine("Lap" + lapDec.LapsDone + " " + (raceStat[lapDec.PLID] as raceStats).userName + " -> " + raceStats.LfstimeToString(lapDec.LTime));
                            if (lapDec.LapsDone > currInfoRace.currLap)
                            {
                                currInfoRace.currLap = lapDec.LapsDone;
#if WINDOWS
                                Console.Title = "Lap : " + (lapDec.LapsDone +1).ToString();
#endif
                            }
                            break;

//                        case "SP1":
//                        case "SP2":
//                        case "SP3":
                        case "SPX":
                            InSim.Decoder.SPX splitdec = new InSim.Decoder.SPX(recvPacket);
// Assign temporary nickname to Player ID
                            if (splitdec.STime == timeConv.HMSToLong(60, 0, 0))
                                break;
                            (raceStat[splitdec.PLID] as raceStats).UpdateSplit(splitdec.Split, splitdec.STime);
                            if( flagShowInfo )
                                Console.WriteLine("SP" + splitdec.Split + " " + (raceStat[splitdec.PLID] as raceStats).userName + " = " +  raceStats.LfstimeToString(splitdec.STime ));
                            if (splitdec.Split == 1)
                            {
                                if( currInfoRace.maxSplit < 1 )
                                    currInfoRace.maxSplit = 1;
                            }
                            if (splitdec.Split == 2)
                            {
                                if (currInfoRace.maxSplit < 2)
                                    currInfoRace.maxSplit = 2;
                            }
                            if (splitdec.Split == 3)
                            {
                                if (currInfoRace.maxSplit < 3)
                                    currInfoRace.maxSplit = 3;
                            }
                            break;

                        case "RES":
                            InSim.Decoder.RES result = new InSim.Decoder.RES(recvPacket);
                            if (debugmode) Console.WriteLine("RESult (qualify or finish)");
                            if (InRace == true)
                            {
                                if (flagShowInfo)
                                    Console.WriteLine("RES " + result.ResultNum.ToString() + ":" + exportstats.lfsStripColor(result.nickName));
                            }
                            int lplid = result.PLID;
                            if (result.PLID == 0)
                                lplid = PLIDbyNickName(result.nickName);
// Retreive current PLID with the Finish PLID, in case of player spectate and rejoin race after finish
                            lplid = PLIDbyFinPLID(lplid);
                            if (lplid != -1 && InRace == true)
                                (raceStat[lplid] as raceStats).UpdateResult(result.TTime, result.ResultNum, result.CName, result.Confirm, result.NumStops);
                            if (lplid != -1 && InQual == true)
                            {
                                if (flagShowInfo)
                                    Console.WriteLine("Lap " + (raceStat[lplid] as raceStats).userName + " -> " + raceStats.LfstimeToString(result.BTime));
                                (raceStat[lplid] as raceStats).UpdateQualResult(result.TTime,
                                                                                result.BTime,
                                                                                result.NumStops,
                                                                                result.Confirm,
                                                                                result.LapDone,
                                                                                result.ResultNum,
                                                                                result.NumRes
                                );
                            }

                            break;
                        case "FIN": // New Insim Packet
                            InSim.Decoder.FIN fin = new InSim.Decoder.FIN(recvPacket);
//                            if (debugmode) 
                                Console.WriteLine("FINISH (qualify or finish)");
                            (raceStat[fin.PLID] as raceStats).finished = true;
                            (raceStat[fin.PLID] as raceStats).finPLID = fin.PLID;
                            break;
                        case "REO":
                            InSim.Decoder.REO pacreo = new InSim.Decoder.REO(recvPacket);
                            if (debugmode) 
                                 Console.WriteLine("REOrder (when race restarts after qualifying)");

                            if (pacreo.ReqI != 0) // Ignore and get Only if requested
                            {
                                for (int i = 0; i < pacreo.NumP; i++)
                                {
                                    int PLID = (int)pacreo.PLID[i];
                                    if (!raceStat.ContainsKey(PLID))
                                    {
                                        raceStat[PLID] = new raceStats(0, PLID);
                                    }
                                    (raceStat[PLID] as raceStats).gridPos = i + 1;
                                }
                            }
                            break;

                        case "STA":
//                            Console.WriteLine("STATE");
                            if (debugmode) Console.WriteLine("STAte");
                            InSim.Decoder.STA state = new InSim.Decoder.STA(recvPacket);
                            if (flagFirst == true && (state.Flags & 512) == 512)
                            {
                                flagFirst = false;
                                // Get All Connections
                                byte[] ncn = InSim.Encoder.NCN();
                                insimConnection.Send(ncn, ncn.Length);
                                // Get All Players
                                byte[] npl = InSim.Encoder.NPL();
                                insimConnection.Send(npl, npl.Length);
                            }
                            currInfoRace.currentTrackName = state.ShortTrackName;
                            currInfoRace.weather = state.Weather;
                            currInfoRace.wind = state.Wind;
                            currInfoRace.raceLaps = state.RaceLaps;
                            currInfoRace.qualMins = state.QualMins;
                            if (currInfoRace.raceLaps == 0)
                                currInfoRace.sraceLaps = "Practice";
                            else if (currInfoRace.raceLaps < 100)
                                currInfoRace.sraceLaps = currInfoRace.raceLaps.ToString();
                            else if (currInfoRace.raceLaps < 191)
                                currInfoRace.sraceLaps = ((currInfoRace.raceLaps - 100) * 10 + 100).ToString();
                            else if (currInfoRace.raceLaps < 239)
                                currInfoRace.sraceLaps = (currInfoRace.raceLaps - 190).ToString();

                            if (debugmode) Console.WriteLine("Current track:" + currInfoRace.currentTrackName);
                            // On End of Race, générate Statistics
                            if (state.RaceInProg == 0 && InRace == true)
                            {
                                InRace = false;
                                Console.WriteLine("End OF RACE by STAte");
#if WINDOWS
                                Console.Title = consoleTitle;
#endif
								switch (exportOnSTAte)
								{
									case "yes":
										if (askForFileNameOnSTA)
										{
											Console.Write("> Enter name of stats: ");
											exportRaceStats(Console.ReadLine());
										}
										else
										{
											exportRaceStats(generateFileName());
										}
										break;

									case "ask":
										Console.Write("> Export Stats? [yes/no]: ");
										string answer = Console.ReadLine();

										if (answer.Equals("yes", StringComparison.OrdinalIgnoreCase)
											|| answer.Equals("y", StringComparison.OrdinalIgnoreCase))
										{
											if (askForFileNameOnSTA)
											{
												Console.Write("> Enter name of stats: ");
												exportRaceStats(Console.ReadLine());
											}
											else
											{
												exportRaceStats(generateFileName());
											}
										}
										break;

									case "no":
										break;
								}
                            }
                            // On End of Race, générate Statistics
                            if (state.RaceInProg == 0 && InQual == true)
                            {
                                InQual = false;
                                Console.WriteLine("End of Qual by STAte");
#if WINDOWS
                                Console.Title = consoleTitle;
#endif
								switch (exportOnSTAte)
								{
									case "yes":
										if (askForFileNameOnSTA)
										{
											Console.Write("> Enter name of stats: ");
											exportQualStats(Console.ReadLine());
										}
										else
										{
											exportQualStats(generateFileName());
										}
										break;

									case "ask":
										Console.Write("> Export Stats? [yes/no]: ");
										string answer = Console.ReadLine();

										if (answer.Equals("yes", StringComparison.OrdinalIgnoreCase)
											|| answer.Equals("y", StringComparison.OrdinalIgnoreCase))
										{
											if (askForFileNameOnSTA)
											{
												Console.Write("> Enter name of stats: ");
												exportQualStats(Console.ReadLine());
											}
											else
											{
												exportQualStats(generateFileName());
											}
										}
										break;

									case "no":
										break;
								}
                            }
                            break;
/*
                        case "MSS":
                            InSim.Decoder.MSS mss = new InSim.Decoder.MSS(recvPacket);
                            if (debugmode) Console.WriteLine("Message received Username:{0} Player name:{1} Message:{2}",mss.UserName,mss.PlayerName,mss.Message);
                            string nicknamewithoutcolors = mss.PlayerName;

                            ackReq = false;
                            break;
*/

                        case "MSO":
                            InSim.Decoder.MSO msg = new InSim.Decoder.MSO(recvPacket);
                            if (debugmode) Console.WriteLine("Message received:" + msg.message);

                            if (msg.message.StartsWith("!ver"))
                                Ver(msg.PLID);
                            if (msg.UserType == 1)
                            {
								string schat = exportstats.lfsColorToHtml(NickNameByUCID(msg.UCID)) + ":" + exportstats.lfsChatTextToHtml(msg.message);
                                currInfoRace.chat.Add(schat);
                            }
                            break;
                        case "ISM":
                            InSim.Decoder.ISM multi = new InSim.Decoder.ISM(recvPacket);
                            if (debugmode) Console.WriteLine("Insim Multi:" + multi.HName);
                            // Get All Connections
                            byte[] ismncn = InSim.Encoder.NCN();
                            insimConnection.Send(ismncn, ismncn.Length);
                            // Get All Players
                            byte[] ismnpl = InSim.Encoder.NPL();
                            insimConnection.Send(ismnpl, ismnpl.Length);
                            break;

                        case "MCI":

                            InSim.Decoder.MCI mci = new InSim.Decoder.MCI(recvPacket );
                            for (int i = 0; i < System.Math.Min(8, mci.numOfPlayers); i++)
                            {
                                if (raceStat.ContainsKey(mci.compCar[i].PLID))
                                {
                                    (raceStat[mci.compCar[i].PLID] as raceStats).updateMCI(mci.compCar[i].speed);
                                }
                            }
                            break;
                        case "FLG": // NEW FLG : (yellow or blue flags)
                            InSim.Decoder.FLG flg = new InSim.Decoder.FLG(recvPacket);
                            if (flg.OffOn == 1 && flg.Flag == 1 && (raceStat[flg.PLID] as raceStats).inBlue == false)
                            { // Blue flag On
                                (raceStat[flg.PLID] as raceStats).blueFlags++;
                                (raceStat[flg.PLID] as raceStats).inBlue = true;
                            }
                            if (flg.OffOn == 1 && flg.Flag == 2 && (raceStat[flg.PLID] as raceStats).inYellow == false)
                            { // Yellow flag On
                                (raceStat[flg.PLID] as raceStats).yellowFlags++;
                                (raceStat[flg.PLID] as raceStats).inYellow = true;
                            }
                            if (flg.OffOn == 0 && flg.Flag == 1)
                            { // Blue flag Off
                                (raceStat[flg.PLID] as raceStats).inBlue = false;
                            }
                            if (flg.OffOn == 0 && flg.Flag == 2)
                            { // Yellow flag Off
                                (raceStat[flg.PLID] as raceStats).inYellow = false;
                            }
                            break;
                        case "PEN": // NEW PEN : (penalty)
                            InSim.Decoder.PEN pen = new InSim.Decoder.PEN(recvPacket);
                            (raceStat[pen.PLID] as raceStats).UpdatePen(pen.OldPen,pen.NewPen,pen.Reason);
                            break;
                        case "NLP":
                            break;
                        case "VTC":
                            break;
                        case "VTN": // Insim Vote
                            break;
                        case "VTA": // Insim Vote Action
                            break;
                        case "III": // NEW III : InSimInfo
                            break;
                        case "PLA": // NEW PLA : (Pit LAne)
                            break;
                        case "TOC": // NEW TOC : (take over car)
                            #region TOC
                            InSim.Decoder.TOC toc = new InSim.Decoder.TOC(recvPacket);
                            if ( !raceStat.ContainsKey(toc.PLID) )
                            {
                                break;
                            }
                            currInfoRace.isToc = true;


                            int OldPLID = UCIDToPLID(toc.NewUCID);
                            PLIDToUCID.Remove(OldPLID);
                            raceStat.Remove(OldPLID);

                            string oldUserName = (raceStat[toc.PLID] as raceStats).userName;
                            string oldNickName = (raceStat[toc.PLID] as raceStats).nickName;
                            (raceStat[toc.PLID] as raceStats).nickName = (UCIDToUN[toc.NewUCID] as UN).nickName;
                            (raceStat[toc.PLID] as raceStats).userName = (UCIDToUN[toc.NewUCID] as UN).userName;
                            (raceStat[toc.PLID] as raceStats).allUN[(UCIDToUN[toc.NewUCID] as UN).userName] = new UN( (UCIDToUN[toc.NewUCID] as UN).userName, (UCIDToUN[toc.NewUCID] as UN).nickName );
                            string newUserName = (raceStat[toc.PLID] as raceStats).userName;
                            string newNickName = (raceStat[toc.PLID] as raceStats).nickName;
                            (raceStat[toc.PLID] as raceStats).updateTOC(oldNickName, oldUserName, newNickName, newUserName);
                            Console.WriteLine("<<<--------------------- TOC: " + oldUserName + "-->" + newUserName + "--------------------->>>");

                            PLIDToUCID[toc.PLID] = toc.NewUCID;
                            #endregion
                            break;
/*
                        case "TOC": // NEW TOC : (take over car)
                            if (debugmode) Console.WriteLine("Take over CVar");
                            break;
*/
                        case "PFL": // NEW PFL : (player help flags)
                            break;
                        case "CCH": // NEW CCH : (camera changed)
                            break;
                        case "AXI": // send an IS_AXI
                            break;  // autocross cleared
                        case "AXC":
                            break;

                        default:
                            if (debugmode) Console.WriteLine("Unknown packet received:" + packetHead);
//                            Console.WriteLine("Unknown packet received:" + packetHead);
                            break;
                    }
// Not Used in insim 4
/*
                    if (ackReq)
                    {
                        byte[] ackPack = InSim.Encoder.ACK(verifyID);
                        insimConnection.Send(ackPack, ackPack.Length);
                    }
 */
                }
            }

        }
        private void HandlePacket(InSim insim, IS_LAP packet) {
            // player has completed lap, get player from list, and raise lapcompleted event
            var player = players[packet.PLID];

            var e = new LapCompletedEventArgs(
                player.PlayerName,
                currentTrack,
                player.Car,
                packet.LapsDone,
                packet.LTime,
                player.GetSplits());

            OnLapCompleted(e);

            player.ClearSplits(); // do this last
        }
 private void HandlePacket(InSim insim, IS_PLL packet) {
     // remove player from list
     players.Remove(packet.PLID);
 }