### Complete DBPF File Workflow Example (Scala) Source: https://context7.com/memo33/scdbpf/llms.txt Illustrates a full workflow for reading a DBPF file, processing its entries (rotating models, shifting text GIDs), and writing the modified content to a new file. This example utilizes the `throwExceptions` strategy. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.DbpfUtil.RotFlip import io.github.memo33.scdbpf.strategy.throwExceptions import io.github.memo33.passera.unsigned.UInt import java.io.File // Read input file val inputFile = new File("input.dat") val dbpf = DbpfFile.read(inputFile) // Process all entries val processedEntries = dbpf.entries.map { entry => entry.tgi match { // Rotate all SC4Paths by 90 degrees case tgi if tgi matches Tgi.Sc4Path => val be = entry.toBufferedEntry.convertContentTo(Sc4Path) be.copy(content = be.content * RotFlip.R1F0) // Rotate all S3D models by 90 degrees case tgi if tgi matches Tgi.S3d => val be = entry.toBufferedEntry.convertContentTo(S3d) be.copy(content = be.content * RotFlip.R1F0) // Shift GID of all LText entries case tgi if tgi matches Tgi.LText => entry.copy(entry.tgi.copy(gid = entry.tgi.gid + 1)) // Keep other entries unchanged case _ => entry } } // Write to output file val outputFile = new File("output.dat") DbpfFile.write(processedEntries, outputFile) println(s"Processed ${processedEntries.size} entries") ``` -------------------------------- ### Sort DBPF Entries by TGI in Scala Console Source: https://github.com/memo33/scdbpf/blob/master/README.md Example of reading a DBPF file, sorting its entries by TGI (Type, Group, ID), and writing the sorted entries back to a file. This demonstrates the library's API for file manipulation and data sorting. ```scala val dbpf = DbpfFile.read(new File("foobar.dat")) dbpf.write(dbpf.entries.sortBy(_.tgi)) ``` -------------------------------- ### Read, Transform, and Create S3D Models in Scala Source: https://context7.com/memo33/scdbpf/llms.txt Demonstrates how to read S3D models from DBPF files, perform transformations like rotation, scaling, and translation, and create new S3D models programmatically. It requires the scdbpf library and standard Java IO. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.S3d._ import io.github.memo33.scdbpf.DbpfUtil.RotFlip import io.github.memo33.scdbpf.strategy.throwExceptions import java.io.File val dbpf = DbpfFile.read(new File("mymod.dat")) // Read and transform S3D models for (entry <- dbpf.entries if entry.tgi matches Tgi.S3d) { val buffered = entry.toBufferedEntry.convertContentTo(S3d) val s3d = buffered.content println(s"Vertex groups: ${s3d.vert.size}") println(s"Index groups: ${s3d.indx.size}") println(s"Material groups: ${s3d.mats.size}") println(s"Animation groups: ${s3d.anim.size}") // Rotate model by 90 degrees val rotated = s3d * RotFlip.R1F0 // Scale model by 2x val scaled = s3d.scale(2.0f) // Translate model val translated = s3d.translate(Translation(10.0f, 0.0f, 5.0f)) // Flip normals val flipped = s3d.withNormalsFlipped // Remove unused groups val trimmed = s3d.trim // Combine two models // val combined = s3d ++ otherS3d } // Create new S3D model val vertices = VertGroup(IndexedSeq( Vert(-1.0f, 0.0f, -1.0f, 0.0f, 0.0f), Vert( 1.0f, 0.0f, -1.0f, 1.0f, 0.0f), Vert( 0.0f, 0.0f, 1.0f, 0.5f, 1.0f) )) val indices = IndxGroup(IndexedSeq(0, 1, 2)) val primitives = PrimGroup(IndexedSeq( Prim(PrimType.Triangle, 0, 3) )) val materials = S3d.defaultMats( transparency = Transparency.Opaque, id = 0x12345678, name = Some("MyTexture") ) val animation = AnimGroup.vipm( vertBlock = 0, indxBlock = 0, primBlock = 0, matsBlock = 0, name = Some("Main") ) val newS3d = S3d( vert = IndexedSeq(vertices), indx = IndexedSeq(indices), prim = IndexedSeq(primitives), mats = IndexedSeq(materials), anim = IndexedSeq(animation) ) ``` -------------------------------- ### Manipulate Exemplar Property Containers Source: https://context7.com/memo33/scdbpf/llms.txt Demonstrates how to search for specific properties within an Exemplar, modify existing property values, and construct new Exemplar objects from scratch using the scdbpf library. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.DbpfProperty._ import io.github.memo33.scdbpf.strategy.throwExceptions import io.github.memo33.passera.unsigned.UInt import java.io.File val dbpf = DbpfFile.read(new File("mymod.dat")) // Find exemplar with specific property val propId = UInt(0x12345678) val found = dbpf.entries.view .filter(_.tgi matches Tgi.Exemplar) .map(_.toBufferedEntry.convertContentTo(Exemplar)) .find(_.content.properties.contains(propId)) // Read and modify exemplar properties for (entry <- dbpf.entries if entry.tgi matches Tgi.Exemplar) { val buffered = entry.toBufferedEntry.convertContentTo(Exemplar) val exemplar = buffered.content // Access property by ID if (exemplar.properties.contains(propId)) { val prop = exemplar.properties(propId) prop match { case ValueType.Uint32(Single(value)) => println(s"UInt32 value: $value") case ValueType.Float32(Single(value)) => println(s"Float value: $value") case ValueType.Sint32(Multi(values)) => println(s"Int array: ${values.mkString(", ")}") case ValueType.String(Single(text)) => println(s"String: $text") case _ => println("Other type") } } // Create modified exemplar val newProps = exemplar.properties + (propId -> DbpfProperty(UInt(42))) val newExemplar = exemplar.copy(properties = newProps) val newEntry = buffered.copy(content = newExemplar) } // Create new exemplar from scratch val newExemplar = Exemplar( parent = Tgi.Blank, isCohort = false, props = Seq( (UInt(0x10), DbpfProperty(UInt(100))), (UInt(0x20), DbpfProperty(3.14f)), (UInt(0x30), DbpfProperty("Hello")) ) ) ``` -------------------------------- ### Apply RotFlip Transformations in Scala Source: https://context7.com/memo33/scdbpf/llms.txt Illustrates the usage of the RotFlip utility for applying rotations and flips to coordinates, S3D models, and SC4Paths. It shows how to combine transformations and check for flip operations. Requires the scdbpf library. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.DbpfUtil.RotFlip import io.github.memo33.scdbpf.DbpfUtil.RotFlip._ // Available RotFlip values (rotation, flip) // R0F0 = (0,0) - identity // R1F0 = (1,0) - 90 degrees clockwise // R2F0 = (2,0) - 180 degrees // R3F0 = (3,0) - 270 degrees clockwise // R0F1 = (0,1) - mirror horizontally // R1F1 = (1,1) - 90 degrees + mirror // R2F1 = (2,1) - 180 degrees + mirror // R3F1 = (3,1) - 270 degrees + mirror // Combine rotations (group multiplication) val combined = R1F0 * R1F0 // = R2F0 (180 degrees) // Check if flipped if (R1F1.flipped) println("This transformation includes a flip") // Apply to coordinates using *: operator import io.github.memo33.scdbpf.Sc4Path.Coord val coord: Coord = (1.0f, 2.0f, 3.0f) val rotatedCoord: Coord = coord *: R1F0 // Rotate 90 degrees // Apply to S3D models and SC4Paths // val rotatedModel = s3d * R1F0 // val rotatedPath = sc4path * R1F0 ``` -------------------------------- ### Read DBPF Files with Scala Source: https://context7.com/memo33/scdbpf/llms.txt Demonstrates how to read a DBPF file using `DbpfFile.read`. It shows how to access file header information, iterate through entries, and retrieve specific entries by their TGI. This function requires a `java.io.File` object as input and returns a `DbpfFile` container. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.strategy.throwExceptions import java.io.File // Read a DBPF file val dbpf = DbpfFile.read(new File("mymod.dat")) // Access file header information println(s"DBPF Version: ${dbpf.header.majorVersion}.${dbpf.header.minorVersion}") println(s"Number of entries: ${dbpf.entries.size}") // Iterate over all entries for (entry <- dbpf.entries) { println(s"TGI: ${entry.tgi}, Size: ${entry.size}") } // Access entries by TGI using the map val tgi = Tgi(0x6534284a, 0x12345678, 0x87654321) dbpf.tgiMap.get(tgi) match { case Some(entry) => println(s"Found entry: ${entry.tgi}") case None => println("Entry not found") } ``` -------------------------------- ### Write DBPF Files with Scala Source: https://context7.com/memo33/scdbpf/llms.txt Illustrates how to write DBPF entries to files using `DbpfFile.write`. It covers writing sorted entries back to the original file (using a temporary file for safety), writing to a new file, and filtering entries before writing. The method accepts a sequence of entries and a `java.io.File` object. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.strategy.throwExceptions import java.io.File val dbpf = DbpfFile.read(new File("input.dat")) // Sort entries by TGI and write to same file dbpf.write(dbpf.entries.sortBy(_.tgi)) // Write to a different file DbpfFile.write(dbpf.entries, new File("output.dat")) // Filter entries and write val filteredEntries = dbpf.entries.filter(_.tgi matches Tgi.Exemplar) DbpfFile.write(filteredEntries, new File("exemplars_only.dat")) ``` -------------------------------- ### Manage Localized Text (LText) Entries Source: https://context7.com/memo33/scdbpf/llms.txt Shows how to read LText content, create new localized text entries with specific encodings, and perform batch modifications on DBPF entries. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.strategy.throwExceptions import java.io.File val dbpf = DbpfFile.read(new File("mymod.dat")) // Read LText entries for (entry <- dbpf.entries if entry.tgi matches Tgi.LText) { val buffered = entry.toBufferedEntry.convertContentTo(LText) val ltext = buffered.content println(s"Text: ${ltext.text}") println(s"Format: ${ltext.format}") // Utf16, Utf8, Ascii, or AsciiNoHeader } // Create new LText val newLText = LText("Hello, SimCity!", LText.Format.Utf16) val newEntry = BufferedEntry( tgi = Tgi(0x2026960b, 0x12345678, 0x00000001), content = newLText, compressed = true ) // Modify GID of all LText entries val modified = dbpf.entries.map { e => if (e.tgi matches Tgi.LText) e.copy(e.tgi.copy(gid = e.tgi.gid + 3)) else e } dbpf.write(modified) ``` -------------------------------- ### Exception Handling Strategies in scdbpf (Scala) Source: https://context7.com/memo33/scdbpf/llms.txt Demonstrates two exception handling strategies: throwing exceptions (default) and capturing them in a wrapper type. This allows for flexible error management in DBPF file operations. ```scala import io.github.memo33.scdbpf._ import java.io.File // Strategy 1: Throw exceptions (default, recommended for scripts) { import io.github.memo33.scdbpf.strategy.throwExceptions try { val dbpf = DbpfFile.read(new File("mymod.dat")) // Work with dbpf... } catch { case e: DbpfFileFormatException => println(s"Invalid file format: ${e.getMessage}") case e: DbpfDecodeFailedException => println(s"Decode failed: ${e.getMessage}") case e: DbpfStreamOutOfDateException => println(s"File changed: ${e.getMessage}") case e: java.io.IOException => println(s"IO error: ${e.getMessage}") } } // Strategy 2: Capture exceptions (for functional error handling) { import io.github.memo33.scdbpf.strategy.captureExceptions val result = DbpfFile.read(new File("mymod.dat")) result match { case Right(dbpf) => println(s"Success: ${dbpf.entries.size} entries") case Left(error) => println(s"Error: $error") } } ``` -------------------------------- ### Convert DBPF Entries to Buffered Types in Scala Source: https://context7.com/memo33/scdbpf/llms.txt Details the process of converting lightweight `StreamedEntry` objects to `BufferedEntry` for decoded access to their content. The `convertContentTo` method is used to transform the raw data into specific DBPF types like `Exemplar`. Lazy evaluation using `view` for efficient conversion is also shown. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.strategy.throwExceptions import java.io.File val dbpf = DbpfFile.read(new File("mymod.dat")) // Convert entry to BufferedEntry with decoded content for (entry <- dbpf.entries if entry.tgi matches Tgi.Exemplar) { val buffered = entry.toBufferedEntry.convertContentTo(Exemplar) println(s"Parent cohort: ${buffered.content.parent}") println(s"Is cohort: ${buffered.content.isCohort}") println(s"Properties: ${buffered.content.properties.size}") } // Efficient conversion using view (lazy evaluation) val exemplarOpt = dbpf.entries.view .filter(_.tgi matches Tgi.Exemplar) .map(_.toBufferedEntry.convertContentTo(Exemplar)) .headOption ``` -------------------------------- ### Work with TGI Identifiers in Scala Source: https://context7.com/memo33/scdbpf/llms.txt Explains how to create and manipulate TGI (Type-Group-Instance) identifiers, which are used to uniquely identify DBPF entries. It shows how to create TGIs, copy them with modifications, and use predefined and custom TGI masks for matching entries. Sorting entries by TGI is also demonstrated. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.strategy.throwExceptions // Create a TGI val tgi = Tgi(0x6534284a, 0x00000001, 0x12345678) // Copy with modified IID val newTgi = tgi.copy(iid = 0x87654321) // Match against predefined masks if (tgi matches Tgi.Exemplar) println("This is an Exemplar") if (tgi matches Tgi.Fsh) println("This is an FSH texture") if (tgi matches Tgi.Sc4Path) println("This is an SC4Path") if (tgi matches Tgi.S3d) println("This is a 3D model") if (tgi matches Tgi.LText) println("This is localized text") // Create custom mask (None = wildcard) val customMask = TgiMask(Some(0x6534284a), None, None) // Use TGI ordering for sorting val entries: Seq[Tgi] = Seq(tgi, newTgi) val sorted = entries.sorted(Tgi.itgOrdering) // Sort by IID, TID, GID ``` -------------------------------- ### Process SC4Path Network Data Source: https://context7.com/memo33/scdbpf/llms.txt Covers reading, rotating, and shifting SC4Path entries, as well as constructing new pathing data for transportation networks. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.Sc4Path._ import io.github.memo33.scdbpf.DbpfUtil.RotFlip import io.github.memo33.scdbpf.strategy.throwExceptions import java.io.File val dbpf = DbpfFile.read(new File("mymod.dat")) // Read and rotate SC4Path entries for (entry <- dbpf.entries if entry.tgi matches Tgi.Sc4Path) { val buffered = entry.toBufferedEntry.convertContentTo(Sc4Path) val sc4path = buffered.content println(s"Terrain variance: ${sc4path.terrainVariance}") println(s"Paths: ${sc4path.paths.size}") println(s"Stop paths: ${sc4path.stopPaths.size}") // Rotate path by 90 degrees val rotated = sc4path * RotFlip.R1F0 // Shift path height val raised = sc4path.shiftHeight(5.0f) } // Create new path val newPath = Path( comment = Some("My custom path"), transportType = TransportType.Car, classNumber = 0, entry = Cardinal.West, exit = Cardinal.East, junction = false, coords = Seq( (-8.0f, 0.0f, 0.0f), (0.0f, 0.0f, 0.0f), (8.0f, 0.0f, 0.0f) ) ) val newSc4Path = Sc4Path( terrainVariance = false, paths = Seq(newPath), stopPaths = Seq.empty, decFormat = Some(Sc4Path.threeDecimals) ) // Write rotated paths back val writeList = dbpf.entries.map { e => if (e.tgi matches Tgi.Sc4Path) { val be = e.toBufferedEntry.convertContentTo(Sc4Path) be.copy(content = be.content * RotFlip.R1F0) } else { e } } dbpf.write(writeList) ``` -------------------------------- ### Read FSH Textures in Scala Source: https://context7.com/memo33/scdbpf/llms.txt Shows how to read FSH texture files from DBPF archives, access image dimensions, and iterate through different texture elements and their mipmaps. This functionality relies on the scdbpf library and Java IO. ```scala import io.github.memo33.scdbpf._ import io.github.memo33.scdbpf.Fsh._ import io.github.memo33.scdbpf.strategy.throwExceptions import java.io.File val dbpf = DbpfFile.read(new File("mymod.dat")) // Read FSH textures for (entry <- dbpf.entries if entry.tgi matches Tgi.Fsh) { val buffered = entry.toBufferedEntry.convertContentTo(Fsh) val fsh = buffered.content println(s"Directory ID: ${fsh.dirId}") println(s"Elements: ${fsh.elements.size}") // Access first image (convenience method) val mainImage = fsh.image println(s"Image size: ${mainImage.width}x${mainImage.height}") // Access all elements and their mipmaps for ((elem, i) <- fsh.elements.zipWithIndex) { println(s"Element $i: format=${elem.format}, images=${elem.images.size}") for (img <- elem.images) { println(s" Mipmap: ${img.width}x${img.height}") } } } // Supported FSH formats: // FshFormat.A8R8G8B8 - 32-bit ARGB // FshFormat.A0R8G8B8 - 24-bit RGB (no alpha) // FshFormat.A1R5G5B5 - 16-bit with 1-bit alpha // FshFormat.A0R5G6B5 - 16-bit RGB (no alpha) // FshFormat.A4R4G4B4 - 16-bit with 4-bit alpha // FshFormat.Dxt1, Dxt3, Dxt5 - DXT compressed formats ``` -------------------------------- ### Add scdbpf Dependency to build.sbt Source: https://github.com/memo33/scdbpf/blob/master/README.md This snippet shows how to add the scdbpf library as a dependency to your Scala project using the sbt build tool. It specifies the group ID, artifact ID, and version number required for integration. ```scala libraryDependencies += "io.github.memo33" %% "scdbpf" % "0.2.1" ``` === COMPLETE CONTENT === This response contains all available snippets from this library. No additional content exists. Do not make further requests.