PianoManu
Members-
Posts
31 -
Joined
-
Last visited
Everything posted by PianoManu
-
Hey, thanks for your reply! I've read your text several times and I'm beginning to understand, but I've never worked with the FaceBakery before, so I don't have any experiences with that. Do I have to rewrite the whole baked model class to extend the FaceBakery instead of implementing IDynamicBakedModel? I've looked through the FaceBakery class and the IVertexBuilder, but I have no clue where to begin with... Maybe you could give me a hint? Or do I have to rewrite everything at all? Also, where is this code part from? I couldn't find anything on Google, when I searched for "getQuadForDigit". I ask because maybe I could get some more information from the context of the code Thank you for your help!
-
Hey guys! I created a block (slab, to be axact), that takes on the texture of the block it is clicked on. For that I used Baked Models. Now nearly everything works fine, but the slab texture (when covered by a block) is way too dark (see attached pictures), as if the light level was zero. As you can see in the first picture, it works well for the json-block-model, when the slab does not contain any block (oak planks texture). So I guess the problem is somewhere in the baked model, but I can't figure it out. Here's the code for my BakedModel-Class extending IDynamicBakedModel: getQuads (Overrides interface method) public List<BakedQuad> getQuads(@Nullable BlockState state, @Nullable Direction side, @Nonnull Random rand, @Nonnull IModelData extraData) { //get block saved in slab's tile entity BlockState mimic = extraData.getData(FrameBlockTile.MIMIC); //check if not empty if (mimic != null && !(mimic.getBlock() instanceof FrameBlock)) { //location of BlockModel ModelResourceLocation location = BlockModelShapes.getModelLocation(mimic); if (location != null) { IBakedModel model = Minecraft.getInstance().getModelManager().getModel(location); model.getBakedModel().getQuads(mimic, side, rand, extraData); if (model != null) { //new quad-model with data from slab return getMimicQuads(mimic, side, rand, extraData); } } } return Collections.emptyList(); the called method "getMimicQuads": public List<BakedQuad> getMimicQuads(@Nullable BlockState state, @Nullable Direction side, @Nonnull Random rand, @Nonnull IModelData extraData) { if (side != null) { return Collections.emptyList(); } BlockState mimic = extraData.getData(FrameBlockTile.MIMIC); if (mimic!=null) { //get texture from block saved in slab TextureAtlasSprite texture = Minecraft.getInstance().getAtlasSpriteGetter(AtlasTexture.LOCATION_BLOCKS_TEXTURE).apply(new ResourceLocation(mimic.getBlock().getRegistryName().getNamespace(), "block/"+mimic.getBlock().getRegistryName().getPath())); List<BakedQuad> quads = new ArrayList<>(); //create 6 faces of slab //down quads.add(createQuad(v(1, 0, 0), v(1, 0, 1), v(0, 0, 1), v(0, 0, 0), texture)); //up quads.add(createQuad(v(0, 0.5, 0), v(0, 0.5, 1), v(1, 0.5, 1), v(1, 0.5, 0), texture)); //sides quads.add(createHalfQuad(v(0, 0, 0), v(0, 0, 1), v(0, 0.5, 1), v(0, 0.5, 0), texture)); quads.add(createHalfQuad(v(0, 0, 0), v(0, 0.5, 0), v(1, 0.5, 0), v(1, 0, 0), texture)); quads.add(createHalfQuad(v(0, 0, 1), v(1, 0, 1), v(1, 0.5, 1), v(0, 0.5, 1), texture)); quads.add(createHalfQuad(v(1, 0.5, 0), v(1, 0.5, 1), v(1, 0, 1), v(1, 0, 0), texture)); return quads; } return Collections.emptyList(); } the called createQuad and createHalfQuad methods: //for squared part of slab (top and bottom side) private BakedQuad createQuad(Vec3d v1, Vec3d v2, Vec3d v3, Vec3d v4, TextureAtlasSprite sprite) { Vec3d normal = v3.subtract(v2).crossProduct(v1.subtract(v2)).normalize(); BakedQuadBuilder builder = new BakedQuadBuilder(sprite); builder.setQuadOrientation(Direction.getFacingFromVector(normal.x, normal.y, normal.z)); putVertex(builder, normal, v1.x, v1.y, v1.z, 0, 0, sprite, 1.0f, 1.0f, 1.0f); putVertex(builder, normal, v2.x, v2.y, v2.z, 0, 16, sprite, 1.0f, 1.0f, 1.0f); putVertex(builder, normal, v3.x, v3.y, v3.z, 16, 16, sprite, 1.0f, 1.0f, 1.0f); putVertex(builder, normal, v4.x, v4.y, v4.z, 16, 0, sprite, 1.0f, 1.0f, 1.0f); return builder.build(); } //for rectangles (sides of slab) private BakedQuad createHalfQuad(Vec3d v1, Vec3d v2, Vec3d v3, Vec3d v4, TextureAtlasSprite sprite) { Vec3d normal = v3.subtract(v2).crossProduct(v1.subtract(v2)).normalize(); BakedQuadBuilder builder = new BakedQuadBuilder(sprite); builder.setQuadOrientation(Direction.getFacingFromVector(normal.x, normal.y, normal.z)); putVertex(builder, normal, v1.x, v1.y, v1.z, 0, 0, sprite, 1.0f, 1.0f, 1.0f); putVertex(builder, normal, v2.x, v2.y, v2.z, 0, 8, sprite, 1.0f, 1.0f, 1.0f); putVertex(builder, normal, v3.x, v3.y, v3.z, 16, 8, sprite, 1.0f, 1.0f, 1.0f); putVertex(builder, normal, v4.x, v4.y, v4.z, 16, 0, sprite, 1.0f, 1.0f, 1.0f); return builder.build(); } and the putVertex-method for creating the vertices: private void putVertex(BakedQuadBuilder builder, Vec3d normal, double x, double y, double z, float u, float v, TextureAtlasSprite sprite, float r, float g, float b) { ImmutableList<VertexFormatElement> elements = builder.getVertexFormat().getElements().asList(); for (int j = 0 ; j < elements.size() ; j++) { VertexFormatElement e = elements.get(j); switch (e.getUsage()) { case POSITION: builder.put(j, (float) x, (float) y, (float) z, 1.0f); break; case COLOR: builder.put(j, r, g, b, 1.0f); break; case UV: switch (e.getIndex()) { case 0: float iu = sprite.getInterpolatedU(u); float iv = sprite.getInterpolatedV(v); builder.put(j, iu, iv); break; case 2: builder.put(j, 0f, 1f); break; default: builder.put(j); break; } break; case NORMAL: builder.put(j, (float) normal.x, (float) normal.y, (float) normal.z); break; default: builder.put(j); break; } } } Ambient Occlusion is set to true (I read, that this might be the reason, but when I toggled it multiple times nothing really changed) Gui3d and BuildInRenderer both return false As I said, the texture is too dark, like if the light level was zero and I want to fix that. I really don't know what to do anymore. Any help is appreciated. Thanks in advance (I hope you understand, what I was trying to say, english is not my native language) Kind Regards, Manu
-
How do I assign a model to a block based on its state?
PianoManu replied to PianoManu's topic in Modder Support
Oh.. Okay, thank you very much. I'll try this! Have a nice day and thanks for telling me ? -
Hey guys! I want to make something like a coverable block, that get's a texture depending on its blockstate. For that I already made a class CoverableBlock with a Property "BlockContainerProperty" extending Property<String>. The BlockContainerProperty could take every possible block (see code below), and it already works with a block of the CoverableBlock-class. So for example, if the property of the block is set to "diamond ore", it will look like diamond ore. Well, I know the basics of JSON-blockmodels and that I could manually make these models, but then I would have to create tons of similar json-files (all just differing in textures) and I guess it wouldn't work with blocks from other mods. So my question is: Is it possible that the block takes the texture of the block that is saved as a String in its property? And then how do I create the json block-models for that? I'm using Minecraft 1.15 and forge 29.0.4. Code for the BlockContainerPropertyClass: The constructor is to get all blocks from the IForgeRegistry and save them as strings in a list BLOCKS_TO_STRING public class BlockContainerProperty extends Property<String> { private static final IForgeRegistry<Block> BLOCKS = RegistryManager.ACTIVE.getRegistry(Block.class); private static List<String> BLOCKS_TO_STRING; protected BlockContainerProperty(String name) { super(name, String.class); BLOCKS_TO_STRING = new ArrayList<>(); BLOCKS_TO_STRING.add("empty"); for (Block b: BLOCKS) { BLOCKS_TO_STRING.add(Objects.requireNonNull(b.getRegistryName()).getPath().toLowerCase()); } } @Override public Collection<String> getAllowedValues() { return BLOCKS_TO_STRING; } @Override public Optional<String> parseValue(String value) { if(this.getAllowedValues().contains(value)) { return Optional.of(value); } return Optional.empty(); } @Override public String getName(String value) { return value; } public static BlockContainerProperty create(String name) { return new BlockContainerProperty(name); } } The code for the CoverableBlock - Class: public class CoverableBlock extends Block { public static final BlockContainerProperty CONTAINS = BCBlockStateProperties.CONTAINS; public CoverableBlock(Properties properties) { super(properties); this.setDefaultState(this.getDefaultState().with(CONTAINS,"empty")); } @Override protected void fillStateContainer(StateContainer.Builder<Block, BlockState> builder) { builder.add(CONTAINS); } } And the code for BCBlockStateProperties is just this one line, so the Property is shown as "contains:" and then the block: public static final BlockContainerProperty CONTAINS = BlockContainerProperty.create("contains"); And finally this is, how I register the block: public class BCBlocks { private static final Logger LOGGER = LogManager.getLogger(); @Mod.EventBusSubscriber(bus = Mod.EventBusSubscriber.Bus.MOD) @ObjectHolder(BlockCarpentryMain.MOD_ID) public static class RegistryEvents { @SubscribeEvent public static void onRegisterBlocks(RegistryEvent.Register<Block> event) { event.getRegistry().registerAll( setup(BCBlockList.coverableBlock = new CoverableBlock(CoverableBlock.Properties.create(Material.WOOD, MaterialColor.WOOD).harvestTool(ToolType.AXE).harvestLevel(0).hardnessAndResistance(0.4f).sound(SoundType.WOOD)), "coverable_block") ); LOGGER.info("Registered all blocks from BlockCarpentry"); } public static <T extends IForgeRegistryEntry<T>> T setup(final T entry, final String name) { return setup(entry, new ResourceLocation(BlockCarpentryMain.MOD_ID, name)); } public static <T extends IForgeRegistryEntry<T>> T setup(final T entry, final ResourceLocation registryName) { entry.setRegistryName(registryName); return entry; } } } I would be very glad, if you could teach me, how to get the block to display the texture of the block that is saved as a string in its property. Sorry for bad english and grammatical errors, I've tried my best. Thanks for help in advance! ? P.S.: If you're wondering what the purpose of that is: Since "Carpenters Blocks" is not yet available for 1.15 and I still want to play the mod with friends, I try to create something similar and this is just the base.
-
Nevermind, I found a solution. I made a class with a setup() method (which I call in my main class) that uses the BiomeManager.addBiome-function and it works now public static void setup() { for(Biome biome : ForgeRegistries.BIOMES) { BiomeManager.addBiome(BiomeManager.BiomeType.WARM, new BiomeManager.BiomeEntry(BiomesList.WET_FOREST_BIOME, 20)); BiomeManager.addSpawnBiome(BiomesList.WET_FOREST_BIOME); BiomeProvider.BIOMES_TO_SPAWN_IN.add(BiomesList.WET_FOREST_BIOME); } } Thanks Y'all, see you
-
(Sorry for bad english) Hey guys, I'm new here, please be lenient with me if I say something stupid. I'm currently working on a custom biome. In the Buffet-worldtype, I can choose my biome and it already works as I want. The only problem is, that it does not generate in the "default" world type. I'm pretty sure about that, because I made it generate the EndCity-structure in said biome, which I can find via /locate in the "Buffet-world", but I cannot find it in the "Default-world". This is my custom biomes' class: public class WetForestBiome extends WoodsBiome { public WetForestBiome() { super((new Biome.Builder()).surfaceBuilder(new ConfiguredSurfaceBuilder<SurfaceBuilderConfig>(SurfaceBuilder.DEFAULT, new SurfaceBuilderConfig(Blocks.GRASS_BLOCK.getDefaultState(), Blocks.DIRT.getDefaultState(), Blocks.DIRT.getDefaultState()))).precipitation(Biome.RainType.RAIN).category(Biome.Category.FOREST).depth(-0.05F).scale(0.1F).temperature(0.7F).downfall(0.8F).waterColor(0x007a49).waterFogColor(0x007a49).parent("forest")); this.addStructure(Feature.END_CITY, IFeatureConfig.NO_FEATURE_CONFIG); //some irrelevant this.addSpawn() and DefaultBiomeFeature features This is the class above my custom biome (not sure how to say it in english) public class WoodsBiome extends Biome { protected WoodsBiome(Builder biomeBuilder) { super(biomeBuilder); } public boolean doesMossGenerate(IWorldReader worldIn, BlockPos pos) { //I don't think this function is relevant for my problem but I'll leave it here ^^ if (this.func_225486_c(pos) >= 0.15F) { return false; } else { BlockState blockstate = worldIn.getBlockState(pos); if (blockstate.isAir(worldIn, pos) && BlockList.moss.getDefaultState().isValidPosition(worldIn, pos)) { return true; } return true; } } } And this is my biomes class, where the biome is registered: @net.minecraftforge.registries.ObjectHolder(WoodsMain.MOD_ID) public class Biomes { public static Biome WET_FOREST_BIOME = new WetForestBiome(); public static void registerBiomes() { registerBiome(WET_FOREST_BIOME, Type.FOREST); } public static void registerBiome(Biome biome, Type...types) { BiomeDictionary.addTypes(biome, types); BiomeManager.addSpawnBiome(biome); } static { Collections.addAll(Biome.BIOMES, WET_FOREST_BIOME); } } As I said, it completely works in Buffet-mode. How can I make it to be generated in normal Minecraft-worlds? Do you need any more files/classes? Many thanks in advance for your effort Best regards, Manu Edit: forgot to say I'm using Forge 28.1.107 for Minecraft 1.14.4