Unify and improve moddability of more tile-based images. (#5873)

This commit is contained in:
will-ca 2021-12-29 08:21:34 -08:00 committed by GitHub
parent 7581b7b621
commit 1a8a86cb2c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 48 additions and 56 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

View File

@ -158,16 +158,16 @@ class CityScreen(
val nextTile = city.expansion.chooseNewTileToOwn()
for (tileGroup in tileGroups) {
tileGroup.update()
tileGroup.hideCircle()
tileGroup.hideHighlight()
if (city.tiles.contains(tileGroup.tileInfo.position)
&& constructionsTable.improvementBuildingToConstruct != null) {
val improvement = constructionsTable.improvementBuildingToConstruct!!.getImprovement(city.getRuleset())!!
if (tileGroup.tileInfo.canBuildImprovement(improvement, city.civInfo))
tileGroup.showCircle(Color.GREEN)
else tileGroup.showCircle(Color.RED)
tileGroup.showHighlight(Color.GREEN)
else tileGroup.showHighlight(Color.RED)
}
if (tileGroup.tileInfo == nextTile) {
tileGroup.showCircle(Color.PURPLE)
tileGroup.showHighlight(Color.PURPLE)
tileGroup.setColor(0f, 0f, 0f, 0.7f)
}
}

View File

@ -95,7 +95,7 @@ class TileGroupMap<T: TileGroup>(
unitLayers.add(group.unitLayerGroup.apply { setPosition(group.x,group.y) })
unitImageLayers.add(group.unitImageLayerGroup.apply { setPosition(group.x,group.y) })
cityButtonLayers.add(group.cityButtonLayerGroup.apply { setPosition(group.x,group.y) })
circleCrosshairFogLayers.add(group.circleCrosshairFogLayerGroup.apply { setPosition(group.x,group.y) })
circleCrosshairFogLayers.add(group.highlightCrosshairFogLayerGroup.apply { setPosition(group.x,group.y) })
if (worldWrap) {
for (mirrorTile in mirrorTileGroups[group.tileInfo]!!.toList()) {
@ -105,7 +105,7 @@ class TileGroupMap<T: TileGroup>(
unitLayers.add(mirrorTile.unitLayerGroup.apply { setPosition(mirrorTile.x,mirrorTile.y) })
unitImageLayers.add(mirrorTile.unitImageLayerGroup.apply { setPosition(mirrorTile.x,mirrorTile.y) })
cityButtonLayers.add(mirrorTile.cityButtonLayerGroup.apply { setPosition(mirrorTile.x,mirrorTile.y) })
circleCrosshairFogLayers.add(mirrorTile.circleCrosshairFogLayerGroup.apply { setPosition(mirrorTile.x,mirrorTile.y) })
circleCrosshairFogLayers.add(mirrorTile.highlightCrosshairFogLayerGroup.apply { setPosition(mirrorTile.x,mirrorTile.y) })
}
}
}

View File

@ -106,7 +106,7 @@ class MapEditorScreen(): BaseScreen() {
if (isPainting) {
for (tileInfo in lastDrawnTiles)
mapHolder.tileGroups[tileInfo]!!.forEach { it.hideCircle() }
mapHolder.tileGroups[tileInfo]!!.forEach { it.hideHighlight() }
lastDrawnTiles.clear()
val stageCoords = mapHolder.actor.stageToLocalCoordinates(Vector2(event!!.stageX, event.stageY))
@ -120,7 +120,7 @@ class MapEditorScreen(): BaseScreen() {
tileInfo.setTerrainTransients()
mapHolder.tileGroups[tileInfo]!!.forEach {
it.update()
it.showCircle(Color.WHITE)
it.showHighlight(Color.WHITE)
}
lastDrawnTiles.add(tileInfo)

View File

@ -40,8 +40,8 @@ open class TileGroup(var tileInfo: TileInfo, val tileSetStrings:TileSetStrings,
Layers:
Base image (+ overlay)
Feature overlay / city overlay
Misc: Units, improvements, resources, border
Circle, Crosshair, Fog layer
Misc: Units, improvements, resources, border, arrows
Highlight, Crosshair, Fog layer
City name
*/
@ -121,9 +121,9 @@ open class TileGroup(var tileInfo: TileInfo, val tileSetStrings:TileSetStrings,
val cityButtonLayerGroup = Group().apply { isTransform = false; setSize(groupSize, groupSize)
touchable = Touchable.childrenOnly; setOrigin(Align.center) }
val circleCrosshairFogLayerGroup = ActionlessGroup().apply { isTransform = false; setSize(groupSize, groupSize) }
val circleImage = ImageGetter.getCircle() // for blue and red circles on the tile
private val crosshairImage = ImageGetter.getImage("OtherIcons/Crosshair") // for when a unit is targeted
val highlightCrosshairFogLayerGroup = ActionlessGroup().apply { isTransform = false; setSize(groupSize, groupSize) }
val highlightImage = ImageGetter.getImage(tileSetStrings.orFallback { getString(tileSetLocation, "Highlight") }) // for blue and red circles/emphasis on the tile
private val crosshairImage = ImageGetter.getImage(tileSetStrings.orFallback { getString(tileSetLocation, "Crosshair") }) // for when a unit is targeted
private val fogImage = ImageGetter.getImage(tileSetStrings.orFallback { crosshatchHexagon } )
/**
@ -161,14 +161,14 @@ open class TileGroup(var tileInfo: TileInfo, val tileSetStrings:TileSetStrings,
this.addActor(miscLayerGroup)
this.addActor(unitLayerGroup)
this.addActor(cityButtonLayerGroup)
this.addActor(circleCrosshairFogLayerGroup)
this.addActor(highlightCrosshairFogLayerGroup)
terrainFeatureLayerGroup.addActor(pixelMilitaryUnitGroup)
terrainFeatureLayerGroup.addActor(pixelCivilianUnitGroup)
updateTileImage(null)
addCircleImage()
addHighlightImage()
addFogImage()
addCrosshairImage()
isTransform = false // performance helper - nothing here is rotated or scaled
@ -178,34 +178,27 @@ open class TileGroup(var tileInfo: TileInfo, val tileSetStrings:TileSetStrings,
//region init functions
private fun addCircleImage() {
circleImage.width = 50f
circleImage.height = 50f
circleImage.center(this)
circleCrosshairFogLayerGroup.addActor(circleImage)
circleImage.isVisible = false
private fun addHighlightImage() {
highlightCrosshairFogLayerGroup.addActor(highlightImage)
setHexagonImageSize(highlightImage)
highlightImage.isVisible = false
}
private fun addFogImage() {
val imageScale = groupSize * 1.5f / fogImage.width
fogImage.setScale(imageScale)
fogImage.setOrigin(Align.center)
fogImage.center(this)
fogImage.color = Color.WHITE.cpy().apply { a = 0.2f }
circleCrosshairFogLayerGroup.addActor(fogImage)
highlightCrosshairFogLayerGroup.addActor(fogImage)
setHexagonImageSize(fogImage)
}
private fun addCrosshairImage() {
crosshairImage.width = 70f
crosshairImage.height = 70f
crosshairImage.center(this)
crosshairImage.isVisible = false
circleCrosshairFogLayerGroup.addActor(crosshairImage)
highlightCrosshairFogLayerGroup.addActor(crosshairImage)
setHexagonImageSize(crosshairImage)
}
//endregion
fun showCrosshair(color: Color) {
crosshairImage.color = color.cpy().apply { a = 0.5f }
fun showCrosshair(alpha: Float = 1f) {
crosshairImage.color.a = alpha
crosshairImage.isVisible = true
}
@ -254,7 +247,6 @@ open class TileGroup(var tileInfo: TileInfo, val tileSetStrings:TileSetStrings,
Parent should already be set when calling. */
private fun setHexagonImageSize(hexagonImage: Image) {
// Using "scale" can get really confusing when positioning, how about no
// TODO: Make as many images use this as possible— Standardized "Image on tile" placement for consistently moddable crosshairs, circles, etc.
hexagonImage.setSize(hexagonImageWidth, hexagonImage.height * hexagonImageWidth / hexagonImage.width)
hexagonImage.setOrigin(hexagonImageOrigin.first, hexagonImageOrigin.second)
hexagonImage.x = hexagonImagePosition.first
@ -339,7 +331,7 @@ open class TileGroup(var tileInfo: TileInfo, val tileSetStrings:TileSetStrings,
fogImage.isVisible = true
}
hideCircle()
hideHighlight()
if (viewingCiv != null && !isExplored(viewingCiv)) {
clearUnexploredTiles()
for(image in tileBaseImages) image.color = tileSetStrings.tileSetConfig.unexploredTileColor
@ -768,7 +760,7 @@ open class TileGroup(var tileInfo: TileInfo, val tileSetStrings:TileSetStrings,
/**
* Add an arrow to be drawn from this tile.
* Similar to [showCircle].
* Similar to [showHighlight].
*
* Zero-length arrows are ignored.
*
@ -785,18 +777,18 @@ open class TileGroup(var tileInfo: TileInfo, val tileSetStrings:TileSetStrings,
/**
* Clear all arrows to be drawn from this tile.
* Similar to [hideCircle].
* Similar to [hideHighlight].
*/
fun resetArrows() {
arrowsToDraw.clear()
}
fun showCircle(color: Color, alpha: Float = 0.3f) {
circleImage.isVisible = true
circleImage.color = color.cpy().apply { a = alpha }
fun showHighlight(color: Color, alpha: Float = 0.3f) {
highlightImage.isVisible = true
highlightImage.color = color.cpy().apply { a = alpha }
}
fun hideCircle() { circleImage.isVisible = false }
fun hideHighlight() { highlightImage.isVisible = false }
/** This exists so we can easily find the TileGroup draw method in the android profiling, otherwise it's just a mass of Group.draw->drawChildren->Group.draw etc. */
override fun draw(batch: Batch?, parentAlpha: Float) { super.draw(batch, parentAlpha) }

View File

@ -502,13 +502,13 @@ class WorldMapHolder(internal val worldScreen: WorldScreen, internal val tileMap
if (tileGroup.tileInfo.getShownImprovement(viewingCiv) == Constants.barbarianEncampment
&& tileGroup.tileInfo.position in viewingCiv.exploredTiles)
tileGroup.showCircle(Color.RED)
tileGroup.showHighlight(Color.RED)
val unitsInTile = tileGroup.tileInfo.getUnits()
val canSeeEnemy = unitsInTile.any() && unitsInTile.first().civInfo.isAtWarWith(viewingCiv)
&& tileGroup.showMilitaryUnit(viewingCiv)
if (tileGroup.isViewable(viewingCiv) && canSeeEnemy)
tileGroup.showCircle(Color.RED) // Display ALL viewable enemies with a red circle so that users don't need to go "hunting" for enemy units
tileGroup.showHighlight(Color.RED) // Display ALL viewable enemies with a red circle so that users don't need to go "hunting" for enemy units
}
val unitTable = worldScreen.bottomUnitTable
@ -531,7 +531,7 @@ class WorldMapHolder(internal val worldScreen: WorldScreen, internal val tileMap
val worldTileGroupsForSelectedTile = tileGroups[selectedTile]
if (worldTileGroupsForSelectedTile != null)
for (group in worldTileGroupsForSelectedTile)
group.showCircle(Color.WHITE)
group.showHighlight(Color.WHITE)
zoom(scaleX) // zoom to current scale, to set the size of the city buttons after "next turn"
}
@ -563,7 +563,7 @@ class WorldMapHolder(internal val worldScreen: WorldScreen, internal val tileMap
val swapUnitsTileOverlayColor = Color.PURPLE
for (tile in unitSwappableTiles) {
for (tileToColor in tileGroups[tile]!!) {
tileToColor.showCircle(swapUnitsTileOverlayColor,
tileToColor.showHighlight(swapUnitsTileOverlayColor,
if (UncivGame.Current.settings.singleTapMove) 0.7f else 0.3f)
}
}
@ -579,14 +579,14 @@ class WorldMapHolder(internal val worldScreen: WorldScreen, internal val tileMap
if (isAirUnit)
if (tile.aerialDistanceTo(unit.getTile()) <= unit.getRange()) {
// The tile is within attack range
tileToColor.showCircle(Color.RED, 0.3f)
tileToColor.showHighlight(Color.RED, 0.3f)
} else {
// The tile is within move range
tileToColor.showCircle(Color.BLUE, 0.3f)
tileToColor.showHighlight(Color.BLUE, 0.3f)
}
if (unit.movement.canMoveTo(tile) ||
unit.movement.isUnknownTileWeShouldAssumeToBePassable(tile) && !unit.baseUnit.movesLikeAirUnits())
tileToColor.showCircle(moveTileOverlayColor,
tileToColor.showHighlight(moveTileOverlayColor,
if (UncivGame.Current.settings.singleTapMove || isAirUnit) 0.7f else 0.3f)
}
}
@ -595,14 +595,14 @@ class WorldMapHolder(internal val worldScreen: WorldScreen, internal val tileMap
if (unitMovementPaths.containsKey(unit)) {
for (tile in unitMovementPaths[unit]!!) {
for (tileToColor in tileGroups[tile]!!)
tileToColor.showCircle(Color.SKY, 0.8f)
tileToColor.showHighlight(Color.SKY, 0.8f)
}
}
if (unit.isMoving()) {
val destinationTileGroups = tileGroups[unit.getMovementDestination()]!!
for (destinationTileGroup in destinationTileGroups)
destinationTileGroup.showCircle(Color.WHITE, 0.7f)
destinationTileGroup.showHighlight(Color.WHITE, 0.7f)
}
val attackableTiles: List<AttackableTile> = if (unit.isCivilian()) listOf()
@ -617,12 +617,12 @@ class WorldMapHolder(internal val worldScreen: WorldScreen, internal val tileMap
for (attackableTile in attackableTiles) {
for (tileGroupToAttack in tileGroups[attackableTile.tileToAttack]!!) {
tileGroupToAttack.showCircle(colorFromRGB(237, 41, 57))
tileGroupToAttack.showHighlight(colorFromRGB(237, 41, 57))
tileGroupToAttack.showCrosshair(
// the targets which cannot be attacked without movements shown as orange-ish
if (attackableTile.tileToAttackFrom != unit.currentTile)
colorFromRGB(255, 75, 0)
else Color.RED
0.5f
else 1f
)
}
}
@ -635,8 +635,8 @@ class WorldMapHolder(internal val worldScreen: WorldScreen, internal val tileMap
.filter { (UncivGame.Current.viewEntireMapForDebug || playerViewableTilePositions.contains(it.position)) }
for (attackableTile in attackableTiles) {
for (group in tileGroups[attackableTile]!!) {
group.showCircle(colorFromRGB(237, 41, 57))
group.showCrosshair(Color.RED)
group.showHighlight(colorFromRGB(237, 41, 57))
group.showCrosshair()
}
}
}
@ -685,9 +685,9 @@ class WorldMapHolder(internal val worldScreen: WorldScreen, internal val tileMap
removeAction(blinkAction) // so we don't have multiple blinks at once
blinkAction = Actions.repeat(3, Actions.sequence(
Actions.run { tileGroup.circleImage.isVisible = false },
Actions.run { tileGroup.highlightImage.isVisible = false },
Actions.delay(.3f),
Actions.run { tileGroup.circleImage.isVisible = true },
Actions.run { tileGroup.highlightImage.isVisible = true },
Actions.delay(.3f)
))
addAction(blinkAction) // Don't set it on the group because it's an actionless group