public class ClientLoader {
	/**
	 * Loads a .mcmd model from the given {@link ResourceLocation} and binds it to the skeleton. Note that while the raw
	 * data from the ResourceLocation is cached, the model is not (because its state is not immutable), so try to not
	 * load a model per frame but save it somewhere.
	 * 
	 * @param resLoc
	 *            the resource location to load from
	 * @param skeleton
	 *            the skeleton that the model should use
	 * @return
	 * @see CommonLoader#loadSkeleton(ResourceLocation)
	 * @see CommonLoader#loadLegacySkeleton(ResourceLocation)
	 * @see CommonLoader#loadAnimation(ResourceLocation)
	 * @see ISkeleton#EMPTY
	 */
	public static ModelMCMD loadModel(ResourceLocation resLoc, ISkeleton skeleton) {
		Objects.requireNonNull(skeleton);
		ClassLoader loader = CallResolver.INSTANCE.getCallingClass().getClassLoader();
		ModelMCMD model = new ModelMCMD(MCAnm.proxy.getSidedResource(resLoc, loader), skeleton);
		return model;
	}
} public interface IModel {
	void render(IRenderPass renderPass);
} public interface IEntityAnimator<T extends EntityLiving> {
	public static final IEntityAnimator<EntityLiving> STATIC_ANIMATOR = new IEntityAnimator<EntityLiving>() {
		@Override
		public IRenderPassInformation preRenderCallback(
				EntityLiving entity,
				RenderPassInformation buffer,
				float partialTick,
				float uLimbSwing,
				float interpolatedSwing,
				float uRotfloat,
				float headYaw,
				float interpolatedPitch) {
			return buffer;
		};
	};

	@SuppressWarnings("unchecked")
	public static <T extends EntityLiving> IEntityAnimator<T> STATIC_ENTITY() {
		// Actually safe cast, because T is only in, not out
		return (IEntityAnimator<T>) STATIC_ANIMATOR;
	}

	/**
	 * Pre-render callback for the animator.<br>
	 * This method should, when called, fill the given {@link IRenderPassInformation} with the correct values for the
	 * current call and return it.<br>
	 * Additional OpenGL transformations can be safely done, too (matrix is pushed). E.g. resizing the model, etc...
	 *
	 * @param entity
	 *            the entity being rendered
	 * @param buffer
	 *            an {@link IRenderPassInformation} you can write to
	 * @param subFrame
	 *            the current partial frame
	 * @param uLimbSwing
	 *            the current limb-swing
	 * @param interpolatedSwing
	 *            the interpolated limb-swing
	 * @param uRotfloat
	 *            Unknown, just being passed on
	 * @param headYaw
	 *            the current yaw of the entity
	 * @param interpolatedPitch
	 *            the interpolated pitch
	 * @return the {@link IRenderPassInformation} to use for this pass. Most of the time return the passed in buffer
	 *         after setting your values
	 */
	IRenderPassInformation preRenderCallback(
			T entity,
			RenderPassInformation buffer,
			float partialTick,
			float uLimbSwing,
			float interpolatedSwing,
			float uRotfloat,
			float headYaw,
			float interpolatedPitch);
}
 public interface IEntityRender<T extends EntityLiving> {
	/**
	 * Retrieves the current animator
	 *
	 * @return
	 */
	IEntityAnimator<T> getAnimator();

	/**
	 * Binds a texture
	 */
	void bindTextureFrom(ResourceLocation resLoc);
}
 public interface IRenderPassInformation extends IModelStateInformation {
	/**
	 * Retrieves the texture that should go into the texture slot slot
	 * 
	 * @param slot
	 *            the name of the texture slot getting polled
	 * @return the resource location of the texture to stick
	 */
	ResourceLocation getActualResourceLocation(String slot);
}
 public class ModelAnimated extends ModelBase {
	private IModel model;
	private IRenderPass renderPass;

	/**
	 * This constructor just puts the model into itself. Nothing is checked
	 *
	 * @param model
	 *            the model to render
	 */
	public ModelAnimated(IModel model) {
		this.model = model; // No null-checks, getters could be overridden
		// Useless piece of .... sklsdalsafhkjasd
		// So we don't get problems with arrows in our entity.
		// I want to kill the programmer who thought it would be a good idea
		// not to let the entity decide where to put the arrow
		ModelRenderer argggghhhh = new ModelRenderer(this, 0, 0);
		argggghhhh.addBox(0, 0, 0, 1, 1, 1);
	}

	/**
	 * Renders the underlying model.
	 */
	@Override
	public void render(
			Entity entity,
			float uLimbSwing,
			float interpolatedSwing,
			float uRotfloat,
			float headYaw,
			float interpolatedPitch,
			float size) {
		GlStateManager.pushMatrix();

		getModel().render(renderPass);

		GlStateManager.popMatrix();
	}

	// Will not use this method
	@Override
	public TextureOffset getTextureOffset(String boxName) {
		return new TextureOffset(0, 0);
	}

	/**
	 * The current model is accessed via this getter. If a subclass chooses to override this, the returned model will be
	 * rendered.
	 *
	 * @return
	 */
	protected IModel getModel() {
		return this.model;
	}

	public void setRenderPass(IRenderPass renderPass) {
		this.renderPass = renderPass;
	}
} public class RenderPass<T extends EntityLiving> implements IRenderPass {
	private IRenderPassInformation userInfo;
	private IEntityRender<T> render;

	public RenderPass(IRenderPassInformation info, IEntityRender<T> renderer) {
		this.userInfo = Objects.requireNonNull(info);
		this.render = Objects.requireNonNull(renderer);
	}

	@Override
	public IAnimation getAnimation() {
		return userInfo.getAnimation();
	}

	@Override
	public float getFrame() {
		return userInfo.getFrame();
	}

	@Override
	public boolean shouldRenderPart(String part) {
		return userInfo.shouldRenderPart(part);
	}

	@Override
	public ResourceLocation getActualResourceLocation(String in) {
		return userInfo.getActualResourceLocation(in);
	}

	@Override
	public void bindTexture(ResourceLocation resLoc) {
		this.render.bindTextureFrom(resLoc);
	}

	public RenderPass<T> setRenderPassInformation(IRenderPassInformation info) {
		this.userInfo = Objects.requireNonNull(info);
		return this;
	}
}
 public class RenderPassInformation extends ModelStateInformation implements IRenderPassInformation {
	public static final Function<String, ResourceLocation> makeCachingTransform(
			Function<String, ResourceLocation> cacheLoader) {
		LoadingCache<String, ResourceLocation> cachedResourceLoc = CacheBuilder.newBuilder().maximumSize(100)
				.build(new CacheLoader<String, ResourceLocation>() {
					@Override
					public ResourceLocation load(String key) {
						return cacheLoader.apply(key);
					}
				});
		return cachedResourceLoc::getUnchecked;
	}

	public static final Function<String, ResourceLocation> TRANSFORM_DIRECT = makeCachingTransform(
			ResourceLocation::new);
	/**
	 * This is the default texture rebinding, it just returns the given resource-location and as such does not change
	 * the bound texture.
	 */
	public static final Function<ResourceLocation, ResourceLocation> IDENTITY = Function.identity();

	private Function<String, ResourceLocation> textureRemap;

	public RenderPassInformation() {
		this.reset();
	}

	public RenderPassInformation(
			float frame,
			Optional<IAnimation> animation,
			Optional<Predicate<String>> partPredicate,
			Optional<Function<String, ResourceLocation>> resourceRemap) {
		this.setFrame(frame).setAnimation(animation).setPartPredicate(partPredicate).setTextureTransform(resourceRemap);
	}

	/**
	 * Resets this information to be reused.
	 */
	@Override
	public void reset() {
		super.reset();
		this.setTextureTransform(Optional.empty());
	}

	@Override
	public ResourceLocation getActualResourceLocation(String in) {
		return this.textureRemap.apply(in);
	}

	@Override
	public RenderPassInformation setAnimation(Optional<IAnimation> animation) {
		super.setAnimation(animation);
		return this;
	}

	@Override
	public RenderPassInformation setAnimation(IAnimation animation) {
		super.setAnimation(animation);
		return this;
	}

	/**
	 * @param frame
	 *            the frame to set
	 */
	@Override
	public RenderPassInformation setFrame(float frame) {
		super.setFrame(frame);
		return this;
	}

	/**
	 * @param partPredicate
	 *            the partPredicate to set, Optional.empty() for RENDER_ALL
	 */
	@Override
	public RenderPassInformation setPartPredicate(Optional<Predicate<String>> partPredicate) {
		super.setPartPredicate(partPredicate);
		return this;
	}

	@Override
	public RenderPassInformation setPartPredicate(Predicate<String> partPredicate) {
		super.setPartPredicate(partPredicate);
		return this;
	}

	public RenderPassInformation setTextureTransform(Optional<Function<String, ResourceLocation>> textureRemap) {
		return setTextureTransform(textureRemap.orElse(TRANSFORM_DIRECT));
	}

	public RenderPassInformation setTextureTransform(Function<String, ResourceLocation> textureRemap) {
		this.textureRemap = Objects.requireNonNull(textureRemap);
		return this;
	}
}
 public interface IAnimatedObject {
	/**
	 * An animator that can be used in
	 * {@link RenderAnimatedModel#fromResLocation(IEntityAnimator, ResourceLocation, ISkeleton, float)} when the
	 * animated entity implements the {@link IAnimatedObject} interface.
	 */
	public static <T extends EntityLiving & IAnimatedObject> IEntityAnimator<T> ANIMATOR_ADAPTER() {
		return new IEntityAnimator<T>() {
			@Override
			public IRenderPassInformation preRenderCallback(
					T entity,
					RenderPassInformation buffer,
					float partialTick,
					float uLimbSwing,
					float interpolatedSwing,
					float uRotfloat,
					float headYaw,
					float interpolatedPitch) {
				return IAnimatedObject.class.cast(entity).preRenderCallback(partialTick, buffer);
			}
		};
	}

	/**
	 * A callback to the animated object just before it is rendered. The method is always called BEFORE. The object
	 * should setup and return the {@link RenderPassInformation} given as callback (never null).
	 *
	 * @param subFrame
	 *            the current subFrame (subTick)
	 * @param callback
	 *            a {@link RenderPassInformation} to prepare
	 * @return A {@link RenderPassInformation} to use in the current pass, not null
	 */
	public RenderPassInformation preRenderCallback(float subFrame, RenderPassInformation callback);
} public interface ISkeleton {
	public static final ISkeleton EMPTY = new ISkeleton() {

		@Override
		public void setup(IAnimation animation, float frame) {}

		@Override
		public IBone getBoneByName(String bone) {
			return IBone.STATIC_BONE;
		}

		@Override
		public IBone getBoneByIndex(int index) {
			return IBone.STATIC_BONE;
		}

		@Override
		public void debugDraw(Tessellator tess) {}
	};

	IBone getBoneByName(String bone);

	IBone getBoneByIndex(int index);

	/**
	 * Sets up the Skeleton for the animation given
	 */
	void setup(IAnimation animation, float frame);

	/**
	 * Added for debug, don't actually use this, especially when on the server
	 * 
	 * @param tess
	 */
	void debugDraw(Tessellator tess);

	@Override
	boolean equals(Object obj);

	@Override
	int hashCode();
}
import com.github.worldsender.mcanm.client.ClientLoader;
import com.github.worldsender.mcanm.client.mcanmmodel.IModel;
import com.github.worldsender.mcanm.client.model.IEntityAnimator;
import com.github.worldsender.mcanm.client.model.IEntityRender;
import com.github.worldsender.mcanm.client.model.IRenderPassInformation;
import com.github.worldsender.mcanm.client.model.ModelAnimated;
import com.github.worldsender.mcanm.client.model.util.RenderPass;
import com.github.worldsender.mcanm.client.model.util.RenderPassInformation;
import com.github.worldsender.mcanm.client.renderer.IAnimatedObject;
import com.github.worldsender.mcanm.common.skeleton.ISkeleton;
import net.minecraft.client.renderer.GlStateManager;
import net.minecraft.client.renderer.entity.RenderLiving;
import net.minecraft.client.renderer.entity.RenderManager;
import net.minecraft.client.resources.DefaultPlayerSkin;
import net.minecraft.entity.EntityLiving;
import net.minecraft.util.ResourceLocation;
import net.minecraftforge.fml.client.registry.IRenderFactory;
package com.github.worldsender.mcanm.client.renderer.entity;



public class RenderAnimatedModel<T extends EntityLiving> extends RenderLiving<T> implements IEntityRender<T> {
	private static final ResourceLocation UNUSED_TEXTURE = DefaultPlayerSkin.getDefaultSkinLegacy();
	protected ModelAnimated model;
	private IEntityAnimator<T> animator;

	private RenderPassInformation userPassCache = new RenderPassInformation();