Fix gacha avatars (fixes #1870)

This commit is contained in:
AnimeGitB 2022-10-18 15:11:10 +10:30
parent 85f44ebdf3
commit aacf013c06
5 changed files with 49 additions and 14 deletions

View File

@ -1,6 +1,7 @@
package emu.grasscutter.data.excels; package emu.grasscutter.data.excels;
import java.util.List; import java.util.List;
import java.util.Optional;
import java.util.stream.IntStream; import java.util.stream.IntStream;
import emu.grasscutter.data.GameData; import emu.grasscutter.data.GameData;
@ -36,6 +37,7 @@ public class AvatarSkillDepotData extends GameResource {
@Getter private AvatarSkillData energySkillData; @Getter private AvatarSkillData energySkillData;
@Getter private ElementType elementType; @Getter private ElementType elementType;
@Getter private IntList abilities; @Getter private IntList abilities;
@Getter private int talentCostItemId;
@Override @Override
public int getId() { public int getId() {
@ -66,6 +68,13 @@ public class AvatarSkillDepotData extends GameResource {
this.setAbilities(new AbilityEmbryoEntry(getSkillDepotAbilityGroup(), config.abilities.stream().map(Object::toString).toArray(String[]::new))); this.setAbilities(new AbilityEmbryoEntry(getSkillDepotAbilityGroup(), config.abilities.stream().map(Object::toString).toArray(String[]::new)));
} }
} }
// Get constellation item from GameData
Optional.ofNullable(this.talents)
.map(talents -> talents.get(0))
.map(i -> GameData.getAvatarTalentDataMap().get((int) i))
.map(talentData -> talentData.getMainCostItemId())
.ifPresent(itemId -> this.talentCostItemId = itemId);
} }
public static class InherentProudSkillOpens { public static class InherentProudSkillOpens {

View File

@ -2,6 +2,7 @@ package emu.grasscutter.data.excels;
import java.util.Arrays; import java.util.Arrays;
import java.util.List; import java.util.List;
import java.util.Objects;
import com.google.gson.annotations.SerializedName; import com.google.gson.annotations.SerializedName;
import emu.grasscutter.data.GameResource; import emu.grasscutter.data.GameResource;
@ -133,6 +134,7 @@ public class ItemData extends GameResource {
this.itemUseActions = this.itemUse.stream() this.itemUseActions = this.itemUse.stream()
.filter(x -> x.getUseOp() != ItemUseOp.ITEM_USE_NONE) .filter(x -> x.getUseOp() != ItemUseOp.ITEM_USE_NONE)
.map(ItemUseAction::fromItemUseData) .map(ItemUseAction::fromItemUseData)
.filter(Objects::nonNull)
.toList(); .toList();
} }
} }

View File

@ -316,10 +316,10 @@ public class GachaSystem extends BaseGameSystem {
pools.removeFromAllPools(new int[] {itemId}); pools.removeFromAllPools(new int[] {itemId});
} }
addStarglitter = (itemData.getRankLevel()==5)? 10 : 2; addStarglitter = (itemData.getRankLevel()==5)? 10 : 2;
int constItemId = itemId + 100; int constItemId = itemId + 100; // This may not hold true for future characters. Examples of strictly correct constellation item lookup are elsewhere for now.
GameItem constItem = inventory.getInventoryTab(ItemType.ITEM_MATERIAL).getItemById(constItemId); boolean haveConstItem = inventory.getInventoryTab(ItemType.ITEM_MATERIAL).getItemById(constItemId) == null;
gachaItem.addTransferItems(GachaTransferItem.newBuilder().setItem(ItemParam.newBuilder().setItemId(constItemId).setCount(1)).setIsTransferItemNew(constItem == null)); gachaItem.addTransferItems(GachaTransferItem.newBuilder().setItem(ItemParam.newBuilder().setItemId(constItemId).setCount(1)).setIsTransferItemNew(haveConstItem));
inventory.addItem(constItemId, 1); //inventory.addItem(constItemId, 1); // This is now managed by the avatar card item itself
} }
isTransferItem = true; isTransferItem = true;
break; break;

View File

@ -1,5 +1,7 @@
package emu.grasscutter.game.props.ItemUseAction; package emu.grasscutter.game.props.ItemUseAction;
import java.util.Optional;
import emu.grasscutter.game.avatar.Avatar; import emu.grasscutter.game.avatar.Avatar;
import emu.grasscutter.game.props.ItemUseOp; import emu.grasscutter.game.props.ItemUseOp;
import emu.grasscutter.game.systems.InventorySystem; import emu.grasscutter.game.systems.InventorySystem;
@ -36,7 +38,10 @@ public class ItemUseGainAvatar extends ItemUseInt {
params.player.addAvatar(avatar); params.player.addAvatar(avatar);
return true; return true;
} else { } else {
int itemId = (this.i % 1000) + 100; int itemId = Optional.ofNullable(params.player.getAvatars().getAvatarById(this.i))
.map(Avatar::getSkillDepot)
.map(depot -> depot.getTalentCostItemId())
.orElse((this.i % 1000) + 100);
return params.player.getInventory().addItem(itemId); return params.player.getInventory().addItem(itemId);
} }
} }

View File

@ -8,7 +8,6 @@ import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Objects; import java.util.Objects;
import java.util.Optional; import java.util.Optional;
import java.util.stream.Collectors;
import java.util.stream.Stream; import java.util.stream.Stream;
import emu.grasscutter.Grasscutter; import emu.grasscutter.Grasscutter;
@ -799,18 +798,38 @@ public class InventorySystem extends BaseGameSystem {
.reduce(false, (a,b) -> a || b); // Don't short-circuit!!! .reduce(false, (a,b) -> a || b); // Don't short-circuit!!!
} }
public static synchronized int checkPlayerAvatarConstellationLevel(Player player, int itemId) { public static synchronized int checkPlayerAvatarConstellationLevel(Player player, int id) {
ItemData itemData = GameData.getItemDataMap().get(itemId); // Try to accept itemId OR avatarId
if ((itemData == null) || (itemData.getMaterialType() != MaterialType.MATERIAL_AVATAR)) { int avatarId = 0;
if (GameData.getAvatarDataMap().containsKey(id)) {
avatarId = id;
} else {
avatarId = Optional.ofNullable(GameData.getItemDataMap().get(id))
.map(itemData -> itemData.getItemUseActions())
.flatMap(actions ->
actions.stream()
.filter(action -> action.getItemUseOp() == ItemUseOp.ITEM_USE_GAIN_AVATAR)
.map(action -> ((emu.grasscutter.game.props.ItemUseAction.ItemUseGainAvatar) action).getI())
.findFirst())
.orElse(0);
}
if (avatarId == 0)
return -2; // Not an Avatar return -2; // Not an Avatar
}
Avatar avatar = player.getAvatars().getAvatarById((itemId % 1000) + 10000000); Avatar avatar = player.getAvatars().getAvatarById(avatarId);
if (avatar == null) { if (avatar == null)
return -1; // Doesn't have return -1; // Doesn't have
}
// Constellation // Constellation
int constLevel = avatar.getCoreProudSkillLevel(); int constLevel = avatar.getCoreProudSkillLevel();
GameItem constItem = player.getInventory().getInventoryTab(ItemType.ITEM_MATERIAL).getItemById(itemId + 100); val avatarData = avatar.getSkillDepot();
if (avatarData == null) {
Grasscutter.getLogger().error("Attempted to check constellation level for UID"+player.getUid()+"'s avatar "+avatarId+" but avatar has no skillDepot!");
return 0;
}
int constItemId = avatarData.getTalentCostItemId();
GameItem constItem = player.getInventory().getInventoryTab(ItemType.ITEM_MATERIAL).getItemById(constItemId);
constLevel += Optional.ofNullable(constItem).map(GameItem::getCount).orElse(0); constLevel += Optional.ofNullable(constItem).map(GameItem::getCount).orElse(0);
return constLevel; return constLevel;
} }