private void Defaults()
 {
     Name         = "";
     Type         = MissionType.Normal;
     Enhancement  = MissionEnhancement.Standard;
     Levels       = new List <string>();
     SecretLevels = new List <MissionSecretLevel>();
     HOGName      = null;
     BriefingName = null;
     EndingName   = null;
     Metadata     = new MissionMetadata();
     Other        = new InsertionOrderedDictionary <string, string>();
 }
        /// <summary>
        /// Loads a mission file from a stream.
        /// </summary>
        /// <param name="stream">The stream to load from.</param>
        public void Read(Stream stream)
        {
            Defaults();
            using (StreamReader reader = new StreamReader(stream, Encoding.Default))
            {
                char[] separators = new char[] { '=' };
                string line;
                while ((line = reader.ReadLine()) != null)
                {
                    if (line.Contains("="))
                    {
                        string[] tokens = line.Split(separators, 2, StringSplitOptions.None);
                        string   key = tokens[0].Trim(), value = tokens[1].TrimStart();
                        int      num;

                        switch (key)
                        {
                        case "name":
                            Name = value; Enhancement = MissionEnhancement.Standard; break;

                        case "xname":
                            Name = value; Enhancement = MissionEnhancement.HAM; break;

                        case "zname":
                            Name = value; Enhancement = MissionEnhancement.VHAM; break;

                        case "d2x-name":
                            Name = value; Enhancement = MissionEnhancement.XL; break;

                        case "type":
                            Type = value == "anarchy" ? MissionType.Anarchy : MissionType.Normal; break;

                        case "hog":
                            HOGName = value; break;

                        case "briefing":
                            BriefingName = value; break;

                        case "ending":
                            EndingName = value; break;

                        case "num_levels":
                            if (Int32.TryParse(value, out num))
                            {
                                for (int i = 0; i < num; ++i)
                                {
                                    Levels.Add(reader.ReadLine());
                                }
                            }
                            break;

                        case "num_secrets":
                            if (Int32.TryParse(value, out num))
                            {
                                for (int i = 0; i < num; ++i)
                                {
                                    MissionSecretLevel sl = ParseSecretLevel(reader.ReadLine());
                                    if (sl == null)
                                    {
                                        break;
                                    }
                                    SecretLevels.Add(sl);
                                }
                            }
                            break;

                        case "editor":
                            Metadata.Editor = value; break;

                        case "build_time":
                            Metadata.BuildTime = value; break;

                        case "date":
                            Metadata.Date = value; break;

                        case "revision":
                            Metadata.Revision = value; break;

                        case "author":
                            Metadata.Author = value; break;

                        case "email":
                            Metadata.Email = value; break;

                        case "web_site":
                            Metadata.Website = value; break;

                        case "custom_textures":
                            Metadata.CustomTextures = MissionMetadata.IsYes(value);
                            break;

                        case "custom_robots":
                            Metadata.CustomRobots = MissionMetadata.IsYes(value);
                            break;

                        case "custom_music":
                            Metadata.CustomMusic = MissionMetadata.IsYes(value);
                            break;

                        case "normal":
                            if (!Metadata.GameModes.HasValue)
                            {
                                Metadata.GameModes = MissionGameMode.None;
                            }
                            if (MissionMetadata.IsYes(value))
                            {
                                Metadata.GameModes |= MissionGameMode.Singleplayer;
                            }
                            break;

                        case "anarchy":
                            if (!Metadata.GameModes.HasValue)
                            {
                                Metadata.GameModes = MissionGameMode.None;
                            }
                            if (MissionMetadata.IsYes(value))
                            {
                                Metadata.GameModes |= MissionGameMode.Anarchy;
                            }
                            break;

                        case "robo_anarchy":
                            if (!Metadata.GameModes.HasValue)
                            {
                                Metadata.GameModes = MissionGameMode.None;
                            }
                            if (MissionMetadata.IsYes(value))
                            {
                                Metadata.GameModes |= MissionGameMode.RoboAnarchy;
                            }
                            break;

                        case "coop":
                            if (!Metadata.GameModes.HasValue)
                            {
                                Metadata.GameModes = MissionGameMode.None;
                            }
                            if (MissionMetadata.IsYes(value))
                            {
                                Metadata.GameModes |= MissionGameMode.Cooperative;
                            }
                            break;

                        case "capture_flag":
                            if (!Metadata.GameModes.HasValue)
                            {
                                Metadata.GameModes = MissionGameMode.None;
                            }
                            if (MissionMetadata.IsYes(value))
                            {
                                Metadata.GameModes |= MissionGameMode.CaptureTheFlag;
                            }
                            break;

                        case "hoard":
                            if (!Metadata.GameModes.HasValue)
                            {
                                Metadata.GameModes = MissionGameMode.None;
                            }
                            if (MissionMetadata.IsYes(value))
                            {
                                Metadata.GameModes |= MissionGameMode.Hoard;
                            }
                            break;

                        case "multi_author":
                            Metadata.MultiAuthor = MissionMetadata.IsYes(value);
                            break;

                        case "want_feedback":
                            Metadata.WantFeedback = MissionMetadata.IsYes(value);
                            break;

                        case "!ham":
                            RebirthHAMFile = value;
                            break;

                        default:
                            Other[key] = value; break;
                        }
                    }
                    else if (line.StartsWith(";"))
                    {
                        if (Metadata.Comment == null)
                        {
                            Metadata.Comment = "";
                        }
                        Metadata.Comment += line.Substring(1) + Environment.NewLine;
                    }
                }
            }
        }