Jump to content

[1.16.5] How to render texture like a nameplate?


Zemelua

Recommended Posts

I want to draw a texture on a black background as well as a nameplate. However, there are issues such as not being visible across blocks and entities. Therefore, I would like to refer to RenderSystem and bufferBuilder for rendering nameplates. But if you follow the code, it's very complicated and unclear. Where in the code is the RenderSystem, bufferBuilder for rendering nameplates?

Link to comment
Share on other sites

double d0 = entityRenderer.getRenderManager().squareDistanceTo(entity);
		if (net.minecraftforge.client.ForgeHooksClient.isNameplateInRenderDistance(entity, d0) && this.minecraft.pointedEntity == entity) {
			this.profiler.startSection("otherHealth");
			matrixStack.push();
			matrixStack.translate(0.0D, entity.getHeight() + 0.5F, 0.0D);
			matrixStack.rotate(entityRenderer.getRenderManager().getCameraOrientation());
			matrixStack.scale(-0.025F, -0.025F, 0.025F);

			RenderSystem.enableBlend();
			RenderSystem.disableDepthTest();
			RenderSystem.disableAlphaTest();

			int health    = MathHelper.ceil(entity.getHealth());
			int maxHealth = MathHelper.ceil(entity.getMaxHealth());
			int absorb    = MathHelper.ceil(entity.getAbsorptionAmount());
			int rowCount = (int) Math.ceil(health / 20D) - 1;
			int hideHealth = Math.max(rowCount * 20, 0);
			int hideAbsorb = Math.max((int) Math.ceil(absorb / 20D) - 1, 0);
			ITextComponent rowText = new StringTextComponent("x" + rowCount);
			String amountString = String.valueOf(health);
			if (absorb > 0) amountString = amountString + "+" + absorb;
			amountString = amountString + "/" + maxHealth;
			ITextComponent amountText = new StringTextComponent(amountString);
			int xStart = - (81 + 5 + this.minecraft.fontRenderer.getStringPropertyWidth(amountText)) / 2;

			int BACKGROUND_X_DRAW_START   = xStart; int BACKGROUND_X_DRAW_END     = -xStart;
			int ICONS_X_DRAW              = xStart; int ICONS_Y_DRAW              =       0;
			int ICONS_BACKGROUND_U_OFFSET =     51; int ICONS_BACKGROUND_V_OFFSET =       0;
			int ICONS_BACKGROUND_U_SIZE   =      9; int ICONS_BACKGROUND_V_SIZE   =       9;
			int ICONS_FOREGROUND_U_OFFSET =     87; int ICONS_FOREGROUND_V_OFFSET =       0;
			int ICONS_FOREGROUND_U_SIZE   =      9; int ICONS_FOREGROUND_V_SIZE   =       9;
			int ICONS_ABSORB_U_OFFSET     =    195; int ICONS_ABSORB_V_OFFSET     =       0;
			int ICONS_ABSORB_U_SIZE       =      9; int ICONS_ABSORB_V_SIZE       =       9;
			int TEXT_X_DRAW               = xStart + 81 + 5; int TEXT_Y_DRAW      =       0;

			this.minecraft.getTextureManager().bindTexture(UMUClientIngameGUI.GUI_ICONS_LOCATION);

			float color = Minecraft.getInstance().gameSettings.getTextBackgroundOpacity(0.25F);
			Color4f color4f = Color4f.fromInt((int) (color * 255.0F) << 24);
			float red = color4f.getRed();
			float green = color4f.getGreen();
			float blue = color4f.getBlue();
			float alpha = color4f.getAlpha();

			Matrix4f matrix = matrixStack.getLast().getMatrix();
			Tessellator tessellator = Tessellator.getInstance();
			BufferBuilder buffer = tessellator.getBuffer();

			RenderSystem.disableTexture();

			buffer.begin(7, DefaultVertexFormats.POSITION_COLOR);
			buffer.pos(matrix, BACKGROUND_X_DRAW_START - 2.0F, 10.0F, 0.01F).color(red, green, blue, alpha).endVertex();
			buffer.pos(matrix, BACKGROUND_X_DRAW_END + 2.0F, 10.0F, 0.01F).color(red, green, blue, alpha).endVertex();
			buffer.pos(matrix, BACKGROUND_X_DRAW_END + 2.0F, -2.0F, 0.01F).color(red, green, blue, alpha).endVertex();
			buffer.pos(matrix, BACKGROUND_X_DRAW_START - 2.0F, -2.0F, 0.01F).color(red, green, blue, alpha).endVertex();
			tessellator.draw();

			RenderSystem.enableTexture();

			for (int i = 0; i < 10; i++) {
				int iconHealth = health - hideHealth - i * 2;
				int iconAbsorb = absorb - hideAbsorb - i * 2;

				int ICON_X_DRAW = ICONS_X_DRAW + i * 8;
				int ICON_BACKGROUND_U_OFFSET = ICONS_BACKGROUND_U_OFFSET;
				int ICON_FOREGROUND_U_OFFSET = ICONS_FOREGROUND_U_OFFSET;
				int ICON_ABSORB_U_OFFSET = ICONS_ABSORB_U_OFFSET;

				if (!(maxHealth - hideHealth - i * 2 > 0)) ICON_BACKGROUND_U_OFFSET = 999;
				if (iconHealth > 0) {
					if (iconHealth <= 1) ICON_FOREGROUND_U_OFFSET += 9;
				} else {
					ICON_FOREGROUND_U_OFFSET = 999;
				}
				if (iconAbsorb > 0) {
					if (iconAbsorb <= 1) ICON_ABSORB_U_OFFSET += 9;
				} else {
					ICON_ABSORB_U_OFFSET = 999;
				}

				this.blit(matrixStack, ICON_X_DRAW, ICONS_Y_DRAW, ICON_BACKGROUND_U_OFFSET, ICONS_BACKGROUND_V_OFFSET, ICONS_BACKGROUND_U_SIZE, ICONS_BACKGROUND_V_SIZE);
				this.blit(matrixStack, ICON_X_DRAW, ICONS_Y_DRAW, ICON_FOREGROUND_U_OFFSET, ICONS_FOREGROUND_V_OFFSET, ICONS_FOREGROUND_U_SIZE, ICONS_FOREGROUND_V_SIZE);
				this.blit(matrixStack, ICON_X_DRAW, ICONS_Y_DRAW, ICON_ABSORB_U_OFFSET,     ICONS_ABSORB_V_OFFSET,     ICONS_ABSORB_U_SIZE,     ICONS_ABSORB_V_SIZE    );

			}
			if (rowCount != 0) {
				this.minecraft.fontRenderer.drawText(matrixStack, rowText, TEXT_X_DRAW, TEXT_Y_DRAW, WHITE);
				TEXT_X_DRAW += (this.minecraft.fontRenderer.getStringPropertyWidth(rowText) + 5);
			}
			this.minecraft.fontRenderer.drawText(matrixStack, amountText, TEXT_X_DRAW, TEXT_Y_DRAW, WHITE);

			matrixStack.pop();

			this.profiler.endSection();
		}
	

It is now also visible through blocks. However, there are still two problems.

1. When there is water or clouds behind, the rendered texture will appear to be below the water or clouds.
2. It is displayed through the block, but unlike the nameplate, the color does not darken.

Link to comment
Share on other sites

This isn't quite right.

Quote

			float color = Minecraft.getInstance().gameSettings.getTextBackgroundOpacity(0.25F);
			Color4f color4f = Color4f.fromInt((int) (color * 255.0F) << 24);
			float red = color4f.getRed();
			float green = color4f.getGreen();
			float blue = color4f.getBlue();
			float alpha = color4f.getAlpha();

 

            int color = (int) (Minecraft.getInstance().gameSettings.getTextBackgroundOpacity(0.25F) * 255.0F) << 24;
            float alpha = (float)(color >> 24 & 255) / 255.0F;
            float red = (float)(color >> 16 & 255) / 255.0F;
            float green = (float)(color >> 8 & 255) / 255.0F;
            float blue = (float)(color & 255) / 255.0F;

check EntityRenderer L97, 98, and FontRenderer#func_238441_a_ (finish)

Link to comment
Share on other sites

I know I should refer to FontRenderer#func_238441_a_, but it's complicated to dig deeper the code. This method draws both background and text. The background is probably drawn with TrenderEffect#renderEffect(FontRenderer: L344), but I don't know where the letters are drawn.

Link to comment
Share on other sites

43 minutes ago, Zemelua said:

I know I should refer to FontRenderer#func_238441_a_, but it's complicated to dig deeper the code. This method draws both background and text. The background is probably drawn with TrenderEffect#renderEffect(FontRenderer: L344), but I don't know where the letters are drawn.

Just change your code to the code I attached, I've tested it that it worked. Play around with it and should be easier for you to understand.

Link to comment
Share on other sites

Color4f is my class, but what I'm doing is the same as the code provided. Replacing it didn't change anything. The problem I'm having is the image below ("Name Ta" is the nameplate).

1st picture: If there is water behind, it will be rendered overlapping with the water. The nameplate is darker through the entity, while the texture isn't (it looks a bit darker, because the nameplate background overlaps).

2nd picture: The texture is not darkened through the block.

987094557_(87).png.be8adaf880987a338315c2a4355c6198.png475261521_(88).png.7fdb90985e5800522e3f004276ad9060.png

Edited by Zemelua
Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Announcements



×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.