Skip to content

Commit 1a64b82

Browse files
authored
Cosmetic Form change, Battle Conditions UI, Tera Packet (#116)
* cosmetic form change, battle conditions ui, tera packet * exp all, more external transformations, 3 31 IVs on legends * fixes to previous commits * a bit of cleanup
1 parent 68c458a commit 1a64b82

File tree

51 files changed

+1969
-118
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

51 files changed

+1969
-118
lines changed

common/src/main/java/generations/gg/generations/core/generationscore/common/GenerationsCore.kt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,8 @@ import generations.gg.generations.core.generationscore.common.api.player.Caught
2121
import generations.gg.generations.core.generationscore.common.client.render.rarecandy.instanceOrNull
2222
import generations.gg.generations.core.generationscore.common.config.Config
2323
import generations.gg.generations.core.generationscore.common.config.ConfigLoader.loadConfig
24+
import generations.gg.generations.core.generationscore.common.event.GenerationsArchitecturyEvents
25+
import generations.gg.generations.core.generationscore.common.event.GenerationsCobblemonEvents
2426
import generations.gg.generations.core.generationscore.common.recipe.GenerationsIngredidents
2527
import generations.gg.generations.core.generationscore.common.world.container.GenerationsContainers
2628
import generations.gg.generations.core.generationscore.common.world.entity.GenerationsEntities
Lines changed: 326 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,326 @@
1+
package generations.gg.generations.core.generationscore.common.battle
2+
3+
import com.cobblemon.mod.common.api.battles.interpreter.BattleMessage
4+
import com.cobblemon.mod.common.api.battles.model.PokemonBattle
5+
import com.cobblemon.mod.common.api.battles.model.actor.BattleActor
6+
import com.cobblemon.mod.common.battles.BattleSide
7+
import com.cobblemon.mod.common.battles.actor.PlayerBattleActor
8+
import com.cobblemon.mod.common.battles.actor.PokemonBattleActor
9+
import com.cobblemon.mod.common.battles.actor.TrainerBattleActor
10+
import com.cobblemon.mod.common.entity.npc.NPCBattleActor
11+
import com.cobblemon.mod.common.util.getPlayer
12+
import generations.gg.generations.core.generationscore.common.network.packets.BattleConditionsPacket
13+
import java.util.UUID
14+
15+
object BattleConditionsProcessor {
16+
val conditionsDataMap = mutableMapOf<UUID, ConditionsData>()
17+
18+
@JvmStatic
19+
fun processAbility(battle: PokemonBattle, message: BattleMessage) {
20+
val conditionsData = conditionsDataMap[battle.battleId]
21+
22+
val abilityName = message.effectAt(1)?.id ?: return
23+
24+
var neutGasPresent = false
25+
battle.activePokemon.forEach { activePokemon ->
26+
val abilityName = activePokemon.battlePokemon?.originalPokemon?.ability?.name ?: return
27+
if (abilityName.isNeutGas()) neutGasPresent = true
28+
}
29+
30+
if (conditionsData != null) {
31+
val originalDisabled = conditionsData.weatherTracker.disabled
32+
33+
if (abilityName.canDisableWeather() && !neutGasPresent) {
34+
conditionsData.weatherTracker.disabled = true
35+
} else {
36+
conditionsData.weatherTracker.disabled = false
37+
}
38+
39+
if (conditionsData.weatherTracker.disabled != originalDisabled) {
40+
battle.sendToPlayersAndSpectators()
41+
}
42+
}
43+
}
44+
45+
@JvmStatic
46+
fun processWeatherDisabling(battle: PokemonBattle) {
47+
val conditionsData = conditionsDataMap[battle.battleId]
48+
var neutGasPresent = false
49+
var weatherDisablingAbility = false
50+
if (conditionsData != null) {
51+
battle.activePokemon.forEach { activePokemon ->
52+
val abilityName = activePokemon.battlePokemon?.originalPokemon?.ability?.name ?: return
53+
if (abilityName.isNeutGas()) neutGasPresent = true
54+
if (abilityName.canDisableWeather()) weatherDisablingAbility = true
55+
}
56+
57+
val originalDisabled = conditionsData.weatherTracker.disabled
58+
59+
if (weatherDisablingAbility && !neutGasPresent) {
60+
conditionsData.weatherTracker.disabled = true
61+
} else {
62+
conditionsData.weatherTracker.disabled = false
63+
}
64+
65+
if (conditionsData.weatherTracker.disabled != originalDisabled) {
66+
battle.sendToPlayersAndSpectators()
67+
}
68+
}
69+
}
70+
71+
@JvmStatic
72+
fun processFieldStart(battle: PokemonBattle, message: BattleMessage): String {
73+
val conditionsData = conditionsDataMap[battle.battleId]
74+
75+
val effect = processFieldMessage(message)
76+
77+
conditionsData?.fieldList?.removeIf { it.first.contains("Terrain") }
78+
conditionsData?.fieldList?.add(effect to 0) ?: return ""
79+
80+
battle.sendToPlayersAndSpectators()
81+
82+
return effect
83+
}
84+
85+
@JvmStatic
86+
fun processFieldEnd(battle: PokemonBattle, message: BattleMessage) {
87+
val conditionsData = conditionsDataMap[battle.battleId]
88+
val effect = processFieldMessage(message)
89+
if (conditionsData != null) {
90+
conditionsData.fieldList.removeIf { it.first == effect }
91+
battle.sendToPlayersAndSpectators()
92+
}
93+
}
94+
95+
@JvmStatic
96+
fun processSideStart(battle: PokemonBattle, message: BattleMessage) {
97+
val conditionsData = conditionsDataMap[battle.battleId]
98+
val sidePair = processSideMessage(message)
99+
100+
if (sidePair.first == "" || sidePair.second == "") return
101+
102+
val pSideRaw = sidePair.first
103+
val sideEffect = sidePair.second
104+
105+
val pSide = pSideRaw.take(2).substring(1)
106+
val pUUID = pSideRaw.substring(2).toUUIDFromPlainString()
107+
var playerName = "Unknown"
108+
109+
for (actor in battle.actors) {
110+
if (actor.uuid == pUUID) {
111+
playerName = actor.getTypeName()
112+
break
113+
}
114+
}
115+
116+
if (conditionsData != null) {
117+
val existing = conditionsData.sideList.find { it.side == pSide && it.effect == sideEffect }
118+
if (existing != null) {
119+
when (sideEffect) {
120+
"Spikes", "Toxic Spikes" -> {
121+
existing.layers++
122+
}
123+
}
124+
} else {
125+
val newData = BattleSideData(pSide, playerName, sideEffect, 0, 0)
126+
if (sideEffect == "Spikes" || sideEffect == "Toxic Spikes") {
127+
newData.layers = 1
128+
}
129+
conditionsData.sideList.add(newData)
130+
}
131+
132+
battle.sendToPlayersAndSpectators()
133+
}
134+
}
135+
136+
@JvmStatic
137+
fun processSideEnd(battle: PokemonBattle, message: BattleMessage) {
138+
val conditionsData = conditionsDataMap[battle.battleId]
139+
val sidePair = processSideMessage(message)
140+
val pSide = sidePair.first.take(2).substring(1)
141+
val sideEffect = sidePair.second
142+
if (conditionsData != null) {
143+
for (sideData in conditionsData.sideList) {
144+
if (sideData.side == pSide && sideData.effect == sideEffect) {
145+
conditionsData.sideList.remove(sideData)
146+
battle.sendToPlayersAndSpectators()
147+
break
148+
}
149+
}
150+
}
151+
}
152+
153+
@JvmStatic
154+
fun processSwapSideConditions(battle: PokemonBattle) {
155+
val conditionsData = conditionsDataMap[battle.battleId] ?: return
156+
157+
for (sideData in conditionsData.sideList) {
158+
when (sideData.side) {
159+
"1" -> {
160+
sideData.side = "2"
161+
sideData.playerName = getPlayerNameBySide(battle, battle.side2) ?: sideData.playerName
162+
}
163+
164+
"2" -> {
165+
sideData.side = "1"
166+
sideData.playerName = getPlayerNameBySide(battle, battle.side1) ?: sideData.playerName
167+
}
168+
}
169+
}
170+
171+
battle.sendToPlayersAndSpectators()
172+
}
173+
174+
@JvmStatic
175+
fun updateCounters(battle: PokemonBattle) {
176+
val conditionsData = conditionsDataMap[battle.battleId]
177+
if (conditionsData != null) {
178+
if (conditionsData.weatherTracker.weather != "") {
179+
conditionsData.weatherTracker.turns++
180+
}
181+
182+
for ((index, effectPair) in conditionsData.fieldList.withIndex()) {
183+
conditionsData.fieldList[index] = effectPair.first to (effectPair.second + 1)
184+
}
185+
186+
for ((index, sideData) in conditionsData.sideList.withIndex()) {
187+
if (!(sideData.effect.contains("Spikes") || sideData.effect == "Sticky Web" || sideData.effect == "Stealth Rock")) {
188+
conditionsData.sideList[index].turnCounter++
189+
}
190+
}
191+
192+
var neutGasPresent = false
193+
var weatherDisablingAbility = false
194+
battle.activePokemon.forEach { activePokemon ->
195+
val abilityName = activePokemon.battlePokemon?.originalPokemon?.ability?.name ?: return
196+
if (abilityName.isNeutGas()) neutGasPresent = true
197+
if (abilityName.canDisableWeather()) weatherDisablingAbility = true
198+
}
199+
200+
if (weatherDisablingAbility && !neutGasPresent) {
201+
conditionsData.weatherTracker.disabled = true
202+
} else {
203+
conditionsData.weatherTracker.disabled = false
204+
}
205+
206+
battle.sendToPlayersAndSpectators()
207+
}
208+
}
209+
210+
@JvmStatic
211+
fun processWeatherTurns(battle: PokemonBattle, message: BattleMessage) {
212+
val conditionsData = conditionsDataMap[battle.battleId]
213+
val weatherRaw = message.effectAt(0)?.id ?: return
214+
val weather = when (weatherRaw) {
215+
"raindance" -> "Rain"
216+
"sunnyday" -> "Sun"
217+
"sandstorm" -> "Sand"
218+
"hail" -> "Hail"
219+
"snow" -> "Snow"
220+
"deltastream" -> "Delta Stream"
221+
"desolateland" -> "Desolate Land"
222+
"primordialsea" -> "Primordial Sea"
223+
224+
else -> weatherRaw
225+
}
226+
227+
val weatherTracker = conditionsData?.weatherTracker ?: return
228+
weatherTracker.upkeep = message.hasOptionalArgument("upkeep")
229+
230+
if (weatherTracker.weather != weather) {
231+
weatherTracker.weather = weather
232+
weatherTracker.turns = 0
233+
battle.sendToPlayersAndSpectators()
234+
}
235+
}
236+
237+
@JvmStatic
238+
fun processBattleEnd(battle: PokemonBattle) {
239+
conditionsDataMap.remove(battle.battleId)
240+
}
241+
242+
fun processFieldMessage(message: BattleMessage): String {
243+
val effectRaw = message.effectAt(0)?.id ?: return ""
244+
return when {
245+
effectRaw.endsWith("terrain") -> {
246+
val name = effectRaw.removeSuffix("terrain").replaceFirstChar { it.uppercaseChar() }
247+
"$name Terrain"
248+
}
249+
250+
effectRaw == "gravity" -> "Gravity"
251+
252+
effectRaw.endsWith("room") -> {
253+
val name = effectRaw.removeSuffix("room").replaceFirstChar { it.uppercaseChar() }
254+
"$name Room"
255+
}
256+
257+
else -> effectRaw
258+
}
259+
}
260+
261+
fun processSideMessage(message: BattleMessage): Pair<String, String> {
262+
val pSideRaw = message.effectAt(0)?.id ?: return "" to ""
263+
val rawEffect = message.effectAt(1)?.id ?: return "" to ""
264+
val sideEffect = when (rawEffect) {
265+
"spikes" -> "Spikes"
266+
"stealthrock" -> "Stealth Rock"
267+
"stickyweb" -> "Sticky Web"
268+
"toxicspikes" -> "Toxic Spikes"
269+
270+
"auroraveil" -> "Aurora Veil"
271+
"lightscreen" -> "Light Screen"
272+
"reflect" -> "Reflect"
273+
274+
"luckychant" -> "Lucky Chant"
275+
"safeguard" -> "Safeguard"
276+
"tailwind" -> "Tailwind"
277+
278+
else -> rawEffect
279+
}
280+
return pSideRaw to sideEffect
281+
}
282+
283+
fun String.toUUIDFromPlainString(): UUID {
284+
return UUID.fromString(
285+
"${this.substring(0, 8)}-${this.substring(8, 12)}-${this.substring(12, 16)}-${
286+
this.substring(
287+
16,
288+
20
289+
)
290+
}-${this.substring(20)}"
291+
)
292+
}
293+
294+
fun String.canDisableWeather(): Boolean {
295+
return this == "airlock" || this == "cloudnine"
296+
}
297+
298+
fun String.isNeutGas(): Boolean {
299+
return this == "neutralizinggas"
300+
}
301+
302+
fun PokemonBattle.sendToPlayersAndSpectators() {
303+
val conditionsData = conditionsDataMap[this.battleId] ?: return
304+
this.sendToActors(BattleConditionsPacket(true, conditionsData.copy()))
305+
this.sendSpectatorUpdate(BattleConditionsPacket(false, conditionsData.copy()))
306+
}
307+
308+
fun getPlayerNameBySide(battle: PokemonBattle, side: BattleSide): String? {
309+
for (actor in battle.actors) {
310+
if (side.actors.contains(actor)) {
311+
return actor.getTypeName()
312+
}
313+
}
314+
return null
315+
}
316+
317+
fun BattleActor.getTypeName(): String {
318+
return when (this) {
319+
is PlayerBattleActor -> this.uuid.getPlayer()?.name?.string ?: "Unknown"
320+
is PokemonBattleActor -> this.pokemon.originalPokemon.species.name
321+
is TrainerBattleActor -> this.trainerName
322+
is NPCBattleActor -> this.npc.name.string ?: "Unknown"
323+
else -> "Unknown"
324+
}
325+
}
326+
}
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
package generations.gg.generations.core.generationscore.common.battle
2+
3+
import java.util.UUID
4+
5+
data class ConditionsData (
6+
val weatherTracker: WeatherTracker = WeatherTracker(),
7+
val fieldList: MutableList<Pair<String, Int>> = mutableListOf<Pair<String, Int>>(),
8+
val sideList: MutableList<BattleSideData> = mutableListOf<BattleSideData>(),
9+
)
10+
11+
data class BattleSideData(
12+
var side: String = "",
13+
var playerName: String = "",
14+
var effect: String = "",
15+
var layers: Int = 0,
16+
var turnCounter: Int = 0
17+
)
18+
19+
data class WeatherTracker(
20+
var weather: String = "",
21+
var turns: Int = 0,
22+
var upkeep: Boolean = false,
23+
var disabled: Boolean = false
24+
25+
)
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
package generations.gg.generations.core.generationscore.common.battle
2+
3+
import com.cobblemon.mod.common.api.battles.model.PokemonBattle
4+
import com.cobblemon.mod.common.api.battles.model.actor.BattleActor
5+
import com.cobblemon.mod.common.battles.pokemon.BattlePokemon
6+
import generations.gg.generations.core.generationscore.common.world.item.GenerationsItems
7+
import net.minecraft.server.level.ServerPlayer
8+
import net.minecraft.world.item.ItemStack
9+
10+
object ExpAllCalculator {
11+
fun BattlePokemon.isFainted(): Boolean {
12+
var isFainted = false
13+
if (this.health <= 0) {
14+
isFainted = true
15+
}
16+
return isFainted
17+
}
18+
19+
fun BattlePokemon.calculateMultiplier(): Double {
20+
val hasParticipated = this.facedOpponents.isNotEmpty()
21+
var multiplier = 1.0
22+
if (!hasParticipated) {
23+
multiplier = 0.5
24+
}
25+
return multiplier
26+
}
27+
28+
fun ServerPlayer.hasExpAll(): Boolean {
29+
if (this.inventory.items.any { it.item == GenerationsItems.EXP_ALL.value() } || this.offhandItem.`is`(GenerationsItems.EXP_ALL.value())) {
30+
return true
31+
}
32+
33+
return false
34+
}
35+
}

0 commit comments

Comments
 (0)