package dangerzone.entities;
/*
 * This code is copyright Richard H. Clark, TheyCallMeDanger, OreSpawn, 2015-2020.
 * You may use this code for reference for modding the DangerZone game program,
 * and are perfectly welcome to cut'n'paste portions for your mod as well.
 * DO NOT USE THIS CODE FOR ANY PURPOSE OTHER THAN MODDING FOR THE DANGERZONE GAME.
 * DO NOT REDISTRIBUTE THIS CODE. 
 * 
 * This copyright remains in effect until January 1st, 2021. 
 * At that time, this code becomes public domain.
 * 
 * WARNING: There are bugs. Big bugs. Little bugs. Every size in-between bugs.
 * This code is NOT suitable for use in anything other than this particular game. 
 * NO GUARANTEES of any sort are given, either express or implied, and Richard H. Clark, 
 * TheyCallMeDanger, OreSpawn are not responsible for any damages, direct, indirect, or otherwise. 
 * You should have made backups. It's your own fault for not making them.
 * 
 * NO ATTEMPT AT SECURITY IS MADE. This code is USE AT YOUR OWN RISK.
 * Regardless of what you may think, the reality is, that the moment you 
 * connected your computer to the Internet, Uncle Sam, among many others, hacked it.
 * DO NOT KEEP VALUABLE INFORMATION ON INTERNET-CONNECTED COMPUTERS.
 * Or your phone...
 * 
 */

import org.lwjgl.opengl.GL11;


import dangerzone.DangerZone;
import dangerzone.InventoryContainer;
import dangerzone.ModelBase;
import dangerzone.ModelRenderer;
import dangerzone.Player;
import dangerzone.blocks.Blocks;
import dangerzone.items.Item;
import dangerzone.items.ItemArmor;
import dangerzone.items.Items;




public class ModelHumanoid extends ModelBase
{
  //fields
    ModelRenderer head;
    ModelRenderer body;
    ModelRenderer leftarm;
    ModelRenderer rightarm;
    ModelRenderer rightleg;
    ModelRenderer leftleg;
  
  public ModelHumanoid()
  {
    
      head = new ModelRenderer( 0, 0);
      head.addCube(-4F, -8F, -4F, 8, 8, 8);
      head.setRotationPoint(0F, 0F, 0F);
      head.setTextureSize(64, 32);
      head.setRotation( 0F, 0F, 0F);
      body = new ModelRenderer( 16, 16);
      body.addCube(-4F, 0F, -2F, 8, 12, 4);
      body.setRotationPoint(0F, 0F, 0F);
      body.setTextureSize(64, 32);
      body.setRotation( 0F, 0F, 0F);
      leftarm = new ModelRenderer( 40, 16);
      leftarm.addCube(0F, -1F, -2F, 4, 12, 4);
      leftarm.setRotationPoint(4F, 1F, 0F);
      leftarm.setTextureSize(64, 32);
      leftarm.setRotation( 0F, 0F, 0F);
      leftarm.mirror = false;
      rightarm = new ModelRenderer( 40, 16);
      rightarm.addCube(-4F, -1F, -2F, 4, 12, 4);
      rightarm.setRotationPoint(-4F, 1F, 0F);
      rightarm.setTextureSize(64, 32);
      rightarm.setRotation( 0F, 0F, 0F);
      rightleg = new ModelRenderer( 0, 16);
      rightleg.addCube(-2F, 0F, -2F, 4, 12, 4);
      rightleg.setRotationPoint(-2F, 12F, 0F);
      rightleg.setTextureSize(64, 32);
      rightleg.setRotation( 0F, 0F, 0F);
      leftleg = new ModelRenderer( 0, 16);
      leftleg.addCube(-2F, 0F, -2F, 4, 12, 4);
      leftleg.setRotationPoint(2F, 12F, 0F);
      leftleg.setTextureSize(64, 32);
      leftleg.setRotation( 0F, 0F, 0F);
      leftleg.mirror = false;
  }
  
  // f = lifetime ticker. Doing Math.toRadians() on it provides a nice smooth wave cycle.
  // f1 = entity velocity
  // f2 = pitch head
  // f3 = yaw head
  // f4 = roll head
  public void render(Entity entity, float f, float f1, float f2, float f3, float f4, float deathfactor)
  {
	  float newangle = 0;
	  Entity ridden = null;
	  
	  if(entity != null){
		  ridden = entity.getRiddenEntity();
	  }

	  if(ridden != null)f1 = 0;
	  
	  if(f1 > 0.02){
		  if(f1 > 1)f1 = 1; //MAX! Otherwise arms and legs go flying in circles...
		  newangle = (float) (Math.cos(Math.toRadians(f*10.6f)) * (float)Math.PI * 0.45F * f1);
		  if(entity.isBaby())newangle = (float) (Math.cos(Math.toRadians(f*20.6f)) * (float)Math.PI * 0.45F * f1);
	  }else{
		  newangle = 0.0F;
	  }

	  leftleg.rotateAngleX = newangle;
	  rightleg.rotateAngleX = -newangle;

	  leftarm.rotateAngleX = -newangle;
	  rightarm.rotateAngleX = newangle;

	  newangle = (float) (Math.cos(Math.toRadians(f*1.6f)) * (float)Math.PI * 0.01f);
	  leftarm.rotateAngleZ = -0.017f + newangle;
	  newangle = (float) (Math.cos(Math.toRadians(f*1.3f)) * (float)Math.PI * 0.01f);
	  rightarm.rotateAngleZ = 0.017f + newangle;

	  newangle = (float) (Math.cos(Math.toRadians(f*1.1f)) * (float)Math.PI * 0.015f);
	  leftarm.rotateAngleX += newangle;
	  newangle = (float) (Math.cos(Math.toRadians(f*1.2f)) * (float)Math.PI * 0.015f);
	  rightarm.rotateAngleX += newangle;
	  if(entity != null){		  
		  if(entity.getArmsUp()){
			  rightarm.rotateAngleX -= Math.PI/2;
			  leftarm.rotateAngleX -= Math.PI/2;
		  }else{
			  rightarm.rotateAngleX += Math.toRadians(entity.getRightArmAngle());
			  rightarm.rotateAngleZ += Math.toRadians(entity.getRightArmAngle())/6f;
		  }
	  }
	  
	  //Don't go breaking our necks!
	  if(f2 > 40)f2 = 40;
	  if(f2 < -40)f2 = -40;
	  if(f3 > 55)f3 = 55;
	  if(f3 < -55)f3 = -55;
	  if(f4 > 30)f4 = 30;
	  if(f4 < -30)f4 = -30;
	  
	  head.rotateAngleX = (float) Math.toRadians(f2);
	  if(entity instanceof Player){
		  head.rotateAngleY = (float) Math.toRadians(f3);
	  }else{
		  head.rotateAngleY = (float) -Math.toRadians(f3);
	  }
	  head.rotateAngleZ = (float) Math.toRadians(f4);

	  //Need to know if we are holding something and will move the arm later.
	  //have to move it now so we don't have to load the texture twice!
	  if(entity != null && (entity != DangerZone.player || DangerZone.f5_front || DangerZone.f5_back)){
		  InventoryContainer ic = entity.getHotbar(entity.gethotbarindex());
		  if(ic != null){
			  //Arm UP a bit...
			  rightarm.rotateAngleX += -0.624f;
		  }
	  }
	  

	  
	  if(entity != null && entity.getSitting()){
		  rightleg.rotateAngleX = leftleg.rotateAngleX = -1.344f;
		  leftleg.rotateAngleY = -0.244f;
		  rightleg.rotateAngleY = 0.244f;
		  GL11.glTranslatef(0f, -10f, 0f);
	  }else{
		  //A little taller when wearing boots!
		  if(entity != null && entity instanceof Player){
			  Player pl = (Player)entity;
			  int armorid = pl.getBootsID();
			  if(armorid != 0){
				  GL11.glTranslatef(0f, 1.45f, 0f);
			  }
		  }
	  }

	  head.render(deathfactor);
	  body.render(deathfactor);
	  leftarm.render(deathfactor);
	  rightarm.render(deathfactor);
	  rightleg.render(deathfactor);
	  leftleg.render(deathfactor);    

	  //Do all this AFTER so we don't have to reload the entity texture!
	  if(entity != null && (entity != DangerZone.player || DangerZone.f5_front || DangerZone.f5_back)){
		  int bid = 0;
		  int iid = 0;
		  InventoryContainer ic = entity.getHotbar(entity.gethotbarindex());
		  if(ic != null){
			  bid = ic.bid;
			  iid = ic.iid;
		  }
		  if(bid != 0 || iid != 0){
			  GL11.glPushMatrix();
			  GL11.glTranslatef(rightarm.rotationPointX, rightarm.rotationPointY+24, rightarm.rotationPointZ);	    			

			  if(bid != 0){
				  
				  GL11.glRotatef(-(float) Math.toDegrees(rightarm.rotateAngleZ), 0.0f, 0.0f, 1.0f); // Rotate
				  GL11.glRotatef((float) Math.toDegrees(rightarm.rotateAngleY), 0.0f, 1.0f, 0.0f);
				  GL11.glRotatef((float) Math.toDegrees(rightarm.rotateAngleX)*8/10, 1.0f, 0.0f, 0.0f); // Rotate

				  GL11.glTranslatef((float) (rightarm.offsetX), 
						  (float) (rightarm.offsetY-8f), 
						  (float) (rightarm.offsetZ+10));

				  GL11.glPushMatrix(); 
				  
				  //GL11.glTranslatef(2.4f + DangerZone.testx, -2.2f + DangerZone.testy, -4.4f + DangerZone.testz);
				  //GL11.glRotatef(46.1f + DangerZone.testr, 0.0f, 0.0f, 1.0f); // Rotate
				  //GL11.glRotatef(22.0f + DangerZone.testw, 0.0f, 1.0f, 0.0f);
				  //GL11.glRotatef(85.8f + DangerZone.testp, 1.0f, 0.0f, 0.0f); // Rotate
				  
				  GL11.glTranslatef(2.4f, -2.2f, -4.4f);
				  GL11.glRotatef(46.1f, 0.0f, 0.0f, 1.0f); // Rotate
				  GL11.glRotatef(22.0f, 0.0f, 1.0f, 0.0f);
				  GL11.glRotatef(85.8f, 1.0f, 0.0f, 0.0f); // Rotate
				  
				  
				  GL11.glScalef(0.30f, 0.30f, 0.30f);
				  if(Blocks.hasOwnRenderer(bid)){
					  Blocks.renderMe(DangerZone.wr, entity.world, entity.dimension, (int)entity.posx, (int)entity.posy, (int)entity.posz, bid, 0, 0xff, false);
				  }else{
					  DangerZone.wr.drawTexturedCube(0xff, Blocks.isSolidForRender(bid), bid, 0, false);
				  }
				  GL11.glPopMatrix();
				  
			  }else{
				  if(iid != 0){

					  GL11.glRotatef(-(float) Math.toDegrees(rightarm.rotateAngleZ), 0.0f, 0.0f, 1.0f); // Rotate
					  GL11.glRotatef((float) Math.toDegrees(rightarm.rotateAngleY), 0.0f, 1.0f, 0.0f);
					  GL11.glRotatef((float) Math.toDegrees(rightarm.rotateAngleX)*8/10, 1.0f, 0.0f, 0.0f); // Rotate - why 0.8???

					  GL11.glTranslatef((float) (rightarm.offsetX), 
							  (float) (rightarm.offsetY-8f), 
							  (float) (rightarm.offsetZ+10));

					  GL11.glPushMatrix();  
					  if(Items.isFlipped(iid)){
						  GL11.glRotatef(268, 0.0f, 0.0f, 1.0f); // Rotate
						  GL11.glRotatef(200, 0.0f, 1.0f, 0.0f);
						  GL11.glRotatef(68, 1.0f, 0.0f, 0.0f); // Rotate
					  }else{
						GL11.glTranslatef(0, -0.7f, 0.6f);
						GL11.glRotatef(-95.7f, 0.0f, 0.0f, 1.0f); // Rotate
						GL11.glRotatef(-53.8f, 0.0f, 1.0f, 0.0f);
						GL11.glRotatef(-73.2f, 1.0f, 0.0f, 0.0f); // Rotate
					  }
					  
					  //GL11.glRotatef(DangerZone.testr, 0.0f, 0.0f, 1.0f); // Rotate
					  //GL11.glRotatef(DangerZone.testw, 0.0f, 1.0f, 0.0f);
					  //GL11.glRotatef(DangerZone.testp, 1.0f, 0.0f, 0.0f); // Rotate
					  
					  

					  //GL11.glScalef(0.75f, 0.75f, 0.75f);
					  DangerZone.wr.loadtexture(Items.getTexture(iid));
					  Items.renderMe(DangerZone.wr, entity.world, entity.dimension, (int)entity.posx, (int)entity.posy, (int)entity.posz, iid, 0, 0, false);

					  GL11.glPopMatrix();
				  }
			  }
			  GL11.glPopMatrix();
		  }	    	
	  }
	  
	  /*
	   * Now let's do armor!
	   * It is essentially the same, just scaled up a smidge to overlay.
	   */
	  if(entity != null && entity instanceof EntityLiving){
		  EntityLiving pl = (EntityLiving)entity;


		  int armorid = pl.getHelmetID();
		  if(armorid != 0){
			  Item it = Items.getItem(armorid);
			  if(it != null && it instanceof ItemArmor){
				  ItemArmor ita = (ItemArmor)it;
				  GL11.glPushMatrix(); 
				  DangerZone.wr.loadtexture(ita.getArmorTexture(armorid));
				  GL11.glScalef(1.10f, 1.10f, 1.10f);
				  GL11.glTranslatef(0f, -2.8f, 0f); //translate down a little because we scaled differently...
				  head.render(deathfactor);
				  GL11.glPopMatrix();
			  }
		  }

		  armorid = pl.getLeggingsID();
		  if(armorid != 0){
			  Item it = Items.getItem(armorid);
			  if(it != null && it instanceof ItemArmor){
				  ItemArmor ita = (ItemArmor)it;
				  GL11.glPushMatrix(); 
				  DangerZone.wr.loadtexture(ita.getArmorTexture2(armorid));
				  GL11.glScalef(1.10f, 1.10f, 1.10f);
				  GL11.glTranslatef(0f, -1.1f, 0f);
				  GL11.glTranslatef(-0.18f, 0f, 0f);
				  leftleg.render(deathfactor);
				  GL11.glTranslatef(0.36f, 0f, 0f);			  
				  rightleg.render(deathfactor);
				  GL11.glPopMatrix();
				  //around the waist!
				  GL11.glPushMatrix(); 
				  //DangerZone.wr.loadtexture(ita.getArmorTexture(armorid));
				  GL11.glScalef(1.10f, 1.10f, 1.10f);
				  GL11.glTranslatef(0f, -1.8f, 0f); //translate down a little because we scaled differently...
				  body.render(deathfactor);
				  GL11.glPopMatrix();
			  }
		  }

		  //chestplate and boots have to come after leggings, because they overlap 
		  armorid = pl.getChestplateID();
		  if(armorid != 0){
			  Item it = Items.getItem(armorid);
			  if(it != null && it instanceof ItemArmor){
				  ItemArmor ita = (ItemArmor)it;
				  GL11.glPushMatrix(); 
				  DangerZone.wr.loadtexture(ita.getArmorTexture(armorid));
				  GL11.glScalef(1.15f, 1.15f, 1.15f);
				  GL11.glTranslatef(0f, -2.9f, 0f); //translate down a little because we scaled differently...
				  body.render(deathfactor);
				  GL11.glTranslatef(-0.6f, 0f, 0f);
				  leftarm.render(deathfactor);
				  GL11.glTranslatef(1.2f, 0f, 0f);
				  rightarm.render(deathfactor);
				  GL11.glPopMatrix();
			  }
		  }

		  armorid = pl.getBootsID();
		  if(armorid != 0){
			  Item it = Items.getItem(armorid);
			  if(it != null && it instanceof ItemArmor){
				  ItemArmor ita = (ItemArmor)it;
				  GL11.glPushMatrix(); 
				  DangerZone.wr.loadtexture(ita.getArmorTexture(armorid));
				  GL11.glScalef(1.15f, 1.15f, 1.15f);
				  GL11.glTranslatef(0f, -1.3f, 0f); //translate down a little because we scaled differently...
				  GL11.glTranslatef(-0.18f, 0f, 0f);
				  leftleg.render(deathfactor);
				  GL11.glTranslatef(0.36f, 0f, 0f);
				  rightleg.render(deathfactor);
				  GL11.glPopMatrix();
			  }
		  }
	  }
	  
  }
  
  
  public void doScale(Entity ent){
	  super.doScale(ent);
	  GL11.glScalef(0.80f, 0.95f, 0.80f); 
  }
  

}
