package pneumaticCraft.common.recipes;
import io.netty.buffer.ByteBuf;
import java.util.ArrayList;
import java.util.List;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.inventory.IInventory;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.world.ChunkPosition;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fluids.IFluidHandler;
import pneumaticCraft.api.PneumaticRegistry;
import pneumaticCraft.common.config.AmadronOfferSettings;
import pneumaticCraft.common.inventory.ContainerAmadron;
import pneumaticCraft.common.network.NetworkHandler;
import pneumaticCraft.common.network.PacketAmadronTradeNotifyDeal;
import pneumaticCraft.common.network.PacketSyncAmadronOffers;
import pneumaticCraft.common.util.PneumaticCraftUtils;
import com.google.gson.JsonObject;
import cpw.mods.fml.common.network.ByteBufUtils;
public class AmadronOfferCustom extends AmadronOffer{
private final String offeringPlayerName;
private String offeringPlayerId;
private int providingDimensionId, returningDimensionId;
private ChunkPosition providingPosition, returningPosition;
private int inStock;
private int maxTrades = -1;
private int pendingPayments;
private TileEntity cachedInput, cachedOutput;
public AmadronOfferCustom(Object input, Object output, EntityPlayer offeringPlayer){
this(input, output, offeringPlayer.getGameProfile().getName(), offeringPlayer.getGameProfile().getId().toString());
}
public AmadronOfferCustom(Object input, Object output, String playerName, String playerId){
super(input, output);
offeringPlayerName = playerName;
offeringPlayerId = playerId;
}
public AmadronOfferCustom setProvidingPosition(ChunkPosition pos, int dimensionId){
providingPosition = pos;
providingDimensionId = dimensionId;
cachedInput = null;
return this;
}
public AmadronOfferCustom setReturningPosition(ChunkPosition pos, int dimensionId){
returningPosition = pos;
returningDimensionId = dimensionId;
cachedOutput = null;
return this;
}
public AmadronOfferCustom invert(){
Object temp = input;
input = output;
output = temp;
return this;
}
public AmadronOfferCustom copy(){
NBTTagCompound tag = new NBTTagCompound();
writeToNBT(tag);
return loadFromNBT(tag);
}
public void updatePlayerId(){
EntityPlayer player = PneumaticCraftUtils.getPlayerFromName(offeringPlayerName);
if(player != null) offeringPlayerId = player.getGameProfile().getId().toString();
}
public void addStock(int stock){
inStock += stock;
}
@Override
public int getStock(){
return inStock;
}
public void addPayment(int payment){
pendingPayments += payment;
}
public void setMaxTrades(int maxTrades){
this.maxTrades = maxTrades;
}
@Override
public String getVendor(){
return offeringPlayerName;
}
public String getPlayerId(){
return offeringPlayerId;
}
@Override
public void onTrade(int tradingAmount, String buyingPlayer){
EntityPlayer player = PneumaticCraftUtils.getPlayerFromId(offeringPlayerId);
if(player != null && AmadronOfferSettings.notifyOfDealMade) {
NetworkHandler.sendTo(new PacketAmadronTradeNotifyDeal(this, tradingAmount, buyingPlayer), (EntityPlayerMP)player);
}
}
public void payout(){
TileEntity returning = getReturningTileEntity();
TileEntity provider = getProvidingTileEntity();
if(pendingPayments > 0) {
int paying = Math.min(pendingPayments, 50);
paying = ContainerAmadron.capShoppingAmount(this, paying, provider instanceof IInventory ? (IInventory)provider : null, returning instanceof IInventory ? (IInventory)returning : null, provider instanceof IFluidHandler ? (IFluidHandler)provider : null, returning instanceof IFluidHandler ? (IFluidHandler)returning : null, null);
if(paying > 0) {
pendingPayments -= paying;
if(getInput() instanceof ItemStack) {
ItemStack deliveringItems = (ItemStack)getInput();
int amount = deliveringItems.stackSize * paying;
List<ItemStack> stacks = new ArrayList<ItemStack>();
while(amount > 0) {
ItemStack stack = deliveringItems.copy();
stack.stackSize = Math.min(amount, stack.getMaxStackSize());
stacks.add(stack);
amount -= stack.stackSize;
}
PneumaticRegistry.getInstance().deliverItemsAmazonStyle(returning.getWorldObj(), returning.xCoord, returning.yCoord, returning.zCoord, stacks.toArray(new ItemStack[stacks.size()]));
} else {
FluidStack deliveringFluid = ((FluidStack)getInput()).copy();
deliveringFluid.amount *= paying;
PneumaticRegistry.getInstance().deliverFluidAmazonStyle(returning.getWorldObj(), returning.xCoord, returning.yCoord, returning.zCoord, deliveringFluid);
}
}
}
}
public void returnStock(){
TileEntity provider = getProvidingTileEntity();
TileEntity returning = getReturningTileEntity();
invert();
while(inStock > 0) {
int stock = Math.min(inStock, 50);
stock = ContainerAmadron.capShoppingAmount(this, stock, returning instanceof IInventory ? (IInventory)returning : null, provider instanceof IInventory ? (IInventory)provider : null, returning instanceof IFluidHandler ? (IFluidHandler)returning : null, provider instanceof IFluidHandler ? (IFluidHandler)provider : null, null);
if(stock > 0) {
inStock -= stock;
if(getInput() instanceof ItemStack) {
ItemStack deliveringItems = (ItemStack)getInput();
int amount = deliveringItems.stackSize * stock;
List<ItemStack> stacks = new ArrayList<ItemStack>();
while(amount > 0) {
ItemStack stack = deliveringItems.copy();
stack.stackSize = Math.min(amount, stack.getMaxStackSize());
stacks.add(stack);
amount -= stack.stackSize;
}
PneumaticRegistry.getInstance().deliverItemsAmazonStyle(provider.getWorldObj(), provider.xCoord, provider.yCoord, provider.zCoord, stacks.toArray(new ItemStack[stacks.size()]));
} else {
FluidStack deliveringFluid = ((FluidStack)getInput()).copy();
deliveringFluid.amount *= stock;
PneumaticRegistry.getInstance().deliverFluidAmazonStyle(provider.getWorldObj(), provider.xCoord, provider.yCoord, provider.zCoord, deliveringFluid);
}
} else {
break;
}
}
}
public TileEntity getProvidingTileEntity(){
if(cachedInput == null || cachedInput.isInvalid()) {
if(providingPosition != null) {
cachedInput = PneumaticCraftUtils.getTileEntity(providingPosition, providingDimensionId);
}
}
return cachedInput;
}
public TileEntity getReturningTileEntity(){
if(cachedOutput == null || cachedOutput.isInvalid()) {
if(returningPosition != null) {
cachedOutput = PneumaticCraftUtils.getTileEntity(returningPosition, returningDimensionId);
}
}
return cachedOutput;
}
@Override
public void writeToNBT(NBTTagCompound tag){
super.writeToNBT(tag);
tag.setString("offeringPlayerId", offeringPlayerId);
tag.setString("offeringPlayerName", offeringPlayerName);
tag.setInteger("inStock", inStock);
tag.setInteger("maxTrades", maxTrades);
tag.setInteger("pendingPayments", pendingPayments);
if(providingPosition != null) {
tag.setInteger("providingDimensionId", providingDimensionId);
tag.setInteger("providingX", providingPosition.chunkPosX);
tag.setInteger("providingY", providingPosition.chunkPosY);
tag.setInteger("providingZ", providingPosition.chunkPosZ);
}
if(returningPosition != null) {
tag.setInteger("returningDimensionId", returningDimensionId);
tag.setInteger("returningX", returningPosition.chunkPosX);
tag.setInteger("returningY", returningPosition.chunkPosY);
tag.setInteger("returningZ", returningPosition.chunkPosZ);
}
}
public static AmadronOfferCustom loadFromNBT(NBTTagCompound tag){
AmadronOffer offer = AmadronOffer.loadFromNBT(tag);
AmadronOfferCustom custom = new AmadronOfferCustom(offer.getInput(), offer.getOutput(), tag.getString("offeringPlayerName"), tag.getString("offeringPlayerId"));
custom.inStock = tag.getInteger("inStock");
custom.maxTrades = tag.getInteger("maxTrades");
custom.pendingPayments = tag.getInteger("pendingPayments");
if(tag.hasKey("providingDimensionId")) {
custom.setProvidingPosition(new ChunkPosition(tag.getInteger("providingX"), tag.getInteger("providingY"), tag.getInteger("providingZ")), tag.getInteger("providingDimensionId"));
}
if(tag.hasKey("returningDimensionId")) {
custom.setReturningPosition(new ChunkPosition(tag.getInteger("returningX"), tag.getInteger("returningY"), tag.getInteger("returningZ")), tag.getInteger("returningDimensionId"));
}
return custom;
}
public void writeToBuf(ByteBuf buf){
ByteBufUtils.writeUTF8String(buf, offeringPlayerName);
ByteBufUtils.writeUTF8String(buf, offeringPlayerId);
if(providingPosition != null) {
buf.writeBoolean(true);
buf.writeInt(providingPosition.chunkPosX);
buf.writeInt(providingPosition.chunkPosY);
buf.writeInt(providingPosition.chunkPosZ);
buf.writeInt(providingDimensionId);
} else {
buf.writeBoolean(false);
}
if(returningPosition != null) {
buf.writeBoolean(true);
buf.writeInt(returningPosition.chunkPosX);
buf.writeInt(returningPosition.chunkPosY);
buf.writeInt(returningPosition.chunkPosZ);
buf.writeInt(returningDimensionId);
} else {
buf.writeBoolean(false);
}
buf.writeInt(inStock);
buf.writeInt(maxTrades);
buf.writeInt(pendingPayments);
}
public static AmadronOfferCustom loadFromBuf(ByteBuf buf){
AmadronOfferCustom offer = new AmadronOfferCustom(PacketSyncAmadronOffers.getFluidOrItemStack(buf), PacketSyncAmadronOffers.getFluidOrItemStack(buf), ByteBufUtils.readUTF8String(buf), ByteBufUtils.readUTF8String(buf));
if(buf.readBoolean()) {
offer.setProvidingPosition(new ChunkPosition(buf.readInt(), buf.readInt(), buf.readInt()), buf.readInt());
}
if(buf.readBoolean()) {
offer.setReturningPosition(new ChunkPosition(buf.readInt(), buf.readInt(), buf.readInt()), buf.readInt());
}
offer.inStock = buf.readInt();
offer.maxTrades = buf.readInt();
offer.pendingPayments = buf.readInt();
return offer;
}
@Override
public JsonObject toJson(){
JsonObject json = super.toJson();
json.addProperty("offeringPlayerName", offeringPlayerName);
json.addProperty("offeringPlayerId", offeringPlayerId);
json.addProperty("inStock", inStock);
json.addProperty("maxTrades", maxTrades);
json.addProperty("pendingPayments", pendingPayments);
if(providingPosition != null) {
json.addProperty("providingDimensionId", providingDimensionId);
json.addProperty("providingX", providingPosition.chunkPosX);
json.addProperty("providingY", providingPosition.chunkPosY);
json.addProperty("providingZ", providingPosition.chunkPosZ);
}
if(returningPosition != null) {
json.addProperty("returningDimensionId", returningDimensionId);
json.addProperty("returningX", returningPosition.chunkPosX);
json.addProperty("returningY", returningPosition.chunkPosY);
json.addProperty("returningZ", returningPosition.chunkPosZ);
}
return json;
}
public static AmadronOfferCustom fromJson(JsonObject json){
AmadronOffer offer = AmadronOffer.fromJson(json);
if(offer != null) {
AmadronOfferCustom custom = new AmadronOfferCustom(offer.input, offer.output, json.get("offeringPlayerName").getAsString(), json.get("offeringPlayerId").getAsString());
custom.inStock = json.get("inStock").getAsInt();
custom.maxTrades = json.get("maxTrades").getAsInt();
custom.pendingPayments = json.get("pendingPayments").getAsInt();
if(json.has("providingDimensionId")) {
custom.providingDimensionId = json.get("providingDimensionId").getAsInt();
custom.providingPosition = new ChunkPosition(json.get("providingX").getAsInt(), json.get("providingY").getAsInt(), json.get("providingZ").getAsInt());
}
if(json.has("returningDimensionId")) {
custom.returningDimensionId = json.get("returningDimensionId").getAsInt();
custom.returningPosition = new ChunkPosition(json.get("returningX").getAsInt(), json.get("returningY").getAsInt(), json.get("returningZ").getAsInt());
}
return custom;
} else {
return null;
}
}
@Override
public boolean equals(Object o){
if(o instanceof AmadronOfferCustom) {
AmadronOfferCustom offer = (AmadronOfferCustom)o;
return super.equals(o) && offer.offeringPlayerId.equals(offeringPlayerId);
} else {
return false;
}
}
@Override
public int hashCode(){
return super.hashCode() * 31 + offeringPlayerId.hashCode();
}
}