示例#1
0
            /// <summary>Attempts to load and parse the current train's panel configuration file.</summary>
            /// <param name="TrainPath">The absolute on-disk path to the train folder.</param>
            /// <param name="Encoding">The selected train encoding</param>
            internal void ParsePanelConfig(string TrainPath, System.Text.Encoding Encoding)
            {
                Cars[DriverCar].CarSections    = new CarSection[1];
                Cars[DriverCar].CarSections[0] = new CarSection(Program.CurrentHost, ObjectType.Overlay);
                string File = OpenBveApi.Path.CombineFile(TrainPath, "panel.xml");

                if (!System.IO.File.Exists(File))
                {
                    //Try animated variant too
                    File = OpenBveApi.Path.CombineFile(TrainPath, "panel.animated.xml");
                }

                if (System.IO.File.Exists(File))
                {
                    Program.FileSystem.AppendToLogFile("Loading train panel: " + File);
                    try
                    {
                        /*
                         * First load the XML. We use this to determine
                         * whether this is a 2D or a 3D animated panel
                         */
                        XDocument CurrentXML = XDocument.Load(File, LoadOptions.SetLineInfo);

                        // Check for null
                        if (CurrentXML.Root != null)
                        {
                            IEnumerable <XElement> DocumentElements = CurrentXML.Root.Elements("PanelAnimated");
                            if (DocumentElements.Any())
                            {
                                PanelAnimatedXmlParser.ParsePanelAnimatedXml(System.IO.Path.GetFileName(File), TrainPath, this, DriverCar);
                                if (Cars[DriverCar].CameraRestrictionMode != CameraRestrictionMode.Restricted3D)
                                {
                                    Cars[DriverCar].CameraRestrictionMode = CameraRestrictionMode.NotAvailable;
                                }
                            }

                            DocumentElements = CurrentXML.Root.Elements("Panel");
                            if (DocumentElements.Any())
                            {
                                PanelXmlParser.ParsePanelXml(System.IO.Path.GetFileName(File), TrainPath, this, DriverCar);
                                Cars[DriverCar].CameraRestrictionMode      = CameraRestrictionMode.On;
                                Program.Renderer.Camera.CurrentRestriction = CameraRestrictionMode.On;
                            }
                        }
                    }
                    catch
                    {
                        var currentError = Translations.GetInterfaceString("errors_critical_file");
                        currentError = currentError.Replace("[file]", "panel.xml");
                        MessageBox.Show(currentError, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                        Program.RestartArguments = " ";
                        Loading.Cancel           = true;
                        return;
                    }

                    if (Cars[DriverCar].CarSections[0].Groups[0].Elements.Any())
                    {
                        OpenBVEGame.RunInRenderThread(() =>
                        {
                            //Needs to be on the thread containing the openGL context
                            Program.Renderer.InitializeVisibility();
                        });
                        Program.Renderer.UpdateViewingDistances(Program.CurrentRoute.CurrentBackground.BackgroundImageDistance);
                        return;
                    }

                    Interface.AddMessage(MessageType.Error, false, "The panel.xml file " + File + " failed to load. Falling back to legacy panel.");
                }
                else
                {
                    File = OpenBveApi.Path.CombineFile(TrainPath, "panel.animated");
                    if (System.IO.File.Exists(File))
                    {
                        Program.FileSystem.AppendToLogFile("Loading train panel: " + File);
                        if (System.IO.File.Exists(OpenBveApi.Path.CombineFile(TrainPath, "panel2.cfg")) || System.IO.File.Exists(OpenBveApi.Path.CombineFile(TrainPath, "panel.cfg")))
                        {
                            Program.FileSystem.AppendToLogFile("INFO: This train contains both a 2D and a 3D panel. The 3D panel will always take precedence");
                        }

                        UnifiedObject currentObject;
                        Program.CurrentHost.LoadObject(File, Encoding, out currentObject);
                        var a = currentObject as AnimatedObjectCollection;
                        if (a != null)
                        {
                            //HACK: If a == null , loading our animated object completely failed (Missing objects?). Fallback to trying the panel2.cfg
                            try
                            {
                                for (int i = 0; i < a.Objects.Length; i++)
                                {
                                    Program.CurrentHost.CreateDynamicObject(ref a.Objects[i].internalObject);
                                }

                                Cars[DriverCar].CarSections[0].Groups[0].Elements = a.Objects;
                                if (Cars[DriverCar].CameraRestrictionMode != CameraRestrictionMode.Restricted3D)
                                {
                                    Cars[DriverCar].CameraRestrictionMode      = CameraRestrictionMode.NotAvailable;
                                    Program.Renderer.Camera.CurrentRestriction = CameraRestrictionMode.NotAvailable;
                                }

                                Program.Renderer.UpdateViewingDistances(Program.CurrentRoute.CurrentBackground.BackgroundImageDistance);
                                return;
                            }
                            catch
                            {
                                var currentError = Translations.GetInterfaceString("errors_critical_file");
                                currentError = currentError.Replace("[file]", "panel.animated");
                                MessageBox.Show(currentError, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                                Program.RestartArguments = " ";
                                Loading.Cancel           = true;
                                return;
                            }
                        }

                        Interface.AddMessage(MessageType.Error, false, "The panel.animated file " + File + " failed to load. Falling back to 2D panel.");
                    }
                }

                var Panel2 = false;

                try
                {
                    File = OpenBveApi.Path.CombineFile(TrainPath, "panel2.cfg");
                    if (System.IO.File.Exists(File))
                    {
                        Program.FileSystem.AppendToLogFile("Loading train panel: " + File);
                        Panel2 = true;
                        Panel2CfgParser.ParsePanel2Config("panel2.cfg", TrainPath, Cars[DriverCar]);
                        Cars[DriverCar].CameraRestrictionMode      = CameraRestrictionMode.On;
                        Program.Renderer.Camera.CurrentRestriction = CameraRestrictionMode.On;
                    }
                    else
                    {
                        File = OpenBveApi.Path.CombineFile(TrainPath, "panel.cfg");
                        if (System.IO.File.Exists(File))
                        {
                            Program.FileSystem.AppendToLogFile("Loading train panel: " + File);
                            PanelCfgParser.ParsePanelConfig(TrainPath, Encoding, Cars[DriverCar]);
                            Cars[DriverCar].CameraRestrictionMode      = CameraRestrictionMode.On;
                            Program.Renderer.Camera.CurrentRestriction = CameraRestrictionMode.On;
                        }
                        else
                        {
                            Program.Renderer.Camera.CurrentRestriction = CameraRestrictionMode.NotAvailable;
                        }
                    }
                }
                catch
                {
                    var currentError = Translations.GetInterfaceString("errors_critical_file");
                    currentError = currentError.Replace("[file]", Panel2 ? "panel2.cfg" : "panel.cfg");
                    MessageBox.Show(currentError, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                    Program.RestartArguments = " ";
                    Loading.Cancel           = true;
                }
            }
示例#2
0
        private static void LoadEverythingThreaded()
        {
            string RailwayFolder = GetRailwayFolder(CurrentRouteFile);
            string ObjectFolder  = OpenBveApi.Path.CombineDirectory(RailwayFolder, "Object");
            string SoundFolder   = OpenBveApi.Path.CombineDirectory(RailwayFolder, "Sound");

            Game.Reset(true);
            Game.MinimalisticSimulation = true;
            // screen
            Program.Renderer.Camera.CurrentMode = CameraViewMode.Interior;

            bool loaded = false;

            Program.FileSystem.AppendToLogFile("INFO: " + Program.CurrentHost.AvailableRoutePluginCount + " Route loading plugins available.");
            Program.FileSystem.AppendToLogFile("INFO: " + Program.CurrentHost.AvailableObjectPluginCount + " Object loading plugins available.");
            Program.FileSystem.AppendToLogFile("INFO: " + Program.CurrentHost.AvailableRoutePluginCount + " Sound loading plugins available.");
            for (int i = 0; i < Program.CurrentHost.Plugins.Length; i++)
            {
                if (Program.CurrentHost.Plugins[i].Route != null && Program.CurrentHost.Plugins[i].Route.CanLoadRoute(CurrentRouteFile))
                {
                    object Route = (object)Program.CurrentRoute;                     //must cast to allow us to use the ref keyword.
                    if (Program.CurrentHost.Plugins[i].Route.LoadRoute(CurrentRouteFile, CurrentRouteEncoding, CurrentTrainFolder, ObjectFolder, SoundFolder, false, ref Route))
                    {
                        Program.CurrentRoute = (CurrentRoute)Route;
                        Program.CurrentRoute.UpdateLighting();

                        loaded = true;
                        break;
                    }
                    var currentError = Translations.GetInterfaceString("errors_critical_file");
                    currentError = currentError.Replace("[file]", System.IO.Path.GetFileName(CurrentRouteFile));
                    MessageBox.Show(currentError, @"OpenBVE", MessageBoxButtons.OK, MessageBoxIcon.Hand);
                    Interface.AddMessage(MessageType.Critical, false, "The route and train loader encountered the following critical error: " + Program.CurrentHost.Plugins[i].Route.LastException.Message);
                    CrashHandler.LoadingCrash(Program.CurrentHost.Plugins[i].Route.LastException.Message, false);
                    Program.RestartArguments = " ";
                    Cancel = true;
                    return;
                }
            }

            TrainManager.Derailments  = Interface.CurrentOptions.Derailments;
            TrainManager.Toppling     = Interface.CurrentOptions.Toppling;
            TrainManager.CurrentRoute = Program.CurrentRoute;
            if (!loaded)
            {
                throw new Exception("No plugins capable of loading routefile " + CurrentRouteFile + " were found.");
            }
            Thread createIllustrations = new Thread(Program.CurrentRoute.Information.LoadInformation)
            {
                IsBackground = true
            };

            createIllustrations.Start();
            System.Threading.Thread.Sleep(1); if (Cancel)
            {
                return;
            }
            Program.CurrentRoute.Atmosphere.CalculateSeaLevelConstants();
            if (Program.CurrentRoute.BogusPreTrainInstructions.Length != 0)
            {
                double t = Program.CurrentRoute.BogusPreTrainInstructions[0].Time;
                double p = Program.CurrentRoute.BogusPreTrainInstructions[0].TrackPosition;
                for (int i = 1; i < Program.CurrentRoute.BogusPreTrainInstructions.Length; i++)
                {
                    if (Program.CurrentRoute.BogusPreTrainInstructions[i].Time > t)
                    {
                        t = Program.CurrentRoute.BogusPreTrainInstructions[i].Time;
                    }
                    else
                    {
                        t += 1.0;
                        Program.CurrentRoute.BogusPreTrainInstructions[i].Time = t;
                    }
                    if (Program.CurrentRoute.BogusPreTrainInstructions[i].TrackPosition > p)
                    {
                        p = Program.CurrentRoute.BogusPreTrainInstructions[i].TrackPosition;
                    }
                    else
                    {
                        p += 1.0;
                        Program.CurrentRoute.BogusPreTrainInstructions[i].TrackPosition = p;
                    }
                }
            }
            Program.Renderer.CameraTrackFollower = new TrackFollower(Program.CurrentHost)
            {
                Train = null, Car = null
            };
            if (Program.CurrentRoute.Stations.Length == 1)
            {
                //Log the fact that only a single station is present, as this is probably not right
                Program.FileSystem.AppendToLogFile("The processed route file only contains a single station.");
            }
            Program.FileSystem.AppendToLogFile("Route file loaded successfully.");
            // initialize trains
            System.Threading.Thread.Sleep(1); if (Cancel)
            {
                return;
            }
            Program.TrainManager.Trains = new TrainBase[Program.CurrentRoute.PrecedingTrainTimeDeltas.Length + 1 + (Program.CurrentRoute.BogusPreTrainInstructions.Length != 0 ? 1 : 0)];
            for (int k = 0; k < Program.TrainManager.Trains.Length; k++)
            {
                if (k == Program.TrainManager.Trains.Length - 1 & Program.CurrentRoute.BogusPreTrainInstructions.Length != 0)
                {
                    Program.TrainManager.Trains[k] = new TrainBase(TrainState.Bogus);
                }
                else
                {
                    Program.TrainManager.Trains[k] = new TrainBase(TrainState.Pending);
                }
            }
            TrainManager.PlayerTrain = Program.TrainManager.Trains[Program.CurrentRoute.PrecedingTrainTimeDeltas.Length];



            // load trains
            for (int k = 0; k < Program.TrainManager.Trains.Length; k++)
            {
                AbstractTrain currentTrain = Program.TrainManager.Trains[k];
                for (int i = 0; i < Program.CurrentHost.Plugins.Length; i++)
                {
                    if (Program.CurrentHost.Plugins[i].Train != null && Program.CurrentHost.Plugins[i].Train.CanLoadTrain(CurrentTrainFolder))
                    {
                        Program.CurrentHost.Plugins[i].Train.LoadTrain(CurrentTrainEncoding, CurrentTrainFolder, ref currentTrain, ref Interface.CurrentControls);
                        break;
                    }
                }
                Program.Renderer.UpdateViewingDistances(Program.CurrentRoute.CurrentBackground.BackgroundImageDistance);
                // configure other properties
                if (currentTrain.IsPlayerTrain)
                {
                    currentTrain.TimetableDelta = 0.0;
                    if (Game.InitialReversedConsist)
                    {
                        currentTrain.Reverse();
                        TrainManager.PlayerTrain.CameraCar         = currentTrain.DriverCar;
                        Program.Renderer.Camera.CurrentRestriction = TrainManager.PlayerTrain.Cars[TrainManager.PlayerTrain.DriverCar].CameraRestrictionMode;
                    }
                }
                else if (currentTrain.State != TrainState.Bogus)
                {
                    TrainBase train = currentTrain as TrainBase;
                    currentTrain.AI             = new Game.SimpleHumanDriverAI(train, Interface.CurrentOptions.PrecedingTrainSpeedLimit);
                    currentTrain.TimetableDelta = Program.CurrentRoute.PrecedingTrainTimeDeltas[k];
                    train.Specs.DoorOpenMode    = DoorMode.Manual;
                    train.Specs.DoorCloseMode   = DoorMode.Manual;
                }
            }
            // finished created objects
            System.Threading.Thread.Sleep(1); if (Cancel)
            {
                return;
            }
            Array.Resize(ref ObjectManager.AnimatedWorldObjects, ObjectManager.AnimatedWorldObjectsUsed);
            // update sections
            if (Program.CurrentRoute.Sections.Length > 0)
            {
                Program.CurrentRoute.UpdateAllSections();
            }
            // load plugin


            CurrentTrain = 0;
            for (int i = 0; i < Program.TrainManager.Trains.Length; i++)
            {
                if (Program.TrainManager.Trains[i].State != TrainState.Bogus)
                {
                    if (Program.TrainManager.Trains[i].IsPlayerTrain)
                    {
                        if (!Program.TrainManager.Trains[i].LoadCustomPlugin(Program.TrainManager.Trains[i].TrainFolder, CurrentTrainEncoding))
                        {
                            Program.TrainManager.Trains[i].LoadDefaultPlugin(Program.TrainManager.Trains[i].TrainFolder);
                        }
                    }
                    else
                    {
                        Program.TrainManager.Trains[i].LoadDefaultPlugin(Program.TrainManager.Trains[i].TrainFolder);
                    }
                    for (int j = 0; j < InputDevicePlugin.AvailablePluginInfos.Count; j++)
                    {
                        if (InputDevicePlugin.AvailablePluginInfos[j].Status == InputDevicePlugin.PluginInfo.PluginStatus.Enable && InputDevicePlugin.AvailablePlugins[j] is ITrainInputDevice)
                        {
                            ITrainInputDevice trainInputDevice = (ITrainInputDevice)InputDevicePlugin.AvailablePlugins[j];
                            trainInputDevice.SetVehicleSpecs(Program.TrainManager.Trains[i].vehicleSpecs());
                        }
                    }
                }
                CurrentTrain++;
            }
        }
示例#3
0
            private void LoadCalibration(string calibrationFile)
            {
                if (!File.Exists(calibrationFile))
                {
                    return;
                }
                try
                {
                    for (int i = 0; i < Calibration.Length; i++)
                    {
                        Calibration[i] = new AxisCalibration();
                    }
                    XmlDocument currentXML = new XmlDocument();
                    currentXML.Load(calibrationFile);
                    XmlNodeList documentNodes = currentXML.SelectNodes("openBVE/RailDriverCalibration");
                    if (documentNodes != null && documentNodes.Count != 0)
                    {
                        for (int i = 0; i < documentNodes.Count; i++)
                        {
                            int idx  = -1;
                            int lMin = 0;
                            int lMax = 255;
                            foreach (XmlNode node in documentNodes[i].ChildNodes)
                            {
                                switch (node.Name.ToLowerInvariant())
                                {
                                case "axis":
                                    foreach (XmlNode n in node.ChildNodes)
                                    {
                                        switch (n.Name.ToLowerInvariant())
                                        {
                                        case "index":
                                            if (!NumberFormats.TryParseIntVb6(n.InnerText, out idx))
                                            {
                                                Program.FileSystem.AppendToLogFile(@"Invalid index in RailDriver calibration file");
                                            }
                                            break;

                                        case "minimum":
                                            if (!NumberFormats.TryParseIntVb6(n.InnerText, out lMin))
                                            {
                                                Program.FileSystem.AppendToLogFile(@"Invalid minimum in RailDriver calibration file");
                                            }
                                            break;

                                        case "maximum":
                                            if (!NumberFormats.TryParseIntVb6(n.InnerText, out lMax))
                                            {
                                                Program.FileSystem.AppendToLogFile(@"Invalid minimum in RailDriver calibration file");
                                            }
                                            break;
                                        }
                                    }
                                    lMin = Math.Abs(lMin);
                                    lMax = Math.Abs(lMax);
                                    if (lMin > 255)
                                    {
                                        lMin = 255;
                                    }
                                    else if (lMin < 0)
                                    {
                                        lMin = 0;
                                    }
                                    if (lMax >= 255)
                                    {
                                        lMax = 255;
                                    }
                                    else if (lMax < 0)
                                    {
                                        lMax = 0;
                                    }
                                    if (lMin >= lMax)
                                    {
                                        throw new InvalidDataException(@"Maximum must be non-zero and greater than minimum.");
                                    }
                                    if (idx == -1)
                                    {
                                        throw new InvalidDataException(@"Invalid axis specified.");
                                    }
                                    Calibration[idx].Minimum = lMin;
                                    Calibration[idx].Maximum = lMax;
                                    break;
                                }
                            }
                        }
                    }
                }
                catch
                {
                    for (int i = 0; i < Calibration.Length; i++)
                    {
                        Calibration[i] = new AxisCalibration();
                    }
                    MessageBox.Show(Translations.GetInterfaceString("raildriver_config_error"), Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                    //Clear the calibration file
                    File.Delete(calibrationFile);
                }
            }
示例#4
0
        /// <summary>Exports the current score data to a file</summary>
        /// <param name="File">The file to write</param>
        internal static void ExportScore(string File)
        {
            CultureInfo Culture = CultureInfo.InvariantCulture;

            System.Text.StringBuilder Builder = new System.Text.StringBuilder();
            string[][] Lines = new string[Game.ScoreLogCount + 1][];
            Lines[0] = new string[] {
                Translations.GetInterfaceString("log_time"),
                Translations.GetInterfaceString("log_position"),
                Translations.GetInterfaceString("log_value"),
                Translations.GetInterfaceString("log_cumulative"),
                Translations.GetInterfaceString("log_reason")
            };
            int Columns    = Lines[0].Length;
            int TotalScore = 0;

            for (int i = 0; i < Game.ScoreLogCount; i++)
            {
                int j = i + 1;
                Lines[j] = new string[Columns];
                {
                    double x = Game.ScoreLogs[i].Time;
                    int    h = (int)Math.Floor(x / 3600.0);
                    x -= (double)h * 3600.0;
                    int m = (int)Math.Floor(x / 60.0);
                    x -= (double)m * 60.0;
                    int s = (int)Math.Floor(x);
                    Lines[j][0] = h.ToString("00", Culture) + ":" + m.ToString("00", Culture) + ":" + s.ToString("00", Culture);
                }
                Lines[j][1] = Game.ScoreLogs[i].Position.ToString("0", Culture);
                Lines[j][2] = Game.ScoreLogs[i].Value.ToString(Culture);
                TotalScore += Game.ScoreLogs[i].Value;
                Lines[j][3] = TotalScore.ToString(Culture);
                Lines[j][4] = GetScoreText(Game.ScoreLogs[i].TextToken);
            }
            int[] Widths = new int[Columns];
            for (int i = 0; i < Lines.Length; i++)
            {
                for (int j = 0; j < Columns; j++)
                {
                    if (Lines[i][j].Length > Widths[j])
                    {
                        Widths[j] = Lines[i][j].Length;
                    }
                }
            }
            {             // header rows
                int TotalWidth = 0;
                for (int j = 0; j < Columns; j++)
                {
                    TotalWidth += Widths[j] + 2;
                }
                TotalWidth += Columns - 1;
                Builder.Append('╔');
                Builder.Append('═', TotalWidth);
                Builder.Append("╗\n");
                {
                    Builder.Append('║');
                    Builder.Append((" " + Translations.GetInterfaceString("log_route") + " " + Game.LogRouteName).PadRight(TotalWidth, ' '));
                    Builder.Append("║\n║");
                    Builder.Append((" " + Translations.GetInterfaceString("log_train") + " " + Game.LogTrainName).PadRight(TotalWidth, ' '));
                    Builder.Append("║\n║");
                    Builder.Append((" " + Translations.GetInterfaceString("log_date") + " " + Game.LogDateTime.ToString("yyyy-MM-dd HH:mm:ss", Culture)).PadRight(TotalWidth, ' '));
                    Builder.Append("║\n");
                }
                Builder.Append('╠');
                Builder.Append('═', TotalWidth);
                Builder.Append("╣\n");
                {
                    double ratio = Game.CurrentScore.Maximum == 0 ? 0.0 : (double)Game.CurrentScore.CurrentValue / (double)Game.CurrentScore.Maximum;
                    if (ratio < 0.0)
                    {
                        ratio = 0.0;
                    }

                    if (ratio > 1.0)
                    {
                        ratio = 1.0;
                    }

                    int index = (int)Math.Floor(ratio * (double)Translations.RatingsCount);
                    if (index >= Translations.RatingsCount)
                    {
                        index = Translations.RatingsCount - 1;
                    }

                    string s;
                    switch (Interface.CurrentOptions.GameMode)
                    {
                    case Interface.GameMode.Arcade: s = Translations.GetInterfaceString("mode_arcade"); break;

                    case Interface.GameMode.Normal: s = Translations.GetInterfaceString("mode_normal"); break;

                    case Interface.GameMode.Expert: s = Translations.GetInterfaceString("mode_expert"); break;

                    default: s = Translations.GetInterfaceString("mode_unknown"); break;
                    }
                    Builder.Append('║');
                    Builder.Append((" " + Translations.GetInterfaceString("log_mode") + " " + s).PadRight(TotalWidth, ' '));
                    Builder.Append("║\n║");
                    Builder.Append((" " + Translations.GetInterfaceString("log_score") + " " + Game.CurrentScore.CurrentValue.ToString(Culture) + " / " + Game.CurrentScore.Maximum.ToString(Culture)).PadRight(TotalWidth, ' '));
                    Builder.Append("║\n║");
                    Builder.Append((" " + Translations.GetInterfaceString("log_rating") + " " + Translations.GetInterfaceString("rating_" + index.ToString(Culture)) + " (" + (100.0 * ratio).ToString("0.00") + "%)").PadRight(TotalWidth, ' '));
                    Builder.Append("║\n");
                }
            }
            {             // top border row
                Builder.Append('╠');
                for (int j = 0; j < Columns; j++)
                {
                    if (j != 0)
                    {
                        Builder.Append('╤');
                    }
                    Builder.Append('═', Widths[j] + 2);
                }
                Builder.Append("╣\n");
            }
            for (int i = 0; i < Lines.Length; i++)
            {
                // center border row
                if (i != 0)
                {
                    Builder.Append('╟');
                    for (int j = 0; j < Columns; j++)
                    {
                        if (j != 0)
                        {
                            Builder.Append('┼');
                        }
                        Builder.Append('─', Widths[j] + 2);
                    }
                    Builder.Append("╢\n");
                }
                // cell content
                Builder.Append('║');
                for (int j = 0; j < Columns; j++)
                {
                    if (j != 0)
                    {
                        Builder.Append('│');
                    }

                    Builder.Append(' ');
                    if (i != 0 & j <= 3)
                    {
                        Builder.Append(Lines[i][j].PadLeft(Widths[j], ' '));
                    }
                    else
                    {
                        Builder.Append(Lines[i][j].PadRight(Widths[j], ' '));
                    }
                    Builder.Append(' ');
                }
                Builder.Append("║\n");
            }
            {             // bottom border row
                Builder.Append('╚');
                for (int j = 0; j < Columns; j++)
                {
                    if (j != 0)
                    {
                        Builder.Append('╧');
                    }
                    Builder.Append('═', Widths[j] + 2);
                }
                Builder.Append('╝');
            }
            System.IO.File.WriteAllText(File, Builder.ToString(), new System.Text.UTF8Encoding(true));
        }
示例#5
0
 internal override void Trigger(int Direction, EventTriggerType TriggerType, TrainManager.Train Train, int CarIndex)
 {
     if (Train == null)
     {
         return;
     }
     if (Train.RouteLimits == null)
     {
         Train.RouteLimits = new double[] { };
     }
     if (Direction < 0)
     {
         if (TriggerType == EventTriggerType.FrontCarFrontAxle)
         {
             int n = Train.RouteLimits.Length;
             if (n > 0)
             {
                 Array.Resize <double>(ref Train.RouteLimits, n - 1);
                 Train.CurrentRouteLimit = double.PositiveInfinity;
                 for (int i = 0; i < n - 1; i++)
                 {
                     if (Train.RouteLimits[i] < Train.CurrentRouteLimit)
                     {
                         Train.CurrentRouteLimit = Train.RouteLimits[i];
                     }
                 }
             }
         }
         else if (TriggerType == EventTriggerType.RearCarRearAxle)
         {
             int n = Train.RouteLimits.Length;
             Array.Resize <double>(ref Train.RouteLimits, n + 1);
             for (int i = n; i > 0; i--)
             {
                 Train.RouteLimits[i] = Train.RouteLimits[i - 1];
             }
             Train.RouteLimits[0] = this.PreviousSpeedLimit;
         }
     }
     else if (Direction > 0)
     {
         if (TriggerType == EventTriggerType.FrontCarFrontAxle)
         {
             int n = Train.RouteLimits.Length;
             Array.Resize <double>(ref Train.RouteLimits, n + 1);
             Train.RouteLimits[n] = this.NextSpeedLimit;
             if (this.NextSpeedLimit < Train.CurrentRouteLimit)
             {
                 Train.CurrentRouteLimit = this.NextSpeedLimit;
             }
             if (Train.Specs.CurrentAverageSpeed > this.NextSpeedLimit)
             {
                 Game.AddMessage(Translations.GetInterfaceString("message_route_overspeed"), MessageManager.MessageDependency.RouteLimit, Interface.GameMode.Normal, MessageColor.Orange, double.PositiveInfinity, null);
             }
         }
         else if (TriggerType == EventTriggerType.RearCarRearAxle)
         {
             int n = Train.RouteLimits.Length;
             if (n > 0)
             {
                 Train.CurrentRouteLimit = double.PositiveInfinity;
                 for (int i = 0; i < n - 1; i++)
                 {
                     Train.RouteLimits[i] = Train.RouteLimits[i + 1];
                     if (Train.RouteLimits[i] < Train.CurrentRouteLimit)
                     {
                         Train.CurrentRouteLimit = Train.RouteLimits[i];
                     }
                 }
                 Array.Resize <double>(ref Train.RouteLimits, n - 1);
             }
         }
     }
 }
示例#6
0
        /// <summary>
        /// Launches the calibration wizard to guess the button indices used by the adapter.
        /// </summary>
        internal static void Calibrate()
        {
            string[] input =
            {
                "SELECT",
                "START",
                "A",
                "B",
                "C",
                Translations.QuickReferences.HandleEmergency,
                Translations.QuickReferences.HandleBrake + "6",
                Translations.QuickReferences.HandleBrake + "5",
                Translations.QuickReferences.HandleBrake + "4",
                Translations.QuickReferences.HandleBrake + "8",
                Translations.QuickReferences.HandlePower + "5",
                Translations.QuickReferences.HandlePowerNull,
                Translations.QuickReferences.HandlePower + "2",
                Translations.QuickReferences.HandlePower + "1",
                Translations.QuickReferences.HandlePower + "5",
            };

            List <OpenTK.Input.ButtonState> buttonState = GetButtonsState();
            List <OpenTK.Input.ButtonState> PreviousButtonState;
            List <HatPosition> HatPositions = GetHatPositions();
            List <HatPosition> PreviousHatPositions;
            List <int>         ignored = new List <int>();

            // Button calibration
            for (int i = 0; i < 5; i++)
            {
                MessageBox.Show(Translations.GetInterfaceString("denshadego_calibrate_button").Replace("[button]", input[i]));
                PreviousButtonState = buttonState;
                buttonState         = GetButtonsState();
                int index = GetDifferentPressedIndex(PreviousButtonState, buttonState, ignored);
                ignored.Add(index);
                switch (i)
                {
                case 0:
                    ButtonIndex.Select = index;
                    break;

                case 1:
                    ButtonIndex.Start = index;
                    break;

                case 2:
                    ButtonIndex.A = index;
                    break;

                case 3:
                    ButtonIndex.B = index;
                    break;

                case 4:
                    ButtonIndex.C = index;
                    break;
                }
            }

            // The brake handle needs to be moved to EMG to initialise properly
            MessageBox.Show(Translations.GetInterfaceString("denshadego_calibrate_brake").Replace("[notch]", input[5]));

            // Brake handle calibration
            for (int i = 6; i < 10; i++)
            {
                MessageBox.Show(Translations.GetInterfaceString("denshadego_calibrate_brake").Replace("[notch]", input[i]));
                PreviousButtonState = buttonState;
                buttonState         = GetButtonsState();
                int index = GetDifferentPressedIndex(PreviousButtonState, buttonState, ignored);
                ignored.Add(index);
                switch (i)
                {
                case 6:
                    ButtonIndex.Brake4 = index;
                    break;

                case 7:
                    ButtonIndex.Brake1 = index;
                    break;

                case 8:
                    ButtonIndex.Brake2 = index;
                    break;

                case 9:
                    ButtonIndex.Brake3 = index;
                    break;
                }
            }

            // The power handle needs to be moved to P5 and N to initialise properly
            MessageBox.Show(Translations.GetInterfaceString("denshadego_calibrate_power").Replace("[notch]", input[10]));
            MessageBox.Show(Translations.GetInterfaceString("denshadego_calibrate_power").Replace("[notch]", input[11]));

            // Clear previous data before calibrating the power handle
            ignored.Clear();
            buttonState  = GetButtonsState();
            HatPositions = GetHatPositions();

            // Power handle calibration
            for (int i = 12; i < 15; i++)
            {
                MessageBox.Show(Translations.GetInterfaceString("denshadego_calibrate_power").Replace("[notch]", input[i]));
                PreviousButtonState  = buttonState;
                PreviousHatPositions = HatPositions;
                buttonState          = GetButtonsState();
                HatPositions         = GetHatPositions();
                int index = GetDifferentPressedIndex(PreviousButtonState, buttonState, ignored);
                ignored.Add(index);

                int hat = GetChangedHat(PreviousHatPositions, HatPositions);
                if (hat != -1 && i != 13)
                {
                    // If a hat has changed, it means the converter is mapping the direction buttons
                    UsesHat  = true;
                    HatIndex = hat;
                }
                else
                {
                    UsesHat = false;
                }

                switch (i)
                {
                case 12:
                    ButtonIndex.Power2 = index;
                    break;

                case 13:
                    ButtonIndex.Power1 = index;
                    break;

                case 14:
                    ButtonIndex.Power3 = index;
                    break;
                }
            }
        }
示例#7
0
        /// <summary>Exports the current black box data to a file</summary>
        /// <param name="File">The file to write</param>
        /// <param name="Format">The format in which to write the data</param>
        internal static void ExportBlackBox(string File, BlackBoxFormat Format)
        {
            switch (Format)
            {
            // comma separated value
            case BlackBoxFormat.CommaSeparatedValue:
            {
                CultureInfo Culture = CultureInfo.InvariantCulture;
                System.Text.StringBuilder Builder = new System.Text.StringBuilder();
                for (int i = 0; i < Game.BlackBoxEntryCount; i++)
                {
                    Builder.Append(Game.BlackBoxEntries[i].Time.ToString(Culture) + ",");
                    Builder.Append(Game.BlackBoxEntries[i].Position.ToString(Culture) + ",");
                    Builder.Append(Game.BlackBoxEntries[i].Speed.ToString(Culture) + ",");
                    Builder.Append(Game.BlackBoxEntries[i].Acceleration.ToString(Culture) + ",");
                    Builder.Append(((short)Game.BlackBoxEntries[i].ReverserDriver).ToString(Culture) + ",");
                    Builder.Append(((short)Game.BlackBoxEntries[i].ReverserSafety).ToString(Culture) + ",");
                    Builder.Append(((short)Game.BlackBoxEntries[i].PowerDriver).ToString(Culture) + ",");
                    Builder.Append(((short)Game.BlackBoxEntries[i].PowerSafety).ToString(Culture) + ",");
                    Builder.Append(((short)Game.BlackBoxEntries[i].BrakeDriver).ToString(Culture) + ",");
                    Builder.Append(((short)Game.BlackBoxEntries[i].BrakeSafety).ToString(Culture) + ",");
                    Builder.Append(((short)Game.BlackBoxEntries[i].EventToken).ToString(Culture));
                    Builder.Append("\r\n");
                }
                System.IO.File.WriteAllText(File, Builder.ToString(), new System.Text.UTF8Encoding(true));
            } break;

            // formatted text
            case BlackBoxFormat.FormattedText:
            {
                CultureInfo Culture = CultureInfo.InvariantCulture;
                System.Text.StringBuilder Builder = new System.Text.StringBuilder();
                string[][] Lines = new string[Game.BlackBoxEntryCount + 1][];
                Lines[0] = new string[] {
                    Translations.GetInterfaceString("log_time"),
                    Translations.GetInterfaceString("log_position"),
                    Translations.GetInterfaceString("log_speed"),
                    Translations.GetInterfaceString("log_acceleration"),
                    Translations.GetInterfaceString("log_reverser"),
                    Translations.GetInterfaceString("log_power"),
                    Translations.GetInterfaceString("log_brake"),
                    Translations.GetInterfaceString("log_event"),
                };
                int Columns = Lines[0].Length;
                for (int i = 0; i < Game.BlackBoxEntryCount; i++)
                {
                    int j = i + 1;
                    Lines[j] = new string[Columns];
                    {
                        double x = Game.BlackBoxEntries[i].Time;
                        int    h = (int)Math.Floor(x / 3600.0);
                        x -= (double)h * 3600.0;
                        int m = (int)Math.Floor(x / 60.0);
                        x -= (double)m * 60.0;
                        int s = (int)Math.Floor(x);
                        x -= (double)s;
                        int n = (int)Math.Floor(1000.0 * x);
                        Lines[j][0] = h.ToString("00", Culture) + ":" + m.ToString("00", Culture) + ":" + s.ToString("00", Culture) + ":" + n.ToString("000", Culture);
                    }
                    Lines[j][1] = Game.BlackBoxEntries[i].Position.ToString("0.000", Culture);
                    Lines[j][2] = Game.BlackBoxEntries[i].Speed.ToString("0.0000", Culture);
                    Lines[j][3] = Game.BlackBoxEntries[i].Acceleration.ToString("0.0000", Culture);
                    {
                        string[] reverser = new string[2];
                        for (int k = 0; k < 2; k++)
                        {
                            short r = k == 0 ? Game.BlackBoxEntries[i].ReverserDriver : Game.BlackBoxEntries[i].ReverserSafety;
                            switch (r)
                            {
                            case -1:
                                reverser[k] = Translations.QuickReferences.HandleBackward;
                                break;

                            case 0:
                                reverser[k] = Translations.QuickReferences.HandleNeutral;
                                break;

                            case 1:
                                reverser[k] = Translations.QuickReferences.HandleForward;
                                break;

                            default:
                                reverser[k] = r.ToString(Culture);
                                break;
                            }
                        }
                        Lines[j][4] = reverser[0] + " → " + reverser[1];
                    }
                    {
                        string[] power = new string[2];
                        for (int k = 0; k < 2; k++)
                        {
                            Game.BlackBoxPower p = k == 0 ? Game.BlackBoxEntries[i].PowerDriver : Game.BlackBoxEntries[i].PowerSafety;
                            switch (p)
                            {
                            case Game.BlackBoxPower.PowerNull:
                                power[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandlePowerNull);
                                break;

                            default:
                                power[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandlePower) + ((short)p).ToString(Culture);
                                break;
                            }
                        }
                        Lines[j][5] = power[0] + " → " + power[1];
                    }
                    {
                        string[] brake = new string[2];
                        for (int k = 0; k < 2; k++)
                        {
                            Game.BlackBoxBrake b = k == 0 ? Game.BlackBoxEntries[i].BrakeDriver : Game.BlackBoxEntries[i].BrakeSafety;
                            switch (b)
                            {
                            case Game.BlackBoxBrake.BrakeNull:
                                brake[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandleBrakeNull);
                                break;

                            case Game.BlackBoxBrake.Emergency:
                                brake[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandleEmergency);
                                break;

                            case Game.BlackBoxBrake.HoldBrake:
                                brake[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandleHoldBrake);
                                break;

                            case Game.BlackBoxBrake.Release:
                                brake[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandleRelease);
                                break;

                            case Game.BlackBoxBrake.Lap:
                                brake[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandleLap);
                                break;

                            case Game.BlackBoxBrake.Service:
                                brake[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandleService);
                                break;

                            default:
                                brake[k] = Translations.GetInterfaceString(Translations.QuickReferences.HandleBrake) + ((short)b).ToString(Culture);
                                break;
                            }
                        }
                        Lines[j][6] = brake[0] + " → " + brake[1];
                    }
                    Lines[j][7] = GetBlackBoxText(Game.BlackBoxEntries[i].EventToken);
                }
                int[] Widths = new int[Columns];
                for (int i = 0; i < Lines.Length; i++)
                {
                    for (int j = 0; j < Columns; j++)
                    {
                        if (Lines[i][j].Length > Widths[j])
                        {
                            Widths[j] = Lines[i][j].Length;
                        }
                    }
                }
                {                                 // header rows
                    int TotalWidth = 0;
                    for (int j = 0; j < Columns; j++)
                    {
                        TotalWidth += Widths[j] + 2;
                    }
                    TotalWidth += Columns - 1;
                    Builder.Append('╔');
                    Builder.Append('═', TotalWidth);
                    Builder.Append("╗\r\n");
                    {
                        Builder.Append('║');
                        Builder.Append((" " + Translations.GetInterfaceString("log_route") + " " + Game.LogRouteName).PadRight(TotalWidth, ' '));
                        Builder.Append("║\r\n║");
                        Builder.Append((" " + Translations.GetInterfaceString("log_train") + " " + Game.LogTrainName).PadRight(TotalWidth, ' '));
                        Builder.Append("║\r\n║");
                        Builder.Append((" " + Translations.GetInterfaceString("log_date") + " " + Game.LogDateTime.ToString("yyyy-MM-dd HH:mm:ss", Culture)).PadRight(TotalWidth, ' '));
                        Builder.Append("║\r\n");
                    }
                }
                {                                 // top border row
                    Builder.Append('╠');
                    for (int j = 0; j < Columns; j++)
                    {
                        if (j != 0)
                        {
                            Builder.Append('╤');
                        }
                        Builder.Append('═', Widths[j] + 2);
                    }
                    Builder.Append("╣\r\n");
                }
                for (int i = 0; i < Lines.Length; i++)
                {
                    // center border row
                    if (i != 0)
                    {
                        Builder.Append('╟');
                        for (int j = 0; j < Columns; j++)
                        {
                            if (j != 0)
                            {
                                Builder.Append('┼');
                            }
                            Builder.Append('─', Widths[j] + 2);
                        }
                        Builder.Append("╢\r\n");
                    }
                    // cell content
                    Builder.Append('║');
                    for (int j = 0; j < Columns; j++)
                    {
                        if (j != 0)
                        {
                            Builder.Append('│');
                        }
                        Builder.Append(' ');
                        if (i != 0 & j <= 3)
                        {
                            Builder.Append(Lines[i][j].PadLeft(Widths[j], ' '));
                        }
                        else
                        {
                            Builder.Append(Lines[i][j].PadRight(Widths[j], ' '));
                        }
                        Builder.Append(' ');
                    }
                    Builder.Append("║\r\n");
                }
                {                                 // bottom border row
                    Builder.Append('╚');
                    for (int j = 0; j < Columns; j++)
                    {
                        if (j != 0)
                        {
                            Builder.Append('╧');
                        }
                        Builder.Append('═', Widths[j] + 2);
                    }
                    Builder.Append('╝');
                }
                System.IO.File.WriteAllText(File, Builder.ToString(), new System.Text.UTF8Encoding(true));
            } break;
            }
        }
示例#8
0
        //
        // DRAW LOADING SCREEN
        //
        /// <summary>Draws on OpenGL canvas the route/train loading screen</summary>
        internal static void DrawLoadingScreen()
        {
            // begin HACK //
            if (!BlendEnabled)
            {
                GL.Enable(EnableCap.Blend);
                GL.BlendFunc(BlendingFactor.SrcAlpha, BlendingFactor.OneMinusSrcAlpha);
                BlendEnabled = true;
            }
            if (LightingEnabled)
            {
                GL.Disable(EnableCap.Lighting);
                LightingEnabled = false;
            }
            GL.Clear(ClearBufferMask.ColorBufferBit | ClearBufferMask.DepthBufferBit);
            GL.PushMatrix();
            // fill the screen with background colour
            GL.Color4(bkgR, bkgG, bkgB, bkgA);
            Renderer.RenderOverlaySolid(0.0, 0.0, (double)Screen.Width, (double)Screen.Height);
            GL.Color4(1.0f, 1.0f, 1.0f, 1.0f);

            // BACKGROUND IMAGE
            int fontHeight = (int)Fonts.SmallFont.FontSize;
            int logoBottom;
            //			int		versionTop;
            int halfWidth = Screen.Width / 2;

            if (TextureLoadingBkg != null)
            {
                int bkgHeight, bkgWidth;
                // stretch the background image to fit at least one screen dimension
                double ratio = (double)TextureLoadingBkg.Width / (double)TextureLoadingBkg.Height;
                if (Screen.Width / ratio > Screen.Height)     // if screen ratio is shorter than bkg...
                {
                    bkgHeight = Screen.Height;                // set height to screen height
                    bkgWidth  = (int)(Screen.Height * ratio); // and scale width proprtionally
                }
                else                                          // if screen ratio is wider than bkg...
                {
                    bkgWidth  = Screen.Width;                 // set width to screen width
                    bkgHeight = (int)(Screen.Width / ratio);  // and scale height accordingly
                }
                // draw the background image down from the top screen edge
                DrawRectangle(TextureLoadingBkg, new Point((Screen.Width - bkgWidth) / 2, 0), new Size(bkgWidth, bkgHeight), Color128.White);
            }
            // if the route has no custom loading image, add the openBVE logo
            // (the route custom image is loaded in OldParsers/CsvRwRouteParser.cs)
            if (!customLoadScreen)
            {
                if (TextureLogo != null)
                {
                    // place the centre of the logo at from the screen top
                    int logoTop = (int)(Screen.Height * logoCentreYFactor - TextureLogo.Height / 2.0);
                    logoBottom = logoTop + TextureLogo.Height;
                    DrawRectangle(TextureLogo, new Point((Screen.Width - TextureLogo.Width) / 2, logoTop), new Size(TextureLogo.Width, TextureLogo.Height), Color128.White);
                }
            }
            else
            {
                // if custom route image, no logo and leave a conventional black area below the potential logo
            }
            logoBottom = Screen.Height / 2;
            // take the height remaining below the logo and divide in 3 horiz. parts
            int blankHeight = (Screen.Height - logoBottom) / 3;

            // VERSION NUMBER
            // place the version above the first division
            int versionTop = logoBottom + blankHeight - fontHeight;

            DrawString(Fonts.NormalFont, "API Version: " + RAGLINKCommons.RPlatform.SettingsContent.simulatorVersion.ToString(),
                       new Point(65, 5), TextAlignment.TopMiddle, Color128.White);
            // for the moment, do not show any URL; would go right below the first division
            //			DrawString(Fonts.SmallFont, "https://sites.google.com/site/openbvesim/home",
            //				new Point(halfWidth, versionTop + fontHeight+2),
            //				TextAlignment.TopMiddle, Color128.White);

            // PROGRESS MESSAGE AND BAR
            // place progress bar right below the second division
            //int		progressTop		= Screen.Height - blankHeight;
            int progressTop = Screen.Height - 6;
            //int		progressWidth	= Screen.Width - progrMargin * 2;
            int    progressWidth = Screen.Width;
            double routeProgress = Math.Max(0.0, Math.Min(1.0, Loading.RouteProgress));
            double trainProgress = Math.Max(0.0, Math.Min(1.0, Loading.TrainProgress));
            // sum of route progress and train progress arrives up to 2.0:
            // => times 50.0 to convert to %
            double percent = 50.0 * (routeProgress + trainProgress);
            string percStr = percent.ToString("0") + "%";
            // draw progress message right above the second division
            string text = Translations.GetInterfaceString(
                routeProgress < 1.0 ? "loading_loading_route" :
                (trainProgress < 1.0 ? "loading_loading_train" : "message_loading")) + " (" + percStr + ")";

            DrawString(Fonts.NormalFont, text, new Point(halfWidth, progressTop - fontHeight - 8),
                       TextAlignment.TopMiddle, Color128.White);
            // progress frame
            //DrawRectangle(null, new Point(progrMargin-progrBorder, progressTop-progrBorder),
            //	new Size(progressWidth+progrBorder*2, fontHeight+6), Color128.White);
            // progress bar
            DrawRectangle(null, new Point(0, progressTop),
                          new Size(progressWidth * (int)percent / 100, fontHeight + 4), ColourProgressBar);
            // progress percent
            //DrawString(Fonts.SmallFont, percStr, new Point(halfWidth, progressTop),
            //	TextAlignment.TopMiddle, Color128.Black);
            GL.PopMatrix();
        }
示例#9
0
        // get control details
        private string GetControlDetails(int Index)
        {
            System.Globalization.CultureInfo Culture = System.Globalization.CultureInfo.InvariantCulture;
            string Separator = Translations.GetInterfaceString("controls_assignment_separator");

            if (Interface.CurrentControls[Index].Method == Interface.ControlMethod.Keyboard)
            {
                string t = Translations.GetInterfaceString("controls_assignment_keyboard") + Separator;
                if ((Interface.CurrentControls[Index].Modifier & Interface.KeyboardModifier.Shift) != 0)
                {
                    t += Translations.GetInterfaceString("controls_assignment_keyboard_shift");
                }
                if ((Interface.CurrentControls[Index].Modifier & Interface.KeyboardModifier.Ctrl) != 0)
                {
                    t += Translations.GetInterfaceString("controls_assignment_keyboard_ctrl");
                }
                if ((Interface.CurrentControls[Index].Modifier & Interface.KeyboardModifier.Alt) != 0)
                {
                    t += Translations.GetInterfaceString("controls_assignment_keyboard_alt");
                }


                int j;
                for (j = 0; j < 133; j++)
                {
                    //OpenTK key description
                    if (Interface.CurrentControls[Index].Key != Key.Unknown)
                    {
                        for (int k = 0; k < Translations.TranslatedKeys.Length; k++)
                        {
                            if (Interface.CurrentControls[Index].Key == Translations.TranslatedKeys[k].Key)
                            {
                                t += Translations.TranslatedKeys[k].Description;
                                return(t);
                            }
                        }
                        t += Interface.CurrentControls[Index].Key;
                        return(t);
                    }
                }
                if (j == 133)
                {
                    t += "{" + Interface.CurrentControls[Index].Element.ToString(Culture) + "}";
                }
                return(t);
            }

            if (Interface.CurrentControls[Index].Method == Interface.ControlMethod.Joystick)
            {
                string t = Translations.GetInterfaceString("controls_assignment_joystick").Replace("[index]", (Interface.CurrentControls[Index].Device + 1).ToString(Culture));
                switch (Interface.CurrentControls[Index].Component)
                {
                case Interface.JoystickComponent.Axis:
                    t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_axis").Replace("[index]", (Interface.CurrentControls[Index].Element + 1).ToString(Culture));
                    if (Interface.CurrentControls[Index].Direction == -1)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_axis_negative");
                    }
                    else if (Interface.CurrentControls[Index].Direction == 1)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_axis_positive");
                    }
                    else
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_axis_invalid");
                    } break;

                case Interface.JoystickComponent.Button:
                    t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_button").Replace("[index]", (Interface.CurrentControls[Index].Element + 1).ToString(Culture));
                    break;

                case Interface.JoystickComponent.Hat:
                    t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat").Replace("[index]", (Interface.CurrentControls[Index].Element + 1).ToString(Culture));
                    if (Interface.CurrentControls[Index].Direction == (int)HatPosition.Left)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_left");
                    }
                    else if (Interface.CurrentControls[Index].Direction == (int)HatPosition.UpLeft)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_upleft");
                    }
                    else if (Interface.CurrentControls[Index].Direction == (int)HatPosition.Up)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_up");
                    }
                    else if (Interface.CurrentControls[Index].Direction == (int)HatPosition.UpRight)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_upright");
                    }
                    else if (Interface.CurrentControls[Index].Direction == (int)HatPosition.Right)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_right");
                    }
                    else if (Interface.CurrentControls[Index].Direction == (int)HatPosition.DownRight)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_downright");
                    }
                    else if (Interface.CurrentControls[Index].Direction == (int)HatPosition.Down)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_down");
                    }
                    else if (Interface.CurrentControls[Index].Direction == (int)HatPosition.DownLeft)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_downleft");
                    }
                    else
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_hat_invalid");
                    } break;
                }
                return(t);
            }
            if (Interface.CurrentControls[Index].Method == Interface.ControlMethod.RailDriver)
            {
                string t = "RailDriver";
                switch (Interface.CurrentControls[Index].Component)
                {
                case Interface.JoystickComponent.Axis:
                    switch (Interface.CurrentControls[Index].Element)
                    {
                    case 0:
                        t += Separator + "Reverser";
                        break;

                    case 1:
                        t += Separator + "Combined Power / Brake";
                        break;

                    case 2:
                        t += Separator + "Auto-Brake";
                        break;

                    case 3:
                        t += Separator + "Independant Brake";
                        break;

                    case 4:
                        t += Separator + "Bail-Off";
                        break;

                    case 5:
                        t += Separator + "Wiper Switch";
                        break;

                    case 6:
                        t += Separator + "Light Switch";
                        break;
                    }

                    if (Interface.CurrentControls[Index].Direction == -1)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_axis_negative");
                    }
                    else if (Interface.CurrentControls[Index].Direction == 1)
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_axis_positive");
                    }
                    else
                    {
                        t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_axis_invalid");
                    } break;

                case Interface.JoystickComponent.Button:
                    t += Separator + Translations.GetInterfaceString("controls_assignment_joystick_button").Replace("[index]", (Interface.CurrentControls[Index].Element + 1).ToString(Culture));
                    break;
                }
                return(t);
            }

            return(Translations.GetInterfaceString("controls_assignment_invalid"));
        }
示例#10
0
        /// <summary>Attempts to load and parse the current train's panel configuration file.</summary>
        /// <param name="Train">The train</param>
        /// <param name="Encoding">The selected train encoding</param>
        internal void ParsePanelConfig(TrainBase Train, Encoding Encoding)
        {
            Train.Cars[Train.DriverCar].CarSections    = new CarSection[1];
            Train.Cars[Train.DriverCar].CarSections[0] = new CarSection(currentHost, ObjectType.Overlay, true);
            string File = Path.CombineFile(Train.TrainFolder, "panel.xml");

            if (!System.IO.File.Exists(File))
            {
                //Try animated variant too
                File = Path.CombineFile(Train.TrainFolder, "panel.animated.xml");
            }

            if (System.IO.File.Exists(File))
            {
                FileSystem.AppendToLogFile("Loading train panel: " + File);
                try
                {
                    /*
                     * First load the XML. We use this to determine
                     * whether this is a 2D or a 3D animated panel
                     */
                    XDocument CurrentXML = XDocument.Load(File, LoadOptions.SetLineInfo);

                    // Check for null
                    if (CurrentXML.Root != null)
                    {
                        IEnumerable <XElement> DocumentElements = CurrentXML.Root.Elements("PanelAnimated");
                        if (DocumentElements.Any())
                        {
                            PanelAnimatedXmlParser.ParsePanelAnimatedXml(System.IO.Path.GetFileName(File), Train, Train.DriverCar);
                            if (Train.Cars[Train.DriverCar].CameraRestrictionMode != CameraRestrictionMode.Restricted3D)
                            {
                                Train.Cars[Train.DriverCar].CameraRestrictionMode = CameraRestrictionMode.NotAvailable;
                            }
                            return;
                        }

                        DocumentElements = CurrentXML.Root.Elements("Panel");
                        if (DocumentElements.Any())
                        {
                            PanelXmlParser.ParsePanelXml(System.IO.Path.GetFileName(File), Train, Train.DriverCar);
                            Train.Cars[Train.DriverCar].CameraRestrictionMode = CameraRestrictionMode.On;
                            Renderer.Camera.CurrentRestriction = CameraRestrictionMode.On;
                            return;
                        }
                    }
                }
                catch
                {
                    var currentError = Translations.GetInterfaceString("errors_critical_file");
                    currentError = currentError.Replace("[file]", "panel.xml");
                    currentHost.ReportProblem(ProblemType.InvalidData, currentError);
                    Cancel = true;
                    return;
                }

                currentHost.AddMessage(MessageType.Error, false, "The panel.xml file " + File + " failed to load. Falling back to legacy panel.");
            }
            else
            {
                File = Path.CombineFile(Train.TrainFolder, "panel.animated");
                if (System.IO.File.Exists(File))
                {
                    FileSystem.AppendToLogFile("Loading train panel: " + File);
                    if (System.IO.File.Exists(Path.CombineFile(Train.TrainFolder, "panel2.cfg")) || System.IO.File.Exists(Path.CombineFile(Train.TrainFolder, "panel.cfg")))
                    {
                        FileSystem.AppendToLogFile("INFO: This train contains both a 2D and a 3D panel. The 3D panel will always take precedence");
                    }

                    UnifiedObject currentObject;
                    currentHost.LoadObject(File, Encoding, out currentObject);
                    var a = currentObject as AnimatedObjectCollection;
                    if (a != null)
                    {
                        //HACK: If a == null , loading our animated object completely failed (Missing objects?). Fallback to trying the panel2.cfg
                        try
                        {
                            for (int i = 0; i < a.Objects.Length; i++)
                            {
                                currentHost.CreateDynamicObject(ref a.Objects[i].internalObject);
                            }

                            Train.Cars[Train.DriverCar].CarSections[0].Groups[0].Elements = a.Objects;
                            if (Train.Cars[Train.DriverCar].CameraRestrictionMode != CameraRestrictionMode.Restricted3D)
                            {
                                Train.Cars[Train.DriverCar].CameraRestrictionMode = CameraRestrictionMode.NotAvailable;
                                Renderer.Camera.CurrentRestriction = CameraRestrictionMode.NotAvailable;
                            }

                            return;
                        }
                        catch
                        {
                            var currentError = Translations.GetInterfaceString("errors_critical_file");
                            currentError = currentError.Replace("[file]", "panel.animated");
                            currentHost.ReportProblem(ProblemType.InvalidData, currentError);
                            Cancel = true;
                            return;
                        }
                    }

                    currentHost.AddMessage(MessageType.Error, false, "The panel.animated file " + File + " failed to load. Falling back to 2D panel.");
                }
            }

            var Panel2 = false;

            try
            {
                File = Path.CombineFile(Train.TrainFolder, "panel2.cfg");
                if (System.IO.File.Exists(File))
                {
                    FileSystem.AppendToLogFile("Loading train panel: " + File);
                    Panel2 = true;
                    Panel2CfgParser.ParsePanel2Config("panel2.cfg", Train.TrainFolder, Train.Cars[Train.DriverCar]);
                    Train.Cars[Train.DriverCar].CameraRestrictionMode = CameraRestrictionMode.On;
                    Renderer.Camera.CurrentRestriction = CameraRestrictionMode.On;
                }
                else
                {
                    File = Path.CombineFile(Train.TrainFolder, "panel.cfg");
                    if (System.IO.File.Exists(File))
                    {
                        FileSystem.AppendToLogFile("Loading train panel: " + File);
                        PanelCfgParser.ParsePanelConfig(Train.TrainFolder, Encoding, Train.Cars[Train.DriverCar]);
                        Train.Cars[Train.DriverCar].CameraRestrictionMode = CameraRestrictionMode.On;
                        Renderer.Camera.CurrentRestriction = CameraRestrictionMode.On;
                    }
                    else
                    {
                        Renderer.Camera.CurrentRestriction = CameraRestrictionMode.NotAvailable;
                    }
                }
            }
            catch
            {
                var currentError = Translations.GetInterfaceString("errors_critical_file");
                currentError = currentError.Replace("[file]", Panel2 ? "panel2.cfg" : "panel.cfg");
                currentHost.ReportProblem(ProblemType.InvalidData, currentError);
                Cancel = true;
            }
        }
示例#11
0
 private FormMain()
 {
     InitializeComponent();
     CheckForIllegalCrossThreadCalls = false;
     this.Text = Translations.GetInterfaceString("program_title");
 }
示例#12
0
        private static void Main(string[] args)
        {
            // Add handler for UI thread exceptions
            Application.ThreadException += (CrashHandler.UIThreadException);

            // Force all WinForms errors to go through handler
            Application.SetUnhandledExceptionMode(UnhandledExceptionMode.CatchException);

            // This handler is for catching non-UI thread exceptions
            AppDomain.CurrentDomain.UnhandledException += (CrashHandler.CurrentDomain_UnhandledException);


            //Determine the current CPU architecture-
            //ARM will generally only support OpenGL-ES
            PortableExecutableKinds peKind;

            typeof(object).Module.GetPEKind(out peKind, out CurrentCPUArchitecture);

            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            CurrentHost = new Host();
            if (IntPtr.Size == 4)
            {
                Joysticks = new JoystickManager32();
            }
            else
            {
                Joysticks = new JoystickManager64();
            }
            try {
                FileSystem = FileSystem.FromCommandLineArgs(args, CurrentHost);
                FileSystem.CreateFileSystem();
            } catch (Exception ex) {
                MessageBox.Show(Translations.GetInterfaceString("errors_filesystem_invalid") + Environment.NewLine + Environment.NewLine + ex.Message, Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
                return;
            }

            Renderer     = new NewRenderer();
            Sounds       = new Sounds();
            CurrentRoute = new CurrentRoute(CurrentHost, Renderer);

            //Platform specific startup checks
            // --- Check if we're running as root, and prompt not to ---
            if (CurrentHost.Platform == HostPlatform.GNULinux && getuid() == 0)
            {
                MessageBox.Show(
                    "You are currently running as the root user." + System.Environment.NewLine +
                    "This is a bad idea, please dont!", Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
            }


            // --- load options and controls ---
            try
            {
                Interface.LoadOptions();
            }
            catch
            {
                // ignored
            }
            TrainManager = new TrainManager(CurrentHost, Renderer, Interface.CurrentOptions, FileSystem);

            //Switch between SDL2 and native backends; use native backend by default
            var options = new ToolkitOptions();

            if (Interface.CurrentOptions.PreferNativeBackend)
            {
                options.Backend = PlatformBackend.PreferNative;
            }
            Toolkit.Init(options);
            // --- load language ---
            string folder = Program.FileSystem.GetDataFolder("Languages");

            Translations.LoadLanguageFiles(folder);

            folder = Program.FileSystem.GetDataFolder("Cursors");
            Cursors.LoadCursorImages(folder);

            Interface.LoadControls(null, out Interface.CurrentControls);
            folder = Program.FileSystem.GetDataFolder("Controls");
            string file = OpenBveApi.Path.CombineFile(folder, "Default keyboard assignment.controls");

            Control[] controls;
            Interface.LoadControls(file, out controls);
            Interface.AddControls(ref Interface.CurrentControls, controls);

            InputDevicePlugin.LoadPlugins(Program.FileSystem);

            // --- check the command-line arguments for route and train ---
            formMain.MainDialogResult result = new formMain.MainDialogResult();
            CommandLine.ParseArguments(args, ref result);
            // --- check whether route and train exist ---
            if (result.RouteFile != null)
            {
                if (!System.IO.File.Exists(result.RouteFile))
                {
                    result.RouteFile = null;
                }
            }
            if (result.TrainFolder != null)
            {
                if (!System.IO.Directory.Exists(result.TrainFolder))
                {
                    result.TrainFolder = null;
                }
            }
            // --- if a route was provided but no train, try to use the route default ---
            if (result.RouteFile != null & result.TrainFolder == null)
            {
                string error;
                if (!CurrentHost.LoadPlugins(FileSystem, Interface.CurrentOptions, out error, TrainManager, Renderer))
                {
                    MessageBox.Show(error, @"OpenBVE", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    throw new Exception("Unable to load the required plugins- Please reinstall OpenBVE");
                }
                Game.Reset(false);
                bool loaded = false;
                for (int i = 0; i < Program.CurrentHost.Plugins.Length; i++)
                {
                    if (Program.CurrentHost.Plugins[i].Route != null && Program.CurrentHost.Plugins[i].Route.CanLoadRoute(result.RouteFile))
                    {
                        object Route = (object)Program.CurrentRoute;                         //must cast to allow us to use the ref keyword.
                        Program.CurrentHost.Plugins[i].Route.LoadRoute(result.RouteFile, result.RouteEncoding, null, null, null, true, ref Route);
                        Program.CurrentRoute = (CurrentRoute)Route;
                        Program.Renderer.Lighting.OptionAmbientColor  = CurrentRoute.Atmosphere.AmbientLightColor;
                        Program.Renderer.Lighting.OptionDiffuseColor  = CurrentRoute.Atmosphere.DiffuseLightColor;
                        Program.Renderer.Lighting.OptionLightPosition = CurrentRoute.Atmosphere.LightPosition;
                        loaded = true;
                        break;
                    }
                }

                if (!CurrentHost.UnloadPlugins(out error))
                {
                    MessageBox.Show(error, @"OpenBVE", MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
                if (!loaded)
                {
                    throw new Exception("No plugins capable of loading routefile " + result.RouteFile + " were found.");
                }
                if (!string.IsNullOrEmpty(Interface.CurrentOptions.TrainName))
                {
                    folder = System.IO.Path.GetDirectoryName(result.RouteFile);
                    while (true)
                    {
                        string trainFolder = OpenBveApi.Path.CombineDirectory(folder, "Train");
                        if (System.IO.Directory.Exists(trainFolder))
                        {
                            try
                            {
                                folder = OpenBveApi.Path.CombineDirectory(trainFolder, Interface.CurrentOptions.TrainName);
                            }
                            catch (Exception ex)
                            {
                                if (ex is ArgumentException)
                                {
                                    break;
                                }
                            }
                            if (System.IO.Directory.Exists(folder))
                            {
                                file = OpenBveApi.Path.CombineFile(folder, "train.dat");
                                if (System.IO.File.Exists(file))
                                {
                                    result.TrainFolder   = folder;
                                    result.TrainEncoding = System.Text.Encoding.UTF8;
                                    for (int j = 0; j < Interface.CurrentOptions.TrainEncodings.Length; j++)
                                    {
                                        if (string.Compare(Interface.CurrentOptions.TrainEncodings[j].Value, result.TrainFolder, StringComparison.InvariantCultureIgnoreCase) == 0)
                                        {
                                            result.TrainEncoding = System.Text.Encoding.GetEncoding(Interface.CurrentOptions.TrainEncodings[j].Codepage);
                                            break;
                                        }
                                    }
                                }
                            }
                            break;
                        }
                        if (folder == null)
                        {
                            continue;
                        }
                        System.IO.DirectoryInfo info = System.IO.Directory.GetParent(folder);
                        if (info != null)
                        {
                            folder = info.FullName;
                        }
                        else
                        {
                            break;
                        }
                    }
                }
                Game.Reset(false);
            }
            // --- show the main menu if necessary ---
            if (result.RouteFile == null | result.TrainFolder == null)
            {
                Joysticks.RefreshJoysticks();

                // end HACK //
                result = formMain.ShowMainDialog(result);
            }
            else
            {
                result.Start = true;
                //Apply translations
                Translations.SetInGameLanguage(Translations.CurrentLanguageCode);
            }
            // --- start the actual program ---
            if (result.Start)
            {
                if (Initialize())
                {
                                        #if !DEBUG
                    try {
                                                #endif
                    MainLoop.StartLoopEx(result);
                                                #if !DEBUG
                }
                catch (Exception ex) {
                    bool found = false;
                    for (int i = 0; i < TrainManager.Trains.Length; i++)
                    {
                        if (TrainManager.Trains[i] != null && TrainManager.Trains[i].Plugin != null)
                        {
                            if (TrainManager.Trains[i].Plugin.LastException != null)
                            {
                                CrashHandler.LoadingCrash(ex.Message, true);
                                MessageBox.Show("The train plugin " + TrainManager.Trains[i].Plugin.PluginTitle + " caused a runtime exception: " + TrainManager.Trains[i].Plugin.LastException.Message, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                                found            = true;
                                RestartArguments = "";
                                break;
                            }
                        }
                    }
                    if (!found)
                    {
                        if (ex is System.DllNotFoundException)
                        {
                            Interface.AddMessage(MessageType.Critical, false, "The required system library " + ex.Message + " was not found on the system.");
                            switch (ex.Message)
                            {
                            case "libopenal.so.1":
                                MessageBox.Show("openAL was not found on this system. \n Please install libopenal1 via your distribtion's package management system.", Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
                                break;

                            default:
                                MessageBox.Show("The required system library " + ex.Message + " was not found on this system.", Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
                                break;
                            }
                        }
                        else
                        {
                            Interface.AddMessage(MessageType.Critical, false, "The route and train loader encountered the following critical error: " + ex.Message);
                            CrashHandler.LoadingCrash(ex + Environment.StackTrace, false);
                        }
                        RestartArguments = "";
                    }
                }
#endif
                }
                Deinitialize();
            }
            // --- restart the program if necessary ---
            if (RestartArguments != null)
            {
                string arguments;
                if (FileSystem.RestartArguments.Length != 0 & RestartArguments.Length != 0)
                {
                    arguments = FileSystem.RestartArguments + " " + RestartArguments;
                }
                else
                {
                    arguments = FileSystem.RestartArguments + RestartArguments;
                }
                try {
                    System.Diagnostics.Process.Start(System.IO.File.Exists(FileSystem.RestartProcess) ? FileSystem.RestartProcess : Application.ExecutablePath, arguments);
                } catch (Exception ex) {
                    MessageBox.Show(ex.Message + "\n\nProcess = " + FileSystem.RestartProcess + "\nArguments = " + arguments, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Error);
                }
            }
        }
示例#13
0
            internal Lamp(LampType Type)
            {
                this.Type = Type;
                switch (Type)
                {
                case LampType.None:
                    this.Text = null;
                    break;

                case LampType.Ats:
                    this.Text = Translations.GetInterfaceString("lamps_ats");
                    break;

                case LampType.AtsOperation:
                    this.Text = Translations.GetInterfaceString("lamps_atsoperation");
                    break;

                case LampType.AtsPPower:
                    this.Text = Translations.GetInterfaceString("lamps_atsppower");
                    break;

                case LampType.AtsPPattern:
                    this.Text = Translations.GetInterfaceString("lamps_atsppattern");
                    break;

                case LampType.AtsPBrakeOverride:
                    this.Text = Translations.GetInterfaceString("lamps_atspbrakeoverride");
                    break;

                case LampType.AtsPBrakeOperation:
                    this.Text = Translations.GetInterfaceString("lamps_atspbrakeoperation");
                    break;

                case LampType.AtsP:
                    this.Text = Translations.GetInterfaceString("lamps_atsp");
                    break;

                case LampType.AtsPFailure:
                    this.Text = Translations.GetInterfaceString("lamps_atspfailure");
                    break;

                case LampType.Atc:
                    this.Text = Translations.GetInterfaceString("lamps_atc");
                    break;

                case LampType.AtcPower:
                    this.Text = Translations.GetInterfaceString("lamps_atcpower");
                    break;

                case LampType.AtcUse:
                    this.Text = Translations.GetInterfaceString("lamps_atcuse");
                    break;

                case LampType.AtcEmergency:
                    this.Text = Translations.GetInterfaceString("lamps_atcemergency");
                    break;

                case LampType.Eb:
                    this.Text = Translations.GetInterfaceString("lamps_eb");
                    break;

                case LampType.ConstSpeed:
                    this.Text = Translations.GetInterfaceString("lamps_constspeed");
                    break;

                default:
                    this.Text = "TEXT";
                    break;
                }
                OpenGlFont font = Fonts.NormalFont;

                for (int i = 0; i < HUD.CurrentHudElements.Length; i++)
                {
                    if (HUD.CurrentHudElements[i].Subject.Equals("ats", StringComparison.OrdinalIgnoreCase))
                    {
                        font = HUD.CurrentHudElements[i].Font;
                        break;
                    }
                }
                System.Drawing.Size size = font.MeasureString(this.Text);
                this.Width  = size.Width;
                this.Height = size.Height;
            }
示例#14
0
        private void paintImage()
        {
            switch (calibrationStage)
            {
            case 0:
                pictureBox1.Image         = main;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_start");
                break;

            case 1:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(210, 130, 80, 145));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_down.png")), 234, 284);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_a");
                break;

            case 2:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(210, 130, 80, 145));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_up.png")), 234, 84);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_b");
                break;

            case 3:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(290, 130, 90, 145));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_down.png")), 314, 284);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_c");
                break;

            case 4:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(290, 130, 90, 145));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_up.png")), 314, 84);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_d");
                break;

            case 5:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(450, 130, 80, 165));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_down.png")), 470, 304);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_e");
                break;

            case 6:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(450, 130, 80, 165));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_up.png")), 470, 79);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_f");
                break;

            case 7:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(610, 130, 75, 165));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_down.png")), 630, 304);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_g");
                break;

            case 8:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(610, 130, 75, 165));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_up.png")), 630, 79);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_h");
                break;

            case 9:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(610, 130, 75, 165));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_left.png")), 560, 175);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_i");
                break;

            case 10:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(610, 130, 75, 165));
                    graphics.DrawImage(ImageExtensions.FromFile(OpenBveApi.Path.CombineFile(Program.FileSystem.DataFolder, "Menu\\arrow_right.png")), 690, 175);
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_j");
                break;

            case 11:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(715, 100, 55, 75));
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_k");
                break;

            case 12:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(715, 100, 55, 75));
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_l");
                break;

            case 13:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(715, 210, 55, 75));
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_m");
                break;

            case 14:
                Modified = new Bitmap(main);
                using (var graphics = System.Drawing.Graphics.FromImage(Modified))
                {
                    graphics.DrawRectangle(new Pen(Color.Blue, 3.0f), new Rectangle(715, 210, 55, 75));
                }
                pictureBox1.Image         = Modified;
                labelCalibrationText.Text = Translations.GetInterfaceString("raildriver_calibration_n");
                break;

            case 15:
                pictureBox1.Image          = main;
                labelCalibrationText.Text  = Translations.GetInterfaceString("raildriver_calibration_o");
                buttonCalibrationNext.Text = Translations.GetInterfaceString("packages_success");
                break;
            }
        }
示例#15
0
        /// <summary>This method is called once the route and train data have been preprocessed, in order to physically setup the simulation</summary>
        private void SetupSimulation()
        {
            if (Loading.Cancel)
            {
                Close();
            }

            lock (Illustrations.Locker)
            {
                Timetable.CreateTimetable();
            }
            //Check if any critical errors have occured during the route or train loading
            for (int i = 0; i < Interface.MessageCount; i++)
            {
                if (Interface.LogMessages[i].Type == MessageType.Critical)
                {
                    MessageBox.Show("A critical error has occured:\n\n" + Interface.LogMessages[i].Text + "\n\nPlease inspect the error log file for further information.", "Load", MessageBoxButtons.OK, MessageBoxIcon.Hand);
                    Close();
                }
            }
            Renderer.InitializeLighting();
            Game.LogRouteName = System.IO.Path.GetFileName(MainLoop.currentResult.RouteFile);
            Game.LogTrainName = System.IO.Path.GetFileName(MainLoop.currentResult.TrainFolder);
            Game.LogDateTime  = DateTime.Now;

            if (Interface.CurrentOptions.LoadInAdvance)
            {
                Textures.LoadAllTextures();
            }
            else
            {
                Textures.UnloadAllTextures();
            }
            // camera
            ObjectManager.InitializeVisibility();
            World.CurrentDriverBody = new World.DriverBody();
            World.CameraTrackFollower.Update(0.0, true, false);
            World.CameraTrackFollower.Update(-0.1, true, false);
            World.CameraTrackFollower.Update(0.1, true, false);
            World.CameraTrackFollower.TriggerType = TrackManager.EventTriggerType.Camera;
            // starting time and track position
            Game.SecondsSinceMidnight = 0.0;
            Game.StartupTime          = 0.0;
            int    PlayerFirstStationIndex = -1;
            double PlayerFirstStationPosition;
            int    os = -1;
            bool   f  = false;

            for (int i = 0; i < Game.Stations.Length; i++)
            {
                if (!String.IsNullOrEmpty(Game.InitialStationName))
                {
                    if (Game.InitialStationName.ToLowerInvariant() == Game.Stations[i].Name.ToLowerInvariant())
                    {
                        PlayerFirstStationIndex = i;
                    }
                }
                if (Game.Stations[i].StopMode == StationStopMode.AllStop | Game.Stations[i].StopMode == StationStopMode.PlayerStop & Game.Stations[i].Stops.Length != 0)
                {
                    if (f == false)
                    {
                        os = i;
                        f  = true;
                    }
                }
            }
            if (PlayerFirstStationIndex == -1)
            {
                PlayerFirstStationIndex = os;
            }
            {
                int s = Game.GetStopIndex(PlayerFirstStationIndex, TrainManager.PlayerTrain.Cars.Length);
                if (s >= 0)
                {
                    PlayerFirstStationPosition = Game.Stations[PlayerFirstStationIndex].Stops[s].TrackPosition;

                    double TrainLength = 0.0;
                    for (int c = 0; c < TrainManager.PlayerTrain.Cars.Length; c++)
                    {
                        TrainLength += TrainManager.PlayerTrain.Cars[c].Length;
                    }

                    for (int j = 0; j < Game.BufferTrackPositions.Length; j++)
                    {
                        if (PlayerFirstStationPosition > Game.BufferTrackPositions[j] && PlayerFirstStationPosition - TrainLength < Game.BufferTrackPositions[j])
                        {
                            /*
                             * HACK: The initial start position for the player train is stuck on a set of buffers
                             * This means we have to make some one the fly adjustments to the first station stop position
                             */

                            //Set the start position to be the buffer position plus the train length plus 1m
                            PlayerFirstStationPosition = Game.BufferTrackPositions[j] + TrainLength + 1;
                            //Update the station stop location
                            if (s >= 0)
                            {
                                Game.Stations[PlayerFirstStationIndex].Stops[s].TrackPosition = PlayerFirstStationPosition;
                            }
                            else
                            {
                                Game.Stations[PlayerFirstStationIndex].DefaultTrackPosition = PlayerFirstStationPosition;
                            }
                            break;
                        }
                    }
                }
                else
                {
                    PlayerFirstStationPosition = Game.Stations[PlayerFirstStationIndex].DefaultTrackPosition;
                }
                if (Game.InitialStationTime != -1)
                {
                    Game.SecondsSinceMidnight = Game.InitialStationTime;
                    Game.StartupTime          = Game.InitialStationTime;
                }
                else
                {
                    if (Game.Stations[PlayerFirstStationIndex].ArrivalTime < 0.0)
                    {
                        if (Game.Stations[PlayerFirstStationIndex].DepartureTime < 0.0)
                        {
                            Game.SecondsSinceMidnight = 0.0;
                            Game.StartupTime          = 0.0;
                        }
                        else
                        {
                            Game.SecondsSinceMidnight = Game.Stations[PlayerFirstStationIndex].DepartureTime -
                                                        Game.Stations[PlayerFirstStationIndex].StopTime;
                            Game.StartupTime = Game.Stations[PlayerFirstStationIndex].DepartureTime -
                                               Game.Stations[PlayerFirstStationIndex].StopTime;
                        }
                    }
                    else
                    {
                        Game.SecondsSinceMidnight = Game.Stations[PlayerFirstStationIndex].ArrivalTime;
                        Game.StartupTime          = Game.Stations[PlayerFirstStationIndex].ArrivalTime;
                    }
                }
            }
            int    OtherFirstStationIndex    = -1;
            double OtherFirstStationPosition = 0.0;
            double OtherFirstStationTime     = 0.0;

            for (int i = 0; i < Game.Stations.Length; i++)
            {
                if (Game.Stations[i].StopMode == StationStopMode.AllStop | Game.Stations[i].StopMode == StationStopMode.PlayerPass & Game.Stations[i].Stops.Length != 0)
                {
                    OtherFirstStationIndex = i;
                    int s = Game.GetStopIndex(i, TrainManager.PlayerTrain.Cars.Length);
                    if (s >= 0)
                    {
                        OtherFirstStationPosition = Game.Stations[i].Stops[s].TrackPosition;
                    }
                    else
                    {
                        OtherFirstStationPosition = Game.Stations[i].DefaultTrackPosition;
                    }
                    if (Game.Stations[i].ArrivalTime < 0.0)
                    {
                        if (Game.Stations[i].DepartureTime < 0.0)
                        {
                            OtherFirstStationTime = 0.0;
                        }
                        else
                        {
                            OtherFirstStationTime = Game.Stations[i].DepartureTime - Game.Stations[i].StopTime;
                        }
                    }
                    else
                    {
                        OtherFirstStationTime = Game.Stations[i].ArrivalTime;
                    }
                    break;
                }
            }
            if (Game.PrecedingTrainTimeDeltas.Length != 0)
            {
                OtherFirstStationTime -= Game.PrecedingTrainTimeDeltas[Game.PrecedingTrainTimeDeltas.Length - 1];
                if (OtherFirstStationTime < Game.SecondsSinceMidnight)
                {
                    Game.SecondsSinceMidnight = OtherFirstStationTime;
                }
            }
            // initialize trains
            for (int i = 0; i < TrainManager.Trains.Length; i++)
            {
                TrainManager.Trains[i].Initialize();
                int s = TrainManager.Trains[i] == TrainManager.PlayerTrain ? PlayerFirstStationIndex : OtherFirstStationIndex;
                if (s >= 0)
                {
                    if (Game.Stations[s].OpenLeftDoors)
                    {
                        for (int j = 0; j < TrainManager.Trains[i].Cars.Length; j++)
                        {
                            TrainManager.Trains[i].Cars[j].Doors[0].AnticipatedOpen = true;
                        }
                    }
                    if (Game.Stations[s].OpenRightDoors)
                    {
                        for (int j = 0; j < TrainManager.Trains[i].Cars.Length; j++)
                        {
                            TrainManager.Trains[i].Cars[j].Doors[1].AnticipatedOpen = true;
                        }
                    }
                }
                if (Game.Sections.Length != 0)
                {
                    Game.Sections[0].Enter(TrainManager.Trains[i]);
                }
                for (int j = 0; j < TrainManager.Trains[i].Cars.Length; j++)
                {
                    double length = TrainManager.Trains[i].Cars[0].Length;
                    TrainManager.Trains[i].Cars[j].Move(-length);
                    TrainManager.Trains[i].Cars[j].Move(length);
                }
            }
            // score
            Game.CurrentScore.ArrivalStation   = PlayerFirstStationIndex + 1;
            Game.CurrentScore.DepartureStation = PlayerFirstStationIndex;
            Game.CurrentScore.Maximum          = 0;
            for (int i = 0; i < Game.Stations.Length; i++)
            {
                if (i != PlayerFirstStationIndex & Game.PlayerStopsAtStation(i))
                {
                    if (i == 0 || Game.Stations[i - 1].Type != StationType.ChangeEnds)
                    {
                        Game.CurrentScore.Maximum += Game.ScoreValueStationArrival;
                    }
                }
            }
            if (Game.CurrentScore.Maximum <= 0)
            {
                Game.CurrentScore.Maximum = Game.ScoreValueStationArrival;
            }
            // signals
            if (Game.Sections.Length > 0)
            {
                Game.UpdateSection(Game.Sections.Length - 1);
            }
            // move train in position
            for (int i = 0; i < TrainManager.Trains.Length; i++)
            {
                double p;
                if (TrainManager.Trains[i] == TrainManager.PlayerTrain)
                {
                    p = PlayerFirstStationPosition;
                }
                else if (TrainManager.Trains[i].State == TrainManager.TrainState.Bogus)
                {
                    p = Game.BogusPretrainInstructions[0].TrackPosition;
                    TrainManager.Trains[i].AI = new Game.BogusPretrainAI(TrainManager.Trains[i]);
                }
                else
                {
                    p = OtherFirstStationPosition;
                }
                for (int j = 0; j < TrainManager.Trains[i].Cars.Length; j++)
                {
                    TrainManager.Trains[i].Cars[j].Move(p);
                }
            }
            // timetable
            if (Timetable.DefaultTimetableDescription.Length == 0)
            {
                Timetable.DefaultTimetableDescription = Game.LogTrainName;
            }

            // initialize camera
            if (World.CameraRestriction == Camera.RestrictionMode.NotAvailable)
            {
                World.CameraMode = CameraViewMode.InteriorLookAhead;
            }
            //Place the initial camera in the driver car
            TrainManager.PlayerTrain.Cars[TrainManager.PlayerTrain.DriverCar].UpdateCamera();
            World.CameraTrackFollower.Update(-1.0, true, false);
            ObjectManager.UpdateVisibility(World.CameraTrackFollower.TrackPosition + World.CameraCurrentAlignment.Position.Z);
            World.CameraSavedExterior = new World.CameraAlignment(new OpenBveApi.Math.Vector3(-2.5, 1.5, -15.0), 0.3, -0.2, 0.0, PlayerFirstStationPosition, 1.0);
            World.CameraSavedTrack    = new World.CameraAlignment(new OpenBveApi.Math.Vector3(-3.0, 2.5, 0.0), 0.3, 0.0, 0.0, TrainManager.PlayerTrain.Cars[0].FrontAxle.Follower.TrackPosition - 10.0, 1.0);
            // signalling sections
            for (int i = 0; i < TrainManager.Trains.Length; i++)
            {
                int s = TrainManager.Trains[i].CurrentSectionIndex;
                Game.Sections[s].Enter(TrainManager.Trains[i]);
            }
            if (Game.Sections.Length > 0)
            {
                Game.UpdateSection(Game.Sections.Length - 1);
            }
            // fast-forward until start time
            {
                Game.MinimalisticSimulation = true;
                const double w = 0.25;
                double       u = Game.StartupTime - Game.SecondsSinceMidnight;
                if (u > 0)
                {
                    while (true)
                    {
                        double v = u < w ? u : w; u -= v;
                        Game.SecondsSinceMidnight += v;
                        TrainManager.UpdateTrains(v);
                        if (u <= 0.0)
                        {
                            break;
                        }
                        TotalTimeElapsedForSectionUpdate += v;
                        if (TotalTimeElapsedForSectionUpdate >= 1.0)
                        {
                            if (Game.Sections.Length > 0)
                            {
                                Game.UpdateSection(Game.Sections.Length - 1);
                            }
                            TotalTimeElapsedForSectionUpdate = 0.0;
                        }
                    }
                }
                Game.MinimalisticSimulation = false;
            }
            // animated objects
            ObjectManager.UpdateAnimatedWorldObjects(0.0, true);
            TrainManager.UpdateTrainObjects(0.0, true);
            //HACK: This function calls a single update on all objects attached to the player's train
            //      but ignores any specified damping so that all needles etc. are in the correct place
            //      for the first frame, rather than spinning wildly to get to the starting point.
            TrainManager.PlayerTrain.UpdateCabObjects();
            // timetable
            if (TrainManager.PlayerTrain.Station >= 0)
            {
                Timetable.UpdateCustomTimetable(Game.Stations[TrainManager.PlayerTrain.Station].TimetableDaytimeTexture, Game.Stations[TrainManager.PlayerTrain.Station].TimetableNighttimeTexture);
                if (Timetable.CustomObjectsUsed != 0 & Timetable.CustomTimetableAvailable && Interface.CurrentOptions.TimeTableStyle != Interface.TimeTableMode.AutoGenerated && Interface.CurrentOptions.TimeTableStyle != Interface.TimeTableMode.None)
                {
                    Timetable.CurrentTimetable = Timetable.TimetableState.Custom;
                }
            }
            //Create AI driver for the player train if specified via the commmand line
            if (Game.InitialAIDriver == true)
            {
                TrainManager.PlayerTrain.AI = new Game.SimpleHumanDriverAI(TrainManager.PlayerTrain);
                if (TrainManager.PlayerTrain.Plugin != null && !TrainManager.PlayerTrain.Plugin.SupportsAI)
                {
                    Game.AddMessage(Translations.GetInterfaceString("notification_aiunable"), MessageManager.MessageDependency.None, Interface.GameMode.Expert,
                                    OpenBveApi.Colors.MessageColor.White, Game.SecondsSinceMidnight + 10.0, null);
                }
            }

            // warnings / errors
            if (Interface.MessageCount != 0)
            {
                int filesNotFound = 0;
                int errors        = 0;
                int warnings      = 0;
                for (int i = 0; i < Interface.MessageCount; i++)
                {
                    if (Interface.LogMessages[i].FileNotFound)
                    {
                        filesNotFound++;
                    }
                    else if (Interface.LogMessages[i].Type == MessageType.Error)
                    {
                        errors++;
                    }
                    else if (Interface.LogMessages[i].Type == MessageType.Warning)
                    {
                        warnings++;
                    }
                }
                string NotFound = null;
                string Messages;
                if (filesNotFound != 0)
                {
                    NotFound = filesNotFound.ToString() + " file(s) not found";
                    Game.AddMessage(NotFound, MessageManager.MessageDependency.None, Interface.GameMode.Expert, MessageColor.Magenta, Game.SecondsSinceMidnight + 10.0, null);
                }
                if (errors != 0 & warnings != 0)
                {
                    Messages = errors.ToString() + " error(s), " + warnings.ToString() + " warning(s)";
                    Game.AddMessage(Messages, MessageManager.MessageDependency.None, Interface.GameMode.Expert, MessageColor.Magenta, Game.SecondsSinceMidnight + 10.0, null);
                }
                else if (errors != 0)
                {
                    Messages = errors.ToString() + " error(s)";
                    Game.AddMessage(Messages, MessageManager.MessageDependency.None, Interface.GameMode.Expert, MessageColor.Magenta, Game.SecondsSinceMidnight + 10.0, null);
                }
                else
                {
                    Messages = warnings.ToString() + " warning(s)";
                    Game.AddMessage(Messages, MessageManager.MessageDependency.None, Interface.GameMode.Expert, MessageColor.Magenta, Game.SecondsSinceMidnight + 10.0, null);
                }
                Game.RouteInformation.FilesNotFound     = NotFound;
                Game.RouteInformation.ErrorsAndWarnings = Messages;
                //Print the plugin error encountered (If any) for 10s
                //This must be done after the simulation has init, as otherwise the timeout doesn't work
                if (Loading.PluginError != null)
                {
                    Game.AddMessage(Loading.PluginError, MessageManager.MessageDependency.None, Interface.GameMode.Expert, OpenBveApi.Colors.MessageColor.Red, Game.SecondsSinceMidnight + 5.0, null);
                    Game.AddMessage(Translations.GetInterfaceString("errors_plugin_failure2"), MessageManager.MessageDependency.None, Interface.GameMode.Expert, OpenBveApi.Colors.MessageColor.Red, Game.SecondsSinceMidnight + 5.0, null);
                }
            }
            loadComplete          = true;
            RenderRealTimeElapsed = 0.0;
            RenderTimeElapsed     = 0.0;
            World.InitializeCameraRestriction();
            Loading.SimulationSetup = true;
            switch (Game.InitialViewpoint)
            {
            case 1:
                //Switch camera to exterior
                MainLoop.SaveCameraSettings();
                World.CameraMode = CameraViewMode.Exterior;
                MainLoop.RestoreCameraSettings();
                for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                {
                    TrainManager.PlayerTrain.Cars[j].ChangeCarSection(TrainManager.CarSectionType.Exterior);
                }
                //Make bogies visible
                for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                {
                    TrainManager.PlayerTrain.Cars[j].FrontBogie.ChangeSection(0);
                    TrainManager.PlayerTrain.Cars[j].RearBogie.ChangeSection(0);
                }
                World.CameraAlignmentDirection = new World.CameraAlignment();
                World.CameraAlignmentSpeed     = new World.CameraAlignment();
                Renderer.UpdateViewport(Renderer.ViewPortChangeMode.NoChange);
                World.UpdateAbsoluteCamera(0.0);
                World.UpdateViewingDistances();
                break;

            case 2:
                //Switch camera to track
                MainLoop.SaveCameraSettings();
                World.CameraMode = CameraViewMode.Track;
                MainLoop.RestoreCameraSettings();
                for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                {
                    TrainManager.PlayerTrain.Cars[j].ChangeCarSection(TrainManager.CarSectionType.Exterior);
                }

                for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                {
                    TrainManager.PlayerTrain.Cars[j].FrontBogie.ChangeSection(0);
                    TrainManager.PlayerTrain.Cars[j].RearBogie.ChangeSection(0);
                }

                World.CameraAlignmentDirection = new World.CameraAlignment();
                World.CameraAlignmentSpeed     = new World.CameraAlignment();
                Renderer.UpdateViewport(Renderer.ViewPortChangeMode.NoChange);
                World.UpdateAbsoluteCamera(0.0);
                World.UpdateViewingDistances();
                break;

            case 3:
                //Switch camera to flyby
                MainLoop.SaveCameraSettings();
                World.CameraMode = CameraViewMode.FlyBy;
                MainLoop.RestoreCameraSettings();
                for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                {
                    TrainManager.PlayerTrain.Cars[j].ChangeCarSection(TrainManager.CarSectionType.Exterior);
                }

                for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                {
                    TrainManager.PlayerTrain.Cars[j].FrontBogie.ChangeSection(0);
                    TrainManager.PlayerTrain.Cars[j].RearBogie.ChangeSection(0);
                }

                World.CameraAlignmentDirection = new World.CameraAlignment();
                World.CameraAlignmentSpeed     = new World.CameraAlignment();
                Renderer.UpdateViewport(Renderer.ViewPortChangeMode.NoChange);
                World.UpdateAbsoluteCamera(0.0);
                World.UpdateViewingDistances();
                break;

            case 4:
                //Switch camera to flyby
                MainLoop.SaveCameraSettings();
                World.CameraMode = CameraViewMode.FlyByZooming;
                MainLoop.RestoreCameraSettings();
                for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                {
                    TrainManager.PlayerTrain.Cars[j].ChangeCarSection(TrainManager.CarSectionType.Exterior);
                }

                for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                {
                    TrainManager.PlayerTrain.Cars[j].FrontBogie.ChangeSection(0);
                    TrainManager.PlayerTrain.Cars[j].RearBogie.ChangeSection(0);
                }

                World.CameraAlignmentDirection = new World.CameraAlignment();
                World.CameraAlignmentSpeed     = new World.CameraAlignment();
                Renderer.UpdateViewport(Renderer.ViewPortChangeMode.NoChange);
                World.UpdateAbsoluteCamera(0.0);
                World.UpdateViewingDistances();
                break;
            }
        }
示例#16
0
        // attached joysticks
        private void pictureboxJoysticks_Paint(object sender, PaintEventArgs e)
        {
            this.DoubleBuffered = true;
            int device = -1;

            Interface.JoystickComponent component = Interface.JoystickComponent.Invalid;
            int element   = -1;
            int direction = -1;

            Translations.CommandType type = Translations.CommandType.Digital;
            if (this.Tag == null & listviewControls.SelectedIndices.Count == 1)
            {
                int j = listviewControls.SelectedIndices[0];
                if (Interface.CurrentControls[j].Method == Interface.ControlMethod.Joystick)
                {
                    device    = Interface.CurrentControls[j].Device;
                    component = Interface.CurrentControls[j].Component;
                    element   = Interface.CurrentControls[j].Element;
                    direction = Interface.CurrentControls[j].Direction;
                    type      = Interface.CurrentControls[j].InheritedType;
                }
            }

            System.Globalization.CultureInfo Culture = System.Globalization.CultureInfo.InvariantCulture;
            e.Graphics.SmoothingMode     = System.Drawing.Drawing2D.SmoothingMode.AntiAlias;
            e.Graphics.TextRenderingHint = System.Drawing.Text.TextRenderingHint.ClearTypeGridFit;
            Font  f = new Font(this.Font.Name, 0.875f * this.Font.Size);
            float x = 2.0f, y = 2.0f;
            float threshold = ((float)trackbarJoystickAxisThreshold.Value - (float)trackbarJoystickAxisThreshold.Minimum) / (float)(trackbarJoystickAxisThreshold.Maximum - trackbarJoystickAxisThreshold.Minimum);

            for (int i = 0; i < JoystickManager.AttachedJoysticks.Length; i++)
            {
                JoystickManager.AttachedJoysticks[i].Poll();
                float w, h;
                if (JoystickImage != null)
                {
                    e.Graphics.DrawImage(JoystickImage, x, y);
                    w = (float)JoystickImage.Width;
                    h = (float)JoystickImage.Height;
                    if (h < 64.0f)
                    {
                        h = 64.0f;
                    }
                }
                else
                {
                    w = 64.0f; h = 64.0f;
                    e.Graphics.DrawRectangle(new Pen(labelControlsTitle.BackColor), x, y, w, h);
                }
                {                 // joystick number
                    e.Graphics.FillEllipse(Brushes.Gold, x + w - 16.0f, y, 16.0f, 16.0f);
                    e.Graphics.DrawEllipse(Pens.Black, x + w - 16.0f, y, 16.0f, 16.0f);
                    string t = (i + 1).ToString(Culture);
                    SizeF  s = e.Graphics.MeasureString(t, f);
                    e.Graphics.DrawString(t, f, Brushes.Black, x + w - 8.0f - 0.5f * s.Width, y + 8.0f - 0.5f * s.Height);
                }
                {                 // joystick name
                    e.Graphics.DrawString(JoystickManager.AttachedJoysticks[i].Name, this.Font, Brushes.Black, x + w + 8.0f, y);
                }
                if (OpenTK.Configuration.RunningOnSdl2)
                {
                    //HACK: Control configuration doesn't work in-form on SDL2
                    string error = Translations.GetInterfaceString("errors_controls_ingame");
                    if (OpenTK.Configuration.RunningOnSdl2)
                    {
                        error = error.Replace("[platform]", "SDL2");
                    }
                    e.Graphics.DrawString(error, this.Font, Brushes.Black, x + w + 8.0f, y + 30.0f);
                    return;
                }
                float m;
                if (groupboxJoysticks.Enabled)
                {
                    m = x;
                    Pen p  = new Pen(Color.DarkGoldenrod, 2.0f);
                    Pen ps = new Pen(Color.Firebrick, 2.0f);
                    {                     // first row
                        float u = x + w + 8.0f;
                        float v = y + 24.0f;
                        float g = h - 24.0f;
                        {                         // hats
                            int n = JoystickManager.AttachedJoysticks[i].HatCount();
                            for (int j = 0; j < n; j++)
                            {
                                if (device == i & component == Interface.JoystickComponent.Hat & element == j)
                                {
                                    e.Graphics.DrawEllipse(ps, u, v, g, g);
                                }
                                else
                                {
                                    e.Graphics.DrawEllipse(p, u, v, g, g);
                                }
                                string t = "H" + (j + 1).ToString(Culture);
                                SizeF  s = e.Graphics.MeasureString(t, f);
                                e.Graphics.DrawString(t, f, Brushes.Black, u + 0.5f * (g - s.Width), v + 0.5f * (g - s.Height));
                                JoystickHatState aa = JoystickManager.AttachedJoysticks[i].GetHat(j);
                                HatPosition      a  = aa.Position;
                                if (a != HatPosition.Centered)
                                {
                                    double rx = 0.0;
                                    double ry = 0.0;
                                    switch (a)
                                    {
                                    case HatPosition.Up:
                                        rx = 0.0;
                                        ry = -1.0;
                                        break;

                                    case HatPosition.Down:
                                        rx = 0.0;
                                        ry = 1.0;
                                        break;

                                    case HatPosition.Left:
                                        rx = -1.0;
                                        ry = 0.0;
                                        break;

                                    case HatPosition.Right:
                                        rx = 1.0;
                                        ry = 0.0;
                                        break;

                                    case HatPosition.UpLeft:
                                        rx = -1.0;
                                        ry = -1.0;
                                        break;

                                    case HatPosition.UpRight:
                                        rx = 1.0;
                                        ry = -1.0;
                                        break;

                                    case HatPosition.DownLeft:
                                        rx = -1.0;
                                        ry = 1.0;
                                        break;

                                    case HatPosition.DownRight:
                                        rx = 1.0;
                                        ry = 1.0;
                                        break;
                                    }

                                    double rt = rx * rx + ry * ry;
                                    rt  = 1.0 / Math.Sqrt(rt);
                                    rx *= rt; ry *= rt;
                                    float dx = (float)(0.5 * rx * (g - 8.0));
                                    float dy = (float)(0.5 * ry * (g - 8.0));
                                    e.Graphics.FillEllipse(Brushes.White, u + 0.5f * g + dx - 4.0f, v + 0.5f * g + dy - 4.0f, 8.0f, 8.0f);
                                    e.Graphics.DrawEllipse(new Pen(Color.Firebrick, 2.0f), u + 0.5f * g + dx - 4.0f, v + 0.5f * g + dy - 4.0f, 8.0f, 8.0f);
                                }
                                if (device == i & component == Interface.JoystickComponent.Hat & element == j)
                                {
                                    double rx = ((HatPosition)direction & HatPosition.Left) != 0 ? -1.0 : ((HatPosition)direction & HatPosition.Right) != 0 ? 1.0 : 0.0;
                                    double ry = ((HatPosition)direction & HatPosition.Up) != 0 ? -1.0 : ((HatPosition)direction & HatPosition.Down) != 0 ? 1.0 : 0.0;
                                    double rt = rx * rx + ry * ry;
                                    rt  = 1.0 / Math.Sqrt(rt);
                                    rx *= rt; ry *= rt;
                                    float dx = (float)(0.5 * rx * (g - 8.0));
                                    float dy = (float)(0.5 * ry * (g - 8.0));
                                    e.Graphics.FillEllipse(Brushes.Firebrick, u + 0.5f * g + dx - 2.0f, v + 0.5f * g + dy - 2.0f, 4.0f, 4.0f);
                                }
                                u += g + 8.0f;
                            }
                        }
                        if (u > m)
                        {
                            m = u;
                        }
                    }

                    {                     // second row
                        float u = x;
                        float v = y + h + 8.0f;
                        {                         // axes
                            int   n = JoystickManager.AttachedJoysticks[i].AxisCount();
                            float g = (float)pictureboxJoysticks.ClientRectangle.Height - v - 2.0f;
                            for (int j = 0; j < n; j++)
                            {
                                float r  = (float)JoystickManager.AttachedJoysticks[i].GetAxis(j);
                                float r0 = r < 0.0f ? r : 0.0f;
                                float r1 = r > 0.0f ? r : 0.0f;
                                if ((float)Math.Abs((double)r) < threshold)
                                {
                                    e.Graphics.FillRectangle(Brushes.RosyBrown, u, v + 0.5f * g - 0.5f * r1 * g, 16.0f, 0.5f * g * (r1 - r0));
                                }
                                else
                                {
                                    e.Graphics.FillRectangle(Brushes.Firebrick, u, v + 0.5f * g - 0.5f * r1 * g, 16.0f, 0.5f * g * (r1 - r0));
                                }
                                if (device == i & component == Interface.JoystickComponent.Axis & element == j)
                                {
                                    if (direction == -1 & type != Translations.CommandType.AnalogFull)
                                    {
                                        e.Graphics.DrawRectangle(p, u, v, 16.0f, g);
                                        e.Graphics.DrawRectangle(ps, u, v + 0.5f * g, 16.0f, 0.5f * g);
                                    }
                                    else if (direction == 1 & type != Translations.CommandType.AnalogFull)
                                    {
                                        e.Graphics.DrawRectangle(p, u, v, 16.0f, g);
                                        e.Graphics.DrawRectangle(ps, u, v, 16.0f, 0.5f * g);
                                    }
                                    else
                                    {
                                        e.Graphics.DrawRectangle(ps, u, v, 16.0f, g);
                                    }
                                }
                                else
                                {
                                    e.Graphics.DrawRectangle(p, u, v, 16.0f, g);
                                }
                                e.Graphics.DrawLine(p, u, v + (0.5f - 0.5f * threshold) * g, u + 16.0f, v + (0.5f - 0.5f * threshold) * g);
                                e.Graphics.DrawLine(p, u, v + (0.5f + 0.5f * threshold) * g, u + 16.0f, v + (0.5f + 0.5f * threshold) * g);
                                string t = "A" + (j + 1).ToString(Culture);
                                SizeF  s = e.Graphics.MeasureString(t, f);
                                e.Graphics.DrawString(t, f, Brushes.Black, u + 0.5f * (16.0f - s.Width), v + g - s.Height - 2.0f);
                                u += 24.0f;
                            }
                        }

                        {                         // buttons
                            int   n = JoystickManager.AttachedJoysticks[i].ButtonCount();
                            float g = (float)0.5f * (pictureboxJoysticks.ClientRectangle.Height - v - 10.0f);
                            for (int j = 0; j < n; j++)
                            {
                                bool  q  = JoystickManager.AttachedJoysticks[i].GetButton(j) != 0;
                                float dv = (float)(j & 1) * (g + 8.0f);
                                if (q)
                                {
                                    e.Graphics.FillRectangle(Brushes.Firebrick, u, v + dv, g, g);
                                }
                                if (device == i & component == Interface.JoystickComponent.Button & element == j)
                                {
                                    e.Graphics.DrawRectangle(ps, u, v + dv, g, g);
                                }
                                else
                                {
                                    e.Graphics.DrawRectangle(p, u, v + dv, g, g);
                                }
                                string t = "B" + (j + 1).ToString(Culture);
                                SizeF  s = e.Graphics.MeasureString(t, f);
                                e.Graphics.DrawString(t, f, Brushes.Black, u + 0.5f * (g - s.Width), v + dv + 0.5f * (g - s.Height));
                                if ((j & 1) != 0 | j == n - 1)
                                {
                                    u += g + 8.0f;
                                }
                            }
                        }

                        if (u > m)
                        {
                            m = u;
                        }
                    }
                }
                else
                {
                    m = x + w + 64.0f;
                }
                x = m + 8.0f;
            }
        }
示例#17
0
        /// <summary>Is called once by the main renderer loop, in order to render all overlays shown on the screen</summary>
        /// <param name="TimeElapsed">The time elapsed since the last call to this function</param>
        internal void Render(double TimeElapsed)
        {
            //Initialize openGL
            renderer.SetBlendFunc();
            GL.Enable(EnableCap.Blend);
            renderer.PushMatrix(MatrixMode.Projection);
            Matrix4D.CreateOrthographicOffCenter(0.0f, renderer.Screen.Width, renderer.Screen.Height, 0.0f, -1.0f, 1.0f, out renderer.CurrentProjectionMatrix);
            renderer.PushMatrix(MatrixMode.Modelview);
            renderer.CurrentViewMatrix = Matrix4D.Identity;

            //Check which overlays to show
            switch (renderer.CurrentOutputMode)
            {
            case OutputMode.Default:

                //Route info overlay (if selected)
                Game.routeInfoOverlay.Show();

                //HUD
                foreach (HUD.Element element in HUD.CurrentHudElements)
                {
                    switch (element.Subject.ToLowerInvariant())
                    {
                    case "messages":
                        RenderGameMessages(element, TimeElapsed);
                        break;

                    case "scoremessages":
                        RenderScoreMessages(element, TimeElapsed);
                        break;

                    case "ats":
                        RenderATSLamps(element, TimeElapsed);
                        break;

                    default:
                        RenderHUDElement(element, TimeElapsed);
                        break;
                    }
                }

                //Marker textures
                if (Interface.CurrentOptions.GameMode != GameMode.Expert)
                {
                    double y = 8.0;

                    foreach (Texture t in renderer.Marker.MarkerTextures)
                    {
                        if (Program.CurrentHost.LoadTexture(t, OpenGlTextureWrapMode.ClampClamp))
                        {
                            double w = t.Width;
                            double h = t.Height;
                            renderer.Rectangle.Draw(t, new OpenBveApi.Math.Vector2(renderer.Screen.Width - w - 8.0, y), new Vector2(w, h), Color128.White);
                            y += h + 8.0;
                        }
                    }
                }

                //Timetable overlay
                //NOTE: Only affects auto-generated timetable, possibly change this inconsistant behaviour
                if (Program.Renderer.CurrentTimetable == DisplayedTimetable.Default)
                {
                    // default
                    if (Program.CurrentHost.LoadTexture(Timetable.DefaultTimetableTexture, OpenGlTextureWrapMode.ClampClamp))
                    {
                        int w = Timetable.DefaultTimetableTexture.Width;
                        int h = Timetable.DefaultTimetableTexture.Height;
                        renderer.Rectangle.Draw(Timetable.DefaultTimetableTexture, new OpenBveApi.Math.Vector2(renderer.Screen.Width - w, Timetable.DefaultTimetablePosition), new Vector2(w, h), Color128.White);
                    }
                }
                else if (Program.Renderer.CurrentTimetable == DisplayedTimetable.Custom & Timetable.CustomObjectsUsed == 0)
                {
                    // custom
                    if (Program.CurrentHost.LoadTexture(Timetable.CurrentCustomTimetableDaytimeTexture, OpenGlTextureWrapMode.ClampClamp))
                    {
                        int w = Timetable.CurrentCustomTimetableDaytimeTexture.Width;
                        int h = Timetable.CurrentCustomTimetableDaytimeTexture.Height;
                        renderer.Rectangle.Draw(Timetable.CurrentCustomTimetableDaytimeTexture, new OpenBveApi.Math.Vector2(renderer.Screen.Width - w, Timetable.CustomTimetablePosition), new Vector2(w, h), Color128.White);
                    }

                    if (Program.CurrentHost.LoadTexture(Timetable.CurrentCustomTimetableDaytimeTexture, OpenGlTextureWrapMode.ClampClamp))
                    {
                        int   w = Timetable.CurrentCustomTimetableDaytimeTexture.Width;
                        int   h = Timetable.CurrentCustomTimetableDaytimeTexture.Height;
                        float alpha;

                        if (Timetable.CurrentCustomTimetableDaytimeTexture != null)
                        {
                            double t = (TrainManager.PlayerTrain.Cars[TrainManager.PlayerTrain.DriverCar].TrackPosition - TrainManager.PlayerTrain.Cars[TrainManager.PlayerTrain.DriverCar].Brightness.PreviousTrackPosition) / (TrainManager.PlayerTrain.Cars[TrainManager.PlayerTrain.DriverCar].Brightness.NextTrackPosition - TrainManager.PlayerTrain.Cars[TrainManager.PlayerTrain.DriverCar].Brightness.PreviousTrackPosition);
                            alpha = (float)((1.0 - t) * TrainManager.PlayerTrain.Cars[TrainManager.PlayerTrain.DriverCar].Brightness.PreviousBrightness + t * TrainManager.PlayerTrain.Cars[TrainManager.PlayerTrain.DriverCar].Brightness.NextBrightness);
                        }
                        else
                        {
                            alpha = 1.0f;
                        }

                        renderer.Rectangle.Draw(Timetable.CurrentCustomTimetableDaytimeTexture, new OpenBveApi.Math.Vector2(renderer.Screen.Width - w, Timetable.CustomTimetablePosition), new Vector2(w, h), new Color128(1.0f, 1.0f, 1.0f, alpha));
                    }
                }
                break;

            case OutputMode.Debug:
                RenderDebugOverlays();
                break;

            case OutputMode.DebugATS:
                RenderATSDebugOverlay();
                break;
            }

            // air brake debug output
            if (Interface.CurrentOptions.GameMode != GameMode.Expert & renderer.OptionBrakeSystems)
            {
                RenderBrakeSystemDebug();
            }

            switch (Program.Renderer.CurrentInterface)
            {
            case InterfaceType.Pause:
            {
                //If paused, fade out the screen & write PAUSE
                renderer.Rectangle.Draw(null, Vector2.Null, new Vector2(renderer.Screen.Width, renderer.Screen.Height), new Color128(0.0f, 0.0f, 0.0f, 0.5f));
                renderer.OpenGlString.Draw(renderer.Fonts.VeryLargeFont, Translations.GetInterfaceString("menu_pause_title"), new Point(renderer.Screen.Width / 2, renderer.Screen.Height / 2), TextAlignment.CenterMiddle, Color128.White, true);
                if (Interface.CurrentOptions.ScreenReaderAvailable && !PauseAnnounced)
                {
                    if (!Tolk.Output(Translations.GetInterfaceString("menu_pause_title")))
                    {
                        Interface.CurrentOptions.ScreenReaderAvailable = false;
                    }
                    PauseAnnounced = true;
                }
                break;
            }

            case InterfaceType.Menu:
                Game.Menu.Draw();
                PauseAnnounced = false;
                break;

            default:
                PauseAnnounced = false;
                break;
            }

            //Fade to black on change ends
            if (TrainManager.PlayerTrain != null)
            {
                if (TrainManager.PlayerTrain.Station >= 0 && Program.CurrentRoute.Stations[TrainManager.PlayerTrain.Station].Type == StationType.ChangeEnds && TrainManager.PlayerTrain.StationState == TrainStopState.Boarding)
                {
                    double time = TrainManager.PlayerTrain.StationDepartureTime - Program.CurrentRoute.SecondsSinceMidnight;
                    if (time < 1.0)
                    {
                        FadeToBlackDueToChangeEnds = Math.Max(0.0, 1.0 - time);
                    }
                    else if (FadeToBlackDueToChangeEnds > 0.0)
                    {
                        FadeToBlackDueToChangeEnds -= TimeElapsed;
                        if (FadeToBlackDueToChangeEnds < 0.0)
                        {
                            FadeToBlackDueToChangeEnds = 0.0;
                        }
                    }
                }
                else if (FadeToBlackDueToChangeEnds > 0.0)
                {
                    FadeToBlackDueToChangeEnds -= TimeElapsed;
                    if (FadeToBlackDueToChangeEnds < 0.0)
                    {
                        FadeToBlackDueToChangeEnds = 0.0;
                    }
                }
                if (FadeToBlackDueToChangeEnds > 0.0 & (renderer.Camera.CurrentMode == CameraViewMode.Interior | renderer.Camera.CurrentMode == CameraViewMode.InteriorLookAhead))
                {
                    renderer.Rectangle.Draw(null, Vector2.Null, new Vector2(renderer.Screen.Width, renderer.Screen.Height), new Color128(0.0f, 0.0f, 0.0f, (float)FadeToBlackDueToChangeEnds));
                }
            }

            // finalize
            renderer.PopMatrix(MatrixMode.Projection);
            renderer.PopMatrix(MatrixMode.Modelview);
        }
示例#18
0
        //
        // CREATE GRADIENT PROFILE
        //
        /// <summary>Creates the route gradient profile.</summary>
        /// <returns>The route gradient profile as Bitmap.</returns>
        /// <param name="Width">The width of the bitmap to create.</param>
        /// <param name="Height">The height of the bitmap to create.</param>
        /// <param name="inGame"><c>true</c> = bitmap for in-game overlay | <c>false</c> = for standard window.</param>
        public static Bitmap CreateRouteGradientProfile(int Width, int Height, bool inGame)
        {
            if (CurrentRoute.Tracks[0].Elements.Length > 36 && CurrentRoute.Stations.Length == 0)
            {
                // If we have track elements, but no stations, show a specific error message, rather
                // than the more generic one thrown later
                // NOTE: Will throw the generic error message on routes shorter than 900m with no stations
                throw new InvalidDataException(Translations.GetInterfaceString("errors_route_corrupt_nostations"));
            }
            // Track elements are assumed to be all of the same length, and this length
            // is used as measure unit, rather than computing the incremental track length
            // in any 'real world' unit (like m).

            // HORIZONTAL RANGE: find first and last used element based on stations
            int n, n0, n1;

            RouteRange(out n, out n0, out n1);
            // VERTICAL RANGE
            double y0 = double.PositiveInfinity, y1 = double.NegativeInfinity;

            for (int i = n0; i <= n1; i++)
            {
                double y = CurrentRoute.Tracks[0].Elements[i].WorldPosition.Y;
                if (y < y0)
                {
                    y0 = y;
                }
                if (y > y1)
                {
                    y1 = y;
                }
            }
            if (y0 >= y1 - 1.0)
            {
                y0 = y1 - 1.0;
            }

            // allow for some padding around actual data
            double ox = LeftPad, oy = TopPad;
            double w = (double)(Width - (LeftPad + RightPad));
            double h = (double)(Height - (TopPad + BottomPad + TrackOffsPad));
            // horizontal and vertical scale
            double nd = w / (double)(n1 - n0);
            double yd = h / (double)(y1 - y0);
            // set total bitmap track position range; used by in-game profile to place
            // the current position of the trains; as the train positions are known as track positions,
            // actual track positions are needed here, rather than indices into the track element array.
            double minX = CurrentRoute.Tracks[0].Elements[n0].StartingTrackPosition;
            double maxX = CurrentRoute.Tracks[0].Elements[n1].StartingTrackPosition;
            double offX = ox * (maxX - minX) / w;

            lastGradientMinTrack = (int)(minX - offX);
            lastGradientMaxTrack = (int)(maxX + offX);

            // BITMAP (in-game display needs transparency)
            Bitmap b = new Bitmap(Width, Height,
                                  inGame ? System.Drawing.Imaging.PixelFormat.Format32bppArgb
                                        : System.Drawing.Imaging.PixelFormat.Format24bppRgb);
            Graphics g = Graphics.FromImage(b);

            g.SmoothingMode     = System.Drawing.Drawing2D.SmoothingMode.AntiAlias;
            g.TextRenderingHint = System.Drawing.Text.TextRenderingHint.ClearTypeGridFit;
            int mode = inGame ? 1 : 0;

            g.Clear(mapColors[mode].background);

            // BELOW SEA LEVEL
            {
                double y  = oy + (h - 0.5 * (double)(-CurrentRoute.Atmosphere.InitialElevation - y0) * yd);
                double x0 = ox - (double)(0) * nd;
                double x1 = ox + (double)(n1 - n0) * nd;
                g.FillRectangle(mapColors[mode].belowSeaFill, (float)x0, (float)y, (float)x1, (float)(oy + h) - (float)y);
                g.DrawLine(mapColors[mode].belowSeaBrdr, (float)x0, (float)y, (float)x1, (float)y);
            }
            // GRADIENT PROFILE
            {
                n = n1 - n0 + 1;
                PointF[] p = new PointF[n + 2];
                p[0] = new PointF((float)ox, (float)(oy + h));
                for (int i = n0; i <= n1; i++)
                {
                    double x = ox + (double)(i - n0) * nd;
                    double y = oy + (h - 0.5 *
                                     (double)(CurrentRoute.Tracks[0].Elements[i].WorldPosition.Y - y0) * yd);
                    p[i - n0 + 1] = new PointF((float)x, (float)y);
                }
                p[n + 1] = new PointF((float)(ox + (double)(n - 1) * nd), (float)(oy + h));
                g.FillPolygon(mapColors[mode].elevFill, p);
                for (int i = 1; i < n; i++)
                {
                    g.DrawLine(mapColors[mode].elevBrdr, p[i], p[i + 1]);
                }
                g.DrawLine(mapColors[mode].elevBrdr, 0.0f, (float)(oy + h), (float)Width, (float)(oy + h));
            }
            // STATION NAMES
            {
                Font         f = new Font(FontFamily.GenericSansSerif, 12.0f, GraphicsUnit.Pixel);
                StringFormat m = new StringFormat();
                for (int i = n0; i <= n1; i++)
                {
                    for (int j = 0; j < CurrentRoute.Tracks[0].Elements[i].Events.Length; j++)
                    {
                        if (CurrentRoute.Tracks[0].Elements[i].Events[j] is StationStartEvent)
                        {
                            StationStartEvent e = (StationStartEvent)CurrentRoute.Tracks[0].Elements[i].Events[j];
                            if (CurrentRoute.Stations[e.StationIndex].Name != string.Empty)
                            {
                                bool stop = CurrentRoute.Stations[e.StationIndex].PlayerStops();
                                if (CurrentRoute.Stations[e.StationIndex].Name.IsJapanese())
                                {
                                    m.Alignment     = StringAlignment.Near;
                                    m.LineAlignment = StringAlignment.Near;
                                    double x = ox + (double)(i - n0) * nd;
                                    double y = oy + (h - 0.5 *
                                                     (double)(CurrentRoute.Tracks[0].Elements[i].WorldPosition.Y - y0) * yd);
                                    string t = CurrentRoute.Stations[e.StationIndex].Name;
                                    float  tx = 0.0f, ty = (float)oy;
                                    for (int k = 0; k < t.Length; k++)
                                    {
                                        SizeF s = g.MeasureString(t.Substring(k, 1), f, 65536, StringFormat.GenericTypographic);
                                        if (s.Width > tx)
                                        {
                                            tx = s.Width;
                                        }
                                    }
                                    for (int k = 0; k < t.Length; k++)
                                    {
                                        g.DrawString(t.Substring(k, 1), f,
                                                     stop ? mapColors[mode].actNameText : mapColors[mode].inactNameText,
                                                     (float)x - 0.5f * tx, ty);
                                        SizeF s = g.MeasureString(t.Substring(k, 1), f, 65536, StringFormat.GenericTypographic);
                                        ty += s.Height;
                                    }
                                    g.DrawLine(stop ? mapColors[mode].actNameBrdr : mapColors[mode].inactNameBrdr,
                                               new PointF((float)x, ty + 4.0f), new PointF((float)x, (float)y));
                                }
                                else
                                {
                                    m.Alignment     = StringAlignment.Far;
                                    m.LineAlignment = StringAlignment.Near;
                                    double x = ox + (double)(i - n0) * nd;
                                    double y = oy + (h - 0.5 *
                                                     (double)(CurrentRoute.Tracks[0].Elements[i].WorldPosition.Y - y0) * yd);
                                    g.RotateTransform(-90.0f);
                                    g.TranslateTransform((float)x, (float)oy, System.Drawing.Drawing2D.MatrixOrder.Append);
                                    g.DrawString(CurrentRoute.Stations[e.StationIndex].Name, f,
                                                 stop ? mapColors[mode].actNameText : mapColors[mode].inactNameText,
                                                 new PointF(0.0f, -5.0f), m);
                                    g.ResetTransform();
                                    SizeF s = g.MeasureString(CurrentRoute.Stations[e.StationIndex].Name, f);
                                    g.DrawLine(stop ? mapColors[mode].actNameBrdr : mapColors[mode].inactNameBrdr,
                                               new PointF((float)x, (float)(oy + s.Width + 4)), new PointF((float)x, (float)y));
                                }
                            }
                        }
                    }
                }
            }
            // ROUTE MARKERS
            {
                Font         f  = new Font(FontFamily.GenericSansSerif, 10.0f, GraphicsUnit.Pixel);
                Font         fs = new Font(FontFamily.GenericSansSerif, 9.0f, GraphicsUnit.Pixel);
                StringFormat m  = new StringFormat
                {
                    Alignment     = StringAlignment.Far,
                    LineAlignment = StringAlignment.Center
                };
                System.Globalization.CultureInfo Culture = System.Globalization.CultureInfo.InvariantCulture;
                int k = TrackOffDist * n / Width;
                if (k == 0)
                {
                    if (!inGame)
                    {
                        //If k is equal to zero, this generally means that the WithTrack section is missing from our routefile
                        //Adding zero to the loop control variable will also produce an infinite loop, so that's a bad idea too
                        throw new InvalidDataException(Translations.GetInterfaceString("errors_route_corrupt_withtrack"));
                    }

                    /*
                     * A route with a single station can somehow sometimes work OK in preview but not in-game
                     * Whilst the routefile is probably broken don't chuck the exception here as it takes down the loader
                     */
                    k = 1;
                }

                for (int i = n0; i <= n1; i += k)
                {
                    double x = ox + (double)(i - n0) * nd;
                    double y = (double)(CurrentRoute.Tracks[0].Elements[i].WorldPosition.Y - y0) * yd;
                    // track offset label
                    if (x < w)
                    {
                        string t = ((int)Math.Round(CurrentRoute.Tracks[0].Elements[i].StartingTrackPosition)).ToString(Culture);
                        g.DrawString(t + "m", f, mapColors[mode].actNameText, (float)x, (float)(oy + h + TrackOffY));
                    }
                    // route height at track offset (with measure and vertical line)
                    {
                        y = oy + (h - 0.5 * y) + 2.0f;
                        string t = ((int)Math.Round(CurrentRoute.Atmosphere.InitialElevation + CurrentRoute.Tracks[0].Elements[i].WorldPosition.Y)).ToString(Culture);
                        SizeF  s = g.MeasureString(t, fs);
                        if (y < oy + h - (double)s.Width - 10.0)
                        {
                            g.RotateTransform(-90.0f);
                            g.TranslateTransform((float)x, (float)y + 4.0f, System.Drawing.Drawing2D.MatrixOrder.Append);
                            g.DrawString(t + "m", fs, mapColors[mode].actNameText, 0.0f, 0.0f, m);
                            g.ResetTransform();
                            g.DrawLine(mapColors[mode].inactNameBrdr,
                                       (float)x, (float)(y + s.Width + 12.0), (float)x, (float)(oy + h));
                        }
                    }
                }
            }
            // finalize
            return(b);
        }
示例#19
0
        /// <summary>Draws on OpenGL canvas the route/train loading screen</summary>
        public void DrawLoadingScreen(OpenGlFont Font, double RouteProgress, double TrainProgress)
        {
            renderer.SetBlendFunc(BlendingFactor.SrcAlpha, BlendingFactor.OneMinusSrcAlpha);             //FIXME: Remove when text switches between two renderer types
            GL.Clear(ClearBufferMask.ColorBufferBit | ClearBufferMask.DepthBufferBit);

            renderer.Rectangle.Draw(null, Vector2.Null, new Vector2(renderer.Screen.Width, renderer.Screen.Height), bkg);

            // BACKGROUND IMAGE
            int fontHeight = (int)Font.FontSize;
            int logoBottom;
            //int versionTop;
            int halfWidth = renderer.Screen.Width / 2;

            if (TextureLoadingBkg != null && renderer.currentHost.LoadTexture(TextureLoadingBkg, OpenGlTextureWrapMode.ClampClamp))
            {
                int bkgHeight, bkgWidth;

                // stretch the background image to fit at least one screen dimension
                double ratio = TextureLoadingBkg.Width / (double)TextureLoadingBkg.Height;

                if (renderer.Screen.Width / ratio > renderer.Screen.Height) // if screen ratio is shorter than bkg...
                {
                    bkgHeight = renderer.Screen.Height;                     // set height to screen height
                    bkgWidth  = (int)(renderer.Screen.Height * ratio);      // and scale width proprtionally
                }
                else                                                        // if screen ratio is wider than bkg...
                {
                    bkgWidth  = renderer.Screen.Width;                      // set width to screen width
                    bkgHeight = (int)(renderer.Screen.Width / ratio);       // and scale height accordingly
                }

                // draw the background image down from the top screen edge
                renderer.Rectangle.Draw(TextureLoadingBkg, new Vector2((renderer.Screen.Width - bkgWidth) / 2.0, 0), new Vector2(bkgWidth, bkgHeight), Color128.White);
            }

            // if the route has no custom loading image, add the openBVE logo
            // (the route custom image is loaded in OldParsers/CsvRwRouteParser.cs)
            if (!customLoadScreen)
            {
                if (TextureLogo != null && renderer.currentHost.LoadTexture(TextureLogo, OpenGlTextureWrapMode.ClampClamp))
                {
                    // place the centre of the logo at from the screen top
                    int logoTop = (int)(renderer.Screen.Height * logoCentreYFactor - TextureLogo.Height / 2.0);
                    renderer.UnsetBlendFunc();
                    renderer.SetAlphaFunc(AlphaFunction.Equal, 1.0f);
                    GL.DepthMask(true);
                    renderer.Rectangle.Draw(TextureLogo, new Vector2((renderer.Screen.Width - TextureLogo.Width) / 2.0, logoTop), new Vector2(TextureLogo.Width, TextureLogo.Height), Color128.White);
                    renderer.SetBlendFunc();
                    renderer.SetAlphaFunc(AlphaFunction.Less, 1.0f);
                    GL.DepthMask(false);
                    renderer.Rectangle.Draw(TextureLogo, new Vector2((renderer.Screen.Width - TextureLogo.Width) / 2.0, logoTop), new Vector2(TextureLogo.Width, TextureLogo.Height), Color128.White);
                    renderer.SetAlphaFunc(AlphaFunction.Equal, 1.0f);
                }
            }
            // ReSharper disable once RedundantIfElseBlock
            else
            {
                // if custom route image, no logo and leave a conventional black area below the potential logo
            }

            logoBottom = renderer.Screen.Height / 2;

            // take the height remaining below the logo and divide in 3 horiz. parts
            int blankHeight = (renderer.Screen.Height - logoBottom) / 3;

            // VERSION NUMBER
            // place the version above the first division
            int versionTop = logoBottom + blankHeight - fontHeight;

            renderer.OpenGlString.Draw(Font, "Version " + ProgramVersion, new Point(halfWidth, versionTop), TextAlignment.TopMiddle, Color128.White);
            // for the moment, do not show any URL; would go right below the first division
            //			DrawString(Fonts.SmallFont, "https://openbve-project.net",
            //				new Point(halfWidth, versionTop + fontHeight+2),
            //				TextAlignment.TopMiddle, Color128.White);

            // PROGRESS MESSAGE AND BAR
            // place progress bar right below the second division
            int    progressTop   = renderer.Screen.Height - blankHeight;
            int    progressWidth = renderer.Screen.Width - progrMargin * 2;
            double routeProgress = Math.Max(0.0, Math.Min(1.0, RouteProgress));
            double trainProgress = Math.Max(0.0, Math.Min(1.0, TrainProgress));

            // draw progress message right above the second division
            string text = Translations.GetInterfaceString(routeProgress < 1.0 ? "loading_loading_route" : trainProgress < 1.0 ? "loading_loading_train" : "message_loading");

            renderer.OpenGlString.Draw(Font, text, new Point(halfWidth, progressTop - fontHeight - 6), TextAlignment.TopMiddle, Color128.White);

            // sum of route progress and train progress arrives up to 2.0:
            // => times 50.0 to convert to %
            double percent = 50.0 * (routeProgress + trainProgress);
            string percStr = percent.ToString("0") + "%";

            // progress frame
            renderer.Rectangle.Draw(null, new Vector2(progrMargin - progrBorder, progressTop - progrBorder), new Vector2(progressWidth + progrBorder * 2, fontHeight + 6), Color128.White);

            // progress bar
            renderer.Rectangle.Draw(null, new Vector2(progrMargin, progressTop), new Vector2(progressWidth * (int)percent / 100.0, fontHeight + 4), ColourProgressBar);

            // progress percent
            renderer.OpenGlString.Draw(Font, percStr, new Point(halfWidth, progressTop), TextAlignment.TopMiddle, Color128.Black);
        }
示例#20
0
        // --- initialization and deinitialization ---

        /// <summary>Initializes audio. A call to Deinitialize must be made when terminating the program.</summary>
        /// <returns>Whether initializing audio was successful.</returns>
        public void Initialize(HostInterface host, SoundRange range)
        {
            Deinitialize();

            CurrentHost = host;

            switch (range)
            {
            case SoundRange.Low:
                OuterRadiusFactorMinimum      = 2.0;
                OuterRadiusFactorMaximum      = 8.0;
                OuterRadiusFactorMaximumSpeed = 1.0;
                break;

            case SoundRange.Medium:
                OuterRadiusFactorMinimum      = 4.0;
                OuterRadiusFactorMaximum      = 16.0;
                OuterRadiusFactorMaximumSpeed = 2.0;
                break;

            case SoundRange.High:
                OuterRadiusFactorMinimum      = 6.0;
                OuterRadiusFactorMaximum      = 24.0;
                OuterRadiusFactorMaximumSpeed = 3.0;
                break;
            }
            OuterRadiusFactor      = Math.Sqrt(OuterRadiusFactorMinimum * OuterRadiusFactorMaximum);
            OuterRadiusFactorSpeed = 0.0;
            OpenAlDevice           = Alc.OpenDevice(null);
            try
            {
                OpenAlMic = new AudioCapture(AudioCapture.DefaultDevice, SamplingRate, ALFormat.Mono16, BufferSize);
            }
            catch
            {
            }

            if (OpenAlDevice != IntPtr.Zero)
            {
                OpenAlContext = Alc.CreateContext(OpenAlDevice, (int[])null);
                if (OpenAlContext != ContextHandle.Zero)
                {
                    Alc.MakeContextCurrent(OpenAlContext);
                    try
                    {
                        AL.SpeedOfSound(343.0f);
                    }
                    catch
                    {
                        MessageBox.Show(Translations.GetInterfaceString("errors_sound_openal_version"), Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
                    }
                    AL.DistanceModel(ALDistanceModel.None);
                    return;
                }
                Alc.CloseDevice(OpenAlDevice);
                OpenAlDevice = IntPtr.Zero;
                OpenAlMic.Dispose();
                OpenAlMic = null;
                MessageBox.Show(Translations.GetInterfaceString("errors_sound_openal_context"), Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
                return;
            }
            OpenAlContext = ContextHandle.Zero;
            MessageBox.Show(Translations.GetInterfaceString("errors_sound_openal_device"), Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
        }
示例#21
0
        /// <summary>Attempts to load and parse the current train's panel configuration file.</summary>
        /// <param name="TrainPath">The absolute on-disk path to the train folder.</param>
        /// <param name="Encoding">The automatically detected or manually set encoding of the panel configuration file.</param>
        /// <param name="Train">The base train on which to apply the panel configuration.</param>
        internal static void ParsePanelConfig(string TrainPath, System.Text.Encoding Encoding, Train Train)
        {
            Train.Cars[Train.DriverCar].CarSections    = new CarSection[1];
            Train.Cars[Train.DriverCar].CarSections[0] = new CarSection
            {
                Groups = new ElementsGroup[1]
            };
            Train.Cars[Train.DriverCar].CarSections[0].Groups[0] = new ElementsGroup
            {
                Elements = new ObjectManager.AnimatedObject[] { },
                Overlay  = true
            };
            string File = OpenBveApi.Path.CombineFile(TrainPath, "panel.xml");

            if (!System.IO.File.Exists(File))
            {
                //Try animated variant too
                File = OpenBveApi.Path.CombineFile(TrainPath, "panel.animated.xml");
            }
            if (System.IO.File.Exists(File))
            {
                Program.FileSystem.AppendToLogFile("Loading train panel: " + File);
                try
                {
                    /*
                     * First load the XML. We use this to determine
                     * whether this is a 2D or a 3D animated panel
                     */
                    XDocument CurrentXML = XDocument.Load(File, LoadOptions.SetLineInfo);

                    // Check for null
                    if (CurrentXML.Root != null)
                    {
                        IEnumerable <XElement> DocumentElements = CurrentXML.Root.Elements("PanelAnimated");
                        if (DocumentElements.Any())
                        {
                            PanelAnimatedXmlParser.ParsePanelAnimatedXml(System.IO.Path.GetFileName(File), TrainPath, Train, Train.DriverCar);
                            Train.Cars[Train.DriverCar].CameraRestrictionMode = Camera.RestrictionMode.NotAvailable;
                            World.CameraRestriction = Camera.RestrictionMode.NotAvailable;
                        }

                        DocumentElements = CurrentXML.Root.Elements("Panel");
                        if (DocumentElements.Any())
                        {
                            PanelXmlParser.ParsePanelXml(System.IO.Path.GetFileName(File), TrainPath, Train, Train.DriverCar);
                            Train.Cars[Train.DriverCar].CameraRestrictionMode = Camera.RestrictionMode.On;
                            World.CameraRestriction = Camera.RestrictionMode.On;
                        }
                    }
                }
                catch
                {
                    var currentError = Translations.GetInterfaceString("errors_critical_file");
                    currentError = currentError.Replace("[file]", "panel.xml");
                    MessageBox.Show(currentError, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                    Program.RestartArguments = " ";
                    Loading.Cancel           = true;
                    return;
                }

                if (Train.Cars[Train.DriverCar].CarSections[0].Groups[0].Elements.Any())
                {
                    World.UpdateViewingDistances();
                    return;
                }
                Interface.AddMessage(MessageType.Error, false, "The panel.xml file " + File + " failed to load. Falling back to legacy panel.");
            }
            else
            {
                File = OpenBveApi.Path.CombineFile(TrainPath, "panel.animated");
                if (System.IO.File.Exists(File))
                {
                    Program.FileSystem.AppendToLogFile("Loading train panel: " + File);
                    if (System.IO.File.Exists(OpenBveApi.Path.CombineFile(TrainPath, "panel2.cfg")) || System.IO.File.Exists(OpenBveApi.Path.CombineFile(TrainPath, "panel.cfg")))
                    {
                        Program.FileSystem.AppendToLogFile("INFO: This train contains both a 2D and a 3D panel. The 3D panel will always take precedence");
                    }
                    ObjectManager.AnimatedObjectCollection a = AnimatedObjectParser.ReadObject(File, Encoding);
                    if (a != null)
                    {
                        //HACK: If a == null , loading our animated object completely failed (Missing objects?). Fallback to trying the panel2.cfg
                        try
                        {
                            for (int i = 0; i < a.Objects.Length; i++)
                            {
                                a.Objects[i].ObjectIndex = ObjectManager.CreateDynamicObject();
                            }
                            Train.Cars[Train.DriverCar].CarSections[0].Groups[0].Elements = a.Objects;
                            Train.Cars[Train.DriverCar].CameraRestrictionMode             = Camera.RestrictionMode.NotAvailable;
                            World.CameraRestriction = Camera.RestrictionMode.NotAvailable;
                            World.UpdateViewingDistances();
                            return;
                        }
                        catch
                        {
                            var currentError = Translations.GetInterfaceString("errors_critical_file");
                            currentError = currentError.Replace("[file]", "panel.animated");
                            MessageBox.Show(currentError, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                            Program.RestartArguments = " ";
                            Loading.Cancel           = true;
                            return;
                        }
                    }
                    Interface.AddMessage(MessageType.Error, false, "The panel.animated file " + File + " failed to load. Falling back to 2D panel.");
                }
            }

            var Panel2 = false;

            try
            {
                File = OpenBveApi.Path.CombineFile(TrainPath, "panel2.cfg");
                if (System.IO.File.Exists(File))
                {
                    Program.FileSystem.AppendToLogFile("Loading train panel: " + File);
                    Panel2 = true;
                    Panel2CfgParser.ParsePanel2Config("panel2.cfg", TrainPath, Encoding, Train, Train.DriverCar);
                    Train.Cars[Train.DriverCar].CameraRestrictionMode = Camera.RestrictionMode.On;
                    World.CameraRestriction = Camera.RestrictionMode.On;
                }
                else
                {
                    File = OpenBveApi.Path.CombineFile(TrainPath, "panel.cfg");
                    if (System.IO.File.Exists(File))
                    {
                        Program.FileSystem.AppendToLogFile("Loading train panel: " + File);
                        PanelCfgParser.ParsePanelConfig(TrainPath, Encoding, Train);
                        Train.Cars[Train.DriverCar].CameraRestrictionMode = Camera.RestrictionMode.On;
                        World.CameraRestriction = Camera.RestrictionMode.On;
                    }
                    else
                    {
                        World.CameraRestriction = Camera.RestrictionMode.NotAvailable;
                    }
                }
            }
            catch
            {
                var currentError = Translations.GetInterfaceString("errors_critical_file");
                currentError = currentError.Replace("[file]", Panel2 ? "panel2.cfg" : "panel.cfg");
                MessageBox.Show(currentError, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                Program.RestartArguments = " ";
                Loading.Cancel           = true;
            }
        }
示例#22
0
            /// <summary>This method should be called once a frame to update the player's score</summary>
            /// <param name="TimeElapsed">The time elapsed since this function was last called</param>
            internal void Update(double TimeElapsed)
            {
                // doors
                {
                    bool leftopen  = false;
                    bool rightopen = false;
                    for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                    {
                        for (int k = 0; k < TrainManager.PlayerTrain.Cars[j].Doors.Length; k++)
                        {
                            if (TrainManager.PlayerTrain.Cars[j].Doors[k].State != 0.0)
                            {
                                if (TrainManager.PlayerTrain.Cars[j].Doors[k].Direction == -1)
                                {
                                    leftopen = true;
                                }
                                else if (TrainManager.PlayerTrain.Cars[j].Doors[k].Direction == 1)
                                {
                                    rightopen = true;
                                }
                            }
                        }
                    }
                    bool bad;
                    if (leftopen | rightopen)
                    {
                        bad = true;
                        int j = TrainManager.PlayerTrain.Station;
                        if (j >= 0)
                        {
                            int p = CurrentRoute.Stations[j].GetStopIndex(TrainManager.PlayerTrain.NumberOfCars);
                            if (p >= 0)
                            {
                                if (Math.Abs(TrainManager.PlayerTrain.CurrentSpeed) < 0.1)
                                {
                                    if (leftopen == CurrentRoute.Stations[j].OpenLeftDoors & rightopen == CurrentRoute.Stations[j].OpenRightDoors)
                                    {
                                        bad = false;
                                    }
                                }
                            }
                        }
                    }
                    else
                    {
                        bad = false;
                    }
                    if (bad)
                    {
                        OpenedDoorsCounter += (Math.Abs(TrainManager.PlayerTrain.CurrentSpeed) + 0.25) * TimeElapsed;
                    }
                    else if (OpenedDoorsCounter != 0.0)
                    {
                        int x = (int)Math.Ceiling(ScoreFactorOpenedDoors * OpenedDoorsCounter);
                        this.CurrentValue += x;
                        if (x != 0)
                        {
                            AddScore(x, ScoreTextToken.DoorsOpened, 5.0);
                        }
                        OpenedDoorsCounter = 0.0;
                    }
                }
                // overspeed
                double nr = TrainManager.PlayerTrain.CurrentRouteLimit;
                double ns = TrainManager.PlayerTrain.CurrentSectionLimit;
                double n  = nr < ns ? nr : ns;
                double a  = Math.Abs(TrainManager.PlayerTrain.CurrentSpeed) - 0.277777777777778;

                if (a > n)
                {
                    OverspeedCounter += (a - n) * TimeElapsed;
                }
                else if (OverspeedCounter != 0.0)
                {
                    int x = (int)Math.Ceiling(ScoreFactorOverspeed * OverspeedCounter);
                    this.CurrentValue += x;
                    if (x != 0)
                    {
                        AddScore(x, ScoreTextToken.Overspeed, 5.0);
                    }
                    OverspeedCounter = 0.0;
                }
                // toppling
                {
                    bool q = false;
                    for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                    {
                        if (TrainManager.PlayerTrain.Cars[j].Topples)
                        {
                            q = true;
                            break;
                        }
                    }
                    if (q)
                    {
                        TopplingCounter += TimeElapsed;
                    }
                    else if (TopplingCounter != 0.0)
                    {
                        int x = (int)Math.Ceiling(ScoreFactorToppling * TopplingCounter);
                        this.CurrentValue += x;
                        if (x != 0)
                        {
                            AddScore(x, ScoreTextToken.Toppling, 5.0);
                        }
                        TopplingCounter = 0.0;
                    }
                }
                // derailment
                if (!Derailed)
                {
                    bool q = false;
                    for (int j = 0; j < TrainManager.PlayerTrain.Cars.Length; j++)
                    {
                        if (TrainManager.PlayerTrain.Cars[j].Derailed)
                        {
                            q = true;
                            break;
                        }
                    }
                    if (q)
                    {
                        int x = ScoreValueDerailment;
                        if (this.CurrentValue > 0)
                        {
                            x -= this.CurrentValue;
                        }
                        this.CurrentValue += x;
                        if (x != 0)
                        {
                            AddScore(x, ScoreTextToken.Derailed, 5.0);
                        }
                        Derailed = true;
                    }
                }
                // red signal
                {
                    if (TrainManager.PlayerTrain.CurrentSectionLimit == 0.0)
                    {
                        if (!RedSignal)
                        {
                            int x = ScoreValueRedSignal;
                            this.CurrentValue += x;
                            if (x != 0)
                            {
                                AddScore(x, ScoreTextToken.PassedRedSignal, 5.0);
                            }
                            RedSignal = true;
                        }
                    }
                    else
                    {
                        RedSignal = false;
                    }
                }
                // arrival
                {
                    int j = TrainManager.PlayerTrain.Station;
                    if (j >= 0 & j < CurrentRoute.Stations.Length)
                    {
                        if (j >= ArrivalStation & TrainManager.PlayerTrain.StationState == TrainStopState.Boarding)
                        {
                            if (j == 0 || CurrentRoute.Stations[j - 1].Type != StationType.ChangeEnds)
                            {
                                // arrival
                                int xa = ScoreValueStationArrival;
                                this.CurrentValue += xa;
                                if (xa != 0)
                                {
                                    AddScore(xa, ScoreTextToken.ArrivedAtStation, 10.0);
                                }
                                // early/late
                                int xb;
                                if (CurrentRoute.Stations[j].ArrivalTime >= 0)
                                {
                                    double d = SecondsSinceMidnight - CurrentRoute.Stations[j].ArrivalTime;
                                    if (d >= -5.0 & d <= 0.0)
                                    {
                                        xb = ScoreValueStationPerfectTime;
                                        this.CurrentValue += xb;
                                        AddScore(xb, ScoreTextToken.PerfectTimeBonus, 10.0);
                                    }
                                    else if (d > 0.0)
                                    {
                                        xb = (int)Math.Ceiling(ScoreFactorStationLate * (d - 1.0));
                                        this.CurrentValue += xb;
                                        if (xb != 0)
                                        {
                                            AddScore(xb, ScoreTextToken.Late, 10.0);
                                        }
                                    }
                                    else
                                    {
                                        xb = 0;
                                    }
                                }
                                else
                                {
                                    xb = 0;
                                }
                                // position
                                int xc;
                                int p = CurrentRoute.Stations[j].GetStopIndex(TrainManager.PlayerTrain.NumberOfCars);
                                if (p >= 0)
                                {
                                    double d = TrainManager.PlayerTrain.StationDistanceToStopPoint;
                                    double r;
                                    if (d >= 0)
                                    {
                                        double t = CurrentRoute.Stations[j].Stops[p].BackwardTolerance;
                                        r = (Math.Sqrt(d * d + 1.0) - 1.0) / (Math.Sqrt(t * t + 1.0) - 1.0);
                                    }
                                    else
                                    {
                                        double t = CurrentRoute.Stations[j].Stops[p].ForwardTolerance;
                                        r = (Math.Sqrt(d * d + 1.0) - 1.0) / (Math.Sqrt(t * t + 1.0) - 1.0);
                                    }
                                    if (r < 0.01)
                                    {
                                        xc = ScoreValueStationPerfectStop;
                                        this.CurrentValue += xc;
                                        AddScore(xc, ScoreTextToken.PerfectStopBonus, 10.0);
                                    }
                                    else
                                    {
                                        if (r > 1.0)
                                        {
                                            r = 1.0;
                                        }
                                        r  = (r - 0.01) * 1.01010101010101;
                                        xc = (int)Math.Ceiling(ScoreFactorStationStop * r);
                                        this.CurrentValue += xc;
                                        if (xc != 0)
                                        {
                                            AddScore(xc, ScoreTextToken.Stop, 10.0);
                                        }
                                    }
                                }
                                else
                                {
                                    xc = 0;
                                }
                                // sum
                                if (Interface.CurrentOptions.GameMode == GameMode.Arcade)
                                {
                                    int xs = xa + xb + xc;
                                    AddScore("", 10.0);
                                    AddScore(xs, ScoreTextToken.Total, 10.0, false);
                                    AddScore(" ", 10.0);
                                }
                                // evaluation
                                if (Interface.CurrentOptions.GameMode == GameMode.Arcade)
                                {
                                    if (CurrentRoute.Stations[j].Type == StationType.Terminal)
                                    {
                                        double y = (double)this.CurrentValue / (double)Maximum;
                                        if (y < 0.0)
                                        {
                                            y = 0.0;
                                        }
                                        if (y > 1.0)
                                        {
                                            y = 1.0;
                                        }
                                        int k = (int)Math.Floor(y * (double)Translations.RatingsCount);
                                        if (k >= Translations.RatingsCount)
                                        {
                                            k = Translations.RatingsCount - 1;
                                        }
                                        System.Globalization.CultureInfo Culture = System.Globalization.CultureInfo.InvariantCulture;
                                        AddScore(Translations.GetInterfaceString("score_rating"), 20.0);
                                        AddScore(Translations.GetInterfaceString("rating_" + k.ToString(Culture)) + " (" + (100.0 * y).ToString("0.00", Culture) + "%)", 20.0);
                                    }
                                }
                            }
                            // finalize
                            DepartureStation = j;
                            ArrivalStation   = j + 1;
                        }
                    }
                }
                // departure
                {
                    int j = TrainManager.PlayerTrain.Station;
                    if (j >= 0 & j < CurrentRoute.Stations.Length & j == DepartureStation)
                    {
                        bool q;
                        if (CurrentRoute.Stations[j].OpenLeftDoors | CurrentRoute.Stations[j].OpenRightDoors)
                        {
                            q = TrainManager.PlayerTrain.StationState == TrainStopState.Completed;
                        }
                        else
                        {
                            q = TrainManager.PlayerTrain.StationState != TrainStopState.Pending & (TrainManager.PlayerTrain.CurrentSpeed <-1.5 | TrainManager.PlayerTrain.CurrentSpeed> 1.5);
                        }
                        if (q)
                        {
                            double r = TrainManager.PlayerTrain.StationDepartureTime - SecondsSinceMidnight;
                            if (r > 0.0)
                            {
                                int x = (int)Math.Ceiling(ScoreFactorStationDeparture * r);
                                this.CurrentValue += x;
                                if (x != 0)
                                {
                                    AddScore(x, ScoreTextToken.PrematureDeparture, 5.0);
                                }
                            }
                            DepartureStation = -1;
                        }
                    }
                }
                // passengers
                if (TrainManager.PlayerTrain.Passengers.FallenOver & PassengerTimer == 0.0)
                {
                    int x = ScoreValuePassengerDiscomfort;
                    this.CurrentValue += x;
                    AddScore(x, ScoreTextToken.PassengerDiscomfort, 5.0);
                    PassengerTimer = 5.0;
                }
                else
                {
                    PassengerTimer -= TimeElapsed;
                    if (PassengerTimer <= 0.0)
                    {
                        if (TrainManager.PlayerTrain.Passengers.FallenOver)
                        {
                            PassengerTimer = 5.0;
                        }
                        else
                        {
                            PassengerTimer = 0.0;
                        }
                    }
                }
            }
示例#23
0
            /// <summary>Loads a custom plugin for the specified train.</summary>
            /// <param name="trainFolder">The absolute path to the train folder.</param>
            /// <param name="encoding">The encoding to be used.</param>
            /// <returns>Whether the plugin was loaded successfully.</returns>
            internal bool LoadCustomPlugin(string trainFolder, System.Text.Encoding encoding)
            {
                string config = OpenBveApi.Path.CombineFile(trainFolder, "ats.cfg");

                if (!System.IO.File.Exists(config))
                {
                    return(false);
                }

                string Text = System.IO.File.ReadAllText(config, encoding);

                Text = Text.Replace("\r", "").Replace("\n", "");
                string file;

                try
                {
                    file = OpenBveApi.Path.CombineFile(trainFolder, Text);
                }
                catch
                {
                    Interface.AddMessage(MessageType.Error, true, "The train plugin path was malformed in " + config);
                    return(false);
                }

                string title = System.IO.Path.GetFileName(file);

                if (!System.IO.File.Exists(file))
                {
                    if (Text.EndsWith(".dll") && encoding.Equals(System.Text.Encoding.Unicode))
                    {
                        // Our filename ends with .dll so probably is not mangled Unicode
                        Interface.AddMessage(MessageType.Error, true, "The train plugin " + title + " could not be found in " + config);
                        return(false);
                    }

                    // Try again with ASCII encoding
                    Text = System.IO.File.ReadAllText(config, System.Text.Encoding.GetEncoding(1252));
                    Text = Text.Replace("\r", "").Replace("\n", "");
                    try
                    {
                        file = OpenBveApi.Path.CombineFile(trainFolder, Text);
                    }
                    catch
                    {
                        Interface.AddMessage(MessageType.Error, true, "The train plugin path was malformed in " + config);
                        return(false);
                    }

                    title = System.IO.Path.GetFileName(file);
                    if (!System.IO.File.Exists(file))
                    {
                        // Nope, still not found
                        Interface.AddMessage(MessageType.Error, true, "The train plugin " + title + " could not be found in " + config);
                        return(false);
                    }
                }

                Program.FileSystem.AppendToLogFile("Loading train plugin: " + file);
                bool success = LoadPlugin(file, trainFolder);

                if (success == false)
                {
                    Loading.PluginError = Translations.GetInterfaceString("errors_plugin_failure1").Replace("[plugin]", file);
                }
                else
                {
                    Program.FileSystem.AppendToLogFile("Train plugin loaded successfully.");
                }

                return(success);
            }
示例#24
0
            /// <summary>Renders the timetable data</summary>
            /// <param name="timetableTexture">The texture to create</param>
            internal void RenderData(ref Texture timetableTexture)
            {
                // prepare timetable
                int   w = 384, h = 192;
                int   offsetx           = 0;
                int   actualheight      = h;
                float descriptionwidth  = 256;
                float descriptionheight = 16;
                float stationnamewidth  = 16;

                for (int k = 0; k < 2; k++)
                {
                    Bitmap b = new Bitmap(w, h);
                    System.Drawing.Graphics g = System.Drawing.Graphics.FromImage(b);
                    g.SmoothingMode     = System.Drawing.Drawing2D.SmoothingMode.AntiAlias;
                    g.TextRenderingHint = System.Drawing.Text.TextRenderingHint.ClearTypeGridFit;
                    g.Clear(Color.Transparent);
                    g.FillRectangle(Brushes.White, new RectangleF(offsetx, 0, w, actualheight));
                    Font f   = new Font(FontFamily.GenericSansSerif, 13.0f, GraphicsUnit.Pixel);
                    Font fs  = new Font(FontFamily.GenericSansSerif, 11.0f, GraphicsUnit.Pixel);
                    Font fss = new Font(FontFamily.GenericSansSerif, 9.0f, GraphicsUnit.Pixel);
                    // draw timetable
                    string t;
                    // description
                    float x0 = offsetx + 8;
                    float y0 = 8;
                    if (k == 1)
                    {
                        t = DefaultTimetableDescription;
                        g.DrawString(t, f, Brushes.Black, new RectangleF(x0, 6, descriptionwidth, descriptionheight + 8));
                        y0 += descriptionheight + 2;
                    }

                    // highest speed
                    t = Translations.GetInterfaceString("timetable_highestspeed");
                    SizeF s = g.MeasureString(t, fs);
                    g.DrawString(t, fs, Brushes.Black, x0, y0);
                    float y0a = y0 + s.Height + 2;
                    float x1  = x0 + s.Width + 4;
                    for (int i = 0; i < Tracks.Length; i++)
                    {
                        float y = y0a + 18 * i;
                        t = Tracks[i].Speed;
                        g.DrawString(t, f, Brushes.Black, x0, y);
                        s = g.MeasureString(t, f);
                        float x = x0 + s.Width + 4;
                        if (x > x1)
                        {
                            x1 = x;
                        }
                    }

                    g.DrawLine(Pens.LightGray, new PointF(x1 - 2, 4 + descriptionheight), new PointF(x1 - 2, y0a + 18 * Tracks.Length - 1));
                    // driving time
                    t = Translations.GetInterfaceString("timetable_drivingtime");
                    s = g.MeasureString(t, fs);
                    g.DrawString(t, fs, Brushes.Black, x1, y0);
                    float x2 = x1 + s.Width + 4;
                    for (int i = 0; i < Tracks.Length; i++)
                    {
                        float y = y0a + 18 * i;
                        if (Tracks[i].Time.Hour.Length != 0)
                        {
                            t = Tracks[i].Time.Hour;
                            g.DrawString(t, fss, Brushes.Black, x1, y + 2);
                        }
                        else
                        {
                            t = "0";
                        }

                        s = g.MeasureString(t, fss, 9999, StringFormat.GenericTypographic);
                        float x = x1 + s.Width - 1;
                        if (Tracks[i].Time.Minute.Length != 0)
                        {
                            t = Tracks[i].Time.Minute;
                            g.DrawString(t, fs, Brushes.Black, x, y + 2);
                        }
                        else
                        {
                            t = "00:";
                        }

                        s  = g.MeasureString(t, fs, 9999, StringFormat.GenericTypographic);
                        x += s.Width + 1;
                        t  = Tracks[i].Time.Second;
                        g.DrawString(t, fss, Brushes.Black, x, y + 2);
                        s  = g.MeasureString(t, fss, 9999, StringFormat.GenericTypographic);
                        x += s.Width + 8;
                        if (x > x2)
                        {
                            x2 = x;
                        }
                    }

                    for (int i = 0; i < Tracks.Length; i++)
                    {
                        float y = y0a + 18 * i;
                        g.DrawLine(Pens.LightGray, new PointF(offsetx + 4, y - 1), new PointF(x2 - 2, y - 1));
                    }

                    g.DrawLine(Pens.LightGray, new PointF(x2 - 2, 4 + descriptionheight), new PointF(x2 - 2, y0a + 18 * Tracks.Length - 1));
                    // station name
                    float y2 = y0;
                    t = Translations.GetInterfaceString("timetable_stationname");
                    s = g.MeasureString(t, f);
                    g.DrawString(t, f, Brushes.Black, x2, y2);
                    float x3 = x2 + s.Width + 4;
                    for (int i = 0; i < Stations.Length; i++)
                    {
                        float y = y0 + 18 * (i + 1) + 2;
                        g.DrawLine(Pens.LightGray, new PointF(x2 - 2, y - 1), new PointF(w - 4, y - 1));
                        t = Stations[i].Name;
                        if (Stations[i].NameJapanese & Stations[i].Name.Length > 1)
                        {
                            float[] sizes     = new float[t.Length];
                            float   totalsize = 0.0f;
                            for (int j = 0; j < t.Length; j++)
                            {
                                sizes[j]   = g.MeasureString(new string(t[j], 1), f, 9999, StringFormat.GenericTypographic).Width;
                                totalsize += sizes[j];
                            }

                            float space = (stationnamewidth - totalsize) / (float)(t.Length - 1);
                            float x     = 0.0f;
                            for (int j = 0; j < t.Length; j++)
                            {
                                g.DrawString(new string(t[j], 1), f, Brushes.Black, x2 + x, y);
                                x += sizes[j] + space;
                            }
                        }
                        else
                        {
                            g.DrawString(t, f, Brushes.Black, x2, y);
                        }

                        s = g.MeasureString(t, f);
                        {
                            float x = x2 + s.Width + 4;
                            if (x > x3)
                            {
                                x3 = x;
                            }
                        }
                    }

                    g.DrawLine(Pens.LightGray, new PointF(x3 - 2, 4 + descriptionheight), new PointF(x3 - 2, y0 + 18 * (Stations.Length + 1)));
                    if (k == 0)
                    {
                        stationnamewidth = x3 - x2 - 6;
                    }

                    // arrival time
                    t = Translations.GetInterfaceString("timetable_arrivaltime");
                    s = g.MeasureString(t, f);
                    g.DrawString(t, f, Brushes.Black, x3, y2);
                    float x4 = x3 + s.Width + 4;
                    for (int i = 0; i < Stations.Length; i++)
                    {
                        float y = y0 + 18 * (i + 1) + 2;
                        if (Stations[i].Pass)
                        {
                            t = "00";
                            s = g.MeasureString(t, fs);
                            float x = x3 + s.Width;
                            t = "   ↓";
                            g.DrawString(t, f, Brushes.Black, x, y);
                            s  = g.MeasureString(t, f);
                            x += +s.Width + 4;
                            if (x > x4)
                            {
                                x4 = x;
                            }
                        }
                        else
                        {
                            if (Stations[i].Arrival.Hour.Length != 0)
                            {
                                t = Stations[i].Arrival.Hour;
                                g.DrawString(t, fs, Brushes.Black, x3, y);
                            }
                            else
                            {
                                t = "00";
                            }

                            s = g.MeasureString(t, fs);
                            float x = x3 + s.Width;
                            if (Stations[i].Arrival.Minute.Length != 0 & Stations[i].Arrival.Second.Length != 0)
                            {
                                t = Stations[i].Arrival.Minute + ":" + Stations[i].Arrival.Second;
                            }
                            else
                            {
                                t = "";
                            }

                            g.DrawString(t, f, Brushes.Black, x, y);
                            s  = g.MeasureString(t, f);
                            x += s.Width + 4;
                            if (x > x4)
                            {
                                x4 = x;
                            }
                        }
                    }

                    g.DrawLine(Pens.LightGray, new PointF(x4 - 2, 4 + descriptionheight), new PointF(x4 - 2, y0 + 18 * (Stations.Length + 1)));
                    // departure time
                    t = Translations.GetInterfaceString("timetable_departuretime");
                    s = g.MeasureString(t, f);
                    g.DrawString(t, f, Brushes.Black, x4, y2);
                    float x5 = x4 + s.Width + 4;
                    for (int i = 0; i < Stations.Length; i++)
                    {
                        float y = y0 + 18 * (i + 1) + 2;
                        if (Stations[i].Terminal)
                        {
                            t = "00";
                            s = g.MeasureString(t, fs);
                            float       x  = x4 + s.Width;
                            const float c0 = 4;
                            const float c1 = 32;
                            g.DrawLine(Pens.Black, new PointF(x + c0, y + 6), new PointF(x + c1, y + 6));
                            g.DrawLine(Pens.Black, new PointF(x + c0, y + 10), new PointF(x + c1, y + 10));
                            x += c1 + 4;
                            if (x > x5)
                            {
                                x5 = x;
                            }
                        }
                        else
                        {
                            if (Stations[i].Departure.Hour.Length != 0)
                            {
                                t = Stations[i].Departure.Hour;
                                g.DrawString(t, fs, Brushes.Black, x4, y);
                            }
                            else
                            {
                                t = "00";
                            }

                            s = g.MeasureString(t, fs);
                            float x = x4 + s.Width;
                            if (Stations[i].Departure.Minute.Length != 0 & Stations[i].Departure.Second.Length != 0)
                            {
                                t = Stations[i].Departure.Minute + ":" + Stations[i].Departure.Second;
                            }
                            else
                            {
                                t = "";
                            }

                            g.DrawString(t, f, Brushes.Black, x, y);
                            s  = g.MeasureString(t, f);
                            x += s.Width + 4;
                            if (x > x5)
                            {
                                x5 = x;
                            }
                        }
                    }

                    for (int i = 0; i < Stations.Length; i++)
                    {
                        float y = y0 + 18 * (i + 1) + 2;
                        g.DrawLine(Pens.LightGray, new PointF(x2 - 2, y - 1), new PointF(w - 4, y - 1));
                    }

                    // border
                    if (k == 1)
                    {
                        g.DrawLine(Pens.Black, new PointF(offsetx + 4, 4), new PointF(offsetx + 4, y0a + 18 * Tracks.Length - 1));
                        g.DrawLine(Pens.Black, new PointF(offsetx + 4, y0a + 18 * Tracks.Length - 1), new PointF(x2 - 2, y0a + 18 * Tracks.Length - 1));
                        g.DrawLine(Pens.Black, new PointF(offsetx + 4, 4), new PointF(w - 4, 4));
                        g.DrawLine(Pens.Black, new PointF(offsetx + 4, 4 + descriptionheight), new PointF(w - 4, 4 + descriptionheight));
                        g.DrawLine(Pens.Black, new PointF(x2 - 2, y0 + 18 * (Stations.Length + 1)), new PointF(w - 4, y0 + 18 * (Stations.Length + 1)));
                        g.DrawLine(Pens.Black, new PointF(w - 4, 4), new PointF(w - 4, y0 + 18 * (Stations.Length + 1)));
                        g.DrawLine(Pens.Black, new PointF(x2 - 2, y0a + 18 * Tracks.Length - 1), new PointF(x2 - 2, y0 + 18 * (Stations.Length + 1)));
                    }

                    // measure
                    w = (int)Math.Ceiling((double)(x5 + 1));
                    h = (int)Math.Ceiling((double)(y0 + 18 * (Stations.Length + 1) + 4));
                    // description
                    if (k == 0)
                    {
                        t = DefaultTimetableDescription;
                        s = g.MeasureString(t, f, w - 16);
                        descriptionwidth  = s.Width;
                        descriptionheight = s.Height + 2;
                        h += (int)Math.Ceiling((double)s.Height) + 4;
                    }
                    f.Dispose();
                    fs.Dispose();
                    fss.Dispose();
                    // finish
                    if (k == 0)
                    {
                        // measures
                        int nw = Program.Renderer.TextureManager.RoundUpToPowerOfTwo(w);
                        offsetx      = nw - w;
                        w            = nw;
                        actualheight = h;
                        h            = Program.Renderer.TextureManager.RoundUpToPowerOfTwo(h);
                    }
                    else
                    {
                        // create texture
                        g.Dispose();
                        timetableTexture = Program.Renderer.TextureManager.RegisterTexture(b);
                    }
                }
            }
示例#25
0
        // load threaded
        private static void LoadThreaded()
        {
            try {
                LoadEverythingThreaded();
            } catch (Exception ex) {
                for (int i = 0; i < Program.TrainManager.Trains.Length; i++)
                {
                    if (Program.TrainManager.Trains[i] != null && Program.TrainManager.Trains[i].Plugin != null)
                    {
                        if (Program.TrainManager.Trains[i].Plugin.LastException != null)
                        {
                            Interface.AddMessage(MessageType.Critical, false, "The train plugin " + Program.TrainManager.Trains[i].Plugin.PluginTitle + " caused a critical error in the route and train loader: " + Program.TrainManager.Trains[i].Plugin.LastException.Message);
                            CrashHandler.LoadingCrash(Program.TrainManager.Trains[i].Plugin.LastException + Environment.StackTrace, true);
                            Program.RestartArguments = " ";
                            Cancel = true;
                            return;
                        }
                    }
                }
                if (ex is DllNotFoundException)
                {
                    Interface.AddMessage(MessageType.Critical, false, "The required system library " + ex.Message + " was not found on the system.");
                    switch (ex.Message)
                    {
                    case "libopenal.so.1":
                        MessageBox.Show("openAL was not found on this system. \n Please install libopenal1 via your distribtion's package management system.", Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
                        break;

                    default:
                        MessageBox.Show("The required system library " + ex.Message + " was not found on this system.", Translations.GetInterfaceString("program_title"), MessageBoxButtons.OK, MessageBoxIcon.Hand);
                        break;
                    }
                }
                else
                {
                    Interface.AddMessage(MessageType.Critical, false, "The route and train loader encountered the following critical error: " + ex.Message);
                    CrashHandler.LoadingCrash(ex + Environment.StackTrace, false);
                }

                Program.RestartArguments = " ";
                Cancel = true;
            }
            if (JobAvailable)
            {
                Thread.Sleep(10);
            }
            Complete = true;
        }
示例#26
0
文件: Station.cs 项目: xfleet/OpenBVE
        /// <summary>Is called once a frame to update the station state for the given train</summary>
        /// <param name="Train">The train</param>
        /// <param name="TimeElapsed">The frame time elapsed</param>
        private static void UpdateTrainStation(Train Train, double TimeElapsed)
        {
            if (Train.Station >= 0)
            {
                int    i = Train.Station;
                int    n = Program.CurrentRoute.Stations[Train.Station].GetStopIndex(Train.NumberOfCars);
                double tf, tb;
                if (n >= 0)
                {
                    double p0 = Train.Cars[0].FrontAxle.Follower.TrackPosition - Train.Cars[0].FrontAxle.Position + 0.5 * Train.Cars[0].Length;
                    double p1 = Program.CurrentRoute.Stations[i].Stops[n].TrackPosition;
                    tf = Program.CurrentRoute.Stations[i].Stops[n].ForwardTolerance;
                    tb = Program.CurrentRoute.Stations[i].Stops[n].BackwardTolerance;
                    Train.StationDistanceToStopPoint = p1 - p0;
                }
                else
                {
                    Train.StationDistanceToStopPoint = 0.0;
                    tf = 5.0;
                    tb = 5.0;
                }
                if (Train.StationState == TrainStopState.Pending)
                {
                    Train.StationDepartureSoundPlayed = false;
                    if (Program.CurrentRoute.Stations[i].StopsHere(Train))
                    {
                        Train.StationDepartureSoundPlayed = false;
                        //Check whether all doors are controlled by the driver
                        if (Train.Specs.DoorOpenMode != DoorMode.Manual)
                        {
                            //Check that we are not moving
                            if (Math.Abs(Train.CurrentSpeed) < 0.1 / 3.6 &
                                Math.Abs(Train.Specs.CurrentAverageAcceleration) < 0.1 / 3.6)
                            {
                                AttemptToOpenDoors(Train, i, tb, tf);
                            }
                        }
                        // detect arrival
                        if (Train.CurrentSpeed > -0.277777777777778 & Train.CurrentSpeed < 0.277777777777778)
                        {
                            bool left, right;
                            if (Program.CurrentRoute.Stations[i].OpenLeftDoors)
                            {
                                left = false;
                                for (int j = 0; j < Train.Cars.Length; j++)
                                {
                                    if (Train.Cars[j].Doors[0].AnticipatedOpen)
                                    {
                                        left = true; break;
                                    }
                                }
                            }
                            else
                            {
                                left = true;
                            }
                            if (Program.CurrentRoute.Stations[i].OpenRightDoors)
                            {
                                right = false;
                                for (int j = 0; j < Train.Cars.Length; j++)
                                {
                                    if (Train.Cars[j].Doors[1].AnticipatedOpen)
                                    {
                                        right = true; break;
                                    }
                                }
                            }
                            else
                            {
                                right = true;
                            }
                            if (left & right)
                            {
                                // arrival
                                Train.StationState = TrainStopState.Boarding;
                                Train.SafetySystems.StationAdjust.Lit = false;
                                Train.Specs.DoorClosureAttempted      = false;
                                Train.SafetySystems.PassAlarm.Halt();
                                SoundBuffer buffer = (SoundBuffer)Program.CurrentRoute.Stations[i].ArrivalSoundBuffer;
                                if (buffer != null)
                                {
                                    OpenBveApi.Math.Vector3 pos = Program.CurrentRoute.Stations[i].SoundOrigin;
                                    Program.Sounds.PlaySound(buffer, 1.0, 1.0, pos, false);
                                }
                                Train.StationArrivalTime   = Program.CurrentRoute.SecondsSinceMidnight;
                                Train.StationDepartureTime = Program.CurrentRoute.Stations[i].DepartureTime - Train.TimetableDelta;
                                if (Train.StationDepartureTime - Program.CurrentRoute.SecondsSinceMidnight < Program.CurrentRoute.Stations[i].StopTime)
                                {
                                    Train.StationDepartureTime = Program.CurrentRoute.SecondsSinceMidnight + Program.CurrentRoute.Stations[i].StopTime;
                                }
                                Train.Passengers.PassengerRatio = Program.CurrentRoute.Stations[i].PassengerRatio;
                                UpdateTrainMassFromPassengerRatio(Train);
                                if (Train.IsPlayerTrain)
                                {
                                    double early = 0.0;
                                    if (Program.CurrentRoute.Stations[i].ArrivalTime >= 0.0)
                                    {
                                        early = (Program.CurrentRoute.Stations[i].ArrivalTime - Train.TimetableDelta) - Train.StationArrivalTime;
                                    }
                                    string s;
                                    if (early < -1.0)
                                    {
                                        s = Translations.GetInterfaceString("message_station_arrival_late");
                                    }
                                    else if (early > 1.0)
                                    {
                                        s = Translations.GetInterfaceString("message_station_arrival_early");
                                    }
                                    else
                                    {
                                        s = Translations.GetInterfaceString("message_station_arrival");
                                    }
                                    System.Globalization.CultureInfo Culture = System.Globalization.CultureInfo.InvariantCulture;
                                    TimeSpan a = TimeSpan.FromSeconds(Math.Abs(early));
                                    string   b = a.Hours.ToString("00", Culture) + ":" + a.Minutes.ToString("00", Culture) + ":" + a.Seconds.ToString("00", Culture);
                                    if (Train.StationDistanceToStopPoint < -0.1)
                                    {
                                        s += Translations.GetInterfaceString("message_delimiter") + Translations.GetInterfaceString("message_station_overrun");
                                    }
                                    else if (Train.StationDistanceToStopPoint > 0.1)
                                    {
                                        s += Translations.GetInterfaceString("message_delimiter") + Translations.GetInterfaceString("message_station_underrun");
                                    }
                                    double d = Math.Abs(Train.StationDistanceToStopPoint);
                                    string c = d.ToString("0.0", Culture);
                                    if (Program.CurrentRoute.Stations[i].Type == StationType.Terminal)
                                    {
                                        s += Translations.GetInterfaceString("message_delimiter") + Translations.GetInterfaceString("message_station_terminal");
                                    }
                                    s = s.Replace("[name]", Program.CurrentRoute.Stations[i].Name);
                                    s = s.Replace("[time]", b);
                                    s = s.Replace("[difference]", c);
                                    MessageManager.AddMessage(s, MessageDependency.StationArrival, GameMode.Normal, MessageColor.White, Program.CurrentRoute.SecondsSinceMidnight + 10.0, null);
                                    if (Program.CurrentRoute.Stations[i].Type == StationType.Normal)
                                    {
                                        s = Translations.GetInterfaceString("message_station_deadline");
                                        MessageManager.AddMessage(s, MessageDependency.StationDeparture, GameMode.Normal, MessageColor.White, double.PositiveInfinity, null);
                                    }
                                    Timetable.UpdateCustomTimetable(Program.CurrentRoute.Stations[i].TimetableDaytimeTexture, Program.CurrentRoute.Stations[i].TimetableNighttimeTexture);
                                }
                                // schedule door locks (passengers stuck between the doors)
                                for (int j = 0; j < Train.Cars.Length; j++)
                                {
                                    for (int k = 0; k < Train.Cars[j].Doors.Length; k++)
                                    {
                                        Train.Cars[j].Doors[k].DoorLockDuration = 0.0;
                                        if (Program.CurrentRoute.Stations[i].OpenLeftDoors & Train.Cars[j].Doors[k].Direction == -1 | Program.CurrentRoute.Stations[i].OpenRightDoors & Train.Cars[j].Doors[k].Direction == 1)
                                        {
                                            double p = 0.005 * Program.CurrentRoute.Stations[i].PassengerRatio * Program.CurrentRoute.Stations[i].PassengerRatio * Program.CurrentRoute.Stations[i].PassengerRatio * Program.CurrentRoute.Stations[i].PassengerRatio;
                                            if (Program.RandomNumberGenerator.NextDouble() < p)
                                            {
                                                /*
                                                 * -- door lock at state --
                                                 * minimum: 0.2 (nearly closed)
                                                 * maximum: 0.8 (nearly opened)
                                                 * */
                                                Train.Cars[j].Doors[k].DoorLockState = 0.2 + 0.6 * Program.RandomNumberGenerator.NextDouble();

                                                /* -- waiting time --
                                                 * minimum: 2.9 s
                                                 * maximum: 40.0 s
                                                 * average: 7.6 s
                                                 * */
                                                p = Program.RandomNumberGenerator.NextDouble();
                                                Train.Cars[j].Doors[k].DoorLockDuration = (50.0 - 10.0 * p) / (17.0 - 16.0 * p);
                                            }
                                        }
                                    }
                                }
                            }
                            else
                            {
                                if (Train.SafetySystems.StationAdjust != null)
                                {
                                    Train.SafetySystems.StationAdjust.Update(tb, tf);
                                }
                            }
                        }
                    }
                }
                else if (Train.StationState == TrainStopState.Boarding)
                {
                    for (int j = 0; j < Train.Cars.Length; j++)
                    {
                        if (GetDoorsState(Train, j, Program.CurrentRoute.Stations[i].OpenLeftDoors, Program.CurrentRoute.Stations[i].OpenRightDoors) == (TrainDoorState.Opened | TrainDoorState.AllOpened))
                        {
                            //Check whether all doors are controlled by the driver, and whether this is a non-standard station type
                            //e.g. Change ends
                            if (Train.Specs.DoorCloseMode != DoorMode.Manual & Program.CurrentRoute.Stations[i].Type == StationType.Normal)
                            {
                                AttemptToCloseDoors(Train);

                                if (Train.Specs.DoorClosureAttempted)
                                {
                                    if (Program.CurrentRoute.Stations[i].OpenLeftDoors && !Train.Cars[j].Doors[0].AnticipatedReopen && Program.RandomNumberGenerator.NextDouble() < Program.CurrentRoute.Stations[i].ReopenDoor)
                                    {
                                        Train.Cars[j].Doors[0].ReopenLimit           = Program.RandomNumberGenerator.Next(1, Program.CurrentRoute.Stations[i].ReopenStationLimit);
                                        Train.Cars[j].Doors[0].ReopenCounter         = 0;
                                        Train.Cars[j].Doors[0].InterferingObjectRate = Program.RandomNumberGenerator.Next(1, Program.CurrentRoute.Stations[i].MaxInterferingObjectRate) * 0.01;
                                        if (Train.Cars[j].Doors[0].InterferingObjectRate * Train.Cars[j].Doors[0].Width >= Train.Cars[j].Doors[0].MaxTolerance)
                                        {
                                            Train.Cars[j].Doors[0].AnticipatedReopen = true;
                                        }
                                    }
                                    if (Program.CurrentRoute.Stations[i].OpenRightDoors && !Train.Cars[j].Doors[1].AnticipatedReopen && Program.RandomNumberGenerator.NextDouble() < Program.CurrentRoute.Stations[i].ReopenDoor)
                                    {
                                        Train.Cars[j].Doors[1].ReopenLimit           = Program.RandomNumberGenerator.Next(1, Program.CurrentRoute.Stations[i].ReopenStationLimit);
                                        Train.Cars[j].Doors[1].ReopenCounter         = 0;
                                        Train.Cars[j].Doors[1].InterferingObjectRate = Program.RandomNumberGenerator.Next(1, Program.CurrentRoute.Stations[i].MaxInterferingObjectRate) * 0.01;
                                        if (Train.Cars[j].Doors[1].InterferingObjectRate * Train.Cars[j].Doors[1].Width >= Train.Cars[j].Doors[1].MaxTolerance)
                                        {
                                            Train.Cars[j].Doors[1].AnticipatedReopen = true;
                                        }
                                    }
                                }
                            }
                        }
                    }
                    // detect departure
                    bool left, right;
                    if (!Program.CurrentRoute.Stations[i].OpenLeftDoors & !Program.CurrentRoute.Stations[i].OpenRightDoors)
                    {
                        left  = true;
                        right = true;
                    }
                    else
                    {
                        if (Program.CurrentRoute.Stations[i].OpenLeftDoors)
                        {
                            left = false;
                            for (int j = 0; j < Train.Cars.Length; j++)
                            {
                                for (int k = 0; k < Train.Cars[j].Doors.Length; k++)
                                {
                                    if (Train.Cars[j].Doors[k].State != 0.0)
                                    {
                                        left = true; break;
                                    }
                                }
                                if (left)
                                {
                                    break;
                                }
                            }
                        }
                        else
                        {
                            left = false;
                        }
                        if (Program.CurrentRoute.Stations[i].OpenRightDoors)
                        {
                            right = false;
                            for (int j = 0; j < Train.Cars.Length; j++)
                            {
                                for (int k = 0; k < Train.Cars[j].Doors.Length; k++)
                                {
                                    if (Train.Cars[j].Doors[k].State != 0.0)
                                    {
                                        right = true; break;
                                    }
                                }
                                if (right)
                                {
                                    break;
                                }
                            }
                        }
                        else
                        {
                            right = false;
                        }
                    }
                    // departure sound
                    if (!Train.StationDepartureSoundPlayed)
                    {
                        SoundBuffer buffer = (SoundBuffer)Program.CurrentRoute.Stations[i].DepartureSoundBuffer;
                        if (buffer != null)
                        {
                            double dur = Program.Sounds.GetDuration(buffer);
                            if (Program.CurrentRoute.SecondsSinceMidnight >= Train.StationDepartureTime - dur)
                            {
                                Program.Sounds.PlaySound(buffer, 1.0, 1.0, Program.CurrentRoute.Stations[i].SoundOrigin, false);
                                Train.StationDepartureSoundPlayed = true;
                            }
                        }
                    }
                    for (int j = 0; j < Train.Cars.Length; j++)
                    {
                        if (Train.Cars[j].Doors[0].AnticipatedReopen && Train.Cars[j].Doors[0].State == Train.Cars[j].Doors[0].InterferingObjectRate)
                        {
                            if (Train.Cars[j].Doors[0].NextReopenTime == 0.0)
                            {
                                Train.Cars[j].Doors[0].NextReopenTime = Program.CurrentRoute.SecondsSinceMidnight + Program.CurrentRoute.Stations[i].InterferenceInDoor;
                            }
                            else if (Train.Cars[j].Doors[0].ReopenCounter < Train.Cars[j].Doors[0].ReopenLimit)
                            {
                                if (Program.CurrentRoute.SecondsSinceMidnight >= Train.Cars[j].Doors[0].NextReopenTime)
                                {
                                    OpenTrainDoors(Train, j, true, false);
                                }
                            }
                            else
                            {
                                Train.Cars[j].Doors[0].AnticipatedReopen = false;
                            }
                        }
                        if (Train.Cars[j].Doors[1].AnticipatedReopen && Train.Cars[j].Doors[1].State == Train.Cars[j].Doors[1].InterferingObjectRate)
                        {
                            if (Train.Cars[j].Doors[1].NextReopenTime == 0.0)
                            {
                                Train.Cars[j].Doors[1].NextReopenTime = Program.CurrentRoute.SecondsSinceMidnight + Program.CurrentRoute.Stations[i].InterferenceInDoor;
                            }
                            else if (Train.Cars[j].Doors[1].ReopenCounter < Train.Cars[j].Doors[1].ReopenLimit)
                            {
                                if (Program.CurrentRoute.SecondsSinceMidnight >= Train.Cars[j].Doors[1].NextReopenTime)
                                {
                                    OpenTrainDoors(Train, j, false, true);
                                }
                            }
                            else
                            {
                                Train.Cars[j].Doors[1].AnticipatedReopen = false;
                            }
                        }
                    }
                    TrainDoorState doorState = GetDoorsState(Train, Program.CurrentRoute.Stations[i].OpenLeftDoors, Program.CurrentRoute.Stations[i].OpenRightDoors);
                    if (left | right)
                    {
                        /*
                         * Assume that passengers only board at a scheduled stop
                         * If the player has opened the doors somewhere else (lineside?)
                         * then passengers should not be boarding
                         */
                        if (doorState != TrainDoorState.AllClosed && Interface.CurrentOptions.LoadingSway)
                        {
                            // passengers boarding
                            for (int j = 0; j < Train.Cars.Length; j++)
                            {
                                if (!Train.Cars[j].EnableLoadingSway)
                                {
                                    continue;
                                }
                                double r = 2.0 * Program.CurrentRoute.Stations[i].PassengerRatio * TimeElapsed;
                                if (r >= Program.RandomNumberGenerator.NextDouble())
                                {
                                    int d =
                                        (int)Math.Floor(Program.RandomNumberGenerator.NextDouble() * (double)Train.Cars[j].Doors.Length);
                                    if (Train.Cars[j].Doors[d].State == 1.0)
                                    {
                                        Train.Cars[j].Specs.CurrentRollShakeDirection += (double)Train.Cars[j].Doors[d].Direction;
                                    }
                                }
                            }
                        }
                    }
                    if (Train.Specs.DoorCloseMode == DoorMode.Manual || doorState == TrainDoorState.None || doorState == (TrainDoorState.Closed | TrainDoorState.AllClosed) || (Program.CurrentRoute.Stations[Train.Station].Type == StationType.ChangeEnds || Program.CurrentRoute.Stations[Train.Station].Type == StationType.Jump))
                    {
                        if (left | right)
                        {
                            // departure message
                            if (Program.CurrentRoute.SecondsSinceMidnight > Train.StationDepartureTime && (Program.CurrentRoute.Stations[i].Type != StationType.Terminal || Train != PlayerTrain))
                            {
                                Train.StationState = TrainStopState.Completed;
                                switch (Program.CurrentRoute.Stations[i].Type)
                                {
                                case StationType.Normal:
                                    if (!Train.IsPlayerTrain)
                                    {
                                        break;                                                 // Only trigger messages for the player train
                                    }
                                    if (!Program.CurrentRoute.Stations[i].OpenLeftDoors & !Program.CurrentRoute.Stations[i].OpenRightDoors | Train.Specs.DoorCloseMode != DoorMode.Manual)
                                    {
                                        MessageManager.AddMessage(Translations.GetInterfaceString("message_station_depart"), MessageDependency.None, GameMode.Normal, MessageColor.White, Program.CurrentRoute.SecondsSinceMidnight + 5.0, null);
                                    }
                                    else
                                    {
                                        MessageManager.AddMessage(Translations.GetInterfaceString("message_station_depart_closedoors"), MessageDependency.None, GameMode.Normal, MessageColor.White, Program.CurrentRoute.SecondsSinceMidnight + 5.0, null);
                                    }
                                    break;

                                case StationType.ChangeEnds:
                                    // Change ends always jumps to the NEXT station
                                    JumpTrain(Train, i + 1);
                                    break;

                                case StationType.Jump:
                                    // Jumps to an arbritrary station as defined in the routefile
                                    JumpTrain(Train, Program.CurrentRoute.Stations[i].JumpIndex);
                                    break;
                                }
                            }
                        }
                        else
                        {
                            Train.StationState = TrainStopState.Completed;
                            if (Train.IsPlayerTrain & Program.CurrentRoute.Stations[i].Type == StationType.Normal)
                            {
                                MessageManager.AddMessage(Translations.GetInterfaceString("message_station_depart"), MessageDependency.None, GameMode.Normal, MessageColor.White, Program.CurrentRoute.SecondsSinceMidnight + 5.0, null);
                            }
                        }
                    }
                }
            }
            else
            {
                if (Train.StationState != TrainStopState.Jumping)
                {
                    Train.StationState = TrainStopState.Pending;
                }
            }
            // automatically close doors
            if (Train.Specs.DoorCloseMode != DoorMode.Manual & !Train.Specs.DoorClosureAttempted)
            {
                if (Train.Station == -1 | Train.StationState == TrainStopState.Completed)
                {
                    if ((GetDoorsState(Train, true, true) & TrainDoorState.AllClosed) == 0)
                    {
                        CloseTrainDoors(Train, true, true);
                        Train.Specs.DoorClosureAttempted = true;
                    }
                }
            }
        }
示例#27
0
文件: Screen.cs 项目: xfleet/OpenBVE
        /// <summary>Changes to or from fullscreen mode.</summary>
        internal static void ToggleFullscreen()
        {
            Program.Renderer.Screen.Fullscreen = !Program.Renderer.Screen.Fullscreen;

            // begin HACK //
            Program.Renderer.OptionFog      = false;
            Program.Renderer.OptionLighting = false;

            if (Program.Renderer.Screen.Fullscreen)
            {
                IList <DisplayResolution> resolutions = DisplayDevice.Default.AvailableResolutions;

                for (int i = 0; i < resolutions.Count; i++)
                {
                    //Test each resolution
                    if (resolutions[i].Width == Interface.CurrentOptions.FullscreenWidth &&
                        resolutions[i].Height == Interface.CurrentOptions.FullscreenHeight &&
                        resolutions[i].BitsPerPixel == Interface.CurrentOptions.FullscreenBits)
                    {
                        DisplayDevice.Default.ChangeResolution(resolutions[i]);
                        Program.currentGameWindow.Width       = resolutions[i].Width;
                        Program.currentGameWindow.Height      = resolutions[i].Height;
                        Program.Renderer.Screen.Width         = Interface.CurrentOptions.FullscreenWidth;
                        Program.Renderer.Screen.Height        = Interface.CurrentOptions.FullscreenHeight;
                        Program.currentGameWindow.WindowState = WindowState.Fullscreen;
                        break;
                    }
                }
                System.Threading.Thread.Sleep(20);
                if (Program.currentGameWindow.WindowState != WindowState.Fullscreen)
                {
                    MessageBox.Show(Translations.GetInterfaceString("errors_fullscreen_switch1") + System.Environment.NewLine +
                                    Translations.GetInterfaceString("errors_fullscreen_switch2"), Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                    Program.Renderer.Screen.Fullscreen = false;
                }
            }
            else
            {
                DisplayDevice.Default.RestoreResolution();
                Program.currentGameWindow.WindowState = WindowState.Normal;
                Program.currentGameWindow.Width       = Interface.CurrentOptions.WindowWidth;
                Program.currentGameWindow.Height      = Interface.CurrentOptions.WindowHeight;

                Program.Renderer.Screen.Width  = Interface.CurrentOptions.WindowWidth;
                Program.Renderer.Screen.Height = Interface.CurrentOptions.WindowHeight;
            }
            Program.Renderer.Lighting.Initialize();
            Program.Renderer.UpdateViewport(ViewportChangeMode.NoChange);
            Program.Renderer.MotionBlur.Initialize(Interface.CurrentOptions.MotionBlur);
            lock (BaseRenderer.GdiPlusLock)
            {
                Timetable.CreateTimetable();
            }
            Timetable.UpdateCustomTimetable(null, null);

            World.InitializeCameraRestriction();
            if (Program.Renderer.OptionBackFaceCulling)
            {
                GL.Enable(EnableCap.CullFace);
            }
            else
            {
                GL.Disable(EnableCap.CullFace);
            }
            // end HACK //

            //Reset the camera when switching between fullscreen and windowed mode
            //Otherwise, if the aspect ratio changes distortion will occur until the view is changed or the camera reset
            if (Program.Renderer.Camera.CurrentMode == CameraViewMode.Interior | Program.Renderer.Camera.CurrentMode == CameraViewMode.InteriorLookAhead)
            {
                Program.Renderer.Camera.Alignment.Position = OpenBveApi.Math.Vector3.Zero;
            }
            Program.Renderer.Camera.Alignment.Yaw   = 0.0;
            Program.Renderer.Camera.Alignment.Pitch = 0.0;
            Program.Renderer.Camera.Alignment.Roll  = 0.0;
        }
示例#28
0
 //We need to explicitly specify the default constructor
 public OpenBVEGame(int width, int height, GraphicsMode currentGraphicsMode, GameWindowFlags @default) : base(width, height, currentGraphicsMode, Translations.GetInterfaceString("program_title"), @default)
 {
     try
     {
         var assemblyFolder      = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);
         System.Drawing.Icon ico = new System.Drawing.Icon(OpenBveApi.Path.CombineFile(OpenBveApi.Path.CombineDirectory(assemblyFolder, "Data"), "icon.ico"));
         this.Icon = ico;
     }
     catch
     {
     }
 }
示例#29
0
        /// <summary>Loads the current controls from the controls.cfg file</summary>
        /// <param name="FileOrNull">An absolute path reference to a saved controls.cfg file, or a null reference to check the default locations</param>
        /// <param name="Controls">The current controls array</param>
        internal static void LoadControls(string FileOrNull, out Control[] Controls)
        {
            string File;
            bool   ControlsReset = false;

            if (FileOrNull == null)
            {
                File = OpenBveApi.Path.CombineFile(Program.FileSystem.SettingsFolder, "1.5.0/controls.cfg");
                if (!System.IO.File.Exists(File))
                {
                    File = OpenBveApi.Path.CombineFile(Program.FileSystem.SettingsFolder, "controls.cfg");
                }
                if (!System.IO.File.Exists(File))
                {
                    //Load the default key assignments if the user settings don't exist
                    File = OpenBveApi.Path.CombineFile(Program.FileSystem.GetDataFolder("Controls"), "Default keyboard assignment.controls");
                    if (!System.IO.File.Exists(File))
                    {
                        MessageBox.Show(Translations.GetInterfaceString("errors_warning") + Environment.NewLine + Translations.GetInterfaceString("errors_controls_missing"),
                                        Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                        Controls = new Control[0];
                        return;
                    }
                }
            }
            else
            {
                File = FileOrNull;
            }
            Controls = new Control[256];
            int         Length  = 0;
            CultureInfo Culture = CultureInfo.InvariantCulture;

            if (System.IO.File.Exists(File))
            {
                string[] Lines = System.IO.File.ReadAllLines(File, new System.Text.UTF8Encoding());
                for (int i = 0; i < Lines.Length; i++)
                {
                    Lines[i] = Lines[i].Trim();
                    if (Lines[i].Length != 0 && !Lines[i].StartsWith(";", StringComparison.OrdinalIgnoreCase))
                    {
                        string[] Terms = Lines[i].Split(',');
                        for (int j = 0; j < Terms.Length; j++)
                        {
                            Terms[j] = Terms[j].Trim();
                        }
                        if (Terms.Length >= 2)
                        {
                            if (Length >= Controls.Length)
                            {
                                Array.Resize <Control>(ref Controls, Controls.Length << 1);
                            }
                            int j;
                            for (j = 0; j < Translations.CommandInfos.Length; j++)
                            {
                                if (string.Compare(Translations.CommandInfos[j].Name, Terms[0], StringComparison.OrdinalIgnoreCase) == 0)
                                {
                                    break;
                                }
                            }
                            if (j == Translations.CommandInfos.Length)
                            {
                                Controls[Length].Command       = Translations.Command.None;
                                Controls[Length].InheritedType = Translations.CommandType.Digital;
                                Controls[Length].Method        = ControlMethod.Invalid;
                                Controls[Length].Device        = -1;
                                Controls[Length].Component     = JoystickComponent.Invalid;
                                Controls[Length].Element       = -1;
                                Controls[Length].Direction     = 0;
                                Controls[Length].Modifier      = KeyboardModifier.None;
                                Controls[Length].Option        = 0;
                            }
                            else
                            {
                                Controls[Length].Command       = Translations.CommandInfos[j].Command;
                                Controls[Length].InheritedType = Translations.CommandInfos[j].Type;
                                string Method = Terms[1].ToLowerInvariant();
                                bool   Valid  = false;
                                if (Method == "keyboard" & Terms.Length >= 4)
                                {
                                    Key CurrentKey;
                                    // ReSharper disable once NotAccessedVariable
                                    int SDLTest;
                                    if (int.TryParse(Terms[2], out SDLTest))
                                    {
                                        //We've discovered a SDL keybinding is present, so reset the loading process with the default keyconfig & show an appropriate error message
                                        if (ControlsReset == false)
                                        {
                                            MessageBox.Show(Translations.GetInterfaceString("errors_controls_oldversion") + Environment.NewLine + Translations.GetInterfaceString("errors_controls_reset"), Application.ProductName,
                                                            MessageBoxButtons.OK, MessageBoxIcon.Hand);
                                        }
                                        var DefaultControls = OpenBveApi.Path.CombineFile(Program.FileSystem.GetDataFolder("Controls"), "Default keyboard assignment.controls");
                                        if (System.IO.File.Exists(DefaultControls))
                                        {
                                            if (ControlsReset == false)
                                            {
                                                LoadControls(DefaultControls, out CurrentControls);
                                                ControlsReset = true;
                                            }
                                            else
                                            {
                                                MessageBox.Show(Translations.GetInterfaceString("errors_warning") + Environment.NewLine + Translations.GetInterfaceString("errors_controls_default_oldversion"),
                                                                Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                                                Controls = new Control[0];
                                            }
                                        }
                                        else
                                        {
                                            MessageBox.Show(Translations.GetInterfaceString("errors_warning") + Environment.NewLine + Translations.GetInterfaceString("errors_controls_default_missing"),
                                                            Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Hand);
                                            Controls = new Control[0];
                                        }
                                        continue;
                                    }
                                    if (Enum.TryParse(Terms[2], true, out CurrentKey))
                                    {
                                        int Modifiers;
                                        if (int.TryParse(Terms[3], NumberStyles.Integer, Culture, out Modifiers))
                                        {
                                            Controls[Length].Method    = ControlMethod.Keyboard;
                                            Controls[Length].Device    = -1;
                                            Controls[Length].Component = JoystickComponent.Invalid;
                                            Controls[Length].Key       = CurrentKey;
                                            Controls[Length].Direction = 0;
                                            Controls[Length].Modifier  = (KeyboardModifier)Modifiers;
                                            int Option;
                                            if (Terms.Length >= 5 && int.TryParse(Terms[4], NumberStyles.Integer, Culture, out Option))
                                            {
                                                Controls[Length].Option = Option;
                                            }
                                            Valid = true;
                                        }
                                    }
                                }


                                else if (Method == "joystick" & Terms.Length >= 4)
                                {
                                    int Device;
                                    if (int.TryParse(Terms[2], NumberStyles.Integer, Culture, out Device))
                                    {
                                        string Component = Terms[3].ToLowerInvariant();
                                        if (Component == "axis" & Terms.Length >= 6)
                                        {
                                            int CurrentAxis;
                                            if (Int32.TryParse(Terms[4], out CurrentAxis))
                                            {
                                                int Direction;
                                                if (int.TryParse(Terms[5], NumberStyles.Integer, Culture, out Direction))
                                                {
                                                    Controls[Length].Method    = ControlMethod.Joystick;
                                                    Controls[Length].Device    = Device;
                                                    Controls[Length].Component = JoystickComponent.Axis;
                                                    Controls[Length].Element   = CurrentAxis;
                                                    Controls[Length].Direction = Direction;
                                                    Controls[Length].Modifier  = KeyboardModifier.None;
                                                    int Option;
                                                    if (Terms.Length >= 7 && int.TryParse(Terms[6], NumberStyles.Integer, Culture, out Option))
                                                    {
                                                        Controls[Length].Option = Option;
                                                    }
                                                    Valid = true;
                                                }
                                            }
                                        }
                                        else if (Component == "hat" & Terms.Length >= 6)
                                        {
                                            int CurrentHat;
                                            if (Int32.TryParse(Terms[4], out CurrentHat))
                                            {
                                                int HatDirection;
                                                if (Int32.TryParse(Terms[5], out HatDirection))
                                                {
                                                    Controls[Length].Method    = ControlMethod.Joystick;
                                                    Controls[Length].Device    = Device;
                                                    Controls[Length].Component = JoystickComponent.Hat;
                                                    Controls[Length].Element   = CurrentHat;
                                                    Controls[Length].Direction = HatDirection;
                                                    Controls[Length].Modifier  = KeyboardModifier.None;
                                                    int Option;
                                                    if (Terms.Length >= 7 && int.TryParse(Terms[6], NumberStyles.Integer, Culture, out Option))
                                                    {
                                                        Controls[Length].Option = Option;
                                                    }
                                                    Valid = true;
                                                }
                                            }
                                        }
                                        else if (Component == "button" & Terms.Length >= 5)
                                        {
                                            int CurrentButton;
                                            if (Int32.TryParse(Terms[4], out CurrentButton))
                                            {
                                                Controls[Length].Method    = ControlMethod.Joystick;
                                                Controls[Length].Device    = Device;
                                                Controls[Length].Component = JoystickComponent.Button;
                                                Controls[Length].Element   = CurrentButton;
                                                Controls[Length].Direction = 0;
                                                Controls[Length].Modifier  = KeyboardModifier.None;
                                                int Option;
                                                if (Terms.Length >= 6 && int.TryParse(Terms[5], NumberStyles.Integer, Culture, out Option))
                                                {
                                                    Controls[Length].Option = Option;
                                                }
                                                Valid = true;
                                            }
                                        }
                                    }
                                }
                                else if (Method == "raildriver" & Terms.Length >= 4)
                                {
                                    int Device;
                                    if (int.TryParse(Terms[2], NumberStyles.Integer, Culture, out Device))
                                    {
                                        string Component = Terms[3].ToLowerInvariant();
                                        if (Component == "axis" & Terms.Length >= 6)
                                        {
                                            int CurrentAxis;
                                            if (Int32.TryParse(Terms[4], out CurrentAxis))
                                            {
                                                int Direction;
                                                if (int.TryParse(Terms[5], NumberStyles.Integer, Culture, out Direction))
                                                {
                                                    Controls[Length].Method    = ControlMethod.RailDriver;
                                                    Controls[Length].Device    = Device;
                                                    Controls[Length].Component = JoystickComponent.Axis;
                                                    Controls[Length].Element   = CurrentAxis;
                                                    Controls[Length].Direction = Direction;
                                                    Controls[Length].Modifier  = KeyboardModifier.None;
                                                    int Option;
                                                    if (Terms.Length >= 7 && int.TryParse(Terms[6], NumberStyles.Integer, Culture, out Option))
                                                    {
                                                        Controls[Length].Option = Option;
                                                    }
                                                    Valid = true;
                                                }
                                            }
                                        }
                                        else if (Component == "button" & Terms.Length >= 5)
                                        {
                                            int CurrentButton;
                                            if (Int32.TryParse(Terms[4], out CurrentButton))
                                            {
                                                Controls[Length].Method    = ControlMethod.RailDriver;
                                                Controls[Length].Device    = Device;
                                                Controls[Length].Component = JoystickComponent.Button;
                                                Controls[Length].Element   = CurrentButton;
                                                Controls[Length].Direction = 0;
                                                Controls[Length].Modifier  = KeyboardModifier.None;
                                                int Option;
                                                if (Terms.Length >= 6 && int.TryParse(Terms[5], NumberStyles.Integer, Culture, out Option))
                                                {
                                                    Controls[Length].Option = Option;
                                                }
                                                Valid = true;
                                            }
                                        }
                                    }
                                }

                                if (!Valid)
                                {
                                    Controls[Length].Method    = ControlMethod.Invalid;
                                    Controls[Length].Device    = -1;
                                    Controls[Length].Component = JoystickComponent.Invalid;
                                    Controls[Length].Element   = -1;
                                    Controls[Length].Direction = 0;
                                    Controls[Length].Modifier  = KeyboardModifier.None;
                                    Controls[Length].Option    = 0;
                                }
                            }
                            Length++;
                        }
                    }
                }
            }
            Array.Resize <Control>(ref Controls, Length);
        }
示例#30
0
            /// <summary>Updates the physics and controls for this train</summary>
            /// <param name="TimeElapsed">The time elapsed</param>
            private void UpdatePhysicsAndControls(double TimeElapsed)
            {
                if (TimeElapsed == 0.0 || TimeElapsed > 1000)
                {
                    //HACK: The physics engine really does not like update times above 1000ms
                    //This works around a bug experienced when jumping to a station on a steep hill
                    //causing exessive acceleration
                    return;
                }
                // move cars
                for (int i = 0; i < Cars.Length; i++)
                {
                    Cars[i].Move(Cars[i].CurrentSpeed * TimeElapsed);
                    if (State == TrainState.Disposed)
                    {
                        return;
                    }
                }
                // update station and doors
                UpdateStation(TimeElapsed);
                UpdateDoors(TimeElapsed);
                // delayed handles
                if (Plugin == null)
                {
                    Handles.Power.Safety          = Handles.Power.Driver;
                    Handles.Brake.Safety          = Handles.Brake.Driver;
                    Handles.EmergencyBrake.Safety = Handles.EmergencyBrake.Driver;
                }
                Handles.Power.Update();
                Handles.Brake.Update();
                Handles.Brake.Update();
                Handles.EmergencyBrake.Update();
                Handles.HoldBrake.Actual = Handles.HoldBrake.Driver;
                // update speeds
                UpdateSpeeds(TimeElapsed);
                // Update Run and Motor sounds
                for (int i = 0; i < Cars.Length; i++)
                {
                    Cars[i].UpdateRunSounds(TimeElapsed);
                    Cars[i].UpdateMotorSounds(TimeElapsed);
                }

                // safety system
                if (!Game.MinimalisticSimulation | !IsPlayerTrain)
                {
                    UpdateSafetySystem();
                }
                {
                    // breaker sound
                    bool breaker;
                    if (Cars[DriverCar].CarBrake is AutomaticAirBrake)
                    {
                        breaker = Handles.Reverser.Actual != 0 & Handles.Power.Safety >= 1 & Handles.Brake.Safety == (int)AirBrakeHandleState.Release & !Handles.EmergencyBrake.Safety & !Handles.HoldBrake.Actual;
                    }
                    else
                    {
                        breaker = Handles.Reverser.Actual != 0 & Handles.Power.Safety >= 1 & Handles.Brake.Safety == 0 & !Handles.EmergencyBrake.Safety & !Handles.HoldBrake.Actual;
                    }
                    Cars[DriverCar].Breaker.Update(breaker);
                }
                // passengers
                Passengers.Update(Specs.CurrentAverageAcceleration, TimeElapsed);
                // signals
                if (CurrentSectionLimit == 0.0)
                {
                    if (Handles.EmergencyBrake.Driver & CurrentSpeed > -0.03 & CurrentSpeed < 0.03)
                    {
                        CurrentSectionLimit = 6.94444444444444;
                        if (IsPlayerTrain)
                        {
                            string s = Translations.GetInterfaceString("message_signal_proceed");
                            double a = (3.6 * CurrentSectionLimit) * Interface.CurrentOptions.SpeedConversionFactor;
                            s = s.Replace("[speed]", a.ToString("0", CultureInfo.InvariantCulture));
                            s = s.Replace("[unit]", Game.UnitOfSpeed);
                            MessageManager.AddMessage(s, MessageDependency.None, GameMode.Normal, MessageColor.Red, Program.CurrentRoute.SecondsSinceMidnight + 5.0, null);
                        }
                    }
                }
                // infrequent updates
                InternalTimerTimeElapsed += TimeElapsed;
                if (InternalTimerTimeElapsed > 10.0)
                {
                    InternalTimerTimeElapsed -= 10.0;
                    Synchronize();
                }
            }