auto qol hunters button conflict resolution

This commit is contained in:
radimous 2024-12-04 22:34:06 +01:00
parent 1ef461ab37
commit d2969663bc
6 changed files with 88 additions and 60 deletions

View file

@ -8,21 +8,17 @@ public class Config {
public static final ForgeConfigSpec.BooleanValue ALLOW_DUPE; public static final ForgeConfigSpec.BooleanValue ALLOW_DUPE;
public static final ForgeConfigSpec.IntValue BUTTON_X; public static final ForgeConfigSpec.IntValue BUTTON_X;
public static final ForgeConfigSpec.IntValue BUTTON_Y; public static final ForgeConfigSpec.IntValue BUTTON_Y;
public static final ForgeConfigSpec.BooleanValue COMBINE_LVL_TO_ABILITIES;
public static final ForgeConfigSpec.IntValue MAX_LEVEL_OVERRIDE; public static final ForgeConfigSpec.IntValue MAX_LEVEL_OVERRIDE;
public static final ForgeConfigSpec.BooleanValue SHOW_ABILITY_ENHANCEMENTS; public static final ForgeConfigSpec.BooleanValue SHOW_ABILITY_ENHANCEMENTS;
public static final ForgeConfigSpec.BooleanValue SHOW_WEIGHT; public static final ForgeConfigSpec.BooleanValue SHOW_WEIGHT;
public static final ForgeConfigSpec.BooleanValue SHOW_CHANCE; public static final ForgeConfigSpec.BooleanValue SHOW_CHANCE;
public static final ForgeConfigSpec.BooleanValue QOL_HUNTERS_CONFLICT_RESOLUTION;
static { static {
ForgeConfigSpec.Builder builder = new ForgeConfigSpec.Builder(); ForgeConfigSpec.Builder builder = new ForgeConfigSpec.Builder();
COMBINE_LVL_TO_ABILITIES = builder builder.push("BUTTON");
.comment("combine +lvl to abilities into one row")
.define("combineAddedLvlToAbilities", false);
builder.push("BUTTON");
VAULT_SCREEN_BUTTON = builder VAULT_SCREEN_BUTTON = builder
.comment("open VHat can I roll? from vault screen") .comment("open VHat can I roll? from vault screen")
.define("vaultScreenButton", true); .define("vaultScreenButton", true);
@ -30,7 +26,6 @@ public class Config {
.comment("x position of the button") .comment("x position of the button")
.defineInRange("buttonPositionX", 5, Integer.MIN_VALUE, Integer.MAX_VALUE); .defineInRange("buttonPositionX", 5, Integer.MIN_VALUE, Integer.MAX_VALUE);
//TODO: auto move the button to 130 if QOL Hunters is loaded (button conflict)
BUTTON_Y = builder BUTTON_Y = builder
.comment("y position of the button") .comment("y position of the button")
.defineInRange("buttonPositionY", 109, Integer.MIN_VALUE, Integer.MAX_VALUE); .defineInRange("buttonPositionY", 109, Integer.MIN_VALUE, Integer.MAX_VALUE);
@ -40,6 +35,9 @@ public class Config {
ALLOW_DUPE = builder ALLOW_DUPE = builder
.comment("allow duplicate modifiers") .comment("allow duplicate modifiers")
.define("allowDupe", false); .define("allowDupe", false);
QOL_HUNTERS_CONFLICT_RESOLUTION = builder
.comment("QOL Hunters conflict resolution")
.define("QOLHuntersConflictResolution", true);
builder.pop(); builder.pop();
MAX_LEVEL_OVERRIDE = builder MAX_LEVEL_OVERRIDE = builder

View file

@ -0,0 +1,41 @@
package com.radimous.vhatcaniroll;
import net.minecraftforge.common.ForgeConfigSpec;
public class QOLHuntersCompat {
private static boolean qolHuntersLoaded = true;
private static ForgeConfigSpec.BooleanValue qolConfigButton = null;
public static void resolveQOLHuntersButtonConflict(){
if(!Config.QOL_HUNTERS_CONFLICT_RESOLUTION.get()){
// just for debugging or if it blows up
return;
}
if (!qolHuntersLoaded) {
if (Config.BUTTON_Y.get() == 130) {
Config.BUTTON_Y.set(109);
}
return;
}
if (qolConfigButton == null) {
// use reflection to avoid a million dependencies
try {
var cl = Class.forName("io.iridium.qolhunters.config.QOLHuntersClientConfigs");
var qolButton = cl.getField("SHOW_CONFIG_BUTTON").get(null);
qolConfigButton = (ForgeConfigSpec.BooleanValue) qolButton;
} catch (NoSuchFieldException | ClassNotFoundException | IllegalAccessException e) {
qolHuntersLoaded = false;
}
}
// if qol button, move our button down
if (qolConfigButton != null && qolConfigButton.get() && Config.BUTTON_Y.get() == 109) {
Config.BUTTON_Y.set(130);
}
// if no qol button, move our button up
if ((qolConfigButton == null || !qolConfigButton.get()) && Config.BUTTON_Y.get() == 130) {
Config.BUTTON_Y.set(109);
}
}
}

View file

@ -60,9 +60,9 @@ public class Modifiers {
componentList.add(new TextComponent(affixTagGroup.toString().replace("_", " ")).withStyle(ChatFormatting.BOLD)); componentList.add(new TextComponent(affixTagGroup.toString().replace("_", " ")).withStyle(ChatFormatting.BOLD));
int totalWeight = modifierGroup.get(affixTagGroup).stream() int totalWeight = modifierGroup.get(affixTagGroup).stream()
.mapToInt(x -> getModifierTiers(lvl, x).stream().mapToInt(VaultGearTierConfig.ModifierTier::getWeight).sum()) .mapToInt(x -> getModifierTiers(lvl, x, modifierCategory).stream().mapToInt(VaultGearTierConfig.ModifierTier::getWeight).sum())
.sum(); .sum();
if (Config.SHOW_WEIGHT.get()) { if (Config.SHOW_WEIGHT.get() && modifierCategory == ModifierCategory.NORMAL) {
componentList.add(new TextComponent("Total Weight: " + totalWeight).withStyle(ChatFormatting.BOLD)); componentList.add(new TextComponent("Total Weight: " + totalWeight).withStyle(ChatFormatting.BOLD));
} }
@ -73,21 +73,24 @@ public class Modifiers {
for (VaultGearTierConfig.ModifierTierGroup modifierTierGroup : modifierGroup.get(affixTagGroup)) { for (VaultGearTierConfig.ModifierTierGroup modifierTierGroup : modifierGroup.get(affixTagGroup)) {
ArrayList<VaultGearTierConfig.ModifierTier<?>> mTierList; ArrayList<VaultGearTierConfig.ModifierTier<?>> mTierList;
// TODO: support greater modifiers (greater is +1 tier, legendary is +2 tiers) (look how VH does it) mTierList = getModifierTiers(lvl, modifierTierGroup, modifierCategory);
// maybe ENUM - NORMAL, GREATER, LEGENDARY and the button would cycle through them
if (modifierCategory.getTierIncrease() > 0) {
mTierList = getIncreasedModifierTiers(lvl, modifierTierGroup, modifierCategory);
} else {
mTierList = getModifierTiers(lvl, modifierTierGroup);
}
if (mTierList.isEmpty()) { if (mTierList.isEmpty()) {
continue; continue;
} }
String modGr = modifierTierGroup.getModifierGroup(); String modGr = modifierTierGroup.getModifierGroup();
Component newMod = getModifierComponent(VaultGearAttributeRegistry.getAttribute(modifierTierGroup.getAttribute()),mTierList); MutableComponent newMod = getModifierComponent(VaultGearAttributeRegistry.getAttribute(modifierTierGroup.getAttribute()),mTierList);
int weight = modTierListWeight(mTierList);
if (Config.SHOW_WEIGHT.get() && modifierCategory == ModifierCategory.NORMAL) {
newMod.append(new TextComponent(" w"+weight).withStyle(ChatFormatting.GRAY));
}
if (Config.SHOW_CHANCE.get() && modifierCategory == ModifierCategory.NORMAL) {
newMod.append(new TextComponent(String.format(" %.2f%%", ((double) weight * 100 / totalWeight))).withStyle(ChatFormatting.GRAY));
}
if (groupCounts.get(modGr) > 1) { if (groupCounts.get(modGr) > 1) {
groupedModifiers.computeIfAbsent(modGr, k -> new ArrayList<>()).add(newMod); groupedModifiers.computeIfAbsent(modGr, k -> new ArrayList<>()).add(newMod);
continue; continue;
@ -97,15 +100,6 @@ public class Modifiers {
full.append(newMod); full.append(newMod);
int weight = modTierListWeight(mTierList);
if (Config.SHOW_WEIGHT.get()) {
full.append(" w"+weight);
}
if (Config.SHOW_CHANCE.get()) {
full.append(String.format(" %.2f%%", ((double) weight * 100 / totalWeight)));
}
if (Config.ALLOW_DUPE.get() || !(componentList.get(componentList.size() - 1).getString()).equals(full.getString())) { //dumb way to fix ability lvl+ duplication if (Config.ALLOW_DUPE.get() || !(componentList.get(componentList.size() - 1).getString()).equals(full.getString())) { //dumb way to fix ability lvl+ duplication
componentList.add(full); componentList.add(full);
} }
@ -132,11 +126,7 @@ public class Modifiers {
Map<String, Integer> groupCounts = new HashMap<>(); Map<String, Integer> groupCounts = new HashMap<>();
for (VaultGearTierConfig.ModifierTierGroup modifierTierGroup : modifierGroup.get(affixTagGroup)) { for (VaultGearTierConfig.ModifierTierGroup modifierTierGroup : modifierGroup.get(affixTagGroup)) {
ArrayList<VaultGearTierConfig.ModifierTier<?>> mTierList; ArrayList<VaultGearTierConfig.ModifierTier<?>> mTierList;
if (modifierCategory.getTierIncrease() > 0) { mTierList = getModifierTiers(lvl, modifierTierGroup, modifierCategory);
mTierList = getIncreasedModifierTiers(lvl, modifierTierGroup, modifierCategory);
} else {
mTierList = getModifierTiers(lvl, modifierTierGroup);
}
if (mTierList.isEmpty()) { if (mTierList.isEmpty()) {
continue; continue;
} }
@ -147,8 +137,12 @@ public class Modifiers {
} }
//TODO: check how noLegendary works in VH //TODO: check how noLegendary works in VH
private static ArrayList<VaultGearTierConfig.ModifierTier<?>> getIncreasedModifierTiers(int lvl, private static ArrayList<VaultGearTierConfig.ModifierTier<?>> getModifierTiers(int lvl,
VaultGearTierConfig.ModifierTierGroup modifierTierGroup, ModifierCategory modifierCategory) { VaultGearTierConfig.ModifierTierGroup modifierTierGroup, ModifierCategory modifierCategory) {
if (modifierCategory == ModifierCategory.NORMAL) {
return getNormalModifierTiers(lvl, modifierTierGroup);
}
var res = new ArrayList<VaultGearTierConfig.ModifierTier<?>>(); var res = new ArrayList<VaultGearTierConfig.ModifierTier<?>>();
var highest = modifierTierGroup.getHighestForLevel(lvl); var highest = modifierTierGroup.getHighestForLevel(lvl);
@ -167,8 +161,8 @@ public class Modifiers {
res.add(legendTier); res.add(legendTier);
return res; // only one return res; // only one
} }
@NotNull private static ArrayList<VaultGearTierConfig.ModifierTier<?>> getModifierTiers(int lvl, @NotNull private static ArrayList<VaultGearTierConfig.ModifierTier<?>> getNormalModifierTiers(int lvl,
VaultGearTierConfig.ModifierTierGroup modifierTierGroup) { VaultGearTierConfig.ModifierTierGroup modifierTierGroup) {
return modifierTierGroup.getModifiersForLevel(lvl).stream() return modifierTierGroup.getModifiersForLevel(lvl).stream()
.filter(x -> x.getWeight() != 0 .filter(x -> x.getWeight() != 0
&& !(x.getModifierConfiguration() instanceof BooleanFlagGenerator.BooleanFlag bf && && !(x.getModifierConfiguration() instanceof BooleanFlagGenerator.BooleanFlag bf &&
@ -177,7 +171,7 @@ public class Modifiers {
} }
@SuppressWarnings("unchecked") // I don't think proper generics are possible, VaultGearTierConfig#getModifiersForLevel returns List<ModifierTier<?>> @SuppressWarnings("unchecked") // I don't think proper generics are possible, VaultGearTierConfig#getModifiersForLevel returns List<ModifierTier<?>>
private static <T, C> Component getModifierComponent(VaultGearAttribute<T> atr, private static <T, C> MutableComponent getModifierComponent(VaultGearAttribute<T> atr,
ArrayList<VaultGearTierConfig.ModifierTier<?>> modifierTiers) { ArrayList<VaultGearTierConfig.ModifierTier<?>> modifierTiers) {
if (modifierTiers.isEmpty()) { if (modifierTiers.isEmpty()) {
return new TextComponent("ERR - EMPTY MODIFIER TIERS"); return new TextComponent("ERR - EMPTY MODIFIER TIERS");
@ -269,10 +263,6 @@ public class Modifiers {
private static MutableComponent abilityLvlComponent(MutableComponent res, VaultGearAttribute<?> atr, private static MutableComponent abilityLvlComponent(MutableComponent res, VaultGearAttribute<?> atr,
AbilityLevelAttribute.Config minConfig) { AbilityLevelAttribute.Config minConfig) {
if (Config.COMBINE_LVL_TO_ABILITIES.get()) {
return res.append(" added ability levels").withStyle(atr.getReader().getColoredTextStyle());
}
var abComp = new TextComponent("+").withStyle(atr.getReader().getColoredTextStyle()); var abComp = new TextComponent("+").withStyle(atr.getReader().getColoredTextStyle());
var optSkill = ModConfigs.ABILITIES.getAbilityById(minConfig.getAbilityKey()); var optSkill = ModConfigs.ABILITIES.getAbilityById(minConfig.getAbilityKey());
if (optSkill.isEmpty()) { if (optSkill.isEmpty()) {

View file

@ -1,6 +1,7 @@
package com.radimous.vhatcaniroll.mixin; package com.radimous.vhatcaniroll.mixin;
import com.radimous.vhatcaniroll.Config; import com.radimous.vhatcaniroll.Config;
import com.radimous.vhatcaniroll.QOLHuntersCompat;
import com.radimous.vhatcaniroll.ui.GearModifierScreen; import com.radimous.vhatcaniroll.ui.GearModifierScreen;
import iskallia.vault.client.gui.framework.ScreenTextures; import iskallia.vault.client.gui.framework.ScreenTextures;
import iskallia.vault.client.gui.framework.element.ButtonElement; import iskallia.vault.client.gui.framework.element.ButtonElement;
@ -20,6 +21,7 @@ import net.minecraft.network.chat.TextComponent;
import net.minecraft.sounds.SoundEvents; import net.minecraft.sounds.SoundEvents;
import net.minecraft.world.entity.player.Inventory; import net.minecraft.world.entity.player.Inventory;
import net.minecraft.world.item.ItemStack; import net.minecraft.world.item.ItemStack;
import net.minecraftforge.common.ForgeConfigSpec;
import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow; import org.spongepowered.asm.mixin.Shadow;
import org.spongepowered.asm.mixin.injection.At; import org.spongepowered.asm.mixin.injection.At;
@ -42,6 +44,8 @@ public class StatisticsElementContainerScreenMixin extends AbstractSkillTabEleme
// TODO: figure out how to add button like the quest button, not this ugly shit // TODO: figure out how to add button like the quest button, not this ugly shit
QOLHuntersCompat.resolveQOLHuntersButtonConflict();
// add blank button to vault screen // add blank button to vault screen
this.addElement( this.addElement(
new ButtonElement<>(Spatials.positionXY(-3, 3), ScreenTextures.BUTTON_EMPTY_16_TEXTURES, () -> { new ButtonElement<>(Spatials.positionXY(-3, 3), ScreenTextures.BUTTON_EMPTY_16_TEXTURES, () -> {
@ -56,8 +60,9 @@ public class StatisticsElementContainerScreenMixin extends AbstractSkillTabEleme
}) })
); );
// add chestplate icon to it // add chestplate icon to it
var chestplateStack = new ItemStack(ModItems.CHESTPLATE);
this.addElement( this.addElement(
new FakeItemSlotElement<>(Spatials.positionXY(-3, 3), () -> new ItemStack(ModItems.CHESTPLATE), () -> false, ScreenTextures.EMPTY, ScreenTextures.EMPTY new FakeItemSlotElement<>(Spatials.positionXY(-3, 3), () -> chestplateStack, () -> false, ScreenTextures.EMPTY, ScreenTextures.EMPTY
).layout( ).layout(
(screen, gui, parent, world) -> world.width(21).height(21).translateX(gui.right() + Config.BUTTON_X.get()).translateY(this.getTabContentSpatial().bottom() + Config.BUTTON_Y.get()) (screen, gui, parent, world) -> world.width(21).height(21).translateX(gui.right() + Config.BUTTON_X.get()).translateY(this.getTabContentSpatial().bottom() + Config.BUTTON_Y.get())
) )

View file

@ -1,7 +1,6 @@
package com.radimous.vhatcaniroll.ui; package com.radimous.vhatcaniroll.ui;
import com.mojang.blaze3d.platform.InputConstants; import com.mojang.blaze3d.platform.InputConstants;
import com.radimous.vhatcaniroll.Config;
import com.radimous.vhatcaniroll.logic.Items; import com.radimous.vhatcaniroll.logic.Items;
import com.radimous.vhatcaniroll.logic.ModifierCategory; import com.radimous.vhatcaniroll.logic.ModifierCategory;
@ -71,7 +70,7 @@ public class GearModifierScreen extends AbstractElementScreen {
this.lvlInput = this.addElement(createLvlInput()); this.lvlInput = this.addElement(createLvlInput());
createLvlButtons(lvlInput); createLvlButtons(lvlInput);
createLegendaryButton(); createModifierCategoryButton();
// inner black window // inner black window
ISpatial modListSpatial = Spatials.positionXY(7, 50).size(this.getGuiSpatial().width() - 14, this.getGuiSpatial().height() - 57); ISpatial modListSpatial = Spatials.positionXY(7, 50).size(this.getGuiSpatial().width() - 14, this.getGuiSpatial().height() - 57);
@ -187,7 +186,6 @@ public class GearModifierScreen extends AbstractElementScreen {
this.translateWorldSpatial())); this.translateWorldSpatial()));
} }
// header // header
private ScrollableLvlInputElement createLvlInput() { private ScrollableLvlInputElement createLvlInput() {
@ -224,11 +222,11 @@ public class GearModifierScreen extends AbstractElementScreen {
private void cycleModifierCategories() { private void cycleModifierCategories() {
this.modifierCategory = modifierCategory.next(); this.modifierCategory = modifierCategory.next();
updateModifierCategoryLabel(); updateModifierCategoryButtonLabel();
updateModifierList(true); updateModifierList(true);
} }
private void updateModifierCategoryLabel() { private void updateModifierCategoryButtonLabel() {
if (this.modifierCategoryLabel != null) { if (this.modifierCategoryLabel != null) {
this.removeElement(this.modifierCategoryLabel); this.removeElement(this.modifierCategoryLabel);
} }
@ -238,8 +236,8 @@ public class GearModifierScreen extends AbstractElementScreen {
this.addElement(modifierCategoryLabel); this.addElement(modifierCategoryLabel);
} }
private void createLegendaryButton() { private void createModifierCategoryButton() {
updateModifierCategoryLabel(); updateModifierCategoryButtonLabel();
NineSliceButtonElement<?> btnLegend = NineSliceButtonElement<?> btnLegend =
new NineSliceButtonElement<>(Spatials.positionXY(this.getGuiSpatial().width() - 8 - 13, 35).size(14, 14), new NineSliceButtonElement<>(Spatials.positionXY(this.getGuiSpatial().width() - 8 - 13, 35).size(14, 14),
ScreenTextures.BUTTON_EMPTY_TEXTURES, this::cycleModifierCategories).layout(this.translateWorldSpatial()); ScreenTextures.BUTTON_EMPTY_TEXTURES, this::cycleModifierCategories).layout(this.translateWorldSpatial());
@ -274,11 +272,6 @@ public class GearModifierScreen extends AbstractElementScreen {
if (keyCode == InputConstants.KEY_LCONTROL || keyCode == InputConstants.KEY_RCONTROL) { if (keyCode == InputConstants.KEY_LCONTROL || keyCode == InputConstants.KEY_RCONTROL) {
cycleModifierCategories(); cycleModifierCategories();
} }
// ctrl + , to toggle compact +lvl to abilities
if (keyCode == InputConstants.KEY_COMMA && hasControlDown()) {
Config.COMBINE_LVL_TO_ABILITIES.set(!Config.COMBINE_LVL_TO_ABILITIES.get());
updateModifierList(true);
}
return super.keyPressed(keyCode, scanCode, modifiers); return super.keyPressed(keyCode, scanCode, modifiers);
} }
} }

View file

@ -9,6 +9,7 @@ import iskallia.vault.client.gui.framework.spatial.Spatials;
import iskallia.vault.client.gui.framework.spatial.spi.ISpatial; import iskallia.vault.client.gui.framework.spatial.spi.ISpatial;
import iskallia.vault.client.gui.framework.text.LabelTextStyle; import iskallia.vault.client.gui.framework.text.LabelTextStyle;
import iskallia.vault.config.gear.VaultGearTierConfig; import iskallia.vault.config.gear.VaultGearTierConfig;
import net.minecraft.ChatFormatting;
import net.minecraft.network.chat.TextComponent; import net.minecraft.network.chat.TextComponent;
import net.minecraft.world.item.ItemStack; import net.minecraft.world.item.ItemStack;
@ -29,7 +30,7 @@ public class ModifierListContainer extends VerticalScrollClipContainer<ModifierL
LabelElement<?> itemName = new LabelElement<>( LabelElement<?> itemName = new LabelElement<>(
Spatials.positionXY(labelX, 5).width(this.innerWidth() - labelX).height(15), new TextComponent( Spatials.positionXY(labelX, 5).width(this.innerWidth() - labelX).height(15), new TextComponent(
gearPiece.getItem().toString().toUpperCase() + " - LVL " + lvl) gearPiece.getItem().toString().toUpperCase() + " - LVL " + lvl)
.withStyle(modifierCategory.getStyle()), LabelTextStyle.defaultStyle() .withStyle(ChatFormatting.UNDERLINE).withStyle(modifierCategory.getStyle()), LabelTextStyle.defaultStyle()
); );
this.addElement(itemName); this.addElement(itemName);
@ -43,7 +44,7 @@ public class ModifierListContainer extends VerticalScrollClipContainer<ModifierL
/* TODO: maybe weight/chance should be added here, because there is everything you need for custom position /* TODO: maybe weight/chance should be added here, because there is everything you need for custom position
that would require returning something else from getModifierList (maybe List<Pair<Component, Component>>) that would require returning something else from getModifierList (maybe List<Pair<Component, Component>>)
where first component is the modifier and second is the weight/chance or both (depending on the config) where first component is the modifier and second is the weight/chance or both (depending on the config)
also it should potentionally return a list of modifiers to get all tiers of the modifier also it should potentially return a list of modifiers to get all tiers of the modifier
I want to display I want to display