<commit_before>package com.cazsius.solcarrot.tracking;

import com.cazsius.solcarrot.SOLCarrot;
import com.cazsius.solcarrot.SOLCarrotConfig;
import net.minecraft.entity.SharedMonsterAttributes;
import net.minecraft.entity.ai.attributes.AttributeModifier;
import net.minecraft.entity.ai.attributes.IAttributeInstance;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraftforge.event.entity.player.PlayerEvent;
import net.minecraftforge.eventbus.api.SubscribeEvent;
import net.minecraftforge.fml.common.Mod;

import javax.annotation.Nullable;
import java.util.UUID;

@Mod.EventBusSubscriber(modid = SOLCarrot.MOD_ID)
public final class MaxHealthHandler {
	private static final UUID MILESTONE_HEALTH_MODIFIER_ID = UUID.fromString("b20d3436-0d39-4868-96ab-d0a4856e68c6");
	
	@SubscribeEvent
	public static void onPlayerLogin(PlayerEvent.PlayerLoggedInEvent event) {
		updateFoodHPModifier(event.getPlayer());
	}
	
	@SubscribeEvent
	public static void onPlayerClone(PlayerEvent.Clone event) {
		AttributeModifier prevModifier = getHealthModifier(event.getOriginal());
		if (prevModifier == null) return;
		
		updateHealthModifier(event.getPlayer(), prevModifier);
	}
	
	/** @return whether or not the player reached a new milestone in this update */
	public static boolean updateFoodHPModifier(PlayerEntity player) {
		if (player.world.isRemote) return false;
		
		AttributeModifier prevModifier = getHealthModifier(player);
		
		int healthPenalty = 2 * (SOLCarrotConfig.getBaseHearts() - 10);
		
		ProgressInfo progressInfo = FoodList.get(player).getProgressInfo();
		int milestonesAchieved = progressInfo.milestonesAchieved();
		int addedHealthFromFood = milestonesAchieved * 2 * SOLCarrotConfig.getHeartsPerMilestone();
		
		double totalHealthModifier = healthPenalty + addedHealthFromFood;
		
		if (prevModifier == null || prevModifier.getAmount() != totalHealthModifier) {
			AttributeModifier modifier = new AttributeModifier(
				MILESTONE_HEALTH_MODIFIER_ID,
				"Health Gained from Trying New Foods",
				totalHealthModifier,
				AttributeModifier.Operation.ADDITION
			);
			
			float oldMax = player.getMaxHealth();
			updateHealthModifier(player, modifier);
			
			// adjust current health proportionally to increase in max health
			player.setHealth(player.getHealth() * player.getMaxHealth() / oldMax);
			
			return true;
		} else {
			return false;
		}
	}
	
	@Nullable
	private static AttributeModifier getHealthModifier(PlayerEntity player) {
		return maxHealthAttribute(player).getModifier(MILESTONE_HEALTH_MODIFIER_ID);
	}
	
	private static void updateHealthModifier(PlayerEntity player, AttributeModifier modifier) {
		IAttributeInstance attribute = maxHealthAttribute(player);
		attribute.removeModifier(modifier);
		attribute.applyModifier(modifier);<commit_msg>fixed max health sometimes desyncing<commit_after>package com.cazsius.solcarrot.tracking;

import com.cazsius.solcarrot.SOLCarrot;
import com.cazsius.solcarrot.SOLCarrotConfig;
import net.minecraft.entity.SharedMonsterAttributes;
import net.minecraft.entity.ai.attributes.AttributeModifier;
import net.minecraft.entity.ai.attributes.IAttributeInstance;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraftforge.event.entity.player.PlayerEvent;
import net.minecraftforge.eventbus.api.SubscribeEvent;
import net.minecraftforge.fml.common.Mod;

import javax.annotation.Nullable;
import java.util.UUID;

@Mod.EventBusSubscriber(modid = SOLCarrot.MOD_ID)
public final class MaxHealthHandler {
	private static final UUID MILESTONE_HEALTH_MODIFIER_ID = UUID.fromString("b20d3436-0d39-4868-96ab-d0a4856e68c6");
	
	@SubscribeEvent
	public static void onPlayerLogin(PlayerEvent.PlayerLoggedInEvent event) {
		updateFoodHPModifier(event.getPlayer());
	}
	
	@SubscribeEvent
	public static void onPlayerClone(PlayerEvent.Clone event) {
		AttributeModifier prevModifier = getHealthModifier(event.getOriginal());
		if (prevModifier == null) return;
		
		updateHealthModifier(event.getPlayer(), prevModifier);
	}
	
	/** @return whether or not the player reached a new milestone in this update */
	public static boolean updateFoodHPModifier(PlayerEntity player) {
		if (player.world.isRemote) return false;
		
		AttributeModifier prevModifier = getHealthModifier(player);
		
		int healthPenalty = 2 * (SOLCarrotConfig.getBaseHearts() - 10);
		
		ProgressInfo progressInfo = FoodList.get(player).getProgressInfo();
		int milestonesAchieved = progressInfo.milestonesAchieved();
		int addedHealthFromFood = milestonesAchieved * 2 * SOLCarrotConfig.getHeartsPerMilestone();
		
		double totalHealthModifier = healthPenalty + addedHealthFromFood;
		boolean hasChanged = prevModifier == null || prevModifier.getAmount() != totalHealthModifier;
		
		AttributeModifier modifier = new AttributeModifier(
			MILESTONE_HEALTH_MODIFIER_ID,
			"Health Gained from Trying New Foods",
			totalHealthModifier,
			AttributeModifier.Operation.ADDITION
		);
		
		updateHealthModifier(player, modifier);
		
		return hasChanged;
	}
	
	@Nullable
	private static AttributeModifier getHealthModifier(PlayerEntity player) {
		return maxHealthAttribute(player).getModifier(MILESTONE_HEALTH_MODIFIER_ID);
	}
	
	private static void updateHealthModifier(PlayerEntity player, AttributeModifier modifier) {
		float oldMax = player.getMaxHealth();
		
		IAttributeInstance attribute = maxHealthAttribute(player);
		attribute.removeModifier(modifier);
		attribute.applyModifier(modifier);
		
		float newHealth = player.getHealth() * player.getMaxHealth() / oldMax;
		// because apparently it doesn't update unless changed
		player.setHealth(0.1f);
		// adjust current health proportionally to increase in max health
		player.setHealth(newHealth);
{'fraction_non_alphanumeric': 0.0856842474154547, 'fraction_numerical': 0.009812510951463115, 'mean_word_length': 5.85234093637455, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5396251', 'n_tokens_mistral': 1839, 'n_tokens_neox': 1672, 'n_words': 338}