From 29276f779022e3ea2d7a645f87cedf16ca8a8c7e Mon Sep 17 00:00:00 2001
From: Treeki <treeki@gmail.com>
Date: Sun, 6 Nov 2011 00:36:41 +0100
Subject: unfinished, untested and probably horribly broken map exporter

---
 src/exporter.py | 130 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 130 insertions(+)
 create mode 100644 src/exporter.py

(limited to 'src')

diff --git a/src/exporter.py b/src/exporter.py
new file mode 100644
index 0000000..fec2f86
--- /dev/null
+++ b/src/exporter.py
@@ -0,0 +1,130 @@
+from common import *
+import array
+import sys
+
+
+class KPMapExporter:
+	class LayerExporter:
+		def __init__(self, layer):
+			self.layer = layer
+
+		def buildSectors(self, sectors, indices):
+			# we'll use the cache held by the layer: why reinvent the wheel?
+			layer.updateCache()
+			cache = layer.cache
+
+			# first off, get all the info and figure out the sector bounds
+			layerX, layerY = layer.cacheBasePos
+			layerWidth, layerHeight = layer.cacheSize
+
+			sectorLeft = layerX / 16
+			sectorTop = layerY / 16
+			sectorRight = (layerX + layerWidth) / 16
+			sectorBottom = (layerY + layerHeight) / 16
+
+			rawSectors = []
+			for i in xrange(sectorBottom - sectorTop + 1):
+				rawSectors.append([None for j in xrange(sectorRight - sectorLeft + 1)])
+
+			# copy every tile index over
+			for srcY in xrange(layerHeight):
+				srcRow = cache[srcY]
+				worldY = srcY + layerY
+				sectorY = worldY / 16
+				destY = worldY % 16
+
+				destRow = rawSectors[sectorY]
+				
+				for srcX in xrange(layerX, layerX+layerWidth):
+					worldX = srcX + layerX
+					sectorX = worldX / 16
+					destX = worldX % 16
+
+					tile = srcRow[i]
+					if tile == -1: continue
+
+					destSector = destRow[sectorX]
+					if destSector is None:
+						destSector = [[-1 for j in xrange(16)] for i in xrange(16)]
+						destRow[sectorX] = destSector
+
+					destSector[destY][destX] = tile
+
+			# now add the created sectors to the data
+			sectorMap = [-1 for i in xrange(len(self.rawSectors))]
+
+			for srcRow, mapRow in zip(self.rawSectors, sectorMap):
+				for index, sector in enumerate(srcRow):
+					if sector is not None:
+						# see if it's a duplicate or not
+						sectorKey = '|'.join(map(lambda x: ','.join(map(str, x)), sector))
+
+						try:
+							mapRow[index] = sectorIndices[sectorKey]
+						except ValueError:
+							sectorIndices[sectorKey] = len(sectors)
+							mapRow[index] = len(sectors)
+							sectors.append(sector)
+
+			self.sectorBounds = (sectorLeft, sectorTop, sectorRight, sectorBottom)
+			self.sectorMap = sectorMap
+
+
+	
+	def __init__(self, mapObj):
+		self.map = mapObj
+
+		self.layers = map(KPMapExporter.LayerExporter, self.map.layers)
+
+		self.archive = WiiArchiveU8()
+	
+	def buildAndPack(self, handle=None):
+		# make the BG data
+		sectors = []
+		sectorIndices = {}
+
+		for layer in self.layers:
+			layer.buildSectors(sectors, sectorIndices)
+
+		# pack it into the arc
+		self.archive.resolvePath('/sectors.bin').data = self._packSectorData(sectors)
+		self.archive.resolvePath('/sectorMaps.bin').data = self._packSectorMaps()
+
+		return self.archive.pack(handle)
+
+
+	def _packSectorData(self, sectors):
+		rowStruct = struct.Struct('>16h')
+		output = []
+
+		for sector in sectors:
+			for row in sector:
+				output.append(rowStruct.pack(*row))
+
+		return ''.join(output)
+
+	def _packSectorMaps(self):
+		offsets = array.array('I')
+		assert offsets.itemsize == 4
+
+		currentOffset = len(self.layers) * 4
+
+		data = []
+
+		for index, layer in enumerate(self.layers):
+			offsets.append(currentOffset)
+
+			data.append(struct.pack('>hhhh', *layer.sectorBounds))
+			currentOffset += 8
+			
+			first = layer.sectorMap[0]
+			rowStruct = struct.Struct('>%dh' % len(first))
+			for row in layer.sectorMap:
+				data.append(rowStruct.pack(*row))
+
+			currentOffset += (len(first) * len(layer.sectorMap) * 2)
+
+		if sys.byteorder == 'little': offsets.byteswap()
+		return offsets.tostring() + ''.join(data)
+
+
-- 
cgit v1.2.3