/* * This file is part of Matter Overdrive * Copyright (c) 2015., Simeon Radivoev, All rights reserved. * * Matter Overdrive is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * Matter Overdrive is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Matter Overdrive. If not, see <http://www.gnu.org/licenses>. */ package matteroverdrive.util; import cofh.api.energy.IEnergyContainerItem; import matteroverdrive.Reference; import matteroverdrive.api.weapon.IWeapon; import matteroverdrive.api.weapon.IWeaponModule; import matteroverdrive.data.WeightedRandomItemStack; import matteroverdrive.init.MatterOverdriveItems; import matteroverdrive.items.weapon.EnergyWeapon; import matteroverdrive.items.weapon.module.WeaponModuleBarrel; import net.minecraft.entity.Entity; import net.minecraft.item.ItemStack; import net.minecraft.util.EnumChatFormatting; import net.minecraft.util.WeightedRandom; import java.util.*; /** * Created by Simeon on 11/16/2015. */ public class WeaponFactory { public static final int MAX_LOOT_LEVEL = 3; private Random random; public List<WeightedRandomItemStack> weapons; public List<WeightedRandomWeaponModule> barrelModules; public List<WeightedRandomWeaponModule> batteryModules; public List<WeightedRandomWeaponModule> otherModules; public WeaponFactory() { this.random = new Random(); this.barrelModules = new ArrayList<>(); this.batteryModules = new ArrayList<>(); this.otherModules = new ArrayList<>(); this.weapons = new ArrayList<>(); } public void initModules() { barrelModules.add(new WeightedRandomWeaponModule(null,200,0,MAX_LOOT_LEVEL)); barrelModules.add(new WeightedRandomWeaponModule(new ItemStack(MatterOverdriveItems.weapon_module_barrel,1, WeaponModuleBarrel.DAMAGE_BARREL_ID),100,1,MAX_LOOT_LEVEL)); barrelModules.add(new WeightedRandomWeaponModule(new ItemStack(MatterOverdriveItems.weapon_module_barrel,1, WeaponModuleBarrel.FIRE_BARREL_ID),10,1,MAX_LOOT_LEVEL)); barrelModules.add(new WeightedRandomWeaponModule(new ItemStack(MatterOverdriveItems.weapon_module_barrel,1, WeaponModuleBarrel.EXPLOSION_BARREL_ID),5,2,MAX_LOOT_LEVEL)); batteryModules.add(new WeightedRandomWeaponModule(new ItemStack(MatterOverdriveItems.battery),100,1,MAX_LOOT_LEVEL)); batteryModules.add(new WeightedRandomWeaponModule(new ItemStack(MatterOverdriveItems.hc_battery),20,1,MAX_LOOT_LEVEL)); otherModules.add(new WeightedRandomWeaponModule(null,300,0,MAX_LOOT_LEVEL)); otherModules.add(new WeightedRandomWeaponModule(new ItemStack(MatterOverdriveItems.sniperScope),10,1,MAX_LOOT_LEVEL)); } public void initWeapons() { weapons.add(new WeightedRandomItemStack(new ItemStack(MatterOverdriveItems.phaserRifle),70)); weapons.add(new WeightedRandomItemStack(new ItemStack(MatterOverdriveItems.omniTool),30)); weapons.add(new WeightedRandomItemStack(new ItemStack(MatterOverdriveItems.plasmaShotgun),10)); weapons.add(new WeightedRandomItemStack(new ItemStack(MatterOverdriveItems.ionSniper),5)); } public ItemStack getRandomDecoratedEnergyWeapon(WeaponGenerationContext context) { ItemStack weapon = getRandomEnergyWeapon(context); context.setWeaponStack(weapon); decorateWeapon(weapon,context); if (context.fullCharge) { ((EnergyWeapon)weapon.getItem()).rechargeFully(weapon); } return weapon; } public ItemStack getRandomEnergyWeapon(WeaponGenerationContext context) { ItemStack weapon; weapon = ((WeightedRandomItemStack)WeightedRandom.getRandomItem(random,weapons)).getStack(); if (context.fullCharge) { ((EnergyWeapon)weapon.getItem()).rechargeFully(weapon); } return weapon; } public void decorateWeapon(ItemStack weapon,WeaponGenerationContext context) { WeightedRandomWeaponModule barrelModule = null; if (context.barrel) { barrelModule = getRandomModule(random, barrelModules, context); if (barrelModule != null && barrelModule.getWeaponModule() != null) { WeaponHelper.setModuleAtSlot(barrelModule.getModuleSlot(), weapon, barrelModule.getWeaponModule()); } } if (context.battery) { WeightedRandomWeaponModule battery = getRandomModule(random, batteryModules, context); if (battery != null && battery.getWeaponModule() != null) { WeaponHelper.setModuleAtSlot(battery.getModuleSlot(), weapon, battery.getWeaponModule()); } } if (context.other) { WeightedRandomWeaponModule other = getRandomModule(random,otherModules,context); if (other != null) { if (other.getWeaponModule() != null) { WeaponHelper.setModuleAtSlot(other.getModuleSlot(),weapon,other.getWeaponModule()); } }else { if (barrelModule != null && barrelModule.weaponModule != null) { setColorModuleBasedOnBarrel(weapon,barrelModule.weaponModule); } } } if (context.legendary) { modifyToLegendary(weapon,context); } } public void setColorModuleBasedOnBarrel(ItemStack weapon,ItemStack barrel) { if (barrel.getItem() instanceof WeaponModuleBarrel) { if (barrel.getItemDamage() == WeaponModuleBarrel.EXPLOSION_BARREL_ID) { //gold WeaponHelper.setModuleAtSlot(1, weapon, new ItemStack(MatterOverdriveItems.weapon_module_color,1, 6)); }else if (barrel.getItemDamage() == WeaponModuleBarrel.FIRE_BARREL_ID) { //red WeaponHelper.setModuleAtSlot(1, weapon, new ItemStack(MatterOverdriveItems.weapon_module_color,1)); }else if (barrel.getItemDamage() == WeaponModuleBarrel.DAMAGE_BARREL_ID) { //blue WeaponHelper.setModuleAtSlot(1, weapon, new ItemStack(MatterOverdriveItems.weapon_module_color,1, 2)); } } } public void modifyToLegendary(ItemStack weapon,WeaponGenerationContext context) { weapon.setStackDisplayName(Reference.UNICODE_LEGENDARY + " " + EnumChatFormatting.GOLD + MOStringHelper.translateToLocal("rarity.legendary") + " " + weapon.getDisplayName()); int damageLevel = random.nextInt(context.level+1); if (damageLevel > 0) weapon.getTagCompound().setFloat(EnergyWeapon.CUSTOM_DAMAGE_MULTIPLY_TAG,1 + 0.1f*damageLevel); int accuracyLevel = random.nextInt(context.level+1); if (accuracyLevel > 0) weapon.getTagCompound().setFloat(EnergyWeapon.CUSTOM_ACCURACY_MULTIPLY_TAG,1f - (0.1f*accuracyLevel)); int shootCooldownLevel = random.nextInt(context.level+1); if (shootCooldownLevel > 0) weapon.getTagCompound().setFloat(EnergyWeapon.CUSTOM_SPEED_MULTIPLY_TAG,1f - (0.05f*shootCooldownLevel)); int rangeLevel = random.nextInt(context.level+1); if (rangeLevel > 0) weapon.getTagCompound().setFloat(EnergyWeapon.CUSTOM_RANGE_MULTIPLY_TAG,1f + 0.15f*rangeLevel); } public void setSeed(long seed) { random.setSeed(seed); } //region random calculation public static int getTotalModulesWeight(Collection<WeightedRandomWeaponModule> collection,WeaponGenerationContext context) { int i = 0; for (WeightedRandomWeaponModule module : collection) { if (module.fits(context)) { i += module.itemWeight; } } return i; } public static WeightedRandomWeaponModule getItem(Collection<WeightedRandomWeaponModule> par1Collection, int weight,WeaponGenerationContext context) { int j = weight; Iterator<WeightedRandomWeaponModule> iterator = par1Collection.iterator(); WeightedRandomWeaponModule module = null; do { if (!iterator.hasNext()) { return null; } WeightedRandomWeaponModule temp = iterator.next(); if (temp.fits(context)) { module = temp; j -= temp.itemWeight; } } while (j >= 0); return module; } public static WeightedRandomWeaponModule getRandomModule(Random random, Collection collection,WeaponGenerationContext context) { return getItem(collection,random.nextInt(getTotalModulesWeight(collection,context)+1),context); } //endregion //region Classes public static class WeaponGenerationContext { public final int level; public Entity entity; public boolean legendary; public boolean fullCharge = true; public boolean barrel = true; public boolean battery = true; public boolean other = true; public ItemStack weaponStack; public WeaponGenerationContext(int level) { this.level = level; } public WeaponGenerationContext(int level,Entity entity) { this(level); this.entity = entity; } public WeaponGenerationContext(int level,Entity entity,boolean legendary) { this(level,entity); this.legendary = legendary; } public void setWeaponStack(ItemStack weaponStack) { this.weaponStack = weaponStack; } } public static class WeightedRandomWeaponModule extends WeightedRandom.Item { private int minLevel; private int maxLevel; private boolean legendary; private int slotID; private final ItemStack weaponModule; public WeightedRandomWeaponModule(ItemStack weaponModule,int weight,int minLevel,int maxLevel) { super(weight); if (weaponModule != null) { if (weaponModule.getItem() instanceof IWeaponModule) { this.slotID = ((IWeaponModule) weaponModule.getItem()).getSlot(weaponModule); }else if (weaponModule.getItem() instanceof IEnergyContainerItem) { this.slotID = Reference.MODULE_BATTERY; } } this.weaponModule = weaponModule; this.minLevel = minLevel; this.maxLevel = maxLevel; } public int getModuleSlot() { return slotID; } public ItemStack getWeaponModule() { if (this.weaponModule != null) return this.weaponModule.copy(); return null; } public boolean fits(WeaponGenerationContext context) { boolean weaponSupportModule = false; if (context.weaponStack != null && context.weaponStack.getItem() instanceof IWeapon) { weaponSupportModule = context.weaponStack.getItem() instanceof IWeapon && ((IWeapon) context.weaponStack.getItem()).supportsModule(context.weaponStack,weaponModule); } if (legendary && !context.legendary) { return weaponSupportModule; } return context.level >= minLevel && context.level <= maxLevel && weaponSupportModule; } } //endregion }