public Floor Get(ulong id, bool ts1) { if (ById.ContainsKey((ushort)id)) { return(ById[(ushort)id]); } else { //get from iff if (!Entries.ContainsKey((ushort)id)) { return(null); } Files.Formats.IFF.IffFile iff = this.Floors.Get(Entries[(ushort)id].FileName); if (iff == null) { return(null); } var far = iff.Get <SPR2>(1); var medium = iff.Get <SPR2>(257); var near = iff.Get <SPR2>(513); ById[(ushort)id] = new Floor { ID = (ushort)id, Near = near, Medium = medium, Far = far }; return(ById[(ushort)id]); } }
public Wall Get(ulong id) { if (ById.ContainsKey((ushort)id)) { return(ById[(ushort)id]); } else { //get from iff Files.Formats.IFF.IffFile iff = this.Walls.Get(Entries[(ushort)id].FileName); if (iff == null) { return(null); } var far = iff.Get <SPR>(1); var medium = iff.Get <SPR>(1793); var near = iff.Get <SPR>(2049); ById[(ushort)id] = new Wall { ID = (ushort)id, Near = near, Medium = medium, Far = far }; return(ById[(ushort)id]); } }
public Texture2D GetFloorThumb(ushort id, GraphicsDevice device) { if (id < 256) { return(TextureUtils.Copy(device, ById[id].Near.Frames[0].GetTexture(device))); } else if (id == 65535) { return(TextureUtils.Copy(device, FloorGlobals.Get <SPR2>(0x420).Frames[0].GetTexture(device))); } else { return(this.Floors.ThrowawayGet(Entries[(ushort)id].FileName).Get <SPR2>(513).Frames[0].GetTexture(device)); } }
public Tuple <string, string> GetHouseNameDesc(int houseID) { STR res; if (houseID < 80) { res = NeighbourhoodDesc.Get <STR>((ushort)(houseID + 2000)); } else if (houseID < 90) { res = STDesc.Get <STR>((ushort)(houseID + 2000)); } else { res = MTDesc.Get <STR>((ushort)(houseID + 2000)); } if (res == null) { return(new Tuple <string, string>("", "")); } else { return(new Tuple <string, string>(res.GetString(0), res.GetString(1))); } }
public UIHeadlineRenderer(VMRuntimeHeadline headline) : base(headline) { if (Sprites == null) { Sprites = new Files.Formats.IFF.IffFile(Content.Content.Get().GetPath("objectdata/globals/sprites.iff")); WhitePx = TextureGenerator.GetPxWhite(GameFacade.GraphicsDevice); } if (Headline.Operand.Group != VMSetBalloonHeadlineOperandGroup.Algorithmic) { Sprite = Sprites.Get <SPR>((ushort)(GroupOffsets[(int)Headline.Operand.Group] + Headline.Index)); } if (Headline.Operand.Type != 255 && Headline.Operand.Type != 3) { BGSprite = Sprites.Get <SPR>((ushort)(GroupOffsets[(int)VMSetBalloonHeadlineOperandGroup.Balloon] + Headline.Operand.Type)); } LastZoom = WorldZoom.Near; RecalculateTarget(); }
/// <summary> /// Initiates loading of floors. /// </summary> public void Init() { this.Entries = new Dictionary <ushort, FloorReference>(); this.ById = new Dictionary <ushort, Floor>(); this.DynamicFloorFromID = new Dictionary <string, ushort>(); var floorGlobalsPath = ContentManager.GetPath("objectdata/globals/floors.iff"); var floorGlobals = new Files.Formats.IFF.IffFile(floorGlobalsPath); FloorGlobals = floorGlobals; var buildGlobalsPath = ContentManager.GetPath("objectdata/globals/build.iff"); var buildGlobals = new Files.Formats.IFF.IffFile(buildGlobalsPath); //todo: centralize? /** There is a small handful of floors in a global file for some reason **/ ushort floorID = 1; var floorStrs = buildGlobals.Get <STR>(0x83); for (ushort i = 1; i < (floorStrs.Length / 3); i++) { var far = floorGlobals.Get <SPR2>(i); var medium = floorGlobals.Get <SPR2>((ushort)(i + 256)); var near = floorGlobals.Get <SPR2>((ushort)(i + 512)); //2048 is water tile this.AddFloor(new Floor { ID = floorID, Far = far, Medium = medium, Near = near }); Entries.Add(floorID, new FloorReference(this) { ID = floorID, FileName = "global", Name = floorStrs.GetString((i - 1) * 3 + 1), Price = int.Parse(floorStrs.GetString((i - 1) * 3 + 0)), Description = floorStrs.GetString((i - 1) * 3 + 2) }); floorID++; } var waterStrs = buildGlobals.Get <STR>(0x85); //add pools for catalog logic Entries.Add(65535, new FloorReference(this) { ID = 65535, FileName = "global", Price = int.Parse(waterStrs.GetString(0)), Name = waterStrs.GetString(1), Description = waterStrs.GetString(2) }); floorID = 256; var archives = new string[] { "housedata/floors/floors.far", "housedata/floors2/floors2.far", "housedata/floors3/floors3.far", "housedata/floors4/floors4.far" }; for (var i = 0; i < archives.Length; i++) { var archivePath = ContentManager.GetPath(archives[i]); var archive = new FAR1Archive(archivePath, true); var entries = archive.GetAllEntries(); foreach (var entry in entries) { var iff = new Files.Formats.IFF.IffFile(); DynamicFloorFromID[new string(entry.Key.TakeWhile(x => x != '.').ToArray()).ToLowerInvariant()] = floorID; var bytes = archive.GetEntry(entry); using (var stream = new MemoryStream(bytes)) { iff.Read(stream); } var catStrings = iff.Get <STR>(0); Entries.Add(floorID, new FloorReference(this) { ID = floorID, FileName = entry.Key, Name = catStrings.GetString(0), Price = int.Parse(catStrings.GetString(1)), Description = catStrings.GetString(2) }); floorID++; } archive.Close(); } NumFloors = floorID; this.Floors = new FAR1Provider <Files.Formats.IFF.IffFile>(ContentManager, new IffCodec(), new Regex(".*/floors.*\\.far")); Floors.Init(); }
public Blueprint LoadFromIff(Files.Formats.IFF.IffFile iff) { var simi = iff.Get <SIMI>(1); var hous = iff.Get <HOUS>(0); short size = simi.GlobalData[23]; var type = simi.GlobalData[35]; //ts1 lots are 64x64... but we convert them into dynamic size. //if (VM.UseWorld) this.Blueprint = new Blueprint(size, size); //VM.Entities = new List<VMEntity>(); //VM.Context = new VMContext(VM.Context.World); //VM.Context.VM = VM; VM.Context.Blueprint = Blueprint; VM.Context.Architecture = new VMArchitecture(size, size, Blueprint, VM.Context); FlipRoad = (hous.CameraDir & 1) > 0; VM.GlobalState = simi.GlobalData; VM.GlobalState[20] = 255; //Game Edition. Basically, what "expansion packs" are running. Let's just say all of them. VM.GlobalState[25] = 4; //as seen in EA-Land edith's simulator globals, this needs to be set for people to do their idle interactions. VM.GlobalState[17] = 4; //Runtime Code Version, is this in EA-Land. VM.SetGlobalValue(10, 1); //set house number VM.SetGlobalValue(32, 0); //simless build mode VM.Context.Clock.Hours = VM.GlobalState[0]; VM.Context.Clock.DayOfMonth = VM.GlobalState[1]; VM.Context.Clock.Minutes = VM.GlobalState[5]; VM.Context.Clock.MinuteFractions = (VM.GlobalState[6] * VM.Context.Clock.TicksPerMinute); VM.Context.Clock.Month = VM.GlobalState[7]; VM.Context.Clock.Year = VM.GlobalState[8]; var floorM = iff.Get <FLRm>(1)?.Entries ?? iff.Get <FLRm>(0)?.Entries ?? new List <WALmEntry>(); var wallM = iff.Get <WALm>(1)?.Entries ?? iff.Get <WALm>(0)?.Entries ?? new List <WALmEntry>(); var floorDict = BuildFloorDict(floorM); var wallDict = BuildWallDict(wallM); var arch = VM.Context.Architecture; //altitude as 0 var advFloors = iff.Get <ARRY>(11); var flags = iff.Get <ARRY>(8).TransposeData; if (advFloors != null) { //advanced walls and floors from modern ts1. use 16 bit wall/floor data. arch.Floors[0] = RemapFloors(DecodeAdvFloors(advFloors.TransposeData), floorDict, flags); arch.Floors[1] = RemapFloors(DecodeAdvFloors(iff.Get <ARRY>(111).TransposeData), floorDict, flags); //objects as 3 arch.Walls[0] = RemapWalls(DecodeAdvWalls(iff.Get <ARRY>(12).TransposeData), wallDict, floorDict); arch.Walls[1] = RemapWalls(DecodeAdvWalls(iff.Get <ARRY>(112).TransposeData), wallDict, floorDict); } else { arch.Floors[0] = RemapFloors(DecodeFloors(iff.Get <ARRY>(1).TransposeData), floorDict, flags); arch.Floors[1] = RemapFloors(DecodeFloors(iff.Get <ARRY>(101).TransposeData), floorDict, flags); //objects as 3 arch.Walls[0] = RemapWalls(DecodeWalls(iff.Get <ARRY>(2).TransposeData), wallDict, floorDict); arch.Walls[1] = RemapWalls(DecodeWalls(iff.Get <ARRY>(102).TransposeData), wallDict, floorDict); } //objects as 103 //Blueprint.Terrain.GrassState = iff.Get<ARRY>(6).TransposeData.Select(x => (byte)(127 - x)).ToArray(); //Blueprint.Terrain.DarkType = Content.Model.TerrainType.SAND; //arch.Terrain.LightType = Content.Model.TerrainType.GRASS; arch.SignalRedraw(); //targetgrass is 7 //flags is 8/108 var pools = iff.Get <ARRY>(9).TransposeData; var water = iff.Get <ARRY>(10).TransposeData; for (int i = 0; i < pools.Length; i++) { //pools in freeso are slightly different if (pools[i] != 0xff && pools[i] != 0x0) { arch.Floors[0][i].Pattern = 65535; } if (water[i] != 0xff && water[i] != 0x0) { arch.Floors[0][i].Pattern = 65534; } } arch.Floors[0] = ResizeFloors(arch.Floors[0], size); arch.Floors[1] = ResizeFloors(arch.Floors[1], size); arch.Walls[0] = ResizeWalls(arch.Walls[0], size); arch.Walls[1] = ResizeWalls(arch.Walls[1], size); //arch.FineBuildableArea = ResizeFlags(flags, size); //arch.Terrain.GrassState = ResizeGrass(arch.Terrain.GrassState, size); //arch.Terrain.Heights = Array.ConvertAll(ResizeGrass(DecodeHeights(iff.Get<ARRY>(0).TransposeData), size), x => (short)(x * 10)); //arch.Terrain.RegenerateCenters(); arch.RoofStyle = (uint)Content.Content.Get().WorldRoofs.NameToID(hous.RoofName.ToLowerInvariant() + ".bmp"); if (VM.UseWorld) { World.State.WorldSize = size; Blueprint.Terrain = CreateTerrain(size); //Blueprint.Altitude = arch.Terrain.Heights; //Blueprint.FineArea = arch.FineBuildableArea; } arch.RegenWallsAt(); arch.RegenRoomMap(); VM.Context.RegeneratePortalInfo(); var objm = iff.Get <OBJM>(1); var objt = iff.Get <OBJT>(0); int j = 0; for (int i = 0; i < objm.IDToOBJT.Length; i += 2) { if (objm.IDToOBJT[i] == 0) { continue; } MappedObject target; if (!objm.ObjectData.TryGetValue(objm.IDToOBJT[i], out target)) { continue; } var entry = objt.Entries[objm.IDToOBJT[i + 1] - 1]; target.Name = entry.Name; target.GUID = entry.GUID; //Console.WriteLine((objm.IDToOBJT[i]) + ": " + objt.Entries[objm.IDToOBJT[i + 1] - 1].Name); } var objFlrs = new ushort[][] { DecodeObjID(iff.Get <ARRY>(3)?.TransposeData), DecodeObjID(iff.Get <ARRY>(103)?.TransposeData) }; for (int flr = 0; flr < 2; flr++) { var objs = objFlrs[flr]; if (objs == null) { continue; } for (int i = 0; i < objs.Length; i++) { var obj = objs[i]; if (obj != 0) { var x = i % 64; var y = i / 64; MappedObject targ; if (!objm.ObjectData.TryGetValue(obj, out targ)) { continue; } targ.ArryX = x; targ.ArryY = y; targ.ArryLevel = flr + 1; } } } var content = Content.Content.Get(); foreach (var controller in ControllerObjects) { VM.Context.CreateObjectInstance(controller, LotTilePos.OUT_OF_WORLD, Direction.NORTH, false); } var ents = new List <Tuple <VMEntity, OBJM.MappedObject> >(); foreach (var obj in objm.ObjectData.Values) { if (ControllerObjects.Contains(obj.GUID)) { continue; } var res = content.WorldObjects.Get(obj.GUID, false); if (res == null) { continue; //failed to load this object } var objd = res.OBJ; if (res.OBJ.MasterID != 0) { var allObjs = res.Resource.List <OBJD>().Where(x => x.MasterID == res.OBJ.MasterID); var hasLead = allObjs.Any(x => x.MyLeadObject != 0); if ((hasLead && res.OBJ.MyLeadObject != 0) || (!hasLead && res.OBJ.SubIndex == 0)) { //this is the object //look for its master //multitile object.. find master objd var master = allObjs.FirstOrDefault(x => x.SubIndex < 0); if (master == null) { continue; } objd = master; obj.GUID = master.GUID; } else { continue; } } //if (DeleteAvatars && objd.ObjectType == OBJDType.Person) continue; //objm parent positioning //objects without positions inherit position from the objects in their "parent id". MappedObject src = obj; while (src != null && src.ParentID != 0) { if (objm.ObjectData.TryGetValue(src.ParentID, out src)) { if (src.ParentID == 0) { obj.ArryX = src.ArryX; obj.ArryY = src.ArryY; obj.ArryLevel = src.ArryLevel; } } } LotTilePos pos = LotTilePos.OUT_OF_WORLD; var dir = (Direction)(1 << obj.Direction); var nobj = VM.Context.CreateObjectInstance(obj.GUID, pos, dir, true); if (nobj.Objects.Count == 0) { continue; } if (obj.ContainerID == 0 && obj.ArryX != 0 && obj.ArryY != 0) { nobj.BaseObject.SetPosition(LotTilePos.FromBigTile((short)(obj.ArryX), (short)(obj.ArryY), (sbyte)obj.ArryLevel), dir, VM.Context); } ents.Add(new Tuple <VMEntity, OBJM.MappedObject>(nobj.BaseObject, obj)); } //place objects in slots foreach (var ent in ents) { var obj = ent.Item2; if (ent.Item1.Position == LotTilePos.OUT_OF_WORLD && obj.ContainerID != 0 && obj.ArryX != 0 && obj.ArryY != 0) { var dir = (Direction)(1 << obj.Direction); ent.Item1.SetPosition(LotTilePos.FromBigTile((short)(obj.ArryX), (short)(obj.ArryY), (sbyte)obj.ArryLevel), dir, VM.Context); /* * var target = ents.First(x => x.Item2.ObjectID == obj.ContainerID); * target.Item1.PlaceInSlot(ent.Item1, obj.ContainerSlot, true, VM.Context); */ } } var entClone = new List <VMEntity>(VM.Entities); foreach (var nobj in entClone) { nobj.ExecuteEntryPoint(11, VM.Context, true); } arch.SignalRedraw(); VM.Context.World?.InitBlueprint(Blueprint); arch.Tick(); return(Blueprint); }
/// <summary> /// Initiates loading of walls. /// </summary> public void Init() { WallStyleToIndex = WallStyleIDs.ToDictionary(x => x, x => Array.IndexOf(WallStyleIDs, x)); this.Entries = new Dictionary <ushort, WallReference>(); this.ById = new Dictionary <ushort, Wall>(); this.DynamicWallFromID = new Dictionary <string, ushort>(); this.StyleById = new Dictionary <ushort, WallStyle>(); this.WallStyles = new List <WallStyle>(); var wallGlobalsPath = ContentManager.GetPath("objectdata/globals/walls.iff"); WallGlobals = new Files.Formats.IFF.IffFile(wallGlobalsPath); var buildGlobalsPath = ContentManager.GetPath("objectdata/globals/build.iff"); var buildGlobals = new Files.Formats.IFF.IffFile(buildGlobalsPath); //todo: centralize? /** Get wall styles from globals file **/ var styleStrs = buildGlobals.Get <STR>(0x81); ushort wallID = 1; for (ushort i = 2; i < 512; i += 2) { var far = WallGlobals.Get <SPR>((ushort)(i)); var medium = WallGlobals.Get <SPR>((ushort)(i + 512)); var near = WallGlobals.Get <SPR>((ushort)(i + 1024)); var fard = WallGlobals.Get <SPR>((ushort)(i + 1)); var mediumd = WallGlobals.Get <SPR>((ushort)(i + 513)); var neard = WallGlobals.Get <SPR>((ushort)(i + 1025)); if (fard == null) { //no walls down, just render exactly the same fard = far; mediumd = medium; neard = near; } string name = null, description = null; int price = -1; int buyIndex = -1; WallStyleToIndex.TryGetValue(wallID, out buyIndex); if (buyIndex != -1) { price = int.Parse(styleStrs.GetString(buyIndex * 3)); name = styleStrs.GetString(buyIndex * 3 + 1); description = styleStrs.GetString(buyIndex * 3 + 2); } this.AddWallStyle(new WallStyle { ID = wallID, WallsUpFar = far, WallsUpMedium = medium, WallsUpNear = near, WallsDownFar = fard, WallsDownMedium = mediumd, WallsDownNear = neard, Price = price, Name = name, Description = description }); wallID++; } DynamicStyleID = 256; //styles loaded from objects start at 256. The objd reference is dynamically altered to reference this new id, //so only refresh wall cache at same time as obj cache! (do this on lot unload) /** Get wall patterns from globals file **/ var wallStrs = buildGlobals.Get <STR>(0x83); wallID = 0; for (ushort i = 0; i < 256; i++) { var far = WallGlobals.Get <SPR>((ushort)(i + 1536)); var medium = WallGlobals.Get <SPR>((ushort)(i + 1536 + 256)); var near = WallGlobals.Get <SPR>((ushort)(i + 1536 + 512)); this.AddWall(new Wall { ID = wallID, Far = far, Medium = medium, Near = near, }); if (i > 0 && i < (wallStrs.Length / 3) + 1) { Entries.Add(wallID, new WallReference(this) { ID = wallID, FileName = "global", Name = wallStrs.GetString((i - 1) * 3 + 1), Price = int.Parse(wallStrs.GetString((i - 1) * 3 + 0)), Description = wallStrs.GetString((i - 1) * 3 + 2) }); } wallID++; } Junctions = new Wall { ID = wallID, Far = WallGlobals.Get <SPR>(4096), Medium = WallGlobals.Get <SPR>(4097), Near = WallGlobals.Get <SPR>(4098), }; wallID = 256; var archives = new string[] { "housedata/walls/walls.far", "housedata/walls2/walls2.far", "housedata/walls3/walls3.far", "housedata/walls4/walls4.far" }; for (var i = 0; i < archives.Length; i++) { var archivePath = ContentManager.GetPath(archives[i]); var archive = new FAR1Archive(archivePath, true); var entries = archive.GetAllEntries(); foreach (var entry in entries) { var iff = new Files.Formats.IFF.IffFile(); DynamicWallFromID[Path.GetFileNameWithoutExtension(entry.ToString().Replace('\\', '/')).ToLowerInvariant()] = wallID; var bytes = archive.GetEntry(entry); using (var stream = new MemoryStream(bytes)) { iff.Read(stream); } var catStrings = iff.Get <STR>(0); Entries.Add(wallID, new WallReference(this) { ID = wallID, FileName = entry.Key, Name = catStrings.GetString(0), Price = int.Parse(catStrings.GetString(1)), Description = catStrings.GetString(2) }); wallID++; } archive.Close(); } this.Walls = new FAR1Provider <Files.Formats.IFF.IffFile>(ContentManager, new IffCodec(), new Regex(".*/walls.*\\.far")); Walls.Init(); NumWalls = wallID; }
public BMP GetWallStyleIcon(ushort id) { return(WallGlobals.Get <BMP>(id)); }