package appeng.block.paint; import java.util.ArrayList; import java.util.Collections; import java.util.List; import javax.annotation.Nullable; import com.google.common.base.Function; import com.google.common.collect.ImmutableList; import net.minecraft.block.state.IBlockState; import net.minecraft.client.renderer.block.model.BakedQuad; import net.minecraft.client.renderer.block.model.IBakedModel; import net.minecraft.client.renderer.block.model.ItemCameraTransforms; import net.minecraft.client.renderer.block.model.ItemOverrideList; import net.minecraft.client.renderer.texture.TextureAtlasSprite; import net.minecraft.client.renderer.vertex.VertexFormat; import net.minecraft.util.EnumFacing; import net.minecraft.util.ResourceLocation; import net.minecraftforge.common.property.IExtendedBlockState; import appeng.client.render.cablebus.CubeBuilder; import appeng.core.AppEng; import appeng.helpers.Splotch; /** * Renders paint blocks, which render multiple "splotches" that have been applied to the sides of adjacent blocks using a * matter cannon with paint balls. */ class PaintBakedModel implements IBakedModel { private static final ResourceLocation TEXTURE_PAINT1 = new ResourceLocation( AppEng.MOD_ID, "blocks/paint1" ); private static final ResourceLocation TEXTURE_PAINT2 = new ResourceLocation( AppEng.MOD_ID, "blocks/paint2" ); private static final ResourceLocation TEXTURE_PAINT3 = new ResourceLocation( AppEng.MOD_ID, "blocks/paint3" ); private final VertexFormat vertexFormat; private final TextureAtlasSprite[] textures; PaintBakedModel( VertexFormat vertexFormat, Function<ResourceLocation, TextureAtlasSprite> bakedTextureGetter ) { this.vertexFormat = vertexFormat; this.textures = new TextureAtlasSprite[] { bakedTextureGetter.apply( TEXTURE_PAINT1 ), bakedTextureGetter.apply( TEXTURE_PAINT2 ), bakedTextureGetter.apply( TEXTURE_PAINT3 ) }; } @Override public List<BakedQuad> getQuads( @Nullable IBlockState state, @Nullable EnumFacing side, long rand ) { if( side != null ) { return Collections.emptyList(); } if( !( state instanceof IExtendedBlockState ) ) { // This is the inventory model which should usually not be used other than in special cases List<BakedQuad> quads = new ArrayList<>( 1 ); CubeBuilder builder = new CubeBuilder( this.vertexFormat, quads ); builder.setTexture( textures[0] ); builder.addCube( 0, 0, 0, 16, 16, 16 ); return quads; } IExtendedBlockState extendedBlockState = (IExtendedBlockState) state; PaintSplotches splotchesState = extendedBlockState.getValue( BlockPaint.SPLOTCHES ); if( splotchesState == null ) { return Collections.emptyList(); } List<Splotch> splotches = splotchesState.getSplotches(); CubeBuilder builder = new CubeBuilder( vertexFormat ); float offsetConstant = 0.001f; for( final Splotch s : splotches) { if( s.isLumen() ) { builder.setColorRGB( s.getColor().whiteVariant ); builder.setRenderFullBright( true ); } else { builder.setColorRGB( s.getColor().mediumVariant ); builder.setRenderFullBright( false ); } float offset = offsetConstant; offsetConstant += 0.001f; final float buffer = 0.1f; float pos_x = s.x(); float pos_y = s.y(); pos_x = Math.max( buffer, Math.min( 1.0f - buffer, pos_x ) ); pos_y = Math.max( buffer, Math.min( 1.0f - buffer, pos_y ) ); TextureAtlasSprite ico = textures[s.getSeed() % textures.length]; builder.setTexture( ico ); builder.setCustomUv( s.getSide().getOpposite(), 0, 0, 16, 16 ); switch( s.getSide() ) { case UP: offset = 1.0f - offset; builder.addQuad( EnumFacing.DOWN, pos_x - buffer, offset, pos_y - buffer, pos_x + buffer, offset, pos_y + buffer ); break; case DOWN: builder.addQuad( EnumFacing.UP, pos_x - buffer, offset, pos_y - buffer, pos_x + buffer, offset, pos_y + buffer ); break; case EAST: offset = 1.0f - offset; builder.addQuad( EnumFacing.WEST, offset, pos_x - buffer, pos_y - buffer, offset, pos_x + buffer, pos_y + buffer ); break; case WEST: builder.addQuad( EnumFacing.EAST, offset, pos_x - buffer, pos_y - buffer, offset, pos_x + buffer, pos_y + buffer ); break; case SOUTH: offset = 1.0f - offset; builder.addQuad( EnumFacing.NORTH, pos_x - buffer, pos_y - buffer, offset, pos_x + buffer, pos_y + buffer, offset ); break; case NORTH: builder.addQuad( EnumFacing.SOUTH, pos_x - buffer, pos_y - buffer, offset, pos_x + buffer, pos_y + buffer, offset ); break; default: } } return builder.getOutput(); } @Override public boolean isAmbientOcclusion() { return false; } @Override public boolean isGui3d() { return true; } @Override public boolean isBuiltInRenderer() { return false; } @Override public TextureAtlasSprite getParticleTexture() { return textures[0]; } @Override public ItemCameraTransforms getItemCameraTransforms() { return ItemCameraTransforms.DEFAULT; } @Override public ItemOverrideList getOverrides() { return ItemOverrideList.NONE; } static List<ResourceLocation> getRequiredTextures() { return ImmutableList.of( TEXTURE_PAINT1, TEXTURE_PAINT2, TEXTURE_PAINT3 ); } }