const fs = require('fs'); const path = require('path'); const src = 'assets/tiled/ProbnaFarma.tmx'; const dest = 'assets/maps/NovaFarma.json'; try { const xml = fs.readFileSync(src, 'utf8'); // Super simple Regex parser for Tiled TMX (Caveat: Fragile!) const parseAttr = (tag, attr) => { const match = tag.match(new RegExp(`${attr}="([^"]*)"`)); return match ? match[1] : null; }; // Extract Map Info const mapMatch = xml.match(/]+>/); if (!mapMatch) throw new Error("No tag"); const mapTag = mapMatch[0]; const width = parseInt(parseAttr(mapTag, 'width')); const height = parseInt(parseAttr(mapTag, 'height')); const tilewidth = parseInt(parseAttr(mapTag, 'tilewidth')); const tileheight = parseInt(parseAttr(mapTag, 'tileheight')); const json = { width, height, tilewidth, tileheight, layers: [], tilesets: [], orientation: "orthogonal", renderorder: "right-down", type: "map" }; // Extract Layers const layerRegex = /]+>([\s\S]*?)<\/layer>/g; let layerMatch; let idCounter = 1; while ((layerMatch = layerRegex.exec(xml)) !== null) { const fullLayer = layerMatch[0]; const content = layerMatch[1]; const openTag = fullLayer.match(/]+>/)[0]; const name = parseAttr(openTag, 'name'); const visible = parseAttr(openTag, 'visible') !== '0'; let data = []; // Extract CSV Data const dataMatch = content.match(/([\s\S]*?)<\/data>/); if (dataMatch) { data = dataMatch[1].replace(/\s/g, '').split(',').map(Number); } json.layers.push({ id: idCounter++, name: name, type: "tilelayer", width: width, height: height, visible: visible, opacity: 1, x: 0, y: 0, data: data }); } // Extract Object Groups const objGroupRegex = /]+>([\s\S]*?)<\/objectgroup>/g; while ((layerMatch = objGroupRegex.exec(xml)) !== null) { const openTag = layerMatch[0].match(/]+>/)[0]; const name = parseAttr(openTag, 'name'); json.layers.push({ id: idCounter++, name: name, type: "objectgroup", visible: true, opacity: 1, objects: [] // Parsing objects is harder, skipping for now as user just wants visuals mostly }); } // Extract Tilesets // const tilesetRegex = /]+>/g; let tsMatch; while ((tsMatch = tilesetRegex.exec(xml)) !== null) { const tsTag = tsMatch[0]; const firstgid = parseInt(parseAttr(tsTag, 'firstgid')); const source = parseAttr(tsTag, 'source'); // We need to bake the tileset data or link it. // Phaser supports linked tilesets if JSON. // But for simplicity, let's create a minimal embedded definition referring to image collection // Actually, Tiled JSON exports 'source' usually. // Fix path: TMX is in assets/tiled/, references are relative. // JSON is in assets/maps/. // If source is "Buildings.tsx", in TMX it means "assets/tiled/Buildings.tsx". // In JSON (assets/maps), it should be "../tiled/Buildings.tsx". let jsonSource = source; if (!source.includes('/')) jsonSource = '../tiled/' + source; json.tilesets.push({ firstgid: firstgid, source: jsonSource }); } // Write fs.writeFileSync(dest, JSON.stringify(json, null, 4)); console.log(`✅ Converted TMX to JSON: ${dest}`); } catch (e) { console.error("❌ Conversion failed:", e); // Create Dummy fs.writeFileSync(dest, JSON.stringify({ width: 10, height: 10, layers: [] })); }