public static Car Load(string path, bool suppressFolderCheck) { DocumentParser file = new DocumentParser(path); Car car = new Car { Name = file.ReadLine() }; if (!suppressFolderCheck) { if (string.Compare(Path.GetFileName(path).ToUpper(), car.Name) != 0) { Logger.LogToFile(Logger.LogLevel.Error, "Not a valid Carmageddon car .txt file, expected {0} but found {1}", Path.GetFileName(path).ToUpper(), car.Name); return(null); } } if (file.ReadLine() != "START OF DRIVABLE STUFF") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "START OF DRIVABLE STUFF"); return(null); } car.DriversHeadOffset = file.ReadVector3(); car.DriversHeadTurnAngles = file.ReadVector2(); car.MirrorCamera = file.ReadVector4(); car.PratcamBorders = file.ReadStrings(); if (file.ReadLine() != "END OF DRIVABLE STUFF") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "END OF DRIVABLE STUFF"); return(null); } car.EngineNoises = file.ReadInts(); car.Stealworthy = file.ReadLine().ToLower() == "stealworthy"; car.ImpactTop = ImpactSpec.Load("top", file); car.ImpactBottom = ImpactSpec.Load("bottom", file); car.ImpactLeft = ImpactSpec.Load("left", file); car.ImpactRight = ImpactSpec.Load("right", file); car.ImpactFront = ImpactSpec.Load("front", file); car.ImpactBack = ImpactSpec.Load("rear", file); car.GridImages = file.ReadStrings(); int pixCount = file.ReadInt(); for (int i = 0; i < pixCount; i++) { car.PixelmapsLoMem.Add(file.ReadLine()); } pixCount = file.ReadInt(); for (int i = 0; i < pixCount; i++) { car.PixelmapsLoRes.Add(file.ReadLine()); } pixCount = file.ReadInt(); for (int i = 0; i < pixCount; i++) { car.PixelmapsHiRes.Add(file.ReadLine()); } int shadeCount = file.ReadInt(); for (int j = 0; j < shadeCount; j++) { car.ShadeTables.Add(file.ReadLine()); } int matCount = file.ReadInt(); for (int i = 0; i < matCount; i++) { car.MaterialsLoMem.Add(file.ReadLine()); } matCount = file.ReadInt(); for (int i = 0; i < matCount; i++) { car.MaterialsLoRes.Add(file.ReadLine()); } matCount = file.ReadInt(); for (int i = 0; i < matCount; i++) { car.MaterialsHiRes.Add(file.ReadLine()); } int modelCount = file.ReadInt(); for (int j = 0; j < modelCount; j++) { car.Models.Add(file.ReadLine()); } int actorCount = file.ReadInt(); for (int j = 0; j < actorCount; j++) { string[] s = file.ReadStrings(); car.ActorLODs.Add(s[0].ToInt()); car.Actors.Add(s[1]); } car.ReflectiveScreenMaterial = file.ReadLine(); int steerableWheelsCount = file.ReadInt(); for (int j = 0; j < steerableWheelsCount; j++) { car.SteerableWheels.Add(file.ReadInt()); } car.LeftFrontSuspension = file.ReadInts(); car.RightFrontSuspension = file.ReadInts(); car.LeftRearSuspension = file.ReadInts(); car.RightRearSuspension = file.ReadInts(); car.DrivenWheels = file.ReadInts(); car.NonDrivenWheels = file.ReadInts(); car.DrivenWheelDiameter = file.ReadSingle(); car.NonDrivenWheelDiameter = file.ReadSingle(); if (file.ReadLine() != "START OF FUNK") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "START OF FUNK"); return(null); } while (file.PeekLine() != "END OF FUNK") { car.Funks.Add(Funk.Load(file)); if (file.PeekLine() == "NEXT FUNK") { file.ReadLine(); } } file.ReadLine(); if (file.ReadLine() != "START OF GROOVE") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "START OF GROOVE"); return(null); } while (file.PeekLine() != "END OF GROOVE") { car.Grooves.Add(Groove.Load(file)); if (file.PeekLine() == "NEXT GROOVE") { file.ReadLine(); } } file.ReadLine(); for (int i = 0; i < car.Actors.Count; i++) { car.Crushes.Add(Crush.Load(file)); } car.MechanicsVersion = file.ReadLine().Replace("START OF MECHANICS STUFF version ", "", StringComparison.InvariantCultureIgnoreCase).ToInt(); car.LRWheelPos = file.ReadVector3(); car.RRWheelPos = file.ReadVector3(); car.LFWheelPos = file.ReadVector3(); car.RFWheelPos = file.ReadVector3(); car.CentreOfMass = file.ReadVector3(); switch (car.MechanicsVersion) { case 2: int boundingBoxCount = file.ReadInt(); for (int i = 0; i < boundingBoxCount; i++) { car.BoundingBoxes.Add(new BoundingBox { Min = file.ReadVector3(), Max = file.ReadVector3() }); } break; case 3: case 4: car.BoundingBoxes.Add(new BoundingBox { Min = file.ReadVector3(), Max = file.ReadVector3() }); int additionalPointsCount = file.ReadInt(); for (int i = 0; i < additionalPointsCount; i++) { car.AdditionalPoints.Add(file.ReadVector3()); } break; } car.MinimumTurningCircle = file.ReadSingle(); car.SuspensionGive = file.ReadVector2(); car.RideHeight = file.ReadSingle(); car.DampingFactor = file.ReadSingle(); car.Mass = file.ReadSingle(); car.SlipFrictionReductionFraction = file.ReadSingle(); if (car.MechanicsVersion == 4) { car.FrictionAngle = file.ReadVector3(); } else { car.FrictionAngle = (Vector3)file.ReadVector2(); } car.AngularMomentumProportions = file.ReadVector3(); car.TractionFractionalMultiplier = file.ReadSingle(); car.DownforceToWeightBalanceSpeed = file.ReadSingle(); car.BrakeMultiplier = file.ReadSingle(); car.BrakingStrengthMultiplier = file.ReadSingle(); car.RollingResistance = file.ReadVector2(); car.NumberOfGears = file.ReadInt(); car.TopGearRedlineSpeed = file.ReadInt(); car.TopGearAcceleration = file.ReadSingle(); if (file.ReadLine() != "END OF MECHANICS STUFF") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "END OF MECHANICS STUFF"); return(null); } int shrapnelCount = file.ReadInt(); for (int i = 0; i < shrapnelCount; i++) { car.Shrapnel.Add(file.ReadLine()); } if (!file.EOF) { for (int i = 0; i < 12; i++) { car.FirePoints.Add(file.ReadInt()); } } if (!file.EOF) { Console.WriteLine("Still data to parse in {0}", path); } return(car); }
public static Car Load(string path) { DocumentParser file = new DocumentParser(path); Car car = new Car(); string version = file.ReadLine(); if (!version.StartsWith("VERSION")) { Logger.LogToFile(Logger.LogLevel.Error, "Not a valid Carmageddon 2 car .txt file"); return(null); } car.Version = version.Replace("VERSION ", "").ToInt(); if (file.PeekLine() == "GIRL") { car.FemaleDriver = true; file.ReadLine(); } car.Name = file.ReadLine(); car.SoftnessFactor = file.ReadSingle(); if (file.ReadLine() != "START OF DRIVABLE STUFF") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "START OF DRIVABLE STUFF"); return(null); } car.DriversHeadOffset = file.ReadVector3(); car.DriversHeadTurnAngles = file.ReadVector2(); car.MirrorCamera = file.ReadVector4(); car.PratcamBorders = file.ReadStrings(); if (file.ReadLine() != "END OF DRIVABLE STUFF") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "END OF DRIVABLE STUFF"); return(null); } car.EngineNoises = file.ReadInts(); car.Stealworthy = file.ReadLine().ToLower() == "stealworthy"; car.ImpactTop = ImpactSpec.Load("top", file); car.ImpactBottom = ImpactSpec.Load("bottom", file); car.ImpactLeft = ImpactSpec.Load("left", file); car.ImpactRight = ImpactSpec.Load("right", file); car.ImpactFront = ImpactSpec.Load("front", file); car.ImpactBack = ImpactSpec.Load("rear", file); car.GridImages = file.ReadStrings(); int extraLevelsOfDetail = file.ReadInt(); for (int j = 0; j < extraLevelsOfDetail; j++) { car.ExtraLevelsOfDetail.Add(file.ReadInt()); } car.WAM = file.ReadLine(); car.ReflectiveScreenMaterial = file.ReadLine(); car.TransparencyOfWindscreen = file.ReadSingle(); int steerableWheelsCount = file.ReadInt(); for (int j = 0; j < steerableWheelsCount; j++) { car.SteerableWheels.Add(file.ReadInt()); } car.LeftFrontSuspension = file.ReadInts(); car.RightFrontSuspension = file.ReadInts(); car.LeftRearSuspension = file.ReadInts(); car.RightRearSuspension = file.ReadInts(); car.DrivenWheels = file.ReadInts(); car.NonDrivenWheels = file.ReadInts(); car.DrivenWheelDiameter = file.ReadSingle(); car.NonDrivenWheelDiameter = file.ReadSingle(); if (file.ReadLine() != "START OF FUNK") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "START OF FUNK"); return(null); } while (file.PeekLine() != "END OF FUNK") { car.Funks.Add(Funk.Load(file)); if (file.PeekLine() == "NEXT FUNK") { file.ReadLine(); } } file.ReadLine(); if (file.ReadLine() != "START OF GROOVE") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "START OF GROOVE"); return(null); } while (file.PeekLine() != "END OF GROOVE") { car.Grooves.Add(Groove.Load(file)); if (file.PeekLine() == "NEXT GROOVE") { file.ReadLine(); } } file.ReadLine(); int _ = file.ReadLine().Replace("START OF MECHANICS STUFF version ", "", StringComparison.InvariantCultureIgnoreCase).ToInt(); car.MinimumTurningCircle = file.ReadSingle(); car.BrakeMultiplier = file.ReadSingle(); car.BrakingStrengthMultiplier = file.ReadSingle(); car.NumberOfGears = file.ReadSingle(); car.TopGearRedlineSpeed = file.ReadSingle(); car.TopGearAcceleration = file.ReadSingle(); car.RootPartType = file.ReadEnum <PartType>(); car.RootPartIdentifier = file.ReadLine(); car.RootPartActor = file.ReadLine(); car.SubPartType = file.ReadEnum <PartType>(); car.CentreOfMass = file.ReadVector3(); car.Mass = file.ReadSingle(); car.AngularMomentumProportions = file.ReadVector3(); car.DownforceToWeightBalanceSpeed = file.ReadSingle(); int numberOfWheels = file.ReadInt(); for (int j = 0; j < numberOfWheels; j++) { Wheel wheel = new Wheel { Type = file.ReadEnum <Wheel.WheelType>(), Identifier = file.ReadLine(), Actor = file.ReadLine(), Position = file.ReadVector3(), SteerableFlags = file.ReadInt(), DrivenFlags = file.ReadInt(), SuspensionGive = file.ReadSingle(), DampingFactor = file.ReadSingle(), SlipFrictionReductionFraction = file.ReadSingle(), FrictionAngles = file.ReadVector2(), TractionFractionalMultiplier = file.ReadSingle(), RollingResistance = file.ReadSingle() }; car.Wheels.Add(wheel); } int boundingShapes = file.ReadInt(); for (int j = 0; j < boundingShapes; j++) { BoundingShape shape = new BoundingShape { Type = file.ReadEnum <BoundingShape.BoundingShapeType>() }; int shapePoints = file.ReadInt(); for (int k = 0; k < shapePoints; k++) { shape.Points.Add(file.ReadVector3()); } car.BoundingShapes.Add(shape); } int subParts = file.ReadInt(); for (int j = 0; j < subParts; j++) { throw new NotImplementedException("subparts?!"); } if (file.ReadLine() != "END OF MECHANICS STUFF") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Car.TXT file?", "END OF MECHANICS STUFF"); return(null); } int shrapnelCount = file.ReadInt(); for (int i = 0; i < shrapnelCount; i++) { car.Shrapnel.Add(file.ReadLine()); } for (int i = 0; i < 12; i++) { car.FirePoints.Add(file.ReadInt()); } while (file.PeekLine() != "END") { string keyWord = file.ReadLine(); switch (keyWord) { case "CAMERA_POSITIONS": car.Keywords.Add(new CameraPosition { BumperPosition = file.ReadVector3(), CockpitPosition = file.ReadVector3() }); break; case "CAMERA_TURN_OFF_MATERIALS": { CameraTurnOffMaterials ctom = new CameraTurnOffMaterials(); int materialCount = file.ReadInt(); for (int i = 0; i < materialCount; i++) { CameraTurnOffMaterialEntry ctomEntry = new CameraTurnOffMaterialEntry { MaterialName = file.ReadLine() }; int entryCount = file.ReadInt(); for (int j = 0; j < entryCount; j++) { ctomEntry.Materials.Add(file.ReadLine()); } ctom.Entries.Add(ctomEntry); } car.Keywords.Add(ctom); } break; default: throw new NotImplementedException($"{keyWord} not supported!"); } } return(car); }
public static Map Load(string path) { DocumentParser file = new DocumentParser(path); Map map = new Map(); string version = file.ReadLine(); if (!version.StartsWith("VERSION")) { Logger.LogToFile(Logger.LogLevel.Error, "Not a valid Carmageddon 2 race .txt file"); return(null); } map.Version = version.Replace("VERSION ", "").ToInt(); if (map.Version == 1) { // V1 has global lighting data map.LightColour = file.ReadVector3(); // RGB for main directional light-source map.DiffuseLight0 = file.ReadVector2(); // Ambient/Diffuse light to be used when plaything ambient says 0 map.DiffuseLight1 = file.ReadVector2(); // Ambient/Diffuse light to be used when plaything ambient says 1 map.DiffuseLightOther = file.ReadVector2(); // Ambient/Diffuse light to be used when plaything ambient says anything else } map.GridPosition = file.ReadVector3(); // Position of centre of start of grid map.GridRotation = file.ReadInt(); // Direction that grid faces in //string t = getNextLine(sr); //if (version == 8) //{ // // alpha and demo v8 files had an extra block here, we'll test if it // if (t.Contains(",")) // { // getNextLine(sr); // # laps // getNextLine(sr); // Race completed bonus (all laps raced) for each skill level // getNextLine(sr); // Race completed bonus (all peds killed) for each skill level // getNextLine(sr); // Race completed bonus (all oppos wasted) for each skill level // t = getNextLine(sr); // } //} int checkpointCount = file.ReadInt(); for (int i = 0; i < checkpointCount; i++) { Checkpoint cp = new Checkpoint() { TimerIncrements = file.ReadVector3() }; int quadCount = file.ReadInt(); for (int j = 0; j < quadCount; j++) { cp.Points.Add(file.ReadVector3()); cp.Points.Add(file.ReadVector3()); cp.Points.Add(file.ReadVector3()); cp.Points.Add(file.ReadVector3()); } map.Checkpoints.Add(cp); } int smashSpecs = file.ReadInt(); for (int i = 0; i < smashSpecs; i++) { SmashData smashable = new SmashData { Flags = file.ReadInt(), Trigger = file.ReadLine() }; if (smashable.Trigger.Length == 3 && smashable.Trigger.StartsWith("&")) { smashable.TriggerFlags = file.ReadInt(); } smashable.TriggerMode = file.ReadEnum <SmashData.SmashTriggerMode>(); switch (smashable.TriggerMode) { case SmashData.SmashTriggerMode.nochange: case SmashData.SmashTriggerMode.remove: smashable.RemovalThreshold = file.ReadSingle(); smashable.Connotations.Load(file); break; case SmashData.SmashTriggerMode.replacemodel: smashable.RemovalThreshold = file.ReadSingle(); smashable.Connotations.Load(file); smashable.NewModel = file.ReadLine(); smashable.ChanceOfFire = file.ReadInt(); if (smashable.ChanceOfFire > 0) { smashable.NumFires = file.ReadInt(); smashable.SmokeLevel = file.ReadInts(); } break; case SmashData.SmashTriggerMode.texturechange: smashable.IntactMaterial = file.ReadLine(); int textureLevels = file.ReadInt(); for (int j = 0; j < textureLevels; j++) { SmashDataTextureLevel textureLevel = new SmashDataTextureLevel() { TriggerThreshold = file.ReadSingle(), Flags = file.ReadInt(), CollisionType = file.ReadEnum <SmashDataTextureLevel.TextureLevelCollisionType>() }; textureLevel.Connotations.Load(file); int pixelmaps = file.ReadInt(); for (int k = 0; k < pixelmaps; k++) { textureLevel.Pixelmaps.Add(file.ReadLine()); } smashable.Levels.Add(textureLevel); } break; default: throw new NotImplementedException($"Unknown TriggerMode '{smashable.TriggerMode}'"); } smashable.Reserved1 = file.ReadInt(); smashable.Reserved2 = file.ReadInt(); smashable.Reserved3 = file.ReadInt(); smashable.Reserved4 = file.ReadInt(); map.Smashables.Add(smashable); } int pedSpecs = file.ReadInt(); for (int i = 0; i < pedSpecs; i++) { PedSpec ps = new PedSpec() { MaterialName = file.ReadLine(), MovementIndex = file.ReadInt(), GroupIndex = file.ReadInt(), PedsPer100SquareMetres = file.ReadSingle() }; int exclusionCount = file.ReadInt(); for (int j = 0; j < exclusionCount; j++) { ps.ExclusionMaterials.Add(new PedExclusionMaterial { Flags = file.ReadInt(), Name = file.ReadLine() }); } int exceptionCount = file.ReadInt(); for (int j = 0; j < exceptionCount; j++) { ps.ExceptionMaterials.Add(file.ReadLine()); } map.PedSpecs.Add(ps); } map.AdditionalActor = file.ReadLine(); map.SkyPixelmap = file.ReadLine(); map.HorizontalRepetitions = file.ReadInt(); map.VerticalSize = file.ReadInt(); map.PositionOfHorizon = file.ReadInt(); map.DepthCueMode = file.ReadLine(); map.FogDarkness = file.ReadVector2(); map.DepthCueColour = file.ReadVector3(); map.DefaultEngineNoise = file.ReadInt(); int specialEffectVolumeCount = file.ReadInt(); for (int i = 0; i < specialEffectVolumeCount; i++) { SpecialEffectVolume sev = new SpecialEffectVolume { Type = file.ReadLine() }; if (sev.Type.ToUpper() == "BOX") { sev.Corners.Add(file.ReadVector3()); sev.Corners.Add(file.ReadVector3()); sev.Corners.Add(file.ReadVector3()); sev.Corners.Add(file.ReadVector3()); } sev.GravityMultiplier = file.ReadSingle(); sev.ViscosityMultiplier = file.ReadSingle(); sev.CarDamagePerMillisecond = file.ReadSingle(); sev.PedDamagePerMillisecond = file.ReadSingle(); sev.CameraEffectIndex = file.ReadInt(); if (file.PeekLine().Contains(",")) { sev.SkyColourRGB = file.ReadVector3(); } else { sev.SkyColour = file.ReadInt(); } sev.WindscreenMaterial = file.ReadLine(); sev.EntrySoundID = file.ReadInt(); sev.ExitSoundID = file.ReadInt(); sev.EngineNoiseIndex = file.ReadInt(); sev.MaterialIndex = file.ReadInt(); if (sev.Type.ToUpper() == "BOX") { sev.SoundType = file.ReadEnum <SpecialEffectVolume.SpecVolSoundType>(); if (sev.SoundType != SpecialEffectVolume.SpecVolSoundType.NONE) { sev.SoundSpec = SoundSpec.Load(file); } } map.SpecialVolumes.Add(sev); } int soundGeneratorCount = file.ReadInt(); if (soundGeneratorCount > 0) { throw new NotImplementedException("Can't handle sound generators yet!"); } map.MaterialDefault = file.ReadLine(); map.MaterialDarkness = file.ReadLine(); map.MaterialFog = file.ReadLine(); file.ReadLine(); // (ignore) # areas with different screens map.MapPixelmap = file.ReadLine(); map.WorldMapTransform = new Matrix3D( file.ReadVector3(), file.ReadVector3(), file.ReadVector3(), file.ReadVector3() ); if (file.ReadLine() != "START OF FUNK") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Map.TXT file?", "START OF FUNK"); return(null); } while (file.PeekLine() != "END OF FUNK") { map.Funks.Add(Funk.Load(file)); if (file.PeekLine() == "NEXT FUNK") { file.ReadLine(); } } file.ReadLine(); if (file.ReadLine() != "START OF GROOVE") { Logger.LogToFile(Logger.LogLevel.Error, "Expected \"{0}\", didn't get it. Are you sure this is a Map.TXT file?", "START OF GROOVE"); return(null); } while (file.PeekLine() != "END OF GROOVE") { map.Grooves.Add(Groove.Load(file)); if (file.PeekLine() == "NEXT GROOVE") { file.ReadLine(); } } file.ReadLine(); if (file.ReadLine() != "START OF OPPONENT PATHS") { Logger.LogToFile(Logger.LogLevel.Error, "Not a valid Carmageddon 2 race .txt file"); return(null); } int nodeCount = file.ReadInt(); for (int i = 0; i < nodeCount; i++) { map.Nodes.Add(file.ReadVector3()); } int pathCount = file.ReadInt(); for (int i = 0; i < pathCount; i++) { string[] parts = file.ReadLine().Split(','); map.Paths.Add(new OpponentPathSection { StartNode = parts[0].ToInt(), EndNode = parts[1].ToInt(), Unknown1 = parts[2].ToInt(), Unknown2 = parts[3].ToInt(), Unknown3 = parts[4].ToInt(), Unknown4 = parts[5].ToInt(), Width = parts[6].ToSingle(), SectionType = parts[7].ToInt() }); } int copStartPoints = file.ReadInt(); if (copStartPoints > 0) { throw new NotImplementedException("Cop start points? Really?"); } if (file.ReadLine() != "END OF OPPONENT PATHS") { Logger.LogToFile(Logger.LogLevel.Error, "Not a valid Carmageddon 2 race .txt file"); return(null); } if (file.ReadLine() != "START OF DRONE PATHS") { Logger.LogToFile(Logger.LogLevel.Error, "Not a valid Carmageddon 2 race .txt file"); return(null); } map.DronePathVersion = file.ReadInt(); int dronepathNodeCount = file.ReadInt(); for (int i = 0; i < dronepathNodeCount; i++) { DronePathNode node = new DronePathNode { Position = file.ReadVector3(), DroneName = file.ReadLine() }; if (map.DronePathVersion == 0) { node.UnknownVector = file.ReadVector3(); } else { node.UnknownInt = file.ReadInt(); } int nextNodeCount = file.ReadInt(); for (int j = 0; j < nextNodeCount; j++) { node.Destinations.Add(file.ReadLine()); } map.DronePaths.Add(node); } if (file.ReadLine() != "END OF DRONE PATHS") { Logger.LogToFile(Logger.LogLevel.Error, "Not a valid Carmageddon 2 race .txt file"); return(null); } int materialModifierCount = file.ReadInt(); for (int i = 0; i < materialModifierCount; i++) { map.MaterialModifiers.Add(new MaterialModifier { CarWallFriction = file.ReadSingle(), TyreRoadFriction = file.ReadSingle(), DownForce = file.ReadSingle(), Bumpiness = file.ReadSingle(), TyreSoundIndex = file.ReadInt(), CrashSoundIndex = file.ReadInt(), ScrapeNoiseIndex = file.ReadInt(), Sparkiness = file.ReadSingle(), RoomForExpansion = file.ReadInt(), SkidmarkMaterial = file.ReadLine() }); } int noncarCount = file.ReadInt(); for (int i = 0; i < noncarCount; i++) { map.Noncars.Add(file.ReadLine()); } int shadetableCount = file.ReadInt(); for (int i = 0; i < shadetableCount; i++) { map.ShadeTables.Add(new ShadeTable { RGB = file.ReadVector3(), Strengths = file.ReadVector3() }); } int networkStartCount = file.ReadInt(); for (int i = 0; i < networkStartCount; i++) { map.NetworkStarts.Add(new NetworkStart { Position = file.ReadVector3(), Rotation = file.ReadInt() }); } int splashfileCount = file.ReadInt(); for (int i = 0; i < splashfileCount; i++) { map.SplashFiles.Add(file.ReadLine()); } int txtfileCount = file.ReadInt(); for (int i = 0; i < txtfileCount; i++) { map.TxtFiles.Add(file.ReadLine()); } return(map); }