mirror of
https://github.com/jlengrand/korge-intellij-plugin.git
synced 2026-03-10 08:31:19 +00:00
Fix adding tsx files to tilemap
This commit is contained in:
@@ -38,22 +38,16 @@ class MapComponent(val tmx: TiledMap) : JComponent() {
|
||||
field = value
|
||||
mapRepaint(false)
|
||||
}
|
||||
val maxTileGid = tmx.tilesets.map { it.firstgid + it.tileset.textures.size }.max() ?: 0
|
||||
val tilesSize = tmx.tilesets.sumBy { it.tileset.textures.size }
|
||||
|
||||
data class TileInfo(val bmp32: Bitmap32) {
|
||||
val miniSlice = bmp32.slice()
|
||||
val isTransparent by lazy { bmp32.all { it.a == 0 } }
|
||||
}
|
||||
|
||||
val tiles = Array<TileInfo?>(maxTileGid) { null }.also { tiles ->
|
||||
val tiles = HashMap<Int, BitmapSlice<Bitmap32>?>(tilesSize).also { tiles ->
|
||||
for (tileset in tmx.tilesets) {
|
||||
for (tileIdx in tileset.tileset.textures.indices) {
|
||||
val tile = tileset.tileset.textures[tileIdx]
|
||||
if (tile != null) {
|
||||
val miniSlice = (tile as BitmapSlice<*>).extract().toBMP32()
|
||||
tiles[tileset.firstgid + tileIdx] = when {
|
||||
miniSlice.allFixed { it.a == 0 } -> null // Transparent
|
||||
else -> TileInfo(miniSlice)
|
||||
val tileBmp = (tile as BitmapSlice<*>).extract().toBMP32()
|
||||
if (tileBmp.any { it.a != 0 }) { // not transparent
|
||||
tiles[tileset.firstgid + tileIdx] = tileBmp.slice()
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -169,8 +163,8 @@ class MapComponent(val tmx: TiledMap) : JComponent() {
|
||||
RenderingHints.VALUE_INTERPOLATION_NEAREST_NEIGHBOR
|
||||
)
|
||||
val clipBounds = g.clipBounds
|
||||
val displayTilesX = ((clipBounds.width / TILE_WIDTH / scale) + 3).toInt().coerceIn(0, tmx.width - 1)
|
||||
val displayTilesY = ((clipBounds.height / TILE_HEIGHT / scale) + 3).toInt().coerceIn(0, tmx.height - 1)
|
||||
val displayTilesX = ((clipBounds.width / TILE_WIDTH / scale) + 3).toInt().coerceIn(1, tmx.width)
|
||||
val displayTilesY = ((clipBounds.height / TILE_HEIGHT / scale) + 3).toInt().coerceIn(1, tmx.height)
|
||||
val offsetX = (clipBounds.x / TILE_WIDTH / scale).toInt()
|
||||
val offsetY = (clipBounds.y / TILE_HEIGHT / scale).toInt()
|
||||
|
||||
@@ -178,7 +172,7 @@ class MapComponent(val tmx: TiledMap) : JComponent() {
|
||||
offsetX = offsetX, offsetY = offsetY,
|
||||
displayTilesX = displayTilesX,
|
||||
displayTilesY = displayTilesY,
|
||||
TILE_WIDTH = TILE_WIDTH, TILE_HEIGHT = TILE_WIDTH
|
||||
TILE_WIDTH = TILE_WIDTH, TILE_HEIGHT = TILE_HEIGHT
|
||||
)) {
|
||||
val temp = Bitmap32(
|
||||
(displayTilesX * TILE_WIDTH),
|
||||
@@ -197,9 +191,9 @@ class MapComponent(val tmx: TiledMap) : JComponent() {
|
||||
if (ry < 0 || ry >= layer.map.height) continue
|
||||
|
||||
val tileIdx = layer.map[rx, ry].value
|
||||
val tile = tiles.getOrNull(tileIdx)
|
||||
if (tile != null && !tile.isTransparent) {
|
||||
temp._fastMix(tile.miniSlice, x * TILE_WIDTH, y * TILE_HEIGHT)
|
||||
val tile = tiles.getOrDefault(tileIdx, null)
|
||||
if (tile != null) {
|
||||
temp._fastMix(tile, x * TILE_WIDTH, y * TILE_HEIGHT)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -314,6 +308,3 @@ fun fastBlend(dst: RGBAPremultiplied, src: RGBAPremultiplied): RGBAPremultiplied
|
||||
val ag = (colora and 0xFF00FF00L) + ((alpha * (colorb and 0xFF00FF00L)) ushr 8)
|
||||
return RGBAPremultiplied(((rb and 0xFF00FFL) + (ag and 0xFF00FF00L)).toInt())
|
||||
}
|
||||
|
||||
inline fun Bitmap32.anyFixed(callback: (RGBA) -> Boolean): Boolean = (0 until area).any { callback(data[it]) }
|
||||
inline fun Bitmap32.allFixed(callback: (RGBA) -> Boolean): Boolean = (0 until area).all { callback(data[it]) }
|
||||
@@ -83,8 +83,7 @@ data class TileSetData constructor(
|
||||
//@AsyncFactoryClass(TiledMapFactory::class)
|
||||
class TiledMap constructor(
|
||||
var data: TiledMapData,
|
||||
var tilesets: List<TiledTileset>,
|
||||
var tileset: TileSet
|
||||
var tilesets: List<TiledTileset>
|
||||
) {
|
||||
val width get() = data.width
|
||||
val height get() = data.height
|
||||
@@ -93,11 +92,12 @@ class TiledMap constructor(
|
||||
val pixelWidth: Int get() = data.pixelWidth
|
||||
val pixelHeight: Int get() = data.pixelHeight
|
||||
val allLayers get() = data.allLayers
|
||||
val patternLayers get() = data.tileLayers
|
||||
val tileLayers get() = data.tileLayers
|
||||
val imageLayers get() = data.imageLayers
|
||||
val objectLayers get() = data.objectLayers
|
||||
val nextGid get() = tilesets.map { it.firstgid + it.tileset.textures.size }.max() ?: 1
|
||||
|
||||
fun clone() = TiledMap(data.clone(), tilesets.map { it.clone() }, tileset.clone())
|
||||
fun clone() = TiledMap(data.clone(), tilesets.map { it.clone() })
|
||||
|
||||
data class TiledTileset(
|
||||
val tileset: TileSet,
|
||||
@@ -116,7 +116,7 @@ class TiledMap constructor(
|
||||
terrains = listOf(),
|
||||
tiles = tileset.textures.mapIndexed { index, bmpSlice -> TileData(index) }
|
||||
),
|
||||
val firstgid: Int = 0
|
||||
val firstgid: Int = 1
|
||||
) {
|
||||
fun clone(): TiledTileset = TiledTileset(tileset.clone(), data.clone(), firstgid)
|
||||
}
|
||||
@@ -149,7 +149,7 @@ class TiledMap constructor(
|
||||
}
|
||||
abstract fun clone(): Layer
|
||||
|
||||
class Tiles constructor(
|
||||
class Tiles(
|
||||
var map: Bitmap32 = Bitmap32(0, 0),
|
||||
var encoding: String = "csv",
|
||||
var compression: String = ""
|
||||
|
||||
@@ -14,7 +14,6 @@ import com.soywiz.korio.serialization.xml.*
|
||||
import com.soywiz.korio.util.encoding.*
|
||||
import com.soywiz.korma.geom.*
|
||||
|
||||
|
||||
suspend fun VfsFile.readTiledMap(
|
||||
hasTransparentColor: Boolean = false,
|
||||
transparentColor: RGBA = Colors.FUCHSIA,
|
||||
@@ -40,7 +39,7 @@ suspend fun VfsFile.readTiledMap(
|
||||
tiledTilesets += tileset.toTiledSet(folder, hasTransparentColor, transparentColor, createBorder)
|
||||
}
|
||||
|
||||
return TiledMap(data, tiledTilesets, tiledTilesets.combine(data.tilewidth, data.tileheight))
|
||||
return TiledMap(data, tiledTilesets)
|
||||
}
|
||||
|
||||
private fun Xml.parseProperties(): Map<String, Any> {
|
||||
@@ -148,18 +147,6 @@ suspend fun TileSetData.toTiledSet(
|
||||
return tiledTileset
|
||||
}
|
||||
|
||||
fun Iterable<TiledMap.TiledTileset>.combine(tilewidth: Int, tileheight: Int): TileSet {
|
||||
val maxGid = this.map { it.firstgid + it.tileset.textures.size }.max() ?: 1
|
||||
val combinedTileset = arrayOfNulls<BmpSlice>(maxGid + 1)
|
||||
for (tileset in this) {
|
||||
val ptileset = tileset.tileset
|
||||
for (n in ptileset.textures.indices) {
|
||||
combinedTileset[tileset.firstgid + n] = ptileset.textures[n]
|
||||
}
|
||||
}
|
||||
return TileSet(combinedTileset.toList(), tilewidth, tileheight)
|
||||
}
|
||||
|
||||
suspend fun VfsFile.readTiledMapData(): TiledMapData {
|
||||
val log = tilemapLog
|
||||
val file = this
|
||||
|
||||
@@ -60,8 +60,7 @@ fun TileSetData.toXML(): Xml {
|
||||
// <image source="Overworld.png" width="640" height="576"/>
|
||||
//</tileset>
|
||||
return buildXml("tileset",
|
||||
"version" to 1.2,
|
||||
"tiledversion" to "1.3.1",
|
||||
"firstgid" to firstgid,
|
||||
"name" to name,
|
||||
"tilewidth" to tilewidth,
|
||||
"tileheight" to tileheight,
|
||||
|
||||
@@ -11,6 +11,7 @@ import com.soywiz.korge.view.tiles.*
|
||||
import com.soywiz.korim.bitmap.*
|
||||
import com.soywiz.korim.color.*
|
||||
import com.soywiz.korim.format.*
|
||||
import com.soywiz.korio.file.*
|
||||
import com.soywiz.korma.geom.*
|
||||
import kotlinx.coroutines.*
|
||||
import javax.swing.*
|
||||
@@ -25,10 +26,10 @@ fun Styled<out JTabbedPane>.tilesetTab(
|
||||
fill()
|
||||
uiSequence({ tilemap.tilesets }, tilesetsUpdated) { tileset ->
|
||||
println("TAB.TILESET: $tileset")
|
||||
tab("Untitled") {
|
||||
tab(tileset.data.name) {
|
||||
val tilemap = tileset.pickerTilemap()
|
||||
val mapComponent = MapComponent(tilemap)
|
||||
val patternLayer = tilemap.patternLayers.first()
|
||||
val tileLayer = tilemap.tileLayers.first()
|
||||
mapComponent.selectedRange(0, 0)
|
||||
var downStart: PointInt? = null
|
||||
val zoomLevel =
|
||||
@@ -60,7 +61,7 @@ fun Styled<out JTabbedPane>.tilesetTab(
|
||||
val width = xmax - xmin + 1
|
||||
val height = ymax - ymin + 1
|
||||
val bmp =
|
||||
Bitmap32(width, height) { x, y -> RGBA(patternLayer.map[xmin + x, ymin + y].value) }
|
||||
Bitmap32(width, height) { x, y -> RGBA(tileLayer.map[xmin + x, ymin + y].value) }
|
||||
picked.value = PickedSelection(bmp)
|
||||
mapComponent.selectedRange(xmin, ymin, bmp.width, bmp.height)
|
||||
}
|
||||
@@ -69,28 +70,28 @@ fun Styled<out JTabbedPane>.tilesetTab(
|
||||
}
|
||||
}
|
||||
toolbar {
|
||||
iconButton(toolbarIcon("add.png")) {
|
||||
iconButton(toolbarIcon("add.png"), "Add tileset file or image") {
|
||||
click {
|
||||
val file = projectContext.chooseFile()
|
||||
if (file != null) {
|
||||
val vfsFile = file.toVfs()
|
||||
val vfsFile = projectContext.chooseFile()?.toVfs()
|
||||
if (vfsFile != null) {
|
||||
runBlocking {
|
||||
val tileset = try {
|
||||
val firstgid = tilemap.nextGid
|
||||
val tileset = if (vfsFile.extensionLC != "tsx") {
|
||||
val bmp = vfsFile.readBitmap()
|
||||
TiledMap.TiledTileset(TileSet(bmp.slice().split(32, 32), 32, 32, bmp))
|
||||
} catch (e: Throwable) {
|
||||
vfsFile.readTileSetData().toTiledSet(vfsFile.parent)
|
||||
tiledsetFromBitmap(vfsFile.baseName, 32, 32, bmp, firstgid)
|
||||
} else {
|
||||
vfsFile.readTileSetData(firstgid).toTiledSet(vfsFile.parent)
|
||||
}
|
||||
|
||||
val oldMap = tilemap
|
||||
history.addAndDo("ADD TILESET") { redo ->
|
||||
if (redo) {
|
||||
tilemap.data.tilesets += tileset.data
|
||||
tilemap.tilesets += tileset
|
||||
tilemap.tileset = tileset.tileset
|
||||
tilesetsUpdated(Unit)
|
||||
} else {
|
||||
TODO("Unsupported now")
|
||||
tilemap.data.tilesets -= tileset.data
|
||||
tilemap.tilesets -= tileset
|
||||
tilesetsUpdated(Unit)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -124,6 +125,29 @@ private fun TiledMap.TiledTileset.pickerTilemap(): TiledMap {
|
||||
return TiledMap(TiledMapData(
|
||||
width = mapWidth, height = mapHeight,
|
||||
tilewidth = tileset.width, tileheight = tileset.height,
|
||||
allLayers = arrayListOf(TiledMap.Layer.Tiles(Bitmap32(mapWidth.coerceAtLeast(1), mapHeight.coerceAtLeast(1)) { x, y -> RGBA(y * mapWidth + x) }))
|
||||
), listOf(this), tileset)
|
||||
allLayers = arrayListOf(TiledMap.Layer.Tiles(
|
||||
Bitmap32(mapWidth.coerceAtLeast(1), mapHeight.coerceAtLeast(1)) { x, y -> RGBA(y * mapWidth + x + firstgid) }
|
||||
))
|
||||
), listOf(this))
|
||||
}
|
||||
|
||||
private fun tiledsetFromBitmap(name: String, tileWidth: Int, tileHeight: Int, bmp: Bitmap, firstgid: Int): TiledMap.TiledTileset {
|
||||
val tileset = TileSet(bmp.slice().split(tileWidth, tileHeight), tileWidth, tileHeight)
|
||||
return TiledMap.TiledTileset(tileset,
|
||||
TileSetData(
|
||||
name = name.substringBeforeLast("."),
|
||||
firstgid = firstgid,
|
||||
tilewidth = tileset.width,
|
||||
tileheight = tileset.height,
|
||||
tilecount = tileset.textures.size,
|
||||
columns = tileset.base.width / tileset.width,
|
||||
image = null,
|
||||
imageSource = name,
|
||||
width = tileset.base.width,
|
||||
height = tileset.base.height,
|
||||
tilesetSource = null,
|
||||
terrains = listOf(),
|
||||
tiles = tileset.textures.mapIndexed { index, bmpSlice -> TileData(index) }
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -101,7 +101,7 @@ fun Styled<out Container>.toolbar(direction: Direction = Direction.HORIZONTAL, p
|
||||
}
|
||||
|
||||
fun Styled<out Container>.tabs(block: @UIDslMarker Styled<JBTabbedPane>.() -> Unit = {}): JBTabbedPane {
|
||||
val container = JBTabbedPane(JBTabbedPane.TOP)
|
||||
val container = JBTabbedPane(JBTabbedPane.TOP, JTabbedPane.SCROLL_TAB_LAYOUT)
|
||||
component.add(container)
|
||||
block(container.styled)
|
||||
return container
|
||||
|
||||
Reference in New Issue
Block a user